create-cartbase 0.1.16 → 0.1.17

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 (34) hide show
  1. package/LICENSE +21 -21
  2. package/README.md +25 -25
  3. package/dist/index.js +20 -20
  4. package/package.json +24 -24
  5. package/template/app/docs/auth.md +105 -105
  6. package/template/app/docs/carts.md +376 -376
  7. package/template/app/docs/categories.md +194 -194
  8. package/template/app/docs/checkout.md +714 -714
  9. package/template/app/docs/components.md +44 -11
  10. package/template/app/docs/consent.md +91 -91
  11. package/template/app/docs/deploy.md +197 -197
  12. package/template/app/docs/gift-cards.md +153 -153
  13. package/template/app/docs/metaobjects.md +126 -126
  14. package/template/app/docs/orders.md +221 -221
  15. package/template/app/docs/products.md +51 -2
  16. package/template/app/docs/regions.md +269 -269
  17. package/template/app/docs/reviews.md +223 -223
  18. package/template/app/docs/search.md +227 -227
  19. package/template/app/docs/store.md +47 -47
  20. package/template/app/docs/subscriptions.md +148 -148
  21. package/template/app/docs/variables.md +315 -315
  22. package/template/app/package.json +1 -1
  23. package/template/app/postcss.config.cjs +11 -11
  24. package/template/app/src/app/checkout/checkout-page-client.tsx +73 -73
  25. package/template/app/src/app/checkout/page.tsx +48 -48
  26. package/template/app/src/app/globals.css +26 -26
  27. package/template/app/src/app/page.tsx +28 -28
  28. package/template/app/src/app/products/[handle]/page.tsx +87 -87
  29. package/template/app/src/app/providers.tsx +64 -64
  30. package/template/app/src/app/search/page.tsx +23 -23
  31. package/template/app/src/lib/browser-client.ts +35 -35
  32. package/template/app/src/lib/config.ts +41 -41
  33. package/template/app/src/lib/server-client.ts +25 -25
  34. package/template/app/src/lib/cart-actions.ts +0 -47
