@contractspec/lib.feature-flags 0.0.0-canary-20260113162409

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.
Files changed (225) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +173 -0
  3. package/dist/contracts/index.d.ts +1010 -0
  4. package/dist/contracts/index.d.ts.map +1 -0
  5. package/dist/contracts/index.js +908 -0
  6. package/dist/contracts/index.js.map +1 -0
  7. package/dist/contracts/src/app-config/lifecycle.d.ts +1 -0
  8. package/dist/contracts/src/app-config/runtime.d.ts +13 -0
  9. package/dist/contracts/src/app-config/spec.d.ts +9 -0
  10. package/dist/contracts/src/app-config/validation.d.ts +8 -0
  11. package/dist/contracts/src/capabilities/capabilities.d.ts +33 -0
  12. package/dist/contracts/src/capabilities/capabilities.d.ts.map +1 -0
  13. package/dist/contracts/src/capabilities/index.d.ts +2 -0
  14. package/dist/contracts/src/capabilities/openbanking.d.ts +1 -0
  15. package/dist/contracts/src/client/index.d.ts +1 -0
  16. package/dist/contracts/src/client/react/drivers/rn-reusables.d.ts +1 -0
  17. package/dist/contracts/src/client/react/drivers/shadcn.d.ts +1 -0
  18. package/dist/contracts/src/client/react/feature-render.d.ts +3 -0
  19. package/dist/contracts/src/client/react/form-render.d.ts +4 -0
  20. package/dist/contracts/src/client/react/index.d.ts +4 -0
  21. package/dist/contracts/src/contract-registry/index.d.ts +2 -0
  22. package/dist/contracts/src/contract-registry/schemas.d.ts +2 -0
  23. package/dist/contracts/src/contract-registry/types.d.ts +1 -0
  24. package/dist/contracts/src/data-views/index.d.ts +3 -0
  25. package/dist/contracts/src/data-views/registry.d.ts +2 -0
  26. package/dist/contracts/src/data-views/spec.d.ts +2 -0
  27. package/dist/contracts/src/data-views/types.d.ts +2 -0
  28. package/dist/contracts/src/docs/accessibility_wcag_compliance_specs.docblock.d.ts +1 -0
  29. package/dist/contracts/src/docs/index.d.ts +25 -0
  30. package/dist/contracts/src/docs/presentations.d.ts +2 -0
  31. package/dist/contracts/src/docs/registry.d.ts +10 -0
  32. package/dist/contracts/src/docs/registry.d.ts.map +1 -0
  33. package/dist/contracts/src/docs/tech/auth/better-auth-nextjs.docblock.d.ts +1 -0
  34. package/dist/contracts/src/docs/tech/contracts/README.docblock.d.ts +1 -0
  35. package/dist/contracts/src/docs/tech/contracts/openapi-export.docblock.d.ts +1 -0
  36. package/dist/contracts/src/docs/tech/contracts/openapi-import.docblock.d.ts +1 -0
  37. package/dist/contracts/src/docs/tech/lifecycle-stage-system.docblock.d.ts +1 -0
  38. package/dist/contracts/src/docs/tech/llm/llm-integration.docblock.d.ts +1 -0
  39. package/dist/contracts/src/docs/tech/mcp-endpoints.docblock.d.ts +1 -0
  40. package/dist/contracts/src/docs/tech/presentation-runtime.docblock.d.ts +1 -0
  41. package/dist/contracts/src/docs/tech/schema/README.docblock.d.ts +1 -0
  42. package/dist/contracts/src/docs/tech/studio/learning-events.docblock.d.ts +1 -0
  43. package/dist/contracts/src/docs/tech/studio/learning-journeys.docblock.d.ts +1 -0
  44. package/dist/contracts/src/docs/tech/studio/platform-admin-panel.docblock.d.ts +1 -0
  45. package/dist/contracts/src/docs/tech/studio/project-access-teams.docblock.d.ts +1 -0
  46. package/dist/contracts/src/docs/tech/studio/project-routing.docblock.d.ts +1 -0
  47. package/dist/contracts/src/docs/tech/studio/sandbox-unlogged.docblock.d.ts +1 -0
  48. package/dist/contracts/src/docs/tech/studio/team-invitations.docblock.d.ts +1 -0
  49. package/dist/contracts/src/docs/tech/studio/workspace-ops.docblock.d.ts +1 -0
  50. package/dist/contracts/src/docs/tech/studio/workspaces.docblock.d.ts +1 -0
  51. package/dist/contracts/src/docs/tech/telemetry-ingest.docblock.d.ts +1 -0
  52. package/dist/contracts/src/docs/tech/vscode-extension.docblock.d.ts +1 -0
  53. package/dist/contracts/src/events.d.ts +25 -0
  54. package/dist/contracts/src/events.d.ts.map +1 -0
  55. package/dist/contracts/src/examples/index.d.ts +4 -0
  56. package/dist/contracts/src/examples/registry.d.ts +2 -0
  57. package/dist/contracts/src/examples/schema.d.ts +2 -0
  58. package/dist/contracts/src/examples/types.d.ts +3 -0
  59. package/dist/contracts/src/examples/validation.d.ts +1 -0
  60. package/dist/contracts/src/experiments/evaluator.d.ts +2 -0
  61. package/dist/contracts/src/experiments/spec-resolver.d.ts +4 -0
  62. package/dist/contracts/src/experiments/spec.d.ts +13 -0
  63. package/dist/contracts/src/experiments/spec.d.ts.map +1 -0
  64. package/dist/contracts/src/features/index.d.ts +4 -0
  65. package/dist/contracts/src/features/install.d.ts +6 -0
  66. package/dist/contracts/src/features/registry.d.ts +2 -0
  67. package/dist/contracts/src/features/types.d.ts +86 -0
  68. package/dist/contracts/src/features/types.d.ts.map +1 -0
  69. package/dist/contracts/src/features/validation.d.ts +2 -0
  70. package/dist/contracts/src/forms/forms.d.ts +3 -0
  71. package/dist/contracts/src/forms/index.d.ts +1 -0
  72. package/dist/contracts/src/index.d.ts +51 -0
  73. package/dist/contracts/src/install.d.ts +7 -0
  74. package/dist/contracts/src/integrations/connection.d.ts +1 -0
  75. package/dist/contracts/src/integrations/index.d.ts +6 -0
  76. package/dist/contracts/src/integrations/openbanking/contracts/accounts.d.ts +4 -0
  77. package/dist/contracts/src/integrations/openbanking/contracts/balances.d.ts +4 -0
  78. package/dist/contracts/src/integrations/openbanking/contracts/index.d.ts +5 -0
  79. package/dist/contracts/src/integrations/openbanking/contracts/transactions.d.ts +4 -0
  80. package/dist/contracts/src/integrations/openbanking/guards.d.ts +1 -0
  81. package/dist/contracts/src/integrations/openbanking/models.d.ts +1 -0
  82. package/dist/contracts/src/integrations/openbanking/openbanking.feature.d.ts +1 -0
  83. package/dist/contracts/src/integrations/operations.d.ts +4 -0
  84. package/dist/contracts/src/integrations/providers/elevenlabs.d.ts +2 -0
  85. package/dist/contracts/src/integrations/providers/gcs-storage.d.ts +2 -0
  86. package/dist/contracts/src/integrations/providers/gmail.d.ts +2 -0
  87. package/dist/contracts/src/integrations/providers/google-calendar.d.ts +2 -0
  88. package/dist/contracts/src/integrations/providers/index.d.ts +11 -0
  89. package/dist/contracts/src/integrations/providers/mistral.d.ts +2 -0
  90. package/dist/contracts/src/integrations/providers/postmark.d.ts +2 -0
  91. package/dist/contracts/src/integrations/providers/powens.d.ts +2 -0
  92. package/dist/contracts/src/integrations/providers/qdrant.d.ts +2 -0
  93. package/dist/contracts/src/integrations/providers/registry.d.ts +1 -0
  94. package/dist/contracts/src/integrations/providers/stripe.d.ts +2 -0
  95. package/dist/contracts/src/integrations/providers/twilio-sms.d.ts +2 -0
  96. package/dist/contracts/src/integrations/spec.d.ts +3 -0
  97. package/dist/contracts/src/jsonschema.d.ts +4 -0
  98. package/dist/contracts/src/knowledge/index.d.ts +2 -0
  99. package/dist/contracts/src/knowledge/operations.d.ts +4 -0
  100. package/dist/contracts/src/knowledge/spaces/email-threads.d.ts +1 -0
  101. package/dist/contracts/src/knowledge/spaces/financial-docs.d.ts +1 -0
  102. package/dist/contracts/src/knowledge/spaces/financial-overview.d.ts +1 -0
  103. package/dist/contracts/src/knowledge/spaces/index.d.ts +6 -0
  104. package/dist/contracts/src/knowledge/spaces/product-canon.d.ts +1 -0
  105. package/dist/contracts/src/knowledge/spaces/support-faq.d.ts +1 -0
  106. package/dist/contracts/src/knowledge/spaces/uploaded-docs.d.ts +1 -0
  107. package/dist/contracts/src/knowledge/spec.d.ts +3 -0
  108. package/dist/contracts/src/llm/exporters.d.ts +7 -0
  109. package/dist/contracts/src/llm/index.d.ts +3 -0
  110. package/dist/contracts/src/llm/prompts.d.ts +2 -0
  111. package/dist/contracts/src/llm/types.d.ts +5 -0
  112. package/dist/contracts/src/migrations.d.ts +1 -0
  113. package/dist/contracts/src/model-registry.d.ts +1 -0
  114. package/dist/contracts/src/onboarding-base.d.ts +2 -0
  115. package/dist/contracts/src/openapi.d.ts +1 -0
  116. package/dist/contracts/src/operations/index.d.ts +2 -0
  117. package/dist/contracts/src/operations/operation.d.ts +170 -0
  118. package/dist/contracts/src/operations/operation.d.ts.map +1 -0
  119. package/dist/contracts/src/operations/registry.d.ts +6 -0
  120. package/dist/contracts/src/ownership.d.ts +61 -0
  121. package/dist/contracts/src/ownership.d.ts.map +1 -0
  122. package/dist/contracts/src/policy/engine.d.ts +3 -0
  123. package/dist/contracts/src/policy/index.d.ts +4 -0
  124. package/dist/contracts/src/policy/opa-adapter.d.ts +3 -0
  125. package/dist/contracts/src/policy/registry.d.ts +2 -0
  126. package/dist/contracts/src/policy/spec.d.ts +11 -0
  127. package/dist/contracts/src/policy/spec.d.ts.map +1 -0
  128. package/dist/contracts/src/presentations/index.d.ts +3 -0
  129. package/dist/contracts/src/presentations/presentations.d.ts +9 -0
  130. package/dist/contracts/src/presentations/presentations.d.ts.map +1 -0
  131. package/dist/contracts/src/presentations/registry.d.ts +2 -0
  132. package/dist/contracts/src/presentations/transform-engine.d.ts +2 -0
  133. package/dist/contracts/src/prompt.d.ts +2 -0
  134. package/dist/contracts/src/promptRegistry.d.ts +2 -0
  135. package/dist/contracts/src/regenerator/adapters.d.ts +1 -0
  136. package/dist/contracts/src/regenerator/executor.d.ts +1 -0
  137. package/dist/contracts/src/regenerator/index.d.ts +6 -0
  138. package/dist/contracts/src/regenerator/service.d.ts +2 -0
  139. package/dist/contracts/src/regenerator/sinks.d.ts +2 -0
  140. package/dist/contracts/src/regenerator/types.d.ts +3 -0
  141. package/dist/contracts/src/regenerator/utils.d.ts +1 -0
  142. package/dist/contracts/src/registry-utils.d.ts +1 -0
  143. package/dist/contracts/src/registry.d.ts +3 -0
  144. package/dist/contracts/src/resources.d.ts +19 -0
  145. package/dist/contracts/src/resources.d.ts.map +1 -0
  146. package/dist/contracts/src/schema-to-markdown.d.ts +1 -0
  147. package/dist/contracts/src/server/graphql-pothos.d.ts +7 -0
  148. package/dist/contracts/src/server/index.d.ts +7 -0
  149. package/dist/contracts/src/server/mcp/createMcpServer.d.ts +5 -0
  150. package/dist/contracts/src/server/mcp/mcpTypes.d.ts +2 -0
  151. package/dist/contracts/src/server/provider-mcp.d.ts +1 -0
  152. package/dist/contracts/src/server/rest-elysia.d.ts +3 -0
  153. package/dist/contracts/src/server/rest-express.d.ts +3 -0
  154. package/dist/contracts/src/server/rest-generic.d.ts +2 -0
  155. package/dist/contracts/src/server/rest-next-app.d.ts +3 -0
  156. package/dist/contracts/src/server/rest-next-pages.d.ts +3 -0
  157. package/dist/contracts/src/telemetry/anomaly.d.ts +2 -0
  158. package/dist/contracts/src/telemetry/index.d.ts +3 -0
  159. package/dist/contracts/src/telemetry/spec.d.ts +2 -0
  160. package/dist/contracts/src/telemetry/tracker.d.ts +2 -0
  161. package/dist/contracts/src/tests/index.d.ts +2 -0
  162. package/dist/contracts/src/tests/runner.d.ts +3 -0
  163. package/dist/contracts/src/tests/spec.d.ts +11 -0
  164. package/dist/contracts/src/tests/spec.d.ts.map +1 -0
  165. package/dist/contracts/src/themes.d.ts +2 -0
  166. package/dist/contracts/src/types.d.ts +5 -0
  167. package/dist/contracts/src/workflow/adapters/db-adapter.d.ts +1 -0
  168. package/dist/contracts/src/workflow/adapters/file-adapter.d.ts +1 -0
  169. package/dist/contracts/src/workflow/adapters/index.d.ts +3 -0
  170. package/dist/contracts/src/workflow/adapters/memory-store.d.ts +1 -0
  171. package/dist/contracts/src/workflow/index.d.ts +5 -0
  172. package/dist/contracts/src/workflow/overview.docblock.d.ts +1 -0
  173. package/dist/contracts/src/workflow/runner.d.ts +5 -0
  174. package/dist/contracts/src/workflow/spec.d.ts +5 -0
  175. package/dist/contracts/src/workflow/state.d.ts +1 -0
  176. package/dist/contracts/src/workflow/validation.d.ts +3 -0
  177. package/dist/contracts/src/workspace-config/contractsrc-schema.d.ts +1 -0
  178. package/dist/contracts/src/workspace-config/index.d.ts +1 -0
  179. package/dist/contracts/src/workspace-config/workspace-config.docblock.d.ts +1 -0
  180. package/dist/docs/feature-flags.docblock.d.ts +1 -0
  181. package/dist/docs/feature-flags.docblock.js +76 -0
  182. package/dist/docs/feature-flags.docblock.js.map +1 -0
  183. package/dist/docs/index.d.ts +1 -0
  184. package/dist/docs/index.js +1 -0
  185. package/dist/entities/index.d.ts +201 -0
  186. package/dist/entities/index.d.ts.map +1 -0
  187. package/dist/entities/index.js +325 -0
  188. package/dist/entities/index.js.map +1 -0
  189. package/dist/evaluation/index.d.ts +163 -0
  190. package/dist/evaluation/index.d.ts.map +1 -0
  191. package/dist/evaluation/index.js +221 -0
  192. package/dist/evaluation/index.js.map +1 -0
  193. package/dist/events.d.ts +628 -0
  194. package/dist/events.d.ts.map +1 -0
  195. package/dist/events.js +536 -0
  196. package/dist/events.js.map +1 -0
  197. package/dist/feature-flags.capability.d.ts +9 -0
  198. package/dist/feature-flags.capability.d.ts.map +1 -0
  199. package/dist/feature-flags.capability.js +25 -0
  200. package/dist/feature-flags.capability.js.map +1 -0
  201. package/dist/feature-flags.feature.d.ts +12 -0
  202. package/dist/feature-flags.feature.d.ts.map +1 -0
  203. package/dist/feature-flags.feature.js +148 -0
  204. package/dist/feature-flags.feature.js.map +1 -0
  205. package/dist/index.d.ts +6 -0
  206. package/dist/index.js +8 -0
  207. package/dist/schema/src/EnumType.d.ts +36 -0
  208. package/dist/schema/src/EnumType.d.ts.map +1 -0
  209. package/dist/schema/src/FieldType.d.ts +30 -0
  210. package/dist/schema/src/FieldType.d.ts.map +1 -0
  211. package/dist/schema/src/GraphQLSchemaType.d.ts +2 -0
  212. package/dist/schema/src/JsonSchemaType.d.ts +2 -0
  213. package/dist/schema/src/ScalarTypeEnum.d.ts +1 -0
  214. package/dist/schema/src/SchemaModel.d.ts +70 -0
  215. package/dist/schema/src/SchemaModel.d.ts.map +1 -0
  216. package/dist/schema/src/SchemaModelType.d.ts +38 -0
  217. package/dist/schema/src/SchemaModelType.d.ts.map +1 -0
  218. package/dist/schema/src/ZodSchemaType.d.ts +2 -0
  219. package/dist/schema/src/entity/defineEntity.d.ts +1 -0
  220. package/dist/schema/src/entity/generator.d.ts +1 -0
  221. package/dist/schema/src/entity/index.d.ts +3 -0
  222. package/dist/schema/src/entity/types.d.ts +146 -0
  223. package/dist/schema/src/entity/types.d.ts.map +1 -0
  224. package/dist/schema/src/index.d.ts +10 -0
  225. package/package.json +74 -0
