@contractspec/example.saas-boilerplate 3.7.6 → 3.8.2

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 (143) hide show
  1. package/.turbo/turbo-build.log +39 -27
  2. package/AGENTS.md +50 -27
  3. package/CHANGELOG.md +36 -0
  4. package/README.md +65 -144
  5. package/dist/billing/billing.event.js +1 -1
  6. package/dist/billing/index.d.ts +6 -6
  7. package/dist/billing/index.js +1 -1
  8. package/dist/browser/billing/billing.event.js +1 -1
  9. package/dist/browser/billing/index.js +1 -1
  10. package/dist/browser/index.js +1147 -869
  11. package/dist/browser/project/index.js +209 -209
  12. package/dist/browser/project/project.event.js +1 -1
  13. package/dist/browser/saas-boilerplate.feature.js +208 -0
  14. package/dist/browser/ui/SaasDashboard.js +356 -105
  15. package/dist/browser/ui/SaasDashboard.visualizations.js +249 -0
  16. package/dist/browser/ui/SaasProjectList.js +7 -7
  17. package/dist/browser/ui/SaasSettingsPanel.js +12 -12
  18. package/dist/browser/ui/hooks/index.js +2 -2
  19. package/dist/browser/ui/hooks/useProjectList.js +1 -1
  20. package/dist/browser/ui/hooks/useProjectMutations.js +1 -1
  21. package/dist/browser/ui/index.js +790 -521
  22. package/dist/browser/ui/modals/CreateProjectModal.js +10 -10
  23. package/dist/browser/ui/modals/ProjectActionsModal.js +13 -13
  24. package/dist/browser/ui/modals/index.js +23 -23
  25. package/dist/browser/ui/renderers/index.js +341 -115
  26. package/dist/browser/ui/renderers/project-list.markdown.js +229 -3
  27. package/dist/browser/ui/renderers/project-list.renderer.js +7 -7
  28. package/dist/browser/visualizations/catalog.js +155 -0
  29. package/dist/browser/visualizations/index.js +217 -0
  30. package/dist/browser/visualizations/selectors.js +210 -0
  31. package/dist/handlers/index.d.ts +2 -2
  32. package/dist/index.d.ts +5 -4
  33. package/dist/index.js +1147 -869
  34. package/dist/node/billing/billing.event.js +1 -1
  35. package/dist/node/billing/index.js +1 -1
  36. package/dist/node/index.js +1147 -869
  37. package/dist/node/project/index.js +209 -209
  38. package/dist/node/project/project.event.js +1 -1
  39. package/dist/node/saas-boilerplate.feature.js +208 -0
  40. package/dist/node/ui/SaasDashboard.js +356 -105
  41. package/dist/node/ui/SaasDashboard.visualizations.js +249 -0
  42. package/dist/node/ui/SaasProjectList.js +7 -7
  43. package/dist/node/ui/SaasSettingsPanel.js +12 -12
  44. package/dist/node/ui/hooks/index.js +2 -2
  45. package/dist/node/ui/hooks/useProjectList.js +1 -1
  46. package/dist/node/ui/hooks/useProjectMutations.js +1 -1
  47. package/dist/node/ui/index.js +790 -521
  48. package/dist/node/ui/modals/CreateProjectModal.js +10 -10
  49. package/dist/node/ui/modals/ProjectActionsModal.js +13 -13
  50. package/dist/node/ui/modals/index.js +23 -23
  51. package/dist/node/ui/renderers/index.js +341 -115
  52. package/dist/node/ui/renderers/project-list.markdown.js +229 -3
  53. package/dist/node/ui/renderers/project-list.renderer.js +7 -7
  54. package/dist/node/visualizations/catalog.js +155 -0
  55. package/dist/node/visualizations/index.js +217 -0
  56. package/dist/node/visualizations/selectors.js +210 -0
  57. package/dist/presentations/index.d.ts +1 -1
  58. package/dist/project/index.d.ts +7 -7
  59. package/dist/project/index.js +209 -209
  60. package/dist/project/project.event.js +1 -1
  61. package/dist/saas-boilerplate.feature.js +208 -0
  62. package/dist/settings/index.d.ts +1 -1
  63. package/dist/ui/SaasDashboard.js +356 -105
  64. package/dist/ui/SaasDashboard.visualizations.d.ts +5 -0
  65. package/dist/ui/SaasDashboard.visualizations.js +250 -0
  66. package/dist/ui/SaasProjectList.js +7 -7
  67. package/dist/ui/SaasSettingsPanel.js +12 -12
  68. package/dist/ui/hooks/index.d.ts +2 -2
  69. package/dist/ui/hooks/index.js +2 -2
  70. package/dist/ui/hooks/useProjectList.d.ts +5 -0
  71. package/dist/ui/hooks/useProjectList.js +1 -1
  72. package/dist/ui/hooks/useProjectMutations.d.ts +8 -0
  73. package/dist/ui/hooks/useProjectMutations.js +1 -1
  74. package/dist/ui/index.d.ts +4 -4
  75. package/dist/ui/index.js +790 -521
  76. package/dist/ui/modals/CreateProjectModal.js +10 -10
  77. package/dist/ui/modals/ProjectActionsModal.js +13 -13
  78. package/dist/ui/modals/index.js +23 -23
  79. package/dist/ui/renderers/index.d.ts +1 -1
  80. package/dist/ui/renderers/index.js +341 -115
  81. package/dist/ui/renderers/project-list.markdown.js +229 -3
  82. package/dist/ui/renderers/project-list.renderer.d.ts +1 -1
  83. package/dist/ui/renderers/project-list.renderer.js +7 -7
  84. package/dist/visualizations/catalog.d.ts +11 -0
  85. package/dist/visualizations/catalog.js +156 -0
  86. package/dist/visualizations/index.d.ts +2 -0
  87. package/dist/visualizations/index.js +218 -0
  88. package/dist/visualizations/selectors.d.ts +8 -0
  89. package/dist/visualizations/selectors.js +211 -0
  90. package/dist/visualizations/selectors.test.d.ts +1 -0
  91. package/package.json +70 -14
  92. package/src/billing/billing.entity.ts +132 -132
  93. package/src/billing/billing.enum.ts +9 -9
  94. package/src/billing/billing.event.ts +71 -71
  95. package/src/billing/billing.handler.ts +87 -87
  96. package/src/billing/billing.operations.ts +158 -158
  97. package/src/billing/billing.presentation.ts +45 -45
  98. package/src/billing/billing.schema.ts +76 -76
  99. package/src/billing/index.ts +43 -48
  100. package/src/dashboard/dashboard.presentation.ts +45 -45
  101. package/src/dashboard/index.ts +2 -2
  102. package/src/docs/saas-boilerplate.docblock.ts +43 -43
  103. package/src/example.ts +32 -32
  104. package/src/handlers/index.ts +9 -9
  105. package/src/handlers/saas.handlers.ts +250 -249
  106. package/src/index.ts +41 -41
  107. package/src/presentations/index.ts +18 -20
  108. package/src/project/index.ts +45 -50
  109. package/src/project/project.entity.ts +68 -68
  110. package/src/project/project.enum.ts +8 -8
  111. package/src/project/project.event.ts +79 -79
  112. package/src/project/project.handler.ts +103 -103
  113. package/src/project/project.operations.ts +236 -236
  114. package/src/project/project.presentation.ts +46 -46
  115. package/src/project/project.schema.ts +90 -90
  116. package/src/saas-boilerplate.feature.ts +103 -100
  117. package/src/seeders/index.ts +20 -20
  118. package/src/settings/index.ts +2 -3
  119. package/src/settings/settings.entity.ts +65 -65
  120. package/src/settings/settings.enum.ts +4 -4
  121. package/src/shared/mock-data.ts +92 -92
  122. package/src/shared/overlay-types.ts +23 -23
  123. package/src/tests/operations.test-spec.ts +96 -96
  124. package/src/ui/SaasDashboard.tsx +278 -270
  125. package/src/ui/SaasDashboard.visualizations.tsx +41 -0
  126. package/src/ui/SaasProjectList.tsx +90 -90
  127. package/src/ui/SaasSettingsPanel.tsx +84 -84
  128. package/src/ui/hooks/index.ts +3 -3
  129. package/src/ui/hooks/useProjectList.ts +69 -68
  130. package/src/ui/hooks/useProjectMutations.ts +144 -143
  131. package/src/ui/index.ts +8 -12
  132. package/src/ui/modals/CreateProjectModal.tsx +154 -154
  133. package/src/ui/modals/ProjectActionsModal.tsx +321 -321
  134. package/src/ui/overlays/demo-overlays.ts +49 -49
  135. package/src/ui/renderers/index.ts +5 -4
  136. package/src/ui/renderers/project-list.markdown.ts +229 -205
  137. package/src/ui/renderers/project-list.renderer.tsx +14 -13
  138. package/src/visualizations/catalog.ts +153 -0
  139. package/src/visualizations/index.ts +2 -0
  140. package/src/visualizations/selectors.test.ts +25 -0
  141. package/src/visualizations/selectors.ts +85 -0
  142. package/tsconfig.json +7 -8
  143. package/tsdown.config.js +7 -3
