@withwiz/gallery 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 (77) hide show
  1. package/README.ko.md +484 -0
  2. package/README.md +484 -0
  3. package/dist/chunk-B3MQL6ZR.mjs +79 -0
  4. package/dist/chunk-B3MQL6ZR.mjs.map +1 -0
  5. package/dist/chunk-BC3TPJQY.mjs +122 -0
  6. package/dist/chunk-BC3TPJQY.mjs.map +1 -0
  7. package/dist/chunk-BTLELFKC.mjs +11 -0
  8. package/dist/chunk-BTLELFKC.mjs.map +1 -0
  9. package/dist/chunk-GDUGKVDQ.mjs +50 -0
  10. package/dist/chunk-GDUGKVDQ.mjs.map +1 -0
  11. package/dist/chunk-GFOWZGJX.js +50 -0
  12. package/dist/chunk-GFOWZGJX.js.map +1 -0
  13. package/dist/chunk-ILSZPLME.js +47 -0
  14. package/dist/chunk-ILSZPLME.js.map +1 -0
  15. package/dist/chunk-M7CCTDUG.js +122 -0
  16. package/dist/chunk-M7CCTDUG.js.map +1 -0
  17. package/dist/chunk-WVRTM6E7.js +19 -0
  18. package/dist/chunk-WVRTM6E7.js.map +1 -0
  19. package/dist/chunk-XLPMNJJV.js +11 -0
  20. package/dist/chunk-XLPMNJJV.js.map +1 -0
  21. package/dist/chunk-XSPWM4DD.js +79 -0
  22. package/dist/chunk-XSPWM4DD.js.map +1 -0
  23. package/dist/chunk-YUMB3GBN.mjs +47 -0
  24. package/dist/chunk-YUMB3GBN.mjs.map +1 -0
  25. package/dist/chunk-ZEZCUJJD.mjs +19 -0
  26. package/dist/chunk-ZEZCUJJD.mjs.map +1 -0
  27. package/dist/components/gallery.css +1074 -0
  28. package/dist/components/index.d.mts +156 -0
  29. package/dist/components/index.d.ts +156 -0
  30. package/dist/components/index.js +1215 -0
  31. package/dist/components/index.js.map +1 -0
  32. package/dist/components/index.mjs +1215 -0
  33. package/dist/components/index.mjs.map +1 -0
  34. package/dist/errors-B9gzUsX-.d.ts +39 -0
  35. package/dist/errors-DYrlDCzP.d.mts +39 -0
  36. package/dist/gallery.css +1074 -0
  37. package/dist/hooks/index.d.mts +65 -0
  38. package/dist/hooks/index.d.ts +65 -0
  39. package/dist/hooks/index.js +14 -0
  40. package/dist/hooks/index.js.map +1 -0
  41. package/dist/hooks/index.mjs +14 -0
  42. package/dist/hooks/index.mjs.map +1 -0
  43. package/dist/index.d.mts +17 -0
  44. package/dist/index.d.ts +17 -0
  45. package/dist/index.js +37 -0
  46. package/dist/index.js.map +1 -0
  47. package/dist/index.mjs +37 -0
  48. package/dist/index.mjs.map +1 -0
  49. package/dist/presets/ballet.d.mts +64 -0
  50. package/dist/presets/ballet.d.ts +64 -0
  51. package/dist/presets/ballet.js +162 -0
  52. package/dist/presets/ballet.js.map +1 -0
  53. package/dist/presets/ballet.mjs +162 -0
  54. package/dist/presets/ballet.mjs.map +1 -0
  55. package/dist/server/index.d.mts +157 -0
  56. package/dist/server/index.d.ts +157 -0
  57. package/dist/server/index.js +619 -0
  58. package/dist/server/index.js.map +1 -0
  59. package/dist/server/index.mjs +619 -0
  60. package/dist/server/index.mjs.map +1 -0
  61. package/dist/types/index.d.mts +137 -0
  62. package/dist/types/index.d.ts +137 -0
  63. package/dist/types/index.js +1 -0
  64. package/dist/types/index.js.map +1 -0
  65. package/dist/types/index.mjs +1 -0
  66. package/dist/types/index.mjs.map +1 -0
  67. package/dist/useGalleryLightbox-BYzPyBYB.d.mts +22 -0
  68. package/dist/useGalleryLightbox-BYzPyBYB.d.ts +22 -0
  69. package/dist/validators/index.d.mts +68 -0
  70. package/dist/validators/index.d.ts +68 -0
  71. package/dist/validators/index.js +7 -0
  72. package/dist/validators/index.js.map +1 -0
  73. package/dist/validators/index.mjs +7 -0
  74. package/dist/validators/index.mjs.map +1 -0
  75. package/package.json +85 -0
  76. package/prisma/gallery.schema.prisma +62 -0
  77. package/prisma/migrations/2026-05-24-enum-to-table.sql +65 -0
