import { normalizeText, nowIso, wrapModeBWorkflowStream } from './helpers.js';
import { runtimeGenerateText, runtimeStreamText, runtimeGenerateEmbedding, } from './runtime-ai-text.js';
import { FallbackPolicy } from './generated/runtime/v1/ai.js';
import { runtimeSubmitScenarioJobForMedia, runtimeGetScenarioJobForMedia, runtimeCancelScenarioJobForMedia, runtimeSubscribeScenarioJobForMedia, runtimeGetScenarioArtifactsForMedia, } from './runtime-media.js';
import { runtimeGenerateImage, runtimeGenerateVideo, runtimeGenerateMusicIteration, runtimeGenerateMusic, runtimeSynthesizeSpeech, runtimeTranscribeSpeech, runtimeStreamImage, runtimeStreamVideo, runtimeStreamSpeech, runtimeListSpeechVoices, } from './runtime-modality.js';
import { runtimeAiRequestRequiresSubject } from './runtime-guards.js';
let runtimeAiUploadModulePromise = null;
function loadRuntimeAiUploadModule() {
    if (!runtimeAiUploadModulePromise) {
        runtimeAiUploadModulePromise = import('./runtime-ai-upload.js');
    }
    return runtimeAiUploadModulePromise;
}
const AUTH_METHODS = [
    'registerApp',
    'openSession',
    'refreshSession',
    'revokeSession',
    'registerExternalPrincipal',
    'openExternalPrincipalSession',
    'revokeExternalPrincipalSession',
];
const ACCOUNT_METHODS = [
    'getAccountSessionStatus',
    'beginLogin',
    'completeLogin',
    'getAccessToken',
    'refreshAccountSession',
    'logout',
    'switchAccount',
    'issueScopedAppBinding',
    'revokeScopedAppBinding',
    'issueWorkspaceBinding',
    'revokeWorkspaceBinding',
];
const MODEL_METHODS = [
    'list',
    'pull',
    'remove',
    'checkHealth',
];
const LOCAL_METHODS = [
    'listLocalAssets',
    'listVerifiedAssets',
    'searchCatalogModels',
    'resolveModelInstallPlan',
    'installVerifiedAsset',
    'importLocalAsset',
    'importLocalAssetFile',
    'scanUnregisteredAssets',
    'scaffoldOrphanAsset',
    'removeLocalAsset',
    'startLocalAsset',
    'stopLocalAsset',
    'checkLocalAssetHealth',
    'warmLocalAsset',
    'listLocalTransfers',
    'pauseLocalTransfer',
    'resumeLocalTransfer',
    'cancelLocalTransfer',
    'resolveLocalEnvironmentPlan',
    'listLocalEnvironmentSelectedSources',
    'listLocalEnvironmentDependencyJobs',
    'resolveLocalEnvironmentActivationGate',
    'mintRuntimeBaselineReadiness',
    'resolveRuntimeBaselineReadiness',
    'mintFirstRunExecutionEvidence',
    'resolveFirstRunExecutionEvidence',
    'startLocalEnvironmentDependencyJob',
    'cancelLocalEnvironmentDependencyJob',
    'retryLocalEnvironmentDependencyJob',
    'repairLocalEnvironmentDependency',
    'resolveLocalStateReconciliation',
    'executeLocalStateCutover',
    'collectDeviceProfile',
    'resolveProfile',
    'applyProfile',
    'listLocalServices',
    'installLocalService',
    'startLocalService',
    'stopLocalService',
    'checkLocalServiceHealth',
    'removeLocalService',
    'listNodeCatalog',
    'listLocalAudits',
    'appendInferenceAudit',
    'appendRuntimeAudit',
    'listEngines',
    'ensureEngine',
    'startEngine',
    'stopEngine',
    'getEngineStatus',
];
const CONNECTOR_METHODS = [
    'createConnector',
    'getConnector',
    'listConnectors',
    'updateConnector',
    'deleteConnector',
    'testConnector',
    'listConnectorModels',
    'listProviderCatalog',
    'listModelCatalogProviders',
    'listCatalogProviderModels',
    'getCatalogModelDetail',
    'upsertModelCatalogProvider',
    'deleteModelCatalogProvider',
    'upsertCatalogModelOverlay',
    'deleteCatalogModelOverlay',
];
const KNOWLEDGE_METHODS = [
    'createKnowledgeBank',
    'getKnowledgeBank',
    'listKnowledgeBanks',
    'deleteKnowledgeBank',
    'putPage',
    'getPage',
    'listPages',
    'deletePage',
    'searchKeyword',
    'searchHybrid',
    'addLink',
    'removeLink',
    'listLinks',
    'listBacklinks',
    'traverseGraph',
    'ingestDocument',
    'getIngestTask',
];
const MEMORY_METHODS = [
    'createBank',
    'getBank',
    'listBanks',
    'deleteBank',
    'retain',
    'recall',
    'history',
    'deleteMemory',
    'subscribeEvents',
];
const AGENT_METHODS = [
    'initializeAgent',
    'terminateAgent',
    'getAgent',
    'listAgents',
    'openConversationAnchor',
    'getConversationAnchorSnapshot',
    'registerAvatarLiveInstanceBinding',
    'resolveAvatarLiveInstanceBinding',
    'getPublicChatSessionSnapshot',
    'getCompanionParticipationProjection',
    'requestCompanionParticipation',
    'cancelCompanionParticipation',
    'openCompanionParticipationReplay',
    'createRealmGroupMessageCandidate',
    'getRealmGroupMessageCandidateEvidence',
    'getAvatarDebugSnapshot',
    'requestAvatarDebugProbe',
    'listAvatarDebugProbeResults',
    'getAvatarDebugReplay',
    'listDelegatedProviderProfiles',
    'upsertDelegatedProviderProfile',
    'setDelegatedProviderState',
    'listDelegatedApprovalRequests',
    'submitDelegatedApprovalDecision',
    'listDelegatedDiagnostics',
    'getDelegatedReplayTrace',
    'getDelegatedControlSurfaceSnapshot',
    'executeDelegatedCapability',
    'getAgentState',
    'updateAgentState',
    'setPresentationProfile',
    'enableAutonomy',
    'disableAutonomy',
    'setAutonomyConfig',
    'listPendingHooks',
    'cancelHook',
    'queryMemory',
    'writeMemory',
    'subscribeEvents',
];
const AUDIT_METHODS = [
    'listAuditEvents',
    'exportAuditEvents',
    'listUsageStats',
    'getRuntimeHealth',
    'listAIProviderHealth',
    'subscribeAIProviderHealthEvents',
    'subscribeRuntimeHealthEvents',
];
function createPassthroughModule(moduleKey, methods, input) {
    const { guard, invokeWithClient } = input;
    const moduleClient = {};
    for (const methodName of methods) {
        moduleClient[methodName] = (async (request, options) => {
            guard(moduleKey, methodName);
            return invokeWithClient(async (client) => {
                const runtimeModule = client[moduleKey];
                const runtimeMethod = runtimeModule[methodName];
                if (typeof runtimeMethod !== 'function') {
                    throw new Error(`runtime passthrough method missing: ${String(moduleKey)}.${String(methodName)}`);
                }
                return runtimeMethod(request, options);
            });
        });
    }
    return moduleClient;
}
export function createRuntimeEventsModule(eventBus) {
    return {
        on: (name, handler) => eventBus.on(name, handler),
        once: (name, handler) => eventBus.once(name, handler),
    };
}
export function createCorePassthroughClients(input) {
    const { assertMethodAvailable, invokeWithClient } = input;
    const guard = (mod, method) => assertMethodAvailable(mod, method);
    const auth = createPassthroughModule('auth', AUTH_METHODS, { guard, invokeWithClient });
    const accountBase = createPassthroughModule('account', ACCOUNT_METHODS, { guard, invokeWithClient });
    const account = {
        ...accountBase,
        subscribeAccountSessionEvents: async (request, optionsValue) => {
            guard('account', 'subscribeAccountSessionEvents');
            return invokeWithClient(async (client) => client.account.subscribeAccountSessionEvents(request, optionsValue));
        },
    };
    const workflowBase = createPassthroughModule('workflow', ['submit', 'get', 'cancel'], { guard, invokeWithClient });
    const workflow = {
        ...workflowBase,
        subscribeEvents: async (req, opts) => {
            guard('workflow', 'subscribeEvents');
            const raw = await invokeWithClient((c) => c.workflow.subscribeEvents(req, opts));
            return wrapModeBWorkflowStream(raw);
        },
    };
    const model = createPassthroughModule('model', MODEL_METHODS, { guard, invokeWithClient });
    const localBase = createPassthroughModule('local', LOCAL_METHODS, { guard, invokeWithClient });
    const local = {
        ...localBase,
        watchLocalTransfers: async (request, optionsValue) => {
            guard('local', 'watchLocalTransfers');
            return invokeWithClient(async (client) => client.local.watchLocalTransfers(request, optionsValue));
        },
    };
    const connector = createPassthroughModule('connector', CONNECTOR_METHODS, { guard, invokeWithClient });
    const knowledge = createPassthroughModule('knowledge', KNOWLEDGE_METHODS, { guard, invokeWithClient });
    const memoryBase = createPassthroughModule('memory', MEMORY_METHODS, { guard, invokeWithClient });
    const memory = {
        ...memoryBase,
        subscribeEvents: async (request, optionsValue) => {
            guard('memory', 'subscribeEvents');
            return invokeWithClient(async (client) => client.memory.subscribeEvents(request, optionsValue));
        },
    };
    const agentBase = createPassthroughModule('agent', AGENT_METHODS, { guard, invokeWithClient });
    const agent = {
        ...agentBase,
        subscribeEvents: async (request, optionsValue) => {
            guard('agent', 'subscribeEvents');
            return invokeWithClient(async (client) => client.agent.subscribeEvents(request, optionsValue));
        },
    };
    const audit = createPassthroughModule('audit', AUDIT_METHODS, { guard, invokeWithClient });
    return { auth, account, workflow, model, local, connector, knowledge, memory, agent, audit };
}
export function createAppClient(input) {
    return {
        sendMessage: async (request, options) => input.invokeWithClient(async (client) => client.app.sendAppMessage(request, options)),
        subscribeMessages: async (request, options) => {
            const raw = await input.invokeWithClient(async (client) => client.app.subscribeAppMessages(request, options));
            return input.wrapModeDStream(raw);
        },
    };
}
export function createAppAuthClient(input) {
    const { invokeWithClient, resolvePublishedCatalogVersion, emitTelemetry, authEvents, } = input;
    return {
        authorizeExternalPrincipal: async (request, optionsValue) => {
            const resolvedScopeCatalogVersion = resolvePublishedCatalogVersion(request.scopeCatalogVersion);
            const response = await invokeWithClient(async (client) => client.appAuth.authorizeExternalPrincipal({
                ...request,
                scopeCatalogVersion: resolvedScopeCatalogVersion,
            }, optionsValue));
            const issuedScopeCatalogVersion = normalizeText(response.issuedScopeCatalogVersion);
            if (issuedScopeCatalogVersion && issuedScopeCatalogVersion !== resolvedScopeCatalogVersion) {
                emitTelemetry('runtime.app-auth.scope-version-mismatch', {
                    requested: resolvedScopeCatalogVersion,
                    issued: issuedScopeCatalogVersion,
                });
            }
            const tokenId = normalizeText(response.tokenId);
            if (tokenId) {
                authEvents.emitTokenIssued(tokenId);
            }
            return response;
        },
        validateToken: async (request, optionsValue) => invokeWithClient(async (client) => client.appAuth.validateToken(request, optionsValue)),
        revokeToken: async (request, optionsValue) => {
            const response = await invokeWithClient(async (client) => client.appAuth.revokeToken(request, optionsValue));
            const tokenId = normalizeText(request.tokenId);
            if (tokenId) {
                authEvents.emitTokenRevoked(tokenId);
            }
            return response;
        },
        issueDelegatedToken: async (request, optionsValue) => {
            const response = await invokeWithClient(async (client) => client.appAuth.issueDelegatedToken(request, optionsValue));
            const tokenId = normalizeText(response.tokenId);
            if (tokenId) {
                authEvents.emitTokenIssued(tokenId);
            }
            return response;
        },
        listTokenChain: async (request, optionsValue) => invokeWithClient(async (client) => client.appAuth.listTokenChain(request, optionsValue)),
    };
}
export function createScopeClient(input) {
    const { invoke, scopeModule } = input;
    return {
        register: async (manifestInput) => invoke(async () => scopeModule.registerAppScopes({ manifest: manifestInput })),
        publish: async () => invoke(async () => scopeModule.publishCatalog()),
        revoke: async (revokeInput) => invoke(async () => scopeModule.revokeAppScopes({ scopes: revokeInput.scopes })),
        list: async (listInput) => invoke(async () => scopeModule.listCatalog(listInput)),
    };
}
export function createAiModule(input) {
    const { invokeWithClient, ctx } = input;
    const withScenarioHeadSubjectUserId = async (request, optionsValue) => {
        const subjectUserId = runtimeAiRequestRequiresSubject({
            request: { head: request.head },
            metadata: optionsValue?.metadata,
        })
            ? await ctx.resolveSubjectUserId(request.head?.subjectUserId)
            : await ctx.resolveOptionalSubjectUserId(request.head?.subjectUserId);
        const head = {
            ...request.head,
            // High-level SDK surfaces no longer expose app-facing fallback controls.
            // Normalize scenario requests to fail-close here and keep any fallback
            // behavior confined to lower-level internal/runtime strategies.
            fallback: FallbackPolicy.DENY,
            subjectUserId: subjectUserId || '',
        };
        return {
            ...request,
            head,
        };
    };
    return {
        executeScenario: async (request, optionsValue) => {
            const normalizedRequest = await withScenarioHeadSubjectUserId(request, optionsValue);
            return invokeWithClient(async (client) => client.ai.executeScenario(normalizedRequest, optionsValue));
        },
        streamScenario: async (request, optionsValue) => {
            const normalizedRequest = await withScenarioHeadSubjectUserId(request, optionsValue);
            return invokeWithClient(async (client) => client.ai.streamScenario(normalizedRequest, optionsValue));
        },
        submitScenarioJob: async (request, optionsValue) => {
            const normalizedRequest = await withScenarioHeadSubjectUserId(request, optionsValue);
            return invokeWithClient(async (client) => client.ai.submitScenarioJob(normalizedRequest, optionsValue));
        },
        getScenarioJob: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.getScenarioJob(request, optionsValue)),
        cancelScenarioJob: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.cancelScenarioJob(request, optionsValue)),
        subscribeScenarioJobEvents: async (request, optionsValue) => {
            return invokeWithClient(async (client) => client.ai.subscribeScenarioJobEvents(request, optionsValue));
        },
        getScenarioArtifacts: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.getScenarioArtifacts(request, optionsValue)),
        listScenarioProfiles: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.listScenarioProfiles(request, optionsValue)),
        getVoiceAsset: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.getVoiceAsset(request, optionsValue)),
        listVoiceAssets: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.listVoiceAssets(request, optionsValue)),
        deleteVoiceAsset: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.deleteVoiceAsset(request, optionsValue)),
        listPresetVoices: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.listPresetVoices(request, optionsValue)),
        uploadArtifact: async (uploadInput, optionsValue) => {
            const module = await loadRuntimeAiUploadModule();
            return module.runtimeUploadArtifact(ctx, uploadInput, optionsValue);
        },
        openRealtimeSession: async (request, optionsValue) => {
            const normalizedRequest = await withScenarioHeadSubjectUserId(request, optionsValue);
            return invokeWithClient(async (client) => client.ai.openRealtimeSession(normalizedRequest, optionsValue));
        },
        appendRealtimeInput: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.appendRealtimeInput(request, optionsValue)),
        readRealtimeEvents: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.readRealtimeEvents(request, optionsValue)),
        closeRealtimeSession: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.closeRealtimeSession(request, optionsValue)),
        peekScheduling: async (request, optionsValue) => invokeWithClient(async (client) => client.ai.peekScheduling(request, optionsValue)),
        text: {
            generate: async (textInput) => runtimeGenerateText(ctx, textInput),
            stream: async (textInput) => runtimeStreamText(ctx, textInput),
        },
        embedding: {
            generate: async (embeddingInput) => runtimeGenerateEmbedding(ctx, embeddingInput),
        },
    };
}
export function createMediaModule(ctx) {
    return {
        image: {
            generate: async (input) => runtimeGenerateImage(ctx, input),
            stream: async (input) => runtimeStreamImage(ctx, input),
        },
        video: {
            generate: async (input) => runtimeGenerateVideo(ctx, input),
            stream: async (input) => runtimeStreamVideo(ctx, input),
        },
        tts: {
            synthesize: async (input) => runtimeSynthesizeSpeech(ctx, input),
            stream: async (input) => runtimeStreamSpeech(ctx, input),
            listVoices: async (input) => runtimeListSpeechVoices(ctx, input),
        },
        stt: {
            transcribe: async (input) => runtimeTranscribeSpeech(ctx, input),
        },
        music: {
            generate: async (input) => runtimeGenerateMusic(ctx, input),
            iterate: async (input) => runtimeGenerateMusicIteration(ctx, input),
        },
        jobs: {
            submit: async (input) => runtimeSubmitScenarioJobForMedia(ctx, input),
            get: async (jobId) => runtimeGetScenarioJobForMedia(ctx, jobId),
            cancel: async (input) => runtimeCancelScenarioJobForMedia(ctx, input),
            subscribe: async (jobId) => runtimeSubscribeScenarioJobForMedia(ctx, jobId),
            getArtifacts: async (jobId) => runtimeGetScenarioArtifactsForMedia(ctx, jobId),
        },
    };
}
export function createRawModule(input) {
    const { rawCall, invokeWithClient } = input;
    const call = async (methodId, rawInput, options) => rawCall(methodId, rawInput, options);
    return {
        call,
        closeStream: async (streamId) => invokeWithClient(async (client) => client.closeStream(streamId)),
    };
}
export function createHealthEventStreams(input) {
    return {
        healthEvents: async (request, optionsValue) => {
            const raw = await input.audit.subscribeRuntimeHealthEvents(request || {}, optionsValue);
            return input.wrapModeDStream(raw);
        },
        providerHealthEvents: async (request, optionsValue) => {
            const raw = await input.audit.subscribeAIProviderHealthEvents(request || {}, optionsValue);
            return input.wrapModeDStream(raw);
        },
    };
}
export function emitAuthTokenIssuedEvent(eventBus, tokenId) {
    eventBus.emit('auth.token.issued', { tokenId, at: nowIso() });
}
export function emitAuthTokenRevokedEvent(eventBus, tokenId) {
    eventBus.emit('auth.token.revoked', { tokenId, at: nowIso() });
}
//# sourceMappingURL=runtime-modules.js.map