@@ -1,13 +1,13 @@
1
1
  import { defineCommand, defineQuery } from '@contractspec/lib.contracts-spec';
2
2
  import {
3
- CheckFeatureAccessInputModel,
4
- CheckFeatureAccessOutputModel,
5
- GetUsageSummaryInputModel,
6
- GetUsageSummaryOutputModel,
7
- RecordUsageInputModel,
8
- RecordUsageOutputModel,
9
- SubscriptionModel,
10
- UsageRecordedPayloadModel,
3
+ CheckFeatureAccessInputModel,
4
+ CheckFeatureAccessOutputModel,
5
+ GetUsageSummaryInputModel,
6
+ GetUsageSummaryOutputModel,
7
+ RecordUsageInputModel,
8
+ RecordUsageOutputModel,
9
+ SubscriptionModel,
10
+ UsageRecordedPayloadModel,
11
11
  } from './billing.schema';
12
12
 
13
13
  const OWNERS = ['@example.saas-boilerplate'] as const;
@@ -16,172 +16,172 @@ const OWNERS = ['@example.saas-boilerplate'] as const;
16
16
  * Get subscription status.
17
17
  */
18
18
  export const GetSubscriptionContract = defineQuery({
19
- meta: {
20
- key: 'saas.billing.subscription.get',
21
- version: '1.0.0',
22
- stability: 'stable',
23
- owners: [...OWNERS],
24
- tags: ['saas', 'billing', 'subscription'],
25
- description: 'Get organization subscription status.',
26
- goal: 'Show current plan and billing status.',
27
- context: 'Billing page, plan upgrade prompts.',
28
- },
29
- io: {
30
- input: null,
31
- output: SubscriptionModel,
32
- },
33
- policy: {
34
- auth: 'user',
35
- },
36
- acceptance: {
37
- scenarios: [
38
- {
39
- key: 'get-subscription-happy-path',
40
- given: ['Organization has active subscription'],
41
- when: ['User requests subscription status'],
42
- then: ['Subscription details are returned'],
43
- },
44
- ],
45
- examples: [
46
- {
47
- key: 'get-basic',
48
- input: null,
49
- output: {
50
- plan: 'pro',
51
- status: 'active',
52
- currentPeriodEnd: '2025-02-01T00:00:00Z',
53
- },
54
- },
55
- ],
56
- },
19
+ meta: {
20
+ key: 'saas.billing.subscription.get',
21
+ version: '1.0.0',
22
+ stability: 'stable',
23
+ owners: [...OWNERS],
24
+ tags: ['saas', 'billing', 'subscription'],
25
+ description: 'Get organization subscription status.',
26
+ goal: 'Show current plan and billing status.',
27
+ context: 'Billing page, plan upgrade prompts.',
28
+ },
29
+ io: {
30
+ input: null,
31
+ output: SubscriptionModel,
32
+ },
33
+ policy: {
34
+ auth: 'user',
35
+ },
36
+ acceptance: {
37
+ scenarios: [
38
+ {
39
+ key: 'get-subscription-happy-path',
40
+ given: ['Organization has active subscription'],
41
+ when: ['User requests subscription status'],
42
+ then: ['Subscription details are returned'],
43
+ },
44
+ ],
45
+ examples: [
46
+ {
47
+ key: 'get-basic',
48
+ input: null,
49
+ output: {
50
+ plan: 'pro',
51
+ status: 'active',
52
+ currentPeriodEnd: '2025-02-01T00:00:00Z',
53
+ },
54
+ },
55
+ ],
56
+ },
57
57
  });
