@strapi/upload 5.48.0 → 5.48.1

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 (30) hide show
  1. package/dist/server/controllers/content-api.js +12 -0
  2. package/dist/server/controllers/content-api.js.map +1 -1
  3. package/dist/server/controllers/content-api.mjs +12 -0
  4. package/dist/server/controllers/content-api.mjs.map +1 -1
  5. package/dist/server/routes/content-api.js +15 -0
  6. package/dist/server/routes/content-api.js.map +1 -1
  7. package/dist/server/routes/content-api.mjs +15 -0
  8. package/dist/server/routes/content-api.mjs.map +1 -1
  9. package/dist/server/routes/validation/upload.js +28 -0
  10. package/dist/server/routes/validation/upload.js.map +1 -1
  11. package/dist/server/routes/validation/upload.mjs +28 -0
  12. package/dist/server/routes/validation/upload.mjs.map +1 -1
  13. package/dist/server/services/upload.js +89 -0
  14. package/dist/server/services/upload.js.map +1 -1
  15. package/dist/server/services/upload.mjs +90 -1
  16. package/dist/server/services/upload.mjs.map +1 -1
  17. package/dist/server/src/controllers/content-api.d.ts +1 -0
  18. package/dist/server/src/controllers/content-api.d.ts.map +1 -1
  19. package/dist/server/src/controllers/index.d.ts +1 -0
  20. package/dist/server/src/controllers/index.d.ts.map +1 -1
  21. package/dist/server/src/index.d.ts +5 -0
  22. package/dist/server/src/index.d.ts.map +1 -1
  23. package/dist/server/src/routes/content-api.d.ts.map +1 -1
  24. package/dist/server/src/routes/validation/upload.d.ts +45 -0
  25. package/dist/server/src/routes/validation/upload.d.ts.map +1 -1
  26. package/dist/server/src/services/index.d.ts +4 -0
  27. package/dist/server/src/services/index.d.ts.map +1 -1
  28. package/dist/server/src/services/upload.d.ts +5 -0
  29. package/dist/server/src/services/upload.d.ts.map +1 -1
  30. package/package.json +7 -7
