@stapel/forms-react 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (203) hide show
  1. package/CHANGELOG.md +62 -0
  2. package/MODULE.md +172 -0
  3. package/README.md +207 -0
  4. package/dist/api/export.d.ts +66 -0
  5. package/dist/api/export.d.ts.map +1 -0
  6. package/dist/api/export.js +138 -0
  7. package/dist/api/export.js.map +1 -0
  8. package/dist/api/extensions.d.ts +8 -0
  9. package/dist/api/extensions.d.ts.map +1 -0
  10. package/dist/api/extensions.js +8 -0
  11. package/dist/api/extensions.js.map +1 -0
  12. package/dist/api/formsApi.d.ts +113 -0
  13. package/dist/api/formsApi.d.ts.map +1 -0
  14. package/dist/api/formsApi.js +81 -0
  15. package/dist/api/formsApi.js.map +1 -0
  16. package/dist/api/generated/schema.d.ts +987 -0
  17. package/dist/api/generated/schema.d.ts.map +1 -0
  18. package/dist/api/generated/schema.js +2 -0
  19. package/dist/api/generated/schema.js.map +1 -0
  20. package/dist/api/types.d.ts +222 -0
  21. package/dist/api/types.d.ts.map +1 -0
  22. package/dist/api/types.js +14 -0
  23. package/dist/api/types.js.map +1 -0
  24. package/dist/default/ConfigField.d.ts +32 -0
  25. package/dist/default/ConfigField.d.ts.map +1 -0
  26. package/dist/default/ConfigField.js +101 -0
  27. package/dist/default/ConfigField.js.map +1 -0
  28. package/dist/default/ErrorAlert.d.ts +9 -0
  29. package/dist/default/ErrorAlert.d.ts.map +1 -0
  30. package/dist/default/ErrorAlert.js +27 -0
  31. package/dist/default/ErrorAlert.js.map +1 -0
  32. package/dist/default/FormBuilderPane.d.ts +36 -0
  33. package/dist/default/FormBuilderPane.d.ts.map +1 -0
  34. package/dist/default/FormBuilderPane.js +70 -0
  35. package/dist/default/FormBuilderPane.js.map +1 -0
  36. package/dist/default/FormsListPane.d.ts +18 -0
  37. package/dist/default/FormsListPane.d.ts.map +1 -0
  38. package/dist/default/FormsListPane.js +28 -0
  39. package/dist/default/FormsListPane.js.map +1 -0
  40. package/dist/default/ResponsesPane.d.ts +21 -0
  41. package/dist/default/ResponsesPane.d.ts.map +1 -0
  42. package/dist/default/ResponsesPane.js +118 -0
  43. package/dist/default/ResponsesPane.js.map +1 -0
  44. package/dist/default/StapelForm.d.ts +76 -0
  45. package/dist/default/StapelForm.d.ts.map +1 -0
  46. package/dist/default/StapelForm.js +118 -0
  47. package/dist/default/StapelForm.js.map +1 -0
  48. package/dist/default/fields.d.ts +11 -0
  49. package/dist/default/fields.d.ts.map +1 -0
  50. package/dist/default/fields.js +273 -0
  51. package/dist/default/fields.js.map +1 -0
  52. package/dist/default/index.d.ts +42 -0
  53. package/dist/default/index.d.ts.map +1 -0
  54. package/dist/default/index.js +37 -0
  55. package/dist/default/index.js.map +1 -0
  56. package/dist/default/slots.d.ts +59 -0
  57. package/dist/default/slots.d.ts.map +1 -0
  58. package/dist/default/slots.js +25 -0
  59. package/dist/default/slots.js.map +1 -0
  60. package/dist/default/theme.d.ts +23 -0
  61. package/dist/default/theme.d.ts.map +1 -0
  62. package/dist/default/theme.js +38 -0
  63. package/dist/default/theme.js.map +1 -0
  64. package/dist/default/types.d.ts +12 -0
  65. package/dist/default/types.d.ts.map +1 -0
  66. package/dist/default/types.js +2 -0
  67. package/dist/default/types.js.map +1 -0
  68. package/dist/flows/errors.d.ts +12 -0
  69. package/dist/flows/errors.d.ts.map +1 -0
  70. package/dist/flows/errors.js +13 -0
  71. package/dist/flows/errors.js.map +1 -0
  72. package/dist/flows/registry.d.ts +22 -0
  73. package/dist/flows/registry.d.ts.map +1 -0
  74. package/dist/flows/registry.js +20 -0
  75. package/dist/flows/registry.js.map +1 -0
  76. package/dist/headless/FormBuilder.d.ts +100 -0
  77. package/dist/headless/FormBuilder.d.ts.map +1 -0
  78. package/dist/headless/FormBuilder.js +278 -0
  79. package/dist/headless/FormBuilder.js.map +1 -0
  80. package/dist/headless/FormFill.d.ts +88 -0
  81. package/dist/headless/FormFill.d.ts.map +1 -0
  82. package/dist/headless/FormFill.js +279 -0
  83. package/dist/headless/FormFill.js.map +1 -0
  84. package/dist/headless/FormList.d.ts +34 -0
  85. package/dist/headless/FormList.d.ts.map +1 -0
  86. package/dist/headless/FormList.js +37 -0
  87. package/dist/headless/FormList.js.map +1 -0
  88. package/dist/headless/FormsProvider.d.ts +19 -0
  89. package/dist/headless/FormsProvider.d.ts.map +1 -0
  90. package/dist/headless/FormsProvider.js +15 -0
  91. package/dist/headless/FormsProvider.js.map +1 -0
  92. package/dist/headless/ResponsesTable.d.ts +82 -0
  93. package/dist/headless/ResponsesTable.d.ts.map +1 -0
  94. package/dist/headless/ResponsesTable.js +195 -0
  95. package/dist/headless/ResponsesTable.js.map +1 -0
  96. package/dist/i18n/errorsMap.d.ts +10 -0
  97. package/dist/i18n/errorsMap.d.ts.map +1 -0
  98. package/dist/i18n/errorsMap.js +20 -0
  99. package/dist/i18n/errorsMap.js.map +1 -0
  100. package/dist/i18n/es.d.ts +7 -0
  101. package/dist/i18n/es.d.ts.map +1 -0
  102. package/dist/i18n/es.js +118 -0
  103. package/dist/i18n/es.js.map +1 -0
  104. package/dist/i18n/generated/errors.es.gen.d.ts +16 -0
  105. package/dist/i18n/generated/errors.es.gen.d.ts.map +1 -0
  106. package/dist/i18n/generated/errors.es.gen.js +79 -0
  107. package/dist/i18n/generated/errors.es.gen.js.map +1 -0
  108. package/dist/i18n/generated/errors.gen.d.ts +485 -0
  109. package/dist/i18n/generated/errors.gen.d.ts.map +1 -0
  110. package/dist/i18n/generated/errors.gen.js +246 -0
  111. package/dist/i18n/generated/errors.gen.js.map +1 -0
  112. package/dist/i18n/generated/errors.ru.gen.d.ts +16 -0
  113. package/dist/i18n/generated/errors.ru.gen.d.ts.map +1 -0
  114. package/dist/i18n/generated/errors.ru.gen.js +79 -0
  115. package/dist/i18n/generated/errors.ru.gen.js.map +1 -0
  116. package/dist/i18n/keys.d.ts +141 -0
  117. package/dist/i18n/keys.d.ts.map +1 -0
  118. package/dist/i18n/keys.js +233 -0
  119. package/dist/i18n/keys.js.map +1 -0
  120. package/dist/i18n/ru.d.ts +7 -0
  121. package/dist/i18n/ru.d.ts.map +1 -0
  122. package/dist/i18n/ru.js +127 -0
  123. package/dist/i18n/ru.js.map +1 -0
  124. package/dist/index.d.ts +61 -0
  125. package/dist/index.d.ts.map +1 -0
  126. package/dist/index.js +55 -0
  127. package/dist/index.js.map +1 -0
  128. package/dist/model/context.d.ts +11 -0
  129. package/dist/model/context.d.ts.map +1 -0
  130. package/dist/model/context.js +16 -0
  131. package/dist/model/context.js.map +1 -0
  132. package/dist/model/mutations.d.ts +135 -0
  133. package/dist/model/mutations.d.ts.map +1 -0
  134. package/dist/model/mutations.js +223 -0
  135. package/dist/model/mutations.js.map +1 -0
  136. package/dist/model/queries.d.ts +59 -0
  137. package/dist/model/queries.d.ts.map +1 -0
  138. package/dist/model/queries.js +117 -0
  139. package/dist/model/queries.js.map +1 -0
  140. package/dist/model/queryKeys.d.ts +28 -0
  141. package/dist/model/queryKeys.d.ts.map +1 -0
  142. package/dist/model/queryKeys.js +23 -0
  143. package/dist/model/queryKeys.js.map +1 -0
  144. package/dist/model/runtime.d.ts +28 -0
  145. package/dist/model/runtime.d.ts.map +1 -0
  146. package/dist/model/runtime.js +14 -0
  147. package/dist/model/runtime.js.map +1 -0
  148. package/dist/widgets/configForms.d.ts +112 -0
  149. package/dist/widgets/configForms.d.ts.map +1 -0
  150. package/dist/widgets/configForms.js +211 -0
  151. package/dist/widgets/configForms.js.map +1 -0
  152. package/dist/widgets/registry.d.ts +83 -0
  153. package/dist/widgets/registry.d.ts.map +1 -0
  154. package/dist/widgets/registry.js +27 -0
  155. package/dist/widgets/registry.js.map +1 -0
  156. package/dist/widgets/validate.d.ts +57 -0
  157. package/dist/widgets/validate.d.ts.map +1 -0
  158. package/dist/widgets/validate.js +173 -0
  159. package/dist/widgets/validate.js.map +1 -0
  160. package/llms.txt +124 -0
  161. package/manifest.json +1038 -0
  162. package/package.json +108 -0
  163. package/src/analytics/generated/events.json +7 -0
  164. package/src/api/export.ts +195 -0
  165. package/src/api/extensions.ts +7 -0
  166. package/src/api/formsApi.ts +329 -0
  167. package/src/api/generated/schema.ts +989 -0
  168. package/src/api/types.ts +276 -0
  169. package/src/default/ConfigField.tsx +227 -0
  170. package/src/default/ErrorAlert.tsx +46 -0
  171. package/src/default/FormBuilderPane.tsx +414 -0
  172. package/src/default/FormsListPane.tsx +144 -0
  173. package/src/default/ResponsesPane.tsx +332 -0
  174. package/src/default/StapelForm.tsx +377 -0
  175. package/src/default/fields.tsx +454 -0
  176. package/src/default/index.ts +71 -0
  177. package/src/default/slots.ts +78 -0
  178. package/src/default/theme.tsx +65 -0
  179. package/src/default/types.ts +12 -0
  180. package/src/flows/errors.ts +16 -0
  181. package/src/flows/registry.ts +32 -0
  182. package/src/headless/FormBuilder.tsx +453 -0
  183. package/src/headless/FormFill.tsx +396 -0
  184. package/src/headless/FormList.tsx +74 -0
  185. package/src/headless/FormsProvider.tsx +20 -0
  186. package/src/headless/ResponsesTable.tsx +341 -0
  187. package/src/i18n/errorsMap.ts +31 -0
  188. package/src/i18n/es.ts +140 -0
  189. package/src/i18n/generated/errors.es.gen.ts +85 -0
  190. package/src/i18n/generated/errors.gen.ts +277 -0
  191. package/src/i18n/generated/errors.json +583 -0
  192. package/src/i18n/generated/errors.ru.gen.ts +85 -0
  193. package/src/i18n/keys.ts +264 -0
  194. package/src/i18n/ru.ts +150 -0
  195. package/src/index.ts +184 -0
  196. package/src/model/context.tsx +28 -0
  197. package/src/model/mutations.ts +387 -0
  198. package/src/model/queries.ts +154 -0
  199. package/src/model/queryKeys.ts +61 -0
  200. package/src/model/runtime.ts +48 -0
  201. package/src/widgets/registry.ts +101 -0
  202. package/src/widgets/validate.ts +224 -0
  203. package/tsconfig.json +26 -0