58
58
 
59
59
  /**
60
60
  * Record feature usage.
61
61
  */
62
62
  export const RecordUsageContract = defineCommand({
63
- meta: {
64
- key: 'saas.billing.usage.record',
65
- version: '1.0.0',
66
- stability: 'stable',
67
- owners: [...OWNERS],
68
- tags: ['saas', 'billing', 'usage'],
69
- description: 'Record usage of a metered feature.',
70
- goal: 'Track feature usage for billing.',
71
- context: 'Called by services when metered features are used.',
72
- },
73
- io: {
74
- input: RecordUsageInputModel,
75
- output: RecordUsageOutputModel,
76
- },
77
- policy: {
78
- auth: 'user',
79
- },
80
- sideEffects: {
81
- emits: [
82
- {
83
- key: 'billing.usage.recorded',
84
- version: '1.0.0',
85
- when: 'Usage is recorded',
86
- payload: UsageRecordedPayloadModel,
87
- },
88
- ],
89
- },
90
- acceptance: {
91
- scenarios: [
92
- {
93
- key: 'record-usage-happy-path',
94
- given: ['Organization exists'],
95
- when: ['System records feature usage'],
96
- then: ['Usage is recorded'],
97
- },
98
- ],
99
- examples: [
100
- {
101
- key: 'record-api-call',
102
- input: { feature: 'api_calls', quantity: 1, idempotencyKey: 'abc-123' },
103
- output: { recorded: true, currentUsage: 100 },
104
- },
105
- ],
106
- },
63
+ meta: {
64
+ key: 'saas.billing.usage.record',
65
+ version: '1.0.0',
66
+ stability: 'stable',
67
+ owners: [...OWNERS],
68
+ tags: ['saas', 'billing', 'usage'],
69
+ description: 'Record usage of a metered feature.',
70
+ goal: 'Track feature usage for billing.',
71
+ context: 'Called by services when metered features are used.',
72
+ },
73
+ io: {
74
+ input: RecordUsageInputModel,
75
+ output: RecordUsageOutputModel,
76
+ },
77
+ policy: {
78
+ auth: 'user',
79
+ },
80
+ sideEffects: {
81
+ emits: [
82
+ {
83
+ key: 'billing.usage.recorded',
84
+ version: '1.0.0',
85
+ when: 'Usage is recorded',
86
+ payload: UsageRecordedPayloadModel,
87
+ },
88
+ ],
89
+ },
90
+ acceptance: {
91
+ scenarios: [
92
+ {
93
+ key: 'record-usage-happy-path',
94
+ given: ['Organization exists'],
95
+ when: ['System records feature usage'],
96
+ then: ['Usage is recorded'],
97
+ },
98
+ ],
99
+ examples: [
100
+ {
101
+ key: 'record-api-call',
102
+ input: { feature: 'api_calls', quantity: 1, idempotencyKey: 'abc-123' },
103
+ output: { recorded: true, currentUsage: 100 },
104
+ },
105
+ ],
106
+ },
107
107
  });