@@ -40,6 +40,18 @@ var contentApi = (({ strapi })=>{
40
40
  const signedFiles = await utils.async.map(files, index.getService('file').signFileUrls);
41
41
  ctx.body = await sanitizeOutput(signedFiles, ctx);
42
42
  },
43
+ async findPage (ctx) {
44
+ await validateQuery(ctx.query, ctx);
45
+ const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);
46
+ const { results, pagination } = await index.getService('upload').findAndCountPage(sanitizedQuery);
47
+ const data = await sanitizeOutput(results, ctx);
48
+ ctx.body = {
49
+ data,
50
+ meta: {
51
+ pagination
52
+ }
53
+ };
54
+ },
43
55
  async findOne (ctx) {
44
56
  const { params: { id } } = ctx;
45
57
  await validateQuery(ctx.query, ctx);
@@ -1 +1 @@
1
- {"version":3,"file":"content-api.js","sources":["../../../server/src/controllers/content-api.ts"],"sourcesContent":["import _ from 'lodash';\nimport utils, { async, errors } from '@strapi/utils';\n\nimport type { Context } from 'koa';\nimport type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\nimport { FILE_MODEL_UID } from '../constants';\nimport { validateUploadBody } from './validation/content-api/upload';\nimport { FileInfo } from '../types';\nimport { prepareUploadRequest } from '../utils/mime-validation';\n\nconst { ValidationError } = utils.errors;\n\nexport default ({ strapi }: { strapi: Core.Strapi }) => {\n const sanitizeOutput = async (data: unknown | unknown[], ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth } = ctx.state;\n\n return strapi.contentAPI.sanitize.output(data, schema, { auth });\n };\n\n const validateQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.validate.query(data, schema, { auth, route });\n };\n\n const sanitizeQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.sanitize.query(data, schema, { auth, route });\n };\n\n return {\n async find(ctx: Context) {\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const files = await getService('upload').findMany(sanitizedQuery);\n\n const signedFiles = await async.map(files, getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async findOne(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const file = await getService('upload').findOne(id, sanitizedQuery.populate!);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async destroy(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n const file = await getService('upload').findOne(id);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n await getService('upload').remove(file);\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async updateFileInfo(ctx: Context) {\n const {\n query: { id },\n request: { body },\n } = ctx;\n const data = await validateUploadBody(body);\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const result = await getService('upload').updateFileInfo(id, data.fileInfo as any);\n\n const signedResult = await getService('file').signFileUrls(result);\n\n ctx.body = await sanitizeOutput(signedResult, ctx);\n },\n\n async replaceFile(ctx: Context) {\n const {\n query: { id },\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n // cannot replace with more than one file\n if (Array.isArray(filesInput)) {\n throw new ValidationError('Cannot replace a file with multiple ones');\n }\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const data = (await validateUploadBody(filteredBody)) as { fileInfo: FileInfo };\n\n const replacedFiles = await getService('upload').replace(id, { data, file: validFiles[0] });\n\n const signedFiles = await getService('file').signFileUrls(replacedFiles);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async uploadFiles(ctx: Context) {\n const {\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n const isMultipleFiles = validFiles.length > 1;\n const data: any = await validateUploadBody(filteredBody, isMultipleFiles);\n\n const apiUploadFolderService = getService('api-upload-folder');\n\n const apiUploadFolder = await apiUploadFolderService.getAPIUploadFolder();\n\n if (isMultipleFiles) {\n data.fileInfo = data.fileInfo || [];\n data.fileInfo = validFiles.map((_f, i) => ({\n ...data.fileInfo[i],\n folder: apiUploadFolder.id,\n }));\n } else {\n data.fileInfo = { ...data.fileInfo, folder: apiUploadFolder.id };\n }\n\n const uploadedFiles = await getService('upload').upload({\n data,\n files: validFiles,\n });\n\n const signedFiles = await async.map(uploadedFiles as any[], getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n ctx.status = 201;\n },\n\n // TODO: split into multiple endpoints\n async upload(ctx: Context) {\n const {\n query: { id },\n request: { files: { files } = {} },\n } = ctx;\n\n if (_.isEmpty(files) || (!Array.isArray(files) && files.size === 0)) {\n if (id) {\n return this.updateFileInfo(ctx);\n }\n\n throw new ValidationError('Files are empty');\n }\n\n await (id ? this.replaceFile : this.uploadFiles)(ctx);\n },\n };\n};\n"],"names":["ValidationError","utils","errors","strapi","sanitizeOutput","data","ctx","schema","getModel","FILE_MODEL_UID","auth","state","contentAPI","sanitize","output","validateQuery","route","validate","query","sanitizeQuery","find","sanitizedQuery","files","getService","findMany","signedFiles","async","map","signFileUrls","body","findOne","params","id","file","populate","notFound","signedFile","destroy","remove","updateFileInfo","request","validateUploadBody","result","fileInfo","signedResult","replaceFile","filesInput","validFiles","filteredBody","validationErrors","prepareUploadRequest","length","message","Array","isArray","replacedFiles","replace","uploadFiles","isMultipleFiles","apiUploadFolderService","apiUploadFolder","getAPIUploadFolder","_f","i","folder","uploadedFiles","upload","status","_","isEmpty","size"],"mappings":"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"}
1
+ {"version":3,"file":"content-api.js","sources":["../../../server/src/controllers/content-api.ts"],"sourcesContent":["import _ from 'lodash';\nimport utils, { async, errors } from '@strapi/utils';\n\nimport type { Context } from 'koa';\nimport type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\nimport { FILE_MODEL_UID } from '../constants';\nimport { validateUploadBody } from './validation/content-api/upload';\nimport { FileInfo } from '../types';\nimport { prepareUploadRequest } from '../utils/mime-validation';\n\nconst { ValidationError } = utils.errors;\n\nexport default ({ strapi }: { strapi: Core.Strapi }) => {\n const sanitizeOutput = async (data: unknown | unknown[], ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth } = ctx.state;\n\n return strapi.contentAPI.sanitize.output(data, schema, { auth });\n };\n\n const validateQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.validate.query(data, schema, { auth, route });\n };\n\n const sanitizeQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.sanitize.query(data, schema, { auth, route });\n };\n\n return {\n async find(ctx: Context) {\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const files = await getService('upload').findMany(sanitizedQuery);\n\n const signedFiles = await async.map(files, getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async findPage(ctx: Context) {\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const { results, pagination } = await getService('upload').findAndCountPage(sanitizedQuery);\n\n const data = await sanitizeOutput(results, ctx);\n\n ctx.body = { data, meta: { pagination } };\n },\n\n async findOne(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const file = await getService('upload').findOne(id, sanitizedQuery.populate!);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async destroy(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n const file = await getService('upload').findOne(id);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n await getService('upload').remove(file);\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async updateFileInfo(ctx: Context) {\n const {\n query: { id },\n request: { body },\n } = ctx;\n const data = await validateUploadBody(body);\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const result = await getService('upload').updateFileInfo(id, data.fileInfo as any);\n\n const signedResult = await getService('file').signFileUrls(result);\n\n ctx.body = await sanitizeOutput(signedResult, ctx);\n },\n\n async replaceFile(ctx: Context) {\n const {\n query: { id },\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n // cannot replace with more than one file\n if (Array.isArray(filesInput)) {\n throw new ValidationError('Cannot replace a file with multiple ones');\n }\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const data = (await validateUploadBody(filteredBody)) as { fileInfo: FileInfo };\n\n const replacedFiles = await getService('upload').replace(id, { data, file: validFiles[0] });\n\n const signedFiles = await getService('file').signFileUrls(replacedFiles);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async uploadFiles(ctx: Context) {\n const {\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n const isMultipleFiles = validFiles.length > 1;\n const data: any = await validateUploadBody(filteredBody, isMultipleFiles);\n\n const apiUploadFolderService = getService('api-upload-folder');\n\n const apiUploadFolder = await apiUploadFolderService.getAPIUploadFolder();\n\n if (isMultipleFiles) {\n data.fileInfo = data.fileInfo || [];\n data.fileInfo = validFiles.map((_f, i) => ({\n ...data.fileInfo[i],\n folder: apiUploadFolder.id,\n }));\n } else {\n data.fileInfo = { ...data.fileInfo, folder: apiUploadFolder.id };\n }\n\n const uploadedFiles = await getService('upload').upload({\n data,\n files: validFiles,\n });\n\n const signedFiles = await async.map(uploadedFiles as any[], getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n ctx.status = 201;\n },\n\n // TODO: split into multiple endpoints\n async upload(ctx: Context) {\n const {\n query: { id },\n request: { files: { files } = {} },\n } = ctx;\n\n if (_.isEmpty(files) || (!Array.isArray(files) && files.size === 0)) {\n if (id) {\n return this.updateFileInfo(ctx);\n }\n\n throw new ValidationError('Files are empty');\n }\n\n await (id ? this.replaceFile : this.uploadFiles)(ctx);\n },\n };\n};\n"],"names":["ValidationError","utils","errors","strapi","sanitizeOutput","data","ctx","schema","getModel","FILE_MODEL_UID","auth","state","contentAPI","sanitize","output","validateQuery","route","validate","query","sanitizeQuery","find","sanitizedQuery","files","getService","findMany","signedFiles","async","map","signFileUrls","body","findPage","results","pagination","findAndCountPage","meta","findOne","params","id","file","populate","notFound","signedFile","destroy","remove","updateFileInfo","request","validateUploadBody","result","fileInfo","signedResult","replaceFile","filesInput","validFiles","filteredBody","validationErrors","prepareUploadRequest","length","message","Array","isArray","replacedFiles","replace","uploadFiles","isMultipleFiles","apiUploadFolderService","apiUploadFolder","getAPIUploadFolder","_f","i","folder","uploadedFiles","upload","status","_","isEmpty","size"],"mappings":"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"}
@@ -38,6 +38,18 @@ var contentApi = (({ strapi })=>{
38
38
  const signedFiles = await async.map(files, getService('file').signFileUrls);
39
39
  ctx.body = await sanitizeOutput(signedFiles, ctx);
40
40
  },
41
+ async findPage (ctx) {
42
+ await validateQuery(ctx.query, ctx);
43
+ const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);
44
+ const { results, pagination } = await getService('upload').findAndCountPage(sanitizedQuery);
45
+ const data = await sanitizeOutput(results, ctx);
46
+ ctx.body = {
47
+ data,
48
+ meta: {
49
+ pagination
50
+ }
51
+ };
52
+ },
41
53
  async findOne (ctx) {
42
54
  const { params: { id } } = ctx;
43
55
  await validateQuery(ctx.query, ctx);
@@ -1 +1 @@
1
- {"version":3,"file":"content-api.mjs","sources":["../../../server/src/controllers/content-api.ts"],"sourcesContent":["import _ from 'lodash';\nimport utils, { async, errors } from '@strapi/utils';\n\nimport type { Context } from 'koa';\nimport type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\nimport { FILE_MODEL_UID } from '../constants';\nimport { validateUploadBody } from './validation/content-api/upload';\nimport { FileInfo } from '../types';\nimport { prepareUploadRequest } from '../utils/mime-validation';\n\nconst { ValidationError } = utils.errors;\n\nexport default ({ strapi }: { strapi: Core.Strapi }) => {\n const sanitizeOutput = async (data: unknown | unknown[], ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth } = ctx.state;\n\n return strapi.contentAPI.sanitize.output(data, schema, { auth });\n };\n\n const validateQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.validate.query(data, schema, { auth, route });\n };\n\n const sanitizeQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.sanitize.query(data, schema, { auth, route });\n };\n\n return {\n async find(ctx: Context) {\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const files = await getService('upload').findMany(sanitizedQuery);\n\n const signedFiles = await async.map(files, getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async findOne(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const file = await getService('upload').findOne(id, sanitizedQuery.populate!);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async destroy(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n const file = await getService('upload').findOne(id);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n await getService('upload').remove(file);\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async updateFileInfo(ctx: Context) {\n const {\n query: { id },\n request: { body },\n } = ctx;\n const data = await validateUploadBody(body);\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const result = await getService('upload').updateFileInfo(id, data.fileInfo as any);\n\n const signedResult = await getService('file').signFileUrls(result);\n\n ctx.body = await sanitizeOutput(signedResult, ctx);\n },\n\n async replaceFile(ctx: Context) {\n const {\n query: { id },\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n // cannot replace with more than one file\n if (Array.isArray(filesInput)) {\n throw new ValidationError('Cannot replace a file with multiple ones');\n }\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const data = (await validateUploadBody(filteredBody)) as { fileInfo: FileInfo };\n\n const replacedFiles = await getService('upload').replace(id, { data, file: validFiles[0] });\n\n const signedFiles = await getService('file').signFileUrls(replacedFiles);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async uploadFiles(ctx: Context) {\n const {\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n const isMultipleFiles = validFiles.length > 1;\n const data: any = await validateUploadBody(filteredBody, isMultipleFiles);\n\n const apiUploadFolderService = getService('api-upload-folder');\n\n const apiUploadFolder = await apiUploadFolderService.getAPIUploadFolder();\n\n if (isMultipleFiles) {\n data.fileInfo = data.fileInfo || [];\n data.fileInfo = validFiles.map((_f, i) => ({\n ...data.fileInfo[i],\n folder: apiUploadFolder.id,\n }));\n } else {\n data.fileInfo = { ...data.fileInfo, folder: apiUploadFolder.id };\n }\n\n const uploadedFiles = await getService('upload').upload({\n data,\n files: validFiles,\n });\n\n const signedFiles = await async.map(uploadedFiles as any[], getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n ctx.status = 201;\n },\n\n // TODO: split into multiple endpoints\n async upload(ctx: Context) {\n const {\n query: { id },\n request: { files: { files } = {} },\n } = ctx;\n\n if (_.isEmpty(files) || (!Array.isArray(files) && files.size === 0)) {\n if (id) {\n return this.updateFileInfo(ctx);\n }\n\n throw new ValidationError('Files are empty');\n }\n\n await (id ? this.replaceFile : this.uploadFiles)(ctx);\n },\n };\n};\n"],"names":["ValidationError","utils","errors","strapi","sanitizeOutput","data","ctx","schema","getModel","FILE_MODEL_UID","auth","state","contentAPI","sanitize","output","validateQuery","route","validate","query","sanitizeQuery","find","sanitizedQuery","files","getService","findMany","signedFiles","async","map","signFileUrls","body","findOne","params","id","file","populate","notFound","signedFile","destroy","remove","updateFileInfo","request","validateUploadBody","result","fileInfo","signedResult","replaceFile","filesInput","validFiles","filteredBody","validationErrors","prepareUploadRequest","length","message","Array","isArray","replacedFiles","replace","uploadFiles","isMultipleFiles","apiUploadFolderService","apiUploadFolder","getAPIUploadFolder","_f","i","folder","uploadedFiles","upload","status","_","isEmpty","size"],"mappings":"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"}
1
+ {"version":3,"file":"content-api.mjs","sources":["../../../server/src/controllers/content-api.ts"],"sourcesContent":["import _ from 'lodash';\nimport utils, { async, errors } from '@strapi/utils';\n\nimport type { Context } from 'koa';\nimport type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\nimport { FILE_MODEL_UID } from '../constants';\nimport { validateUploadBody } from './validation/content-api/upload';\nimport { FileInfo } from '../types';\nimport { prepareUploadRequest } from '../utils/mime-validation';\n\nconst { ValidationError } = utils.errors;\n\nexport default ({ strapi }: { strapi: Core.Strapi }) => {\n const sanitizeOutput = async (data: unknown | unknown[], ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth } = ctx.state;\n\n return strapi.contentAPI.sanitize.output(data, schema, { auth });\n };\n\n const validateQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.validate.query(data, schema, { auth, route });\n };\n\n const sanitizeQuery = async (data: Record<string, unknown>, ctx: Context) => {\n const schema = strapi.getModel(FILE_MODEL_UID);\n const { auth, route } = ctx.state;\n\n return strapi.contentAPI.sanitize.query(data, schema, { auth, route });\n };\n\n return {\n async find(ctx: Context) {\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const files = await getService('upload').findMany(sanitizedQuery);\n\n const signedFiles = await async.map(files, getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async findPage(ctx: Context) {\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const { results, pagination } = await getService('upload').findAndCountPage(sanitizedQuery);\n\n const data = await sanitizeOutput(results, ctx);\n\n ctx.body = { data, meta: { pagination } };\n },\n\n async findOne(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n await validateQuery(ctx.query, ctx);\n const sanitizedQuery = await sanitizeQuery(ctx.query, ctx);\n\n const file = await getService('upload').findOne(id, sanitizedQuery.populate!);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async destroy(ctx: Context) {\n const {\n params: { id },\n } = ctx;\n\n const file = await getService('upload').findOne(id);\n\n if (!file) {\n return ctx.notFound('file.notFound');\n }\n\n await getService('upload').remove(file);\n\n const signedFile = await getService('file').signFileUrls(file);\n\n ctx.body = await sanitizeOutput(signedFile, ctx);\n },\n\n async updateFileInfo(ctx: Context) {\n const {\n query: { id },\n request: { body },\n } = ctx;\n const data = await validateUploadBody(body);\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const result = await getService('upload').updateFileInfo(id, data.fileInfo as any);\n\n const signedResult = await getService('file').signFileUrls(result);\n\n ctx.body = await sanitizeOutput(signedResult, ctx);\n },\n\n async replaceFile(ctx: Context) {\n const {\n query: { id },\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n // cannot replace with more than one file\n if (Array.isArray(filesInput)) {\n throw new ValidationError('Cannot replace a file with multiple ones');\n }\n\n if (!id || (typeof id !== 'string' && typeof id !== 'number')) {\n throw new ValidationError('File id is required and must be a single value');\n }\n\n const data = (await validateUploadBody(filteredBody)) as { fileInfo: FileInfo };\n\n const replacedFiles = await getService('upload').replace(id, { data, file: validFiles[0] });\n\n const signedFiles = await getService('file').signFileUrls(replacedFiles);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n },\n\n async uploadFiles(ctx: Context) {\n const {\n request: { body, files: { files: filesInput } = {} },\n } = ctx;\n\n const {\n validFiles,\n filteredBody,\n errors: validationErrors,\n } = await prepareUploadRequest(filesInput, body, strapi);\n if (validFiles.length === 0) {\n throw new errors.ValidationError(validationErrors[0].message);\n }\n\n const isMultipleFiles = validFiles.length > 1;\n const data: any = await validateUploadBody(filteredBody, isMultipleFiles);\n\n const apiUploadFolderService = getService('api-upload-folder');\n\n const apiUploadFolder = await apiUploadFolderService.getAPIUploadFolder();\n\n if (isMultipleFiles) {\n data.fileInfo = data.fileInfo || [];\n data.fileInfo = validFiles.map((_f, i) => ({\n ...data.fileInfo[i],\n folder: apiUploadFolder.id,\n }));\n } else {\n data.fileInfo = { ...data.fileInfo, folder: apiUploadFolder.id };\n }\n\n const uploadedFiles = await getService('upload').upload({\n data,\n files: validFiles,\n });\n\n const signedFiles = await async.map(uploadedFiles as any[], getService('file').signFileUrls);\n\n ctx.body = await sanitizeOutput(signedFiles, ctx);\n ctx.status = 201;\n },\n\n // TODO: split into multiple endpoints\n async upload(ctx: Context) {\n const {\n query: { id },\n request: { files: { files } = {} },\n } = ctx;\n\n if (_.isEmpty(files) || (!Array.isArray(files) && files.size === 0)) {\n if (id) {\n return this.updateFileInfo(ctx);\n }\n\n throw new ValidationError('Files are empty');\n }\n\n await (id ? this.replaceFile : this.uploadFiles)(ctx);\n },\n };\n};\n"],"names":["ValidationError","utils","errors","strapi","sanitizeOutput","data","ctx","schema","getModel","FILE_MODEL_UID","auth","state","contentAPI","sanitize","output","validateQuery","route","validate","query","sanitizeQuery","find","sanitizedQuery","files","getService","findMany","signedFiles","async","map","signFileUrls","body","findPage","results","pagination","findAndCountPage","meta","findOne","params","id","file","populate","notFound","signedFile","destroy","remove","updateFileInfo","request","validateUploadBody","result","fileInfo","signedResult","replaceFile","filesInput","validFiles","filteredBody","validationErrors","prepareUploadRequest","length","message","Array","isArray","replacedFiles","replace","uploadFiles","isMultipleFiles","apiUploadFolderService","apiUploadFolder","getAPIUploadFolder","_f","i","folder","uploadedFiles","upload","status","_","isEmpty","size"],"mappings":"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"}
@@ -55,6 +55,21 @@ const createRoutes = utils.createContentApiRoutesFactory(()=>{
55
55
  },
56
56
  response: validator.files
57
57
  },
58
+ {
59
+ method: 'GET',
60
+ path: '/files/page',
61
+ handler: 'content-api.findPage',
62
+ request: {
63
+ query: {
64
+ fields: validator.queryFields.optional(),
65
+ populate: validator.queryPopulate.optional(),
66
+ sort: validator.querySort.optional(),
67
+ pagination: validator.pagination.optional(),
68
+ filters: validator.filters.optional()
69
+ }
70
+ },
71
+ response: validator.paginatedFiles
72
+ },
58
73
  {
59
74
  method: 'GET',
60
75
  path: '/files/:id',
@@ -1 +1 @@
1
- {"version":3,"file":"content-api.js","sources":["../../../server/src/routes/content-api.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport * as z from 'zod/v4';\nimport { createContentApiRoutesFactory } from '@strapi/utils';\nimport { UploadRouteValidator } from './validation';\n\nconst createRoutes = createContentApiRoutesFactory((): Core.RouterInput['routes'] => {\n const validator = new UploadRouteValidator(strapi);\n\n return [\n {\n method: 'POST',\n path: '/',\n handler: 'content-api.upload',\n request: {\n query: { id: validator.fileId.optional() },\n // Note: multipart/form-data is handled by Koa middleware, not Zod\n },\n response: z.union([validator.file, validator.files]),\n },\n {\n method: 'GET',\n path: '/files',\n handler: 'content-api.find',\n request: {\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n sort: validator.querySort.optional(),\n pagination: validator.pagination.optional(),\n filters: validator.filters.optional(),\n },\n },\n response: validator.files,\n },\n {\n method: 'GET',\n path: '/files/:id',\n handler: 'content-api.findOne',\n request: {\n params: { id: validator.fileId },\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n },\n },\n response: validator.file,\n },\n {\n method: 'DELETE',\n path: '/files/:id',\n handler: 'content-api.destroy',\n request: {\n params: { id: validator.fileId },\n },\n response: validator.file,\n },\n ];\n});\n\nexport const routes = createRoutes;\n"],"names":["createRoutes","createContentApiRoutesFactory","validator","UploadRouteValidator","strapi","method","path","handler","request","query","id","fileId","optional","response","z","union","file","files","fields","queryFields","populate","queryPopulate","sort","querySort","pagination","filters","params","routes"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;AAKA,MAAMA,eAAeC,mCAAAA,CAA8B,IAAA;IACjD,MAAMC,SAAAA,GAAY,IAAIC,2BAAAA,CAAqBC,MAAAA,CAAAA;IAE3C,OAAO;AACL,QAAA;YACEC,MAAAA,EAAQ,MAAA;YACRC,IAAAA,EAAM,GAAA;YACNC,OAAAA,EAAS,oBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBAAEC,EAAAA,EAAIR,SAAAA,CAAUS,MAAM,CAACC,QAAQ;AAAG;AAE3C,aAAA;YACAC,QAAAA,EAAUC,YAAAA,CAAEC,KAAK,CAAC;AAACb,gBAAAA,SAAAA,CAAUc,IAAI;AAAEd,gBAAAA,SAAAA,CAAUe;AAAM,aAAA;AACrD,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,QAAA;YACNC,OAAAA,EAAS,kBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ,EAAA;oBAC1CU,IAAAA,EAAMpB,SAAAA,CAAUqB,SAAS,CAACX,QAAQ,EAAA;oBAClCY,UAAAA,EAAYtB,SAAAA,CAAUsB,UAAU,CAACZ,QAAQ,EAAA;oBACzCa,OAAAA,EAASvB,SAAAA,CAAUuB,OAAO,CAACb,QAAQ;AACrC;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUe;AACtB,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPkB,MAAAA,EAAQ;AAAEhB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO,iBAAA;gBAC/BF,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ;AAC5C;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUc;AACtB,SAAA;AACA,QAAA;YACEX,MAAAA,EAAQ,QAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPkB,MAAAA,EAAQ;AAAEhB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO;AACjC,aAAA;AACAE,YAAAA,QAAAA,EAAUX,UAAUc;AACtB;AACD,KAAA;AACH,CAAA,CAAA;AAEO,MAAMW,SAAS3B;;;;"}
1
+ {"version":3,"file":"content-api.js","sources":["../../../server/src/routes/content-api.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport * as z from 'zod/v4';\nimport { createContentApiRoutesFactory } from '@strapi/utils';\nimport { UploadRouteValidator } from './validation';\n\nconst createRoutes = createContentApiRoutesFactory((): Core.RouterInput['routes'] => {\n const validator = new UploadRouteValidator(strapi);\n\n return [\n {\n method: 'POST',\n path: '/',\n handler: 'content-api.upload',\n request: {\n query: { id: validator.fileId.optional() },\n // Note: multipart/form-data is handled by Koa middleware, not Zod\n },\n response: z.union([validator.file, validator.files]),\n },\n {\n method: 'GET',\n path: '/files',\n handler: 'content-api.find',\n request: {\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n sort: validator.querySort.optional(),\n pagination: validator.pagination.optional(),\n filters: validator.filters.optional(),\n },\n },\n response: validator.files,\n },\n {\n method: 'GET',\n path: '/files/page',\n handler: 'content-api.findPage',\n request: {\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n sort: validator.querySort.optional(),\n pagination: validator.pagination.optional(),\n filters: validator.filters.optional(),\n },\n },\n response: validator.paginatedFiles,\n },\n {\n method: 'GET',\n path: '/files/:id',\n handler: 'content-api.findOne',\n request: {\n params: { id: validator.fileId },\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n },\n },\n response: validator.file,\n },\n {\n method: 'DELETE',\n path: '/files/:id',\n handler: 'content-api.destroy',\n request: {\n params: { id: validator.fileId },\n },\n response: validator.file,\n },\n ];\n});\n\nexport const routes = createRoutes;\n"],"names":["createRoutes","createContentApiRoutesFactory","validator","UploadRouteValidator","strapi","method","path","handler","request","query","id","fileId","optional","response","z","union","file","files","fields","queryFields","populate","queryPopulate","sort","querySort","pagination","filters","paginatedFiles","params","routes"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;AAKA,MAAMA,eAAeC,mCAAAA,CAA8B,IAAA;IACjD,MAAMC,SAAAA,GAAY,IAAIC,2BAAAA,CAAqBC,MAAAA,CAAAA;IAE3C,OAAO;AACL,QAAA;YACEC,MAAAA,EAAQ,MAAA;YACRC,IAAAA,EAAM,GAAA;YACNC,OAAAA,EAAS,oBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBAAEC,EAAAA,EAAIR,SAAAA,CAAUS,MAAM,CAACC,QAAQ;AAAG;AAE3C,aAAA;YACAC,QAAAA,EAAUC,YAAAA,CAAEC,KAAK,CAAC;AAACb,gBAAAA,SAAAA,CAAUc,IAAI;AAAEd,gBAAAA,SAAAA,CAAUe;AAAM,aAAA;AACrD,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,QAAA;YACNC,OAAAA,EAAS,kBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ,EAAA;oBAC1CU,IAAAA,EAAMpB,SAAAA,CAAUqB,SAAS,CAACX,QAAQ,EAAA;oBAClCY,UAAAA,EAAYtB,SAAAA,CAAUsB,UAAU,CAACZ,QAAQ,EAAA;oBACzCa,OAAAA,EAASvB,SAAAA,CAAUuB,OAAO,CAACb,QAAQ;AACrC;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUe;AACtB,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,aAAA;YACNC,OAAAA,EAAS,sBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ,EAAA;oBAC1CU,IAAAA,EAAMpB,SAAAA,CAAUqB,SAAS,CAACX,QAAQ,EAAA;oBAClCY,UAAAA,EAAYtB,SAAAA,CAAUsB,UAAU,CAACZ,QAAQ,EAAA;oBACzCa,OAAAA,EAASvB,SAAAA,CAAUuB,OAAO,CAACb,QAAQ;AACrC;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUwB;AACtB,SAAA;AACA,QAAA;YACErB,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPmB,MAAAA,EAAQ;AAAEjB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO,iBAAA;gBAC/BF,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ;AAC5C;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUc;AACtB,SAAA;AACA,QAAA;YACEX,MAAAA,EAAQ,QAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPmB,MAAAA,EAAQ;AAAEjB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO;AACjC,aAAA;AACAE,YAAAA,QAAAA,EAAUX,UAAUc;AACtB;AACD,KAAA;AACH,CAAA,CAAA;AAEO,MAAMY,SAAS5B;;;;"}
@@ -34,6 +34,21 @@ const createRoutes = createContentApiRoutesFactory(()=>{
34
34
  },
35
35
  response: validator.files
36
36
  },
37
+ {
38
+ method: 'GET',
39
+ path: '/files/page',
40
+ handler: 'content-api.findPage',
41
+ request: {
42
+ query: {
43
+ fields: validator.queryFields.optional(),
44
+ populate: validator.queryPopulate.optional(),
45
+ sort: validator.querySort.optional(),
46
+ pagination: validator.pagination.optional(),
47
+ filters: validator.filters.optional()
48
+ }
49
+ },
50
+ response: validator.paginatedFiles
51
+ },
37
52
  {
38
53
  method: 'GET',
39
54
  path: '/files/:id',
@@ -1 +1 @@
1
- {"version":3,"file":"content-api.mjs","sources":["../../../server/src/routes/content-api.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport * as z from 'zod/v4';\nimport { createContentApiRoutesFactory } from '@strapi/utils';\nimport { UploadRouteValidator } from './validation';\n\nconst createRoutes = createContentApiRoutesFactory((): Core.RouterInput['routes'] => {\n const validator = new UploadRouteValidator(strapi);\n\n return [\n {\n method: 'POST',\n path: '/',\n handler: 'content-api.upload',\n request: {\n query: { id: validator.fileId.optional() },\n // Note: multipart/form-data is handled by Koa middleware, not Zod\n },\n response: z.union([validator.file, validator.files]),\n },\n {\n method: 'GET',\n path: '/files',\n handler: 'content-api.find',\n request: {\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n sort: validator.querySort.optional(),\n pagination: validator.pagination.optional(),\n filters: validator.filters.optional(),\n },\n },\n response: validator.files,\n },\n {\n method: 'GET',\n path: '/files/:id',\n handler: 'content-api.findOne',\n request: {\n params: { id: validator.fileId },\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n },\n },\n response: validator.file,\n },\n {\n method: 'DELETE',\n path: '/files/:id',\n handler: 'content-api.destroy',\n request: {\n params: { id: validator.fileId },\n },\n response: validator.file,\n },\n ];\n});\n\nexport const routes = createRoutes;\n"],"names":["createRoutes","createContentApiRoutesFactory","validator","UploadRouteValidator","strapi","method","path","handler","request","query","id","fileId","optional","response","z","union","file","files","fields","queryFields","populate","queryPopulate","sort","querySort","pagination","filters","params","routes"],"mappings":";;;;AAKA,MAAMA,eAAeC,6BAAAA,CAA8B,IAAA;IACjD,MAAMC,SAAAA,GAAY,IAAIC,oBAAAA,CAAqBC,MAAAA,CAAAA;IAE3C,OAAO;AACL,QAAA;YACEC,MAAAA,EAAQ,MAAA;YACRC,IAAAA,EAAM,GAAA;YACNC,OAAAA,EAAS,oBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBAAEC,EAAAA,EAAIR,SAAAA,CAAUS,MAAM,CAACC,QAAQ;AAAG;AAE3C,aAAA;YACAC,QAAAA,EAAUC,CAAAA,CAAEC,KAAK,CAAC;AAACb,gBAAAA,SAAAA,CAAUc,IAAI;AAAEd,gBAAAA,SAAAA,CAAUe;AAAM,aAAA;AACrD,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,QAAA;YACNC,OAAAA,EAAS,kBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ,EAAA;oBAC1CU,IAAAA,EAAMpB,SAAAA,CAAUqB,SAAS,CAACX,QAAQ,EAAA;oBAClCY,UAAAA,EAAYtB,SAAAA,CAAUsB,UAAU,CAACZ,QAAQ,EAAA;oBACzCa,OAAAA,EAASvB,SAAAA,CAAUuB,OAAO,CAACb,QAAQ;AACrC;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUe;AACtB,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPkB,MAAAA,EAAQ;AAAEhB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO,iBAAA;gBAC/BF,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ;AAC5C;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUc;AACtB,SAAA;AACA,QAAA;YACEX,MAAAA,EAAQ,QAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPkB,MAAAA,EAAQ;AAAEhB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO;AACjC,aAAA;AACAE,YAAAA,QAAAA,EAAUX,UAAUc;AACtB;AACD,KAAA;AACH,CAAA,CAAA;AAEO,MAAMW,SAAS3B;;;;"}
1
+ {"version":3,"file":"content-api.mjs","sources":["../../../server/src/routes/content-api.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport * as z from 'zod/v4';\nimport { createContentApiRoutesFactory } from '@strapi/utils';\nimport { UploadRouteValidator } from './validation';\n\nconst createRoutes = createContentApiRoutesFactory((): Core.RouterInput['routes'] => {\n const validator = new UploadRouteValidator(strapi);\n\n return [\n {\n method: 'POST',\n path: '/',\n handler: 'content-api.upload',\n request: {\n query: { id: validator.fileId.optional() },\n // Note: multipart/form-data is handled by Koa middleware, not Zod\n },\n response: z.union([validator.file, validator.files]),\n },\n {\n method: 'GET',\n path: '/files',\n handler: 'content-api.find',\n request: {\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n sort: validator.querySort.optional(),\n pagination: validator.pagination.optional(),\n filters: validator.filters.optional(),\n },\n },\n response: validator.files,\n },\n {\n method: 'GET',\n path: '/files/page',\n handler: 'content-api.findPage',\n request: {\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n sort: validator.querySort.optional(),\n pagination: validator.pagination.optional(),\n filters: validator.filters.optional(),\n },\n },\n response: validator.paginatedFiles,\n },\n {\n method: 'GET',\n path: '/files/:id',\n handler: 'content-api.findOne',\n request: {\n params: { id: validator.fileId },\n query: {\n fields: validator.queryFields.optional(),\n populate: validator.queryPopulate.optional(),\n },\n },\n response: validator.file,\n },\n {\n method: 'DELETE',\n path: '/files/:id',\n handler: 'content-api.destroy',\n request: {\n params: { id: validator.fileId },\n },\n response: validator.file,\n },\n ];\n});\n\nexport const routes = createRoutes;\n"],"names":["createRoutes","createContentApiRoutesFactory","validator","UploadRouteValidator","strapi","method","path","handler","request","query","id","fileId","optional","response","z","union","file","files","fields","queryFields","populate","queryPopulate","sort","querySort","pagination","filters","paginatedFiles","params","routes"],"mappings":";;;;AAKA,MAAMA,eAAeC,6BAAAA,CAA8B,IAAA;IACjD,MAAMC,SAAAA,GAAY,IAAIC,oBAAAA,CAAqBC,MAAAA,CAAAA;IAE3C,OAAO;AACL,QAAA;YACEC,MAAAA,EAAQ,MAAA;YACRC,IAAAA,EAAM,GAAA;YACNC,OAAAA,EAAS,oBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBAAEC,EAAAA,EAAIR,SAAAA,CAAUS,MAAM,CAACC,QAAQ;AAAG;AAE3C,aAAA;YACAC,QAAAA,EAAUC,CAAAA,CAAEC,KAAK,CAAC;AAACb,gBAAAA,SAAAA,CAAUc,IAAI;AAAEd,gBAAAA,SAAAA,CAAUe;AAAM,aAAA;AACrD,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,QAAA;YACNC,OAAAA,EAAS,kBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ,EAAA;oBAC1CU,IAAAA,EAAMpB,SAAAA,CAAUqB,SAAS,CAACX,QAAQ,EAAA;oBAClCY,UAAAA,EAAYtB,SAAAA,CAAUsB,UAAU,CAACZ,QAAQ,EAAA;oBACzCa,OAAAA,EAASvB,SAAAA,CAAUuB,OAAO,CAACb,QAAQ;AACrC;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUe;AACtB,SAAA;AACA,QAAA;YACEZ,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,aAAA;YACNC,OAAAA,EAAS,sBAAA;YACTC,OAAAA,EAAS;gBACPC,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ,EAAA;oBAC1CU,IAAAA,EAAMpB,SAAAA,CAAUqB,SAAS,CAACX,QAAQ,EAAA;oBAClCY,UAAAA,EAAYtB,SAAAA,CAAUsB,UAAU,CAACZ,QAAQ,EAAA;oBACzCa,OAAAA,EAASvB,SAAAA,CAAUuB,OAAO,CAACb,QAAQ;AACrC;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUwB;AACtB,SAAA;AACA,QAAA;YACErB,MAAAA,EAAQ,KAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPmB,MAAAA,EAAQ;AAAEjB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO,iBAAA;gBAC/BF,KAAAA,EAAO;oBACLS,MAAAA,EAAQhB,SAAAA,CAAUiB,WAAW,CAACP,QAAQ,EAAA;oBACtCQ,QAAAA,EAAUlB,SAAAA,CAAUmB,aAAa,CAACT,QAAQ;AAC5C;AACF,aAAA;AACAC,YAAAA,QAAAA,EAAUX,UAAUc;AACtB,SAAA;AACA,QAAA;YACEX,MAAAA,EAAQ,QAAA;YACRC,IAAAA,EAAM,YAAA;YACNC,OAAAA,EAAS,qBAAA;YACTC,OAAAA,EAAS;gBACPmB,MAAAA,EAAQ;AAAEjB,oBAAAA,EAAAA,EAAIR,UAAUS;AAAO;AACjC,aAAA;AACAE,YAAAA,QAAAA,EAAUX,UAAUc;AACtB;AACD,KAAA;AACH,CAAA,CAAA;AAEO,MAAMY,SAAS5B;;;;"}
@@ -63,6 +63,34 @@ var z__namespace = /*#__PURE__*/_interopNamespaceDefault(z);
63
63
  return z__namespace.array(this.file);
64
64
  }
65
65
  /**
66
+ * Paginated files response schema: `{ data, meta: { pagination } }`.
67
+ *
68
+ * Pagination meta is either page-based (`page`/`pageSize`) or offset-based
69
+ * (`start`/`limit`), and `total`/`pageCount` are omitted when
70
+ * `pagination[withCount]=false`.
71
+ */ get paginatedFiles() {
72
+ const pagedPagination = z__namespace.object({
73
+ page: z__namespace.number().int(),
74
+ pageSize: z__namespace.number().int(),
75
+ pageCount: z__namespace.number().int().optional(),
76
+ total: z__namespace.number().int().optional()
77
+ });
78
+ const offsetPagination = z__namespace.object({
79
+ start: z__namespace.number().int(),
80
+ limit: z__namespace.number().int(),
81
+ total: z__namespace.number().int().optional()
82
+ });
83
+ return z__namespace.object({
84
+ data: this.files,
85
+ meta: z__namespace.object({
86
+ pagination: z__namespace.union([
87
+ pagedPagination,
88
+ offsetPagination
89
+ ])
90
+ })
91
+ });
92
+ }
93
+ /**
66
94
  * File ID parameter validation
67
95
  */ get fileId() {
68
96
  return z__namespace.number().int().positive();
@@ -1 +1 @@
1
- {"version":3,"file":"upload.js","sources":["../../../../server/src/routes/validation/upload.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport { AbstractRouteValidator, type QueryParam } from '@strapi/utils';\nimport * as z from 'zod/v4';\n\nexport type FileQueryParam = QueryParam;\n\n/**\n * UploadRouteValidator provides validation for upload/file routes.\n *\n * Extends the AbstractRouteValidator to inherit common query parameter validation\n * while adding file-specific validation schemas.\n */\nexport class UploadRouteValidator extends AbstractRouteValidator {\n protected readonly _strapi: Core.Strapi;\n\n public constructor(strapi: Core.Strapi) {\n super();\n this._strapi = strapi;\n }\n\n /**\n * File schema for upload responses\n * Defines the structure of a file object returned by the upload API\n */\n get file() {\n return z.object({\n id: this.fileId,\n documentId: z.uuid(),\n name: z.string(),\n alternativeText: z.string().nullable().optional(),\n caption: z.string().nullable().optional(),\n width: z.number().int().optional(),\n height: z.number().int().optional(),\n formats: z.record(z.string(), z.unknown()).optional(),\n hash: z.string(),\n ext: z.string().optional(),\n mime: z.string(),\n size: z.number(),\n url: z.string(),\n previewUrl: z.string().nullable().optional(),\n folder: z.number().optional(),\n folderPath: z.string(),\n provider: z.string(),\n provider_metadata: z.record(z.string(), z.unknown()).nullable().optional(),\n createdAt: z.string(),\n updatedAt: z.string(),\n createdBy: z.number().optional(),\n updatedBy: z.number().optional(),\n });\n }\n\n /**\n * Array of files schema\n */\n get files() {\n return z.array(this.file);\n }\n\n /**\n * File ID parameter validation\n */\n get fileId() {\n return z.number().int().positive();\n }\n\n /**\n * Upload request body schema for single file uploads\n */\n get uploadBody() {\n return z.object({\n fileInfo: z\n .object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n .optional(),\n });\n }\n\n /**\n * Upload request body schema for multiple file uploads\n */\n get multiUploadBody() {\n return z.object({\n fileInfo: z\n .array(\n z.object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n )\n .optional(),\n });\n }\n\n // Note: queryParams() method is inherited from AbstractRouteValidator\n // and provides validation for ['fields', 'populate', 'sort', 'pagination', 'filters']\n}\n"],"names":["UploadRouteValidator","AbstractRouteValidator","file","z","object","id","fileId","documentId","uuid","name","string","alternativeText","nullable","optional","caption","width","number","int","height","formats","record","unknown","hash","ext","mime","size","url","previewUrl","folder","folderPath","provider","provider_metadata","createdAt","updatedAt","createdBy","updatedBy","files","array","positive","uploadBody","fileInfo","multiUploadBody","strapi","_strapi"],"mappings":"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"}
1
+ {"version":3,"file":"upload.js","sources":["../../../../server/src/routes/validation/upload.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport { AbstractRouteValidator, type QueryParam } from '@strapi/utils';\nimport * as z from 'zod/v4';\n\nexport type FileQueryParam = QueryParam;\n\n/**\n * UploadRouteValidator provides validation for upload/file routes.\n *\n * Extends the AbstractRouteValidator to inherit common query parameter validation\n * while adding file-specific validation schemas.\n */\nexport class UploadRouteValidator extends AbstractRouteValidator {\n protected readonly _strapi: Core.Strapi;\n\n public constructor(strapi: Core.Strapi) {\n super();\n this._strapi = strapi;\n }\n\n /**\n * File schema for upload responses\n * Defines the structure of a file object returned by the upload API\n */\n get file() {\n return z.object({\n id: this.fileId,\n documentId: z.uuid(),\n name: z.string(),\n alternativeText: z.string().nullable().optional(),\n caption: z.string().nullable().optional(),\n width: z.number().int().optional(),\n height: z.number().int().optional(),\n formats: z.record(z.string(), z.unknown()).optional(),\n hash: z.string(),\n ext: z.string().optional(),\n mime: z.string(),\n size: z.number(),\n url: z.string(),\n previewUrl: z.string().nullable().optional(),\n folder: z.number().optional(),\n folderPath: z.string(),\n provider: z.string(),\n provider_metadata: z.record(z.string(), z.unknown()).nullable().optional(),\n createdAt: z.string(),\n updatedAt: z.string(),\n createdBy: z.number().optional(),\n updatedBy: z.number().optional(),\n });\n }\n\n /**\n * Array of files schema\n */\n get files() {\n return z.array(this.file);\n }\n\n /**\n * Paginated files response schema: `{ data, meta: { pagination } }`.\n *\n * Pagination meta is either page-based (`page`/`pageSize`) or offset-based\n * (`start`/`limit`), and `total`/`pageCount` are omitted when\n * `pagination[withCount]=false`.\n */\n get paginatedFiles() {\n const pagedPagination = z.object({\n page: z.number().int(),\n pageSize: z.number().int(),\n pageCount: z.number().int().optional(),\n total: z.number().int().optional(),\n });\n\n const offsetPagination = z.object({\n start: z.number().int(),\n limit: z.number().int(),\n total: z.number().int().optional(),\n });\n\n return z.object({\n data: this.files,\n meta: z.object({\n pagination: z.union([pagedPagination, offsetPagination]),\n }),\n });\n }\n\n /**\n * File ID parameter validation\n */\n get fileId() {\n return z.number().int().positive();\n }\n\n /**\n * Upload request body schema for single file uploads\n */\n get uploadBody() {\n return z.object({\n fileInfo: z\n .object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n .optional(),\n });\n }\n\n /**\n * Upload request body schema for multiple file uploads\n */\n get multiUploadBody() {\n return z.object({\n fileInfo: z\n .array(\n z.object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n )\n .optional(),\n });\n }\n\n // Note: queryParams() method is inherited from AbstractRouteValidator\n // and provides validation for ['fields', 'populate', 'sort', 'pagination', 'filters']\n}\n"],"names":["UploadRouteValidator","AbstractRouteValidator","file","z","object","id","fileId","documentId","uuid","name","string","alternativeText","nullable","optional","caption","width","number","int","height","formats","record","unknown","hash","ext","mime","size","url","previewUrl","folder","folderPath","provider","provider_metadata","createdAt","updatedAt","createdBy","updatedBy","files","array","paginatedFiles","pagedPagination","page","pageSize","pageCount","total","offsetPagination","start","limit","data","meta","pagination","union","positive","uploadBody","fileInfo","multiUploadBody","strapi","_strapi"],"mappings":"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"}
@@ -42,6 +42,34 @@ import * as z from 'zod/v4';
42
42
  return z.array(this.file);
43
43
  }
44
44
  /**
45
+ * Paginated files response schema: `{ data, meta: { pagination } }`.
46
+ *
47
+ * Pagination meta is either page-based (`page`/`pageSize`) or offset-based
48
+ * (`start`/`limit`), and `total`/`pageCount` are omitted when
49
+ * `pagination[withCount]=false`.
50
+ */ get paginatedFiles() {
51
+ const pagedPagination = z.object({
52
+ page: z.number().int(),
53
+ pageSize: z.number().int(),
54
+ pageCount: z.number().int().optional(),
55
+ total: z.number().int().optional()
56
+ });
57
+ const offsetPagination = z.object({
58
+ start: z.number().int(),
59
+ limit: z.number().int(),
60
+ total: z.number().int().optional()
61
+ });
62
+ return z.object({
63
+ data: this.files,
64
+ meta: z.object({
65
+ pagination: z.union([
66
+ pagedPagination,
67
+ offsetPagination
68
+ ])
69
+ })
70
+ });
71
+ }
72
+ /**
45
73
  * File ID parameter validation
46
74
  */ get fileId() {
47
75
  return z.number().int().positive();
@@ -1 +1 @@
1
- {"version":3,"file":"upload.mjs","sources":["../../../../server/src/routes/validation/upload.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport { AbstractRouteValidator, type QueryParam } from '@strapi/utils';\nimport * as z from 'zod/v4';\n\nexport type FileQueryParam = QueryParam;\n\n/**\n * UploadRouteValidator provides validation for upload/file routes.\n *\n * Extends the AbstractRouteValidator to inherit common query parameter validation\n * while adding file-specific validation schemas.\n */\nexport class UploadRouteValidator extends AbstractRouteValidator {\n protected readonly _strapi: Core.Strapi;\n\n public constructor(strapi: Core.Strapi) {\n super();\n this._strapi = strapi;\n }\n\n /**\n * File schema for upload responses\n * Defines the structure of a file object returned by the upload API\n */\n get file() {\n return z.object({\n id: this.fileId,\n documentId: z.uuid(),\n name: z.string(),\n alternativeText: z.string().nullable().optional(),\n caption: z.string().nullable().optional(),\n width: z.number().int().optional(),\n height: z.number().int().optional(),\n formats: z.record(z.string(), z.unknown()).optional(),\n hash: z.string(),\n ext: z.string().optional(),\n mime: z.string(),\n size: z.number(),\n url: z.string(),\n previewUrl: z.string().nullable().optional(),\n folder: z.number().optional(),\n folderPath: z.string(),\n provider: z.string(),\n provider_metadata: z.record(z.string(), z.unknown()).nullable().optional(),\n createdAt: z.string(),\n updatedAt: z.string(),\n createdBy: z.number().optional(),\n updatedBy: z.number().optional(),\n });\n }\n\n /**\n * Array of files schema\n */\n get files() {\n return z.array(this.file);\n }\n\n /**\n * File ID parameter validation\n */\n get fileId() {\n return z.number().int().positive();\n }\n\n /**\n * Upload request body schema for single file uploads\n */\n get uploadBody() {\n return z.object({\n fileInfo: z\n .object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n .optional(),\n });\n }\n\n /**\n * Upload request body schema for multiple file uploads\n */\n get multiUploadBody() {\n return z.object({\n fileInfo: z\n .array(\n z.object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n )\n .optional(),\n });\n }\n\n // Note: queryParams() method is inherited from AbstractRouteValidator\n // and provides validation for ['fields', 'populate', 'sort', 'pagination', 'filters']\n}\n"],"names":["UploadRouteValidator","AbstractRouteValidator","file","z","object","id","fileId","documentId","uuid","name","string","alternativeText","nullable","optional","caption","width","number","int","height","formats","record","unknown","hash","ext","mime","size","url","previewUrl","folder","folderPath","provider","provider_metadata","createdAt","updatedAt","createdBy","updatedBy","files","array","positive","uploadBody","fileInfo","multiUploadBody","strapi","_strapi"],"mappings":"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"}
1
+ {"version":3,"file":"upload.mjs","sources":["../../../../server/src/routes/validation/upload.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\nimport { AbstractRouteValidator, type QueryParam } from '@strapi/utils';\nimport * as z from 'zod/v4';\n\nexport type FileQueryParam = QueryParam;\n\n/**\n * UploadRouteValidator provides validation for upload/file routes.\n *\n * Extends the AbstractRouteValidator to inherit common query parameter validation\n * while adding file-specific validation schemas.\n */\nexport class UploadRouteValidator extends AbstractRouteValidator {\n protected readonly _strapi: Core.Strapi;\n\n public constructor(strapi: Core.Strapi) {\n super();\n this._strapi = strapi;\n }\n\n /**\n * File schema for upload responses\n * Defines the structure of a file object returned by the upload API\n */\n get file() {\n return z.object({\n id: this.fileId,\n documentId: z.uuid(),\n name: z.string(),\n alternativeText: z.string().nullable().optional(),\n caption: z.string().nullable().optional(),\n width: z.number().int().optional(),\n height: z.number().int().optional(),\n formats: z.record(z.string(), z.unknown()).optional(),\n hash: z.string(),\n ext: z.string().optional(),\n mime: z.string(),\n size: z.number(),\n url: z.string(),\n previewUrl: z.string().nullable().optional(),\n folder: z.number().optional(),\n folderPath: z.string(),\n provider: z.string(),\n provider_metadata: z.record(z.string(), z.unknown()).nullable().optional(),\n createdAt: z.string(),\n updatedAt: z.string(),\n createdBy: z.number().optional(),\n updatedBy: z.number().optional(),\n });\n }\n\n /**\n * Array of files schema\n */\n get files() {\n return z.array(this.file);\n }\n\n /**\n * Paginated files response schema: `{ data, meta: { pagination } }`.\n *\n * Pagination meta is either page-based (`page`/`pageSize`) or offset-based\n * (`start`/`limit`), and `total`/`pageCount` are omitted when\n * `pagination[withCount]=false`.\n */\n get paginatedFiles() {\n const pagedPagination = z.object({\n page: z.number().int(),\n pageSize: z.number().int(),\n pageCount: z.number().int().optional(),\n total: z.number().int().optional(),\n });\n\n const offsetPagination = z.object({\n start: z.number().int(),\n limit: z.number().int(),\n total: z.number().int().optional(),\n });\n\n return z.object({\n data: this.files,\n meta: z.object({\n pagination: z.union([pagedPagination, offsetPagination]),\n }),\n });\n }\n\n /**\n * File ID parameter validation\n */\n get fileId() {\n return z.number().int().positive();\n }\n\n /**\n * Upload request body schema for single file uploads\n */\n get uploadBody() {\n return z.object({\n fileInfo: z\n .object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n .optional(),\n });\n }\n\n /**\n * Upload request body schema for multiple file uploads\n */\n get multiUploadBody() {\n return z.object({\n fileInfo: z\n .array(\n z.object({\n name: z.string().optional(),\n alternativeText: z.string().optional(),\n caption: z.string().optional(),\n })\n )\n .optional(),\n });\n }\n\n // Note: queryParams() method is inherited from AbstractRouteValidator\n // and provides validation for ['fields', 'populate', 'sort', 'pagination', 'filters']\n}\n"],"names":["UploadRouteValidator","AbstractRouteValidator","file","z","object","id","fileId","documentId","uuid","name","string","alternativeText","nullable","optional","caption","width","number","int","height","formats","record","unknown","hash","ext","mime","size","url","previewUrl","folder","folderPath","provider","provider_metadata","createdAt","updatedAt","createdBy","updatedBy","files","array","paginatedFiles","pagedPagination","page","pageSize","pageCount","total","offsetPagination","start","limit","data","meta","pagination","union","positive","uploadBody","fileInfo","multiUploadBody","strapi","_strapi"],"mappings":"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"}
@@ -7,6 +7,7 @@ var fse = require('fs-extra');
7
7
  var _ = require('lodash');
8
8
  var mimeTypes = require('mime-types');
9
9
  var utils = require('@strapi/utils');
10
+ var fp = require('lodash/fp');
10
11
  var constants = require('../constants.js');
11
12
  var index = require('../utils/index.js');
12
13
 
@@ -377,6 +378,93 @@ var upload = (({ strapi })=>{
377
378
  results: signedResults
378
379
  };
379
380
  }
381
+ /**
382
+ * Resolve whether the count query should run, mirroring core-api's `shouldCount`.
383
+ * Defaults to the `api.rest.withCount` config (true) when not specified on the request.
384
+ */ function resolveWithCount(pagination) {
385
+ if (fp.has('withCount', pagination)) {
386
+ const withCount = pagination.withCount;
387
+ if (typeof withCount === 'boolean') {
388
+ return withCount;
389
+ }
390
+ if (typeof withCount === 'undefined') {
391
+ return false;
392
+ }
393
+ if ([
394
+ 'true',
395
+ 't',
396
+ '1',
397
+ 1
398
+ ].includes(withCount)) {
399
+ return true;
400
+ }
401
+ if ([
402
+ 'false',
403
+ 'f',
404
+ '0',
405
+ 0
406
+ ].includes(withCount)) {
407
+ return false;
408
+ }
409
+ throw new utils.errors.ValidationError('Invalid withCount parameter. Expected "t","1","true","false","0","f"');
410
+ }
411
+ return Boolean(strapi.config.get('api.rest.withCount', true));
412
+ }
413
+ /**
414
+ * REST-aware paginated find for the content API.
415
+ *
416
+ * Unlike `findPage` (used by the admin API), this honors the standard nested
417
+ * `pagination` query object (`pagination[page]`, `pagination[pageSize]`,
418
+ * `pagination[start]`, `pagination[limit]`, `pagination[withCount]`) and the
419
+ * `api.rest.defaultLimit` / `api.rest.maxLimit` / `api.rest.withCount` config,
420
+ * exactly like every other Strapi REST collection-type endpoint.
421
+ */ async function findAndCountPage(query = {}) {
422
+ const { pagination = {} } = query;
423
+ const defaultLimit = fp.toNumber(strapi.config.get('api.rest.defaultLimit', 25));
424
+ const maxLimit = fp.toNumber(strapi.config.get('api.rest.maxLimit')) || null;
425
+ // Whether the consumer used page-based pagination (default) vs offset-based.
426
+ const isOffset = fp.has('start', pagination) || fp.has('limit', pagination);
427
+ const isPaged = !isOffset;
428
+ // Resolve start/limit applying defaults and the maxLimit cap.
429
+ const { start, limit } = utils.pagination.withDefaultPagination(pagination, {
430
+ defaults: {
431
+ offset: {
432
+ limit: defaultLimit
433
+ },
434
+ page: {
435
+ pageSize: defaultLimit
436
+ }
437
+ },
438
+ maxLimit: maxLimit || -1
439
+ });
440
+ // Feed the transform the resolved offset/limit so it ignores the nested
441
+ // `pagination` object (which it cannot read) and applies real bounds.
442
+ const transformed = strapi.get('query-params').transform(constants.FILE_MODEL_UID, {
443
+ ...query,
444
+ pagination: undefined,
445
+ start,
446
+ limit
447
+ });
448
+ const shouldCount = resolveWithCount(pagination);
449
+ const [results, total] = await Promise.all([
450
+ strapi.db.query(constants.FILE_MODEL_UID).findMany(transformed),
451
+ shouldCount ? strapi.db.query(constants.FILE_MODEL_UID).count(transformed) : Promise.resolve(undefined)
452
+ ]);
453
+ const signedResults = await utils.async.map(results, (file)=>fileService.signFileUrls(file));
454
+ const transform = isPaged ? utils.pagination.transformPagedPaginationInfo : utils.pagination.transformOffsetPaginationInfo;
455
+ const paginationInfo = transform({
456
+ start,
457
+ limit
458
+ }, total);
459
+ return {
460
+ results: signedResults,
461
+ // Omit total & pageCount when counting is disabled (withCount=false).
462
+ pagination: fp.isNil(total) ? _.omit(paginationInfo, [
463
+ 'total',
464
+ 'pageCount'
465
+ ]) : paginationInfo
466
+ };
467
+ }
380
468
  async function remove(file) {
381
469
  const config = strapi.config.get('plugin::upload');
382
470
  // execute delete function of the provider
@@ -448,6 +536,7 @@ var upload = (({ strapi })=>{
448
536
  findOne,
449
537
  findMany,
450
538
  findPage,
539
+ findAndCountPage,
451
540
  remove,
452
541
  getSettings,
453
542
  setSettings,