@stacksjs/defaults 0.70.206 → 0.70.208

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 (408) hide show
  1. package/TODO.md +21 -0
  2. package/ai/AGENTS.md +79 -0
  3. package/ai/README.md +45 -0
  4. package/ai/claude/launch.json +12 -0
  5. package/ai/skills/stacks-actions/SKILL.md +128 -0
  6. package/ai/skills/stacks-ai/SKILL.md +276 -0
  7. package/ai/skills/stacks-alias/SKILL.md +94 -0
  8. package/ai/skills/stacks-analytics/SKILL.md +91 -0
  9. package/ai/skills/stacks-api/SKILL.md +738 -0
  10. package/ai/skills/stacks-arrays/SKILL.md +277 -0
  11. package/ai/skills/stacks-auth/SKILL.md +422 -0
  12. package/ai/skills/stacks-auto-imports/SKILL.md +138 -0
  13. package/ai/skills/stacks-brandkit/SKILL.md +811 -0
  14. package/ai/skills/stacks-browse/SKILL.md +127 -0
  15. package/ai/skills/stacks-browse/scripts/browse.ts +492 -0
  16. package/ai/skills/stacks-browser/SKILL.md +145 -0
  17. package/ai/skills/stacks-buddy/SKILL.md +676 -0
  18. package/ai/skills/stacks-build/SKILL.md +163 -0
  19. package/ai/skills/stacks-cache/SKILL.md +125 -0
  20. package/ai/skills/stacks-calendar/SKILL.md +113 -0
  21. package/ai/skills/stacks-chat/SKILL.md +371 -0
  22. package/ai/skills/stacks-cli/SKILL.md +112 -0
  23. package/ai/skills/stacks-cloud/SKILL.md +192 -0
  24. package/ai/skills/stacks-cms/SKILL.md +217 -0
  25. package/ai/skills/stacks-collections/SKILL.md +82 -0
  26. package/ai/skills/stacks-commerce/SKILL.md +114 -0
  27. package/ai/skills/stacks-composables/SKILL.md +161 -0
  28. package/ai/skills/stacks-config/SKILL.md +144 -0
  29. package/ai/skills/stacks-configuration/SKILL.md +154 -0
  30. package/ai/skills/stacks-cron/SKILL.md +123 -0
  31. package/ai/skills/stacks-crosswind/SKILL.md +190 -0
  32. package/ai/skills/stacks-dashboard/SKILL.md +173 -0
  33. package/ai/skills/stacks-database/SKILL.md +286 -0
  34. package/ai/skills/stacks-datetime/SKILL.md +269 -0
  35. package/ai/skills/stacks-dependencies/SKILL.md +111 -0
  36. package/ai/skills/stacks-deploy/SKILL.md +102 -0
  37. package/ai/skills/stacks-design-brutalist/SKILL.md +110 -0
  38. package/ai/skills/stacks-design-minimalist/SKILL.md +115 -0
  39. package/ai/skills/stacks-design-output/SKILL.md +55 -0
  40. package/ai/skills/stacks-design-soft/SKILL.md +156 -0
  41. package/ai/skills/stacks-design-taste/SKILL.md +1012 -0
  42. package/ai/skills/stacks-design-taste-codex/SKILL.md +294 -0
  43. package/ai/skills/stacks-desktop/SKILL.md +78 -0
  44. package/ai/skills/stacks-development/SKILL.md +298 -0
  45. package/ai/skills/stacks-dns/SKILL.md +149 -0
  46. package/ai/skills/stacks-docs/SKILL.md +109 -0
  47. package/ai/skills/stacks-email/SKILL.md +236 -0
  48. package/ai/skills/stacks-enums/SKILL.md +100 -0
  49. package/ai/skills/stacks-env/SKILL.md +181 -0
  50. package/ai/skills/stacks-error-handling/SKILL.md +137 -0
  51. package/ai/skills/stacks-events/SKILL.md +228 -0
  52. package/ai/skills/stacks-faker/SKILL.md +158 -0
  53. package/ai/skills/stacks-git/SKILL.md +158 -0
  54. package/ai/skills/stacks-guard/SKILL.md +98 -0
  55. package/ai/skills/stacks-health/SKILL.md +75 -0
  56. package/ai/skills/stacks-http/SKILL.md +316 -0
  57. package/ai/skills/stacks-i18n/SKILL.md +198 -0
  58. package/ai/skills/stacks-image-to-code/SKILL.md +629 -0
  59. package/ai/skills/stacks-imagegen-mobile/SKILL.md +1474 -0
  60. package/ai/skills/stacks-imagegen-web/SKILL.md +998 -0
  61. package/ai/skills/stacks-investigate/SKILL.md +119 -0
  62. package/ai/skills/stacks-jobs/SKILL.md +136 -0
  63. package/ai/skills/stacks-lint/SKILL.md +184 -0
  64. package/ai/skills/stacks-listeners/SKILL.md +99 -0
  65. package/ai/skills/stacks-logging/SKILL.md +78 -0
  66. package/ai/skills/stacks-mail/SKILL.md +120 -0
  67. package/ai/skills/stacks-middleware/SKILL.md +249 -0
  68. package/ai/skills/stacks-migrations/SKILL.md +105 -0
  69. package/ai/skills/stacks-models/SKILL.md +267 -0
  70. package/ai/skills/stacks-new-feature/SKILL.md +206 -0
  71. package/ai/skills/stacks-notifications/SKILL.md +210 -0
  72. package/ai/skills/stacks-objects/SKILL.md +205 -0
  73. package/ai/skills/stacks-office-hours/SKILL.md +134 -0
  74. package/ai/skills/stacks-orm/SKILL.md +342 -0
  75. package/ai/skills/stacks-path/SKILL.md +118 -0
  76. package/ai/skills/stacks-payments/SKILL.md +373 -0
  77. package/ai/skills/stacks-plan-review/SKILL.md +152 -0
  78. package/ai/skills/stacks-plugins/SKILL.md +149 -0
  79. package/ai/skills/stacks-push/SKILL.md +376 -0
  80. package/ai/skills/stacks-query-builder/SKILL.md +128 -0
  81. package/ai/skills/stacks-queue/SKILL.md +559 -0
  82. package/ai/skills/stacks-realtime/SKILL.md +442 -0
  83. package/ai/skills/stacks-redesign/SKILL.md +182 -0
  84. package/ai/skills/stacks-registry/SKILL.md +58 -0
  85. package/ai/skills/stacks-repl/SKILL.md +80 -0
  86. package/ai/skills/stacks-retro/SKILL.md +122 -0
  87. package/ai/skills/stacks-review/SKILL.md +135 -0
  88. package/ai/skills/stacks-router/SKILL.md +231 -0
  89. package/ai/skills/stacks-routes/SKILL.md +105 -0
  90. package/ai/skills/stacks-scaffolding/SKILL.md +162 -0
  91. package/ai/skills/stacks-scheduler/SKILL.md +363 -0
  92. package/ai/skills/stacks-search-engine/SKILL.md +112 -0
  93. package/ai/skills/stacks-security/SKILL.md +129 -0
  94. package/ai/skills/stacks-security-audit/SKILL.md +128 -0
  95. package/ai/skills/stacks-server/SKILL.md +458 -0
  96. package/ai/skills/stacks-shell/SKILL.md +62 -0
  97. package/ai/skills/stacks-slug/SKILL.md +87 -0
  98. package/ai/skills/stacks-sms/SKILL.md +385 -0
  99. package/ai/skills/stacks-socials/SKILL.md +303 -0
  100. package/ai/skills/stacks-storage/SKILL.md +576 -0
  101. package/ai/skills/stacks-strings/SKILL.md +416 -0
  102. package/ai/skills/stacks-stx/SKILL.md +176 -0
  103. package/ai/skills/stacks-technical-diagrams/LICENSE +22 -0
  104. package/ai/skills/stacks-technical-diagrams/SKILL.md +290 -0
  105. package/ai/skills/stacks-technical-diagrams/agents/openai.yaml +4 -0
  106. package/ai/skills/stacks-technical-diagrams/assets/template.html +1252 -0
  107. package/ai/skills/stacks-technical-diagrams/bin/technical-diagrams.mjs +289 -0
  108. package/ai/skills/stacks-technical-diagrams/bunfig.toml +1 -0
  109. package/ai/skills/stacks-technical-diagrams/examples/agent-run.lifecycle.json +64 -0
  110. package/ai/skills/stacks-technical-diagrams/examples/agent-tool-call.workflow.json +88 -0
  111. package/ai/skills/stacks-technical-diagrams/examples/cache-miss-request.sequence.json +75 -0
  112. package/ai/skills/stacks-technical-diagrams/examples/product-analytics.dataflow.json +70 -0
  113. package/ai/skills/stacks-technical-diagrams/examples/web-app.architecture.json +41 -0
  114. package/ai/skills/stacks-technical-diagrams/renderers/architecture/grid.mjs +62 -0
  115. package/ai/skills/stacks-technical-diagrams/renderers/architecture/render-architecture.mjs +371 -0
  116. package/ai/skills/stacks-technical-diagrams/renderers/dataflow/README.md +82 -0
  117. package/ai/skills/stacks-technical-diagrams/renderers/dataflow/render-dataflow.mjs +295 -0
  118. package/ai/skills/stacks-technical-diagrams/renderers/lifecycle/README.md +91 -0
  119. package/ai/skills/stacks-technical-diagrams/renderers/lifecycle/render-lifecycle.mjs +384 -0
  120. package/ai/skills/stacks-technical-diagrams/renderers/sequence/README.md +84 -0
  121. package/ai/skills/stacks-technical-diagrams/renderers/sequence/render-sequence.mjs +257 -0
  122. package/ai/skills/stacks-technical-diagrams/renderers/shared/cli.mjs +42 -0
  123. package/ai/skills/stacks-technical-diagrams/renderers/shared/generated-validators.mjs +13 -0
  124. package/ai/skills/stacks-technical-diagrams/renderers/shared/geometry.mjs +230 -0
  125. package/ai/skills/stacks-technical-diagrams/renderers/shared/layout-report.mjs +40 -0
  126. package/ai/skills/stacks-technical-diagrams/renderers/shared/utils.mjs +88 -0
  127. package/ai/skills/stacks-technical-diagrams/renderers/shared/validator.mjs +40 -0
  128. package/ai/skills/stacks-technical-diagrams/renderers/workflow/README.md +103 -0
  129. package/ai/skills/stacks-technical-diagrams/renderers/workflow/render-workflow.mjs +481 -0
  130. package/ai/skills/stacks-technical-diagrams/schemas/README.md +68 -0
  131. package/ai/skills/stacks-technical-diagrams/schemas/architecture.schema.json +121 -0
  132. package/ai/skills/stacks-technical-diagrams/schemas/common.schema.json +43 -0
  133. package/ai/skills/stacks-technical-diagrams/schemas/dataflow.schema.json +221 -0
  134. package/ai/skills/stacks-technical-diagrams/schemas/lifecycle.schema.json +241 -0
  135. package/ai/skills/stacks-technical-diagrams/schemas/sequence.schema.json +186 -0
  136. package/ai/skills/stacks-technical-diagrams/schemas/workflow.schema.json +332 -0
  137. package/ai/skills/stacks-technical-diagrams/scripts/check-render-output.mjs +297 -0
  138. package/ai/skills/stacks-technical-diagrams/scripts/render-examples.mjs +28 -0
  139. package/ai/skills/stacks-testing/SKILL.md +129 -0
  140. package/ai/skills/stacks-tunnel/SKILL.md +125 -0
  141. package/ai/skills/stacks-types/SKILL.md +178 -0
  142. package/ai/skills/stacks-ui/SKILL.md +246 -0
  143. package/ai/skills/stacks-utils/SKILL.md +444 -0
  144. package/ai/skills/stacks-validation/SKILL.md +371 -0
  145. package/ai/skills/stacks-whois/SKILL.md +315 -0
  146. package/assets/world-map-data.ts +121 -0
  147. package/bootstrap.ts +114 -0
  148. package/docs/api-examples.md +46 -0
  149. package/docs/index.md +24 -0
  150. package/docs/markdown-examples.md +87 -0
  151. package/functions/analytics.ts +97 -0
  152. package/functions/api.ts +143 -0
  153. package/functions/auth.ts +208 -0
  154. package/functions/billing/payments.ts +149 -0
  155. package/functions/blog.ts +120 -0
  156. package/functions/cms/categorizables.ts +107 -0
  157. package/functions/cms/pages.ts +108 -0
  158. package/functions/cms/posts.ts +100 -0
  159. package/functions/cms/taggables.ts +102 -0
  160. package/functions/commerce/coupons.ts +128 -0
  161. package/functions/commerce/customers.ts +128 -0
  162. package/functions/commerce/gift-cards.ts +119 -0
  163. package/functions/commerce/orders.ts +112 -0
  164. package/functions/commerce/payments.ts +119 -0
  165. package/functions/commerce/products/categories.ts +123 -0
  166. package/functions/commerce/products/manufacturers.ts +123 -0
  167. package/functions/commerce/products/products.ts +123 -0
  168. package/functions/commerce/products/reviews.ts +123 -0
  169. package/functions/commerce/products/units.ts +123 -0
  170. package/functions/commerce/products/variants.ts +123 -0
  171. package/functions/commerce/shippings/delivery-routes.ts +123 -0
  172. package/functions/commerce/shippings/digital-deliveries.ts +119 -0
  173. package/functions/commerce/shippings/drivers.ts +123 -0
  174. package/functions/commerce/shippings/license-keys.ts +123 -0
  175. package/functions/commerce/shippings/shipping-methods.ts +123 -0
  176. package/functions/commerce/shippings/shipping-rates.ts +119 -0
  177. package/functions/commerce/shippings/shipping-zones.ts +119 -0
  178. package/functions/commerce/taxes.ts +119 -0
  179. package/functions/commerce/waitlist/products.ts +123 -0
  180. package/functions/commerce/waitlist/restaurants.ts +123 -0
  181. package/functions/craft.ts +107 -0
  182. package/functions/dashboard.ts +153 -0
  183. package/functions/inbox.ts +95 -0
  184. package/functions/jobs.ts +86 -0
  185. package/functions/monitoring/errors.ts +295 -0
  186. package/functions/queue.ts +111 -0
  187. package/functions/realtime/websockets.ts +96 -0
  188. package/functions/realtime.ts +52 -0
  189. package/functions/releases.ts +49 -0
  190. package/functions/search.ts +126 -0
  191. package/functions/toasts.ts +95 -0
  192. package/functions/uploads.ts +216 -0
  193. package/ide/.gitignore +4 -0
  194. package/ide/cursor/rules/auto-imports.mdc +574 -0
  195. package/ide/cursor/rules/code-style.mdc +12 -0
  196. package/ide/cursor/rules/documentation.mdc +9 -0
  197. package/ide/cursor/rules/error-handling-validation.mdc +11 -0
  198. package/ide/cursor/rules/key-conventions.mdc +11 -0
  199. package/ide/cursor/rules/project-structure.mdc +169 -0
  200. package/ide/cursor/rules/readme.mdc +318 -0
  201. package/ide/cursor/rules/syntax-formatting.mdc +9 -0
  202. package/ide/cursor/rules/testing.mdc +10 -0
  203. package/ide/cursor/rules/typescript.mdc +9 -0
  204. package/ide/cursor/rules/ui-styling.mdc +0 -0
  205. package/ide/dictionary.txt +397 -0
  206. package/ide/jetbrains/.fleet/settings.json +4 -0
  207. package/ide/jetbrains/.idea/.gitignore +5 -0
  208. package/ide/jetbrains/.idea/.name +1 -0
  209. package/ide/jetbrains/.idea/inspectionProfiles/Project_Default.xml +6 -0
  210. package/ide/jetbrains/.idea/jsLinters/eslint.xml +7 -0
  211. package/ide/jetbrains/.idea/modules.xml +8 -0
  212. package/ide/jetbrains/.idea/stacks.iml +22 -0
  213. package/ide/jetbrains/.idea/vcs.xml +6 -0
  214. package/ide/jetbrains/.idea/webResources.xml +14 -0
  215. package/ide/jetbrains/IntelliJ IDEA Global Settings +0 -0
  216. package/ide/jetbrains/installed.txt +4 -0
  217. package/ide/jetbrains/options/github-copilot.xml +5 -0
  218. package/ide/jetbrains/options/nodejs.xml +7 -0
  219. package/ide/jetbrains/options/templates.xml +124 -0
  220. package/ide/jetbrains/templates/JavaScript.xml +6 -0
  221. package/ide/jetbrains/templates/Stacks.xml +8 -0
  222. package/ide/vscode/.vscode/README.md +23 -0
  223. package/ide/vscode/.vscode/extensions.json +5 -0
  224. package/ide/vscode/.vscode/settings.json +176 -0
  225. package/ide/vscode/.vscode/stacks.code-snippets +181 -0
  226. package/ide/vscode/LICENSE.md +21 -0
  227. package/ide/vscode/README.md +36 -0
  228. package/ide/vscode/logo.png +0 -0
  229. package/ide/vscode/package.json +79 -0
  230. package/ide/zed/.zed/settings.json +139 -0
  231. package/lang/README.md +28 -0
  232. package/lang/de.yml +14 -0
  233. package/lang/en.yml +15 -0
  234. package/package.json +19 -3
  235. package/project/bootstrap +161 -0
  236. package/project/buddy +175 -0
  237. package/project/storage/framework/tsconfig.app.json +50 -0
  238. package/project/storage/framework/tsconfig.base.json +58 -0
  239. package/routes/core.ts +78 -0
  240. package/routes/dashboard-api.ts +233 -0
  241. package/routes/dashboard.ts +739 -0
  242. package/routes/email.ts +129 -0
  243. package/stores/[name].stx +16 -0
  244. package/stores/git.ts +71 -0
  245. package/stores/payment.ts +474 -0
  246. package/stores/queue.ts +43 -0
  247. package/stores/user.ts +29 -0
  248. package/stx-components-plugin.ts +25 -0
  249. package/styles/design-tokens.css +597 -0
  250. package/types/dashboard.ts +70 -0
  251. package/types/defaults.ts +438 -0
  252. package/vcs/github/CODE_OF_CONDUCT.md +83 -0
  253. package/vcs/github/CONTRIBUTING.md +187 -0
  254. package/vcs/github/EXPLANATIONS.md +41 -0
  255. package/vcs/github/FUNDING.yml +1 -0
  256. package/vcs/github/ISSUE_TEMPLATE/bug_report.yml +49 -0
  257. package/vcs/github/ISSUE_TEMPLATE/config.yml +10 -0
  258. package/vcs/github/ISSUE_TEMPLATE/feature_request.yml +44 -0
  259. package/vcs/github/SECURITY.md +70 -0
  260. package/vcs/github/renovate.json +5 -0
  261. package/vcs/github/stale.yml +14 -0
  262. package/vcs/github/workflows/README.md +16 -0
  263. package/vcs/github/workflows/ci.yml +114 -0
  264. package/vcs/github/workflows/export-size.yml +25 -0
  265. package/vcs/github/workflows/labeler.yml +13 -0
  266. package/vcs/github/workflows/release.yml +219 -0
  267. package/views/[...all].stx +8 -0
  268. package/views/about.md +3 -0
  269. package/views/auth/login.stx +1 -0
  270. package/views/auth/signup.stx +85 -0
  271. package/views/dashboard/.discovered-models.json +542 -0
  272. package/views/dashboard/AUDIT.md +904 -0
  273. package/views/dashboard/[...all].stx +89 -0
  274. package/views/dashboard/access-tokens/index.stx +177 -0
  275. package/views/dashboard/actions/index.stx +129 -0
  276. package/views/dashboard/analytics/blog/index.stx +356 -0
  277. package/views/dashboard/analytics/browsers/index.stx +263 -0
  278. package/views/dashboard/analytics/commerce/sales/index.stx +329 -0
  279. package/views/dashboard/analytics/commerce/web/index.stx +379 -0
  280. package/views/dashboard/analytics/countries/index.stx +289 -0
  281. package/views/dashboard/analytics/devices/index.stx +305 -0
  282. package/views/dashboard/analytics/events/index.stx +536 -0
  283. package/views/dashboard/analytics/index.stx +88 -0
  284. package/views/dashboard/analytics/marketing/index.stx +315 -0
  285. package/views/dashboard/analytics/pages/index.stx +271 -0
  286. package/views/dashboard/analytics/referrers/index.stx +319 -0
  287. package/views/dashboard/analytics/web/index.stx +356 -0
  288. package/views/dashboard/buddy/index.stx +198 -0
  289. package/views/dashboard/ci/index.stx +462 -0
  290. package/views/dashboard/cloud/index.stx +452 -0
  291. package/views/dashboard/commands/index.stx +295 -0
  292. package/views/dashboard/commerce/categories/index.stx +406 -0
  293. package/views/dashboard/commerce/coupons/index.stx +485 -0
  294. package/views/dashboard/commerce/customers/index.stx +410 -0
  295. package/views/dashboard/commerce/dashboard/index.stx +287 -0
  296. package/views/dashboard/commerce/delivery/delivery-routes.stx +305 -0
  297. package/views/dashboard/commerce/delivery/digital-delivery.stx +332 -0
  298. package/views/dashboard/commerce/delivery/drivers.stx +397 -0
  299. package/views/dashboard/commerce/delivery/index.stx +18 -0
  300. package/views/dashboard/commerce/delivery/license-keys.stx +380 -0
  301. package/views/dashboard/commerce/delivery/shipping-methods.stx +346 -0
  302. package/views/dashboard/commerce/delivery/shipping-rates.stx +338 -0
  303. package/views/dashboard/commerce/delivery/shipping-zones.stx +302 -0
  304. package/views/dashboard/commerce/delivery/tabs.ts +25 -0
  305. package/views/dashboard/commerce/gift-cards/index.stx +561 -0
  306. package/views/dashboard/commerce/manufacturers/index.stx +308 -0
  307. package/views/dashboard/commerce/orders/index.stx +247 -0
  308. package/views/dashboard/commerce/payments/index.stx +535 -0
  309. package/views/dashboard/commerce/pos/index.stx +653 -0
  310. package/views/dashboard/commerce/printers/devices/index.stx +273 -0
  311. package/views/dashboard/commerce/printers/receipts/index.stx +308 -0
  312. package/views/dashboard/commerce/products/detail.stx +563 -0
  313. package/views/dashboard/commerce/products/index.stx +370 -0
  314. package/views/dashboard/commerce/reviews/index.stx +656 -0
  315. package/views/dashboard/commerce/reviews/index.ts +0 -0
  316. package/views/dashboard/commerce/taxes/index.stx +377 -0
  317. package/views/dashboard/commerce/units/index.stx +317 -0
  318. package/views/dashboard/commerce/variants/index.stx +319 -0
  319. package/views/dashboard/commerce/waitlist/products.stx +942 -0
  320. package/views/dashboard/commerce/waitlist/restaurant.stx +1024 -0
  321. package/views/dashboard/components/index.stx +330 -0
  322. package/views/dashboard/composables/index.ts +19 -0
  323. package/views/dashboard/composables/useChart.ts +77 -0
  324. package/views/dashboard/composables/useNavigation.ts +99 -0
  325. package/views/dashboard/composables/useRole.ts +58 -0
  326. package/views/dashboard/composables/useTheme.ts +74 -0
  327. package/views/dashboard/content/authors/index.stx +171 -0
  328. package/views/dashboard/content/blog/index.stx +493 -0
  329. package/views/dashboard/content/categories/index.stx +169 -0
  330. package/views/dashboard/content/comments/index.stx +189 -0
  331. package/views/dashboard/content/dashboard.stx +383 -0
  332. package/views/dashboard/content/files/index.stx +706 -0
  333. package/views/dashboard/content/pages/index.stx +174 -0
  334. package/views/dashboard/content/posts/index.stx +269 -0
  335. package/views/dashboard/content/seo/index.stx +240 -0
  336. package/views/dashboard/content/tags/index.stx +167 -0
  337. package/views/dashboard/data/activity/index.stx +261 -0
  338. package/views/dashboard/data/dashboard/index.stx +116 -0
  339. package/views/dashboard/data/subscribers.stx +270 -0
  340. package/views/dashboard/data/teams.stx +275 -0
  341. package/views/dashboard/data/users.stx +279 -0
  342. package/views/dashboard/dependencies/index.stx +178 -0
  343. package/views/dashboard/deployments/[id].stx +234 -0
  344. package/views/dashboard/deployments/index.stx +9 -0
  345. package/views/dashboard/dns/index.stx +163 -0
  346. package/views/dashboard/environment/index.stx +283 -0
  347. package/views/dashboard/errors/index.stx +274 -0
  348. package/views/dashboard/forgot-password.stx +57 -0
  349. package/views/dashboard/functions/index.stx +159 -0
  350. package/views/dashboard/health/index.stx +248 -0
  351. package/views/dashboard/inbox/activity.stx +350 -0
  352. package/views/dashboard/inbox/index.stx +452 -0
  353. package/views/dashboard/inbox/settings.stx +290 -0
  354. package/views/dashboard/index.stx +252 -0
  355. package/views/dashboard/insights/index.stx +529 -0
  356. package/views/dashboard/jobs/[id].stx +430 -0
  357. package/views/dashboard/jobs/history.stx +222 -0
  358. package/views/dashboard/jobs/index.stx +214 -0
  359. package/views/dashboard/kanban/[id].stx +899 -0
  360. package/views/dashboard/kanban/index.stx +260 -0
  361. package/views/dashboard/layouts/default.stx +565 -0
  362. package/views/dashboard/layouts/guest.stx +10 -0
  363. package/views/dashboard/login.stx +48 -0
  364. package/views/dashboard/logs/index.stx +540 -0
  365. package/views/dashboard/mailboxes/index.stx +149 -0
  366. package/views/dashboard/management/permissions/index.stx +490 -0
  367. package/views/dashboard/marketing/campaigns/index.stx +604 -0
  368. package/views/dashboard/marketing/lists/index.stx +514 -0
  369. package/views/dashboard/marketing/reviews/index.stx +475 -0
  370. package/views/dashboard/marketing/social-posts/index.stx +560 -0
  371. package/views/dashboard/models/[model].stx +195 -0
  372. package/views/dashboard/models/index.stx +159 -0
  373. package/views/dashboard/monitoring/errors/index.stx +415 -0
  374. package/views/dashboard/notifications/dashboard.stx +383 -0
  375. package/views/dashboard/notifications/email.stx +336 -0
  376. package/views/dashboard/notifications/history.stx +373 -0
  377. package/views/dashboard/notifications/sms.stx +332 -0
  378. package/views/dashboard/packages/index.stx +195 -0
  379. package/views/dashboard/queries/[id].stx +381 -0
  380. package/views/dashboard/queries/history.stx +227 -0
  381. package/views/dashboard/queries/index.stx +335 -0
  382. package/views/dashboard/queries/slow.stx +318 -0
  383. package/views/dashboard/queue/index.stx +427 -0
  384. package/views/dashboard/realtime/index.stx +429 -0
  385. package/views/dashboard/register.stx +46 -0
  386. package/views/dashboard/releases/index.stx +389 -0
  387. package/views/dashboard/requests/index.stx +462 -0
  388. package/views/dashboard/serverless/index.stx +475 -0
  389. package/views/dashboard/servers/[id].stx +299 -0
  390. package/views/dashboard/servers/index.stx +483 -0
  391. package/views/dashboard/settings/billing.stx +50 -0
  392. package/views/dashboard/settings/index.stx +256 -0
  393. package/views/dashboard/settings/mail.stx +252 -0
  394. package/views/dashboard/stores/auth.ts +123 -0
  395. package/views/dashboard/stores/ci.ts +342 -0
  396. package/views/dashboard/stores/index.ts +129 -0
  397. package/views/dashboard/stores/kanban.ts +723 -0
  398. package/views/dashboard/stores/rbac.ts +350 -0
  399. package/views/dashboard/stx.config.ts +34 -0
  400. package/views/dashboard/teams/[id].stx +170 -0
  401. package/views/forum/category.stx +92 -0
  402. package/views/forum/index.stx +209 -0
  403. package/views/forum/new-topic.stx +113 -0
  404. package/views/forum/profile.stx +1 -0
  405. package/views/forum/topic.stx +143 -0
  406. package/views/hello-world/[name].stx +47 -0
  407. package/views/index.stx +21 -0
  408. package/views/system-tray/index.stx +147 -0