108
108
 
109
109
  /**
110
110
  * Get usage summary.
111
111
  */
112
112
  export const GetUsageSummaryContract = defineQuery({
113
- meta: {
114
- key: 'saas.billing.usage.summary',
115
- version: '1.0.0',
116
- stability: 'stable',
117
- owners: [...OWNERS],
118
- tags: ['saas', 'billing', 'usage'],
119
- description: 'Get usage summary for the current billing period.',
120
- goal: 'Show usage vs limits.',
121
- context: 'Billing page, usage dashboards.',
122
- },
123
- io: {
124
- input: GetUsageSummaryInputModel,
125
- output: GetUsageSummaryOutputModel,
126
- },
127
- policy: {
128
- auth: 'user',
129
- },
130
- acceptance: {
131
- scenarios: [
132
- {
133
- key: 'get-usage-happy-path',
134
- given: ['Organization has usage history'],
135
- when: ['User requests usage summary'],
136
- then: ['Usage metrics are returned'],
137
- },
138
- ],
139
- examples: [
140
- {
141
- key: 'get-current-usage',
142
- input: { period: 'current' },
143
- output: { features: [{ name: 'api_calls', used: 100, limit: 1000 }] },
144
- },
145
- ],
146
- },
113
+ meta: {
114
+ key: 'saas.billing.usage.summary',
115
+ version: '1.0.0',
116
+ stability: 'stable',
117
+ owners: [...OWNERS],
118
+ tags: ['saas', 'billing', 'usage'],
119
+ description: 'Get usage summary for the current billing period.',
120
+ goal: 'Show usage vs limits.',
121
+ context: 'Billing page, usage dashboards.',
122
+ },
123
+ io: {
124
+ input: GetUsageSummaryInputModel,
125
+ output: GetUsageSummaryOutputModel,
126
+ },
127
+ policy: {
128
+ auth: 'user',
129
+ },
130
+ acceptance: {
131
+ scenarios: [
132
+ {
133
+ key: 'get-usage-happy-path',
134
+ given: ['Organization has usage history'],
135
+ when: ['User requests usage summary'],
136
+ then: ['Usage metrics are returned'],
137
+ },
138
+ ],
139
+ examples: [
140
+ {
141
+ key: 'get-current-usage',
142
+ input: { period: 'current' },
143
+ output: { features: [{ name: 'api_calls', used: 100, limit: 1000 }] },
144
+ },
145
+ ],
146
+ },
147
147
  });