@@ -0,0 +1,619 @@
1
+ "use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } } function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]; let i = 1; while (i < ops.length) { const op = ops[i]; const fn = ops[i + 1]; i += 2; if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) { return undefined; } if (op === 'access' || op === 'optionalAccess') { lastAccessLHS = value; value = fn(value); } else if (op === 'call' || op === 'optionalCall') { value = fn((...args) => value.call(lastAccessLHS, ...args)); lastAccessLHS = undefined; } } return value; }
2
+
3
+
4
+
5
+
6
+
7
+ var _chunkGFOWZGJXjs = require('../chunk-GFOWZGJX.js');
8
+
9
+
10
+
11
+ var _chunkWVRTM6E7js = require('../chunk-WVRTM6E7.js');
12
+
13
+
14
+ var _chunkILSZPLMEjs = require('../chunk-ILSZPLME.js');
15
+
16
+ // src/services/helpers.ts
17
+ function buildPaginatedResult(items, page, limit, total) {
18
+ const totalPages = total === 0 ? 0 : Math.ceil(total / limit);
19
+ return {
20
+ items,
21
+ meta: {
22
+ page,
23
+ limit,
24
+ total,
25
+ totalPages,
26
+ hasNext: page < totalPages,
27
+ hasPrev: page > 1
28
+ }
29
+ };
30
+ }
31
+
32
+ // src/services/category-service.ts
33
+ function createCategoryService(config) {
34
+ const categoryDelegate = () => config.prisma[_nullishCoalesce(config.categoryModelName, () => ( "galleryCategory"))];
35
+ const galleryDelegate = () => config.prisma[_nullishCoalesce(config.modelName, () => ( "gallery"))];
36
+ async function list(opts) {
37
+ const where = _optionalChain([opts, 'optionalAccess', _ => _.isActive]) !== void 0 ? { isActive: opts.isActive } : void 0;
38
+ const rows = await categoryDelegate().findMany({
39
+ ...where ? { where } : {},
40
+ orderBy: [{ sortOrder: "asc" }, { createdAt: "asc" }]
41
+ });
42
+ return rows;
43
+ }
44
+ async function getBySlug(slug) {
45
+ const row = await categoryDelegate().findUnique({ where: { slug } });
46
+ return _nullishCoalesce(row, () => ( null));
47
+ }
48
+ async function getById(id) {
49
+ const row = await categoryDelegate().findUnique({ where: { id } });
50
+ return _nullishCoalesce(row, () => ( null));
51
+ }
52
+ async function create(data) {
53
+ const row = await categoryDelegate().create({ data });
54
+ return row;
55
+ }
56
+ async function update(id, data) {
57
+ const row = await categoryDelegate().update({ where: { id }, data });
58
+ return row;
59
+ }
60
+ async function remove(id) {
61
+ const inUse = await galleryDelegate().count({ where: { categoryId: id } });
62
+ if (inUse > 0) {
63
+ throw new (0, _chunkGFOWZGJXjs.CategoryInUseError)(id, inUse);
64
+ }
65
+ await categoryDelegate().delete({ where: { id } });
66
+ }
67
+ async function reorder(ids) {
68
+ const ops = ids.map(
69
+ (id, idx) => categoryDelegate().update({ where: { id }, data: { sortOrder: idx } })
70
+ );
71
+ await config.prisma.$transaction(ops);
72
+ }
73
+ return { list, getBySlug, getById, create, update, remove, reorder };
74
+ }
75
+
76
+ // src/services/index.ts
77
+ function createGalleryService(config) {
78
+ const galleryDelegate = () => config.prisma[_nullishCoalesce(config.modelName, () => ( "gallery"))];
79
+ const baseInclude = { category: true };
80
+ function orderByFor(sortBy) {
81
+ switch (sortBy) {
82
+ case "sortOrder":
83
+ return [{ sortOrder: "asc" }, { createdAt: "desc" }];
84
+ case "caption":
85
+ return { caption: "asc" };
86
+ case "createdAt":
87
+ case "updatedAt":
88
+ return { [sortBy]: "desc" };
89
+ }
90
+ }
91
+ async function listFeatured(limit) {
92
+ const rows = await galleryDelegate().findMany({
93
+ where: { published: true, featured: true },
94
+ include: baseInclude,
95
+ orderBy: [{ sortOrder: "asc" }, { createdAt: "desc" }],
96
+ ...limit ? { take: limit } : {}
97
+ });
98
+ return rows;
99
+ }
100
+ async function listPublished(limit) {
101
+ const rows = await galleryDelegate().findMany({
102
+ where: { published: true },
103
+ include: baseInclude,
104
+ orderBy: [{ sortOrder: "asc" }, { createdAt: "desc" }],
105
+ ...limit ? { take: limit } : {}
106
+ });
107
+ return rows;
108
+ }
109
+ async function listPublishedByCategory(categorySlug, limit) {
110
+ const rows = await galleryDelegate().findMany({
111
+ where: { published: true, category: { slug: categorySlug } },
112
+ include: baseInclude,
113
+ orderBy: [{ sortOrder: "asc" }, { createdAt: "desc" }],
114
+ ...limit ? { take: limit } : {}
115
+ });
116
+ return rows;
117
+ }
118
+ async function listAll(opts) {
119
+ const page = _nullishCoalesce(opts.page, () => ( 1));
120
+ const limit = _nullishCoalesce(opts.limit, () => ( 20));
121
+ const sortBy = _nullishCoalesce(opts.sortBy, () => ( "sortOrder"));
122
+ const skip = (page - 1) * limit;
123
+ const where = {};
124
+ if (opts.categoryId) where.categoryId = opts.categoryId;
125
+ if (opts.published !== void 0) where.published = opts.published;
126
+ if (opts.search) where.caption = { contains: opts.search, mode: "insensitive" };
127
+ const [items, total] = await Promise.all([
128
+ galleryDelegate().findMany({
129
+ where,
130
+ include: baseInclude,
131
+ orderBy: orderByFor(sortBy),
132
+ skip,
133
+ take: limit
134
+ }),
135
+ galleryDelegate().count({ where })
136
+ ]);
137
+ return buildPaginatedResult(items, page, limit, total);
138
+ }
139
+ async function getById(id) {
140
+ const row = await galleryDelegate().findUnique({
141
+ where: { id },
142
+ include: baseInclude
143
+ });
144
+ return _nullishCoalesce(row, () => ( null));
145
+ }
146
+ async function create(data, authorId) {
147
+ const row = await galleryDelegate().create({
148
+ data: {
149
+ imageUrl: data.imageUrl,
150
+ imageKey: _nullishCoalesce(data.imageKey, () => ( null)),
151
+ caption: _nullishCoalesce(data.caption, () => ( null)),
152
+ categoryId: data.categoryId,
153
+ sortOrder: _nullishCoalesce(data.sortOrder, () => ( 0)),
154
+ featured: _nullishCoalesce(data.featured, () => ( false)),
155
+ published: _nullishCoalesce(data.published, () => ( false)),
156
+ authorId
157
+ },
158
+ include: baseInclude
159
+ });
160
+ return row;
161
+ }
162
+ async function createMany(items, authorId) {
163
+ const result = await galleryDelegate().createMany({
164
+ data: items.map((it) => ({
165
+ imageUrl: it.imageUrl,
166
+ imageKey: _nullishCoalesce(it.imageKey, () => ( null)),
167
+ caption: _nullishCoalesce(it.caption, () => ( null)),
168
+ categoryId: it.categoryId,
169
+ sortOrder: _nullishCoalesce(it.sortOrder, () => ( 0)),
170
+ featured: _nullishCoalesce(it.featured, () => ( false)),
171
+ published: _nullishCoalesce(it.published, () => ( false)),
172
+ authorId
173
+ }))
174
+ });
175
+ return { count: result.count };
176
+ }
177
+ async function update(id, data) {
178
+ const patch = {};
179
+ if (data.imageUrl !== void 0) patch.imageUrl = data.imageUrl;
180
+ if (data.imageKey !== void 0) patch.imageKey = _nullishCoalesce(data.imageKey, () => ( null));
181
+ if (data.caption !== void 0) patch.caption = _nullishCoalesce(data.caption, () => ( null));
182
+ if (data.categoryId !== void 0) patch.categoryId = data.categoryId;
183
+ if (data.sortOrder !== void 0) patch.sortOrder = data.sortOrder;
184
+ if (data.featured !== void 0) patch.featured = data.featured;
185
+ if (data.published !== void 0) patch.published = data.published;
186
+ const row = await galleryDelegate().update({
187
+ where: { id },
188
+ data: patch,
189
+ include: baseInclude
190
+ });
191
+ return row;
192
+ }
193
+ async function remove(id) {
194
+ const storageEnabled = _optionalChain([config, 'access', _2 => _2.storage, 'optionalAccess', _3 => _3.isEnabled, 'optionalCall', _4 => _4()]) === true;
195
+ let imageKey = null;
196
+ if (storageEnabled) {
197
+ const row = await galleryDelegate().findUnique({
198
+ where: { id },
199
+ select: { imageKey: true }
200
+ });
201
+ imageKey = _nullishCoalesce(_optionalChain([row, 'optionalAccess', _5 => _5.imageKey]), () => ( null));
202
+ }
203
+ await galleryDelegate().delete({ where: { id } });
204
+ if (storageEnabled && imageKey && config.storage) {
205
+ const keys = config.storage.collectKeys(imageKey);
206
+ if (keys.length > 0) await config.storage.deleteKeys(keys);
207
+ }
208
+ }
209
+ async function removeMany(ids) {
210
+ const storageEnabled = _optionalChain([config, 'access', _6 => _6.storage, 'optionalAccess', _7 => _7.isEnabled, 'optionalCall', _8 => _8()]) === true;
211
+ let imageKeys = [];
212
+ if (storageEnabled) {
213
+ const rows = await galleryDelegate().findMany({
214
+ where: { id: { in: ids } },
215
+ select: { imageKey: true }
216
+ });
217
+ imageKeys = rows.map((r) => r.imageKey).filter((k) => typeof k === "string" && k.length > 0);
218
+ }
219
+ const result = await galleryDelegate().deleteMany({ where: { id: { in: ids } } });
220
+ if (storageEnabled && imageKeys.length > 0 && config.storage) {
221
+ const allKeys = imageKeys.flatMap((k) => config.storage.collectKeys(k));
222
+ const uniqueKeys = [...new Set(allKeys)];
223
+ if (uniqueKeys.length > 0) await config.storage.deleteKeys(uniqueKeys);
224
+ }
225
+ return { count: result.count };
226
+ }
227
+ async function bulkUpdatePublished(ids, published) {
228
+ const result = await galleryDelegate().updateMany({
229
+ where: { id: { in: ids } },
230
+ data: { published, updatedAt: /* @__PURE__ */ new Date() }
231
+ });
232
+ return { count: result.count };
233
+ }
234
+ async function bulkUpdateFeatured(ids, featured) {
235
+ const result = await galleryDelegate().updateMany({
236
+ where: { id: { in: ids } },
237
+ data: { featured, updatedAt: /* @__PURE__ */ new Date() }
238
+ });
239
+ return { count: result.count };
240
+ }
241
+ async function togglePublish(id) {
242
+ const current = await galleryDelegate().findUnique({
243
+ where: { id },
244
+ select: { published: true }
245
+ });
246
+ if (!current) {
247
+ throw new (0, _chunkGFOWZGJXjs.GalleryNotFoundError)(id);
248
+ }
249
+ const row = await galleryDelegate().update({
250
+ where: { id },
251
+ data: { published: !current.published },
252
+ include: baseInclude
253
+ });
254
+ return row;
255
+ }
256
+ async function count(opts) {
257
+ const where = _optionalChain([opts, 'optionalAccess', _9 => _9.published]) !== void 0 ? { published: opts.published } : void 0;
258
+ const n = await galleryDelegate().count(where ? { where } : {});
259
+ return n;
260
+ }
261
+ async function listRecent(limit) {
262
+ const rows = await galleryDelegate().findMany({
263
+ include: baseInclude,
264
+ orderBy: { createdAt: "desc" },
265
+ take: limit
266
+ });
267
+ return rows;
268
+ }
269
+ return {
270
+ listFeatured,
271
+ listPublished,
272
+ listPublishedByCategory,
273
+ listAll,
274
+ getById,
275
+ create,
276
+ createMany,
277
+ update,
278
+ remove,
279
+ removeMany,
280
+ bulkUpdatePublished,
281
+ bulkUpdateFeatured,
282
+ togglePublish,
283
+ count,
284
+ listRecent
285
+ };
286
+ }
287
+
288
+ // src/server/route-handlers.ts
289
+ var _server = require('next/server');
290
+
291
+ // src/utils/api-helpers.ts
292
+
293
+ function parsePagination(req) {
294
+ const { searchParams } = new URL(req.url);
295
+ const rawPage = Number.parseInt(_nullishCoalesce(searchParams.get("page"), () => ( "1")), 10);
296
+ const rawLimit = Number.parseInt(_nullishCoalesce(searchParams.get("limit"), () => ( "20")), 10);
297
+ const page = Number.isFinite(rawPage) && rawPage > 0 ? rawPage : 1;
298
+ const limit = Number.isFinite(rawLimit) && rawLimit > 0 ? Math.min(rawLimit, 100) : 20;
299
+ return { page, limit };
300
+ }
301
+ function getSearchParam(req, key) {
302
+ const { searchParams } = new URL(req.url);
303
+ const v = searchParams.get(key);
304
+ return _nullishCoalesce(v, () => ( void 0));
305
+ }
306
+ function validateAndParse(schema, data) {
307
+ const parsed = schema.safeParse(data);
308
+ if (parsed.success) return { success: true, data: parsed.data };
309
+ return {
310
+ success: false,
311
+ response: _server.NextResponse.json(
312
+ { success: false, error: "ValidationError", details: parsed.error.issues },
313
+ { status: 400 }
314
+ )
315
+ };
316
+ }
317
+ function validateIds(input) {
318
+ if (!Array.isArray(input) || input.length === 0) {
319
+ return {
320
+ valid: false,
321
+ response: _server.NextResponse.json(
322
+ { success: false, error: "InvalidIds", message: "ids must be a non-empty array" },
323
+ { status: 400 }
324
+ )
325
+ };
326
+ }
327
+ const ids = input.filter((x) => typeof x === "string" && x.length > 0);
328
+ if (ids.length === 0) {
329
+ return {
330
+ valid: false,
331
+ response: _server.NextResponse.json(
332
+ { success: false, error: "InvalidIds", message: "ids array contains no valid strings" },
333
+ { status: 400 }
334
+ )
335
+ };
336
+ }
337
+ return { valid: true, ids };
338
+ }
339
+ function parseSortKey(searchParams, allowed, fallback) {
340
+ const raw = searchParams.get("sortBy");
341
+ return raw && allowed.includes(raw) ? raw : fallback;
342
+ }
343
+
344
+ // src/server/route-handlers.ts
345
+ var VALID_SORT_KEYS = [
346
+ "sortOrder",
347
+ "createdAt",
348
+ "updatedAt",
349
+ "caption"
350
+ ];
351
+ function jsonError(message, status, error) {
352
+ return _server.NextResponse.json(
353
+ { success: false, error: _nullishCoalesce(error, () => ( "Error")), message },
354
+ { status }
355
+ );
356
+ }
357
+ function callRevalidate(config) {
358
+ if (!config.revalidate || !config.revalidatePaths) return;
359
+ for (const p of config.revalidatePaths) {
360
+ config.revalidate(p);
361
+ }
362
+ }
363
+ function getAuthorId(config, ctx) {
364
+ if (config.authorIdFromContext) {
365
+ try {
366
+ const id = config.authorIdFromContext(ctx);
367
+ return id || null;
368
+ } catch (e) {
369
+ return null;
370
+ }
371
+ }
372
+ return _nullishCoalesce(_optionalChain([ctx, 'access', _10 => _10.user, 'optionalAccess', _11 => _11.id]), () => ( null));
373
+ }
374
+ function getRouteId(ctx) {
375
+ const id = _optionalChain([ctx, 'access', _12 => _12.params, 'optionalAccess', _13 => _13.id]);
376
+ return typeof id === "string" && id.length > 0 ? id : null;
377
+ }
378
+ function createGalleryRoutes(config) {
379
+ const service = createGalleryService(config);
380
+ const categoryService = createCategoryService(config);
381
+ const schemas = _chunkILSZPLMEjs.createGallerySchemas.call(void 0, {
382
+ batchMax: config.limits.batchMax,
383
+ captionMaxLength: _nullishCoalesce(config.limits.captionMaxLength, () => ( 200))
384
+ });
385
+ const collectionGET = config.apiWrapper(async (ctx) => {
386
+ const { page, limit } = parsePagination(ctx.request);
387
+ const { searchParams } = new URL(ctx.request.url);
388
+ const categoryId = getSearchParam(ctx.request, "categoryId");
389
+ const publishedRaw = getSearchParam(ctx.request, "published");
390
+ const search = getSearchParam(ctx.request, "search");
391
+ const sortBy = parseSortKey(
392
+ searchParams,
393
+ VALID_SORT_KEYS,
394
+ "sortOrder"
395
+ );
396
+ const published = publishedRaw === "true" ? true : publishedRaw === "false" ? false : void 0;
397
+ const result = await service.listAll({
398
+ page,
399
+ limit,
400
+ categoryId,
401
+ published,
402
+ search,
403
+ sortBy
404
+ });
405
+ return _server.NextResponse.json({ success: true, data: result });
406
+ });
407
+ const collectionPOST = config.apiWrapper(async (ctx) => {
408
+ const authorId = getAuthorId(config, ctx);
409
+ if (!authorId) return jsonError("authentication required", 401, "Unauthorized");
410
+ const body = await ctx.request.json();
411
+ const validation = validateAndParse(schemas.CreateGallerySchema, body);
412
+ if (!validation.success) return validation.response;
413
+ const item = await service.create(validation.data, authorId);
414
+ callRevalidate(config);
415
+ return _server.NextResponse.json({ success: true, data: item }, { status: 201 });
416
+ });
417
+ const collectionDELETE = config.apiWrapper(async (ctx) => {
418
+ const body = await ctx.request.json();
419
+ const check = validateIds(_optionalChain([body, 'optionalAccess', _14 => _14.ids]));
420
+ if (!check.valid) return check.response;
421
+ const { count } = await service.removeMany(check.ids);
422
+ callRevalidate(config);
423
+ return _server.NextResponse.json({ success: true, data: { count } });
424
+ });
425
+ const itemGET = config.apiWrapper(async (ctx) => {
426
+ const id = getRouteId(ctx);
427
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
428
+ const item = await service.getById(id);
429
+ if (!item) return jsonError("Gallery item not found", 404, "NotFound");
430
+ return _server.NextResponse.json({ success: true, data: item });
431
+ });
432
+ const itemPUT = config.apiWrapper(async (ctx) => {
433
+ const id = getRouteId(ctx);
434
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
435
+ const body = await ctx.request.json();
436
+ const validation = validateAndParse(schemas.UpdateGallerySchema, body);
437
+ if (!validation.success) return validation.response;
438
+ const existing = await service.getById(id);
439
+ if (!existing) return jsonError("Gallery item not found", 404, "NotFound");
440
+ if (_optionalChain([config, 'access', _15 => _15.permissions, 'optionalAccess', _16 => _16.canEdit])) {
441
+ const ok = config.permissions.canEdit(ctx, { authorId: existing.authorId });
442
+ if (!ok) return jsonError("forbidden", 403, "Forbidden");
443
+ }
444
+ const item = await service.update(id, validation.data);
445
+ callRevalidate(config);
446
+ return _server.NextResponse.json({ success: true, data: item });
447
+ });
448
+ const itemDELETE = config.apiWrapper(async (ctx) => {
449
+ const id = getRouteId(ctx);
450
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
451
+ if (_optionalChain([config, 'access', _17 => _17.permissions, 'optionalAccess', _18 => _18.canDelete])) {
452
+ const existing = await service.getById(id);
453
+ if (!existing) return jsonError("Gallery item not found", 404, "NotFound");
454
+ const ok = config.permissions.canDelete(ctx, {
455
+ authorId: existing.authorId
456
+ });
457
+ if (!ok) return jsonError("forbidden", 403, "Forbidden");
458
+ }
459
+ await service.remove(id);
460
+ callRevalidate(config);
461
+ return new (0, _server.NextResponse)(null, { status: 204 });
462
+ });
463
+ const publishTogglePATCH = config.apiWrapper(async (ctx) => {
464
+ const id = getRouteId(ctx);
465
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
466
+ if (_optionalChain([config, 'access', _19 => _19.permissions, 'optionalAccess', _20 => _20.canEdit])) {
467
+ const existing = await service.getById(id);
468
+ if (!existing) return jsonError("Gallery item not found", 404, "NotFound");
469
+ const ok = config.permissions.canEdit(ctx, {
470
+ authorId: existing.authorId
471
+ });
472
+ if (!ok) return jsonError("forbidden", 403, "Forbidden");
473
+ }
474
+ try {
475
+ const result = await service.togglePublish(id);
476
+ callRevalidate(config);
477
+ return _server.NextResponse.json({ success: true, data: result });
478
+ } catch (err) {
479
+ if (err instanceof _chunkGFOWZGJXjs.GalleryNotFoundError) {
480
+ return jsonError("Gallery item not found", 404, "NotFound");
481
+ }
482
+ throw err;
483
+ }
484
+ });
485
+ const bulkPOST = config.apiWrapper(async (ctx) => {
486
+ const authorId = getAuthorId(config, ctx);
487
+ if (!authorId) return jsonError("authentication required", 401, "Unauthorized");
488
+ const body = await ctx.request.json();
489
+ const validation = validateAndParse(schemas.BatchCreateGallerySchema, body);
490
+ if (!validation.success) return validation.response;
491
+ const result = await service.createMany(validation.data.items, authorId);
492
+ callRevalidate(config);
493
+ return _server.NextResponse.json(
494
+ { success: true, data: result },
495
+ { status: 201 }
496
+ );
497
+ });
498
+ const bulkPATCH = config.apiWrapper(async (ctx) => {
499
+ const body = await ctx.request.json();
500
+ const validation = validateAndParse(schemas.BulkUpdateSchema, body);
501
+ if (!validation.success) return validation.response;
502
+ const { ids, published, featured } = validation.data;
503
+ let count = 0;
504
+ if (published !== void 0) {
505
+ const r = await service.bulkUpdatePublished(ids, published);
506
+ count = r.count;
507
+ }
508
+ if (featured !== void 0) {
509
+ const r = await service.bulkUpdateFeatured(ids, featured);
510
+ count = r.count;
511
+ }
512
+ callRevalidate(config);
513
+ return _server.NextResponse.json({ success: true, data: { count } });
514
+ });
515
+ const categoryCollectionGET = config.apiWrapper(async (ctx) => {
516
+ const isActiveRaw = getSearchParam(ctx.request, "isActive");
517
+ const isActive = isActiveRaw === "true" ? true : isActiveRaw === "false" ? false : void 0;
518
+ const items = await categoryService.list(
519
+ isActive === void 0 ? void 0 : { isActive }
520
+ );
521
+ return _server.NextResponse.json({ success: true, data: items });
522
+ });
523
+ const categoryCollectionPOST = config.apiWrapper(async (ctx) => {
524
+ const body = await ctx.request.json();
525
+ const validation = validateAndParse(schemas.CreateCategorySchema, body);
526
+ if (!validation.success) return validation.response;
527
+ const item = await categoryService.create(validation.data);
528
+ callRevalidate(config);
529
+ return _server.NextResponse.json({ success: true, data: item }, { status: 201 });
530
+ });
531
+ const categoryItemGET = config.apiWrapper(async (ctx) => {
532
+ const id = getRouteId(ctx);
533
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
534
+ const item = await categoryService.getById(id);
535
+ if (!item) return jsonError("Category not found", 404, "NotFound");
536
+ return _server.NextResponse.json({ success: true, data: item });
537
+ });
538
+ const categoryItemPUT = config.apiWrapper(async (ctx) => {
539
+ const id = getRouteId(ctx);
540
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
541
+ const body = await ctx.request.json();
542
+ const validation = validateAndParse(schemas.UpdateCategorySchema, body);
543
+ if (!validation.success) return validation.response;
544
+ const existing = await categoryService.getById(id);
545
+ if (!existing) return jsonError("Category not found", 404, "NotFound");
546
+ const item = await categoryService.update(id, validation.data);
547
+ callRevalidate(config);
548
+ return _server.NextResponse.json({ success: true, data: item });
549
+ });
550
+ const categoryItemDELETE = config.apiWrapper(async (ctx) => {
551
+ const id = getRouteId(ctx);
552
+ if (!id) return jsonError("missing route param: id", 400, "InvalidParams");
553
+ try {
554
+ await categoryService.remove(id);
555
+ } catch (err) {
556
+ if (err instanceof _chunkGFOWZGJXjs.CategoryInUseError) {
557
+ return jsonError(err.message, 409, "CategoryInUse");
558
+ }
559
+ throw err;
560
+ }
561
+ callRevalidate(config);
562
+ return new (0, _server.NextResponse)(null, { status: 204 });
563
+ });
564
+ return {
565
+ collection: {
566
+ GET: collectionGET,
567
+ POST: collectionPOST,
568
+ DELETE: collectionDELETE
569
+ },
570
+ item: { GET: itemGET, PUT: itemPUT, DELETE: itemDELETE },
571
+ publishToggle: { PATCH: publishTogglePATCH },
572
+ bulk: { POST: bulkPOST, PATCH: bulkPATCH },
573
+ categoryCollection: {
574
+ GET: categoryCollectionGET,
575
+ POST: categoryCollectionPOST
576
+ },
577
+ categoryItem: {
578
+ GET: categoryItemGET,
579
+ PUT: categoryItemPUT,
580
+ DELETE: categoryItemDELETE
581
+ }
582
+ };
583
+ }
584
+
585
+ // src/server/loaders.ts
586
+ async function getGalleryItems(config, opts) {
587
+ const service = createGalleryService(config);
588
+ return service.listAll(opts);
589
+ }
590
+ async function getFeaturedGalleries(config, limit) {
591
+ const service = createGalleryService(config);
592
+ return service.listFeatured(limit);
593
+ }
594
+ async function getRecentGalleries(config, limit) {
595
+ const service = createGalleryService(config);
596
+ return service.listRecent(limit);
597
+ }
598
+ async function getGalleryCount(config, opts) {
599
+ const service = createGalleryService(config);
600
+ return service.count(opts);
601
+ }
602
+
603
+
604
+
605
+
606
+
607
+
608
+
609
+
610
+
611
+
612
+
613
+
614
+
615
+
616
+
617
+
618
+ exports.CategoryInUseError = _chunkGFOWZGJXjs.CategoryInUseError; exports.CategoryNotFoundError = _chunkGFOWZGJXjs.CategoryNotFoundError; exports.GalleryError = _chunkGFOWZGJXjs.GalleryError; exports.GalleryNotFoundError = _chunkGFOWZGJXjs.GalleryNotFoundError; exports.PermissionDeniedError = _chunkGFOWZGJXjs.PermissionDeniedError; exports.buildPaginatedResult = buildPaginatedResult; exports.createCategoryService = createCategoryService; exports.createGalleryRoutes = createGalleryRoutes; exports.createGalleryService = createGalleryService; exports.getFeaturedGalleries = getFeaturedGalleries; exports.getGalleryConfig = _chunkWVRTM6E7js.getGalleryConfig; exports.getGalleryCount = getGalleryCount; exports.getGalleryItems = getGalleryItems; exports.getRecentGalleries = getRecentGalleries; exports.setGalleryConfig = _chunkWVRTM6E7js.setGalleryConfig;
619
+ //# sourceMappingURL=index.js.map