@@ -1,194 +1,194 @@
1
- # Categories
2
-
3
- Taxonomy reads for navigation trees and filter UIs. Categories are
4
- hierarchical (`parent_category_id`) with optional ancestor/descendant tree
5
- embedding; tags and types are flat value lists whose ids feed the `tag_id` /
6
- `type_id` filters on product listings and search.
7
-
8
- SDK module: `@cartbase/storefront/api/categories`.
9
-
10
- **Visibility:** only ACTIVE, non-internal categories exist on the store
11
- surface — enforced by the anon RLS policy, so an inactive/internal category
12
- 404s even when retrieved by id.
13
-
14
- ---
15
-
16
- ## GET /api/store/product-categories
17
-
18
- - **Purpose** — category list / one tree level (pass `parent_category_id`
19
- to walk levels, or the tree flags to embed whole branches).
20
- - **Auth** — anon: `x-client-id` required.
21
- - **Request**
22
-
23
- ```jsonc
24
- // query (all optional)
25
- {
26
- "q": "appa", // case-insensitive substring on name
27
- "handle": "apparel", // exact
28
- "parent_category_id": "pcat_…", // children of this category
29
- "include_ancestors_tree": true, // embed parent_category chains
30
- "include_descendants_tree": true, // embed category_children recursively
31
- "limit": 50, // 1–200, default 50
32
- "offset": 0
33
- }
34
- ```
35
-
36
- - **Response** — `{ product_categories, count, offset, limit }`, ordered by
37
- `rank`:
38
-
39
- ```jsonc
40
- {
41
- "product_categories": [
42
- {
43
- "id": "pcat_01tst00000000000000000001",
44
- "name": "Apparel",
45
- "handle": "apparel",
46
- "description": null,
47
- "parent_category_id": null,
48
- "rank": 0,
49
- "is_active": true, // always true on the store surface
50
- "is_internal": false, // always false on the store surface
51
- "mpath": null,
52
- "seo_title": null, // null = fall back to name
53
- "seo_description": null, // null = fall back to description
54
- "metadata": null,
55
- "created_at": "2026-07-01T00:00:00.000Z",
56
- "updated_at": "2026-07-01T00:00:00.000Z",
57
- // only when include_descendants_tree=true:
58
- "category_children": [ /* same shape, recursive */ ],
59
- // only when include_ancestors_tree=true:
60
- "parent_category": null
61
- }
62
- ],
63
- "count": 1, "offset": 0, "limit": 50
64
- }
65
- ```
66
-
67
- - **Working curl** — the seeded catalog carries the `apparel` category:
68
-
69
- ```bash
70
- CATEGORIES=$(curl -sf "$BASE/api/store/product-categories?handle=apparel" \
71
- -H "x-client-id: $CLIENT_ID")
72
- echo "$CATEGORIES" | grep -q '"product_categories"'
73
- echo "$CATEGORIES" | grep -q '"handle":"apparel"'
74
- CAT_ID=$(echo "$CATEGORIES" | grep -o '"id":"pcat_[^"]*"' | head -1 | cut -d'"' -f4)
75
- test -n "$CAT_ID"
76
- ```
77
-
78
- - **Errors** — 400 `missing_client_id`, 400 `validation_failed`.
79
- - **SDK** — `listCategories(client, query?)`.
80
- - **Components** — category navigation tree, breadcrumbs.
81
- - **Settings** — Admin → Categories: `is_active` / `is_internal` flags,
82
- rank ordering, SEO overrides.
83
-
84
- ---
85
-
86
- ## GET /api/store/product-categories/:id
87
-
88
- - **Purpose** — retrieve one category, optionally with its tree (category
89
- landing page + breadcrumbs in one call).
90
- - **Auth** — anon: `x-client-id` required.
91
- - **Request** — query `{ include_ancestors_tree?, include_descendants_tree? }`.
92
- - **Response** — `{ "product_category": { ... } }` (tree fields only when
93
- requested; trees contain visible categories only).
94
- - **Working curl**
95
-
96
- ```bash
97
- CATEGORY=$(curl -sf \
98
- "$BASE/api/store/product-categories/$CAT_ID?include_descendants_tree=true" \
99
- -H "x-client-id: $CLIENT_ID")
100
- echo "$CATEGORY" | grep -q '"product_category"'
101
- echo "$CATEGORY" | grep -q '"category_children"'
102
- ```
103
-
104
- - **Errors** — 404 `not_found` (unknown, deleted, or inactive/internal —
105
- RLS hides them even by id).
106
-
107
- ```bash
108
- STATUS=$(curl -s -o /dev/null -w '%{http_code}' \
109
- "$BASE/api/store/product-categories/pcat_doesnotexist$RUN" \
110
- -H "x-client-id: $CLIENT_ID")
111
- test "$STATUS" = 404
112
- ```
113
-
114
- - **SDK** — `retrieveCategory(client, categoryId, query?)`.
115
- - **Components** — category page header, breadcrumbs.
116
- - **Settings** — as the list.
117
-
118
- ---
119
-
120
- ## GET /api/store/product-tags
121
-
122
- - **Purpose** — tag list (filter chips). Use the returned ids as `tag_id`
123
- filters on `/products` and `/products/search`.
124
- - **Auth** — anon: `x-client-id` required.
125
- - **Request** — query `{ q?, value?, limit?, offset? }` (`q` substring,
126
- `value` exact; `limit` 1–200, default 50).
127
- - **Response** — ordered by value:
128
-
129
- ```jsonc
130
- {
131
- "product_tags": [
132
- { "id": "ptag_…", "value": "summer", "metadata": null,
133
- "created_at": "2026-07-01T00:00:00.000Z", "updated_at": "2026-07-01T00:00:00.000Z" }
134
- ],
135
- "count": 1, "offset": 0, "limit": 50
136
- }
137
- ```
138
-
139
- - **Working curl** — the dev tenant seeds no tags, so this asserts the
140
- envelope (the shape contract), not contents:
141
-
142
- ```bash
143
- TAGS=$(curl -sf "$BASE/api/store/product-tags" -H "x-client-id: $CLIENT_ID")
144
- echo "$TAGS" | grep -q '"product_tags"'
145
- echo "$TAGS" | grep -q '"count"'
146
- ```
147
-
148
- - **Errors** — 400 `missing_client_id`, 400 `validation_failed`;
149
- retrieve (`GET /api/store/product-tags/:id` → `{ "product_tag": …}`) 404s
150
- on unknown ids:
151
-
152
- ```bash
153
- STATUS=$(curl -s -o /dev/null -w '%{http_code}' \
154
- "$BASE/api/store/product-tags/ptag_doesnotexist$RUN" -H "x-client-id: $CLIENT_ID")
155
- test "$STATUS" = 404
156
- ```
157
-
158
- - **SDK** — `listProductTags(client, query?)` /
159
- `retrieveProductTag(client, tagId)`.
160
- - **Components** — filter sidebar chips.
161
- - **Settings** — tags are authored on products in admin.
162
-
163
- ---
164
-
165
- ## GET /api/store/product-types
166
-
167
- - **Purpose** — type list; ids feed `type_id` filters on listings/search.
168
- - **Auth** — anon: `x-client-id` required.
169
- - **Request** — query `{ q?, value?, limit?, offset? }` (same semantics as
170
- tags).
171
- - **Response** — `{ product_types, count, offset, limit }`, rows
172
- `{ id, value, metadata, created_at, updated_at }`, ordered by value.
173
- - **Working curl**
174
-
175
- ```bash
176
- TYPES=$(curl -sf "$BASE/api/store/product-types" -H "x-client-id: $CLIENT_ID")
177
- echo "$TYPES" | grep -q '"product_types"'
178
- echo "$TYPES" | grep -q '"count"'
179
- ```
180
-
181
- - **Errors** — 400 `missing_client_id`, 400 `validation_failed`; retrieve
182
- (`GET /api/store/product-types/:id` → `{ "product_type": …}`) 404s on
183
- unknown ids:
184
-
185
- ```bash
186
- STATUS=$(curl -s -o /dev/null -w '%{http_code}' \
187
- "$BASE/api/store/product-types/ptyp_doesnotexist$RUN" -H "x-client-id: $CLIENT_ID")
188
- test "$STATUS" = 404
189
- ```
190
-
191
- - **SDK** — `listProductTypes(client, query?)` /
192
- `retrieveProductType(client, typeId)`.
193
- - **Components** — filter sidebar.
194
- - **Settings** — types are authored on products in admin.
1
+ # Categories
2
+
3
+ Taxonomy reads for navigation trees and filter UIs. Categories are
4
+ hierarchical (`parent_category_id`) with optional ancestor/descendant tree
5
+ embedding; tags and types are flat value lists whose ids feed the `tag_id` /
6
+ `type_id` filters on product listings and search.
7
+
8
+ SDK module: `@cartbase/storefront/api/categories`.
9
+
10
+ **Visibility:** only ACTIVE, non-internal categories exist on the store
11
+ surface — enforced by the anon RLS policy, so an inactive/internal category
12
+ 404s even when retrieved by id.
13
+
14
+ ---
15
+
16
+ ## GET /api/store/product-categories
17
+
18
+ - **Purpose** — category list / one tree level (pass `parent_category_id`
19
+ to walk levels, or the tree flags to embed whole branches).
20
+ - **Auth** — anon: `x-client-id` required.
21
+ - **Request**
22
+
23
+ ```jsonc
24
+ // query (all optional)
25
+ {
26
+ "q": "appa", // case-insensitive substring on name
27
+ "handle": "apparel", // exact
28
+ "parent_category_id": "pcat_…", // children of this category
29
+ "include_ancestors_tree": true, // embed parent_category chains
30
+ "include_descendants_tree": true, // embed category_children recursively
31
+ "limit": 50, // 1–200, default 50
32
+ "offset": 0
33
+ }
34
+ ```
35
+
36
+ - **Response** — `{ product_categories, count, offset, limit }`, ordered by
37
+ `rank`:
38
+
39
+ ```jsonc
40
+ {
41
+ "product_categories": [
42
+ {
43
+ "id": "pcat_01tst00000000000000000001",
44
+ "name": "Apparel",
45
+ "handle": "apparel",
46
+ "description": null,
47
+ "parent_category_id": null,
48
+ "rank": 0,
49
+ "is_active": true, // always true on the store surface
50
+ "is_internal": false, // always false on the store surface
51
+ "mpath": null,
52
+ "seo_title": null, // null = fall back to name
53
+ "seo_description": null, // null = fall back to description
54
+ "metadata": null,
55
+ "created_at": "2026-07-01T00:00:00.000Z",
56
+ "updated_at": "2026-07-01T00:00:00.000Z",
57
+ // only when include_descendants_tree=true:
58
+ "category_children": [ /* same shape, recursive */ ],
59
+ // only when include_ancestors_tree=true:
60
+ "parent_category": null
61
+ }
62
+ ],
63
+ "count": 1, "offset": 0, "limit": 50
64
+ }
65
+ ```
66
+
67
+ - **Working curl** — the seeded catalog carries the `apparel` category:
68
+
69
+ ```bash
70
+ CATEGORIES=$(curl -sf "$BASE/api/store/product-categories?handle=apparel" \
71
+ -H "x-client-id: $CLIENT_ID")
72
+ echo "$CATEGORIES" | grep -q '"product_categories"'
73
+ echo "$CATEGORIES" | grep -q '"handle":"apparel"'
74
+ CAT_ID=$(echo "$CATEGORIES" | grep -o '"id":"pcat_[^"]*"' | head -1 | cut -d'"' -f4)
75
+ test -n "$CAT_ID"
76
+ ```
77
+
78
+ - **Errors** — 400 `missing_client_id`, 400 `validation_failed`.
79
+ - **SDK** — `listCategories(client, query?)`.
80
+ - **Components** — category navigation tree, breadcrumbs.
81
+ - **Settings** — Admin → Categories: `is_active` / `is_internal` flags,
82
+ rank ordering, SEO overrides.
83
+
84
+ ---
85
+
86
+ ## GET /api/store/product-categories/:id
87
+
88
+ - **Purpose** — retrieve one category, optionally with its tree (category
89
+ landing page + breadcrumbs in one call).
90
+ - **Auth** — anon: `x-client-id` required.
91
+ - **Request** — query `{ include_ancestors_tree?, include_descendants_tree? }`.
92
+ - **Response** — `{ "product_category": { ... } }` (tree fields only when
93
+ requested; trees contain visible categories only).
94
+ - **Working curl**
95
+
96
+ ```bash
97
+ CATEGORY=$(curl -sf \
98
+ "$BASE/api/store/product-categories/$CAT_ID?include_descendants_tree=true" \
99
+ -H "x-client-id: $CLIENT_ID")
100
+ echo "$CATEGORY" | grep -q '"product_category"'
101
+ echo "$CATEGORY" | grep -q '"category_children"'
102
+ ```
103
+
104
+ - **Errors** — 404 `not_found` (unknown, deleted, or inactive/internal —
105
+ RLS hides them even by id).
106
+
107
+ ```bash
108
+ STATUS=$(curl -s -o /dev/null -w '%{http_code}' \
109
+ "$BASE/api/store/product-categories/pcat_doesnotexist$RUN" \
110
+ -H "x-client-id: $CLIENT_ID")
111
+ test "$STATUS" = 404
112
+ ```
113
+
114
+ - **SDK** — `retrieveCategory(client, categoryId, query?)`.
115
+ - **Components** — category page header, breadcrumbs.
116
+ - **Settings** — as the list.
117
+
118
+ ---
119
+
120
+ ## GET /api/store/product-tags
121
+
122
+ - **Purpose** — tag list (filter chips). Use the returned ids as `tag_id`
123
+ filters on `/products` and `/products/search`.
124
+ - **Auth** — anon: `x-client-id` required.
125
+ - **Request** — query `{ q?, value?, limit?, offset? }` (`q` substring,
126
+ `value` exact; `limit` 1–200, default 50).
127
+ - **Response** — ordered by value:
128
+
129
+ ```jsonc
130
+ {
131
+ "product_tags": [
132
+ { "id": "ptag_…", "value": "summer", "metadata": null,
133
+ "created_at": "2026-07-01T00:00:00.000Z", "updated_at": "2026-07-01T00:00:00.000Z" }
134
+ ],
135
+ "count": 1, "offset": 0, "limit": 50
136
+ }
137
+ ```
138
+
139
+ - **Working curl** — the dev tenant seeds no tags, so this asserts the
140
+ envelope (the shape contract), not contents:
141
+
142
+ ```bash
143
+ TAGS=$(curl -sf "$BASE/api/store/product-tags" -H "x-client-id: $CLIENT_ID")
144
+ echo "$TAGS" | grep -q '"product_tags"'
145
+ echo "$TAGS" | grep -q '"count"'
146
+ ```
147
+
148
+ - **Errors** — 400 `missing_client_id`, 400 `validation_failed`;
149
+ retrieve (`GET /api/store/product-tags/:id` → `{ "product_tag": …}`) 404s
150
+ on unknown ids:
151
+
152
+ ```bash
153
+ STATUS=$(curl -s -o /dev/null -w '%{http_code}' \
154
+ "$BASE/api/store/product-tags/ptag_doesnotexist$RUN" -H "x-client-id: $CLIENT_ID")
155
+ test "$STATUS" = 404
156
+ ```
157
+
158
+ - **SDK** — `listProductTags(client, query?)` /
159
+ `retrieveProductTag(client, tagId)`.
160
+ - **Components** — filter sidebar chips.
161
+ - **Settings** — tags are authored on products in admin.
162
+
163
+ ---
164
+
165
+ ## GET /api/store/product-types
166
+
167
+ - **Purpose** — type list; ids feed `type_id` filters on listings/search.
168
+ - **Auth** — anon: `x-client-id` required.
169
+ - **Request** — query `{ q?, value?, limit?, offset? }` (same semantics as
170
+ tags).
171
+ - **Response** — `{ product_types, count, offset, limit }`, rows
172
+ `{ id, value, metadata, created_at, updated_at }`, ordered by value.
173
+ - **Working curl**
174
+
175
+ ```bash
176
+ TYPES=$(curl -sf "$BASE/api/store/product-types" -H "x-client-id: $CLIENT_ID")
177
+ echo "$TYPES" | grep -q '"product_types"'
178
+ echo "$TYPES" | grep -q '"count"'
179
+ ```
180
+
181
+ - **Errors** — 400 `missing_client_id`, 400 `validation_failed`; retrieve
182
+ (`GET /api/store/product-types/:id` → `{ "product_type": …}`) 404s on
183
+ unknown ids:
184
+
185
+ ```bash
186
+ STATUS=$(curl -s -o /dev/null -w '%{http_code}' \
187
+ "$BASE/api/store/product-types/ptyp_doesnotexist$RUN" -H "x-client-id: $CLIENT_ID")
188
+ test "$STATUS" = 404
189
+ ```
190
+
191
+ - **SDK** — `listProductTypes(client, query?)` /
192
+ `retrieveProductType(client, typeId)`.
193
+ - **Components** — filter sidebar.
194
+ - **Settings** — types are authored on products in admin.