148
148
 
149
149
  /**
150
150
  * Check feature access.
151
151
  */
152
152
  export const CheckFeatureAccessContract = defineQuery({
153
- meta: {
154
- key: 'saas.billing.feature.check',
155
- version: '1.0.0',
156
- stability: 'stable',
157
- owners: [...OWNERS],
158
- tags: ['saas', 'billing', 'feature'],
159
- description: 'Check if organization has access to a feature.',
160
- goal: 'Gate features based on plan/usage.',
161
- context: 'Feature access checks, upgrade prompts.',
162
- },
163
- io: {
164
- input: CheckFeatureAccessInputModel,
165
- output: CheckFeatureAccessOutputModel,
166
- },
167
- policy: {
168
- auth: 'user',
169
- },
170
- acceptance: {
171
- scenarios: [
172
- {
173
- key: 'check-access-granted',
174
- given: ['Organization is on Pro plan'],
175
- when: ['User checks access to Pro feature'],
176
- then: ['Access is granted'],
177
- },
178
- ],
179
- examples: [
180
- {
181
- key: 'check-advanced-reports',
182
- input: { feature: 'advanced_reports' },
183
- output: { hasAccess: true, reason: 'Included in Pro plan' },
184
- },
185
- ],
186
- },
153
+ meta: {
154
+ key: 'saas.billing.feature.check',
155
+ version: '1.0.0',
156
+ stability: 'stable',
157
+ owners: [...OWNERS],
158
+ tags: ['saas', 'billing', 'feature'],
159
+ description: 'Check if organization has access to a feature.',
160
+ goal: 'Gate features based on plan/usage.',
161
+ context: 'Feature access checks, upgrade prompts.',
162
+ },
163
+ io: {
164
+ input: CheckFeatureAccessInputModel,
165
+ output: CheckFeatureAccessOutputModel,
166
+ },
167
+ policy: {
168
+ auth: 'user',
169
+ },
170
+ acceptance: {
171
+ scenarios: [
172
+ {
173
+ key: 'check-access-granted',
174
+ given: ['Organization is on Pro plan'],
175
+ when: ['User checks access to Pro feature'],
176
+ then: ['Access is granted'],
177
+ },
178
+ ],
179
+ examples: [
180
+ {
181
+ key: 'check-advanced-reports',
182
+ input: { feature: 'advanced_reports' },
183
+ output: { hasAccess: true, reason: 'Included in Pro plan' },
184
+ },
185
+ ],
186
+ },
187
187
  });