@@ -0,0 +1,8 @@
1
+ /**
2
+ * Hand-authored API surface the codegen does not (yet) cover — browser-redirect
3
+ * URL builders, open-redirect guards, narrow domain type-guards, header
4
+ * conventions. Everything that CAN be derived from schema.json belongs in the
5
+ * generated operations (`api/formsApi.ts`), not here.
6
+ */
7
+ export {};
8
+ //# sourceMappingURL=extensions.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"extensions.js","sourceRoot":"","sources":["../../src/api/extensions.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EAAE,CAAC"}
@@ -0,0 +1,113 @@
1
+ import type { StapelClient } from "@stapel/core";
2
+ import type { CsvExportPage, FormsApiOptions } from "./export.js";
3
+ import type { FieldKindCatalogue, FormCreateRequest, FormPatchRequest, FormRow, FormSchema, FormState, FormVersion, PublicForm, PublishResult, ResendRequest, ResendResult, Submission, SubmissionListParams, SubmitRequest, SubmitResult } from "./types.js";
4
+ /**
5
+ * The pair's typed operation surface — one method per stapel-forms endpoint a
6
+ * JS client may call, bound to the injected {@link StapelClient} (the
7
+ * per-module override seam of frontend-standard §7.2). Paths are relative to
8
+ * the runtime's `baseUrl` (e.g. `/forms/api/v1/`).
9
+ *
10
+ * Two families, and the split matters:
11
+ *
12
+ * - **public** (`getPublicForm`, `submit`) — ANONYMOUS. No capability, no
13
+ * workspace id, no session. A render-only host page needs nothing but
14
+ * `createFormsRuntime({baseUrl})`; this is the standalone-embed property.
15
+ * - **admin** — every one is `IsNotAnonymousUser` + `authorize()` +
16
+ * `workspace_id`, gated on `forms.view` / `forms.manage` /
17
+ * `forms.responses.view` / `forms.responses.manage`.
18
+ *
19
+ * These operations will be GENERATED from schema.json operationIds by gen-api
20
+ * v2 (task `core-typed-ops`); until then they are hand-authored here (the ONE
21
+ * legal home of path strings — `stapel/no-string-paths` §2.3 carve-out).
22
+ */
23
+ export interface FormsApi {
24
+ readonly client: StapelClient;
25
+ /**
26
+ * The active schema behind a public link. Refuses with
27
+ * `error.404.forms_not_found` (no such link / rotated / soft-deleted) or
28
+ * `error.410.forms_closed` — two DIFFERENT sentences a skin must not merge,
29
+ * and neither of which is "no form here" when the network is what failed.
30
+ */
31
+ getPublicForm(publicId: string): Promise<PublicForm>;
32
+ /**
33
+ * Submit answers. `answers` values are bare scalars keyed by slug; a `select`
34
+ * answer normalizes to a list server-side, so the caller need not wrap it.
35
+ *
36
+ * The refusals a renderer must tell apart: `409
37
+ * error.409.forms_version_superseded` (the schema moved under the
38
+ * respondent — refetch and preserve compatible values), `409
39
+ * error.409.forms_submission_cap`, `410 error.410.forms_closed`, `413
40
+ * error.413.forms_body_too_large`, `429` throttle, and the per-field
41
+ * `error.400.feature_*` family whose `params.field` names the offending slug.
42
+ */
43
+ submit(publicId: string, body: SubmitRequest): Promise<SubmitResult>;
44
+ /**
45
+ * The field kinds a form may be built from, with their config forms.
46
+ * `forms.manage` — a principal who cannot build a form has no use for the
47
+ * builder's dictionary, and the catalogue names host types whose slugs are
48
+ * internal vocabulary.
49
+ *
50
+ * This is what replaced the pair's hand-mirrored copy of
51
+ * `stapel_attributes.config_form` (stapel-forms 0.2.0): the declaration is
52
+ * the single source of truth again, so a type registered through
53
+ * `EXTRA_TYPES` shows up in the builder with no client release.
54
+ */
55
+ listFieldKinds(workspaceId: string): Promise<FieldKindCatalogue>;
56
+ /** The workspace's forms. `forms.view`. */
57
+ listForms(workspaceId: string, state?: FormState): Promise<readonly FormRow[]>;
58
+ /** One form. `forms.view`. */
59
+ getForm(workspaceId: string, formId: string): Promise<FormRow>;
60
+ /** Create a form (state starts `draft`). `forms.manage`. */
61
+ createForm(body: FormCreateRequest): Promise<FormRow>;
62
+ /** Retitle / re-target a form. `forms.manage`. */
63
+ patchForm(workspaceId: string, formId: string, body: FormPatchRequest): Promise<FormRow>;
64
+ /** Soft-delete. `forms.manage`. */
65
+ deleteForm(workspaceId: string, formId: string): Promise<void>;
66
+ /** Replace the builder's scratchpad. `forms.manage`. */
67
+ putDraft(workspaceId: string, formId: string, schema: FormSchema): Promise<FormRow>;
68
+ /**
69
+ * Freeze the draft into the next immutable version. `forms.manage`.
70
+ * Refuses an empty schema, a duplicate slug, a kind outside `FIELD_KINDS`,
71
+ * a field count over the cap, and — backend delta note 1 — a config key the
72
+ * type's dataclass does not know (`error.400.forms_invalid_schema` with
73
+ * `params.key`), because a dropped key is a constraint that silently does
74
+ * not exist.
75
+ */
76
+ publish(workspaceId: string, formId: string): Promise<PublishResult>;
77
+ /** Open / close / return to draft. `forms.manage`. */
78
+ setState(workspaceId: string, formId: string, state: FormState): Promise<FormRow>;
79
+ /** Mint a new `public_id`, retiring the old link. `forms.manage`. */
80
+ rotateLink(workspaceId: string, formId: string): Promise<FormRow>;
81
+ /** Every published version, for the responses view's column sets.
82
+ * `forms.view`. */
83
+ listVersions(workspaceId: string, formId: string): Promise<readonly FormVersion[]>;
84
+ /** One keyset page of responses. `forms.responses.view`. */
85
+ listSubmissions(params: SubmissionListParams): Promise<readonly Submission[]>;
86
+ /** One response. `forms.responses.view`. */
87
+ getSubmission(workspaceId: string, submissionId: string): Promise<Submission>;
88
+ /** Erase one response. `forms.responses.manage`. */
89
+ deleteSubmission(workspaceId: string, submissionId: string): Promise<void>;
90
+ /**
91
+ * Re-deliver one response through the form's notification targets.
92
+ * `forms.responses.manage`. An explicit destination override REPLACES the
93
+ * configured targets (backend delta note 7). Admin-initiated, so it is NOT
94
+ * subject to `NOTIFY_COOLDOWN_SECONDS`.
95
+ */
96
+ resendSubmission(workspaceId: string, submissionId: string, body?: ResendRequest): Promise<ResendResult>;
97
+ /**
98
+ * One page of the CSV export, plus the continuation cursor. `forms.responses.view`.
99
+ * Rides the raw transport, not the JSON client — see `api/export.ts`.
100
+ */
101
+ exportSubmissions(params: {
102
+ readonly workspaceId: string;
103
+ readonly formId: string;
104
+ readonly before?: string;
105
+ readonly version?: number;
106
+ readonly signal?: AbortSignal;
107
+ }): Promise<CsvExportPage>;
108
+ }
109
+ /** Raw-transport binding forwarded from the runtime (declared in
110
+ * `api/export.ts`, which owns the surface that consumes it). */
111
+ export type { FormsApiOptions } from "./export.js";
112
+ export declare function createFormsApi(client: StapelClient, options?: FormsApiOptions): FormsApi;
113
+ //# sourceMappingURL=formsApi.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"formsApi.d.ts","sourceRoot":"","sources":["../../src/api/formsApi.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAwB,MAAM,cAAc,CAAC;AAEvE,OAAO,KAAK,EACV,aAAa,EACb,eAAe,EAEhB,MAAM,aAAa,CAAC;AACrB,OAAO,KAAK,EAEV,kBAAkB,EAClB,iBAAiB,EACjB,gBAAgB,EAChB,OAAO,EACP,UAAU,EACV,SAAS,EACT,WAAW,EACX,UAAU,EACV,aAAa,EACb,aAAa,EACb,YAAY,EACZ,UAAU,EACV,oBAAoB,EACpB,aAAa,EACb,YAAY,EACb,MAAM,YAAY,CAAC;AAuCpB;;;;;;;;;;;;;;;;;;GAkBG;AACH,MAAM,WAAW,QAAQ;IACvB,QAAQ,CAAC,MAAM,EAAE,YAAY,CAAC;IAI9B;;;;;OAKG;IACH,aAAa,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAAC;IAErD;;;;;;;;;;OAUG;IACH,MAAM,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,aAAa,GAAG,OAAO,CAAC,YAAY,CAAC,CAAC;IAIrE;;;;;;;;;;OAUG;IACH,cAAc,CAAC,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,kBAAkB,CAAC,CAAC;IAIjE,2CAA2C;IAC3C,SAAS,CAAC,WAAW,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,SAAS,GAAG,OAAO,CAAC,SAAS,OAAO,EAAE,CAAC,CAAC;IAC/E,8BAA8B;IAC9B,OAAO,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IAC/D,4DAA4D;IAC5D,UAAU,CAAC,IAAI,EAAE,iBAAiB,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IACtD,kDAAkD;IAClD,SAAS,CACP,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,EACd,IAAI,EAAE,gBAAgB,GACrB,OAAO,CAAC,OAAO,CAAC,CAAC;IACpB,mCAAmC;IACnC,UAAU,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAE/D,wDAAwD;IACxD,QAAQ,CACN,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,UAAU,GACjB,OAAO,CAAC,OAAO,CAAC,CAAC;IACpB;;;;;;;OAOG;IACH,OAAO,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,CAAC,CAAC;IACrE,sDAAsD;IACtD,QAAQ,CACN,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,SAAS,GACf,OAAO,CAAC,OAAO,CAAC,CAAC;IACpB,qEAAqE;IACrE,UAAU,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IAClE;uBACmB;IACnB,YAAY,CACV,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,SAAS,WAAW,EAAE,CAAC,CAAC;IAInC,4DAA4D;IAC5D,eAAe,CAAC,MAAM,EAAE,oBAAoB,GAAG,OAAO,CAAC,SAAS,UAAU,EAAE,CAAC,CAAC;IAC9E,4CAA4C;IAC5C,aAAa,CAAC,WAAW,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAAC;IAC9E,oDAAoD;IACpD,gBAAgB,CAAC,WAAW,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAC3E;;;;;OAKG;IACH,gBAAgB,CACd,WAAW,EAAE,MAAM,EACnB,YAAY,EAAE,MAAM,EACpB,IAAI,CAAC,EAAE,aAAa,GACnB,OAAO,CAAC,YAAY,CAAC,CAAC;IAEzB;;;OAGG;IACH,iBAAiB,CAAC,MAAM,EAAE;QACxB,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;QAC7B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;QACxB,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;QACzB,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,CAAC;QAC1B,QAAQ,CAAC,MAAM,CAAC,EAAE,WAAW,CAAC;KAC/B,GAAG,OAAO,CAAC,aAAa,CAAC,CAAC;CAC5B;AAED;gEACgE;AAChE,YAAY,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AAEnD,wBAAgB,cAAc,CAC5B,MAAM,EAAE,YAAY,EACpB,OAAO,GAAE,eAAoB,GAC5B,QAAQ,CAsHV"}
@@ -0,0 +1,81 @@
1
+ import { createExportTransport, exportSubmissionsCsv } from "./export.js";
2
+ /**
3
+ * CSRF rule for cookie-authenticated browser clients (mirrors auth-react and
4
+ * profiles-react): the simplest SPA rule is to always send
5
+ * `X-Requested-With: XMLHttpRequest` on mutating requests. Header-token clients
6
+ * ignore it; it is harmless there, so every mutation carries it.
7
+ *
8
+ * The two ANONYMOUS routes carry it too. They are unauthenticated, so there is
9
+ * no session for a cross-site POST to ride — but a host that mounts the form on
10
+ * a cookie-authenticated origin gets Django's CSRF middleware in the path
11
+ * anyway, and a header a server ignores costs nothing next to a submit that
12
+ * 403s only in production.
13
+ */
14
+ const CSRF_HEADERS = {
15
+ "X-Requested-With": "XMLHttpRequest",
16
+ };
17
+ function mutating(options) {
18
+ return {
19
+ ...options,
20
+ headers: { ...CSRF_HEADERS, ...options?.headers },
21
+ };
22
+ }
23
+ /** URL-safe path segment. `public_id` is a non-enumerable token straight from
24
+ * the host's props, so it is encoded rather than trusted. */
25
+ function seg(value) {
26
+ return encodeURIComponent(value);
27
+ }
28
+ /** Every admin route is workspace-scoped by an explicit query parameter — the
29
+ * module never infers the workspace from the session. */
30
+ function ws(workspaceId) {
31
+ return { workspace_id: workspaceId };
32
+ }
33
+ export function createFormsApi(client, options = {}) {
34
+ const transport = createExportTransport(client.baseUrl, options);
35
+ return {
36
+ client,
37
+ // ── public ───────────────────────────────────────────────────────────────
38
+ getPublicForm: (publicId) => client.get(`/public/${seg(publicId)}/`),
39
+ submit: (publicId, body) => client.post(`/public/${seg(publicId)}/submissions/`, body, mutating()),
40
+ // ── admin: the builder's dictionary ──────────────────────────────────────
41
+ // Note the path: no `admin/` prefix and no trailing slash, unlike the two
42
+ // anonymous routes. Both are load-bearing — Django resolves this exactly.
43
+ listFieldKinds: async (workspaceId) => {
44
+ const dto = await client.get("/field-kinds", { query: ws(workspaceId) });
45
+ // Both members are optional on the wire (dataclass defaults), and a
46
+ // builder that reads `.kinds.map` off `undefined` is a crash where an
47
+ // empty catalogue would do.
48
+ return {
49
+ kinds: dto.kinds ?? [],
50
+ configWidgets: dto.config_widgets ?? {},
51
+ };
52
+ },
53
+ // ── admin: forms ─────────────────────────────────────────────────────────
54
+ listForms: (workspaceId, state) => client.get("/forms", {
55
+ query: { ...ws(workspaceId), ...(state !== undefined ? { state } : {}) },
56
+ }),
57
+ getForm: (workspaceId, formId) => client.get(`/forms/${seg(formId)}`, { query: ws(workspaceId) }),
58
+ createForm: (body) => client.post("/forms", body, mutating()),
59
+ patchForm: (workspaceId, formId, body) => client.patch(`/forms/${seg(formId)}`, body, mutating({ query: ws(workspaceId) })),
60
+ deleteForm: (workspaceId, formId) => client.delete(`/forms/${seg(formId)}`, mutating({ query: ws(workspaceId) })),
61
+ putDraft: (workspaceId, formId, schema) => client.put(`/forms/${seg(formId)}/draft`, { schema }, mutating({ query: ws(workspaceId) })),
62
+ publish: (workspaceId, formId) => client.post(`/forms/${seg(formId)}/publish`, undefined, mutating({ query: ws(workspaceId) })),
63
+ setState: (workspaceId, formId, state) => client.post(`/forms/${seg(formId)}/state`, { state }, mutating({ query: ws(workspaceId) })),
64
+ rotateLink: (workspaceId, formId) => client.post(`/forms/${seg(formId)}/rotate-link`, undefined, mutating({ query: ws(workspaceId) })),
65
+ listVersions: (workspaceId, formId) => client.get(`/forms/${seg(formId)}/versions`, { query: ws(workspaceId) }),
66
+ // ── admin: responses ─────────────────────────────────────────────────────
67
+ listSubmissions: (params) => client.get(`/forms/${seg(params.formId)}/submissions`, {
68
+ query: {
69
+ ...ws(params.workspaceId),
70
+ ...(params.before !== undefined ? { before: params.before } : {}),
71
+ ...(params.limit !== undefined ? { limit: params.limit } : {}),
72
+ ...(params.version !== undefined ? { version: params.version } : {}),
73
+ },
74
+ }),
75
+ getSubmission: (workspaceId, submissionId) => client.get(`/submissions/${seg(submissionId)}`, { query: ws(workspaceId) }),
76
+ deleteSubmission: (workspaceId, submissionId) => client.delete(`/submissions/${seg(submissionId)}`, mutating({ query: ws(workspaceId) })),
77
+ resendSubmission: (workspaceId, submissionId, body) => client.post(`/submissions/${seg(submissionId)}/resend`, body ?? {}, mutating({ query: ws(workspaceId) })),
78
+ exportSubmissions: (params) => exportSubmissionsCsv(transport, params),
79
+ };
80
+ }
81
+ //# sourceMappingURL=formsApi.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"formsApi.js","sourceRoot":"","sources":["../../src/api/formsApi.ts"],"names":[],"mappings":"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"}