@@ -0,0 +1,325 @@
1
+ import { defineEntity, defineEntityEnum, field, index } from "@contractspec/lib.schema";
2
+
3
+ //#region src/entities/index.ts
4
+ /**
5
+ * Feature flag status enum.
6
+ */
7
+ const FlagStatusEnum = defineEntityEnum({
8
+ name: "FlagStatus",
9
+ values: [
10
+ "OFF",
11
+ "ON",
12
+ "GRADUAL"
13
+ ],
14
+ schema: "lssm_feature_flags",
15
+ description: "Status of a feature flag."
16
+ });
17
+ /**
18
+ * Targeting rule operator enum.
19
+ */
20
+ const RuleOperatorEnum = defineEntityEnum({
21
+ name: "RuleOperator",
22
+ values: [
23
+ "EQ",
24
+ "NEQ",
25
+ "IN",
26
+ "NIN",
27
+ "CONTAINS",
28
+ "NOT_CONTAINS",
29
+ "GT",
30
+ "GTE",
31
+ "LT",
32
+ "LTE",
33
+ "PERCENTAGE"
34
+ ],
35
+ schema: "lssm_feature_flags",
36
+ description: "Operator for targeting rule conditions."
37
+ });
38
+ /**
39
+ * Experiment status enum.
40
+ */
41
+ const ExperimentStatusEnum = defineEntityEnum({
42
+ name: "ExperimentStatus",
43
+ values: [
44
+ "DRAFT",
45
+ "RUNNING",
46
+ "PAUSED",
47
+ "COMPLETED",
48
+ "CANCELLED"
49
+ ],
50
+ schema: "lssm_feature_flags",
51
+ description: "Status of an experiment."
52
+ });
53
+ /**
54
+ * FeatureFlag entity - defines a feature flag.
55
+ */
56
+ const FeatureFlagEntity = defineEntity({
57
+ name: "FeatureFlag",
58
+ description: "A feature flag for controlling feature availability.",
59
+ schema: "lssm_feature_flags",
60
+ map: "feature_flag",
61
+ fields: {
62
+ id: field.id({ description: "Unique flag identifier" }),
63
+ key: field.string({
64
+ isUnique: true,
65
+ description: "Flag key (e.g., new_dashboard)"
66
+ }),
67
+ name: field.string({ description: "Human-readable name" }),
68
+ description: field.string({
69
+ isOptional: true,
70
+ description: "Description of the flag"
71
+ }),
72
+ status: field.enum("FlagStatus", {
73
+ default: "OFF",
74
+ description: "Flag status"
75
+ }),
76
+ defaultValue: field.boolean({
77
+ default: false,
78
+ description: "Default value when no rules match"
79
+ }),
80
+ variants: field.json({
81
+ isOptional: true,
82
+ description: "Variant definitions for multivariate flags"
83
+ }),
84
+ orgId: field.string({
85
+ isOptional: true,
86
+ description: "Organization scope (null = global)"
87
+ }),
88
+ tags: field.json({
89
+ isOptional: true,
90
+ description: "Tags for categorization"
91
+ }),
92
+ metadata: field.json({
93
+ isOptional: true,
94
+ description: "Additional metadata"
95
+ }),
96
+ createdAt: field.createdAt(),
97
+ updatedAt: field.updatedAt(),
98
+ targetingRules: field.hasMany("FlagTargetingRule"),
99
+ experiments: field.hasMany("Experiment"),
100
+ evaluations: field.hasMany("FlagEvaluation")
101
+ },
102
+ indexes: [index.on(["orgId", "key"]), index.on(["status"])],
103
+ enums: [FlagStatusEnum]
104
+ });
105
+ /**
106
+ * FlagTargetingRule entity - conditions for targeting.
107
+ */
108
+ const FlagTargetingRuleEntity = defineEntity({
109
+ name: "FlagTargetingRule",
110
+ description: "A targeting rule for conditional flag evaluation.",
111
+ schema: "lssm_feature_flags",
112
+ map: "flag_targeting_rule",
113
+ fields: {
114
+ id: field.id({ description: "Unique rule identifier" }),
115
+ flagId: field.foreignKey({ description: "Parent feature flag" }),
116
+ name: field.string({
117
+ isOptional: true,
118
+ description: "Rule name for debugging"
119
+ }),
120
+ priority: field.int({
121
+ default: 0,
122
+ description: "Rule priority (lower = higher priority)"
123
+ }),
124
+ enabled: field.boolean({
125
+ default: true,
126
+ description: "Whether rule is active"
127
+ }),
128
+ attribute: field.string({ description: "Target attribute (userId, orgId, plan, segment, etc.)" }),
129
+ operator: field.enum("RuleOperator", { description: "Comparison operator" }),
130
+ value: field.json({ description: "Target value(s)" }),
131
+ rolloutPercentage: field.int({
132
+ isOptional: true,
133
+ description: "Percentage for gradual rollout (0-100)"
134
+ }),
135
+ serveValue: field.boolean({
136
+ isOptional: true,
137
+ description: "Boolean value to serve"
138
+ }),
139
+ serveVariant: field.string({
140
+ isOptional: true,
141
+ description: "Variant key to serve (for multivariate)"
142
+ }),
143
+ createdAt: field.createdAt(),
144
+ updatedAt: field.updatedAt(),
145
+ flag: field.belongsTo("FeatureFlag", ["flagId"], ["id"], { onDelete: "Cascade" })
146
+ },
147
+ indexes: [index.on(["flagId", "priority"]), index.on(["attribute"])],
148
+ enums: [RuleOperatorEnum]
149
+ });
150
+ /**
151
+ * Experiment entity - A/B test configuration.
152
+ */
153
+ const ExperimentEntity = defineEntity({
154
+ name: "Experiment",
155
+ description: "An A/B test experiment.",
156
+ schema: "lssm_feature_flags",
157
+ map: "experiment",
158
+ fields: {
159
+ id: field.id({ description: "Unique experiment identifier" }),
160
+ key: field.string({
161
+ isUnique: true,
162
+ description: "Experiment key"
163
+ }),
164
+ name: field.string({ description: "Human-readable name" }),
165
+ description: field.string({
166
+ isOptional: true,
167
+ description: "Experiment description"
168
+ }),
169
+ hypothesis: field.string({
170
+ isOptional: true,
171
+ description: "Experiment hypothesis"
172
+ }),
173
+ flagId: field.foreignKey({ description: "Associated feature flag" }),
174
+ status: field.enum("ExperimentStatus", {
175
+ default: "DRAFT",
176
+ description: "Experiment status"
177
+ }),
178
+ variants: field.json({ description: "Variant definitions with split ratios" }),
179
+ metrics: field.json({
180
+ isOptional: true,
181
+ description: "Metrics to track"
182
+ }),
183
+ audiencePercentage: field.int({
184
+ default: 100,
185
+ description: "Percentage of audience to include"
186
+ }),
187
+ audienceFilter: field.json({
188
+ isOptional: true,
189
+ description: "Audience filter criteria"
190
+ }),
191
+ scheduledStartAt: field.dateTime({
192
+ isOptional: true,
193
+ description: "Scheduled start time"
194
+ }),
195
+ scheduledEndAt: field.dateTime({
196
+ isOptional: true,
197
+ description: "Scheduled end time"
198
+ }),
199
+ startedAt: field.dateTime({
200
+ isOptional: true,
201
+ description: "Actual start time"
202
+ }),
203
+ endedAt: field.dateTime({
204
+ isOptional: true,
205
+ description: "Actual end time"
206
+ }),
207
+ winningVariant: field.string({
208
+ isOptional: true,
209
+ description: "Declared winning variant"
210
+ }),
211
+ results: field.json({
212
+ isOptional: true,
213
+ description: "Experiment results summary"
214
+ }),
215
+ orgId: field.string({
216
+ isOptional: true,
217
+ description: "Organization scope"
218
+ }),
219
+ createdAt: field.createdAt(),
220
+ updatedAt: field.updatedAt(),
221
+ flag: field.belongsTo("FeatureFlag", ["flagId"], ["id"], { onDelete: "Cascade" }),
222
+ assignments: field.hasMany("ExperimentAssignment")
223
+ },
224
+ indexes: [
225
+ index.on(["status"]),
226
+ index.on(["orgId", "status"]),
227
+ index.on(["flagId"])
228
+ ],
229
+ enums: [ExperimentStatusEnum]
230
+ });
231
+ /**
232
+ * ExperimentAssignment entity - tracks which variant a subject is assigned to.
233
+ */
234
+ const ExperimentAssignmentEntity = defineEntity({
235
+ name: "ExperimentAssignment",
236
+ description: "Tracks experiment variant assignments.",
237
+ schema: "lssm_feature_flags",
238
+ map: "experiment_assignment",
239
+ fields: {
240
+ id: field.id({ description: "Unique assignment identifier" }),
241
+ experimentId: field.foreignKey({ description: "Parent experiment" }),
242
+ subjectType: field.string({ description: "Subject type (user, org, session)" }),
243
+ subjectId: field.string({ description: "Subject identifier" }),
244
+ variant: field.string({ description: "Assigned variant key" }),
245
+ bucket: field.int({ description: "Hash bucket (0-99)" }),
246
+ context: field.json({
247
+ isOptional: true,
248
+ description: "Context at assignment time"
249
+ }),
250
+ assignedAt: field.dateTime({ description: "Assignment timestamp" }),
251
+ experiment: field.belongsTo("Experiment", ["experimentId"], ["id"], { onDelete: "Cascade" })
252
+ },
253
+ indexes: [index.unique([
254
+ "experimentId",
255
+ "subjectType",
256
+ "subjectId"
257
+ ], { name: "experiment_assignment_unique" }), index.on(["subjectType", "subjectId"])]
258
+ });
259
+ /**
260
+ * FlagEvaluation entity - evaluation log for analytics.
261
+ */
262
+ const FlagEvaluationEntity = defineEntity({
263
+ name: "FlagEvaluation",
264
+ description: "Log of flag evaluations for debugging and analytics.",
265
+ schema: "lssm_feature_flags",
266
+ map: "flag_evaluation",
267
+ fields: {
268
+ id: field.id({ description: "Unique evaluation identifier" }),
269
+ flagId: field.foreignKey({ description: "Evaluated flag" }),
270
+ flagKey: field.string({ description: "Flag key (denormalized for queries)" }),
271
+ subjectType: field.string({ description: "Subject type (user, org, anonymous)" }),
272
+ subjectId: field.string({ description: "Subject identifier" }),
273
+ result: field.boolean({ description: "Evaluation result" }),
274
+ variant: field.string({
275
+ isOptional: true,
276
+ description: "Served variant (for multivariate)"
277
+ }),
278
+ matchedRuleId: field.string({
279
+ isOptional: true,
280
+ description: "Rule that matched (if any)"
281
+ }),
282
+ reason: field.string({ description: "Evaluation reason (default, rule, experiment, etc.)" }),
283
+ context: field.json({
284
+ isOptional: true,
285
+ description: "Evaluation context"
286
+ }),
287
+ evaluatedAt: field.dateTime({ description: "Evaluation timestamp" }),
288
+ flag: field.belongsTo("FeatureFlag", ["flagId"], ["id"], { onDelete: "Cascade" })
289
+ },
290
+ indexes: [
291
+ index.on(["flagKey", "evaluatedAt"]),
292
+ index.on([
293
+ "subjectType",
294
+ "subjectId",
295
+ "evaluatedAt"
296
+ ]),
297
+ index.on(["flagId", "evaluatedAt"])
298
+ ]
299
+ });
300
+ /**
301
+ * All feature flag entities for schema composition.
302
+ */
303
+ const featureFlagEntities = [
304
+ FeatureFlagEntity,
305
+ FlagTargetingRuleEntity,
306
+ ExperimentEntity,
307
+ ExperimentAssignmentEntity,
308
+ FlagEvaluationEntity
309
+ ];
310
+ /**
311
+ * Module schema contribution for feature flags.
312
+ */
313
+ const featureFlagsSchemaContribution = {
314
+ moduleId: "@contractspec/lib.feature-flags",
315
+ entities: featureFlagEntities,
316
+ enums: [
317
+ FlagStatusEnum,
318
+ RuleOperatorEnum,
319
+ ExperimentStatusEnum
320
+ ]
321
+ };
322
+
323
+ //#endregion
324
+ export { ExperimentAssignmentEntity, ExperimentEntity, ExperimentStatusEnum, FeatureFlagEntity, FlagEvaluationEntity, FlagStatusEnum, FlagTargetingRuleEntity, RuleOperatorEnum, featureFlagEntities, featureFlagsSchemaContribution };
325
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","names":[],"sources":["../../src/entities/index.ts"],"sourcesContent":["import {\n defineEntity,\n defineEntityEnum,\n field,\n index,\n} from '@contractspec/lib.schema';\nimport type { ModuleSchemaContribution } from '@contractspec/lib.schema';\n\n/**\n * Feature flag status enum.\n */\nexport const FlagStatusEnum = defineEntityEnum({\n name: 'FlagStatus',\n values: ['OFF', 'ON', 'GRADUAL'] as const,\n schema: 'lssm_feature_flags',\n description: 'Status of a feature flag.',\n});\n\n/**\n * Targeting rule operator enum.\n */\nexport const RuleOperatorEnum = defineEntityEnum({\n name: 'RuleOperator',\n values: [\n 'EQ',\n 'NEQ',\n 'IN',\n 'NIN',\n 'CONTAINS',\n 'NOT_CONTAINS',\n 'GT',\n 'GTE',\n 'LT',\n 'LTE',\n 'PERCENTAGE',\n ] as const,\n schema: 'lssm_feature_flags',\n description: 'Operator for targeting rule conditions.',\n});\n\n/**\n * Experiment status enum.\n */\nexport const ExperimentStatusEnum = defineEntityEnum({\n name: 'ExperimentStatus',\n values: ['DRAFT', 'RUNNING', 'PAUSED', 'COMPLETED', 'CANCELLED'] as const,\n schema: 'lssm_feature_flags',\n description: 'Status of an experiment.',\n});\n\n/**\n * FeatureFlag entity - defines a feature flag.\n */\nexport const FeatureFlagEntity = defineEntity({\n name: 'FeatureFlag',\n description: 'A feature flag for controlling feature availability.',\n schema: 'lssm_feature_flags',\n map: 'feature_flag',\n fields: {\n id: field.id({ description: 'Unique flag identifier' }),\n key: field.string({\n isUnique: true,\n description: 'Flag key (e.g., new_dashboard)',\n }),\n name: field.string({ description: 'Human-readable name' }),\n description: field.string({\n isOptional: true,\n description: 'Description of the flag',\n }),\n\n // Status and default value\n status: field.enum('FlagStatus', {\n default: 'OFF',\n description: 'Flag status',\n }),\n defaultValue: field.boolean({\n default: false,\n description: 'Default value when no rules match',\n }),\n\n // Multivariate support\n variants: field.json({\n isOptional: true,\n description: 'Variant definitions for multivariate flags',\n }),\n\n // Scope\n orgId: field.string({\n isOptional: true,\n description: 'Organization scope (null = global)',\n }),\n\n // Metadata\n tags: field.json({\n isOptional: true,\n description: 'Tags for categorization',\n }),\n metadata: field.json({\n isOptional: true,\n description: 'Additional metadata',\n }),\n\n // Timestamps\n createdAt: field.createdAt(),\n updatedAt: field.updatedAt(),\n\n // Relations\n targetingRules: field.hasMany('FlagTargetingRule'),\n experiments: field.hasMany('Experiment'),\n evaluations: field.hasMany('FlagEvaluation'),\n },\n indexes: [index.on(['orgId', 'key']), index.on(['status'])],\n enums: [FlagStatusEnum],\n});\n\n/**\n * FlagTargetingRule entity - conditions for targeting.\n */\nexport const FlagTargetingRuleEntity = defineEntity({\n name: 'FlagTargetingRule',\n description: 'A targeting rule for conditional flag evaluation.',\n schema: 'lssm_feature_flags',\n map: 'flag_targeting_rule',\n fields: {\n id: field.id({ description: 'Unique rule identifier' }),\n flagId: field.foreignKey({ description: 'Parent feature flag' }),\n\n // Rule definition\n name: field.string({\n isOptional: true,\n description: 'Rule name for debugging',\n }),\n priority: field.int({\n default: 0,\n description: 'Rule priority (lower = higher priority)',\n }),\n enabled: field.boolean({\n default: true,\n description: 'Whether rule is active',\n }),\n\n // Condition\n attribute: field.string({\n description: 'Target attribute (userId, orgId, plan, segment, etc.)',\n }),\n operator: field.enum('RuleOperator', {\n description: 'Comparison operator',\n }),\n value: field.json({ description: 'Target value(s)' }),\n\n // Result\n rolloutPercentage: field.int({\n isOptional: true,\n description: 'Percentage for gradual rollout (0-100)',\n }),\n serveValue: field.boolean({\n isOptional: true,\n description: 'Boolean value to serve',\n }),\n serveVariant: field.string({\n isOptional: true,\n description: 'Variant key to serve (for multivariate)',\n }),\n\n // Timestamps\n createdAt: field.createdAt(),\n updatedAt: field.updatedAt(),\n\n // Relations\n flag: field.belongsTo('FeatureFlag', ['flagId'], ['id'], {\n onDelete: 'Cascade',\n }),\n },\n indexes: [index.on(['flagId', 'priority']), index.on(['attribute'])],\n enums: [RuleOperatorEnum],\n});\n\n/**\n * Experiment entity - A/B test configuration.\n */\nexport const ExperimentEntity = defineEntity({\n name: 'Experiment',\n description: 'An A/B test experiment.',\n schema: 'lssm_feature_flags',\n map: 'experiment',\n fields: {\n id: field.id({ description: 'Unique experiment identifier' }),\n key: field.string({ isUnique: true, description: 'Experiment key' }),\n name: field.string({ description: 'Human-readable name' }),\n description: field.string({\n isOptional: true,\n description: 'Experiment description',\n }),\n hypothesis: field.string({\n isOptional: true,\n description: 'Experiment hypothesis',\n }),\n\n // Associated flag\n flagId: field.foreignKey({ description: 'Associated feature flag' }),\n\n // Configuration\n status: field.enum('ExperimentStatus', {\n default: 'DRAFT',\n description: 'Experiment status',\n }),\n variants: field.json({\n description: 'Variant definitions with split ratios',\n }),\n metrics: field.json({ isOptional: true, description: 'Metrics to track' }),\n\n // Targeting\n audiencePercentage: field.int({\n default: 100,\n description: 'Percentage of audience to include',\n }),\n audienceFilter: field.json({\n isOptional: true,\n description: 'Audience filter criteria',\n }),\n\n // Timeline\n scheduledStartAt: field.dateTime({\n isOptional: true,\n description: 'Scheduled start time',\n }),\n scheduledEndAt: field.dateTime({\n isOptional: true,\n description: 'Scheduled end time',\n }),\n startedAt: field.dateTime({\n isOptional: true,\n description: 'Actual start time',\n }),\n endedAt: field.dateTime({\n isOptional: true,\n description: 'Actual end time',\n }),\n\n // Results\n winningVariant: field.string({\n isOptional: true,\n description: 'Declared winning variant',\n }),\n results: field.json({\n isOptional: true,\n description: 'Experiment results summary',\n }),\n\n // Scope\n orgId: field.string({\n isOptional: true,\n description: 'Organization scope',\n }),\n\n // Timestamps\n createdAt: field.createdAt(),\n updatedAt: field.updatedAt(),\n\n // Relations\n flag: field.belongsTo('FeatureFlag', ['flagId'], ['id'], {\n onDelete: 'Cascade',\n }),\n assignments: field.hasMany('ExperimentAssignment'),\n },\n indexes: [\n index.on(['status']),\n index.on(['orgId', 'status']),\n index.on(['flagId']),\n ],\n enums: [ExperimentStatusEnum],\n});\n\n/**\n * ExperimentAssignment entity - tracks which variant a subject is assigned to.\n */\nexport const ExperimentAssignmentEntity = defineEntity({\n name: 'ExperimentAssignment',\n description: 'Tracks experiment variant assignments.',\n schema: 'lssm_feature_flags',\n map: 'experiment_assignment',\n fields: {\n id: field.id({ description: 'Unique assignment identifier' }),\n experimentId: field.foreignKey({ description: 'Parent experiment' }),\n\n // Subject\n subjectType: field.string({\n description: 'Subject type (user, org, session)',\n }),\n subjectId: field.string({ description: 'Subject identifier' }),\n\n // Assignment\n variant: field.string({ description: 'Assigned variant key' }),\n bucket: field.int({ description: 'Hash bucket (0-99)' }),\n\n // Context\n context: field.json({\n isOptional: true,\n description: 'Context at assignment time',\n }),\n\n // Timestamps\n assignedAt: field.dateTime({ description: 'Assignment timestamp' }),\n\n // Relations\n experiment: field.belongsTo('Experiment', ['experimentId'], ['id'], {\n onDelete: 'Cascade',\n }),\n },\n indexes: [\n index.unique(['experimentId', 'subjectType', 'subjectId'], {\n name: 'experiment_assignment_unique',\n }),\n index.on(['subjectType', 'subjectId']),\n ],\n});\n\n/**\n * FlagEvaluation entity - evaluation log for analytics.\n */\nexport const FlagEvaluationEntity = defineEntity({\n name: 'FlagEvaluation',\n description: 'Log of flag evaluations for debugging and analytics.',\n schema: 'lssm_feature_flags',\n map: 'flag_evaluation',\n fields: {\n id: field.id({ description: 'Unique evaluation identifier' }),\n flagId: field.foreignKey({ description: 'Evaluated flag' }),\n flagKey: field.string({\n description: 'Flag key (denormalized for queries)',\n }),\n\n // Subject\n subjectType: field.string({\n description: 'Subject type (user, org, anonymous)',\n }),\n subjectId: field.string({ description: 'Subject identifier' }),\n\n // Result\n result: field.boolean({ description: 'Evaluation result' }),\n variant: field.string({\n isOptional: true,\n description: 'Served variant (for multivariate)',\n }),\n\n // Match info\n matchedRuleId: field.string({\n isOptional: true,\n description: 'Rule that matched (if any)',\n }),\n reason: field.string({\n description: 'Evaluation reason (default, rule, experiment, etc.)',\n }),\n\n // Context\n context: field.json({\n isOptional: true,\n description: 'Evaluation context',\n }),\n\n // Timestamps\n evaluatedAt: field.dateTime({ description: 'Evaluation timestamp' }),\n\n // Relations\n flag: field.belongsTo('FeatureFlag', ['flagId'], ['id'], {\n onDelete: 'Cascade',\n }),\n },\n indexes: [\n index.on(['flagKey', 'evaluatedAt']),\n index.on(['subjectType', 'subjectId', 'evaluatedAt']),\n index.on(['flagId', 'evaluatedAt']),\n ],\n});\n\n/**\n * All feature flag entities for schema composition.\n */\nexport const featureFlagEntities = [\n FeatureFlagEntity,\n FlagTargetingRuleEntity,\n ExperimentEntity,\n ExperimentAssignmentEntity,\n FlagEvaluationEntity,\n];\n\n/**\n * Module schema contribution for feature flags.\n */\nexport const featureFlagsSchemaContribution: ModuleSchemaContribution = {\n moduleId: '@contractspec/lib.feature-flags',\n entities: featureFlagEntities,\n enums: [FlagStatusEnum, RuleOperatorEnum, ExperimentStatusEnum],\n};\n"],"mappings":"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"}
@@ -0,0 +1,163 @@
1
+ //#region src/evaluation/index.d.ts
2
+ /**
3
+ * Feature flag evaluation engine.
4
+ *
5
+ * Provides deterministic evaluation of feature flags based on targeting rules
6
+ * and experiment assignments.
7
+ */
8
+ interface EvaluationContext {
9
+ /** User identifier */
10
+ userId?: string;
11
+ /** Organization identifier */
12
+ orgId?: string;
13
+ /** User's plan (free, pro, enterprise, etc.) */
14
+ plan?: string;
15
+ /** User segment or cohort */
16
+ segment?: string;
17
+ /** Session identifier for anonymous users */
18
+ sessionId?: string;
19
+ /** Additional custom attributes */
20
+ attributes?: Record<string, unknown>;
21
+ }
22
+ interface FeatureFlag {
23
+ id: string;
24
+ key: string;
25
+ status: 'OFF' | 'ON' | 'GRADUAL';
26
+ defaultValue: boolean;
27
+ variants?: VariantConfig[];
28
+ }
29
+ interface TargetingRule {
30
+ id: string;
31
+ priority: number;
32
+ enabled: boolean;
33
+ attribute: string;
34
+ operator: RuleOperator;
35
+ value: unknown;
36
+ rolloutPercentage?: number;
37
+ serveValue?: boolean;
38
+ serveVariant?: string;
39
+ }
40
+ interface Experiment {
41
+ id: string;
42
+ key: string;
43
+ status: 'DRAFT' | 'RUNNING' | 'PAUSED' | 'COMPLETED' | 'CANCELLED';
44
+ variants: ExperimentVariant[];
45
+ audiencePercentage: number;
46
+ audienceFilter?: Record<string, unknown>;
47
+ }
48
+ interface VariantConfig {
49
+ key: string;
50
+ name: string;
51
+ description?: string;
52
+ weight?: number;
53
+ }
54
+ interface ExperimentVariant {
55
+ key: string;
56
+ name: string;
57
+ percentage: number;
58
+ }
59
+ interface EvaluationResult {
60
+ enabled: boolean;
61
+ variant?: string;
62
+ reason: EvaluationReason;
63
+ ruleId?: string;
64
+ experimentId?: string;
65
+ }
66
+ type EvaluationReason = 'FLAG_OFF' | 'FLAG_ON' | 'DEFAULT_VALUE' | 'RULE_MATCH' | 'PERCENTAGE_ROLLOUT' | 'EXPERIMENT_VARIANT' | 'FLAG_NOT_FOUND';
67
+ type RuleOperator = 'EQ' | 'NEQ' | 'IN' | 'NIN' | 'CONTAINS' | 'NOT_CONTAINS' | 'GT' | 'GTE' | 'LT' | 'LTE' | 'PERCENTAGE';
68
+ /**
69
+ * Simple hash function for consistent bucketing.
70
+ * Uses a deterministic algorithm so the same input always produces the same bucket.
71
+ */
72
+ declare function hashToBucket(value: string, seed?: string): number;
73
+ /**
74
+ * Get subject identifier from context for consistent hashing.
75
+ */
76
+ declare function getSubjectId(context: EvaluationContext): string;
77
+ /**
78
+ * Evaluate a single targeting rule condition.
79
+ */
80
+ declare function evaluateRuleCondition(rule: TargetingRule, context: EvaluationContext): boolean;
81
+ interface FlagRepository {
82
+ getFlag(key: string, orgId?: string): Promise<FeatureFlag | null>;
83
+ getRules(flagId: string): Promise<TargetingRule[]>;
84
+ getActiveExperiment(flagId: string): Promise<Experiment | null>;
85
+ getExperimentAssignment(experimentId: string, subjectType: string, subjectId: string): Promise<string | null>;
86
+ saveExperimentAssignment(experimentId: string, subjectType: string, subjectId: string, variant: string, bucket: number): Promise<void>;
87
+ }
88
+ interface EvaluationLogger {
89
+ log(evaluation: {
90
+ flagId: string;
91
+ flagKey: string;
92
+ subjectType: string;
93
+ subjectId: string;
94
+ result: boolean;
95
+ variant?: string;
96
+ reason: string;
97
+ ruleId?: string;
98
+ experimentId?: string;
99
+ context?: EvaluationContext;
100
+ }): void;
101
+ }
102
+ interface FlagEvaluatorOptions {
103
+ repository: FlagRepository;
104
+ logger?: EvaluationLogger;
105
+ /** Whether to log evaluations (default: false for performance) */
106
+ logEvaluations?: boolean;
107
+ }
108
+ /**
109
+ * Feature flag evaluator.
110
+ *
111
+ * Evaluates flags based on:
112
+ * 1. Flag status (OFF/ON/GRADUAL)
113
+ * 2. Targeting rules (in priority order)
114
+ * 3. Experiments (if running)
115
+ * 4. Default value (fallback)
116
+ */
117
+ declare class FlagEvaluator {
118
+ private repository;
119
+ private logger?;
120
+ private logEvaluations;
121
+ constructor(options: FlagEvaluatorOptions);
122
+ /**
123
+ * Evaluate a feature flag.
124
+ */
125
+ evaluate(key: string, context: EvaluationContext): Promise<EvaluationResult>;
126
+ /**
127
+ * Evaluate experiment and assign variant.
128
+ */
129
+ private evaluateExperiment;
130
+ /**
131
+ * Assign a variant based on bucket and variant percentages.
132
+ */
133
+ private assignVariant;
134
+ /**
135
+ * Create evaluation result.
136
+ */
137
+ private makeResult;
138
+ /**
139
+ * Log evaluation and return result.
140
+ */
141
+ private logAndReturn;
142
+ }
143
+ /**
144
+ * In-memory flag repository for testing and development.
145
+ */
146
+ declare class InMemoryFlagRepository implements FlagRepository {
147
+ private flags;
148
+ private rules;
149
+ private experiments;
150
+ private assignments;
151
+ addFlag(flag: FeatureFlag): void;
152
+ addRule(flagId: string, rule: TargetingRule): void;
153
+ addExperiment(experiment: Experiment, flagId: string): void;
154
+ getFlag(key: string): Promise<FeatureFlag | null>;
155
+ getRules(flagId: string): Promise<TargetingRule[]>;
156
+ getActiveExperiment(flagId: string): Promise<Experiment | null>;
157
+ getExperimentAssignment(experimentId: string, subjectType: string, subjectId: string): Promise<string | null>;
158
+ saveExperimentAssignment(experimentId: string, subjectType: string, subjectId: string, variant: string): Promise<void>;
159
+ clear(): void;
160
+ }
161
+ //#endregion
162
+ export { EvaluationContext, EvaluationLogger, EvaluationReason, EvaluationResult, Experiment, ExperimentVariant, FeatureFlag, FlagEvaluator, FlagEvaluatorOptions, FlagRepository, InMemoryFlagRepository, RuleOperator, TargetingRule, VariantConfig, evaluateRuleCondition, getSubjectId, hashToBucket };
163
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","names":[],"sources":["../../src/evaluation/index.ts"],"sourcesContent":[],"mappings":";;AASA;AAeA;AAQA;AAYA;AASA;AAOiB,UAnDA,iBAAA,CAmDiB;EAMjB;EAQL,MAAA,CAAA,EAAA,MAAA;EASA;EAmBI,KAAA,CAAA,EAAA,MAAA;EAeA;EASA,IAAA,CAAA,EAAA,MAAA;EAwFC;EAC+B,OAAA,CAAA,EAAA,MAAA;EAAR;EACJ,SAAA,CAAA,EAAA,MAAA;EAAR;EACmB,UAAA,CAAA,EApMhC,MAoMgC,CAAA,MAAA,EAAA,OAAA,CAAA;;AAK1C,UAtMY,WAAA,CAsMZ;EAOA,EAAA,EAAA,MAAA;EAAO,GAAA,EAAA,MAAA;EAGK,MAAA,EAAA,KAAA,GAAA,IAAgB,GAAA,SAWnB;EAIG,YAAA,EAAA,OAAA;EAgBJ,QAAA,CAAA,EA1OA,aA0Oa,EAAA;;AAgBb,UAvPI,aAAA,CAuPJ;EACA,EAAA,EAAA,MAAA;EAAR,QAAA,EAAA,MAAA;EAAO,OAAA,EAAA,OAAA;EAsMC,SAAA,EAAA,MAAA;EAMG,QAAA,EA/bJ,YA+bI;EAIgB,KAAA,EAAA,OAAA;EAMJ,iBAAA,CAAA,EAAA,MAAA;EAIU,UAAA,CAAA,EAAA,OAAA;EAAR,YAAA,CAAA,EAAA,MAAA;;AAII,UA1cjB,UAAA,CA0ciB;EAImB,EAAA,EAAA,MAAA;EAAR,GAAA,EAAA,MAAA;EAQxC,MAAA,EAAA,OAAA,GAAA,SAAA,GAAA,QAAA,GAAA,WAAA,GAAA,WAAA;EAUA,QAAA,EA5dO,iBA4dP,EAAA;EA9C0C,kBAAA,EAAA,MAAA;EAAc,cAAA,CAAA,EA5a1C,MA4a0C,CAAA,MAAA,EAAA,OAAA,CAAA;;UAza5C,aAAA;;;;;;UAOA,iBAAA;;;;;UAMA,gBAAA;;;UAGP;;;;KAKE,gBAAA;KASA,YAAA;;;;;iBAmBI,YAAA;;;;iBAeA,YAAA,UAAsB;;;;iBAStB,qBAAA,OACR,wBACG;UAsFM,cAAA;wCACuB,QAAQ;4BACpB,QAAQ;uCACG,QAAQ;yFAK1C;2HAOA;;UAGY,gBAAA;;;;;;;;;;;cAWH;;;UAIG,oBAAA;cACH;WACH;;;;;;;;;;;;;cAcE,aAAA;;;;uBAKU;;;;iCAWV,oBACR,QAAQ;;;;;;;;;;;;;;;;;;;;;cAsMA,sBAAA,YAAkC;;;;;gBAM/B;gCAIgB;4BAMJ;wBAIE,QAAQ;4BAIJ,QAAQ;uCAIG,QAAQ;yFAQhD;2GAUA"}