@@ -1,59 +1,59 @@
1
1
  import {
2
- definePresentation,
3
- StabilityEnum,
2
+ definePresentation,
3
+ StabilityEnum,
4
4
  } from '@contractspec/lib.contracts-spec';
5
5
 
6
6
  /**
7
7
  * Presentation for subscription overview.
8
8
  */
9
9
  export const SubscriptionPresentation = definePresentation({
10
- meta: {
11
- key: 'saas.billing.subscription',
12
- version: '1.0.0',
13
- title: 'Subscription Status',
14
- description:
15
- 'Subscription status with plan info, limits, and current usage',
16
- domain: 'saas-boilerplate',
17
- owners: ['@saas-team'],
18
- tags: ['billing', 'subscription'],
19
- stability: StabilityEnum.Beta,
20
- goal: 'View subscription plan and status',
21
- context: 'Billing section',
22
- },
23
- source: {
24
- type: 'component',
25
- framework: 'react',
26
- componentKey: 'SubscriptionView',
27
- },
28
- targets: ['react', 'markdown'],
29
- policy: {
30
- flags: ['saas.billing.enabled'],
31
- },
10
+ meta: {
11
+ key: 'saas.billing.subscription',
12
+ version: '1.0.0',
13
+ title: 'Subscription Status',
14
+ description:
15
+ 'Subscription status with plan info, limits, and current usage',
16
+ domain: 'saas-boilerplate',
17
+ owners: ['@saas-team'],
18
+ tags: ['billing', 'subscription'],
19
+ stability: StabilityEnum.Beta,
20
+ goal: 'View subscription plan and status',
21
+ context: 'Billing section',
22
+ },
23
+ source: {
24
+ type: 'component',
25
+ framework: 'react',
26
+ componentKey: 'SubscriptionView',
27
+ },
28
+ targets: ['react', 'markdown'],
29
+ policy: {
30
+ flags: ['saas.billing.enabled'],
31
+ },
32
32
  });
33
33
 
34
34
  /**
35
35
  * Presentation for usage dashboard.
36
36
  */
37
37
  export const UsageDashboardPresentation = definePresentation({
38
- meta: {
39
- key: 'saas.billing.usage',
40
- version: '1.0.0',
41
- title: 'Usage Dashboard',
42
- description: 'Usage metrics and breakdown by resource type',
43
- domain: 'saas-boilerplate',
44
- owners: ['@saas-team'],
45
- tags: ['billing', 'usage', 'metrics'],
46
- stability: StabilityEnum.Beta,
47
- goal: 'Monitor feature usage and limits',
48
- context: 'Billing section',
49
- },
50
- source: {
51
- type: 'component',
52
- framework: 'react',
53
- componentKey: 'UsageDashboardView',
54
- },
55
- targets: ['react', 'markdown'],
56
- policy: {
57
- flags: ['saas.billing.enabled'],
58
- },
38
+ meta: {
39
+ key: 'saas.billing.usage',
40
+ version: '1.0.0',
41
+ title: 'Usage Dashboard',
42
+ description: 'Usage metrics and breakdown by resource type',
43
+ domain: 'saas-boilerplate',
44
+ owners: ['@saas-team'],
45
+ tags: ['billing', 'usage', 'metrics'],
46
+ stability: StabilityEnum.Beta,
47
+ goal: 'Monitor feature usage and limits',
48
+ context: 'Billing section',
49
+ },
50
+ source: {
51
+ type: 'component',
52
+ framework: 'react',
53
+ componentKey: 'UsageDashboardView',
54
+ },
55
+ targets: ['react', 'markdown'],
56
+ policy: {
57
+ flags: ['saas.billing.enabled'],
58
+ },
59
59
  });
@@ -1,133 +1,133 @@
1
1
  import { defineSchemaModel, ScalarTypeEnum } from '@contractspec/lib.schema';
2
2
  import {
3
- SubscriptionStatusSchemaEnum,
4
- FeatureAccessReasonEnum,
3
+ FeatureAccessReasonEnum,
4
+ SubscriptionStatusSchemaEnum,
5
5
  } from './billing.enum';
