@lssm/lib.contracts 1.7.3 → 1.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +62 -325
- package/dist/app-config/contracts.d.ts +51 -49
- package/dist/app-config/contracts.d.ts.map +1 -1
- package/dist/app-config/contracts.js +1 -1
- package/dist/app-config/contracts.js.map +1 -1
- package/dist/app-config/events.d.ts +28 -26
- package/dist/app-config/events.d.ts.map +1 -1
- package/dist/app-config/events.js +1 -1
- package/dist/app-config/events.js.map +1 -1
- package/dist/app-config/lifecycle-contracts.d.ts +81 -79
- package/dist/app-config/lifecycle-contracts.d.ts.map +1 -1
- package/dist/app-config/lifecycle-contracts.js +1 -1
- package/dist/app-config/lifecycle-contracts.js.map +1 -1
- package/dist/app-config/runtime.d.ts.map +1 -1
- package/dist/app-config/runtime.js.map +1 -1
- package/dist/app-config/spec.d.ts +2 -2
- package/dist/app-config/spec.d.ts.map +1 -1
- package/dist/app-config/spec.js.map +1 -1
- package/dist/app-config/validation.d.ts.map +1 -1
- package/dist/app-config/validation.js.map +1 -1
- package/dist/capabilities/openbanking.d.ts.map +1 -1
- package/dist/capabilities/openbanking.js.map +1 -1
- package/dist/capabilities.d.ts +2 -1
- package/dist/capabilities.d.ts.map +1 -1
- package/dist/capabilities.js +1 -1
- package/dist/capabilities.js.map +1 -1
- package/dist/client/react/form-render.d.ts +1 -0
- package/dist/client/react/form-render.d.ts.map +1 -1
- package/dist/contracts-adapter-input.d.ts +1 -0
- package/dist/contracts-adapter-input.d.ts.map +1 -1
- package/dist/data-views/query-generator.d.ts +40 -0
- package/dist/data-views/query-generator.d.ts.map +1 -0
- package/dist/data-views/query-generator.js +2 -0
- package/dist/data-views/query-generator.js.map +1 -0
- package/dist/data-views/runtime.d.ts +27 -0
- package/dist/data-views/runtime.d.ts.map +1 -0
- package/dist/data-views/runtime.js +2 -0
- package/dist/data-views/runtime.js.map +1 -0
- package/dist/data-views.js.map +1 -1
- package/dist/events.d.ts +1 -0
- package/dist/events.d.ts.map +1 -1
- package/dist/events.js +1 -1
- package/dist/events.js.map +1 -1
- package/dist/experiments/evaluator.d.ts.map +1 -1
- package/dist/experiments/evaluator.js.map +1 -1
- package/dist/experiments/spec-resolver.d.ts +17 -0
- package/dist/experiments/spec-resolver.d.ts.map +1 -0
- package/dist/experiments/spec-resolver.js +0 -0
- package/dist/experiments/spec.js.map +1 -1
- package/dist/forms.d.ts +1 -0
- package/dist/forms.d.ts.map +1 -1
- package/dist/graphql-federation/dist/index.js +2 -0
- package/dist/graphql-federation/dist/index.js.map +1 -0
- package/dist/index.d.ts +4 -3
- package/dist/index.js +1 -1
- package/dist/install.d.ts +1 -0
- package/dist/install.d.ts.map +1 -1
- package/dist/integrations/connection.d.ts.map +1 -1
- package/dist/integrations/contracts.d.ts +103 -101
- package/dist/integrations/contracts.d.ts.map +1 -1
- package/dist/integrations/contracts.js +1 -1
- package/dist/integrations/contracts.js.map +1 -1
- package/dist/integrations/health.d.ts.map +1 -1
- package/dist/integrations/health.js.map +1 -1
- package/dist/integrations/openbanking/contracts/accounts.d.ts +67 -65
- package/dist/integrations/openbanking/contracts/accounts.d.ts.map +1 -1
- package/dist/integrations/openbanking/contracts/accounts.js +1 -1
- package/dist/integrations/openbanking/contracts/accounts.js.map +1 -1
- package/dist/integrations/openbanking/contracts/balances.d.ts +35 -33
- package/dist/integrations/openbanking/contracts/balances.d.ts.map +1 -1
- package/dist/integrations/openbanking/contracts/balances.js +1 -1
- package/dist/integrations/openbanking/contracts/balances.js.map +1 -1
- package/dist/integrations/openbanking/contracts/index.js.map +1 -1
- package/dist/integrations/openbanking/contracts/transactions.d.ts +49 -47
- package/dist/integrations/openbanking/contracts/transactions.d.ts.map +1 -1
- package/dist/integrations/openbanking/contracts/transactions.js +1 -1
- package/dist/integrations/openbanking/contracts/transactions.js.map +1 -1
- package/dist/integrations/openbanking/guards.js.map +1 -1
- package/dist/integrations/openbanking/models.d.ts +57 -54
- package/dist/integrations/openbanking/models.d.ts.map +1 -1
- package/dist/integrations/openbanking/models.js +1 -1
- package/dist/integrations/openbanking/models.js.map +1 -1
- package/dist/integrations/openbanking/telemetry.js.map +1 -1
- package/dist/integrations/providers/elevenlabs.d.ts.map +1 -1
- package/dist/integrations/providers/elevenlabs.js.map +1 -1
- package/dist/integrations/providers/gcs-storage.js.map +1 -1
- package/dist/integrations/providers/gmail.d.ts.map +1 -1
- package/dist/integrations/providers/gmail.js.map +1 -1
- package/dist/integrations/providers/google-calendar.js.map +1 -1
- package/dist/integrations/providers/impls/elevenlabs-voice.js.map +1 -1
- package/dist/integrations/providers/impls/gcs-storage.js.map +1 -1
- package/dist/integrations/providers/impls/gmail-inbound.js.map +1 -1
- package/dist/integrations/providers/impls/gmail-outbound.d.ts.map +1 -1
- package/dist/integrations/providers/impls/gmail-outbound.js.map +1 -1
- package/dist/integrations/providers/impls/google-calendar.d.ts.map +1 -1
- package/dist/integrations/providers/impls/google-calendar.js.map +1 -1
- package/dist/integrations/providers/impls/mistral-embedding.js.map +1 -1
- package/dist/integrations/providers/impls/mistral-llm.js.map +1 -1
- package/dist/integrations/providers/impls/postmark-email.js.map +1 -1
- package/dist/integrations/providers/impls/powens-client.d.ts.map +1 -1
- package/dist/integrations/providers/impls/powens-client.js.map +1 -1
- package/dist/integrations/providers/impls/powens-openbanking.d.ts.map +1 -1
- package/dist/integrations/providers/impls/powens-openbanking.js.map +1 -1
- package/dist/integrations/providers/impls/provider-factory.d.ts.map +1 -1
- package/dist/integrations/providers/impls/provider-factory.js.map +1 -1
- package/dist/integrations/providers/impls/qdrant-vector.d.ts.map +1 -1
- package/dist/integrations/providers/impls/qdrant-vector.js.map +1 -1
- package/dist/integrations/providers/impls/stripe-payments.d.ts.map +1 -1
- package/dist/integrations/providers/impls/stripe-payments.js.map +1 -1
- package/dist/integrations/providers/impls/twilio-sms.js.map +1 -1
- package/dist/integrations/providers/llm.d.ts.map +1 -1
- package/dist/integrations/providers/mistral.d.ts.map +1 -1
- package/dist/integrations/providers/mistral.js.map +1 -1
- package/dist/integrations/providers/payments.d.ts.map +1 -1
- package/dist/integrations/providers/postmark.d.ts.map +1 -1
- package/dist/integrations/providers/postmark.js.map +1 -1
- package/dist/integrations/providers/powens.js.map +1 -1
- package/dist/integrations/providers/qdrant.d.ts.map +1 -1
- package/dist/integrations/providers/qdrant.js.map +1 -1
- package/dist/integrations/providers/stripe.js.map +1 -1
- package/dist/integrations/providers/twilio-sms.js.map +1 -1
- package/dist/integrations/runtime.d.ts.map +1 -1
- package/dist/integrations/runtime.js.map +1 -1
- package/dist/integrations/secrets/env-secret-provider.js.map +1 -1
- package/dist/integrations/secrets/gcp-secret-manager.d.ts.map +1 -1
- package/dist/integrations/secrets/gcp-secret-manager.js.map +1 -1
- package/dist/integrations/secrets/manager.d.ts +2 -2
- package/dist/integrations/secrets/manager.d.ts.map +1 -1
- package/dist/integrations/secrets/manager.js.map +1 -1
- package/dist/integrations/secrets/provider.js.map +1 -1
- package/dist/integrations/spec.d.ts.map +1 -1
- package/dist/integrations/spec.js.map +1 -1
- package/dist/jobs/gcp-cloud-tasks.js.map +1 -1
- package/dist/jobs/gcp-pubsub.d.ts.map +1 -1
- package/dist/jobs/gcp-pubsub.js.map +1 -1
- package/dist/jobs/handlers/gmail-sync-handler.js.map +1 -1
- package/dist/jobs/handlers/storage-document-handler.js.map +1 -1
- package/dist/jobs/memory-queue.d.ts.map +1 -1
- package/dist/jobs/memory-queue.js.map +1 -1
- package/dist/jobs/queue.d.ts.map +1 -1
- package/dist/jsonschema.d.ts +1 -1
- package/dist/jsonschema.d.ts.map +1 -1
- package/dist/knowledge/contracts.d.ts +67 -65
- package/dist/knowledge/contracts.d.ts.map +1 -1
- package/dist/knowledge/contracts.js +1 -1
- package/dist/knowledge/contracts.js.map +1 -1
- package/dist/knowledge/ingestion/document-processor.js.map +1 -1
- package/dist/knowledge/ingestion/embedding-service.d.ts.map +1 -1
- package/dist/knowledge/ingestion/embedding-service.js.map +1 -1
- package/dist/knowledge/ingestion/gmail-adapter.d.ts.map +1 -1
- package/dist/knowledge/ingestion/gmail-adapter.js.map +1 -1
- package/dist/knowledge/ingestion/storage-adapter.js.map +1 -1
- package/dist/knowledge/ingestion/vector-indexer.js.map +1 -1
- package/dist/knowledge/query/service.d.ts +2 -2
- package/dist/knowledge/query/service.d.ts.map +1 -1
- package/dist/knowledge/query/service.js.map +1 -1
- package/dist/knowledge/runtime.d.ts.map +1 -1
- package/dist/knowledge/runtime.js.map +1 -1
- package/dist/knowledge/spaces/email-threads.js.map +1 -1
- package/dist/knowledge/spaces/financial-docs.js.map +1 -1
- package/dist/knowledge/spaces/financial-overview.js.map +1 -1
- package/dist/knowledge/spaces/product-canon.js.map +1 -1
- package/dist/knowledge/spaces/support-faq.js.map +1 -1
- package/dist/knowledge/spaces/uploaded-docs.js.map +1 -1
- package/dist/knowledge/spec.js.map +1 -1
- package/dist/migrations.d.ts.map +1 -1
- package/dist/migrations.js.map +1 -1
- package/dist/onboarding-base.d.ts +30 -28
- package/dist/onboarding-base.d.ts.map +1 -1
- package/dist/onboarding-base.js +1 -1
- package/dist/onboarding-base.js.map +1 -1
- package/dist/policy/engine.js.map +1 -1
- package/dist/policy/opa-adapter.d.ts.map +1 -1
- package/dist/policy/opa-adapter.js.map +1 -1
- package/dist/policy/spec.d.ts.map +1 -1
- package/dist/policy/spec.js.map +1 -1
- package/dist/presentations.d.ts +1 -0
- package/dist/presentations.d.ts.map +1 -1
- package/dist/presentations.v2.d.ts +1 -0
- package/dist/presentations.v2.d.ts.map +1 -1
- package/dist/regenerator/executor.d.ts.map +1 -1
- package/dist/regenerator/executor.js.map +1 -1
- package/dist/regenerator/service.d.ts.map +1 -1
- package/dist/regenerator/service.js.map +1 -1
- package/dist/regenerator/sinks.d.ts.map +1 -1
- package/dist/regenerator/sinks.js.map +1 -1
- package/dist/regenerator/types.d.ts.map +1 -1
- package/dist/regenerator/utils.js.map +1 -1
- package/dist/registry.d.ts +37 -9
- package/dist/registry.d.ts.map +1 -1
- package/dist/registry.js +1 -1
- package/dist/registry.js.map +1 -1
- package/dist/schema/dist/FieldType.js +2 -0
- package/dist/schema/dist/FieldType.js.map +1 -0
- package/dist/schema/dist/ScalarTypeEnum.js +2 -0
- package/dist/schema/dist/ScalarTypeEnum.js.map +1 -0
- package/dist/schema/{src → dist}/SchemaModel.js +1 -1
- package/dist/schema/dist/SchemaModel.js.map +1 -0
- package/dist/schema/dist/index.js +1 -0
- package/dist/server/graphql-pothos.d.ts +15 -2
- package/dist/server/graphql-pothos.d.ts.map +1 -1
- package/dist/server/graphql-pothos.js.map +1 -1
- package/dist/server/graphql-schema-export.js +1 -1
- package/dist/server/graphql-schema-export.js.map +1 -1
- package/dist/server/provider-mcp.d.ts +22 -4
- package/dist/server/provider-mcp.d.ts.map +1 -1
- package/dist/server/provider-mcp.js.map +1 -1
- package/dist/server/rest-next-app.d.ts +23 -3
- package/dist/server/rest-next-app.d.ts.map +1 -1
- package/dist/server/rest-next-app.js.map +1 -1
- package/dist/spec.d.ts +23 -0
- package/dist/spec.d.ts.map +1 -1
- package/dist/spec.js.map +1 -1
- package/dist/telemetry/anomaly.js.map +1 -1
- package/dist/telemetry/spec.d.ts.map +1 -1
- package/dist/telemetry/spec.js.map +1 -1
- package/dist/telemetry/tracker.d.ts.map +1 -1
- package/dist/telemetry/tracker.js.map +1 -1
- package/dist/tests/runner.js.map +1 -1
- package/dist/tests/spec.js.map +1 -1
- package/dist/themes.d.ts.map +1 -1
- package/dist/themes.js.map +1 -1
- package/dist/types/all.d.ts +2 -2
- package/dist/types.d.ts +3 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/workflow/adapters/db-adapter.d.ts +30 -10
- package/dist/workflow/adapters/db-adapter.d.ts.map +1 -1
- package/dist/workflow/adapters/db-adapter.js +1 -1
- package/dist/workflow/adapters/db-adapter.js.map +1 -1
- package/dist/workflow/adapters/file-adapter.js.map +1 -1
- package/dist/workflow/adapters/index.d.ts +2 -2
- package/dist/workflow/adapters/index.js +1 -1
- package/dist/workflow/adapters/memory-store.d.ts.map +1 -1
- package/dist/workflow/adapters/memory-store.js.map +1 -1
- package/dist/workflow/expression.js.map +1 -1
- package/dist/workflow/index.d.ts +2 -2
- package/dist/workflow/index.js +1 -1
- package/dist/workflow/runner.d.ts +1 -0
- package/dist/workflow/runner.d.ts.map +1 -1
- package/dist/workflow/runner.js +1 -1
- package/dist/workflow/runner.js.map +1 -1
- package/dist/workflow/sla-monitor.d.ts +21 -0
- package/dist/workflow/sla-monitor.d.ts.map +1 -0
- package/dist/workflow/sla-monitor.js +2 -0
- package/dist/workflow/sla-monitor.js.map +1 -0
- package/dist/workflow/spec.d.ts.map +1 -1
- package/dist/workflow/spec.js.map +1 -1
- package/dist/workflow/state.d.ts +1 -0
- package/dist/workflow/state.d.ts.map +1 -1
- package/dist/workflow/validation.d.ts.map +1 -1
- package/dist/workflow/validation.js.map +1 -1
- package/package.json +181 -177
- package/dist/graphql-federation/src/index.js +0 -2
- package/dist/graphql-federation/src/index.js.map +0 -1
- package/dist/schema/src/FieldType.js +0 -2
- package/dist/schema/src/FieldType.js.map +0 -1
- package/dist/schema/src/ScalarTypeEnum.js +0 -2
- package/dist/schema/src/ScalarTypeEnum.js.map +0 -1
- package/dist/schema/src/SchemaModel.js.map +0 -1
- package/dist/schema/src/index.js +0 -1
- /package/dist/schema/{src → dist}/EnumType.js +0 -0
|
@@ -11,9 +11,9 @@ interface KnowledgeQueryConfig {
|
|
|
11
11
|
}
|
|
12
12
|
interface KnowledgeAnswer {
|
|
13
13
|
answer: string;
|
|
14
|
-
references:
|
|
14
|
+
references: (VectorSearchResult & {
|
|
15
15
|
text?: string;
|
|
16
|
-
}
|
|
16
|
+
})[];
|
|
17
17
|
usage?: LLMResponse['usage'];
|
|
18
18
|
}
|
|
19
19
|
declare class KnowledgeQueryService {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"service.d.ts","names":[],"sources":["../../../src/knowledge/query/service.ts"],"sourcesContent":[],"mappings":";;;;;
|
|
1
|
+
{"version":3,"file":"service.d.ts","names":[],"sources":["../../../src/knowledge/query/service.ts"],"sourcesContent":[],"mappings":";;;;;UAWiB,oBAAA;;EAAA,SAAA,CAAA,EAAA,MAAA;EAOA,IAAA,CAAA,EAAA,MAAA;EAQJ,YAAA,CAAA,EAAA,MAAA;;AAQI,UAhBA,eAAA,CAgBA;EACR,MAAA,EAAA,MAAA;EACG,UAAA,EAAA,CAhBG,kBAgBH,GAAA;IAQ6B,IAAA,CAAA,EAAA,MAAA;EAAR,CAAA,CAAA,EAAA;EAAO,KAAA,CAAA,EArB9B,WAqB8B,CAAA,OAAA,CAAA;;cAlB3B,qBAAA;;;;;0BAOG,gCACC,0BACR,qBACG;2BAQqB,QAAQ"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"service.js","names":[],"sources":["../../../src/knowledge/query/service.ts"],"sourcesContent":["import type { EmbeddingProvider } from '../../integrations/providers/embedding';\nimport type {\n VectorStoreProvider,\n VectorSearchResult,\n} from '../../integrations/providers/vector-store';\nimport type {
|
|
1
|
+
{"version":3,"file":"service.js","names":[],"sources":["../../../src/knowledge/query/service.ts"],"sourcesContent":["import type { EmbeddingProvider } from '../../integrations/providers/embedding';\nimport type {\n VectorStoreProvider,\n VectorSearchResult,\n} from '../../integrations/providers/vector-store';\nimport type {\n LLMProvider,\n LLMMessage,\n LLMResponse,\n} from '../../integrations/providers/llm';\n\nexport interface KnowledgeQueryConfig {\n collection: string;\n namespace?: string;\n topK?: number;\n systemPrompt?: string;\n}\n\nexport interface KnowledgeAnswer {\n answer: string;\n references: (VectorSearchResult & {\n text?: string;\n })[];\n usage?: LLMResponse['usage'];\n}\n\nexport class KnowledgeQueryService {\n private readonly embeddings: EmbeddingProvider;\n private readonly vectorStore: VectorStoreProvider;\n private readonly llm: LLMProvider;\n private readonly config: KnowledgeQueryConfig;\n\n constructor(\n embeddings: EmbeddingProvider,\n vectorStore: VectorStoreProvider,\n llm: LLMProvider,\n config: KnowledgeQueryConfig\n ) {\n this.embeddings = embeddings;\n this.vectorStore = vectorStore;\n this.llm = llm;\n this.config = config;\n }\n\n async query(question: string): Promise<KnowledgeAnswer> {\n const embedding = await this.embeddings.embedQuery(question);\n const results = await this.vectorStore.search({\n collection: this.config.collection,\n vector: embedding.vector,\n topK: this.config.topK ?? 5,\n namespace: this.config.namespace,\n filter: undefined,\n });\n const context = buildContext(results);\n const messages = this.buildMessages(question, context);\n const response = await this.llm.chat(messages);\n return {\n answer: response.message.content\n .map((part) => ('text' in part ? part.text : ''))\n .join(''),\n references: results.map((result) => ({\n ...result,\n text: extractText(result),\n })),\n usage: response.usage,\n };\n }\n\n private buildMessages(question: string, context: string): LLMMessage[] {\n const systemPrompt =\n this.config.systemPrompt ??\n 'You are a knowledge assistant that answers questions using the provided context. Cite relevant sources if possible.';\n return [\n {\n role: 'system',\n content: [{ type: 'text', text: systemPrompt }],\n },\n {\n role: 'user',\n content: [\n {\n type: 'text',\n text: `Question:\\n${question}\\n\\nContext:\\n${context}`,\n },\n ],\n },\n ];\n }\n}\n\nfunction buildContext(results: VectorSearchResult[]): string {\n if (results.length === 0) {\n return 'No relevant documents found.';\n }\n return results\n .map((result, index) => {\n const text = extractText(result);\n return `Source ${index + 1} (score: ${result.score.toFixed(3)}):\\n${text}`;\n })\n .join('\\n\\n');\n}\n\nfunction extractText(result: VectorSearchResult): string {\n const payload = result.payload ?? {};\n if (typeof payload.text === 'string') return payload.text;\n if (typeof payload.content === 'string') return payload.content;\n return JSON.stringify(payload);\n}\n"],"mappings":"AA0BA,IAAa,EAAb,KAAmC,CACjC,WACA,YACA,IACA,OAEA,YACE,EACA,EACA,EACA,EACA,CACA,KAAK,WAAa,EAClB,KAAK,YAAc,EACnB,KAAK,IAAM,EACX,KAAK,OAAS,EAGhB,MAAM,MAAM,EAA4C,CACtD,IAAM,EAAY,MAAM,KAAK,WAAW,WAAW,EAAS,CACtD,EAAU,MAAM,KAAK,YAAY,OAAO,CAC5C,WAAY,KAAK,OAAO,WACxB,OAAQ,EAAU,OAClB,KAAM,KAAK,OAAO,MAAQ,EAC1B,UAAW,KAAK,OAAO,UACvB,OAAQ,IAAA,GACT,CAAC,CACI,EAAU,EAAa,EAAQ,CAC/B,EAAW,KAAK,cAAc,EAAU,EAAQ,CAChD,EAAW,MAAM,KAAK,IAAI,KAAK,EAAS,CAC9C,MAAO,CACL,OAAQ,EAAS,QAAQ,QACtB,IAAK,GAAU,SAAU,EAAO,EAAK,KAAO,GAAI,CAChD,KAAK,GAAG,CACX,WAAY,EAAQ,IAAK,IAAY,CACnC,GAAG,EACH,KAAM,EAAY,EAAO,CAC1B,EAAE,CACH,MAAO,EAAS,MACjB,CAGH,cAAsB,EAAkB,EAA+B,CAIrE,MAAO,CACL,CACE,KAAM,SACN,QAAS,CAAC,CAAE,KAAM,OAAQ,KAL5B,KAAK,OAAO,cACZ,sHAIgD,CAAC,CAChD,CACD,CACE,KAAM,OACN,QAAS,CACP,CACE,KAAM,OACN,KAAM,cAAc,EAAS,gBAAgB,IAC9C,CACF,CACF,CACF,GAIL,SAAS,EAAa,EAAuC,CAI3D,OAHI,EAAQ,SAAW,EACd,+BAEF,EACJ,KAAK,EAAQ,IAAU,CACtB,IAAM,EAAO,EAAY,EAAO,CAChC,MAAO,UAAU,EAAQ,EAAE,WAAW,EAAO,MAAM,QAAQ,EAAE,CAAC,MAAM,KACpE,CACD,KAAK;;EAAO,CAGjB,SAAS,EAAY,EAAoC,CACvD,IAAM,EAAU,EAAO,SAAW,EAAE,CAGpC,OAFI,OAAO,EAAQ,MAAS,SAAiB,EAAQ,KACjD,OAAO,EAAQ,SAAY,SAAiB,EAAQ,QACjD,KAAK,UAAU,EAAQ"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"runtime.d.ts","names":[],"sources":["../../src/knowledge/runtime.ts"],"sourcesContent":[],"mappings":";;;;
|
|
1
|
+
{"version":3,"file":"runtime.d.ts","names":[],"sources":["../../src/knowledge/runtime.ts"],"sourcesContent":[],"mappings":";;;;UAMiB,sBAAA;;EAAA,KAAA,EAAA,MAAA;EASA,WAAA,CAAA,EAAA,MAAA;EAMA,YAAA,CAAA,EAAA,MAAA;EAQJ,SAAA,CAAA,EAAA,MAAA;EAKU,SAAA,EAAA,MAAA,GAAA,OAAA,GAAA,QAAA;;AAUV,UA7BI,qBAAA,CA6BJ;EACE,OAAA,EAAA,OAAA;EACV,MAAA,CAAA,EAAA,MAAA;EAAqB,QAAA,CAAA,EAAA,OAAA,GAAA,SAAA;;UAzBT,2BAAA;4BACW;;;;cAOf,oBAAA;;;;wBAKU;4BASL,4BACL,mCACE,oBACV"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"runtime.js","names":["DEFAULT_DISALLOWED_WRITE: KnowledgeCategory[]"],"sources":["../../src/knowledge/runtime.ts"],"sourcesContent":["import type {
|
|
1
|
+
{"version":3,"file":"runtime.js","names":["DEFAULT_DISALLOWED_WRITE: KnowledgeCategory[]"],"sources":["../../src/knowledge/runtime.ts"],"sourcesContent":["import type {\n ResolvedAppConfig,\n ResolvedKnowledge,\n} from '../app-config/runtime';\nimport type { KnowledgeCategory } from './spec';\n\nexport interface KnowledgeAccessContext {\n tenantId: string;\n appId: string;\n environment?: string;\n workflowName?: string;\n agentName?: string;\n operation: 'read' | 'write' | 'search';\n}\n\nexport interface KnowledgeAccessResult {\n allowed: boolean;\n reason?: string;\n severity?: 'error' | 'warning';\n}\n\nexport interface KnowledgeAccessGuardOptions {\n disallowWriteCategories?: KnowledgeCategory[];\n requireWorkflowBinding?: boolean;\n requireAgentBinding?: boolean;\n}\n\nconst DEFAULT_DISALLOWED_WRITE: KnowledgeCategory[] = ['external', 'ephemeral'];\n\nexport class KnowledgeAccessGuard {\n private readonly disallowedWrite: Set<KnowledgeCategory>;\n private readonly requireWorkflowBinding: boolean;\n private readonly requireAgentBinding: boolean;\n\n constructor(options: KnowledgeAccessGuardOptions = {}) {\n this.disallowedWrite = new Set(\n options.disallowWriteCategories ?? DEFAULT_DISALLOWED_WRITE\n );\n this.requireWorkflowBinding = options.requireWorkflowBinding ?? true;\n this.requireAgentBinding = options.requireAgentBinding ?? false;\n }\n\n checkAccess(\n spaceBinding: ResolvedKnowledge,\n context: KnowledgeAccessContext,\n appConfig: ResolvedAppConfig\n ): KnowledgeAccessResult {\n const { binding, space } = spaceBinding;\n\n if (\n binding.required !== false &&\n !this.isSpaceBound(spaceBinding, appConfig)\n ) {\n return {\n allowed: false,\n reason: `Knowledge space \"${space.meta.key}\" is not bound in the resolved app config.`,\n };\n }\n\n if (\n context.operation === 'write' &&\n this.disallowedWrite.has(space.meta.category)\n ) {\n return {\n allowed: false,\n reason: `Knowledge space \"${space.meta.key}\" is category \"${space.meta.category}\" and is read-only.`,\n };\n }\n\n if (this.requireWorkflowBinding && context.workflowName) {\n const allowedWorkflows = binding.scope?.workflows;\n if (\n allowedWorkflows &&\n !allowedWorkflows.includes(context.workflowName)\n ) {\n return {\n allowed: false,\n reason: `Workflow \"${context.workflowName}\" is not authorized to access knowledge space \"${space.meta.key}\".`,\n };\n }\n }\n\n if (this.requireAgentBinding && context.agentName) {\n const allowedAgents = binding.scope?.agents;\n if (allowedAgents && !allowedAgents.includes(context.agentName)) {\n return {\n allowed: false,\n reason: `Agent \"${context.agentName}\" is not authorized to access knowledge space \"${space.meta.key}\".`,\n };\n }\n }\n\n if (space.meta.category === 'ephemeral') {\n return {\n allowed: true,\n severity: 'warning',\n reason: `Knowledge space \"${space.meta.key}\" is ephemeral; results may be transient.`,\n };\n }\n\n return { allowed: true };\n }\n\n private isSpaceBound(\n resolved: ResolvedKnowledge,\n appConfig: ResolvedAppConfig\n ): boolean {\n return appConfig.knowledge.some(\n (entry) =>\n entry.space.meta.key === resolved.space.meta.key &&\n (resolved.space.meta.version == null ||\n entry.space.meta.version === resolved.space.meta.version)\n );\n }\n}\n"],"mappings":"AA2BA,MAAMA,EAAgD,CAAC,WAAY,YAAY,CAE/E,IAAa,EAAb,KAAkC,CAChC,gBACA,uBACA,oBAEA,YAAY,EAAuC,EAAE,CAAE,CACrD,KAAK,gBAAkB,IAAI,IACzB,EAAQ,yBAA2B,EACpC,CACD,KAAK,uBAAyB,EAAQ,wBAA0B,GAChE,KAAK,oBAAsB,EAAQ,qBAAuB,GAG5D,YACE,EACA,EACA,EACuB,CACvB,GAAM,CAAE,UAAS,SAAU,EAE3B,GACE,EAAQ,WAAa,IACrB,CAAC,KAAK,aAAa,EAAc,EAAU,CAE3C,MAAO,CACL,QAAS,GACT,OAAQ,oBAAoB,EAAM,KAAK,IAAI,4CAC5C,CAGH,GACE,EAAQ,YAAc,SACtB,KAAK,gBAAgB,IAAI,EAAM,KAAK,SAAS,CAE7C,MAAO,CACL,QAAS,GACT,OAAQ,oBAAoB,EAAM,KAAK,IAAI,iBAAiB,EAAM,KAAK,SAAS,qBACjF,CAGH,GAAI,KAAK,wBAA0B,EAAQ,aAAc,CACvD,IAAM,EAAmB,EAAQ,OAAO,UACxC,GACE,GACA,CAAC,EAAiB,SAAS,EAAQ,aAAa,CAEhD,MAAO,CACL,QAAS,GACT,OAAQ,aAAa,EAAQ,aAAa,iDAAiD,EAAM,KAAK,IAAI,IAC3G,CAIL,GAAI,KAAK,qBAAuB,EAAQ,UAAW,CACjD,IAAM,EAAgB,EAAQ,OAAO,OACrC,GAAI,GAAiB,CAAC,EAAc,SAAS,EAAQ,UAAU,CAC7D,MAAO,CACL,QAAS,GACT,OAAQ,UAAU,EAAQ,UAAU,iDAAiD,EAAM,KAAK,IAAI,IACrG,CAYL,OARI,EAAM,KAAK,WAAa,YACnB,CACL,QAAS,GACT,SAAU,UACV,OAAQ,oBAAoB,EAAM,KAAK,IAAI,2CAC5C,CAGI,CAAE,QAAS,GAAM,CAG1B,aACE,EACA,EACS,CACT,OAAO,EAAU,UAAU,KACxB,GACC,EAAM,MAAM,KAAK,MAAQ,EAAS,MAAM,KAAK,MAC5C,EAAS,MAAM,KAAK,SAAW,MAC9B,EAAM,MAAM,KAAK,UAAY,EAAS,MAAM,KAAK,SACtD"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"email-threads.js","names":["emailThreadsKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/email-threads.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const emailThreadsKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.email-threads',\n version: 1,\n category: 'operational',\n displayName: 'Email Threads',\n title: 'Operational Email Threads',\n description:\n 'Indexed copies of operational email threads used for support, onboarding, and workflows.',\n domain: 'operations',\n owners: ['platform.operations'],\n tags: ['email', 'operations'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: 365,\n },\n access: {\n policy: { name: 'knowledge.access.email-threads', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 600,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Operational email threads synchronized from Gmail to support automations and contextual assistance.',\n};\n\nexport function registerEmailThreadsKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(emailThreadsKnowledgeSpace);\n}\n
|
|
1
|
+
{"version":3,"file":"email-threads.js","names":["emailThreadsKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/email-threads.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const emailThreadsKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.email-threads',\n version: 1,\n category: 'operational',\n displayName: 'Email Threads',\n title: 'Operational Email Threads',\n description:\n 'Indexed copies of operational email threads used for support, onboarding, and workflows.',\n domain: 'operations',\n owners: ['platform.operations'],\n tags: ['email', 'operations'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: 365,\n },\n access: {\n policy: { name: 'knowledge.access.email-threads', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 600,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Operational email threads synchronized from Gmail to support automations and contextual assistance.',\n};\n\nexport function registerEmailThreadsKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(emailThreadsKnowledgeSpace);\n}\n"],"mappings":"mDAGA,MAAaA,EAAiD,CAC5D,KAAM,CACJ,IAAK,0BACL,QAAS,EACT,SAAU,cACV,YAAa,gBACb,MAAO,4BACP,YACE,2FACF,OAAQ,aACR,OAAQ,CAAC,sBAAsB,CAC/B,KAAM,CAAC,QAAS,aAAa,CAC7B,UAAW,EAAc,KAC1B,CACD,UAAW,CACT,QAAS,IACV,CACD,OAAQ,CACN,OAAQ,CAAE,KAAM,iCAAkC,QAAS,EAAG,CAC9D,WAAY,SACZ,mBAAoB,GACrB,CACD,SAAU,CACR,eAAgB,gBAChB,UAAW,IACX,oBAAqB,kBACtB,CACD,YACE,sGACH,CAED,SAAgB,EACd,EACwB,CACxB,OAAO,EAAS,SAAS,EAA2B"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"financial-docs.js","names":["financialDocsKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/financial-docs.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const financialDocsKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.financial-docs',\n version: 1,\n category: 'canonical',\n displayName: 'Financial Documents',\n title: 'Household Financial Documents',\n description:\n 'Invoices, bills, and contracts powering Pocket Family Office financial automation.',\n domain: 'finance',\n owners: ['platform.finance'],\n tags: ['finance', 'documents'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: null,\n },\n access: {\n policy: { name: 'knowledge.access.financial-docs', version: 1 },\n trustLevel: 'high',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 700,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Normalized financial documents enabling bill pay automation, reminders, and summaries.',\n};\n\nexport function registerFinancialDocsKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(financialDocsKnowledgeSpace);\n}\n
|
|
1
|
+
{"version":3,"file":"financial-docs.js","names":["financialDocsKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/financial-docs.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const financialDocsKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.financial-docs',\n version: 1,\n category: 'canonical',\n displayName: 'Financial Documents',\n title: 'Household Financial Documents',\n description:\n 'Invoices, bills, and contracts powering Pocket Family Office financial automation.',\n domain: 'finance',\n owners: ['platform.finance'],\n tags: ['finance', 'documents'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: null,\n },\n access: {\n policy: { name: 'knowledge.access.financial-docs', version: 1 },\n trustLevel: 'high',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 700,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Normalized financial documents enabling bill pay automation, reminders, and summaries.',\n};\n\nexport function registerFinancialDocsKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(financialDocsKnowledgeSpace);\n}\n"],"mappings":"mDAGA,MAAaA,EAAkD,CAC7D,KAAM,CACJ,IAAK,2BACL,QAAS,EACT,SAAU,YACV,YAAa,sBACb,MAAO,gCACP,YACE,qFACF,OAAQ,UACR,OAAQ,CAAC,mBAAmB,CAC5B,KAAM,CAAC,UAAW,YAAY,CAC9B,UAAW,EAAc,KAC1B,CACD,UAAW,CACT,QAAS,KACV,CACD,OAAQ,CACN,OAAQ,CAAE,KAAM,kCAAmC,QAAS,EAAG,CAC/D,WAAY,OACZ,mBAAoB,GACrB,CACD,SAAU,CACR,eAAgB,gBAChB,UAAW,IACX,oBAAqB,kBACtB,CACD,YACE,yFACH,CAED,SAAgB,EACd,EACwB,CACxB,OAAO,EAAS,SAAS,EAA4B"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"financial-overview.js","names":["financialOverviewKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/financial-overview.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const financialOverviewKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.financial-overview',\n version: 1,\n category: 'operational',\n displayName: 'Financial Overview Summaries',\n title: 'Derived Financial Summaries',\n description:\n 'Aggregated cashflow summaries, category breakdowns, and balance trends derived from open banking data.',\n domain: 'finance',\n owners: ['platform.finance'],\n tags: ['open-banking', 'summaries', 'cashflow'],\n stability: StabilityEnum.Experimental,\n },\n retention: {\n ttlDays: 180,\n },\n access: {\n policy: { name: 'knowledge.access.financial-overview', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 600,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Derived knowledge space containing weekly/monthly cashflow rollups and account health summaries. Raw transactions are excluded to respect privacy guardrails.',\n};\n\nexport function registerFinancialOverviewKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(financialOverviewKnowledgeSpace);\n}\n
|
|
1
|
+
{"version":3,"file":"financial-overview.js","names":["financialOverviewKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/financial-overview.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const financialOverviewKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.financial-overview',\n version: 1,\n category: 'operational',\n displayName: 'Financial Overview Summaries',\n title: 'Derived Financial Summaries',\n description:\n 'Aggregated cashflow summaries, category breakdowns, and balance trends derived from open banking data.',\n domain: 'finance',\n owners: ['platform.finance'],\n tags: ['open-banking', 'summaries', 'cashflow'],\n stability: StabilityEnum.Experimental,\n },\n retention: {\n ttlDays: 180,\n },\n access: {\n policy: { name: 'knowledge.access.financial-overview', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 600,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Derived knowledge space containing weekly/monthly cashflow rollups and account health summaries. Raw transactions are excluded to respect privacy guardrails.',\n};\n\nexport function registerFinancialOverviewKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(financialOverviewKnowledgeSpace);\n}\n"],"mappings":"mDAGA,MAAaA,EAAsD,CACjE,KAAM,CACJ,IAAK,+BACL,QAAS,EACT,SAAU,cACV,YAAa,+BACb,MAAO,8BACP,YACE,yGACF,OAAQ,UACR,OAAQ,CAAC,mBAAmB,CAC5B,KAAM,CAAC,eAAgB,YAAa,WAAW,CAC/C,UAAW,EAAc,aAC1B,CACD,UAAW,CACT,QAAS,IACV,CACD,OAAQ,CACN,OAAQ,CAAE,KAAM,sCAAuC,QAAS,EAAG,CACnE,WAAY,SACZ,mBAAoB,GACrB,CACD,SAAU,CACR,eAAgB,gBAChB,UAAW,IACX,oBAAqB,kBACtB,CACD,YACE,gKACH,CAED,SAAgB,EACd,EACwB,CACxB,OAAO,EAAS,SAAS,EAAgC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"product-canon.js","names":["productCanonKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/product-canon.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const productCanonKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.product-canon',\n version: 1,\n category: 'canonical',\n displayName: 'Product Canon',\n title: 'Product Canon Knowledge Space',\n description:\n 'Authoritative product knowledge covering strategy, roadmap, and delivery canon.',\n domain: 'product',\n owners: ['platform.product'],\n tags: ['knowledge', 'product'],\n stability: StabilityEnum.Stable,\n },\n retention: {\n ttlDays: null,\n },\n access: {\n policy: { name: 'knowledge.access.product-canon', version: 1 },\n trustLevel: 'high',\n automationWritable: false,\n },\n indexing: {\n embeddingModel: 'text-embedding-3-large',\n chunkSize: 800,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Single source of truth for product canon, principles, and strategic narratives.',\n};\n\nexport function registerProductCanonKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(productCanonKnowledgeSpace);\n}\n
|
|
1
|
+
{"version":3,"file":"product-canon.js","names":["productCanonKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/product-canon.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const productCanonKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.product-canon',\n version: 1,\n category: 'canonical',\n displayName: 'Product Canon',\n title: 'Product Canon Knowledge Space',\n description:\n 'Authoritative product knowledge covering strategy, roadmap, and delivery canon.',\n domain: 'product',\n owners: ['platform.product'],\n tags: ['knowledge', 'product'],\n stability: StabilityEnum.Stable,\n },\n retention: {\n ttlDays: null,\n },\n access: {\n policy: { name: 'knowledge.access.product-canon', version: 1 },\n trustLevel: 'high',\n automationWritable: false,\n },\n indexing: {\n embeddingModel: 'text-embedding-3-large',\n chunkSize: 800,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Single source of truth for product canon, principles, and strategic narratives.',\n};\n\nexport function registerProductCanonKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(productCanonKnowledgeSpace);\n}\n"],"mappings":"mDAGA,MAAaA,EAAiD,CAC5D,KAAM,CACJ,IAAK,0BACL,QAAS,EACT,SAAU,YACV,YAAa,gBACb,MAAO,gCACP,YACE,kFACF,OAAQ,UACR,OAAQ,CAAC,mBAAmB,CAC5B,KAAM,CAAC,YAAa,UAAU,CAC9B,UAAW,EAAc,OAC1B,CACD,UAAW,CACT,QAAS,KACV,CACD,OAAQ,CACN,OAAQ,CAAE,KAAM,iCAAkC,QAAS,EAAG,CAC9D,WAAY,OACZ,mBAAoB,GACrB,CACD,SAAU,CACR,eAAgB,yBAChB,UAAW,IACX,oBAAqB,kBACtB,CACD,YACE,kFACH,CAED,SAAgB,EACd,EACwB,CACxB,OAAO,EAAS,SAAS,EAA2B"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"support-faq.js","names":["supportFaqKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/support-faq.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const supportFaqKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.support-faq',\n version: 1,\n category: 'operational',\n displayName: 'Support FAQ',\n title: 'Support & Success FAQ',\n description: 'Operational knowledge base for customer support and success.',\n domain: 'support',\n owners: ['platform.support'],\n tags: ['knowledge', 'support'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: 365,\n archiveAfterDays: 180,\n },\n access: {\n policy: { name: 'knowledge.access.support', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'text-embedding-3-small',\n chunkSize: 700,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Operational FAQs, runbooks, and customer success playbooks augmented with automation updates.',\n};\n\nexport function registerSupportFaqKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(supportFaqKnowledgeSpace);\n}\n
|
|
1
|
+
{"version":3,"file":"support-faq.js","names":["supportFaqKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/support-faq.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const supportFaqKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.support-faq',\n version: 1,\n category: 'operational',\n displayName: 'Support FAQ',\n title: 'Support & Success FAQ',\n description: 'Operational knowledge base for customer support and success.',\n domain: 'support',\n owners: ['platform.support'],\n tags: ['knowledge', 'support'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: 365,\n archiveAfterDays: 180,\n },\n access: {\n policy: { name: 'knowledge.access.support', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'text-embedding-3-small',\n chunkSize: 700,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'Operational FAQs, runbooks, and customer success playbooks augmented with automation updates.',\n};\n\nexport function registerSupportFaqKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(supportFaqKnowledgeSpace);\n}\n"],"mappings":"mDAGA,MAAaA,EAA+C,CAC1D,KAAM,CACJ,IAAK,wBACL,QAAS,EACT,SAAU,cACV,YAAa,cACb,MAAO,wBACP,YAAa,+DACb,OAAQ,UACR,OAAQ,CAAC,mBAAmB,CAC5B,KAAM,CAAC,YAAa,UAAU,CAC9B,UAAW,EAAc,KAC1B,CACD,UAAW,CACT,QAAS,IACT,iBAAkB,IACnB,CACD,OAAQ,CACN,OAAQ,CAAE,KAAM,2BAA4B,QAAS,EAAG,CACxD,WAAY,SACZ,mBAAoB,GACrB,CACD,SAAU,CACR,eAAgB,yBAChB,UAAW,IACX,oBAAqB,kBACtB,CACD,YACE,gGACH,CAED,SAAgB,EACd,EACwB,CACxB,OAAO,EAAS,SAAS,EAAyB"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"uploaded-docs.js","names":["uploadedDocsKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/uploaded-docs.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const uploadedDocsKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.uploaded-docs',\n version: 1,\n category: 'external',\n displayName: 'Uploaded Documents',\n title: 'Uploaded Knowledge Assets',\n description:\n 'Documents uploaded by households, including invoices, contracts, and reference files.',\n domain: 'operations',\n owners: ['platform.operations'],\n tags: ['documents', 'storage'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: null,\n },\n access: {\n policy: { name: 'knowledge.access.uploaded-docs', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 900,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'User-provided documents normalized and embedded for retrieval augmented workflows.',\n};\n\nexport function registerUploadedDocsKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(uploadedDocsKnowledgeSpace);\n}\n
|
|
1
|
+
{"version":3,"file":"uploaded-docs.js","names":["uploadedDocsKnowledgeSpace: KnowledgeSpaceSpec"],"sources":["../../../src/knowledge/spaces/uploaded-docs.ts"],"sourcesContent":["import { StabilityEnum } from '../../ownership';\nimport type { KnowledgeSpaceRegistry, KnowledgeSpaceSpec } from '../spec';\n\nexport const uploadedDocsKnowledgeSpace: KnowledgeSpaceSpec = {\n meta: {\n key: 'knowledge.uploaded-docs',\n version: 1,\n category: 'external',\n displayName: 'Uploaded Documents',\n title: 'Uploaded Knowledge Assets',\n description:\n 'Documents uploaded by households, including invoices, contracts, and reference files.',\n domain: 'operations',\n owners: ['platform.operations'],\n tags: ['documents', 'storage'],\n stability: StabilityEnum.Beta,\n },\n retention: {\n ttlDays: null,\n },\n access: {\n policy: { name: 'knowledge.access.uploaded-docs', version: 1 },\n trustLevel: 'medium',\n automationWritable: true,\n },\n indexing: {\n embeddingModel: 'mistral-embed',\n chunkSize: 900,\n vectorDbIntegration: 'vectordb.qdrant',\n },\n description:\n 'User-provided documents normalized and embedded for retrieval augmented workflows.',\n};\n\nexport function registerUploadedDocsKnowledgeSpace(\n registry: KnowledgeSpaceRegistry\n): KnowledgeSpaceRegistry {\n return registry.register(uploadedDocsKnowledgeSpace);\n}\n"],"mappings":"mDAGA,MAAaA,EAAiD,CAC5D,KAAM,CACJ,IAAK,0BACL,QAAS,EACT,SAAU,WACV,YAAa,qBACb,MAAO,4BACP,YACE,wFACF,OAAQ,aACR,OAAQ,CAAC,sBAAsB,CAC/B,KAAM,CAAC,YAAa,UAAU,CAC9B,UAAW,EAAc,KAC1B,CACD,UAAW,CACT,QAAS,KACV,CACD,OAAQ,CACN,OAAQ,CAAE,KAAM,iCAAkC,QAAS,EAAG,CAC9D,WAAY,SACZ,mBAAoB,GACrB,CACD,SAAU,CACR,eAAgB,gBAChB,UAAW,IACX,oBAAqB,kBACtB,CACD,YACE,qFACH,CAED,SAAgB,EACd,EACwB,CACxB,OAAO,EAAS,SAAS,EAA2B"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"spec.js","names":["latest: KnowledgeSpaceSpec | undefined"],"sources":["../../src/knowledge/spec.ts"],"sourcesContent":["import type { OwnerShipMeta } from '../ownership';\nimport type { PolicyRef } from '../policy/spec';\n\nexport type KnowledgeCategory =\n | 'canonical'\n | 'operational'\n | 'external'\n | 'ephemeral'
|
|
1
|
+
{"version":3,"file":"spec.js","names":["latest: KnowledgeSpaceSpec | undefined"],"sources":["../../src/knowledge/spec.ts"],"sourcesContent":["import type { OwnerShipMeta } from '../ownership';\nimport type { PolicyRef } from '../policy/spec';\n\nexport type KnowledgeCategory =\n | 'canonical' // Ground truth - product specs, schemas, official policies\n | 'operational' // Internal docs - support tickets, runbooks, sales materials\n | 'external' // Third-party - PSP docs, regulations, integration guides\n | 'ephemeral'; // Temporary - agent scratchpads, session context, drafts\n\nexport interface KnowledgeSpaceMeta extends OwnerShipMeta {\n /** Stable space identifier (e.g., \"product-canon\", \"support-faq\"). */\n key: string;\n version: number;\n category: KnowledgeCategory;\n displayName: string;\n}\n\nexport interface KnowledgeRetentionPolicy {\n /** TTL in days (null = indefinite). */\n ttlDays?: number | null;\n /** Auto-archive after inactivity. */\n archiveAfterDays?: number;\n}\n\nexport interface KnowledgeAccessPolicy {\n /** Which PolicySpec governs access. */\n policy?: PolicyRef;\n /** Trust level for agent/workflow consumption. */\n trustLevel: 'high' | 'medium' | 'low';\n /** Can this space be mutated by automation? */\n automationWritable: boolean;\n}\n\nexport interface KnowledgeIndexingConfig {\n embeddingModel?: string;\n chunkSize?: number;\n vectorDbIntegration?: string;\n}\n\nexport interface KnowledgeSpaceSpec {\n meta: KnowledgeSpaceMeta;\n /** Retention and cleanup rules. */\n retention: KnowledgeRetentionPolicy;\n /** Access control and trust. */\n access: KnowledgeAccessPolicy;\n /** Optional embedding/indexing config. */\n indexing?: KnowledgeIndexingConfig;\n /** Documentation. */\n description?: string;\n}\n\nconst knowledgeKey = (meta: Pick<KnowledgeSpaceMeta, 'key' | 'version'>) =>\n `${meta.key}.v${meta.version}`;\n\nexport class KnowledgeSpaceRegistry {\n private readonly items = new Map<string, KnowledgeSpaceSpec>();\n\n register(spec: KnowledgeSpaceSpec): this {\n const key = knowledgeKey(spec.meta);\n if (this.items.has(key)) {\n throw new Error(`Duplicate KnowledgeSpaceSpec ${key}`);\n }\n this.items.set(key, spec);\n return this;\n }\n\n list(): KnowledgeSpaceSpec[] {\n return [...this.items.values()];\n }\n\n get(key: string, version?: number): KnowledgeSpaceSpec | undefined {\n if (version != null) {\n return this.items.get(knowledgeKey({ key, version }));\n }\n let latest: KnowledgeSpaceSpec | undefined;\n let maxVersion = -Infinity;\n for (const spec of this.items.values()) {\n if (spec.meta.key !== key) continue;\n if (spec.meta.version > maxVersion) {\n maxVersion = spec.meta.version;\n latest = spec;\n }\n }\n return latest;\n }\n\n getByCategory(category: KnowledgeCategory): KnowledgeSpaceSpec[] {\n return this.list().filter((spec) => spec.meta.category === category);\n }\n}\n\nexport function makeKnowledgeSpaceKey(meta: KnowledgeSpaceMeta) {\n return knowledgeKey(meta);\n}\n"],"mappings":"AAmDA,MAAM,EAAgB,GACpB,GAAG,EAAK,IAAI,IAAI,EAAK,UAEvB,IAAa,EAAb,KAAoC,CAClC,MAAyB,IAAI,IAE7B,SAAS,EAAgC,CACvC,IAAM,EAAM,EAAa,EAAK,KAAK,CACnC,GAAI,KAAK,MAAM,IAAI,EAAI,CACrB,MAAU,MAAM,gCAAgC,IAAM,CAGxD,OADA,KAAK,MAAM,IAAI,EAAK,EAAK,CAClB,KAGT,MAA6B,CAC3B,MAAO,CAAC,GAAG,KAAK,MAAM,QAAQ,CAAC,CAGjC,IAAI,EAAa,EAAkD,CACjE,GAAI,GAAW,KACb,OAAO,KAAK,MAAM,IAAI,EAAa,CAAE,MAAK,UAAS,CAAC,CAAC,CAEvD,IAAIA,EACA,EAAa,KACjB,IAAK,IAAM,KAAQ,KAAK,MAAM,QAAQ,CAChC,EAAK,KAAK,MAAQ,GAClB,EAAK,KAAK,QAAU,IACtB,EAAa,EAAK,KAAK,QACvB,EAAS,GAGb,OAAO,EAGT,cAAc,EAAmD,CAC/D,OAAO,KAAK,MAAM,CAAC,OAAQ,GAAS,EAAK,KAAK,WAAa,EAAS,GAIxE,SAAgB,EAAsB,EAA0B,CAC9D,OAAO,EAAa,EAAK"}
|
package/dist/migrations.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"migrations.d.ts","names":[],"sources":["../src/migrations.ts"],"sourcesContent":[],"mappings":";;;KAEY,iBAAA;UAEK,cAAA;EAFL,WAAA,EAAA,MAAA;EAEK,UAAA,EAAA,MAAc;AAK/B;AACQ,UADS,iBAAA,CACT;EAIM,IAAA,EAJN,iBAIM;EACC,WAAA,CAAA,EAAA,MAAA;EAAc,SAAA,CAAA,EAAA,MAAA;EAGZ,OAAA,CAAA,EAAA,MAAA;EAKA,SAAA,CAAA,EATH,cASqB,EAAA;EAKlB,UAAA,CAAA,EAbF,cAa0B,EAAA;AAKzC;AACI,UAhBa,mBAAA,SAA4B,iBAgBzC,CAAA;EACA,IAAA,EAAA,QAAA;EACA,GAAA,EAAA,MAAA;;AAEa,UAfA,iBAAA,SAA0B,iBAeS,CAAA;EAOnC,IAAA,EAAA,MAAA;EAKA,MAAA,EAAA,MAAA;AAQjB;AAGiB,UAjCA,uBAAA,SAAgC,iBAiChC,CAAA;
|
|
1
|
+
{"version":3,"file":"migrations.d.ts","names":[],"sources":["../src/migrations.ts"],"sourcesContent":[],"mappings":";;;KAEY,iBAAA;UAEK,cAAA;EAFL,WAAA,EAAA,MAAA;EAEK,UAAA,EAAA,MAAc;AAK/B;AACQ,UADS,iBAAA,CACT;EAIM,IAAA,EAJN,iBAIM;EACC,WAAA,CAAA,EAAA,MAAA;EAAc,SAAA,CAAA,EAAA,MAAA;EAGZ,OAAA,CAAA,EAAA,MAAA;EAKA,SAAA,CAAA,EATH,cASqB,EAAA;EAKlB,UAAA,CAAA,EAbF,cAa0B,EAAA;AAKzC;AACI,UAhBa,mBAAA,SAA4B,iBAgBzC,CAAA;EACA,IAAA,EAAA,QAAA;EACA,GAAA,EAAA,MAAA;;AAEa,UAfA,iBAAA,SAA0B,iBAeS,CAAA;EAOnC,IAAA,EAAA,MAAA;EAKA,MAAA,EAAA,MAAA;AAQjB;AAGiB,UAjCA,uBAAA,SAAgC,iBAiChC,CAAA;EAOP,IAAA,EAAA,YAAA;EAS6B,SAAA,EAAA,MAAA;;KA5C3B,aAAA,GACR,sBACA,oBACA;UAEa,aAAA,SAAsB;;;;;;UAOtB,aAAA;MACX;SACG;;UAGQ,aAAA;QACT;QACA;;;cAMK,iBAAA;;iBAGI;UAOP;uCAS6B"}
|
package/dist/migrations.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"migrations.js","names":["candidate: MigrationSpec | undefined"],"sources":["../src/migrations.ts"],"sourcesContent":["import type { OwnerShipMeta } from './ownership';\n\nexport type MigrationStepKind = 'schema' | 'data' | 'validation';\n\nexport interface MigrationCheck {\n description: string;\n expression: string;\n}\n\nexport interface MigrationStepBase {\n kind: MigrationStepKind;\n description?: string;\n timeoutMs?: number;\n retries?: number;\n preChecks?: MigrationCheck[];\n postChecks?: MigrationCheck[];\n}\n\nexport interface SchemaMigrationStep extends MigrationStepBase {\n kind: 'schema';\n sql: string;\n}\n\nexport interface DataMigrationStep extends MigrationStepBase {\n kind: 'data';\n script: string;\n}\n\nexport interface ValidationMigrationStep extends MigrationStepBase {\n kind: 'validation';\n assertion: string;\n}\n\nexport type MigrationStep =\n | SchemaMigrationStep\n | DataMigrationStep\n | ValidationMigrationStep;\n\nexport interface MigrationMeta extends OwnerShipMeta {\n /** Fully qualified migration name (e.g., \"sigil.db.2025_01_add_users\"). */\n name: string;\n /** Increment when the migration changes. */\n version: number;\n}\n\nexport interface MigrationPlan {\n up: MigrationStep[];\n down?: MigrationStep[];\n}\n\nexport interface MigrationSpec {\n meta: MigrationMeta;\n plan: MigrationPlan;\n dependencies?: string[];\n}\n\nconst migrationKey = (name: string, version: number) => `${name}.v${version}`;\n\nexport class MigrationRegistry {\n private readonly items = new Map<string, MigrationSpec>();\n\n register(spec: MigrationSpec): this {\n const key = migrationKey(spec.meta.name, spec.meta.version);\n if (this.items.has(key))
|
|
1
|
+
{"version":3,"file":"migrations.js","names":["candidate: MigrationSpec | undefined"],"sources":["../src/migrations.ts"],"sourcesContent":["import type { OwnerShipMeta } from './ownership';\n\nexport type MigrationStepKind = 'schema' | 'data' | 'validation';\n\nexport interface MigrationCheck {\n description: string;\n expression: string;\n}\n\nexport interface MigrationStepBase {\n kind: MigrationStepKind;\n description?: string;\n timeoutMs?: number;\n retries?: number;\n preChecks?: MigrationCheck[];\n postChecks?: MigrationCheck[];\n}\n\nexport interface SchemaMigrationStep extends MigrationStepBase {\n kind: 'schema';\n sql: string;\n}\n\nexport interface DataMigrationStep extends MigrationStepBase {\n kind: 'data';\n script: string;\n}\n\nexport interface ValidationMigrationStep extends MigrationStepBase {\n kind: 'validation';\n assertion: string;\n}\n\nexport type MigrationStep =\n | SchemaMigrationStep\n | DataMigrationStep\n | ValidationMigrationStep;\n\nexport interface MigrationMeta extends OwnerShipMeta {\n /** Fully qualified migration name (e.g., \"sigil.db.2025_01_add_users\"). */\n name: string;\n /** Increment when the migration changes. */\n version: number;\n}\n\nexport interface MigrationPlan {\n up: MigrationStep[];\n down?: MigrationStep[];\n}\n\nexport interface MigrationSpec {\n meta: MigrationMeta;\n plan: MigrationPlan;\n dependencies?: string[];\n}\n\nconst migrationKey = (name: string, version: number) => `${name}.v${version}`;\n\nexport class MigrationRegistry {\n private readonly items = new Map<string, MigrationSpec>();\n\n register(spec: MigrationSpec): this {\n const key = migrationKey(spec.meta.name, spec.meta.version);\n if (this.items.has(key)) throw new Error(`Duplicate migration ${key}`);\n this.items.set(key, spec);\n return this;\n }\n\n list(): MigrationSpec[] {\n return [...this.items.values()].sort((a, b) =>\n compareKey(\n migrationKey(a.meta.name, a.meta.version),\n migrationKey(b.meta.name, b.meta.version)\n )\n );\n }\n\n get(name: string, version?: number): MigrationSpec | undefined {\n if (version != null) return this.items.get(migrationKey(name, version));\n let candidate: MigrationSpec | undefined;\n let max = -Infinity;\n for (const spec of this.items.values()) {\n if (spec.meta.name !== name) continue;\n if (spec.meta.version > max) {\n max = spec.meta.version;\n candidate = spec;\n }\n }\n return candidate;\n }\n}\n\nfunction compareKey(a: string, b: string) {\n return a < b ? -1 : a > b ? 1 : 0;\n}\n"],"mappings":"AAwDA,MAAM,GAAgB,EAAc,IAAoB,GAAG,EAAK,IAAI,IAEpE,IAAa,EAAb,KAA+B,CAC7B,MAAyB,IAAI,IAE7B,SAAS,EAA2B,CAClC,IAAM,EAAM,EAAa,EAAK,KAAK,KAAM,EAAK,KAAK,QAAQ,CAC3D,GAAI,KAAK,MAAM,IAAI,EAAI,CAAE,MAAU,MAAM,uBAAuB,IAAM,CAEtE,OADA,KAAK,MAAM,IAAI,EAAK,EAAK,CAClB,KAGT,MAAwB,CACtB,MAAO,CAAC,GAAG,KAAK,MAAM,QAAQ,CAAC,CAAC,MAAM,EAAG,IACvC,EACE,EAAa,EAAE,KAAK,KAAM,EAAE,KAAK,QAAQ,CACzC,EAAa,EAAE,KAAK,KAAM,EAAE,KAAK,QAAQ,CAC1C,CACF,CAGH,IAAI,EAAc,EAA6C,CAC7D,GAAI,GAAW,KAAM,OAAO,KAAK,MAAM,IAAI,EAAa,EAAM,EAAQ,CAAC,CACvE,IAAIA,EACA,EAAM,KACV,IAAK,IAAM,KAAQ,KAAK,MAAM,QAAQ,CAChC,EAAK,KAAK,OAAS,GACnB,EAAK,KAAK,QAAU,IACtB,EAAM,EAAK,KAAK,QAChB,EAAY,GAGhB,OAAO,IAIX,SAAS,EAAW,EAAW,EAAW,CACxC,OAAO,EAAI,EAAI,GAAK,EAAI,EAAI,EAAI"}
|
|
@@ -1,133 +1,135 @@
|
|
|
1
1
|
import { ContractSpec } from "./spec.js";
|
|
2
|
+
import * as _lssm_lib_schema0 from "@lssm/lib.schema";
|
|
3
|
+
import { SchemaModel } from "@lssm/lib.schema";
|
|
2
4
|
|
|
3
5
|
//#region src/onboarding-base.d.ts
|
|
4
6
|
/** Save/update onboarding draft (auto-save during flow) */
|
|
5
7
|
declare const SaveOnboardingDraftInput: SchemaModel<{
|
|
6
8
|
data: {
|
|
7
|
-
type:
|
|
9
|
+
type: _lssm_lib_schema0.FieldType<unknown, unknown>;
|
|
8
10
|
isOptional: false;
|
|
9
11
|
};
|
|
10
12
|
}>;
|
|
11
13
|
declare const SaveOnboardingDraftOutput: SchemaModel<{
|
|
12
14
|
id: {
|
|
13
|
-
type:
|
|
15
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
14
16
|
isOptional: false;
|
|
15
17
|
};
|
|
16
18
|
organizationId: {
|
|
17
|
-
type:
|
|
19
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
18
20
|
isOptional: false;
|
|
19
21
|
};
|
|
20
22
|
}>;
|
|
21
23
|
declare const SaveOnboardingDraftBaseSpec: ContractSpec<SchemaModel<{
|
|
22
24
|
data: {
|
|
23
|
-
type:
|
|
25
|
+
type: _lssm_lib_schema0.FieldType<unknown, unknown>;
|
|
24
26
|
isOptional: false;
|
|
25
27
|
};
|
|
26
28
|
}>, SchemaModel<{
|
|
27
29
|
id: {
|
|
28
|
-
type:
|
|
30
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
29
31
|
isOptional: false;
|
|
30
32
|
};
|
|
31
33
|
organizationId: {
|
|
32
|
-
type:
|
|
34
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
33
35
|
isOptional: false;
|
|
34
36
|
};
|
|
35
37
|
}>, undefined>;
|
|
36
38
|
/** Get current onboarding draft (on mount/restore) */
|
|
37
39
|
declare const GetOnboardingDraftOutput: SchemaModel<{
|
|
38
40
|
id: {
|
|
39
|
-
type:
|
|
41
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
40
42
|
isOptional: true;
|
|
41
43
|
};
|
|
42
44
|
organizationId: {
|
|
43
|
-
type:
|
|
45
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
44
46
|
isOptional: true;
|
|
45
47
|
};
|
|
46
48
|
data: {
|
|
47
|
-
type:
|
|
49
|
+
type: _lssm_lib_schema0.FieldType<unknown, unknown>;
|
|
48
50
|
isOptional: true;
|
|
49
51
|
};
|
|
50
52
|
createdAt: {
|
|
51
|
-
type:
|
|
53
|
+
type: _lssm_lib_schema0.FieldType<Date, string>;
|
|
52
54
|
isOptional: true;
|
|
53
55
|
};
|
|
54
56
|
updatedAt: {
|
|
55
|
-
type:
|
|
57
|
+
type: _lssm_lib_schema0.FieldType<Date, string>;
|
|
56
58
|
isOptional: true;
|
|
57
59
|
};
|
|
58
60
|
}>;
|
|
59
|
-
declare const GetOnboardingDraftBaseSpec: ContractSpec<
|
|
61
|
+
declare const GetOnboardingDraftBaseSpec: ContractSpec<_lssm_lib_schema0.AnySchemaModel, SchemaModel<{
|
|
60
62
|
id: {
|
|
61
|
-
type:
|
|
63
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
62
64
|
isOptional: true;
|
|
63
65
|
};
|
|
64
66
|
organizationId: {
|
|
65
|
-
type:
|
|
67
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
66
68
|
isOptional: true;
|
|
67
69
|
};
|
|
68
70
|
data: {
|
|
69
|
-
type:
|
|
71
|
+
type: _lssm_lib_schema0.FieldType<unknown, unknown>;
|
|
70
72
|
isOptional: true;
|
|
71
73
|
};
|
|
72
74
|
createdAt: {
|
|
73
|
-
type:
|
|
75
|
+
type: _lssm_lib_schema0.FieldType<Date, string>;
|
|
74
76
|
isOptional: true;
|
|
75
77
|
};
|
|
76
78
|
updatedAt: {
|
|
77
|
-
type:
|
|
79
|
+
type: _lssm_lib_schema0.FieldType<Date, string>;
|
|
78
80
|
isOptional: true;
|
|
79
81
|
};
|
|
80
82
|
}>, undefined>;
|
|
81
83
|
/** Delete onboarding draft (cleanup after completion or cancel) */
|
|
82
84
|
declare const DeleteOnboardingDraftOutput: SchemaModel<{
|
|
83
85
|
ok: {
|
|
84
|
-
type:
|
|
86
|
+
type: _lssm_lib_schema0.FieldType<boolean, boolean>;
|
|
85
87
|
isOptional: false;
|
|
86
88
|
};
|
|
87
89
|
}>;
|
|
88
|
-
declare const DeleteOnboardingDraftBaseSpec: ContractSpec<
|
|
90
|
+
declare const DeleteOnboardingDraftBaseSpec: ContractSpec<_lssm_lib_schema0.AnySchemaModel, SchemaModel<{
|
|
89
91
|
ok: {
|
|
90
|
-
type:
|
|
92
|
+
type: _lssm_lib_schema0.FieldType<boolean, boolean>;
|
|
91
93
|
isOptional: false;
|
|
92
94
|
};
|
|
93
95
|
}>, undefined>;
|
|
94
96
|
/** Complete onboarding (final submit, creates entities) */
|
|
95
97
|
declare const CompleteOnboardingBaseInput: SchemaModel<{
|
|
96
98
|
data: {
|
|
97
|
-
type:
|
|
99
|
+
type: _lssm_lib_schema0.FieldType<unknown, unknown>;
|
|
98
100
|
isOptional: false;
|
|
99
101
|
};
|
|
100
102
|
}>;
|
|
101
103
|
declare const CompleteOnboardingBaseOutput: SchemaModel<{
|
|
102
104
|
success: {
|
|
103
|
-
type:
|
|
105
|
+
type: _lssm_lib_schema0.FieldType<boolean, boolean>;
|
|
104
106
|
isOptional: false;
|
|
105
107
|
};
|
|
106
108
|
userId: {
|
|
107
|
-
type:
|
|
109
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
108
110
|
isOptional: true;
|
|
109
111
|
};
|
|
110
112
|
organizationId: {
|
|
111
|
-
type:
|
|
113
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
112
114
|
isOptional: true;
|
|
113
115
|
};
|
|
114
116
|
}>;
|
|
115
117
|
declare const CompleteOnboardingBaseSpec: ContractSpec<SchemaModel<{
|
|
116
118
|
data: {
|
|
117
|
-
type:
|
|
119
|
+
type: _lssm_lib_schema0.FieldType<unknown, unknown>;
|
|
118
120
|
isOptional: false;
|
|
119
121
|
};
|
|
120
122
|
}>, SchemaModel<{
|
|
121
123
|
success: {
|
|
122
|
-
type:
|
|
124
|
+
type: _lssm_lib_schema0.FieldType<boolean, boolean>;
|
|
123
125
|
isOptional: false;
|
|
124
126
|
};
|
|
125
127
|
userId: {
|
|
126
|
-
type:
|
|
128
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
127
129
|
isOptional: true;
|
|
128
130
|
};
|
|
129
131
|
organizationId: {
|
|
130
|
-
type:
|
|
132
|
+
type: _lssm_lib_schema0.FieldType<string, string>;
|
|
131
133
|
isOptional: true;
|
|
132
134
|
};
|
|
133
135
|
}>, undefined>;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"onboarding-base.d.ts","names":[],"sources":["../src/onboarding-base.ts"],"sourcesContent":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"onboarding-base.d.ts","names":[],"sources":["../src/onboarding-base.ts"],"sourcesContent":[],"mappings":";;;;;;cASa,0BAAwB;;UAMnC,iBAAA,CAAA;IANW,UAAA,EAAA,KAAA;EAQA,CAAA;CAOX,CAAA;cAPW,2BAAyB;EAAA,EAAA,EAAA;IAAA,IAAA,EAOpC,iBAAA,CAAA,SAPoC,CAAA,MAAA,EAAA,MAAA,CAAA;IASzB,UAAA,EAAA,KAAA;EAwBX,CAAA;EAxBsC,cAAA,EAAA;IAAA,IAAA,6BAAA,CAAA,MAAA,EAAA,MAAA,CAAA;;;;AAAA,cAA3B,2BAA2B,cAAA,CAAA,WAAA,CAAA;EA2B3B,IAAA,EAAA;IAUX,IAAA,EAbA,iBAAA,CAAA,SAaA,CAAA,OAAA,EAAA,OAAA,CAAA;;;;;UArCsC,iBAAA,CAAA;;EA2BH,CAAA;EAAA,cAAA,EAAA;IAYxB,IAAA,6BAuBX,CAAA,MAAA,EAAA,MAAA,CAAA;IAAA,UAAA,EAvBqC,KAAA;EAAA,CAAA;;;cAZ1B,0BAAwB;;UAUnC,iBAAA,CAAA;;EAEqC,CAAA;EAAA,cAAA,EAAA;IAAA,IAAA,6BAAA,CAAA,MAAA,EAAA,MAAA,CAAA;IA0B1B,UAAA,EAAA,IAAA;EAQA,CAAA;EAuBX,IAAA,EAAA;IAvBwC,IAAA,6BAAA,CAAA,OAAA,EAAA,OAAA,CAAA;IAAA,UAAA,EAAA,IAAA;EAAA,CAAA;EAAA,SAAA,EAAA;IA0B7B,IAAA,6BAMX,KAAA,EAAA,MAAA,CAAA;IAEW,UAAA,EAAA,IAAA;EAQX,CAAA;;;IARuC,UAAA,EAAA,IAAA;EAAA,CAAA;AAUzC,CAAA,CAAA;AAwBE,cAtGW,0BAsGX,EAtGqC,YAsGrC,CA/EA,iBAAA,CAvBqC,cAAA,EAAA,WAsGrC,CAAA;EAxBqC,EAAA,EAAA;IAAA,IAAA,EA9EA,iBAAA,CAAA,SA8EA,CAAA,MAAA,EAAA,MAAA,CAAA;;;;;IAAA,UAAA,EAAA,IAAA;;;;;;;;;;;;;;;;cApD1B,6BAA2B;;UAMtC,iBAAA,CAAA;;;;cAEW,+BAA6B,aAuBxC,iBAAA,CAvBwC,cAAA,EAAA;;UAAA,iBAAA,CAAA;;;;;cA0B7B,6BAA2B;;UAMtC,iBAAA,CAAA;;;;cAEW,8BAA4B;;UAQvC,iBAAA,CAAA;;;;;;;;;;;;cAEW,yCAA0B;;UAwBrC,iBAAA,CAAA;;;;;UAxBqC,iBAAA,CAAA"}
|
package/dist/onboarding-base.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{
|
|
1
|
+
import{l as e}from"./schema/dist/ScalarTypeEnum.js";import{t}from"./schema/dist/SchemaModel.js";import"./schema/dist/index.js";import{defineCommand as n,defineQuery as r}from"./spec.js";import{OwnersEnum as i,StabilityEnum as a}from"./ownership.js";const o=new t({name:`SaveOnboardingDraftInput`,description:`Input for saving onboarding draft`,fields:{data:{type:e.JSON(),isOptional:!1}}}),s=new t({name:`SaveOnboardingDraftOutput`,description:`Output for saving onboarding draft`,fields:{id:{type:e.ID(),isOptional:!1},organizationId:{type:e.ID(),isOptional:!1}}}),c=n({meta:{name:`base.onboarding.saveDraft`,version:1,stability:a.Beta,owners:[i.PlatformSigil],tags:[`onboarding`,`draft`],description:`Save or update onboarding draft for active organization`,goal:`Persist onboarding progress incrementally for resumption and safety`,context:`Auto-saves every few seconds during onboarding; enables users to leave and resume`},io:{input:o,output:s},policy:{auth:`user`,escalate:null},transport:{gql:{field:`saveOnboardingDraft`},rest:{method:`POST`}}}),l=new t({name:`GetOnboardingDraftOutput`,description:`Onboarding draft payload`,fields:{id:{type:e.ID(),isOptional:!0},organizationId:{type:e.ID(),isOptional:!0},data:{type:e.JSON(),isOptional:!0},createdAt:{type:e.DateTime(),isOptional:!0},updatedAt:{type:e.DateTime(),isOptional:!0}}}),u=r({meta:{name:`base.onboarding.getDraft`,version:1,stability:a.Beta,owners:[i.PlatformSigil],tags:[`onboarding`,`draft`],description:`Get onboarding draft for active organization`,goal:`Retrieve saved onboarding progress`,context:`Called on mount to restore in-progress onboarding`},io:{input:null,output:l},policy:{auth:`user`,escalate:null},transport:{gql:{field:`getOnboardingDraft`},rest:{method:`GET`}}}),d=new t({name:`DeleteOnboardingDraftOutput`,description:`Result of delete operation`,fields:{ok:{type:e.Boolean(),isOptional:!1}}}),f=n({meta:{name:`base.onboarding.deleteDraft`,version:1,stability:a.Beta,owners:[i.PlatformSigil],tags:[`onboarding`,`draft`],description:`Delete onboarding draft for active organization`,goal:`Clear draft after completion or if user wants to restart`,context:`Called after successful onboarding or explicit user reset`},io:{input:null,output:d},policy:{auth:`user`,escalate:null},transport:{gql:{field:`deleteOnboardingDraft`},rest:{method:`POST`}}}),p=new t({name:`CompleteOnboardingBaseInput`,description:`Input for completing onboarding`,fields:{data:{type:e.JSON(),isOptional:!1}}}),m=new t({name:`CompleteOnboardingBaseOutput`,description:`Result of onboarding completion`,fields:{success:{type:e.Boolean(),isOptional:!1},userId:{type:e.ID(),isOptional:!0},organizationId:{type:e.ID(),isOptional:!0}}}),h=n({meta:{name:`base.onboarding.complete`,version:1,stability:a.Beta,owners:[i.PlatformSigil],tags:[`onboarding`],description:`Complete onboarding and finalize user/organization setup`,goal:`Transition from draft to active profile`,context:`Validates all required fields, creates/updates entities, marks onboarding complete`},io:{input:p,output:m},policy:{auth:`user`,escalate:null},transport:{gql:{field:`completeOnboarding`},rest:{method:`POST`}}});export{p as CompleteOnboardingBaseInput,m as CompleteOnboardingBaseOutput,h as CompleteOnboardingBaseSpec,f as DeleteOnboardingDraftBaseSpec,d as DeleteOnboardingDraftOutput,u as GetOnboardingDraftBaseSpec,l as GetOnboardingDraftOutput,c as SaveOnboardingDraftBaseSpec,o as SaveOnboardingDraftInput,s as SaveOnboardingDraftOutput};
|
|
2
2
|
//# sourceMappingURL=onboarding-base.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"onboarding-base.js","names":[],"sources":["../src/onboarding-base.ts"],"sourcesContent":["/**\n * Shared base contracts for onboarding flows across verticals.\n * These operations are reusable for any app that needs multi-step onboarding with draft persistence.\n */\nimport { defineCommand, defineQuery } from './spec';\nimport { ScalarTypeEnum, SchemaModel } from '@lssm/lib.schema';\nimport { OwnersEnum, StabilityEnum } from './ownership';\n\n/** Save/update onboarding draft (auto-save during flow) */\nexport const SaveOnboardingDraftInput = new SchemaModel({\n name: 'SaveOnboardingDraftInput',\n description: 'Input for saving onboarding draft',\n fields: {\n data: { type: ScalarTypeEnum.JSON(), isOptional: false },\n },\n});\n\nexport const SaveOnboardingDraftOutput = new SchemaModel({\n name: 'SaveOnboardingDraftOutput',\n description: 'Output for saving onboarding draft',\n fields: {\n id: { type: ScalarTypeEnum.ID(), isOptional: false },\n organizationId: { type: ScalarTypeEnum.ID(), isOptional: false },\n },\n});\n\nexport const SaveOnboardingDraftBaseSpec = defineCommand({\n meta: {\n name: 'base.onboarding.saveDraft',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding', 'draft'],\n description: 'Save or update onboarding draft for active organization',\n goal: 'Persist onboarding progress incrementally for resumption and safety',\n context:\n 'Auto-saves every few seconds during onboarding; enables users to leave and resume',\n },\n io: {\n input: SaveOnboardingDraftInput,\n output: SaveOnboardingDraftOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'saveOnboardingDraft' },\n rest: { method: 'POST' },\n },\n});\n\n/** Get current onboarding draft (on mount/restore) */\nexport const GetOnboardingDraftOutput = new SchemaModel({\n name: 'GetOnboardingDraftOutput',\n description: 'Onboarding draft payload',\n fields: {\n id: { type: ScalarTypeEnum.ID(), isOptional: true },\n organizationId: { type: ScalarTypeEnum.ID(), isOptional: true },\n data: { type: ScalarTypeEnum.JSON(), isOptional: true },\n createdAt: { type: ScalarTypeEnum.DateTime(), isOptional: true },\n updatedAt: { type: ScalarTypeEnum.DateTime(), isOptional: true },\n },\n});\n\nexport const GetOnboardingDraftBaseSpec = defineQuery({\n meta: {\n name: 'base.onboarding.getDraft',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding', 'draft'],\n description: 'Get onboarding draft for active organization',\n goal: 'Retrieve saved onboarding progress',\n context: 'Called on mount to restore in-progress onboarding',\n },\n io: {\n input: null,\n output: GetOnboardingDraftOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'getOnboardingDraft' },\n rest: { method: 'GET' },\n },\n});\n\n/** Delete onboarding draft (cleanup after completion or cancel) */\nexport const DeleteOnboardingDraftOutput = new SchemaModel({\n name: 'DeleteOnboardingDraftOutput',\n description: 'Result of delete operation',\n fields: {\n ok: { type: ScalarTypeEnum.Boolean(), isOptional: false },\n },\n});\n\nexport const DeleteOnboardingDraftBaseSpec = defineCommand({\n meta: {\n name: 'base.onboarding.deleteDraft',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding', 'draft'],\n description: 'Delete onboarding draft for active organization',\n goal: 'Clear draft after completion or if user wants to restart',\n context: 'Called after successful onboarding or explicit user reset',\n },\n io: {\n input: null,\n output: DeleteOnboardingDraftOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'deleteOnboardingDraft' },\n rest: { method: 'POST' },\n },\n});\n\n/** Complete onboarding (final submit, creates entities) */\nexport const CompleteOnboardingBaseInput = new SchemaModel({\n name: 'CompleteOnboardingBaseInput',\n description: 'Input for completing onboarding',\n fields: {\n data: { type: ScalarTypeEnum.JSON(), isOptional: false },\n },\n});\n\nexport const CompleteOnboardingBaseOutput = new SchemaModel({\n name: 'CompleteOnboardingBaseOutput',\n description: 'Result of onboarding completion',\n fields: {\n success: { type: ScalarTypeEnum.Boolean(), isOptional: false },\n userId: { type: ScalarTypeEnum.ID(), isOptional: true },\n organizationId: { type: ScalarTypeEnum.ID(), isOptional: true },\n },\n});\n\nexport const CompleteOnboardingBaseSpec = defineCommand({\n meta: {\n name: 'base.onboarding.complete',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding'],\n description: 'Complete onboarding and finalize user/organization setup',\n goal: 'Transition from draft to active profile',\n context:\n 'Validates all required fields, creates/updates entities, marks onboarding complete',\n },\n io: {\n input: CompleteOnboardingBaseInput,\n output: CompleteOnboardingBaseOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'completeOnboarding' },\n rest: { method: 'POST' },\n },\n});\n"],"mappings":"
|
|
1
|
+
{"version":3,"file":"onboarding-base.js","names":["SchemaModel","ScalarTypeEnum"],"sources":["../src/onboarding-base.ts"],"sourcesContent":["/**\n * Shared base contracts for onboarding flows across verticals.\n * These operations are reusable for any app that needs multi-step onboarding with draft persistence.\n */\nimport { defineCommand, defineQuery } from './spec';\nimport { ScalarTypeEnum, SchemaModel } from '@lssm/lib.schema';\nimport { OwnersEnum, StabilityEnum } from './ownership';\n\n/** Save/update onboarding draft (auto-save during flow) */\nexport const SaveOnboardingDraftInput = new SchemaModel({\n name: 'SaveOnboardingDraftInput',\n description: 'Input for saving onboarding draft',\n fields: {\n data: { type: ScalarTypeEnum.JSON(), isOptional: false },\n },\n});\n\nexport const SaveOnboardingDraftOutput = new SchemaModel({\n name: 'SaveOnboardingDraftOutput',\n description: 'Output for saving onboarding draft',\n fields: {\n id: { type: ScalarTypeEnum.ID(), isOptional: false },\n organizationId: { type: ScalarTypeEnum.ID(), isOptional: false },\n },\n});\n\nexport const SaveOnboardingDraftBaseSpec = defineCommand({\n meta: {\n name: 'base.onboarding.saveDraft',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding', 'draft'],\n description: 'Save or update onboarding draft for active organization',\n goal: 'Persist onboarding progress incrementally for resumption and safety',\n context:\n 'Auto-saves every few seconds during onboarding; enables users to leave and resume',\n },\n io: {\n input: SaveOnboardingDraftInput,\n output: SaveOnboardingDraftOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'saveOnboardingDraft' },\n rest: { method: 'POST' },\n },\n});\n\n/** Get current onboarding draft (on mount/restore) */\nexport const GetOnboardingDraftOutput = new SchemaModel({\n name: 'GetOnboardingDraftOutput',\n description: 'Onboarding draft payload',\n fields: {\n id: { type: ScalarTypeEnum.ID(), isOptional: true },\n organizationId: { type: ScalarTypeEnum.ID(), isOptional: true },\n data: { type: ScalarTypeEnum.JSON(), isOptional: true },\n createdAt: { type: ScalarTypeEnum.DateTime(), isOptional: true },\n updatedAt: { type: ScalarTypeEnum.DateTime(), isOptional: true },\n },\n});\n\nexport const GetOnboardingDraftBaseSpec = defineQuery({\n meta: {\n name: 'base.onboarding.getDraft',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding', 'draft'],\n description: 'Get onboarding draft for active organization',\n goal: 'Retrieve saved onboarding progress',\n context: 'Called on mount to restore in-progress onboarding',\n },\n io: {\n input: null,\n output: GetOnboardingDraftOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'getOnboardingDraft' },\n rest: { method: 'GET' },\n },\n});\n\n/** Delete onboarding draft (cleanup after completion or cancel) */\nexport const DeleteOnboardingDraftOutput = new SchemaModel({\n name: 'DeleteOnboardingDraftOutput',\n description: 'Result of delete operation',\n fields: {\n ok: { type: ScalarTypeEnum.Boolean(), isOptional: false },\n },\n});\n\nexport const DeleteOnboardingDraftBaseSpec = defineCommand({\n meta: {\n name: 'base.onboarding.deleteDraft',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding', 'draft'],\n description: 'Delete onboarding draft for active organization',\n goal: 'Clear draft after completion or if user wants to restart',\n context: 'Called after successful onboarding or explicit user reset',\n },\n io: {\n input: null,\n output: DeleteOnboardingDraftOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'deleteOnboardingDraft' },\n rest: { method: 'POST' },\n },\n});\n\n/** Complete onboarding (final submit, creates entities) */\nexport const CompleteOnboardingBaseInput = new SchemaModel({\n name: 'CompleteOnboardingBaseInput',\n description: 'Input for completing onboarding',\n fields: {\n data: { type: ScalarTypeEnum.JSON(), isOptional: false },\n },\n});\n\nexport const CompleteOnboardingBaseOutput = new SchemaModel({\n name: 'CompleteOnboardingBaseOutput',\n description: 'Result of onboarding completion',\n fields: {\n success: { type: ScalarTypeEnum.Boolean(), isOptional: false },\n userId: { type: ScalarTypeEnum.ID(), isOptional: true },\n organizationId: { type: ScalarTypeEnum.ID(), isOptional: true },\n },\n});\n\nexport const CompleteOnboardingBaseSpec = defineCommand({\n meta: {\n name: 'base.onboarding.complete',\n version: 1,\n stability: StabilityEnum.Beta,\n owners: [OwnersEnum.PlatformSigil],\n tags: ['onboarding'],\n description: 'Complete onboarding and finalize user/organization setup',\n goal: 'Transition from draft to active profile',\n context:\n 'Validates all required fields, creates/updates entities, marks onboarding complete',\n },\n io: {\n input: CompleteOnboardingBaseInput,\n output: CompleteOnboardingBaseOutput,\n },\n policy: {\n auth: 'user',\n escalate: null,\n },\n transport: {\n gql: { field: 'completeOnboarding' },\n rest: { method: 'POST' },\n },\n});\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"engine.js","names":["registry: PolicyRegistry","allowReason: string | undefined","appliedRateLimit: PolicyDecision['rateLimit']","escalate: 'human_review' | null | undefined","specs: PolicySpec[]","allowMatch: RuleEvaluation | undefined","evaluation: RuleEvaluation","definition: RateLimitDefinition | undefined"],"sources":["../../src/policy/engine.ts"],"sourcesContent":["import {\n PolicyRegistry,\n type PolicyRef,\n type PolicySpec,\n type PolicyRule,\n type FieldPolicyRule,\n type PolicyCondition,\n type ConsentDefinition,\n type RateLimitDefinition,\n type RelationshipMatcher,\n} from './spec';\nimport type { PolicyDecision, FieldLevelDecision } from '../types';\n\nexport interface SubjectRelationship {\n relation: string;\n object: string;\n objectType?: string;\n}\n\nexport interface SubjectContext {\n roles?: string[];\n attributes?: Record<string, unknown>;\n relationships?: SubjectRelationship[];\n}\n\nexport interface ResourceContext {\n type: string;\n id?: string;\n fields?: string[];\n attributes?: Record<string, unknown>;\n}\n\nexport interface DecisionContext {\n subject: SubjectContext;\n resource: ResourceContext;\n context?: Record<string, unknown>;\n action: string;\n policies: PolicyRef[];\n consents?: string[];\n flags?: string[];\n}\n\ninterface RuleEvaluation {\n rule: PolicyRule;\n missingConsents: ConsentDefinition[];\n rateLimit?: PolicyDecision['rateLimit'];\n}\n\nexport class PolicyEngine {\n constructor(private readonly registry: PolicyRegistry) {}\n\n decide(input: DecisionContext): PolicyDecision {\n const policies = this.resolvePolicies(input.policies);\n let allowReason: string | undefined;\n let appliedRateLimit: PolicyDecision['rateLimit'];\n let escalate: 'human_review' | null | undefined;\n\n for (const policy of policies) {\n const match = this.matchRuleSet(policy, input);\n if (!match) continue;\n if (match.rule.effect === 'deny') {\n return {\n effect: 'deny',\n reason: match.rule.reason ?? policy.meta.name,\n requiredConsents: match.missingConsents.length\n ? match.missingConsents\n : undefined,\n evaluatedBy: 'engine',\n };\n }\n if (match.rule.effect === 'allow') {\n if (match.missingConsents.length) {\n return {\n effect: 'deny',\n reason: 'consent_required',\n requiredConsents: match.missingConsents,\n evaluatedBy: 'engine',\n };\n }\n if (!allowReason) {\n allowReason = match.rule.reason ?? policy.meta.name;\n }\n if (!appliedRateLimit && match.rateLimit) {\n appliedRateLimit = match.rateLimit;\n }\n if (!escalate && match.rule.escalate) {\n escalate = match.rule.escalate;\n }\n }\n }\n\n const fieldDecisions = this.evaluateFields(policies, input);\n const pii = policies.find((p) => p.pii)?.pii;\n const escalateValue =\n typeof escalate === 'undefined' ? undefined : escalate;\n\n return {\n effect: allowReason ? 'allow' : 'deny',\n reason: allowReason,\n rateLimit: appliedRateLimit,\n escalate: escalateValue,\n fieldDecisions: fieldDecisions.length ? fieldDecisions : undefined,\n pii,\n evaluatedBy: 'engine',\n };\n }\n\n private resolvePolicies(refs: PolicyRef[]): PolicySpec[] {\n const specs: PolicySpec[] = [];\n for (const ref of refs) {\n const spec = this.registry.get(ref.name, ref.version);\n if (!spec)\n throw new Error(\n `PolicyEngine: policy not found ${ref.name}.v${ref.version}`\n );\n specs.push(spec);\n }\n return specs;\n }\n\n private matchRuleSet(\n policy: PolicySpec,\n input: DecisionContext\n ): RuleEvaluation | undefined {\n let allowMatch: RuleEvaluation | undefined;\n for (const rule of policy.rules) {\n if (!rule.actions.includes(input.action)) continue;\n if (!matchesSubject(rule, input.subject)) continue;\n if (!matchesResource(rule, input.resource)) continue;\n if (!matchesFlags(rule, input)) continue;\n if (!matchesRelationships(rule.relationships, input)) continue;\n if (!matchesConditions(rule, input)) continue;\n const missingConsents = collectMissingConsents(rule, policy, input);\n const rateLimit = resolveRateLimit(rule, policy, input);\n const evaluation: RuleEvaluation = {\n rule,\n missingConsents,\n rateLimit,\n };\n if (rule.effect === 'deny') return evaluation;\n if (rule.effect === 'allow' && !allowMatch) allowMatch = evaluation;\n }\n return allowMatch;\n }\n\n private evaluateFields(\n policies: PolicySpec[],\n input: DecisionContext\n ): FieldLevelDecision[] {\n const out = new Map<string, FieldLevelDecision>();\n for (const policy of policies) {\n if (!policy.fieldPolicies) continue;\n for (const rule of policy.fieldPolicies) {\n if (!rule.actions.includes(mapActionToFieldAction(input.action))) continue;\n if (!matchesSubject(rule, input.subject)) continue;\n if (!matchesResource(rule, input.resource)) continue;\n if (!matchesConditions(rule, input)) continue;\n const existing = out.get(rule.field);\n if (rule.effect === 'deny') {\n out.set(rule.field, {\n field: rule.field,\n effect: 'deny',\n reason: rule.reason ?? policy.meta.name,\n });\n } else if (!existing) {\n out.set(rule.field, {\n field: rule.field,\n effect: 'allow',\n reason: rule.reason ?? policy.meta.name,\n });\n }\n }\n }\n return [...out.values()];\n }\n}\n\nfunction mapActionToFieldAction(action: string): 'read' | 'write' {\n if (action.startsWith('write')) return 'write';\n return 'read';\n}\n\nfunction matchesSubject(\n rule: { subject?: PolicyRule['subject'] | FieldPolicyRule['subject'] },\n subject: SubjectContext\n): boolean {\n const matcher = rule.subject;\n if (!matcher) return true;\n if (matcher.roles?.length) {\n const roles = subject.roles ?? [];\n const hasRole = matcher.roles.some((role) => roles.includes(role));\n if (!hasRole) return false;\n }\n if (matcher.attributes) {\n const attributes = subject.attributes ?? {};\n if (!matchAttributes(matcher.attributes, attributes)) return false;\n }\n return true;\n}\n\nfunction matchesResource(\n rule: { resource?: PolicyRule['resource'] | FieldPolicyRule['resource'] },\n resource: ResourceContext\n): boolean {\n const matcher = rule.resource;\n if (!matcher) return true;\n if (matcher.type && matcher.type !== resource.type) return false;\n if (matcher.fields?.length) {\n const targetFields = resource.fields ?? [];\n if (!matcher.fields.some((field) => targetFields.includes(field)))\n return false;\n }\n if (matcher.attributes) {\n const attributes = resource.attributes ?? {};\n if (!matchAttributes(matcher.attributes, attributes)) return false;\n }\n return true;\n}\n\nfunction matchesFlags(rule: PolicyRule, input: DecisionContext): boolean {\n if (!rule.flags?.length) return true;\n const available = new Set<string>();\n if (input.flags) {\n for (const flag of input.flags) available.add(flag);\n }\n const attributeFlags = input.subject.attributes?.featureFlags;\n if (Array.isArray(attributeFlags)) {\n for (const flag of attributeFlags) available.add(flag);\n }\n return rule.flags.every((flag) => available.has(flag));\n}\n\nfunction matchesRelationships(\n matchers: RelationshipMatcher[] | undefined,\n input: DecisionContext\n): boolean {\n if (!matchers || matchers.length === 0) return true;\n const relationships = input.subject.relationships ?? [];\n const resourceId = getResourceId(input.resource);\n const resourceType = input.resource.type;\n\n return matchers.every((matcher) =>\n relationships.some((relation) => {\n if (relation.relation !== matcher.relation) return false;\n\n const typeMatches =\n !matcher.objectType ||\n relation.objectType === matcher.objectType ||\n matcher.objectType === resourceType;\n\n if (!typeMatches) return false;\n\n if (!matcher.objectId) return true;\n\n if (matcher.objectId === '$resource') {\n if (resourceId) {\n return relation.object === resourceId;\n }\n return (\n relation.object === resourceType ||\n relation.objectType === resourceType\n );\n }\n\n return relation.object === matcher.objectId;\n })\n );\n}\n\nfunction matchesConditions(\n rule: { conditions?: PolicyCondition[] },\n input: DecisionContext\n): boolean {\n if (!rule.conditions || rule.conditions.length === 0) return true;\n return rule.conditions.every((condition) =>\n evaluateCondition(condition.expression, input)\n );\n}\n\nfunction matchAttributes(\n matcher: Record<string, import('./spec').AttributeMatcher>,\n actual: Record<string, unknown>\n): boolean {\n for (const [key, attrMatcher] of Object.entries(matcher)) {\n const value = actual[key];\n if (attrMatcher.exists && typeof value === 'undefined') return false;\n if (typeof attrMatcher.equals !== 'undefined') {\n if (value !== attrMatcher.equals) return false;\n }\n if (attrMatcher.oneOf && !attrMatcher.oneOf.includes(value)) return false;\n }\n return true;\n}\n\nfunction collectMissingConsents(\n rule: PolicyRule,\n policy: PolicySpec,\n input: DecisionContext\n): ConsentDefinition[] {\n if (!rule.requiresConsent?.length) return [];\n const granted = new Set(input.consents ?? []);\n const missingIds = rule.requiresConsent.filter((id) => !granted.has(id));\n if (missingIds.length === 0) return [];\n return resolveConsentDefinitions(policy, missingIds);\n}\n\nfunction resolveConsentDefinitions(\n policy: PolicySpec,\n ids: string[]\n): ConsentDefinition[] {\n const catalog = policy.consents ?? [];\n return ids.map((id) => {\n const found = catalog.find((consent) => consent.id === id);\n return (\n found ?? {\n id,\n scope: 'unspecified',\n purpose: 'unspecified',\n description: `Consent \"${id}\" required by ${policy.meta.name}`,\n required: true,\n }\n );\n });\n}\n\nfunction resolveRateLimit(\n rule: PolicyRule,\n policy: PolicySpec,\n input: DecisionContext\n): PolicyDecision['rateLimit'] | undefined {\n if (!rule.rateLimit) return undefined;\n const definition: RateLimitDefinition | undefined =\n typeof rule.rateLimit === 'string'\n ? (policy.rateLimits ?? []).find((item) => item.id === rule.rateLimit)\n : rule.rateLimit;\n\n if (!definition) {\n throw new Error(\n `PolicyEngine: rate limit \"${String(\n rule.rateLimit\n )}\" not declared in ${policy.meta.name}`\n );\n }\n\n return {\n rpm: definition.rpm,\n key: definition.key ?? input.resource.type,\n windowSeconds: definition.windowSeconds,\n burst: definition.burst,\n };\n}\n\nfunction evaluateCondition(\n expression: string,\n input: DecisionContext\n): boolean {\n const trimmed = expression.trim();\n if (!trimmed) return true;\n\n const context = {\n subject: input.subject,\n resource: input.resource,\n context: input.context ?? {},\n };\n\n try {\n // very small whitelist of expressions\n // Supports subject/resource/context dot paths, comparisons, and logical operators.\n const fn = new Function(\n 'subject',\n 'resource',\n 'context',\n `return (${transformExpression(trimmed)});`\n );\n const result = fn(context.subject, context.resource, context.context);\n return Boolean(result);\n } catch (_error) {\n return false;\n }\n}\n\nfunction transformExpression(expression: string): string {\n return expression.replace(/&&/g, '&&').replace(/\\|\\|/g, '||');\n}\n\nfunction getResourceId(resource: ResourceContext): string | undefined {\n if (resource.id) return resource.id;\n const candidate = resource.attributes?.id;\n if (typeof candidate === 'string') return candidate;\n if (typeof candidate === 'number') return String(candidate);\n return undefined;\n}\n\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"engine.js","names":["registry: PolicyRegistry","allowReason: string | undefined","appliedRateLimit: PolicyDecision['rateLimit']","escalate: 'human_review' | null | undefined","specs: PolicySpec[]","allowMatch: RuleEvaluation | undefined","evaluation: RuleEvaluation","definition: RateLimitDefinition | undefined"],"sources":["../../src/policy/engine.ts"],"sourcesContent":["import {\n PolicyRegistry,\n type PolicyRef,\n type PolicySpec,\n type PolicyRule,\n type FieldPolicyRule,\n type PolicyCondition,\n type ConsentDefinition,\n type RateLimitDefinition,\n type RelationshipMatcher,\n} from './spec';\nimport type { PolicyDecision, FieldLevelDecision } from '../types';\n\nexport interface SubjectRelationship {\n relation: string;\n object: string;\n objectType?: string;\n}\n\nexport interface SubjectContext {\n roles?: string[];\n attributes?: Record<string, unknown>;\n relationships?: SubjectRelationship[];\n}\n\nexport interface ResourceContext {\n type: string;\n id?: string;\n fields?: string[];\n attributes?: Record<string, unknown>;\n}\n\nexport interface DecisionContext {\n subject: SubjectContext;\n resource: ResourceContext;\n context?: Record<string, unknown>;\n action: string;\n policies: PolicyRef[];\n consents?: string[];\n flags?: string[];\n}\n\ninterface RuleEvaluation {\n rule: PolicyRule;\n missingConsents: ConsentDefinition[];\n rateLimit?: PolicyDecision['rateLimit'];\n}\n\nexport class PolicyEngine {\n constructor(private readonly registry: PolicyRegistry) {}\n\n decide(input: DecisionContext): PolicyDecision {\n const policies = this.resolvePolicies(input.policies);\n let allowReason: string | undefined;\n let appliedRateLimit: PolicyDecision['rateLimit'];\n let escalate: 'human_review' | null | undefined;\n\n for (const policy of policies) {\n const match = this.matchRuleSet(policy, input);\n if (!match) continue;\n if (match.rule.effect === 'deny') {\n return {\n effect: 'deny',\n reason: match.rule.reason ?? policy.meta.name,\n requiredConsents: match.missingConsents.length\n ? match.missingConsents\n : undefined,\n evaluatedBy: 'engine',\n };\n }\n if (match.rule.effect === 'allow') {\n if (match.missingConsents.length) {\n return {\n effect: 'deny',\n reason: 'consent_required',\n requiredConsents: match.missingConsents,\n evaluatedBy: 'engine',\n };\n }\n if (!allowReason) {\n allowReason = match.rule.reason ?? policy.meta.name;\n }\n if (!appliedRateLimit && match.rateLimit) {\n appliedRateLimit = match.rateLimit;\n }\n if (!escalate && match.rule.escalate) {\n escalate = match.rule.escalate;\n }\n }\n }\n\n const fieldDecisions = this.evaluateFields(policies, input);\n const pii = policies.find((p) => p.pii)?.pii;\n const escalateValue =\n typeof escalate === 'undefined' ? undefined : escalate;\n\n return {\n effect: allowReason ? 'allow' : 'deny',\n reason: allowReason,\n rateLimit: appliedRateLimit,\n escalate: escalateValue,\n fieldDecisions: fieldDecisions.length ? fieldDecisions : undefined,\n pii,\n evaluatedBy: 'engine',\n };\n }\n\n private resolvePolicies(refs: PolicyRef[]): PolicySpec[] {\n const specs: PolicySpec[] = [];\n for (const ref of refs) {\n const spec = this.registry.get(ref.name, ref.version);\n if (!spec)\n throw new Error(\n `PolicyEngine: policy not found ${ref.name}.v${ref.version}`\n );\n specs.push(spec);\n }\n return specs;\n }\n\n private matchRuleSet(\n policy: PolicySpec,\n input: DecisionContext\n ): RuleEvaluation | undefined {\n let allowMatch: RuleEvaluation | undefined;\n for (const rule of policy.rules) {\n if (!rule.actions.includes(input.action)) continue;\n if (!matchesSubject(rule, input.subject)) continue;\n if (!matchesResource(rule, input.resource)) continue;\n if (!matchesFlags(rule, input)) continue;\n if (!matchesRelationships(rule.relationships, input)) continue;\n if (!matchesConditions(rule, input)) continue;\n const missingConsents = collectMissingConsents(rule, policy, input);\n const rateLimit = resolveRateLimit(rule, policy, input);\n const evaluation: RuleEvaluation = {\n rule,\n missingConsents,\n rateLimit,\n };\n if (rule.effect === 'deny') return evaluation;\n if (rule.effect === 'allow' && !allowMatch) allowMatch = evaluation;\n }\n return allowMatch;\n }\n\n private evaluateFields(\n policies: PolicySpec[],\n input: DecisionContext\n ): FieldLevelDecision[] {\n const out = new Map<string, FieldLevelDecision>();\n for (const policy of policies) {\n if (!policy.fieldPolicies) continue;\n for (const rule of policy.fieldPolicies) {\n if (!rule.actions.includes(mapActionToFieldAction(input.action)))\n continue;\n if (!matchesSubject(rule, input.subject)) continue;\n if (!matchesResource(rule, input.resource)) continue;\n if (!matchesConditions(rule, input)) continue;\n const existing = out.get(rule.field);\n if (rule.effect === 'deny') {\n out.set(rule.field, {\n field: rule.field,\n effect: 'deny',\n reason: rule.reason ?? policy.meta.name,\n });\n } else if (!existing) {\n out.set(rule.field, {\n field: rule.field,\n effect: 'allow',\n reason: rule.reason ?? policy.meta.name,\n });\n }\n }\n }\n return [...out.values()];\n }\n}\n\nfunction mapActionToFieldAction(action: string): 'read' | 'write' {\n if (action.startsWith('write')) return 'write';\n return 'read';\n}\n\nfunction matchesSubject(\n rule: { subject?: PolicyRule['subject'] | FieldPolicyRule['subject'] },\n subject: SubjectContext\n): boolean {\n const matcher = rule.subject;\n if (!matcher) return true;\n if (matcher.roles?.length) {\n const roles = subject.roles ?? [];\n const hasRole = matcher.roles.some((role) => roles.includes(role));\n if (!hasRole) return false;\n }\n if (matcher.attributes) {\n const attributes = subject.attributes ?? {};\n if (!matchAttributes(matcher.attributes, attributes)) return false;\n }\n return true;\n}\n\nfunction matchesResource(\n rule: { resource?: PolicyRule['resource'] | FieldPolicyRule['resource'] },\n resource: ResourceContext\n): boolean {\n const matcher = rule.resource;\n if (!matcher) return true;\n if (matcher.type && matcher.type !== resource.type) return false;\n if (matcher.fields?.length) {\n const targetFields = resource.fields ?? [];\n if (!matcher.fields.some((field) => targetFields.includes(field)))\n return false;\n }\n if (matcher.attributes) {\n const attributes = resource.attributes ?? {};\n if (!matchAttributes(matcher.attributes, attributes)) return false;\n }\n return true;\n}\n\nfunction matchesFlags(rule: PolicyRule, input: DecisionContext): boolean {\n if (!rule.flags?.length) return true;\n const available = new Set<string>();\n if (input.flags) {\n for (const flag of input.flags) available.add(flag);\n }\n const attributeFlags = input.subject.attributes?.featureFlags;\n if (Array.isArray(attributeFlags)) {\n for (const flag of attributeFlags) available.add(flag);\n }\n return rule.flags.every((flag) => available.has(flag));\n}\n\nfunction matchesRelationships(\n matchers: RelationshipMatcher[] | undefined,\n input: DecisionContext\n): boolean {\n if (!matchers || matchers.length === 0) return true;\n const relationships = input.subject.relationships ?? [];\n const resourceId = getResourceId(input.resource);\n const resourceType = input.resource.type;\n\n return matchers.every((matcher) =>\n relationships.some((relation) => {\n if (relation.relation !== matcher.relation) return false;\n\n const typeMatches =\n !matcher.objectType ||\n relation.objectType === matcher.objectType ||\n matcher.objectType === resourceType;\n\n if (!typeMatches) return false;\n\n if (!matcher.objectId) return true;\n\n if (matcher.objectId === '$resource') {\n if (resourceId) {\n return relation.object === resourceId;\n }\n return (\n relation.object === resourceType ||\n relation.objectType === resourceType\n );\n }\n\n return relation.object === matcher.objectId;\n })\n );\n}\n\nfunction matchesConditions(\n rule: { conditions?: PolicyCondition[] },\n input: DecisionContext\n): boolean {\n if (!rule.conditions || rule.conditions.length === 0) return true;\n return rule.conditions.every((condition) =>\n evaluateCondition(condition.expression, input)\n );\n}\n\nfunction matchAttributes(\n matcher: Record<string, import('./spec').AttributeMatcher>,\n actual: Record<string, unknown>\n): boolean {\n for (const [key, attrMatcher] of Object.entries(matcher)) {\n const value = actual[key];\n if (attrMatcher.exists && typeof value === 'undefined') return false;\n if (typeof attrMatcher.equals !== 'undefined') {\n if (value !== attrMatcher.equals) return false;\n }\n if (attrMatcher.oneOf && !attrMatcher.oneOf.includes(value)) return false;\n }\n return true;\n}\n\nfunction collectMissingConsents(\n rule: PolicyRule,\n policy: PolicySpec,\n input: DecisionContext\n): ConsentDefinition[] {\n if (!rule.requiresConsent?.length) return [];\n const granted = new Set(input.consents ?? []);\n const missingIds = rule.requiresConsent.filter((id) => !granted.has(id));\n if (missingIds.length === 0) return [];\n return resolveConsentDefinitions(policy, missingIds);\n}\n\nfunction resolveConsentDefinitions(\n policy: PolicySpec,\n ids: string[]\n): ConsentDefinition[] {\n const catalog = policy.consents ?? [];\n return ids.map((id) => {\n const found = catalog.find((consent) => consent.id === id);\n return (\n found ?? {\n id,\n scope: 'unspecified',\n purpose: 'unspecified',\n description: `Consent \"${id}\" required by ${policy.meta.name}`,\n required: true,\n }\n );\n });\n}\n\nfunction resolveRateLimit(\n rule: PolicyRule,\n policy: PolicySpec,\n input: DecisionContext\n): PolicyDecision['rateLimit'] | undefined {\n if (!rule.rateLimit) return undefined;\n const definition: RateLimitDefinition | undefined =\n typeof rule.rateLimit === 'string'\n ? (policy.rateLimits ?? []).find((item) => item.id === rule.rateLimit)\n : rule.rateLimit;\n\n if (!definition) {\n throw new Error(\n `PolicyEngine: rate limit \"${String(\n rule.rateLimit\n )}\" not declared in ${policy.meta.name}`\n );\n }\n\n return {\n rpm: definition.rpm,\n key: definition.key ?? input.resource.type,\n windowSeconds: definition.windowSeconds,\n burst: definition.burst,\n };\n}\n\nfunction evaluateCondition(\n expression: string,\n input: DecisionContext\n): boolean {\n const trimmed = expression.trim();\n if (!trimmed) return true;\n\n const context = {\n subject: input.subject,\n resource: input.resource,\n context: input.context ?? {},\n };\n\n try {\n // very small whitelist of expressions\n // Supports subject/resource/context dot paths, comparisons, and logical operators.\n const fn = new Function(\n 'subject',\n 'resource',\n 'context',\n `return (${transformExpression(trimmed)});`\n );\n const result = fn(context.subject, context.resource, context.context);\n return Boolean(result);\n } catch (_error) {\n return false;\n }\n}\n\nfunction transformExpression(expression: string): string {\n return expression.replace(/&&/g, '&&').replace(/\\|\\|/g, '||');\n}\n\nfunction getResourceId(resource: ResourceContext): string | undefined {\n if (resource.id) return resource.id;\n const candidate = resource.attributes?.id;\n if (typeof candidate === 'string') return candidate;\n if (typeof candidate === 'number') return String(candidate);\n return undefined;\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"opa-adapter.d.ts","names":[],"sources":["../../src/policy/opa-adapter.ts"],"sourcesContent":[],"mappings":";;;;;UAIiB,SAAA;qDACoC,QAAQ;AAD7D;AAIiB,UAAA,mBAAA,CAAmB;EAOnB,MAAA,CAAA,EAAA,OAAA,GAAA,MAAiB;EAWrB,MAAA,CAAA,EAAA,MAAA;EAA0B,cAAA,CAAA,EAfpB,cAeoB,CAAA,gBAAA,CAAA;EAEV,gBAAA,CAAA,EAAA,MAAA,EAAA;;AACC,UAdb,iBAca,CAAA,SAdc,mBAcd,GAAA,IAAA,CAAA,CAAA;EAIjB;;;EAGA,YAAA,EAAA,MAAA;EAAR;;
|
|
1
|
+
{"version":3,"file":"opa-adapter.d.ts","names":[],"sources":["../../src/policy/opa-adapter.ts"],"sourcesContent":[],"mappings":";;;;;UAIiB,SAAA;qDACoC,QAAQ;AAD7D;AAIiB,UAAA,mBAAA,CAAmB;EAOnB,MAAA,CAAA,EAAA,OAAA,GAAA,MAAiB;EAWrB,MAAA,CAAA,EAAA,MAAA;EAA0B,cAAA,CAAA,EAfpB,cAeoB,CAAA,gBAAA,CAAA;EAEV,gBAAA,CAAA,EAAA,MAAA,EAAA;;AACC,UAdb,iBAca,CAAA,SAdc,mBAcd,GAAA,IAAA,CAAA,CAAA;EAIjB;;;EAGA,YAAA,EAAA,MAAA;EAAR;;AAqCL;EACW,SAAA,CAAA,EAAA,CAAA,KAAA,EAAA,OAAA,EAAA,GAnDuB,MAmDvB;;AAEO,cAlDL,gBAkDK,CAAA,SAlDqB,mBAkDrB,GAAA,IAAA,CAAA,CAAA;;;sBAhDW,oBACC,kBAAkB;oBAInC,2BACC,8BACM,iBACf,QAAQ;;iBAqCG,aAAA,UACL,2BACC,8BACM"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"opa-adapter.js","names":["client: OPAClient","options: OPAAdapterOptions<Result>"],"sources":["../../src/policy/opa-adapter.ts"],"sourcesContent":["import type { PolicyDecision } from '../types';\nimport type { PolicySpec, ConsentDefinition } from './spec';\nimport type { DecisionContext } from './engine';\n\nexport interface OPAClient {\n evaluate<T>(decisionPath: string, input: unknown): Promise<T>;\n}\n\nexport interface OPAEvaluationResult {\n effect?: 'allow' | 'deny';\n reason?: string;\n fieldDecisions?: PolicyDecision['fieldDecisions'];\n requiredConsents?: string[];\n}\n\nexport interface OPAAdapterOptions<Result = OPAEvaluationResult | null> {\n /**\n * Path fed to the OPA client (e.g., \"sigil/authz/allow\").\n */\n decisionPath: string;\n /**\n * Optional mapper when the OPA client returns a non-standard payload.\n */\n mapResult?: (value: unknown) => Result;\n}\n\nexport class OPAPolicyAdapter<Result = OPAEvaluationResult | null> {\n constructor(\n private readonly client: OPAClient,\n private readonly options: OPAAdapterOptions<Result>\n ) {}\n\n async evaluate(\n context: DecisionContext,\n policies: PolicySpec[],\n engineDecision: PolicyDecision\n ): Promise<PolicyDecision> {\n const input = buildOPAInput(context, policies, engineDecision);\n const raw = await this.client.evaluate<unknown>(\n this.options.decisionPath,\n input\n );\n const resolved = this.options.mapResult\n ? this.options.mapResult(raw)\n : (raw as OPAEvaluationResult | null);\n\n if (!resolved) {\n return {\n ...engineDecision,\n evaluatedBy: engineDecision.evaluatedBy ?? 'engine',\n };\n }\n\n const opaResult = resolved as OPAEvaluationResult;\n const mergedRequiredConsents = mergeRequiredConsents(\n policies,\n engineDecision.requiredConsents ?? [],\n opaResult.requiredConsents ?? []\n );\n\n return {\n ...engineDecision,\n effect: opaResult.effect ?? engineDecision.effect,\n reason: opaResult.reason ?? engineDecision.reason,\n fieldDecisions
|
|
1
|
+
{"version":3,"file":"opa-adapter.js","names":["client: OPAClient","options: OPAAdapterOptions<Result>"],"sources":["../../src/policy/opa-adapter.ts"],"sourcesContent":["import type { PolicyDecision } from '../types';\nimport type { PolicySpec, ConsentDefinition } from './spec';\nimport type { DecisionContext } from './engine';\n\nexport interface OPAClient {\n evaluate<T>(decisionPath: string, input: unknown): Promise<T>;\n}\n\nexport interface OPAEvaluationResult {\n effect?: 'allow' | 'deny';\n reason?: string;\n fieldDecisions?: PolicyDecision['fieldDecisions'];\n requiredConsents?: string[];\n}\n\nexport interface OPAAdapterOptions<Result = OPAEvaluationResult | null> {\n /**\n * Path fed to the OPA client (e.g., \"sigil/authz/allow\").\n */\n decisionPath: string;\n /**\n * Optional mapper when the OPA client returns a non-standard payload.\n */\n mapResult?: (value: unknown) => Result;\n}\n\nexport class OPAPolicyAdapter<Result = OPAEvaluationResult | null> {\n constructor(\n private readonly client: OPAClient,\n private readonly options: OPAAdapterOptions<Result>\n ) {}\n\n async evaluate(\n context: DecisionContext,\n policies: PolicySpec[],\n engineDecision: PolicyDecision\n ): Promise<PolicyDecision> {\n const input = buildOPAInput(context, policies, engineDecision);\n const raw = await this.client.evaluate<unknown>(\n this.options.decisionPath,\n input\n );\n const resolved = this.options.mapResult\n ? this.options.mapResult(raw)\n : (raw as OPAEvaluationResult | null);\n\n if (!resolved) {\n return {\n ...engineDecision,\n evaluatedBy: engineDecision.evaluatedBy ?? 'engine',\n };\n }\n\n const opaResult = resolved as OPAEvaluationResult;\n const mergedRequiredConsents = mergeRequiredConsents(\n policies,\n engineDecision.requiredConsents ?? [],\n opaResult.requiredConsents ?? []\n );\n\n return {\n ...engineDecision,\n effect: opaResult.effect ?? engineDecision.effect,\n reason: opaResult.reason ?? engineDecision.reason,\n fieldDecisions: opaResult.fieldDecisions ?? engineDecision.fieldDecisions,\n requiredConsents: mergedRequiredConsents.length\n ? mergedRequiredConsents\n : undefined,\n evaluatedBy: 'opa',\n };\n }\n}\n\nexport function buildOPAInput(\n context: DecisionContext,\n policies: PolicySpec[],\n engineDecision: PolicyDecision\n) {\n return {\n context,\n decision: engineDecision,\n policies: policies.map((policy) => ({\n meta: policy.meta,\n rules: policy.rules,\n fieldPolicies: policy.fieldPolicies,\n pii: policy.pii,\n relationships: policy.relationships,\n consents: policy.consents,\n rateLimits: policy.rateLimits,\n })),\n };\n}\n\nfunction mergeRequiredConsents(\n policies: PolicySpec[],\n existing: ConsentDefinition[],\n incomingIds: string[]\n): ConsentDefinition[] {\n if (incomingIds.length === 0) return existing;\n const existingIds = new Set(existing.map((consent) => consent.id));\n const merged = [...existing];\n\n for (const id of incomingIds) {\n if (existingIds.has(id)) continue;\n const resolved = resolveConsentAcrossPolicies(policies, id);\n if (resolved) {\n merged.push(resolved);\n existingIds.add(resolved.id);\n }\n }\n\n return merged;\n}\n\nfunction resolveConsentAcrossPolicies(\n policies: PolicySpec[],\n id: string\n): ConsentDefinition | null {\n for (const policy of policies) {\n const match = policy.consents?.find((consent) => consent.id === id);\n if (match) return match;\n }\n\n return {\n id,\n scope: 'unspecified',\n purpose: 'unspecified',\n description: `Consent \"${id}\" returned by OPA`,\n required: true,\n };\n}\n"],"mappings":"AA0BA,IAAa,EAAb,KAAmE,CACjE,YACE,EACA,EACA,CAFiB,KAAA,OAAA,EACA,KAAA,QAAA,EAGnB,MAAM,SACJ,EACA,EACA,EACyB,CACzB,IAAM,EAAQ,EAAc,EAAS,EAAU,EAAe,CACxD,EAAM,MAAM,KAAK,OAAO,SAC5B,KAAK,QAAQ,aACb,EACD,CACK,EAAW,KAAK,QAAQ,UAC1B,KAAK,QAAQ,UAAU,EAAI,CAC1B,EAEL,GAAI,CAAC,EACH,MAAO,CACL,GAAG,EACH,YAAa,EAAe,aAAe,SAC5C,CAGH,IAAM,EAAY,EACZ,EAAyB,EAC7B,EACA,EAAe,kBAAoB,EAAE,CACrC,EAAU,kBAAoB,EAAE,CACjC,CAED,MAAO,CACL,GAAG,EACH,OAAQ,EAAU,QAAU,EAAe,OAC3C,OAAQ,EAAU,QAAU,EAAe,OAC3C,eAAgB,EAAU,gBAAkB,EAAe,eAC3D,iBAAkB,EAAuB,OACrC,EACA,IAAA,GACJ,YAAa,MACd,GAIL,SAAgB,EACd,EACA,EACA,EACA,CACA,MAAO,CACL,UACA,SAAU,EACV,SAAU,EAAS,IAAK,IAAY,CAClC,KAAM,EAAO,KACb,MAAO,EAAO,MACd,cAAe,EAAO,cACtB,IAAK,EAAO,IACZ,cAAe,EAAO,cACtB,SAAU,EAAO,SACjB,WAAY,EAAO,WACpB,EAAE,CACJ,CAGH,SAAS,EACP,EACA,EACA,EACqB,CACrB,GAAI,EAAY,SAAW,EAAG,OAAO,EACrC,IAAM,EAAc,IAAI,IAAI,EAAS,IAAK,GAAY,EAAQ,GAAG,CAAC,CAC5D,EAAS,CAAC,GAAG,EAAS,CAE5B,IAAK,IAAM,KAAM,EAAa,CAC5B,GAAI,EAAY,IAAI,EAAG,CAAE,SACzB,IAAM,EAAW,EAA6B,EAAU,EAAG,CACvD,IACF,EAAO,KAAK,EAAS,CACrB,EAAY,IAAI,EAAS,GAAG,EAIhC,OAAO,EAGT,SAAS,EACP,EACA,EAC0B,CAC1B,IAAK,IAAM,KAAU,EAAU,CAC7B,IAAM,EAAQ,EAAO,UAAU,KAAM,GAAY,EAAQ,KAAO,EAAG,CACnE,GAAI,EAAO,OAAO,EAGpB,MAAO,CACL,KACA,MAAO,cACP,QAAS,cACT,YAAa,YAAY,EAAG,mBAC5B,SAAU,GACX"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"spec.d.ts","names":[],"sources":["../../src/policy/spec.ts"],"sourcesContent":[],"mappings":";;;KAEY,YAAA;UAEK,sBAAA;EAFL,WAAA,EAAA,MAAY;EAEP,QAAA,EAAA,MAAA;EAQA,UAAA,EAAA,MAAA;EAMA,WAAA,CAAA,EAAA,MAAiB;
|
|
1
|
+
{"version":3,"file":"spec.d.ts","names":[],"sources":["../../src/policy/spec.ts"],"sourcesContent":[],"mappings":";;;KAEY,YAAA;UAEK,sBAAA;EAFL,WAAA,EAAA,MAAY;EAEP,QAAA,EAAA,MAAA;EAQA,UAAA,EAAA,MAAA;EAMA,WAAA,CAAA,EAAA,MAAiB;EAcjB,UAAA,CAAA,EAAA,OAAA;AAQjB;AAOiB,UAnCA,mBAAA,CAmCmB;EASnB,QAAA,EAAA,MAAA;EAMA,UAAA,CAAA,EAAA,MAAc;EAKd,QAAA,CAAA,EAAA,MAAA;AAMjB;AAKiB,UA5DA,iBAAA,CA4DU;EACjB,EAAA,EAAA,MAAA;EAEE,KAAA,EAAA,MAAA;EACC,OAAA,EAAA,MAAA;EACK,WAAA,CAAA,EAAA,MAAA;EAGK,WAAA,CAAA,EAAA,SAAA,GAAA,UAAA,GAAA,kBAAA,GAAA,qBAAA;EAER,aAAA,CAAA,EAAA,MAAA;EAAe,QAAA,CAAA,EAAA,OAAA;AAI9B;AACU,UA7DO,mBAAA,CA6DP;EAGE,EAAA,EAAA,MAAA;EACC,GAAA,EAAA,MAAA;EACE,GAAA,CAAA,EAAA,MAAA;EAAe,aAAA,CAAA,EAAA,MAAA;EAIb,KAAA,CAAA,EAAA,MAAS;AAM1B;AACQ,UArES,eAAA,CAqET;EACC;EACS,OAAA,EAAA,MAAA;EACV;EACU,QAAA,CAAA,EAAA,MAAA;;AAEH,UApEE,UAAA,SAAmB,aAoErB,CAAA;EACP;EAAe,IAAA,EAAA,MAAA;EAGN;EAOJ,OAAA,EAAA,MAAA;EAGI;EAOP,KAAA,CAAA,EAAA,QAAA,GAAA,SAAA,GAAA,WAAA;;AAIuC,UApFhC,gBAAA,CAoFgC;EAejC,MAAA,CAAA,EAAA,OAAa;;;;UA7FZ,cAAA;;eAEF,eAAe;;UAGb,eAAA;;;eAGF,eAAe;;UAGb,eAAA;;;;UAKA,UAAA;UACP;;YAEE;aACC;kBACK;;;uBAGK;;eAER;;;UAIE,eAAA;UACP;;;YAGE;aACC;eACE;;;UAIE,SAAA;;;;;UAMA,UAAA;QACT;SACC;kBACS;QACV;kBACU;aACL;eACE;QACP;;UAGS,SAAA;;;;cAOJ,cAAA;;iBAGI;UAOP;uCAI6B;;iBAevB,aAAA,MAAmB"}
|