@@ -0,0 +1,129 @@
1
+ /**
2
+ * Default framework email routes (stacksjs/stacks#1880, #1881).
3
+ *
4
+ * Mounts:
5
+ * - GET /_stacks/email/unsubscribe/:token — opt-out via signed link
6
+ * - POST /webhooks/email/mailgun — bounce/complaint events
7
+ * - POST /webhooks/email/postmark — bounce/complaint events
8
+ * - POST /webhooks/email/ses — SES via SNS
9
+ * - POST /webhooks/email/sendgrid — event webhook
10
+ *
11
+ * All routes are CSRF-exempt (they're called by external providers
12
+ * or anonymous users clicking unsubscribe links). User routes
13
+ * registered first win, so apps that need to mount their own
14
+ * handlers at the same path can override.
15
+ *
16
+ * Each webhook handler self-disables if its provider credentials
17
+ * aren't configured — returns 401 with `missing-config` rather
18
+ * than processing unauthenticated requests.
19
+ */
20
+
21
+ import { route } from '@stacksjs/router'
22
+ import {
23
+ buildUnsubscribeUrl as _ignored, // import-side dep to ensure tree-shake doesn't drop the module
24
+ handleMailgunWebhook,
25
+ handlePostmarkWebhook,
26
+ handleSendgridWebhook,
27
+ handleSesWebhook,
28
+ suppress,
29
+ verifyUnsubscribeToken,
30
+ } from '@stacksjs/email'
31
+ import { config } from '@stacksjs/config'
32
+ import process from 'node:process'
33
+
34
+ // Touch the import so the bundler keeps it referenced (the helper
35
+ // is used by app code; this file ensures the module loads when
36
+ // the framework routes register).
37
+ void _ignored
38
+
39
+ interface EmailConfigShape {
40
+ webhooks?: {
41
+ mailgun?: { signingKey?: string }
42
+ postmark?: { username?: string, password?: string, ipAllowlist?: ReadonlyArray<string> }
43
+ ses?: { autoConfirmSubscriptions?: boolean }
44
+ sendgrid?: { publicKeyPem?: string }
45
+ }
46
+ }
47
+
48
+ function emailConfig(): EmailConfigShape {
49
+ return ((config as { email?: EmailConfigShape } | undefined)?.email ?? {}) as EmailConfigShape
50
+ }
51
+
52
+ // ============================================================================
53
+ // Unsubscribe — signed-link opt-out (stacksjs/stacks#1880)
54
+ // ============================================================================
55
+
56
+ route.get('/_stacks/email/unsubscribe/{token}', async (req) => {
57
+ const params = (req as unknown as { params?: { token?: string } }).params
58
+ const token = params?.token ?? ''
59
+ const result = verifyUnsubscribeToken(token)
60
+ if (!result.valid || !result.email) {
61
+ return new Response(
62
+ `Unsubscribe link invalid or expired (${result.reason ?? 'unknown'}).`,
63
+ { status: 410, headers: { 'Content-Type': 'text/plain; charset=utf-8' } },
64
+ )
65
+ }
66
+ await suppress(result.email, 'unsubscribe', 'user-initiated via signed URL')
67
+ return new Response(
68
+ `You've been unsubscribed. We won't email ${result.email} again.`,
69
+ { status: 200, headers: { 'Content-Type': 'text/plain; charset=utf-8' } },
70
+ )
71
+ }).skipCsrf()
72
+
73
+ // ============================================================================
74
+ // Provider webhooks (stacksjs/stacks#1881)
75
+ // ============================================================================
76
+
77
+ route.post('/webhooks/email/mailgun', async (req) => {
78
+ const cfg = emailConfig().webhooks?.mailgun
79
+ const signingKey = cfg?.signingKey ?? process.env.MAILGUN_WEBHOOK_SIGNING_KEY ?? ''
80
+ if (!signingKey) {
81
+ return Response.json({ ok: false, reason: 'missing-config' }, { status: 401 })
82
+ }
83
+ const rawBody = await req.text()
84
+ const result = await handleMailgunWebhook(rawBody, { signingKey })
85
+ return Response.json(result.body, { status: result.status })
86
+ }).skipCsrf()
87
+
88
+ route.post('/webhooks/email/postmark', async (req) => {
89
+ const cfg = emailConfig().webhooks?.postmark
90
+ const username = cfg?.username ?? process.env.POSTMARK_WEBHOOK_USERNAME ?? ''
91
+ const password = cfg?.password ?? process.env.POSTMARK_WEBHOOK_PASSWORD ?? ''
92
+ if (!username || !password) {
93
+ return Response.json({ ok: false, reason: 'missing-config' }, { status: 401 })
94
+ }
95
+ const rawBody = await req.text()
96
+ const auth = req.headers.get('authorization')
97
+ // Bun's Request exposes the client IP via the server's `requestIP` API,
98
+ // not directly on the request. The framework's enhanced-request layer
99
+ // surfaces it via _clientIp when available; fall back gracefully.
100
+ const sourceIp = (req as unknown as { _clientIp?: string })._clientIp
101
+ const result = await handlePostmarkWebhook(rawBody, auth, sourceIp, {
102
+ username,
103
+ password,
104
+ ipAllowlist: cfg?.ipAllowlist,
105
+ })
106
+ return Response.json(result.body, { status: result.status })
107
+ }).skipCsrf()
108
+
109
+ route.post('/webhooks/email/ses', async (req) => {
110
+ const cfg = emailConfig().webhooks?.ses ?? {}
111
+ const rawBody = await req.text()
112
+ const result = await handleSesWebhook(rawBody, {
113
+ autoConfirmSubscriptions: cfg.autoConfirmSubscriptions,
114
+ })
115
+ return Response.json(result.body, { status: result.status })
116
+ }).skipCsrf()
117
+
118
+ route.post('/webhooks/email/sendgrid', async (req) => {
119
+ const cfg = emailConfig().webhooks?.sendgrid
120
+ const publicKeyPem = cfg?.publicKeyPem ?? process.env.SENDGRID_WEBHOOK_PUBLIC_KEY ?? ''
121
+ if (!publicKeyPem) {
122
+ return Response.json({ ok: false, reason: 'missing-config' }, { status: 401 })
123
+ }
124
+ const rawBody = await req.text()
125
+ const sig = req.headers.get('x-twilio-email-event-webhook-signature')
126
+ const ts = req.headers.get('x-twilio-email-event-webhook-timestamp')
127
+ const result = await handleSendgridWebhook(rawBody, sig, ts, { publicKeyPem })
128
+ return Response.json(result.body, { status: result.status })
129
+ }).skipCsrf()
@@ -0,0 +1,16 @@
1
+ <script>
2
+ const route = useRoute()
3
+ function name() { return String(route.params.name || '') }
4
+
5
+ // set the title of the page
6
+ </script>
7
+
8
+ <main>
9
+ <div class="flex gap-x-4">
10
+ <SettingsSidebar />
11
+
12
+ <div class="container mx-auto p-4 sm:p-6 lg:p-8">
13
+ <SettingsFormManager :name="name()" />
14
+ </div>
15
+ </div>
16
+ </main>
package/stores/git.ts ADDED
@@ -0,0 +1,71 @@
1
+ const owner = 'stacksjs'
2
+ const repo = 'stacks'
3
+ const numberOfCommits = 10
4
+
5
+ // Assuming you are using a library like Axios for HTTP requests
6
+ const apiUrl = `https://api.github.com/repos/${owner}/${repo}`
7
+
8
+ const token = ''
9
+
10
+ declare const defineStore: any
11
+ declare const useHttpFetch: any
12
+
13
+ export const useGitStore = defineStore('git', {
14
+ state: (): any => {
15
+ return {
16
+ commitLists: [] as any[],
17
+ workflowRuns: [] as any[],
18
+ workflowRun: {} as any,
19
+ }
20
+ },
21
+
22
+ actions: {
23
+ async fetchCommits(this: any): Promise<void> {
24
+ const fetch = await useHttpFetch(apiUrl)
25
+
26
+ fetch.setToken(token)
27
+
28
+ const response = await fetch.get(`/commits?per_page=${numberOfCommits}`)
29
+
30
+ this.commitLists = response
31
+ },
32
+
33
+ async fetchWorkflowActions(this: any): Promise<void> {
34
+ const fetch = await useHttpFetch(apiUrl)
35
+
36
+ fetch.setToken(token)
37
+
38
+ const response = await fetch.get(`/actions/runs?per_page=${numberOfCommits}`)
39
+
40
+ this.workflowRuns = response.workflow_runs
41
+ },
42
+
43
+ async fetchWorkflowAction(this: any, id: number): Promise<void> {
44
+ const fetch = await useHttpFetch(apiUrl)
45
+
46
+ fetch.setToken(token)
47
+
48
+ const response = await fetch.get(`/actions/runs/${id}`)
49
+
50
+ this.workflowRun = response
51
+ },
52
+ },
53
+
54
+ getters: {
55
+ getCommits(state: any): any[] {
56
+ return state.commitLists
57
+ },
58
+
59
+ hasCommits(state: any) {
60
+ return state.commitLists.length
61
+ },
62
+
63
+ hasWorkflowRuns(state: any) {
64
+ return state.workflowRuns.length
65
+ },
66
+
67
+ getWorkflowRuns(state: any): any[] {
68
+ return state.workflowRuns
69
+ },
70
+ },
71
+ })
@@ -0,0 +1,474 @@
1
+ type PaymentMethod = any
2
+ type Product = any
3
+ type Subscription = any
4
+ type TransactionHistory = any
5
+
6
+ const apiUrl = `http://localhost:3008`
7
+
8
+ export const usePaymentStore = defineStore('payment', () => {
9
+ // TODO: update the any types
10
+ const loadingStates = ref<Record<string, boolean>>({})
11
+ const paymentMethods = ref<PaymentMethod[]>([])
12
+ const transactionHistory = ref<TransactionHistory[]>([])
13
+ const defaultPaymentMethod = ref<PaymentMethod>({} as PaymentMethod)
14
+ const product = ref<Product>({} as Product)
15
+ const activeSubscription = ref<Subscription>({} as Subscription)
16
+ const subscriptions = ref<Subscription[]>([])
17
+ const stripeCustomer = ref<any>({} as any)
18
+ const planState = ref<boolean>(false)
19
+
20
+ const getPaymentMethods = computed(() => paymentMethods.value)
21
+ const getProduct = computed(() => product.value)
22
+ const getCurrentPlan = computed(() => activeSubscription.value)
23
+ const getTransactionHistory = computed(() => transactionHistory.value)
24
+
25
+ const isLoading = computed(() => loadingStates.value.size)
26
+
27
+ const hasPaymentMethods = computed(() =>
28
+ paymentMethods.value.length > 0
29
+ || !(defaultPaymentMethod.value == null
30
+ || (typeof defaultPaymentMethod.value === 'object' && Object.keys(defaultPaymentMethod.value).length === 0)),
31
+ )
32
+
33
+ const getDefaultPaymentMethod = computed(() => defaultPaymentMethod.value)
34
+ const getStripeCustomer = computed(() => stripeCustomer.value)
35
+ const getPlanState = computed(() => planState.value)
36
+
37
+ async function fetchSetupIntent(id: number): Promise<string> {
38
+ const url = `http://localhost:3008/payments/create-setup-intent/${id}`
39
+
40
+ const response = await fetch(url, {
41
+ method: 'GET',
42
+ headers: {
43
+ 'Content-Type': 'application/json',
44
+ 'Accept': 'application/json',
45
+ },
46
+ })
47
+
48
+ if (!response.ok) {
49
+ throw new Error(`Failed to fetch setup intent: ${response.status}`)
50
+ }
51
+
52
+ const client: any = await response.json()
53
+ const clientSecret = client.client_secret
54
+
55
+ return clientSecret
56
+ }
57
+
58
+ async function fetchPaymentIntent(id: number, productId: number): Promise<string> {
59
+ const body = { productId }
60
+
61
+ const url = `http://localhost:3008/payments/create-payment-intent/${id}`
62
+
63
+ const response = await fetch(url, {
64
+ method: 'POST',
65
+ headers: {
66
+ 'Content-Type': 'application/json',
67
+ 'Accept': 'application/json',
68
+ },
69
+ body: JSON.stringify(body),
70
+ })
71
+
72
+ if (!response.ok) {
73
+ throw new Error(`Failed to create payment intent: ${response.status}`)
74
+ }
75
+
76
+ const client: any = await response.json()
77
+ const clientSecret = client.client_secret
78
+
79
+ return clientSecret
80
+ }
81
+
82
+ async function storeTransaction(id: number, productId: number): Promise<string> {
83
+ const body = { productId }
84
+
85
+ const url = `http://localhost:3008/payments/store-transaction/${id}`
86
+
87
+ const response = await fetch(url, {
88
+ method: 'POST',
89
+ headers: {
90
+ 'Content-Type': 'application/json',
91
+ 'Accept': 'application/json',
92
+ },
93
+ body: JSON.stringify(body),
94
+ })
95
+
96
+ if (!response.ok) {
97
+ throw new Error(`Failed to store transaction: ${response.status}`)
98
+ }
99
+
100
+ const client: any = await response.json()
101
+ const clientSecret = client.client_secret
102
+
103
+ return clientSecret
104
+ }
105
+
106
+ async function subscribeToPlan(body: { type: string, plan: string, description: string }): Promise<string> {
107
+ const url = 'http://localhost:3008/payments/create-subscription'
108
+
109
+ const response = await fetch(url, {
110
+ method: 'POST',
111
+ headers: {
112
+ 'Content-Type': 'application/json',
113
+ 'Accept': 'application/json',
114
+ },
115
+ body: JSON.stringify(body),
116
+ })
117
+
118
+ const client: any = await response.json()
119
+
120
+ ;(globalThis as any).dispatch('subscription:created')
121
+
122
+ return client
123
+ }
124
+
125
+ async function updatePlan(body: { type: string, plan: string, description: string }): Promise<string> {
126
+ const url = 'http://localhost:3008/payments/update-subscription'
127
+
128
+ const response = await fetch(url, {
129
+ method: 'POST',
130
+ headers: {
131
+ 'Content-Type': 'application/json',
132
+ 'Accept': 'application/json',
133
+ },
134
+ body: JSON.stringify(body),
135
+ })
136
+
137
+ const client: any = await response.json()
138
+
139
+ return client
140
+ }
141
+
142
+ async function setDefaultPaymentMethod(paymentId: string): Promise<string> {
143
+ const url = 'http://localhost:3008/payments/set-default-payment-method/1'
144
+
145
+ const body = { paymentId }
146
+
147
+ const response = await fetch(url, {
148
+ method: 'POST',
149
+ headers: {
150
+ 'Content-Type': 'application/json',
151
+ 'Accept': 'application/json',
152
+ },
153
+ body: JSON.stringify(body),
154
+ })
155
+
156
+ const res: any = await response.json()
157
+
158
+ return res
159
+ }
160
+
161
+ async function setUserDefaultPaymentMethod(setupIntent: string): Promise<string> {
162
+ const url = 'http://localhost:3008/payments/user-default-payment-method/1'
163
+
164
+ const body = { setupIntent }
165
+
166
+ const response = await fetch(url, {
167
+ method: 'POST',
168
+ headers: {
169
+ 'Content-Type': 'application/json',
170
+ 'Accept': 'application/json',
171
+ },
172
+ body: JSON.stringify(body),
173
+ })
174
+
175
+ const res: any = await response.json()
176
+
177
+ return res
178
+ }
179
+
180
+ async function storePaymentMethod(setupIntent: string): Promise<string> {
181
+ const url = 'http://localhost:3008/payments/payment-method/1'
182
+
183
+ const body = { setupIntent }
184
+
185
+ const response = await fetch(url, {
186
+ method: 'POST',
187
+ headers: {
188
+ 'Content-Type': 'application/json',
189
+ 'Accept': 'application/json',
190
+ },
191
+ body: JSON.stringify(body),
192
+ })
193
+
194
+ const res: any = await response.json()
195
+
196
+ return res
197
+ }
198
+
199
+ function openPlans() {
200
+ planState.value = true
201
+ }
202
+
203
+ function closePlans() {
204
+ planState.value = false
205
+ }
206
+
207
+ async function fetchSubscriptions(): Promise<void> {
208
+ setLoadingState('fetchSubscriptions')
209
+
210
+ const url = 'http://localhost:3008/payments/fetch-user-subscriptions'
211
+
212
+ const response = await fetch(url, {
213
+ method: 'GET',
214
+ headers: {
215
+ 'Content-Type': 'application/json',
216
+ 'Accept': 'application/json',
217
+ },
218
+ })
219
+
220
+ if (response.status !== 204) {
221
+ const res = await response.json() as any[]
222
+
223
+ subscriptions.value = res
224
+ }
225
+ await response.json()
226
+
227
+ removeLoadingState('fetchSubscriptions')
228
+ }
229
+
230
+ async function cancelPlan(): Promise<void> {
231
+ const url = 'http://localhost:3008/payments/cancel-subscription'
232
+
233
+ const providerId = getCurrentPlan.value.subscription.provider_id
234
+ const subscriptionId = getCurrentPlan.value.subscription.id
235
+ const body = { providerId, subscriptionId }
236
+ const response = await fetch(url, {
237
+ method: 'POST',
238
+ headers: {
239
+ 'Content-Type': 'application/json',
240
+ 'Accept': 'application/json',
241
+ },
242
+ body: JSON.stringify(body),
243
+ })
244
+
245
+ if (response.status !== 204)
246
+ await response.json()
247
+ }
248
+
249
+ async function fetchUserPaymentMethods(id: number): Promise<void> {
250
+ setLoadingState('fetchUserPaymentMethods')
251
+
252
+ const response: any = await fetch(`${apiUrl}/payments/payment-methods/${id}`, {
253
+ method: 'GET',
254
+ headers: {
255
+ 'Content-Type': 'application/json',
256
+ 'Accept': 'application/json',
257
+ },
258
+ })
259
+
260
+ if (response.status !== 204) {
261
+ const res = await response.json()
262
+
263
+ paymentMethods.value = res
264
+ }
265
+
266
+ removeLoadingState('fetchUserPaymentMethods')
267
+
268
+ ;(globalThis as any).dispatch('paymentMethods:fetched')
269
+ }
270
+
271
+ async function fetchTransactionHistory(id: number): Promise<void> {
272
+ setLoadingState('fetchTransactionHistory')
273
+
274
+ const response: any = await fetch(`${apiUrl}/payments/fetch-transaction-history/${id}`, {
275
+ method: 'GET',
276
+ headers: {
277
+ 'Content-Type': 'application/json',
278
+ 'Accept': 'application/json',
279
+ },
280
+ })
281
+
282
+ if (response.status !== 204) {
283
+ const res = await response.json()
284
+
285
+ transactionHistory.value = res.data
286
+ }
287
+
288
+ removeLoadingState('fetchTransactionHistory')
289
+ }
290
+
291
+ async function deletePaymentMethod(paymentMethod: number): Promise<void> {
292
+ setLoadingState('deletePaymentMethod')
293
+ const url = 'http://localhost:3008/payments/delete-payment-method/1'
294
+
295
+ const body = { paymentMethod }
296
+
297
+ try {
298
+ await fetch(url, {
299
+ method: 'DELETE',
300
+ headers: {
301
+ 'Content-Type': 'application/json',
302
+ 'Accept': 'application/json',
303
+ },
304
+ body: JSON.stringify(body),
305
+ })
306
+ }
307
+ catch (err: any) {
308
+ // eslint-disable-next-line no-console
309
+ console.log(err)
310
+ }
311
+
312
+ removeLoadingState('deletePaymentMethod')
313
+ }
314
+
315
+ async function updateDefaultPaymentMethod(paymentMethod: string): Promise<void> {
316
+ setLoadingState('updateDefaultPaymentMethod')
317
+
318
+ const url = 'http://localhost:3008/payments/update-default-payment-method/1'
319
+
320
+ const body = { paymentMethod }
321
+
322
+ try {
323
+ await fetch(url, {
324
+ method: 'PUT',
325
+ headers: {
326
+ 'Content-Type': 'application/json',
327
+ 'Accept': 'application/json',
328
+ },
329
+ body: JSON.stringify(body),
330
+ })
331
+ }
332
+ catch (err: any) {
333
+ // eslint-disable-next-line no-console
334
+ console.log(err)
335
+ }
336
+
337
+ removeLoadingState('updateDefaultPaymentMethod')
338
+ }
339
+
340
+ async function fetchStripeCustomer(id: number): Promise<void> {
341
+ setLoadingState('fetchStripeCustomer')
342
+
343
+ const response: any = await fetch(`${apiUrl}/payments/fetch-customer/${id}`, {
344
+ method: 'GET',
345
+ headers: {
346
+ 'Content-Type': 'application/json',
347
+ 'Accept': 'application/json',
348
+ },
349
+ })
350
+
351
+ if (response.status !== 204) {
352
+ const res = await response.json()
353
+ stripeCustomer.value = res
354
+ }
355
+
356
+ removeLoadingState('fetchStripeCustomer')
357
+ }
358
+
359
+ async function fetchDefaultPaymentMethod(id: number): Promise<void> {
360
+ setLoadingState('fetchDefaultPaymentMethod')
361
+
362
+ const response: any = await fetch(`${apiUrl}/payments/default-payment-method/${id}`, {
363
+ method: 'GET',
364
+ headers: {
365
+ 'Content-Type': 'application/json',
366
+ 'Accept': 'application/json',
367
+ },
368
+ })
369
+
370
+ if (response.status !== 204) {
371
+ const res = await response.json()
372
+
373
+ defaultPaymentMethod.value = res
374
+ }
375
+
376
+ removeLoadingState('fetchDefaultPaymentMethod')
377
+ }
378
+
379
+ async function fetchProduct(id: number): Promise<void> {
380
+ setLoadingState('fetchProduct')
381
+
382
+ const response: any = await fetch(`${apiUrl}/payments/fetch-product/${id}`, {
383
+ method: 'GET',
384
+ headers: {
385
+ 'Content-Type': 'application/json',
386
+ 'Accept': 'application/json',
387
+ },
388
+ })
389
+
390
+ if (response.status !== 204) {
391
+ const res = await response.json()
392
+
393
+ product.value = res
394
+ }
395
+
396
+ removeLoadingState('fetchProduct')
397
+ }
398
+
399
+ async function fetchUserActivePlan(id: number): Promise<void> {
400
+ setLoadingState('fetchActivePlan')
401
+ const response: any = await fetch(`${apiUrl}/payments/fetch-active-subscription/${id}`, {
402
+ method: 'GET',
403
+ headers: {
404
+ 'Content-Type': 'application/json',
405
+ 'Accept': 'application/json',
406
+ },
407
+ })
408
+
409
+ if (response.status !== 204) {
410
+ const res = await response.json()
411
+
412
+ activeSubscription.value = res
413
+ }
414
+ else {
415
+ activeSubscription.value = {}
416
+ }
417
+
418
+ removeLoadingState('fetchActivePlan')
419
+
420
+ ;(globalThis as any).dispatch('subscription:fetched')
421
+ }
422
+
423
+ function setLoadingState(statusKey: string): void {
424
+ loadingStates.value[statusKey] = true
425
+ }
426
+
427
+ function removeLoadingState(statusKey: string): void {
428
+ loadingStates.value[statusKey] = false
429
+ }
430
+
431
+ function isStateLoading(statusKey: string): boolean {
432
+ return loadingStates.value[statusKey] === undefined ? true : loadingStates.value[statusKey]
433
+ }
434
+
435
+ return {
436
+ paymentMethods,
437
+ defaultPaymentMethod,
438
+ stripeCustomer,
439
+ product,
440
+ activeSubscription,
441
+ transactionHistory,
442
+ isLoading,
443
+ getPaymentMethods,
444
+ getProduct,
445
+ getCurrentPlan,
446
+ getTransactionHistory,
447
+ hasPaymentMethods,
448
+ getDefaultPaymentMethod,
449
+ getStripeCustomer,
450
+ getPlanState,
451
+ fetchSetupIntent,
452
+ fetchPaymentIntent,
453
+ storeTransaction,
454
+ subscribeToPlan,
455
+ updatePlan,
456
+ setDefaultPaymentMethod,
457
+ setUserDefaultPaymentMethod,
458
+ storePaymentMethod,
459
+ openPlans,
460
+ closePlans,
461
+ fetchSubscriptions,
462
+ cancelPlan,
463
+ fetchUserPaymentMethods,
464
+ fetchTransactionHistory,
465
+ deletePaymentMethod,
466
+ updateDefaultPaymentMethod,
467
+ fetchStripeCustomer,
468
+ fetchDefaultPaymentMethod,
469
+ fetchProduct,
470
+ isStateLoading,
471
+ fetchUserActivePlan,
472
+
473
+ }
474
+ })