6
6
 
7
7
  /**
8
8
  * Organization subscription details schema.
9
9
  */
10
10
  export const SubscriptionModel = defineSchemaModel({
11
- name: 'Subscription',
12
- description: 'Organization subscription details',
13
- fields: {
14
- id: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
15
- organizationId: {
16
- type: ScalarTypeEnum.String_unsecure(),
17
- isOptional: false,
18
- },
19
- planId: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
20
- planName: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
21
- status: { type: SubscriptionStatusSchemaEnum, isOptional: false },
22
- currentPeriodStart: { type: ScalarTypeEnum.DateTime(), isOptional: false },
23
- currentPeriodEnd: { type: ScalarTypeEnum.DateTime(), isOptional: false },
24
- trialEndsAt: { type: ScalarTypeEnum.DateTime(), isOptional: true },
25
- cancelAtPeriodEnd: { type: ScalarTypeEnum.Boolean(), isOptional: false },
26
- },
11
+ name: 'Subscription',
12
+ description: 'Organization subscription details',
13
+ fields: {
14
+ id: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
15
+ organizationId: {
16
+ type: ScalarTypeEnum.String_unsecure(),
17
+ isOptional: false,
18
+ },
19
+ planId: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
20
+ planName: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
21
+ status: { type: SubscriptionStatusSchemaEnum, isOptional: false },
22
+ currentPeriodStart: { type: ScalarTypeEnum.DateTime(), isOptional: false },
23
+ currentPeriodEnd: { type: ScalarTypeEnum.DateTime(), isOptional: false },
24
+ trialEndsAt: { type: ScalarTypeEnum.DateTime(), isOptional: true },
25
+ cancelAtPeriodEnd: { type: ScalarTypeEnum.Boolean(), isOptional: false },
26
+ },
27
27
  });
28
28
 
29
29
  /**
30
30
  * Usage summary for a feature schema.
31
31
  */
32
32
  export const UsageSummaryModel = defineSchemaModel({
33
- name: 'UsageSummary',
34
- description: 'Usage summary for a feature',
35
- fields: {
36
- feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
37
- used: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
38
- limit: { type: ScalarTypeEnum.Int_unsecure(), isOptional: true },
39
- unit: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
40
- percentage: { type: ScalarTypeEnum.Float_unsecure(), isOptional: true },
41
- },
33
+ name: 'UsageSummary',
34
+ description: 'Usage summary for a feature',
35
+ fields: {
36
+ feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
37
+ used: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
38
+ limit: { type: ScalarTypeEnum.Int_unsecure(), isOptional: true },
39
+ unit: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
40
+ percentage: { type: ScalarTypeEnum.Float_unsecure(), isOptional: true },
41
+ },
42
42
  });
43
43
 
44
44
  /**
45
45
  * Input for recording feature usage.
46
46
  */
47
47
  export const RecordUsageInputModel = defineSchemaModel({
48
- name: 'RecordUsageInput',
49
- description: 'Input for recording feature usage',
50
- fields: {
51
- feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
52
- quantity: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
53
- sourceId: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
54
- sourceType: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
55
- metadata: { type: ScalarTypeEnum.JSONObject(), isOptional: true },
56
- },
48
+ name: 'RecordUsageInput',
49
+ description: 'Input for recording feature usage',
50
+ fields: {
51
+ feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
52
+ quantity: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
53
+ sourceId: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
54
+ sourceType: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
55
+ metadata: { type: ScalarTypeEnum.JSONObject(), isOptional: true },
56
+ },
57
57
  });
58
58
 
59
59
  /**
60
60
  * Output for recording feature usage.
61
61
  */
62
62
  export const RecordUsageOutputModel = defineSchemaModel({
63
- name: 'RecordUsageOutput',
64
- description: 'Output for recording feature usage',
65
- fields: {
66
- recorded: { type: ScalarTypeEnum.Boolean(), isOptional: false },
67
- currentUsage: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
68
- limit: { type: ScalarTypeEnum.Int_unsecure(), isOptional: true },
69
- limitReached: { type: ScalarTypeEnum.Boolean(), isOptional: false },
70
- },
63
+ name: 'RecordUsageOutput',
64
+ description: 'Output for recording feature usage',
65
+ fields: {
66
+ recorded: { type: ScalarTypeEnum.Boolean(), isOptional: false },
67
+ currentUsage: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
68
+ limit: { type: ScalarTypeEnum.Int_unsecure(), isOptional: true },
69
+ limitReached: { type: ScalarTypeEnum.Boolean(), isOptional: false },
70
+ },
71
71
  });
72
72
 
73
73
  /**
74
74
  * Payload for usage.recorded event.
75
75
  */
76
76
  export const UsageRecordedPayloadModel = defineSchemaModel({
77
- name: 'UsageRecordedPayload',
78
- description: 'Payload for usage.recorded event',
79
- fields: {
80
- feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
81
- quantity: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
82
- },
77
+ name: 'UsageRecordedPayload',
78
+ description: 'Payload for usage.recorded event',
79
+ fields: {
80
+ feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
81
+ quantity: { type: ScalarTypeEnum.Int_unsecure(), isOptional: false },
82
+ },
83
83
  });
84
84
 
85
85
  /**
86
86
  * Input for getting usage summary.
87
87
  */
88
88
  export const GetUsageSummaryInputModel = defineSchemaModel({
89
- name: 'GetUsageSummaryInput',
90
- description: 'Input for getting usage summary',
91
- fields: {
92
- billingPeriod: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
93
- },
89
+ name: 'GetUsageSummaryInput',
90
+ description: 'Input for getting usage summary',
91
+ fields: {
92
+ billingPeriod: { type: ScalarTypeEnum.String_unsecure(), isOptional: true },
93
+ },
94
94
  });
95
95
 
96
96
  /**
97
97
  * Output for usage summary.
98
98
  */
99
99
  export const GetUsageSummaryOutputModel = defineSchemaModel({
100
- name: 'GetUsageSummaryOutput',
101
- description: 'Output for usage summary',
102
- fields: {
103
- billingPeriod: {
104
- type: ScalarTypeEnum.String_unsecure(),
105
- isOptional: false,
106
- },
107
- usage: { type: UsageSummaryModel, isArray: true, isOptional: false },
108
- },
100
+ name: 'GetUsageSummaryOutput',
101
+ description: 'Output for usage summary',
102
+ fields: {
103
+ billingPeriod: {
104
+ type: ScalarTypeEnum.String_unsecure(),
105
+ isOptional: false,
106
+ },
107
+ usage: { type: UsageSummaryModel, isArray: true, isOptional: false },
108
+ },
109
109
  });
110
110
 
111
111
  /**
112
112
  * Input for checking feature access.
113
113
  */
114
114
  export const CheckFeatureAccessInputModel = defineSchemaModel({
115
- name: 'CheckFeatureAccessInput',
116
- description: 'Input for checking feature access',
117
- fields: {
118
- feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
119
- },
115
+ name: 'CheckFeatureAccessInput',
116
+ description: 'Input for checking feature access',
117
+ fields: {
118
+ feature: { type: ScalarTypeEnum.String_unsecure(), isOptional: false },
119
+ },
120
120
  });
121
121
 
122
122
  /**
123
123
  * Output for feature access check.
124
124
  */
125
125
  export const CheckFeatureAccessOutputModel = defineSchemaModel({
126
- name: 'CheckFeatureAccessOutput',
127
- description: 'Output for feature access check',
128
- fields: {
129
- hasAccess: { type: ScalarTypeEnum.Boolean(), isOptional: false },
130
- reason: { type: FeatureAccessReasonEnum, isOptional: true },
131
- upgradeUrl: { type: ScalarTypeEnum.URL(), isOptional: true },
132
- },
126
+ name: 'CheckFeatureAccessOutput',
127
+ description: 'Output for feature access check',
128
+ fields: {
129
+ hasAccess: { type: ScalarTypeEnum.Boolean(), isOptional: false },
130
+ reason: { type: FeatureAccessReasonEnum, isOptional: true },
131
+ upgradeUrl: { type: ScalarTypeEnum.URL(), isOptional: true },
132
+ },
133
133
  });