@strapi/upload 5.58.0 → 5.60.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 (395) hide show
  1. package/dist/admin/components/AssetPickerDialog/AssetPickerDialog.js +434 -0
  2. package/dist/admin/components/AssetPickerDialog/AssetPickerDialog.js.map +1 -0
  3. package/dist/admin/components/AssetPickerDialog/AssetPickerDialog.mjs +432 -0
  4. package/dist/admin/components/AssetPickerDialog/AssetPickerDialog.mjs.map +1 -0
  5. package/dist/admin/components/AssetPickerDialog/FolderBreadcrumbs.js +91 -0
  6. package/dist/admin/components/AssetPickerDialog/FolderBreadcrumbs.js.map +1 -0
  7. package/dist/admin/components/AssetPickerDialog/FolderBreadcrumbs.mjs +89 -0
  8. package/dist/admin/components/AssetPickerDialog/FolderBreadcrumbs.mjs.map +1 -0
  9. package/dist/admin/components/AssetPickerDialog/PickerSelectionProvider.js +178 -0
  10. package/dist/admin/components/AssetPickerDialog/PickerSelectionProvider.js.map +1 -0
  11. package/dist/admin/components/AssetPickerDialog/PickerSelectionProvider.mjs +175 -0
  12. package/dist/admin/components/AssetPickerDialog/PickerSelectionProvider.mjs.map +1 -0
  13. package/dist/admin/components/AssetPickerDialog/SortableSelection.js +143 -0
  14. package/dist/admin/components/AssetPickerDialog/SortableSelection.js.map +1 -0
  15. package/dist/admin/components/AssetPickerDialog/SortableSelection.mjs +141 -0
  16. package/dist/admin/components/AssetPickerDialog/SortableSelection.mjs.map +1 -0
  17. package/dist/admin/components/AssetPickerDialog/pickerSelection.js +49 -0
  18. package/dist/admin/components/AssetPickerDialog/pickerSelection.js.map +1 -0
  19. package/dist/admin/components/AssetPickerDialog/pickerSelection.mjs +41 -0
  20. package/dist/admin/components/AssetPickerDialog/pickerSelection.mjs.map +1 -0
  21. package/dist/admin/components/MediaLibraryInput/AddAssetMenu.js +142 -0
  22. package/dist/admin/components/MediaLibraryInput/AddAssetMenu.js.map +1 -0
  23. package/dist/admin/components/MediaLibraryInput/AddAssetMenu.mjs +140 -0
  24. package/dist/admin/components/MediaLibraryInput/AddAssetMenu.mjs.map +1 -0
  25. package/dist/admin/components/MediaLibraryInput/AssetCard.js +240 -0
  26. package/dist/admin/components/MediaLibraryInput/AssetCard.js.map +1 -0
  27. package/dist/admin/components/MediaLibraryInput/AssetCard.mjs +237 -0
  28. package/dist/admin/components/MediaLibraryInput/AssetCard.mjs.map +1 -0
  29. package/dist/admin/components/MediaLibraryInput/AssetCarousel.js +161 -0
  30. package/dist/admin/components/MediaLibraryInput/AssetCarousel.js.map +1 -0
  31. package/dist/admin/components/MediaLibraryInput/AssetCarousel.mjs +159 -0
  32. package/dist/admin/components/MediaLibraryInput/AssetCarousel.mjs.map +1 -0
  33. package/dist/admin/components/MediaLibraryInput/AssetDropZone.js +156 -0
  34. package/dist/admin/components/MediaLibraryInput/AssetDropZone.js.map +1 -0
  35. package/dist/admin/components/MediaLibraryInput/AssetDropZone.mjs +154 -0
  36. package/dist/admin/components/MediaLibraryInput/AssetDropZone.mjs.map +1 -0
  37. package/dist/admin/components/MediaLibraryInput/AssetPreview.js +109 -0
  38. package/dist/admin/components/MediaLibraryInput/AssetPreview.js.map +1 -0
  39. package/dist/admin/components/MediaLibraryInput/AssetPreview.mjs +106 -0
  40. package/dist/admin/components/MediaLibraryInput/AssetPreview.mjs.map +1 -0
  41. package/dist/admin/components/MediaLibraryInput/AssetRow.js +211 -0
  42. package/dist/admin/components/MediaLibraryInput/AssetRow.js.map +1 -0
  43. package/dist/admin/components/MediaLibraryInput/AssetRow.mjs +208 -0
  44. package/dist/admin/components/MediaLibraryInput/AssetRow.mjs.map +1 -0
  45. package/dist/admin/components/MediaLibraryInput/FieldControls.js +32 -0
  46. package/dist/admin/components/MediaLibraryInput/FieldControls.js.map +1 -0
  47. package/dist/admin/components/MediaLibraryInput/FieldControls.mjs +29 -0
  48. package/dist/admin/components/MediaLibraryInput/FieldControls.mjs.map +1 -0
  49. package/dist/admin/components/MediaLibraryInput/MediaLibraryInput.js +439 -0
  50. package/dist/admin/components/MediaLibraryInput/MediaLibraryInput.js.map +1 -0
  51. package/dist/admin/components/MediaLibraryInput/MediaLibraryInput.mjs +433 -0
  52. package/dist/admin/components/MediaLibraryInput/MediaLibraryInput.mjs.map +1 -0
  53. package/dist/admin/components/MediaLibraryInput/UploadProgressBar.js +42 -0
  54. package/dist/admin/components/MediaLibraryInput/UploadProgressBar.js.map +1 -0
  55. package/dist/admin/components/MediaLibraryInput/UploadProgressBar.mjs +40 -0
  56. package/dist/admin/components/MediaLibraryInput/UploadProgressBar.mjs.map +1 -0
  57. package/dist/admin/components/MediaLibraryInput/useFieldUploads.js +122 -0
  58. package/dist/admin/components/MediaLibraryInput/useFieldUploads.js.map +1 -0
  59. package/dist/admin/components/MediaLibraryInput/useFieldUploads.mjs +120 -0
  60. package/dist/admin/components/MediaLibraryInput/useFieldUploads.mjs.map +1 -0
  61. package/dist/admin/components/UploadProgressDialog.js +2 -1
  62. package/dist/admin/components/UploadProgressDialog.js.map +1 -1
  63. package/dist/admin/components/UploadProgressDialog.mjs +2 -1
  64. package/dist/admin/components/UploadProgressDialog.mjs.map +1 -1
  65. package/dist/admin/hooks/useAIMetadataAvailability.js +5 -1
  66. package/dist/admin/hooks/useAIMetadataAvailability.js.map +1 -1
  67. package/dist/admin/hooks/useAIMetadataAvailability.mjs +5 -1
  68. package/dist/admin/hooks/useAIMetadataAvailability.mjs.map +1 -1
  69. package/dist/admin/hooks/useAIMetadataEnabled.js +7 -1
  70. package/dist/admin/hooks/useAIMetadataEnabled.js.map +1 -1
  71. package/dist/admin/hooks/useAIMetadataEnabled.mjs +7 -1
  72. package/dist/admin/hooks/useAIMetadataEnabled.mjs.map +1 -1
  73. package/dist/admin/hooks/useMediaLibraryPermissions.js +16 -2
  74. package/dist/admin/hooks/useMediaLibraryPermissions.js.map +1 -1
  75. package/dist/admin/hooks/useMediaLibraryPermissions.mjs +16 -2
  76. package/dist/admin/hooks/useMediaLibraryPermissions.mjs.map +1 -1
  77. package/dist/admin/hooks/useTracking.js +5 -1
  78. package/dist/admin/hooks/useTracking.js.map +1 -1
  79. package/dist/admin/hooks/useTracking.mjs +5 -1
  80. package/dist/admin/hooks/useTracking.mjs.map +1 -1
  81. package/dist/admin/index.js +7 -2
  82. package/dist/admin/index.js.map +1 -1
  83. package/dist/admin/index.mjs +7 -2
  84. package/dist/admin/index.mjs.map +1 -1
  85. package/dist/admin/legacy/components/AssetCard/AssetCardBase.js.map +1 -1
  86. package/dist/admin/legacy/components/AssetCard/AssetCardBase.mjs.map +1 -1
  87. package/dist/admin/legacy/components/AssetCard/VideoPreview.js +2 -1
  88. package/dist/admin/legacy/components/AssetCard/VideoPreview.js.map +1 -1
  89. package/dist/admin/legacy/components/AssetCard/VideoPreview.mjs +2 -1
  90. package/dist/admin/legacy/components/AssetCard/VideoPreview.mjs.map +1 -1
  91. package/dist/admin/legacy/components/AssetDialog/AssetDialog.js +3 -1
  92. package/dist/admin/legacy/components/AssetDialog/AssetDialog.js.map +1 -1
  93. package/dist/admin/legacy/components/AssetDialog/AssetDialog.mjs +3 -1
  94. package/dist/admin/legacy/components/AssetDialog/AssetDialog.mjs.map +1 -1
  95. package/dist/admin/legacy/components/AssetDialog/BrowseStep/BrowseStep.js +3 -1
  96. package/dist/admin/legacy/components/AssetDialog/BrowseStep/BrowseStep.js.map +1 -1
  97. package/dist/admin/legacy/components/AssetDialog/BrowseStep/BrowseStep.mjs +3 -1
  98. package/dist/admin/legacy/components/AssetDialog/BrowseStep/BrowseStep.mjs.map +1 -1
  99. package/dist/admin/legacy/components/AssetDialog/BrowseStep/Filters.js.map +1 -1
  100. package/dist/admin/legacy/components/AssetDialog/BrowseStep/Filters.mjs.map +1 -1
  101. package/dist/admin/legacy/components/AssetGridList/AssetGridList.js +7 -6
  102. package/dist/admin/legacy/components/AssetGridList/AssetGridList.js.map +1 -1
  103. package/dist/admin/legacy/components/AssetGridList/AssetGridList.mjs +7 -6
  104. package/dist/admin/legacy/components/AssetGridList/AssetGridList.mjs.map +1 -1
  105. package/dist/admin/legacy/components/Breadcrumbs/CrumbSimpleMenuAsync.js +2 -1
  106. package/dist/admin/legacy/components/Breadcrumbs/CrumbSimpleMenuAsync.js.map +1 -1
  107. package/dist/admin/legacy/components/Breadcrumbs/CrumbSimpleMenuAsync.mjs +2 -1
  108. package/dist/admin/legacy/components/Breadcrumbs/CrumbSimpleMenuAsync.mjs.map +1 -1
  109. package/dist/admin/legacy/components/BulkMoveDialog/BulkMoveDialog.js +2 -1
  110. package/dist/admin/legacy/components/BulkMoveDialog/BulkMoveDialog.js.map +1 -1
  111. package/dist/admin/legacy/components/BulkMoveDialog/BulkMoveDialog.mjs +2 -1
  112. package/dist/admin/legacy/components/BulkMoveDialog/BulkMoveDialog.mjs.map +1 -1
  113. package/dist/admin/legacy/components/EditAssetDialog/EditAssetContent.js +3 -1
  114. package/dist/admin/legacy/components/EditAssetDialog/EditAssetContent.js.map +1 -1
  115. package/dist/admin/legacy/components/EditAssetDialog/EditAssetContent.mjs +3 -1
  116. package/dist/admin/legacy/components/EditAssetDialog/EditAssetContent.mjs.map +1 -1
  117. package/dist/admin/legacy/components/FilterList/FilterList.js.map +1 -1
  118. package/dist/admin/legacy/components/FilterList/FilterList.mjs.map +1 -1
  119. package/dist/admin/legacy/components/FilterPopover/FilterPopover.js.map +1 -1
  120. package/dist/admin/legacy/components/FilterPopover/FilterPopover.mjs.map +1 -1
  121. package/dist/admin/legacy/components/FilterPopover/FilterValueInput.js +2 -1
  122. package/dist/admin/legacy/components/FilterPopover/FilterValueInput.js.map +1 -1
  123. package/dist/admin/legacy/components/FilterPopover/FilterValueInput.mjs +2 -1
  124. package/dist/admin/legacy/components/FilterPopover/FilterValueInput.mjs.map +1 -1
  125. package/dist/admin/legacy/components/MediaLibraryDialog/MediaLibraryDialog.js +4 -2
  126. package/dist/admin/legacy/components/MediaLibraryDialog/MediaLibraryDialog.js.map +1 -1
  127. package/dist/admin/legacy/components/MediaLibraryDialog/MediaLibraryDialog.mjs +4 -2
  128. package/dist/admin/legacy/components/MediaLibraryDialog/MediaLibraryDialog.mjs.map +1 -1
  129. package/dist/admin/legacy/components/MediaLibraryInput/MediaLibraryInput.js +2 -1
  130. package/dist/admin/legacy/components/MediaLibraryInput/MediaLibraryInput.js.map +1 -1
  131. package/dist/admin/legacy/components/MediaLibraryInput/MediaLibraryInput.mjs +2 -1
  132. package/dist/admin/legacy/components/MediaLibraryInput/MediaLibraryInput.mjs.map +1 -1
  133. package/dist/admin/legacy/components/SelectTree/SelectTree.js +3 -1
  134. package/dist/admin/legacy/components/SelectTree/SelectTree.js.map +1 -1
  135. package/dist/admin/legacy/components/SelectTree/SelectTree.mjs +3 -1
  136. package/dist/admin/legacy/components/SelectTree/SelectTree.mjs.map +1 -1
  137. package/dist/admin/legacy/components/TableList/TableList.js +3 -1
  138. package/dist/admin/legacy/components/TableList/TableList.js.map +1 -1
  139. package/dist/admin/legacy/components/TableList/TableList.mjs +3 -1
  140. package/dist/admin/legacy/components/TableList/TableList.mjs.map +1 -1
  141. package/dist/admin/legacy/components/TableList/TableRows.js +3 -1
  142. package/dist/admin/legacy/components/TableList/TableRows.js.map +1 -1
  143. package/dist/admin/legacy/components/TableList/TableRows.mjs +3 -1
  144. package/dist/admin/legacy/components/TableList/TableRows.mjs.map +1 -1
  145. package/dist/admin/legacy/components/UploadAssetDialog/UploadAssetDialog.js +3 -1
  146. package/dist/admin/legacy/components/UploadAssetDialog/UploadAssetDialog.js.map +1 -1
  147. package/dist/admin/legacy/components/UploadAssetDialog/UploadAssetDialog.mjs +3 -1
  148. package/dist/admin/legacy/components/UploadAssetDialog/UploadAssetDialog.mjs.map +1 -1
  149. package/dist/admin/legacy/pages/App/ConfigureTheView/ConfigureTheView.js.map +1 -1
  150. package/dist/admin/legacy/pages/App/ConfigureTheView/ConfigureTheView.mjs.map +1 -1
  151. package/dist/admin/legacy/pages/App/components/BulkActions.js +2 -1
  152. package/dist/admin/legacy/pages/App/components/BulkActions.js.map +1 -1
  153. package/dist/admin/legacy/pages/App/components/BulkActions.mjs +2 -1
  154. package/dist/admin/legacy/pages/App/components/BulkActions.mjs.map +1 -1
  155. package/dist/admin/legacy/pages/App/components/BulkMoveButton.js +2 -1
  156. package/dist/admin/legacy/pages/App/components/BulkMoveButton.js.map +1 -1
  157. package/dist/admin/legacy/pages/App/components/BulkMoveButton.mjs +2 -1
  158. package/dist/admin/legacy/pages/App/components/BulkMoveButton.mjs.map +1 -1
  159. package/dist/admin/pages/Assets/AssetsPage.js +13 -302
  160. package/dist/admin/pages/Assets/AssetsPage.js.map +1 -1
  161. package/dist/admin/pages/Assets/AssetsPage.mjs +11 -280
  162. package/dist/admin/pages/Assets/AssetsPage.mjs.map +1 -1
  163. package/dist/admin/pages/Assets/components/AssetsGrid.js +143 -31
  164. package/dist/admin/pages/Assets/components/AssetsGrid.js.map +1 -1
  165. package/dist/admin/pages/Assets/components/AssetsGrid.mjs +146 -34
  166. package/dist/admin/pages/Assets/components/AssetsGrid.mjs.map +1 -1
  167. package/dist/admin/pages/Assets/components/AssetsSearchInput.js +43 -2
  168. package/dist/admin/pages/Assets/components/AssetsSearchInput.js.map +1 -1
  169. package/dist/admin/pages/Assets/components/AssetsSearchInput.mjs +45 -4
  170. package/dist/admin/pages/Assets/components/AssetsSearchInput.mjs.map +1 -1
  171. package/dist/admin/pages/Assets/components/AssetsTable.js +60 -35
  172. package/dist/admin/pages/Assets/components/AssetsTable.js.map +1 -1
  173. package/dist/admin/pages/Assets/components/AssetsTable.mjs +62 -37
  174. package/dist/admin/pages/Assets/components/AssetsTable.mjs.map +1 -1
  175. package/dist/admin/pages/Assets/components/AssetsView.js +145 -0
  176. package/dist/admin/pages/Assets/components/AssetsView.js.map +1 -0
  177. package/dist/admin/pages/Assets/components/AssetsView.mjs +143 -0
  178. package/dist/admin/pages/Assets/components/AssetsView.mjs.map +1 -0
  179. package/dist/admin/pages/Assets/components/BulkActionsBar.js +3 -1
  180. package/dist/admin/pages/Assets/components/BulkActionsBar.js.map +1 -1
  181. package/dist/admin/pages/Assets/components/BulkActionsBar.mjs +4 -2
  182. package/dist/admin/pages/Assets/components/BulkActionsBar.mjs.map +1 -1
  183. package/dist/admin/pages/Assets/components/BusyOverlay.mjs +1 -1
  184. package/dist/admin/pages/Assets/components/DateRangeCalendar.js +10 -7
  185. package/dist/admin/pages/Assets/components/DateRangeCalendar.js.map +1 -1
  186. package/dist/admin/pages/Assets/components/DateRangeCalendar.mjs +10 -7
  187. package/dist/admin/pages/Assets/components/DateRangeCalendar.mjs.map +1 -1
  188. package/dist/admin/pages/Assets/components/Dnd/DragOverlayChip.mjs +1 -1
  189. package/dist/admin/pages/Assets/components/Dnd/ReorderHandle.js +40 -0
  190. package/dist/admin/pages/Assets/components/Dnd/ReorderHandle.js.map +1 -0
  191. package/dist/admin/pages/Assets/components/Dnd/ReorderHandle.mjs +38 -0
  192. package/dist/admin/pages/Assets/components/Dnd/ReorderHandle.mjs.map +1 -0
  193. package/dist/admin/pages/Assets/components/Dnd/assetSortable.js +29 -0
  194. package/dist/admin/pages/Assets/components/Dnd/assetSortable.js.map +1 -0
  195. package/dist/admin/pages/Assets/components/Dnd/assetSortable.mjs +24 -0
  196. package/dist/admin/pages/Assets/components/Dnd/assetSortable.mjs.map +1 -0
  197. package/dist/admin/pages/Assets/components/Dnd/dndIds.js +5 -0
  198. package/dist/admin/pages/Assets/components/Dnd/dndIds.js.map +1 -1
  199. package/dist/admin/pages/Assets/components/Dnd/dndIds.mjs +5 -1
  200. package/dist/admin/pages/Assets/components/Dnd/dndIds.mjs.map +1 -1
  201. package/dist/admin/pages/Assets/components/Dnd/useAssetDnd.js +41 -13
  202. package/dist/admin/pages/Assets/components/Dnd/useAssetDnd.js.map +1 -1
  203. package/dist/admin/pages/Assets/components/Dnd/useAssetDnd.mjs +41 -13
  204. package/dist/admin/pages/Assets/components/Dnd/useAssetDnd.mjs.map +1 -1
  205. package/dist/admin/pages/Assets/components/DropZone/UploadDropZoneContext.js +4 -2
  206. package/dist/admin/pages/Assets/components/DropZone/UploadDropZoneContext.js.map +1 -1
  207. package/dist/admin/pages/Assets/components/DropZone/UploadDropZoneContext.mjs +5 -3
  208. package/dist/admin/pages/Assets/components/DropZone/UploadDropZoneContext.mjs.map +1 -1
  209. package/dist/admin/pages/Assets/components/FilterBadges.js +32 -3
  210. package/dist/admin/pages/Assets/components/FilterBadges.js.map +1 -1
  211. package/dist/admin/pages/Assets/components/FilterBadges.mjs +35 -6
  212. package/dist/admin/pages/Assets/components/FilterBadges.mjs.map +1 -1
  213. package/dist/admin/pages/Assets/components/FilterMenu.mjs +2 -2
  214. package/dist/admin/pages/Assets/components/FolderTree/FolderTree.js +274 -55
  215. package/dist/admin/pages/Assets/components/FolderTree/FolderTree.js.map +1 -1
  216. package/dist/admin/pages/Assets/components/FolderTree/FolderTree.mjs +277 -59
  217. package/dist/admin/pages/Assets/components/FolderTree/FolderTree.mjs.map +1 -1
  218. package/dist/admin/pages/Assets/components/FolderTree/collapsedBranch.js +32 -0
  219. package/dist/admin/pages/Assets/components/FolderTree/collapsedBranch.js.map +1 -0
  220. package/dist/admin/pages/Assets/components/FolderTree/collapsedBranch.mjs +29 -0
  221. package/dist/admin/pages/Assets/components/FolderTree/collapsedBranch.mjs.map +1 -0
  222. package/dist/admin/pages/Assets/components/ViewToggle.js +126 -0
  223. package/dist/admin/pages/Assets/components/ViewToggle.js.map +1 -0
  224. package/dist/admin/pages/Assets/components/ViewToggle.mjs +104 -0
  225. package/dist/admin/pages/Assets/components/ViewToggle.mjs.map +1 -0
  226. package/dist/admin/pages/Assets/hooks/useAssetSearch.js +2 -2
  227. package/dist/admin/pages/Assets/hooks/useAssetSearch.js.map +1 -1
  228. package/dist/admin/pages/Assets/hooks/useAssetSearch.mjs +2 -2
  229. package/dist/admin/pages/Assets/hooks/useAssetSearch.mjs.map +1 -1
  230. package/dist/admin/pages/Assets/hooks/useAssetSelection.js +19 -1
  231. package/dist/admin/pages/Assets/hooks/useAssetSelection.js.map +1 -1
  232. package/dist/admin/pages/Assets/hooks/useAssetSelection.mjs +20 -3
  233. package/dist/admin/pages/Assets/hooks/useAssetSelection.mjs.map +1 -1
  234. package/dist/admin/pages/Assets/hooks/useAssetsList.js +87 -0
  235. package/dist/admin/pages/Assets/hooks/useAssetsList.js.map +1 -0
  236. package/dist/admin/pages/Assets/hooks/useAssetsList.mjs +85 -0
  237. package/dist/admin/pages/Assets/hooks/useAssetsList.mjs.map +1 -0
  238. package/dist/admin/pages/Assets/hooks/useBusyAssets.mjs +1 -1
  239. package/dist/admin/pages/Assets/hooks/useFolderNavigation.js +2 -1
  240. package/dist/admin/pages/Assets/hooks/useFolderNavigation.js.map +1 -1
  241. package/dist/admin/pages/Assets/hooks/useFolderNavigation.mjs +3 -2
  242. package/dist/admin/pages/Assets/hooks/useFolderNavigation.mjs.map +1 -1
  243. package/dist/admin/pages/Assets/hooks/useListFilters.js +2 -1
  244. package/dist/admin/pages/Assets/hooks/useListFilters.js.map +1 -1
  245. package/dist/admin/pages/Assets/hooks/useListFilters.mjs +3 -2
  246. package/dist/admin/pages/Assets/hooks/useListFilters.mjs.map +1 -1
  247. package/dist/admin/pages/Assets/hooks/useListQueryParams.js +80 -0
  248. package/dist/admin/pages/Assets/hooks/useListQueryParams.js.map +1 -0
  249. package/dist/admin/pages/Assets/hooks/useListQueryParams.mjs +77 -0
  250. package/dist/admin/pages/Assets/hooks/useListQueryParams.mjs.map +1 -0
  251. package/dist/admin/pages/Assets/hooks/useListSettings.js +32 -0
  252. package/dist/admin/pages/Assets/hooks/useListSettings.js.map +1 -0
  253. package/dist/admin/pages/Assets/hooks/useListSettings.mjs +29 -0
  254. package/dist/admin/pages/Assets/hooks/useListSettings.mjs.map +1 -0
  255. package/dist/admin/pages/Assets/hooks/useListSort.js +2 -1
  256. package/dist/admin/pages/Assets/hooks/useListSort.js.map +1 -1
  257. package/dist/admin/pages/Assets/hooks/useListSort.mjs +3 -2
  258. package/dist/admin/pages/Assets/hooks/useListSort.mjs.map +1 -1
  259. package/dist/admin/services/api.js +106 -11
  260. package/dist/admin/services/api.js.map +1 -1
  261. package/dist/admin/services/api.mjs +105 -13
  262. package/dist/admin/services/api.mjs.map +1 -1
  263. package/dist/admin/src/components/AssetPickerDialog/AssetPickerDialog.d.ts +19 -0
  264. package/dist/admin/src/components/AssetPickerDialog/FolderBreadcrumbs.d.ts +10 -0
  265. package/dist/admin/src/components/AssetPickerDialog/PickerSelectionProvider.d.ts +28 -0
  266. package/dist/admin/src/components/AssetPickerDialog/SortableSelection.d.ts +12 -0
  267. package/dist/admin/src/components/AssetPickerDialog/pickerSelection.d.ts +26 -0
  268. package/dist/admin/src/components/MediaLibraryInput/AddAssetMenu.d.ts +19 -0
  269. package/dist/admin/src/components/MediaLibraryInput/AssetCard.d.ts +25 -0
  270. package/dist/admin/src/components/MediaLibraryInput/AssetCarousel.d.ts +16 -0
  271. package/dist/admin/src/components/MediaLibraryInput/AssetDropZone.d.ts +21 -0
  272. package/dist/admin/src/components/MediaLibraryInput/AssetPreview.d.ts +17 -0
  273. package/dist/admin/src/components/MediaLibraryInput/AssetRow.d.ts +25 -0
  274. package/dist/admin/src/components/MediaLibraryInput/FieldControls.d.ts +19 -0
  275. package/dist/admin/src/components/MediaLibraryInput/MediaLibraryInput.d.ts +28 -0
  276. package/dist/admin/src/components/MediaLibraryInput/UploadProgressBar.d.ts +7 -0
  277. package/dist/admin/src/components/MediaLibraryInput/useFieldUploads.d.ts +31 -0
  278. package/dist/admin/src/hooks/useMediaLibraryPermissions.d.ts +3 -0
  279. package/dist/admin/src/legacy/components/BulkMoveDialog/BulkMoveDialog.d.ts +1 -1
  280. package/dist/admin/src/legacy/pages/App/components/BulkActions.d.ts +1 -1
  281. package/dist/admin/src/pages/Assets/components/AssetsGrid.d.ts +3 -1
  282. package/dist/admin/src/pages/Assets/components/AssetsSearchInput.d.ts +11 -1
  283. package/dist/admin/src/pages/Assets/components/AssetsView.d.ts +29 -0
  284. package/dist/admin/src/pages/Assets/components/Dnd/ReorderHandle.d.ts +12 -0
  285. package/dist/admin/src/pages/Assets/components/Dnd/assetSortable.d.ts +37 -0
  286. package/dist/admin/src/pages/Assets/components/Dnd/dndIds.d.ts +5 -0
  287. package/dist/admin/src/pages/Assets/components/Dnd/useAssetDnd.d.ts +23 -2
  288. package/dist/admin/src/pages/Assets/components/FolderTree/FolderTree.d.ts +1 -0
  289. package/dist/admin/src/pages/Assets/components/FolderTree/collapsedBranch.d.ts +21 -0
  290. package/dist/admin/src/pages/Assets/components/ViewToggle.d.ts +8 -0
  291. package/dist/admin/src/pages/Assets/hooks/useAssetSelection.d.ts +26 -0
  292. package/dist/admin/src/pages/Assets/hooks/useAssetsList.d.ts +30 -0
  293. package/dist/admin/src/pages/Assets/hooks/useListQueryParams.d.ts +27 -0
  294. package/dist/admin/src/pages/Assets/hooks/useListSettings.d.ts +29 -0
  295. package/dist/admin/src/services/api.d.ts +30 -1
  296. package/dist/admin/src/store/uploadProgress.d.ts +14 -1
  297. package/dist/admin/src/utils/allowedMediaTypes.d.ts +16 -0
  298. package/dist/admin/src/utils/findFolderPath.d.ts +6 -0
  299. package/dist/admin/src/utils/isAllowedAssetType.d.ts +14 -0
  300. package/dist/admin/store/uploadProgress.js +30 -3
  301. package/dist/admin/store/uploadProgress.js.map +1 -1
  302. package/dist/admin/store/uploadProgress.mjs +29 -4
  303. package/dist/admin/store/uploadProgress.mjs.map +1 -1
  304. package/dist/admin/translations/ca.json.js +3 -3
  305. package/dist/admin/translations/ca.json.mjs +3 -3
  306. package/dist/admin/translations/da.json.js +1 -1
  307. package/dist/admin/translations/da.json.mjs +1 -1
  308. package/dist/admin/translations/de.json.js +1 -1
  309. package/dist/admin/translations/de.json.mjs +1 -1
  310. package/dist/admin/translations/en.json.js +29 -0
  311. package/dist/admin/translations/en.json.js.map +1 -1
  312. package/dist/admin/translations/en.json.mjs +29 -0
  313. package/dist/admin/translations/en.json.mjs.map +1 -1
  314. package/dist/admin/translations/es.json.js +1 -1
  315. package/dist/admin/translations/es.json.mjs +1 -1
  316. package/dist/admin/translations/sk.json.js +2 -2
  317. package/dist/admin/translations/sk.json.mjs +2 -2
  318. package/dist/admin/translations/tr.json.js +2 -2
  319. package/dist/admin/translations/tr.json.mjs +2 -2
  320. package/dist/admin/translations/zh-Hans.json.js +1 -1
  321. package/dist/admin/translations/zh-Hans.json.mjs +1 -1
  322. package/dist/admin/translations/zh.json.js +2 -2
  323. package/dist/admin/translations/zh.json.mjs +2 -2
  324. package/dist/admin/utils/allowedMediaTypes.js +42 -0
  325. package/dist/admin/utils/allowedMediaTypes.js.map +1 -0
  326. package/dist/admin/utils/allowedMediaTypes.mjs +39 -0
  327. package/dist/admin/utils/allowedMediaTypes.mjs.map +1 -0
  328. package/dist/admin/utils/findFolderPath.js +26 -0
  329. package/dist/admin/utils/findFolderPath.js.map +1 -0
  330. package/dist/admin/utils/findFolderPath.mjs +24 -0
  331. package/dist/admin/utils/findFolderPath.mjs.map +1 -0
  332. package/dist/admin/utils/isAllowedAssetType.js +33 -0
  333. package/dist/admin/utils/isAllowedAssetType.js.map +1 -0
  334. package/dist/admin/utils/isAllowedAssetType.mjs +31 -0
  335. package/dist/admin/utils/isAllowedAssetType.mjs.map +1 -0
  336. package/dist/server/config.js +6 -0
  337. package/dist/server/config.js.map +1 -1
  338. package/dist/server/config.mjs +6 -0
  339. package/dist/server/config.mjs.map +1 -1
  340. package/dist/server/controllers/admin-settings.js +5 -1
  341. package/dist/server/controllers/admin-settings.js.map +1 -1
  342. package/dist/server/controllers/admin-settings.mjs +5 -1
  343. package/dist/server/controllers/admin-settings.mjs.map +1 -1
  344. package/dist/server/controllers/validation/admin/upload.js.map +1 -1
  345. package/dist/server/controllers/validation/admin/upload.mjs.map +1 -1
  346. package/dist/server/controllers/validation/content-api/upload.js.map +1 -1
  347. package/dist/server/controllers/validation/content-api/upload.mjs.map +1 -1
  348. package/dist/server/mcp/ambient-instance.js +7 -5
  349. package/dist/server/mcp/ambient-instance.js.map +1 -1
  350. package/dist/server/mcp/ambient-instance.mjs +7 -5
  351. package/dist/server/mcp/ambient-instance.mjs.map +1 -1
  352. package/dist/server/mcp/handlers/folder-handlers.js +4 -16
  353. package/dist/server/mcp/handlers/folder-handlers.js.map +1 -1
  354. package/dist/server/mcp/handlers/folder-handlers.mjs +5 -17
  355. package/dist/server/mcp/handlers/folder-handlers.mjs.map +1 -1
  356. package/dist/server/mcp/handlers/read-handlers.js +6 -14
  357. package/dist/server/mcp/handlers/read-handlers.js.map +1 -1
  358. package/dist/server/mcp/handlers/read-handlers.mjs +7 -15
  359. package/dist/server/mcp/handlers/read-handlers.mjs.map +1 -1
  360. package/dist/server/mcp/handlers/write-handlers.js +3 -13
  361. package/dist/server/mcp/handlers/write-handlers.js.map +1 -1
  362. package/dist/server/mcp/handlers/write-handlers.mjs +3 -13
  363. package/dist/server/mcp/handlers/write-handlers.mjs.map +1 -1
  364. package/dist/server/mcp/register-upload-mcp-tools.js +215 -195
  365. package/dist/server/mcp/register-upload-mcp-tools.js.map +1 -1
  366. package/dist/server/mcp/register-upload-mcp-tools.mjs +215 -195
  367. package/dist/server/mcp/register-upload-mcp-tools.mjs.map +1 -1
  368. package/dist/server/services/image-manipulation.js +35 -16
  369. package/dist/server/services/image-manipulation.js.map +1 -1
  370. package/dist/server/services/image-manipulation.mjs +35 -16
  371. package/dist/server/services/image-manipulation.mjs.map +1 -1
  372. package/dist/server/services/upload.js.map +1 -1
  373. package/dist/server/services/upload.mjs.map +1 -1
  374. package/dist/server/src/config.d.ts +3 -0
  375. package/dist/server/src/config.d.ts.map +1 -1
  376. package/dist/server/src/controllers/admin-settings.d.ts.map +1 -1
  377. package/dist/server/src/controllers/validation/admin/upload.d.ts.map +1 -1
  378. package/dist/server/src/controllers/validation/content-api/upload.d.ts.map +1 -1
  379. package/dist/server/src/index.d.ts +4 -1
  380. package/dist/server/src/index.d.ts.map +1 -1
  381. package/dist/server/src/mcp/ambient-instance.d.ts +7 -5
  382. package/dist/server/src/mcp/ambient-instance.d.ts.map +1 -1
  383. package/dist/server/src/mcp/handlers/folder-handlers.d.ts.map +1 -1
  384. package/dist/server/src/mcp/handlers/read-handlers.d.ts +3 -2
  385. package/dist/server/src/mcp/handlers/read-handlers.d.ts.map +1 -1
  386. package/dist/server/src/mcp/handlers/write-handlers.d.ts.map +1 -1
  387. package/dist/server/src/mcp/register-upload-mcp-tools.d.ts +9 -14
  388. package/dist/server/src/mcp/register-upload-mcp-tools.d.ts.map +1 -1
  389. package/dist/server/src/services/extensions/utils.d.ts +11 -11
  390. package/dist/server/src/services/image-manipulation.d.ts +1 -1
  391. package/dist/server/src/services/image-manipulation.d.ts.map +1 -1
  392. package/dist/server/src/services/index.d.ts +1 -1
  393. package/dist/server/src/types.d.ts +64 -12
  394. package/dist/server/src/types.d.ts.map +1 -1
  395. package/package.json +8 -6
@@ -0,0 +1,39 @@
1
+ /**
2
+ * The `allowedTypes` values a `media` attribute can carry, and the mime prefix
3
+ * each one stands for. `files` is the catch-all: anything that is not an image,
4
+ * video or audio.
5
+ */ const MEDIA_KINDS = [
6
+ 'image',
7
+ 'video',
8
+ 'audio'
9
+ ];
10
+ const SINGULAR = {
11
+ files: 'file',
12
+ images: 'image',
13
+ videos: 'video',
14
+ audios: 'audio'
15
+ };
16
+ /**
17
+ * Whether a mime type satisfies a field's `allowedTypes`.
18
+ *
19
+ * No `allowedTypes` means the field takes anything. A file with no mime is only
20
+ * allowed where `files` is, since nothing places it in one of the three media
21
+ * kinds.
22
+ */ const isMediaTypeAllowed = (allowedTypes, mime)=>{
23
+ if (!allowedTypes || allowedTypes.length === 0) {
24
+ return true;
25
+ }
26
+ const singularTypes = new Set(allowedTypes.map((type)=>SINGULAR[type]).filter((type)=>Boolean(type)));
27
+ const kind = mime?.split('/')[0];
28
+ if (!kind) {
29
+ return singularTypes.has('file');
30
+ }
31
+ if (singularTypes.has('file') && !MEDIA_KINDS.includes(kind)) {
32
+ return true;
33
+ }
34
+ return singularTypes.has(kind);
35
+ };
36
+ /** The subset of `files` this field accepts, in the order they were given. */ const filterAllowedFiles = (allowedTypes, files)=>files.filter((file)=>isMediaTypeAllowed(allowedTypes, file.type));
37
+
38
+ export { filterAllowedFiles, isMediaTypeAllowed };
39
+ //# sourceMappingURL=allowedMediaTypes.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"allowedMediaTypes.mjs","sources":["../../../admin/src/utils/allowedMediaTypes.ts"],"sourcesContent":["/**\n * The `allowedTypes` values a `media` attribute can carry, and the mime prefix\n * each one stands for. `files` is the catch-all: anything that is not an image,\n * video or audio.\n */\nexport type AllowedMediaType = 'files' | 'images' | 'videos' | 'audios';\n\nconst MEDIA_KINDS = ['image', 'video', 'audio'] as const;\n\nconst SINGULAR: Record<AllowedMediaType, string> = {\n files: 'file',\n images: 'image',\n videos: 'video',\n audios: 'audio',\n};\n\n/**\n * Whether a mime type satisfies a field's `allowedTypes`.\n *\n * No `allowedTypes` means the field takes anything. A file with no mime is only\n * allowed where `files` is, since nothing places it in one of the three media\n * kinds.\n */\nexport const isMediaTypeAllowed = (\n allowedTypes: AllowedMediaType[] | null | undefined,\n mime: string | undefined\n): boolean => {\n if (!allowedTypes || allowedTypes.length === 0) {\n return true;\n }\n\n const singularTypes = new Set(\n allowedTypes.map((type) => SINGULAR[type]).filter((type): type is string => Boolean(type))\n );\n const kind = mime?.split('/')[0];\n\n if (!kind) {\n return singularTypes.has('file');\n }\n\n if (singularTypes.has('file') && !MEDIA_KINDS.includes(kind as (typeof MEDIA_KINDS)[number])) {\n return true;\n }\n\n return singularTypes.has(kind);\n};\n\n/** The subset of `files` this field accepts, in the order they were given. */\nexport const filterAllowedFiles = (\n allowedTypes: AllowedMediaType[] | null | undefined,\n files: globalThis.File[]\n): globalThis.File[] => files.filter((file) => isMediaTypeAllowed(allowedTypes, file.type));\n"],"names":["MEDIA_KINDS","SINGULAR","files","images","videos","audios","isMediaTypeAllowed","allowedTypes","mime","length","singularTypes","Set","map","type","filter","Boolean","kind","split","has","includes","filterAllowedFiles","file"],"mappings":"AAAA;;;;AAIC,IAGD,MAAMA,WAAAA,GAAc;AAAC,IAAA,OAAA;AAAS,IAAA,OAAA;AAAS,IAAA;AAAQ,CAAA;AAE/C,MAAMC,QAAAA,GAA6C;IACjDC,KAAAA,EAAO,MAAA;IACPC,MAAAA,EAAQ,OAAA;IACRC,MAAAA,EAAQ,OAAA;IACRC,MAAAA,EAAQ;AACV,CAAA;AAEA;;;;;;AAMC,IACM,MAAMC,kBAAAA,GAAqB,CAChCC,YAAAA,EACAC,IAAAA,GAAAA;AAEA,IAAA,IAAI,CAACD,YAAAA,IAAgBA,YAAAA,CAAaE,MAAM,KAAK,CAAA,EAAG;QAC9C,OAAO,IAAA;AACT,IAAA;AAEA,IAAA,MAAMC,gBAAgB,IAAIC,GAAAA,CACxBJ,YAAAA,CAAaK,GAAG,CAAC,CAACC,IAAAA,GAASZ,QAAQ,CAACY,KAAK,CAAA,CAAEC,MAAM,CAAC,CAACD,OAAyBE,OAAAA,CAAQF,IAAAA,CAAAA,CAAAA,CAAAA;AAEtF,IAAA,MAAMG,IAAAA,GAAOR,IAAAA,EAAMS,KAAAA,CAAM,GAAA,CAAI,CAAC,CAAA,CAAE;AAEhC,IAAA,IAAI,CAACD,IAAAA,EAAM;QACT,OAAON,aAAAA,CAAcQ,GAAG,CAAC,MAAA,CAAA;AAC3B,IAAA;IAEA,IAAIR,aAAAA,CAAcQ,GAAG,CAAC,MAAA,CAAA,IAAW,CAAClB,WAAAA,CAAYmB,QAAQ,CAACH,IAAAA,CAAAA,EAAuC;QAC5F,OAAO,IAAA;AACT,IAAA;IAEA,OAAON,aAAAA,CAAcQ,GAAG,CAACF,IAAAA,CAAAA;AAC3B;AAEA,+EACO,MAAMI,kBAAAA,GAAqB,CAChCb,cACAL,KAAAA,GACsBA,KAAAA,CAAMY,MAAM,CAAC,CAACO,IAAAA,GAASf,kBAAAA,CAAmBC,YAAAA,EAAcc,IAAAA,CAAKR,IAAI,CAAA;;;;"}
@@ -0,0 +1,26 @@
1
+ 'use strict';
2
+
3
+ /**
4
+ * The chain of folders from the library root down to `targetId`, inclusive, or
5
+ * `null` when the folder is not in the tree (deleted, or not loaded yet).
6
+ */ const findFolderPath = (nodes, targetId, trail = [])=>{
7
+ for (const node of nodes){
8
+ const nextTrail = node.id != null ? [
9
+ ...trail,
10
+ node
11
+ ] : trail;
12
+ if (node.id === targetId) {
13
+ return nextTrail;
14
+ }
15
+ if (node.children?.length) {
16
+ const found = findFolderPath(node.children, targetId, nextTrail);
17
+ if (found !== null) {
18
+ return found;
19
+ }
20
+ }
21
+ }
22
+ return null;
23
+ };
24
+
25
+ exports.findFolderPath = findFolderPath;
26
+ //# sourceMappingURL=findFolderPath.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"findFolderPath.js","sources":["../../../admin/src/utils/findFolderPath.ts"],"sourcesContent":["import type { FolderNode } from '../../../shared/contracts/folders';\n\n/**\n * The chain of folders from the library root down to `targetId`, inclusive, or\n * `null` when the folder is not in the tree (deleted, or not loaded yet).\n */\nexport const findFolderPath = (\n nodes: FolderNode[],\n targetId: number,\n trail: FolderNode[] = []\n): FolderNode[] | null => {\n for (const node of nodes) {\n const nextTrail = node.id != null ? [...trail, node] : trail;\n\n if (node.id === targetId) {\n return nextTrail;\n }\n\n if (node.children?.length) {\n const found = findFolderPath(node.children, targetId, nextTrail);\n\n if (found !== null) {\n return found;\n }\n }\n }\n\n return null;\n};\n"],"names":["findFolderPath","nodes","targetId","trail","node","nextTrail","id","children","length","found"],"mappings":";;AAEA;;;AAGC,IACM,MAAMA,cAAAA,GAAiB,CAC5BC,KAAAA,EACAC,QAAAA,EACAC,QAAsB,EAAE,GAAA;IAExB,KAAK,MAAMC,QAAQH,KAAAA,CAAO;AACxB,QAAA,MAAMI,SAAAA,GAAYD,IAAAA,CAAKE,EAAE,IAAI,IAAA,GAAO;AAAIH,YAAAA,GAAAA,KAAAA;AAAOC,YAAAA;SAAK,GAAGD,KAAAA;QAEvD,IAAIC,IAAAA,CAAKE,EAAE,KAAKJ,QAAAA,EAAU;YACxB,OAAOG,SAAAA;AACT,QAAA;QAEA,IAAID,IAAAA,CAAKG,QAAQ,EAAEC,MAAAA,EAAQ;AACzB,YAAA,MAAMC,KAAAA,GAAQT,cAAAA,CAAeI,IAAAA,CAAKG,QAAQ,EAAEL,QAAAA,EAAUG,SAAAA,CAAAA;AAEtD,YAAA,IAAII,UAAU,IAAA,EAAM;gBAClB,OAAOA,KAAAA;AACT,YAAA;AACF,QAAA;AACF,IAAA;IAEA,OAAO,IAAA;AACT;;;;"}
@@ -0,0 +1,24 @@
1
+ /**
2
+ * The chain of folders from the library root down to `targetId`, inclusive, or
3
+ * `null` when the folder is not in the tree (deleted, or not loaded yet).
4
+ */ const findFolderPath = (nodes, targetId, trail = [])=>{
5
+ for (const node of nodes){
6
+ const nextTrail = node.id != null ? [
7
+ ...trail,
8
+ node
9
+ ] : trail;
10
+ if (node.id === targetId) {
11
+ return nextTrail;
12
+ }
13
+ if (node.children?.length) {
14
+ const found = findFolderPath(node.children, targetId, nextTrail);
15
+ if (found !== null) {
16
+ return found;
17
+ }
18
+ }
19
+ }
20
+ return null;
21
+ };
22
+
23
+ export { findFolderPath };
24
+ //# sourceMappingURL=findFolderPath.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"findFolderPath.mjs","sources":["../../../admin/src/utils/findFolderPath.ts"],"sourcesContent":["import type { FolderNode } from '../../../shared/contracts/folders';\n\n/**\n * The chain of folders from the library root down to `targetId`, inclusive, or\n * `null` when the folder is not in the tree (deleted, or not loaded yet).\n */\nexport const findFolderPath = (\n nodes: FolderNode[],\n targetId: number,\n trail: FolderNode[] = []\n): FolderNode[] | null => {\n for (const node of nodes) {\n const nextTrail = node.id != null ? [...trail, node] : trail;\n\n if (node.id === targetId) {\n return nextTrail;\n }\n\n if (node.children?.length) {\n const found = findFolderPath(node.children, targetId, nextTrail);\n\n if (found !== null) {\n return found;\n }\n }\n }\n\n return null;\n};\n"],"names":["findFolderPath","nodes","targetId","trail","node","nextTrail","id","children","length","found"],"mappings":"AAEA;;;AAGC,IACM,MAAMA,cAAAA,GAAiB,CAC5BC,KAAAA,EACAC,QAAAA,EACAC,QAAsB,EAAE,GAAA;IAExB,KAAK,MAAMC,QAAQH,KAAAA,CAAO;AACxB,QAAA,MAAMI,SAAAA,GAAYD,IAAAA,CAAKE,EAAE,IAAI,IAAA,GAAO;AAAIH,YAAAA,GAAAA,KAAAA;AAAOC,YAAAA;SAAK,GAAGD,KAAAA;QAEvD,IAAIC,IAAAA,CAAKE,EAAE,KAAKJ,QAAAA,EAAU;YACxB,OAAOG,SAAAA;AACT,QAAA;QAEA,IAAID,IAAAA,CAAKG,QAAQ,EAAEC,MAAAA,EAAQ;AACzB,YAAA,MAAMC,KAAAA,GAAQT,cAAAA,CAAeI,IAAAA,CAAKG,QAAQ,EAAEL,QAAAA,EAAUG,SAAAA,CAAAA;AAEtD,YAAA,IAAII,UAAU,IAAA,EAAM;gBAClB,OAAOA,KAAAA;AACT,YAAA;AACF,QAAA;AACF,IAAA;IAEA,OAAO,IAAA;AACT;;;;"}
@@ -0,0 +1,33 @@
1
+ 'use strict';
2
+
3
+ var enums = require('../enums.js');
4
+
5
+ const MEDIA_KIND_BY_MIME_FAMILY = {
6
+ [enums.ASSET_TYPES.Image]: 'images',
7
+ [enums.ASSET_TYPES.Video]: 'videos',
8
+ [enums.ASSET_TYPES.Audio]: 'audios'
9
+ };
10
+ /**
11
+ * Whether an asset fits a media field's `allowedTypes`, by the same rule as the
12
+ * legacy picker: only the MIME family (before the `/`) counts, and `files`
13
+ * covers everything that is not an image, a video or an audio file.
14
+ *
15
+ * Not `typeFromMime`: it matches anywhere in the MIME type, so
16
+ * `application/x-iso9660-image` would count as an image.
17
+ *
18
+ * No restriction (missing or empty) allows everything.
19
+ */ const isAllowedAssetType = (allowedTypes, mime)=>{
20
+ const kinds = allowedTypes == null ? [] : [
21
+ allowedTypes
22
+ ].flat();
23
+ if (kinds.length === 0) {
24
+ return true;
25
+ }
26
+ if (!mime) {
27
+ return false;
28
+ }
29
+ return kinds.includes(MEDIA_KIND_BY_MIME_FAMILY[mime.split('/')[0]] ?? 'files');
30
+ };
31
+
32
+ exports.isAllowedAssetType = isAllowedAssetType;
33
+ //# sourceMappingURL=isAllowedAssetType.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"isAllowedAssetType.js","sources":["../../../admin/src/utils/isAllowedAssetType.ts"],"sourcesContent":["import { ASSET_TYPES } from '../enums';\n\nimport type { Schema } from '@strapi/types';\n\n/** A media field's `allowedTypes`, exactly as its schema can hold it. */\nexport type MediaAllowedTypes =\n Schema.Attribute.MediaProperties<Schema.Attribute.MediaKind>['allowedTypes'];\n\nconst MEDIA_KIND_BY_MIME_FAMILY: Record<string, Schema.Attribute.MediaKind> = {\n [ASSET_TYPES.Image]: 'images',\n [ASSET_TYPES.Video]: 'videos',\n [ASSET_TYPES.Audio]: 'audios',\n};\n\n/**\n * Whether an asset fits a media field's `allowedTypes`, by the same rule as the\n * legacy picker: only the MIME family (before the `/`) counts, and `files`\n * covers everything that is not an image, a video or an audio file.\n *\n * Not `typeFromMime`: it matches anywhere in the MIME type, so\n * `application/x-iso9660-image` would count as an image.\n *\n * No restriction (missing or empty) allows everything.\n */\nexport const isAllowedAssetType = (\n allowedTypes: MediaAllowedTypes | null,\n mime: string | null | undefined\n): boolean => {\n const kinds = allowedTypes == null ? [] : [allowedTypes].flat();\n\n if (kinds.length === 0) {\n return true;\n }\n\n if (!mime) {\n return false;\n }\n\n return kinds.includes(MEDIA_KIND_BY_MIME_FAMILY[mime.split('/')[0]] ?? 'files');\n};\n"],"names":["MEDIA_KIND_BY_MIME_FAMILY","ASSET_TYPES","Image","Video","Audio","isAllowedAssetType","allowedTypes","mime","kinds","flat","length","includes","split"],"mappings":";;;;AAQA,MAAMA,yBAAAA,GAAwE;IAC5E,CAACC,iBAAAA,CAAYC,KAAK,GAAG,QAAA;IACrB,CAACD,iBAAAA,CAAYE,KAAK,GAAG,QAAA;IACrB,CAACF,iBAAAA,CAAYG,KAAK,GAAG;AACvB,CAAA;AAEA;;;;;;;;;AASC,IACM,MAAMC,kBAAAA,GAAqB,CAChCC,YAAAA,EACAC,IAAAA,GAAAA;AAEA,IAAA,MAAMC,KAAAA,GAAQF,YAAAA,IAAgB,IAAA,GAAO,EAAE,GAAG;AAACA,QAAAA;AAAa,KAAA,CAACG,IAAI,EAAA;IAE7D,IAAID,KAAAA,CAAME,MAAM,KAAK,CAAA,EAAG;QACtB,OAAO,IAAA;AACT,IAAA;AAEA,IAAA,IAAI,CAACH,IAAAA,EAAM;QACT,OAAO,KAAA;AACT,IAAA;AAEA,IAAA,OAAOC,KAAAA,CAAMG,QAAQ,CAACX,yBAAyB,CAACO,IAAAA,CAAKK,KAAK,CAAC,GAAA,CAAI,CAAC,CAAA,CAAE,CAAC,IAAI,OAAA,CAAA;AACzE;;;;"}
@@ -0,0 +1,31 @@
1
+ import { ASSET_TYPES } from '../enums.mjs';
2
+
3
+ const MEDIA_KIND_BY_MIME_FAMILY = {
4
+ [ASSET_TYPES.Image]: 'images',
5
+ [ASSET_TYPES.Video]: 'videos',
6
+ [ASSET_TYPES.Audio]: 'audios'
7
+ };
8
+ /**
9
+ * Whether an asset fits a media field's `allowedTypes`, by the same rule as the
10
+ * legacy picker: only the MIME family (before the `/`) counts, and `files`
11
+ * covers everything that is not an image, a video or an audio file.
12
+ *
13
+ * Not `typeFromMime`: it matches anywhere in the MIME type, so
14
+ * `application/x-iso9660-image` would count as an image.
15
+ *
16
+ * No restriction (missing or empty) allows everything.
17
+ */ const isAllowedAssetType = (allowedTypes, mime)=>{
18
+ const kinds = allowedTypes == null ? [] : [
19
+ allowedTypes
20
+ ].flat();
21
+ if (kinds.length === 0) {
22
+ return true;
23
+ }
24
+ if (!mime) {
25
+ return false;
26
+ }
27
+ return kinds.includes(MEDIA_KIND_BY_MIME_FAMILY[mime.split('/')[0]] ?? 'files');
28
+ };
29
+
30
+ export { isAllowedAssetType };
31
+ //# sourceMappingURL=isAllowedAssetType.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"isAllowedAssetType.mjs","sources":["../../../admin/src/utils/isAllowedAssetType.ts"],"sourcesContent":["import { ASSET_TYPES } from '../enums';\n\nimport type { Schema } from '@strapi/types';\n\n/** A media field's `allowedTypes`, exactly as its schema can hold it. */\nexport type MediaAllowedTypes =\n Schema.Attribute.MediaProperties<Schema.Attribute.MediaKind>['allowedTypes'];\n\nconst MEDIA_KIND_BY_MIME_FAMILY: Record<string, Schema.Attribute.MediaKind> = {\n [ASSET_TYPES.Image]: 'images',\n [ASSET_TYPES.Video]: 'videos',\n [ASSET_TYPES.Audio]: 'audios',\n};\n\n/**\n * Whether an asset fits a media field's `allowedTypes`, by the same rule as the\n * legacy picker: only the MIME family (before the `/`) counts, and `files`\n * covers everything that is not an image, a video or an audio file.\n *\n * Not `typeFromMime`: it matches anywhere in the MIME type, so\n * `application/x-iso9660-image` would count as an image.\n *\n * No restriction (missing or empty) allows everything.\n */\nexport const isAllowedAssetType = (\n allowedTypes: MediaAllowedTypes | null,\n mime: string | null | undefined\n): boolean => {\n const kinds = allowedTypes == null ? [] : [allowedTypes].flat();\n\n if (kinds.length === 0) {\n return true;\n }\n\n if (!mime) {\n return false;\n }\n\n return kinds.includes(MEDIA_KIND_BY_MIME_FAMILY[mime.split('/')[0]] ?? 'files');\n};\n"],"names":["MEDIA_KIND_BY_MIME_FAMILY","ASSET_TYPES","Image","Video","Audio","isAllowedAssetType","allowedTypes","mime","kinds","flat","length","includes","split"],"mappings":";;AAQA,MAAMA,yBAAAA,GAAwE;IAC5E,CAACC,WAAAA,CAAYC,KAAK,GAAG,QAAA;IACrB,CAACD,WAAAA,CAAYE,KAAK,GAAG,QAAA;IACrB,CAACF,WAAAA,CAAYG,KAAK,GAAG;AACvB,CAAA;AAEA;;;;;;;;;AASC,IACM,MAAMC,kBAAAA,GAAqB,CAChCC,YAAAA,EACAC,IAAAA,GAAAA;AAEA,IAAA,MAAMC,KAAAA,GAAQF,YAAAA,IAAgB,IAAA,GAAO,EAAE,GAAG;AAACA,QAAAA;AAAa,KAAA,CAACG,IAAI,EAAA;IAE7D,IAAID,KAAAA,CAAME,MAAM,KAAK,CAAA,EAAG;QACtB,OAAO,IAAA;AACT,IAAA;AAEA,IAAA,IAAI,CAACH,IAAAA,EAAM;QACT,OAAO,KAAA;AACT,IAAA;AAEA,IAAA,OAAOC,KAAAA,CAAMG,QAAQ,CAACX,yBAAyB,CAACO,IAAAA,CAAKK,KAAK,CAAC,GAAA,CAAI,CAAC,CAAA,CAAE,CAAC,IAAI,OAAA,CAAA;AACzE;;;;"}
@@ -26,6 +26,12 @@ const config = {
26
26
  assertPositiveInteger('concurrentUploadSize', config.concurrentUploadSize);
27
27
  // Client-side parallelism: upload requests the admin fires at once.
28
28
  assertPositiveInteger('concurrentUploadRequests', config.concurrentUploadRequests);
29
+ // Sharp throws on anything else at every image call, which the upload flow
30
+ // reads as "not an image" and skips processing silently.
31
+ const limitInputPixels = config.sharp?.limitInputPixels;
32
+ if (limitInputPixels != null && typeof limitInputPixels !== 'boolean' && !(Number.isInteger(limitInputPixels) && limitInputPixels >= 0)) {
33
+ throw new Error('upload plugin config: "sharp.limitInputPixels" must be a boolean or an integer greater than or equal to 0 (use env.int() to read it from the environment)');
34
+ }
29
35
  }
30
36
  };
31
37
 
@@ -1 +1 @@
1
- {"version":3,"file":"config.js","sources":["../../server/src/config.ts"],"sourcesContent":["export const config = {\n default: {\n enabled: true,\n provider: 'local',\n sizeLimit: 1000000000, // 1GB\n actionOptions: {},\n sharp: {\n cache: false,\n concurrency: 1,\n },\n concurrentUploadSize: 1,\n concurrentUploadRequests: 1,\n },\n validator(config: { concurrentUploadSize?: unknown; concurrentUploadRequests?: unknown }) {\n const assertPositiveInteger = (key: string, value: unknown) => {\n if (value === undefined) {\n return;\n }\n if (typeof value !== 'number' || !Number.isInteger(value) || value < 1) {\n throw new Error(\n `upload plugin config: \"${key}\" must be an integer greater than or equal to 1`\n );\n }\n };\n\n // Server-side ceiling: files processed in parallel within one request.\n assertPositiveInteger('concurrentUploadSize', config.concurrentUploadSize);\n // Client-side parallelism: upload requests the admin fires at once.\n assertPositiveInteger('concurrentUploadRequests', config.concurrentUploadRequests);\n },\n};\n"],"names":["config","default","enabled","provider","sizeLimit","actionOptions","sharp","cache","concurrency","concurrentUploadSize","concurrentUploadRequests","validator","assertPositiveInteger","key","value","undefined","Number","isInteger","Error"],"mappings":";;MAAaA,MAAAA,GAAS;IACpBC,OAAAA,EAAS;QACPC,OAAAA,EAAS,IAAA;QACTC,QAAAA,EAAU,OAAA;QACVC,SAAAA,EAAW,UAAA;AACXC,QAAAA,aAAAA,EAAe,EAAC;QAChBC,KAAAA,EAAO;YACLC,KAAAA,EAAO,KAAA;YACPC,WAAAA,EAAa;AACf,SAAA;QACAC,oBAAAA,EAAsB,CAAA;QACtBC,wBAAAA,EAA0B;AAC5B,KAAA;AACAC,IAAAA,SAAAA,CAAAA,CAAUX,MAA8E,EAAA;QACtF,MAAMY,qBAAAA,GAAwB,CAACC,GAAAA,EAAaC,KAAAA,GAAAA;AAC1C,YAAA,IAAIA,UAAUC,SAAAA,EAAW;AACvB,gBAAA;AACF,YAAA;YACA,IAAI,OAAOD,UAAU,QAAA,IAAY,CAACE,OAAOC,SAAS,CAACH,KAAAA,CAAAA,IAAUA,KAAAA,GAAQ,CAAA,EAAG;AACtE,gBAAA,MAAM,IAAII,KAAAA,CACR,CAAC,uBAAuB,EAAEL,GAAAA,CAAI,+CAA+C,CAAC,CAAA;AAElF,YAAA;AACF,QAAA,CAAA;;QAGAD,qBAAAA,CAAsB,sBAAA,EAAwBZ,OAAOS,oBAAoB,CAAA;;QAEzEG,qBAAAA,CAAsB,0BAAA,EAA4BZ,OAAOU,wBAAwB,CAAA;AACnF,IAAA;AACF;;;;"}
1
+ {"version":3,"file":"config.js","sources":["../../server/src/config.ts"],"sourcesContent":["export const config = {\n default: {\n enabled: true,\n provider: 'local',\n sizeLimit: 1000000000, // 1GB\n actionOptions: {},\n sharp: {\n cache: false,\n concurrency: 1,\n },\n concurrentUploadSize: 1,\n concurrentUploadRequests: 1,\n },\n validator(config: {\n concurrentUploadSize?: unknown;\n concurrentUploadRequests?: unknown;\n sharp?: { limitInputPixels?: unknown } | null;\n }) {\n const assertPositiveInteger = (key: string, value: unknown) => {\n if (value === undefined) {\n return;\n }\n if (typeof value !== 'number' || !Number.isInteger(value) || value < 1) {\n throw new Error(\n `upload plugin config: \"${key}\" must be an integer greater than or equal to 1`\n );\n }\n };\n\n // Server-side ceiling: files processed in parallel within one request.\n assertPositiveInteger('concurrentUploadSize', config.concurrentUploadSize);\n // Client-side parallelism: upload requests the admin fires at once.\n assertPositiveInteger('concurrentUploadRequests', config.concurrentUploadRequests);\n\n // Sharp throws on anything else at every image call, which the upload flow\n // reads as \"not an image\" and skips processing silently.\n const limitInputPixels = config.sharp?.limitInputPixels;\n if (\n limitInputPixels != null &&\n typeof limitInputPixels !== 'boolean' &&\n !(Number.isInteger(limitInputPixels) && (limitInputPixels as number) >= 0)\n ) {\n throw new Error(\n 'upload plugin config: \"sharp.limitInputPixels\" must be a boolean or an integer greater than or equal to 0 (use env.int() to read it from the environment)'\n );\n }\n },\n};\n"],"names":["config","default","enabled","provider","sizeLimit","actionOptions","sharp","cache","concurrency","concurrentUploadSize","concurrentUploadRequests","validator","assertPositiveInteger","key","value","undefined","Number","isInteger","Error","limitInputPixels"],"mappings":";;MAAaA,MAAAA,GAAS;IACpBC,OAAAA,EAAS;QACPC,OAAAA,EAAS,IAAA;QACTC,QAAAA,EAAU,OAAA;QACVC,SAAAA,EAAW,UAAA;AACXC,QAAAA,aAAAA,EAAe,EAAC;QAChBC,KAAAA,EAAO;YACLC,KAAAA,EAAO,KAAA;YACPC,WAAAA,EAAa;AACf,SAAA;QACAC,oBAAAA,EAAsB,CAAA;QACtBC,wBAAAA,EAA0B;AAC5B,KAAA;AACAC,IAAAA,SAAAA,CAAAA,CAAUX,MAIT,EAAA;QACC,MAAMY,qBAAAA,GAAwB,CAACC,GAAAA,EAAaC,KAAAA,GAAAA;AAC1C,YAAA,IAAIA,UAAUC,SAAAA,EAAW;AACvB,gBAAA;AACF,YAAA;YACA,IAAI,OAAOD,UAAU,QAAA,IAAY,CAACE,OAAOC,SAAS,CAACH,KAAAA,CAAAA,IAAUA,KAAAA,GAAQ,CAAA,EAAG;AACtE,gBAAA,MAAM,IAAII,KAAAA,CACR,CAAC,uBAAuB,EAAEL,GAAAA,CAAI,+CAA+C,CAAC,CAAA;AAElF,YAAA;AACF,QAAA,CAAA;;QAGAD,qBAAAA,CAAsB,sBAAA,EAAwBZ,OAAOS,oBAAoB,CAAA;;QAEzEG,qBAAAA,CAAsB,0BAAA,EAA4BZ,OAAOU,wBAAwB,CAAA;;;QAIjF,MAAMS,gBAAAA,GAAmBnB,MAAAA,CAAOM,KAAK,EAAEa,gBAAAA;AACvC,QAAA,IACEA,gBAAAA,IAAoB,IAAA,IACpB,OAAOA,gBAAAA,KAAqB,aAC5B,EAAEH,MAAAA,CAAOC,SAAS,CAACE,gBAAAA,CAAAA,IAAqB,gBAACA,IAA+B,CAAA,CAAA,EACxE;AACA,YAAA,MAAM,IAAID,KAAAA,CACR,2JAAA,CAAA;AAEJ,QAAA;AACF,IAAA;AACF;;;;"}
@@ -24,6 +24,12 @@ const config = {
24
24
  assertPositiveInteger('concurrentUploadSize', config.concurrentUploadSize);
25
25
  // Client-side parallelism: upload requests the admin fires at once.
26
26
  assertPositiveInteger('concurrentUploadRequests', config.concurrentUploadRequests);
27
+ // Sharp throws on anything else at every image call, which the upload flow
28
+ // reads as "not an image" and skips processing silently.
29
+ const limitInputPixels = config.sharp?.limitInputPixels;
30
+ if (limitInputPixels != null && typeof limitInputPixels !== 'boolean' && !(Number.isInteger(limitInputPixels) && limitInputPixels >= 0)) {
31
+ throw new Error('upload plugin config: "sharp.limitInputPixels" must be a boolean or an integer greater than or equal to 0 (use env.int() to read it from the environment)');
32
+ }
27
33
  }
28
34
  };
29
35
 
@@ -1 +1 @@
1
- {"version":3,"file":"config.mjs","sources":["../../server/src/config.ts"],"sourcesContent":["export const config = {\n default: {\n enabled: true,\n provider: 'local',\n sizeLimit: 1000000000, // 1GB\n actionOptions: {},\n sharp: {\n cache: false,\n concurrency: 1,\n },\n concurrentUploadSize: 1,\n concurrentUploadRequests: 1,\n },\n validator(config: { concurrentUploadSize?: unknown; concurrentUploadRequests?: unknown }) {\n const assertPositiveInteger = (key: string, value: unknown) => {\n if (value === undefined) {\n return;\n }\n if (typeof value !== 'number' || !Number.isInteger(value) || value < 1) {\n throw new Error(\n `upload plugin config: \"${key}\" must be an integer greater than or equal to 1`\n );\n }\n };\n\n // Server-side ceiling: files processed in parallel within one request.\n assertPositiveInteger('concurrentUploadSize', config.concurrentUploadSize);\n // Client-side parallelism: upload requests the admin fires at once.\n assertPositiveInteger('concurrentUploadRequests', config.concurrentUploadRequests);\n },\n};\n"],"names":["config","default","enabled","provider","sizeLimit","actionOptions","sharp","cache","concurrency","concurrentUploadSize","concurrentUploadRequests","validator","assertPositiveInteger","key","value","undefined","Number","isInteger","Error"],"mappings":"MAAaA,MAAAA,GAAS;IACpBC,OAAAA,EAAS;QACPC,OAAAA,EAAS,IAAA;QACTC,QAAAA,EAAU,OAAA;QACVC,SAAAA,EAAW,UAAA;AACXC,QAAAA,aAAAA,EAAe,EAAC;QAChBC,KAAAA,EAAO;YACLC,KAAAA,EAAO,KAAA;YACPC,WAAAA,EAAa;AACf,SAAA;QACAC,oBAAAA,EAAsB,CAAA;QACtBC,wBAAAA,EAA0B;AAC5B,KAAA;AACAC,IAAAA,SAAAA,CAAAA,CAAUX,MAA8E,EAAA;QACtF,MAAMY,qBAAAA,GAAwB,CAACC,GAAAA,EAAaC,KAAAA,GAAAA;AAC1C,YAAA,IAAIA,UAAUC,SAAAA,EAAW;AACvB,gBAAA;AACF,YAAA;YACA,IAAI,OAAOD,UAAU,QAAA,IAAY,CAACE,OAAOC,SAAS,CAACH,KAAAA,CAAAA,IAAUA,KAAAA,GAAQ,CAAA,EAAG;AACtE,gBAAA,MAAM,IAAII,KAAAA,CACR,CAAC,uBAAuB,EAAEL,GAAAA,CAAI,+CAA+C,CAAC,CAAA;AAElF,YAAA;AACF,QAAA,CAAA;;QAGAD,qBAAAA,CAAsB,sBAAA,EAAwBZ,OAAOS,oBAAoB,CAAA;;QAEzEG,qBAAAA,CAAsB,0BAAA,EAA4BZ,OAAOU,wBAAwB,CAAA;AACnF,IAAA;AACF;;;;"}
1
+ {"version":3,"file":"config.mjs","sources":["../../server/src/config.ts"],"sourcesContent":["export const config = {\n default: {\n enabled: true,\n provider: 'local',\n sizeLimit: 1000000000, // 1GB\n actionOptions: {},\n sharp: {\n cache: false,\n concurrency: 1,\n },\n concurrentUploadSize: 1,\n concurrentUploadRequests: 1,\n },\n validator(config: {\n concurrentUploadSize?: unknown;\n concurrentUploadRequests?: unknown;\n sharp?: { limitInputPixels?: unknown } | null;\n }) {\n const assertPositiveInteger = (key: string, value: unknown) => {\n if (value === undefined) {\n return;\n }\n if (typeof value !== 'number' || !Number.isInteger(value) || value < 1) {\n throw new Error(\n `upload plugin config: \"${key}\" must be an integer greater than or equal to 1`\n );\n }\n };\n\n // Server-side ceiling: files processed in parallel within one request.\n assertPositiveInteger('concurrentUploadSize', config.concurrentUploadSize);\n // Client-side parallelism: upload requests the admin fires at once.\n assertPositiveInteger('concurrentUploadRequests', config.concurrentUploadRequests);\n\n // Sharp throws on anything else at every image call, which the upload flow\n // reads as \"not an image\" and skips processing silently.\n const limitInputPixels = config.sharp?.limitInputPixels;\n if (\n limitInputPixels != null &&\n typeof limitInputPixels !== 'boolean' &&\n !(Number.isInteger(limitInputPixels) && (limitInputPixels as number) >= 0)\n ) {\n throw new Error(\n 'upload plugin config: \"sharp.limitInputPixels\" must be a boolean or an integer greater than or equal to 0 (use env.int() to read it from the environment)'\n );\n }\n },\n};\n"],"names":["config","default","enabled","provider","sizeLimit","actionOptions","sharp","cache","concurrency","concurrentUploadSize","concurrentUploadRequests","validator","assertPositiveInteger","key","value","undefined","Number","isInteger","Error","limitInputPixels"],"mappings":"MAAaA,MAAAA,GAAS;IACpBC,OAAAA,EAAS;QACPC,OAAAA,EAAS,IAAA;QACTC,QAAAA,EAAU,OAAA;QACVC,SAAAA,EAAW,UAAA;AACXC,QAAAA,aAAAA,EAAe,EAAC;QAChBC,KAAAA,EAAO;YACLC,KAAAA,EAAO,KAAA;YACPC,WAAAA,EAAa;AACf,SAAA;QACAC,oBAAAA,EAAsB,CAAA;QACtBC,wBAAAA,EAA0B;AAC5B,KAAA;AACAC,IAAAA,SAAAA,CAAAA,CAAUX,MAIT,EAAA;QACC,MAAMY,qBAAAA,GAAwB,CAACC,GAAAA,EAAaC,KAAAA,GAAAA;AAC1C,YAAA,IAAIA,UAAUC,SAAAA,EAAW;AACvB,gBAAA;AACF,YAAA;YACA,IAAI,OAAOD,UAAU,QAAA,IAAY,CAACE,OAAOC,SAAS,CAACH,KAAAA,CAAAA,IAAUA,KAAAA,GAAQ,CAAA,EAAG;AACtE,gBAAA,MAAM,IAAII,KAAAA,CACR,CAAC,uBAAuB,EAAEL,GAAAA,CAAI,+CAA+C,CAAC,CAAA;AAElF,YAAA;AACF,QAAA,CAAA;;QAGAD,qBAAAA,CAAsB,sBAAA,EAAwBZ,OAAOS,oBAAoB,CAAA;;QAEzEG,qBAAAA,CAAsB,0BAAA,EAA4BZ,OAAOU,wBAAwB,CAAA;;;QAIjF,MAAMS,gBAAAA,GAAmBnB,MAAAA,CAAOM,KAAK,EAAEa,gBAAAA;AACvC,QAAA,IACEA,gBAAAA,IAAoB,IAAA,IACpB,OAAOA,gBAAAA,KAAqB,aAC5B,EAAEH,MAAAA,CAAOC,SAAS,CAACE,gBAAAA,CAAAA,IAAqB,gBAACA,IAA+B,CAAA,CAAA,EACxE;AACA,YAAA,MAAM,IAAID,KAAAA,CACR,2JAAA,CAAA;AAEJ,QAAA;AACF,IAAA;AACF;;;;"}
@@ -15,7 +15,11 @@ var adminSettings = {
15
15
  if (userAbility.cannot(constants.ACTIONS.readSettings, constants.FILE_MODEL_UID)) {
16
16
  return ctx.forbidden();
17
17
  }
18
- const validated = await settings.default(body);
18
+ // Validation runs in strict mode, which skips schema defaults. Casting the
19
+ // validated body applies them, so a body without `aiMetadata` stores `true`
20
+ // (the value `aiMetadata.isEnabled()` assumes) instead of no key at all.
21
+ // The cast only adds defaults to an already valid body, so it is a `Settings`.
22
+ const validated = settings.settingsSchema.cast(await settings.default(body));
19
23
  const source = validated;
20
24
  const data = Object.fromEntries(SETTINGS_KEYS.filter((key)=>key in source).map((key)=>[
21
25
  key,
@@ -1 +1 @@
1
- {"version":3,"file":"admin-settings.js","sources":["../../../server/src/controllers/admin-settings.ts"],"sourcesContent":["import type { Context } from 'koa';\n\nimport { getService } from '../utils';\nimport { ACTIONS, FILE_MODEL_UID } from '../constants';\n\nimport type { Config } from '../types';\nimport validateSettings, { settingsSchema } from './validation/admin/settings';\n\n// The stored settings' known keys. `GET /upload/settings` echoes read-only\n// config (e.g. `concurrentUploadRequests`) alongside them, and the legacy\n// Settings page PUTs the whole payload back — narrowing to these keys keeps\n// those echoes out of the store. Derived from the schema so it can't drift.\nconst SETTINGS_KEYS = Object.keys(settingsSchema.fields);\n\nexport default {\n async updateSettings(ctx: Context) {\n const {\n request: { body },\n state: { userAbility },\n } = ctx;\n\n if (userAbility.cannot(ACTIONS.readSettings, FILE_MODEL_UID)) {\n return ctx.forbidden();\n }\n\n const validated = await validateSettings(body);\n const source = validated as Record<string, unknown>;\n const data = Object.fromEntries(\n SETTINGS_KEYS.filter((key) => key in source).map((key) => [key, source[key]])\n ) as typeof validated;\n\n await getService('upload').setSettings(data);\n\n ctx.body = { data };\n },\n\n async getSettings(ctx: Context) {\n // Gated on `plugin::upload.read` by the route policy.\n const data = await getService('upload').getSettings();\n\n // Read-only echo of the app config so the admin knows how many upload\n // requests it may fire in parallel. Distinct from `concurrentUploadSize`,\n // which is the server-side per-request processing ceiling. Deployments that\n // need to bound this override the config.\n const { concurrentUploadRequests = 1 } = strapi.config.get<Config>('plugin::upload');\n\n ctx.body = {\n data: {\n ...data,\n concurrentUploadRequests,\n aiMetadataAvailable: getService('aiMetadataProvider').hasProvider(),\n },\n };\n },\n};\n"],"names":["SETTINGS_KEYS","Object","keys","settingsSchema","fields","updateSettings","ctx","request","body","state","userAbility","cannot","ACTIONS","readSettings","FILE_MODEL_UID","forbidden","validated","validateSettings","source","data","fromEntries","filter","key","map","getService","setSettings","getSettings","concurrentUploadRequests","strapi","config","get","aiMetadataAvailable","hasProvider"],"mappings":";;;;;;AAQA;AACA;AACA;AACA;AACA,MAAMA,aAAAA,GAAgBC,MAAAA,CAAOC,IAAI,CAACC,wBAAeC,MAAM,CAAA;AAEvD,oBAAe;AACb,IAAA,MAAMC,gBAAeC,GAAY,EAAA;QAC/B,MAAM,EACJC,OAAAA,EAAS,EAAEC,IAAI,EAAE,EACjBC,KAAAA,EAAO,EAAEC,WAAW,EAAE,EACvB,GAAGJ,GAAAA;AAEJ,QAAA,IAAII,YAAYC,MAAM,CAACC,iBAAAA,CAAQC,YAAY,EAAEC,wBAAAA,CAAAA,EAAiB;AAC5D,YAAA,OAAOR,IAAIS,SAAS,EAAA;AACtB,QAAA;QAEA,MAAMC,SAAAA,GAAY,MAAMC,gBAAAA,CAAiBT,IAAAA,CAAAA;AACzC,QAAA,MAAMU,MAAAA,GAASF,SAAAA;AACf,QAAA,MAAMG,IAAAA,GAAOlB,MAAAA,CAAOmB,WAAW,CAC7BpB,cAAcqB,MAAM,CAAC,CAACC,GAAAA,GAAQA,GAAAA,IAAOJ,MAAAA,CAAAA,CAAQK,GAAG,CAAC,CAACD,GAAAA,GAAQ;AAACA,gBAAAA,GAAAA;AAAKJ,gBAAAA,MAAM,CAACI,GAAAA;AAAK,aAAA,CAAA,CAAA;QAG9E,MAAME,gBAAAA,CAAW,QAAA,CAAA,CAAUC,WAAW,CAACN,IAAAA,CAAAA;AAEvCb,QAAAA,GAAAA,CAAIE,IAAI,GAAG;AAAEW,YAAAA;AAAK,SAAA;AACpB,IAAA,CAAA;AAEA,IAAA,MAAMO,aAAYpB,GAAY,EAAA;;AAE5B,QAAA,MAAMa,IAAAA,GAAO,MAAMK,gBAAAA,CAAW,QAAA,CAAA,CAAUE,WAAW,EAAA;;;;;QAMnD,MAAM,EAAEC,2BAA2B,CAAC,EAAE,GAAGC,MAAAA,CAAOC,MAAM,CAACC,GAAG,CAAS,gBAAA,CAAA;AAEnExB,QAAAA,GAAAA,CAAIE,IAAI,GAAG;YACTW,IAAAA,EAAM;AACJ,gBAAA,GAAGA,IAAI;AACPQ,gBAAAA,wBAAAA;gBACAI,mBAAAA,EAAqBP,gBAAAA,CAAW,sBAAsBQ,WAAW;AACnE;AACF,SAAA;AACF,IAAA;AACF,CAAA;;;;"}
1
+ {"version":3,"file":"admin-settings.js","sources":["../../../server/src/controllers/admin-settings.ts"],"sourcesContent":["import type { Context } from 'koa';\n\nimport { getService } from '../utils';\nimport { ACTIONS, FILE_MODEL_UID } from '../constants';\n\nimport type { Config } from '../types';\nimport validateSettings, { settingsSchema, type Settings } from './validation/admin/settings';\n\n// The stored settings' known keys. `GET /upload/settings` echoes read-only\n// config (e.g. `concurrentUploadRequests`) alongside them, and the legacy\n// Settings page PUTs the whole payload back — narrowing to these keys keeps\n// those echoes out of the store. Derived from the schema so it can't drift.\nconst SETTINGS_KEYS = Object.keys(settingsSchema.fields);\n\nexport default {\n async updateSettings(ctx: Context) {\n const {\n request: { body },\n state: { userAbility },\n } = ctx;\n\n if (userAbility.cannot(ACTIONS.readSettings, FILE_MODEL_UID)) {\n return ctx.forbidden();\n }\n\n // Validation runs in strict mode, which skips schema defaults. Casting the\n // validated body applies them, so a body without `aiMetadata` stores `true`\n // (the value `aiMetadata.isEnabled()` assumes) instead of no key at all.\n // The cast only adds defaults to an already valid body, so it is a `Settings`.\n const validated = settingsSchema.cast(await validateSettings(body)) as Settings;\n const source = validated as Record<string, unknown>;\n const data = Object.fromEntries(\n SETTINGS_KEYS.filter((key) => key in source).map((key) => [key, source[key]])\n ) as typeof validated;\n\n await getService('upload').setSettings(data);\n\n ctx.body = { data };\n },\n\n async getSettings(ctx: Context) {\n // Gated on `plugin::upload.read` by the route policy.\n const data = await getService('upload').getSettings();\n\n // Read-only echo of the app config so the admin knows how many upload\n // requests it may fire in parallel. Distinct from `concurrentUploadSize`,\n // which is the server-side per-request processing ceiling. Deployments that\n // need to bound this override the config.\n const { concurrentUploadRequests = 1 } = strapi.config.get<Config>('plugin::upload');\n\n ctx.body = {\n data: {\n ...data,\n concurrentUploadRequests,\n aiMetadataAvailable: getService('aiMetadataProvider').hasProvider(),\n },\n };\n },\n};\n"],"names":["SETTINGS_KEYS","Object","keys","settingsSchema","fields","updateSettings","ctx","request","body","state","userAbility","cannot","ACTIONS","readSettings","FILE_MODEL_UID","forbidden","validated","cast","validateSettings","source","data","fromEntries","filter","key","map","getService","setSettings","getSettings","concurrentUploadRequests","strapi","config","get","aiMetadataAvailable","hasProvider"],"mappings":";;;;;;AAQA;AACA;AACA;AACA;AACA,MAAMA,aAAAA,GAAgBC,MAAAA,CAAOC,IAAI,CAACC,wBAAeC,MAAM,CAAA;AAEvD,oBAAe;AACb,IAAA,MAAMC,gBAAeC,GAAY,EAAA;QAC/B,MAAM,EACJC,OAAAA,EAAS,EAAEC,IAAI,EAAE,EACjBC,KAAAA,EAAO,EAAEC,WAAW,EAAE,EACvB,GAAGJ,GAAAA;AAEJ,QAAA,IAAII,YAAYC,MAAM,CAACC,iBAAAA,CAAQC,YAAY,EAAEC,wBAAAA,CAAAA,EAAiB;AAC5D,YAAA,OAAOR,IAAIS,SAAS,EAAA;AACtB,QAAA;;;;;AAMA,QAAA,MAAMC,SAAAA,GAAYb,uBAAAA,CAAec,IAAI,CAAC,MAAMC,gBAAAA,CAAiBV,IAAAA,CAAAA,CAAAA;AAC7D,QAAA,MAAMW,MAAAA,GAASH,SAAAA;AACf,QAAA,MAAMI,IAAAA,GAAOnB,MAAAA,CAAOoB,WAAW,CAC7BrB,cAAcsB,MAAM,CAAC,CAACC,GAAAA,GAAQA,GAAAA,IAAOJ,MAAAA,CAAAA,CAAQK,GAAG,CAAC,CAACD,GAAAA,GAAQ;AAACA,gBAAAA,GAAAA;AAAKJ,gBAAAA,MAAM,CAACI,GAAAA;AAAK,aAAA,CAAA,CAAA;QAG9E,MAAME,gBAAAA,CAAW,QAAA,CAAA,CAAUC,WAAW,CAACN,IAAAA,CAAAA;AAEvCd,QAAAA,GAAAA,CAAIE,IAAI,GAAG;AAAEY,YAAAA;AAAK,SAAA;AACpB,IAAA,CAAA;AAEA,IAAA,MAAMO,aAAYrB,GAAY,EAAA;;AAE5B,QAAA,MAAMc,IAAAA,GAAO,MAAMK,gBAAAA,CAAW,QAAA,CAAA,CAAUE,WAAW,EAAA;;;;;QAMnD,MAAM,EAAEC,2BAA2B,CAAC,EAAE,GAAGC,MAAAA,CAAOC,MAAM,CAACC,GAAG,CAAS,gBAAA,CAAA;AAEnEzB,QAAAA,GAAAA,CAAIE,IAAI,GAAG;YACTY,IAAAA,EAAM;AACJ,gBAAA,GAAGA,IAAI;AACPQ,gBAAAA,wBAAAA;gBACAI,mBAAAA,EAAqBP,gBAAAA,CAAW,sBAAsBQ,WAAW;AACnE;AACF,SAAA;AACF,IAAA;AACF,CAAA;;;;"}
@@ -13,7 +13,11 @@ var adminSettings = {
13
13
  if (userAbility.cannot(ACTIONS.readSettings, FILE_MODEL_UID)) {
14
14
  return ctx.forbidden();
15
15
  }
16
- const validated = await validateSettings(body);
16
+ // Validation runs in strict mode, which skips schema defaults. Casting the
17
+ // validated body applies them, so a body without `aiMetadata` stores `true`
18
+ // (the value `aiMetadata.isEnabled()` assumes) instead of no key at all.
19
+ // The cast only adds defaults to an already valid body, so it is a `Settings`.
20
+ const validated = settingsSchema.cast(await validateSettings(body));
17
21
  const source = validated;
18
22
  const data = Object.fromEntries(SETTINGS_KEYS.filter((key)=>key in source).map((key)=>[
19
23
  key,
@@ -1 +1 @@
1
- {"version":3,"file":"admin-settings.mjs","sources":["../../../server/src/controllers/admin-settings.ts"],"sourcesContent":["import type { Context } from 'koa';\n\nimport { getService } from '../utils';\nimport { ACTIONS, FILE_MODEL_UID } from '../constants';\n\nimport type { Config } from '../types';\nimport validateSettings, { settingsSchema } from './validation/admin/settings';\n\n// The stored settings' known keys. `GET /upload/settings` echoes read-only\n// config (e.g. `concurrentUploadRequests`) alongside them, and the legacy\n// Settings page PUTs the whole payload back — narrowing to these keys keeps\n// those echoes out of the store. Derived from the schema so it can't drift.\nconst SETTINGS_KEYS = Object.keys(settingsSchema.fields);\n\nexport default {\n async updateSettings(ctx: Context) {\n const {\n request: { body },\n state: { userAbility },\n } = ctx;\n\n if (userAbility.cannot(ACTIONS.readSettings, FILE_MODEL_UID)) {\n return ctx.forbidden();\n }\n\n const validated = await validateSettings(body);\n const source = validated as Record<string, unknown>;\n const data = Object.fromEntries(\n SETTINGS_KEYS.filter((key) => key in source).map((key) => [key, source[key]])\n ) as typeof validated;\n\n await getService('upload').setSettings(data);\n\n ctx.body = { data };\n },\n\n async getSettings(ctx: Context) {\n // Gated on `plugin::upload.read` by the route policy.\n const data = await getService('upload').getSettings();\n\n // Read-only echo of the app config so the admin knows how many upload\n // requests it may fire in parallel. Distinct from `concurrentUploadSize`,\n // which is the server-side per-request processing ceiling. Deployments that\n // need to bound this override the config.\n const { concurrentUploadRequests = 1 } = strapi.config.get<Config>('plugin::upload');\n\n ctx.body = {\n data: {\n ...data,\n concurrentUploadRequests,\n aiMetadataAvailable: getService('aiMetadataProvider').hasProvider(),\n },\n };\n },\n};\n"],"names":["SETTINGS_KEYS","Object","keys","settingsSchema","fields","updateSettings","ctx","request","body","state","userAbility","cannot","ACTIONS","readSettings","FILE_MODEL_UID","forbidden","validated","validateSettings","source","data","fromEntries","filter","key","map","getService","setSettings","getSettings","concurrentUploadRequests","strapi","config","get","aiMetadataAvailable","hasProvider"],"mappings":";;;;AAQA;AACA;AACA;AACA;AACA,MAAMA,aAAAA,GAAgBC,MAAAA,CAAOC,IAAI,CAACC,eAAeC,MAAM,CAAA;AAEvD,oBAAe;AACb,IAAA,MAAMC,gBAAeC,GAAY,EAAA;QAC/B,MAAM,EACJC,OAAAA,EAAS,EAAEC,IAAI,EAAE,EACjBC,KAAAA,EAAO,EAAEC,WAAW,EAAE,EACvB,GAAGJ,GAAAA;AAEJ,QAAA,IAAII,YAAYC,MAAM,CAACC,OAAAA,CAAQC,YAAY,EAAEC,cAAAA,CAAAA,EAAiB;AAC5D,YAAA,OAAOR,IAAIS,SAAS,EAAA;AACtB,QAAA;QAEA,MAAMC,SAAAA,GAAY,MAAMC,gBAAAA,CAAiBT,IAAAA,CAAAA;AACzC,QAAA,MAAMU,MAAAA,GAASF,SAAAA;AACf,QAAA,MAAMG,IAAAA,GAAOlB,MAAAA,CAAOmB,WAAW,CAC7BpB,cAAcqB,MAAM,CAAC,CAACC,GAAAA,GAAQA,GAAAA,IAAOJ,MAAAA,CAAAA,CAAQK,GAAG,CAAC,CAACD,GAAAA,GAAQ;AAACA,gBAAAA,GAAAA;AAAKJ,gBAAAA,MAAM,CAACI,GAAAA;AAAK,aAAA,CAAA,CAAA;QAG9E,MAAME,UAAAA,CAAW,QAAA,CAAA,CAAUC,WAAW,CAACN,IAAAA,CAAAA;AAEvCb,QAAAA,GAAAA,CAAIE,IAAI,GAAG;AAAEW,YAAAA;AAAK,SAAA;AACpB,IAAA,CAAA;AAEA,IAAA,MAAMO,aAAYpB,GAAY,EAAA;;AAE5B,QAAA,MAAMa,IAAAA,GAAO,MAAMK,UAAAA,CAAW,QAAA,CAAA,CAAUE,WAAW,EAAA;;;;;QAMnD,MAAM,EAAEC,2BAA2B,CAAC,EAAE,GAAGC,MAAAA,CAAOC,MAAM,CAACC,GAAG,CAAS,gBAAA,CAAA;AAEnExB,QAAAA,GAAAA,CAAIE,IAAI,GAAG;YACTW,IAAAA,EAAM;AACJ,gBAAA,GAAGA,IAAI;AACPQ,gBAAAA,wBAAAA;gBACAI,mBAAAA,EAAqBP,UAAAA,CAAW,sBAAsBQ,WAAW;AACnE;AACF,SAAA;AACF,IAAA;AACF,CAAA;;;;"}
1
+ {"version":3,"file":"admin-settings.mjs","sources":["../../../server/src/controllers/admin-settings.ts"],"sourcesContent":["import type { Context } from 'koa';\n\nimport { getService } from '../utils';\nimport { ACTIONS, FILE_MODEL_UID } from '../constants';\n\nimport type { Config } from '../types';\nimport validateSettings, { settingsSchema, type Settings } from './validation/admin/settings';\n\n// The stored settings' known keys. `GET /upload/settings` echoes read-only\n// config (e.g. `concurrentUploadRequests`) alongside them, and the legacy\n// Settings page PUTs the whole payload back — narrowing to these keys keeps\n// those echoes out of the store. Derived from the schema so it can't drift.\nconst SETTINGS_KEYS = Object.keys(settingsSchema.fields);\n\nexport default {\n async updateSettings(ctx: Context) {\n const {\n request: { body },\n state: { userAbility },\n } = ctx;\n\n if (userAbility.cannot(ACTIONS.readSettings, FILE_MODEL_UID)) {\n return ctx.forbidden();\n }\n\n // Validation runs in strict mode, which skips schema defaults. Casting the\n // validated body applies them, so a body without `aiMetadata` stores `true`\n // (the value `aiMetadata.isEnabled()` assumes) instead of no key at all.\n // The cast only adds defaults to an already valid body, so it is a `Settings`.\n const validated = settingsSchema.cast(await validateSettings(body)) as Settings;\n const source = validated as Record<string, unknown>;\n const data = Object.fromEntries(\n SETTINGS_KEYS.filter((key) => key in source).map((key) => [key, source[key]])\n ) as typeof validated;\n\n await getService('upload').setSettings(data);\n\n ctx.body = { data };\n },\n\n async getSettings(ctx: Context) {\n // Gated on `plugin::upload.read` by the route policy.\n const data = await getService('upload').getSettings();\n\n // Read-only echo of the app config so the admin knows how many upload\n // requests it may fire in parallel. Distinct from `concurrentUploadSize`,\n // which is the server-side per-request processing ceiling. Deployments that\n // need to bound this override the config.\n const { concurrentUploadRequests = 1 } = strapi.config.get<Config>('plugin::upload');\n\n ctx.body = {\n data: {\n ...data,\n concurrentUploadRequests,\n aiMetadataAvailable: getService('aiMetadataProvider').hasProvider(),\n },\n };\n },\n};\n"],"names":["SETTINGS_KEYS","Object","keys","settingsSchema","fields","updateSettings","ctx","request","body","state","userAbility","cannot","ACTIONS","readSettings","FILE_MODEL_UID","forbidden","validated","cast","validateSettings","source","data","fromEntries","filter","key","map","getService","setSettings","getSettings","concurrentUploadRequests","strapi","config","get","aiMetadataAvailable","hasProvider"],"mappings":";;;;AAQA;AACA;AACA;AACA;AACA,MAAMA,aAAAA,GAAgBC,MAAAA,CAAOC,IAAI,CAACC,eAAeC,MAAM,CAAA;AAEvD,oBAAe;AACb,IAAA,MAAMC,gBAAeC,GAAY,EAAA;QAC/B,MAAM,EACJC,OAAAA,EAAS,EAAEC,IAAI,EAAE,EACjBC,KAAAA,EAAO,EAAEC,WAAW,EAAE,EACvB,GAAGJ,GAAAA;AAEJ,QAAA,IAAII,YAAYC,MAAM,CAACC,OAAAA,CAAQC,YAAY,EAAEC,cAAAA,CAAAA,EAAiB;AAC5D,YAAA,OAAOR,IAAIS,SAAS,EAAA;AACtB,QAAA;;;;;AAMA,QAAA,MAAMC,SAAAA,GAAYb,cAAAA,CAAec,IAAI,CAAC,MAAMC,gBAAAA,CAAiBV,IAAAA,CAAAA,CAAAA;AAC7D,QAAA,MAAMW,MAAAA,GAASH,SAAAA;AACf,QAAA,MAAMI,IAAAA,GAAOnB,MAAAA,CAAOoB,WAAW,CAC7BrB,cAAcsB,MAAM,CAAC,CAACC,GAAAA,GAAQA,GAAAA,IAAOJ,MAAAA,CAAAA,CAAQK,GAAG,CAAC,CAACD,GAAAA,GAAQ;AAACA,gBAAAA,GAAAA;AAAKJ,gBAAAA,MAAM,CAACI,GAAAA;AAAK,aAAA,CAAA,CAAA;QAG9E,MAAME,UAAAA,CAAW,QAAA,CAAA,CAAUC,WAAW,CAACN,IAAAA,CAAAA;AAEvCd,QAAAA,GAAAA,CAAIE,IAAI,GAAG;AAAEY,YAAAA;AAAK,SAAA;AACpB,IAAA,CAAA;AAEA,IAAA,MAAMO,aAAYrB,GAAY,EAAA;;AAE5B,QAAA,MAAMc,IAAAA,GAAO,MAAMK,UAAAA,CAAW,QAAA,CAAA,CAAUE,WAAW,EAAA;;;;;QAMnD,MAAM,EAAEC,2BAA2B,CAAC,EAAE,GAAGC,MAAAA,CAAOC,MAAM,CAACC,GAAG,CAAS,gBAAA,CAAA;AAEnEzB,QAAAA,GAAAA,CAAIE,IAAI,GAAG;YACTY,IAAAA,EAAM;AACJ,gBAAA,GAAGA,IAAI;AACPQ,gBAAAA,wBAAAA;gBACAI,mBAAAA,EAAqBP,UAAAA,CAAW,sBAAsBQ,WAAW;AACnE;AACF,SAAA;AACF,IAAA;AACF,CAAA;;;;"}
@@ -1 +1 @@
1
- {"version":3,"file":"upload.js","sources":["../../../../../server/src/controllers/validation/admin/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\nimport { getService } from '../../../utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup.object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n folder: yup\n .strapiID()\n .nullable()\n .test('folder-exists', 'the folder does not exist', async (folderId) => {\n if (folderId == null) {\n return true;\n }\n\n const exists = await getService('folder').exists({ id: folderId });\n\n return exists;\n }),\n});\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n | yup.InferType<typeof uploadSchema>\n | yup.InferType<typeof multiUploadSchema>;\n\nconst bulkUpdatesSchema = yup.object({\n updates: yup\n .array()\n .of(\n yup.object({\n id: yup.number().required(),\n fileInfo: fileInfoSchema.required(),\n })\n )\n .min(1)\n .required(),\n});\n\nexport const validateBulkUpdateBody = validateYupSchema(bulkUpdatesSchema);\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","folder","strapiID","test","folderId","exists","getService","id","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict","bulkUpdatesSchema","updates","validateBulkUpdateBody"],"mappings":";;;;;AAGA,MAAMA,gBAAAA,GAAmBC,SAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,SAAAA,CAAIC,MAAM,CAAC;IAChCU,IAAAA,EAAMX,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB,gBAAAA;IACZiB,MAAAA,EAAQhB,SAAAA,CACLiB,QAAQ,EAAA,CACRT,QAAQ,GACRU,IAAI,CAAC,eAAA,EAAiB,2BAAA,EAA6B,OAAOC,QAAAA,GAAAA;AACzD,QAAA,IAAIA,YAAY,IAAA,EAAM;YACpB,OAAO,IAAA;AACT,QAAA;AAEA,QAAA,MAAMC,MAAAA,GAAS,MAAMC,gBAAAA,CAAW,QAAA,CAAA,CAAUD,MAAM,CAAC;YAAEE,EAAAA,EAAIH;AAAS,SAAA,CAAA;QAEhE,OAAOC,MAAAA;AACT,IAAA,CAAA;AACJ,CAAA,CAAA;AAEA,MAAMG,YAAAA,GAAevB,SAAAA,CAAIC,MAAM,CAAC;IAC9BuB,QAAAA,EAAUd;AACZ,CAAA,CAAA;AAEA,MAAMe,iBAAAA,GAAoBzB,SAAAA,CAAIC,MAAM,CAAC;AACnCuB,IAAAA,QAAAA,EAAUxB,SAAAA,CAAI0B,KAAK,EAAA,CAAGC,EAAE,CAACjB,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMkB,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,wBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;AAQA,MAAMK,iBAAAA,GAAoBlC,SAAAA,CAAIC,MAAM,CAAC;AACnCkC,IAAAA,OAAAA,EAASnC,UACN0B,KAAK,EAAA,CACLC,EAAE,CACD3B,SAAAA,CAAIC,MAAM,CAAC;QACTqB,EAAAA,EAAItB,SAAAA,CAAIG,MAAM,EAAA,CAAGG,QAAQ,EAAA;AACzBkB,QAAAA,QAAAA,EAAUd,eAAeJ,QAAQ;KACnC,CAAA,CAAA,CAEDF,GAAG,CAAC,CAAA,CAAA,CACJE,QAAQ;AACb,CAAA,CAAA;AAEO,MAAM8B,sBAAAA,GAAyBJ,uBAAAA,CAAkBE,iBAAAA;;;;;"}
1
+ {"version":3,"file":"upload.js","sources":["../../../../../server/src/controllers/validation/admin/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\nimport { getService } from '../../../utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup.object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n folder: yup\n .strapiID()\n .nullable()\n .test('folder-exists', 'the folder does not exist', async (folderId) => {\n if (folderId == null) {\n return true;\n }\n\n const exists = await getService('folder').exists({ id: folderId });\n\n return exists;\n }),\n});\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n yup.InferType<typeof uploadSchema> | yup.InferType<typeof multiUploadSchema>;\n\nconst bulkUpdatesSchema = yup.object({\n updates: yup\n .array()\n .of(\n yup.object({\n id: yup.number().required(),\n fileInfo: fileInfoSchema.required(),\n })\n )\n .min(1)\n .required(),\n});\n\nexport const validateBulkUpdateBody = validateYupSchema(bulkUpdatesSchema);\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","folder","strapiID","test","folderId","exists","getService","id","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict","bulkUpdatesSchema","updates","validateBulkUpdateBody"],"mappings":";;;;;AAGA,MAAMA,gBAAAA,GAAmBC,SAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,SAAAA,CAAIC,MAAM,CAAC;IAChCU,IAAAA,EAAMX,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB,gBAAAA;IACZiB,MAAAA,EAAQhB,SAAAA,CACLiB,QAAQ,EAAA,CACRT,QAAQ,GACRU,IAAI,CAAC,eAAA,EAAiB,2BAAA,EAA6B,OAAOC,QAAAA,GAAAA;AACzD,QAAA,IAAIA,YAAY,IAAA,EAAM;YACpB,OAAO,IAAA;AACT,QAAA;AAEA,QAAA,MAAMC,MAAAA,GAAS,MAAMC,gBAAAA,CAAW,QAAA,CAAA,CAAUD,MAAM,CAAC;YAAEE,EAAAA,EAAIH;AAAS,SAAA,CAAA;QAEhE,OAAOC,MAAAA;AACT,IAAA,CAAA;AACJ,CAAA,CAAA;AAEA,MAAMG,YAAAA,GAAevB,SAAAA,CAAIC,MAAM,CAAC;IAC9BuB,QAAAA,EAAUd;AACZ,CAAA,CAAA;AAEA,MAAMe,iBAAAA,GAAoBzB,SAAAA,CAAIC,MAAM,CAAC;AACnCuB,IAAAA,QAAAA,EAAUxB,SAAAA,CAAI0B,KAAK,EAAA,CAAGC,EAAE,CAACjB,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMkB,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,wBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;AAOA,MAAMK,iBAAAA,GAAoBlC,SAAAA,CAAIC,MAAM,CAAC;AACnCkC,IAAAA,OAAAA,EAASnC,UACN0B,KAAK,EAAA,CACLC,EAAE,CACD3B,SAAAA,CAAIC,MAAM,CAAC;QACTqB,EAAAA,EAAItB,SAAAA,CAAIG,MAAM,EAAA,CAAGG,QAAQ,EAAA;AACzBkB,QAAAA,QAAAA,EAAUd,eAAeJ,QAAQ;KACnC,CAAA,CAAA,CAEDF,GAAG,CAAC,CAAA,CAAA,CACJE,QAAQ;AACb,CAAA,CAAA;AAEO,MAAM8B,sBAAAA,GAAyBJ,uBAAAA,CAAkBE,iBAAAA;;;;;"}
@@ -1 +1 @@
1
- {"version":3,"file":"upload.mjs","sources":["../../../../../server/src/controllers/validation/admin/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\nimport { getService } from '../../../utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup.object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n folder: yup\n .strapiID()\n .nullable()\n .test('folder-exists', 'the folder does not exist', async (folderId) => {\n if (folderId == null) {\n return true;\n }\n\n const exists = await getService('folder').exists({ id: folderId });\n\n return exists;\n }),\n});\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n | yup.InferType<typeof uploadSchema>\n | yup.InferType<typeof multiUploadSchema>;\n\nconst bulkUpdatesSchema = yup.object({\n updates: yup\n .array()\n .of(\n yup.object({\n id: yup.number().required(),\n fileInfo: fileInfoSchema.required(),\n })\n )\n .min(1)\n .required(),\n});\n\nexport const validateBulkUpdateBody = validateYupSchema(bulkUpdatesSchema);\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","folder","strapiID","test","folderId","exists","getService","id","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict","bulkUpdatesSchema","updates","validateBulkUpdateBody"],"mappings":";;;AAGA,MAAMA,gBAAAA,GAAmBC,GAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,GAAAA,CAAIC,MAAM,CAAC;IAChCU,IAAAA,EAAMX,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB,gBAAAA;IACZiB,MAAAA,EAAQhB,GAAAA,CACLiB,QAAQ,EAAA,CACRT,QAAQ,GACRU,IAAI,CAAC,eAAA,EAAiB,2BAAA,EAA6B,OAAOC,QAAAA,GAAAA;AACzD,QAAA,IAAIA,YAAY,IAAA,EAAM;YACpB,OAAO,IAAA;AACT,QAAA;AAEA,QAAA,MAAMC,MAAAA,GAAS,MAAMC,UAAAA,CAAW,QAAA,CAAA,CAAUD,MAAM,CAAC;YAAEE,EAAAA,EAAIH;AAAS,SAAA,CAAA;QAEhE,OAAOC,MAAAA;AACT,IAAA,CAAA;AACJ,CAAA,CAAA;AAEA,MAAMG,YAAAA,GAAevB,GAAAA,CAAIC,MAAM,CAAC;IAC9BuB,QAAAA,EAAUd;AACZ,CAAA,CAAA;AAEA,MAAMe,iBAAAA,GAAoBzB,GAAAA,CAAIC,MAAM,CAAC;AACnCuB,IAAAA,QAAAA,EAAUxB,GAAAA,CAAI0B,KAAK,EAAA,CAAGC,EAAE,CAACjB,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMkB,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,kBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;AAQA,MAAMK,iBAAAA,GAAoBlC,GAAAA,CAAIC,MAAM,CAAC;AACnCkC,IAAAA,OAAAA,EAASnC,IACN0B,KAAK,EAAA,CACLC,EAAE,CACD3B,GAAAA,CAAIC,MAAM,CAAC;QACTqB,EAAAA,EAAItB,GAAAA,CAAIG,MAAM,EAAA,CAAGG,QAAQ,EAAA;AACzBkB,QAAAA,QAAAA,EAAUd,eAAeJ,QAAQ;KACnC,CAAA,CAAA,CAEDF,GAAG,CAAC,CAAA,CAAA,CACJE,QAAQ;AACb,CAAA,CAAA;AAEO,MAAM8B,sBAAAA,GAAyBJ,iBAAAA,CAAkBE,iBAAAA;;;;"}
1
+ {"version":3,"file":"upload.mjs","sources":["../../../../../server/src/controllers/validation/admin/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\nimport { getService } from '../../../utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup.object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n folder: yup\n .strapiID()\n .nullable()\n .test('folder-exists', 'the folder does not exist', async (folderId) => {\n if (folderId == null) {\n return true;\n }\n\n const exists = await getService('folder').exists({ id: folderId });\n\n return exists;\n }),\n});\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n yup.InferType<typeof uploadSchema> | yup.InferType<typeof multiUploadSchema>;\n\nconst bulkUpdatesSchema = yup.object({\n updates: yup\n .array()\n .of(\n yup.object({\n id: yup.number().required(),\n fileInfo: fileInfoSchema.required(),\n })\n )\n .min(1)\n .required(),\n});\n\nexport const validateBulkUpdateBody = validateYupSchema(bulkUpdatesSchema);\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","folder","strapiID","test","folderId","exists","getService","id","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict","bulkUpdatesSchema","updates","validateBulkUpdateBody"],"mappings":";;;AAGA,MAAMA,gBAAAA,GAAmBC,GAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,GAAAA,CAAIC,MAAM,CAAC;IAChCU,IAAAA,EAAMX,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB,gBAAAA;IACZiB,MAAAA,EAAQhB,GAAAA,CACLiB,QAAQ,EAAA,CACRT,QAAQ,GACRU,IAAI,CAAC,eAAA,EAAiB,2BAAA,EAA6B,OAAOC,QAAAA,GAAAA;AACzD,QAAA,IAAIA,YAAY,IAAA,EAAM;YACpB,OAAO,IAAA;AACT,QAAA;AAEA,QAAA,MAAMC,MAAAA,GAAS,MAAMC,UAAAA,CAAW,QAAA,CAAA,CAAUD,MAAM,CAAC;YAAEE,EAAAA,EAAIH;AAAS,SAAA,CAAA;QAEhE,OAAOC,MAAAA;AACT,IAAA,CAAA;AACJ,CAAA,CAAA;AAEA,MAAMG,YAAAA,GAAevB,GAAAA,CAAIC,MAAM,CAAC;IAC9BuB,QAAAA,EAAUd;AACZ,CAAA,CAAA;AAEA,MAAMe,iBAAAA,GAAoBzB,GAAAA,CAAIC,MAAM,CAAC;AACnCuB,IAAAA,QAAAA,EAAUxB,GAAAA,CAAI0B,KAAK,EAAA,CAAGC,EAAE,CAACjB,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMkB,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,kBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;AAOA,MAAMK,iBAAAA,GAAoBlC,GAAAA,CAAIC,MAAM,CAAC;AACnCkC,IAAAA,OAAAA,EAASnC,IACN0B,KAAK,EAAA,CACLC,EAAE,CACD3B,GAAAA,CAAIC,MAAM,CAAC;QACTqB,EAAAA,EAAItB,GAAAA,CAAIG,MAAM,EAAA,CAAGG,QAAQ,EAAA;AACzBkB,QAAAA,QAAAA,EAAUd,eAAeJ,QAAQ;KACnC,CAAA,CAAA,CAEDF,GAAG,CAAC,CAAA,CAAA,CACJE,QAAQ;AACb,CAAA,CAAA;AAEO,MAAM8B,sBAAAA,GAAyBJ,iBAAAA,CAAkBE,iBAAAA;;;;"}
@@ -1 +1 @@
1
- {"version":3,"file":"upload.js","sources":["../../../../../server/src/controllers/validation/content-api/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup\n .object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n })\n .noUnknown();\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n | yup.InferType<typeof uploadSchema>\n | yup.InferType<typeof multiUploadSchema>;\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","noUnknown","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict"],"mappings":";;;;AAEA,MAAMA,gBAAAA,GAAmBC,SAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,SAAAA,CACpBC,MAAM,CAAC;IACNU,IAAAA,EAAMX,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB;AACd,CAAA,CAAA,CACCiB,SAAS,EAAA;AAEZ,MAAMC,YAAAA,GAAejB,SAAAA,CAAIC,MAAM,CAAC;IAC9BiB,QAAAA,EAAUR;AACZ,CAAA,CAAA;AAEA,MAAMS,iBAAAA,GAAoBnB,SAAAA,CAAIC,MAAM,CAAC;AACnCiB,IAAAA,QAAAA,EAAUlB,SAAAA,CAAIoB,KAAK,EAAA,CAAGC,EAAE,CAACX,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMY,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,wBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;;;;"}
1
+ {"version":3,"file":"upload.js","sources":["../../../../../server/src/controllers/validation/content-api/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup\n .object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n })\n .noUnknown();\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n yup.InferType<typeof uploadSchema> | yup.InferType<typeof multiUploadSchema>;\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","noUnknown","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict"],"mappings":";;;;AAEA,MAAMA,gBAAAA,GAAmBC,SAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,SAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,SAAAA,CACpBC,MAAM,CAAC;IACNU,IAAAA,EAAMX,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,SAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB;AACd,CAAA,CAAA,CACCiB,SAAS,EAAA;AAEZ,MAAMC,YAAAA,GAAejB,SAAAA,CAAIC,MAAM,CAAC;IAC9BiB,QAAAA,EAAUR;AACZ,CAAA,CAAA;AAEA,MAAMS,iBAAAA,GAAoBnB,SAAAA,CAAIC,MAAM,CAAC;AACnCiB,IAAAA,QAAAA,EAAUlB,SAAAA,CAAIoB,KAAK,EAAA,CAAGC,EAAE,CAACX,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMY,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,wBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;;;;"}
@@ -1 +1 @@
1
- {"version":3,"file":"upload.mjs","sources":["../../../../../server/src/controllers/validation/content-api/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup\n .object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n })\n .noUnknown();\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n | yup.InferType<typeof uploadSchema>\n | yup.InferType<typeof multiUploadSchema>;\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","noUnknown","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict"],"mappings":";;AAEA,MAAMA,gBAAAA,GAAmBC,GAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,GAAAA,CACpBC,MAAM,CAAC;IACNU,IAAAA,EAAMX,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB;AACd,CAAA,CAAA,CACCiB,SAAS,EAAA;AAEZ,MAAMC,YAAAA,GAAejB,GAAAA,CAAIC,MAAM,CAAC;IAC9BiB,QAAAA,EAAUR;AACZ,CAAA,CAAA;AAEA,MAAMS,iBAAAA,GAAoBnB,GAAAA,CAAIC,MAAM,CAAC;AACnCiB,IAAAA,QAAAA,EAAUlB,GAAAA,CAAIoB,KAAK,EAAA,CAAGC,EAAE,CAACX,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMY,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,kBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;;;;"}
1
+ {"version":3,"file":"upload.mjs","sources":["../../../../../server/src/controllers/validation/content-api/upload.ts"],"sourcesContent":["import { yup, validateYupSchema } from '@strapi/utils';\n\nconst focalPointSchema = yup\n .object({\n x: yup.number().min(0).max(100).required(),\n y: yup.number().min(0).max(100).required(),\n })\n .nullable()\n .default(null);\n\nconst fileInfoSchema = yup\n .object({\n name: yup.string().nullable(),\n alternativeText: yup.string().nullable(),\n caption: yup.string().nullable(),\n focalPoint: focalPointSchema,\n })\n .noUnknown();\n\nconst uploadSchema = yup.object({\n fileInfo: fileInfoSchema,\n});\n\nconst multiUploadSchema = yup.object({\n fileInfo: yup.array().of(fileInfoSchema),\n});\n\nconst validateUploadBody = (data = {}, isMulti = false) => {\n const schema = isMulti ? multiUploadSchema : uploadSchema;\n\n return validateYupSchema(schema, { strict: false })(data);\n};\n\nexport { validateUploadBody };\n\nexport type UploadBody =\n yup.InferType<typeof uploadSchema> | yup.InferType<typeof multiUploadSchema>;\n"],"names":["focalPointSchema","yup","object","x","number","min","max","required","y","nullable","default","fileInfoSchema","name","string","alternativeText","caption","focalPoint","noUnknown","uploadSchema","fileInfo","multiUploadSchema","array","of","validateUploadBody","data","isMulti","schema","validateYupSchema","strict"],"mappings":";;AAEA,MAAMA,gBAAAA,GAAmBC,GAAAA,CACtBC,MAAM,CAAC;IACNC,CAAAA,EAAGF,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ,EAAA;IACxCC,CAAAA,EAAGP,GAAAA,CAAIG,MAAM,EAAA,CAAGC,GAAG,CAAC,CAAA,CAAA,CAAGC,GAAG,CAAC,GAAA,CAAA,CAAKC,QAAQ;AAC1C,CAAA,CAAA,CACCE,QAAQ,EAAA,CACRC,OAAO,CAAC,IAAA,CAAA;AAEX,MAAMC,cAAAA,GAAiBV,GAAAA,CACpBC,MAAM,CAAC;IACNU,IAAAA,EAAMX,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC3BK,eAAAA,EAAiBb,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IACtCM,OAAAA,EAASd,GAAAA,CAAIY,MAAM,EAAA,CAAGJ,QAAQ,EAAA;IAC9BO,UAAAA,EAAYhB;AACd,CAAA,CAAA,CACCiB,SAAS,EAAA;AAEZ,MAAMC,YAAAA,GAAejB,GAAAA,CAAIC,MAAM,CAAC;IAC9BiB,QAAAA,EAAUR;AACZ,CAAA,CAAA;AAEA,MAAMS,iBAAAA,GAAoBnB,GAAAA,CAAIC,MAAM,CAAC;AACnCiB,IAAAA,QAAAA,EAAUlB,GAAAA,CAAIoB,KAAK,EAAA,CAAGC,EAAE,CAACX,cAAAA;AAC3B,CAAA,CAAA;AAEA,MAAMY,qBAAqB,CAACC,IAAAA,GAAO,EAAE,EAAEC,UAAU,KAAK,GAAA;IACpD,MAAMC,MAAAA,GAASD,UAAUL,iBAAAA,GAAoBF,YAAAA;AAE7C,IAAA,OAAOS,kBAAkBD,MAAAA,EAAQ;QAAEE,MAAAA,EAAQ;KAAM,CAAA,CAAGJ,IAAAA,CAAAA;AACtD;;;;"}
@@ -21,9 +21,11 @@ var index = require('../utils/index.js');
21
21
  * `strapi.getModel`, `update` runs a multi-statement transaction, and every admin controller and
22
22
  * validator already depends on the ambient form.
23
23
  *
24
- * So the dependency is made explicit and asserted instead. Handlers call this in their factory
25
- * body — at handler construction, not per call — so a mismatch fails while the tool is being
26
- * registered rather than surfacing to an agent as tool output mid-conversation.
24
+ * So the dependency is made explicit and asserted instead. `buildUploadMcpToolDefinitions`
25
+ * wraps every tool's `createHandler` in this check, so it applies to the whole media surface by
26
+ * construction rather than by each factory remembering to call it. It runs at handler
27
+ * construction, not per call, so a mismatch fails while the tool is being registered rather
28
+ * than surfacing to an agent as tool output mid-conversation.
27
29
  *
28
30
  * A single-app server is unaffected: `createStrapi` assigns its instance to `global.strapi`, so
29
31
  * the two agree. If they ever diverge — a second Strapi instance in one process — this throws
@@ -37,8 +39,8 @@ var index = require('../utils/index.js');
37
39
  * Resolves the `folder` service for an MCP handler.
38
40
  *
39
41
  * A bare `getService('folder', strapi)` reads as instance-bound but is not — see
40
- * `assertAmbientInstance` for why. Handlers assert the instance once at construction; this keeps
41
- * the resolution behind a named helper so the call sites do not reintroduce the misleading form.
42
+ * `assertAmbientInstance` for why, and for where that is enforced. This keeps the resolution
43
+ * behind a named helper so the call sites do not reintroduce the misleading form.
42
44
  */ const getFolderService = (strapi)=>index.getService('folder', strapi);
43
45
 
44
46
  exports.assertAmbientInstance = assertAmbientInstance;
@@ -1 +1 @@
1
- {"version":3,"file":"ambient-instance.js","sources":["../../../server/src/mcp/ambient-instance.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\n\n/**\n * Asserts that an MCP handler's Strapi instance is the ambient `global.strapi`.\n *\n * Two of the upload plugin's services — `folder` and `file` — are registered as plain object\n * literals rather than factories (see `services/index.ts`), so their methods close over the\n * module-scope ambient `strapi` and query `global.strapi.db` regardless of which instance is\n * passed to `getService`. Passing an instance therefore selects the right plugin registry but\n * does *not* bind the queries to it.\n *\n * The folder tools reach `folder` directly. The asset write tools reach `file` transitively:\n * `upload.updateFileInfo` resolves it with a bare `getService('file')` (`services/upload.ts`),\n * and `file.getFolderPath` then queries the ambient `strapi.db`. So a handler that looks\n * instance-bound can still mix ambient reads with instance-bound writes.\n *\n * Threading an instance through both services is a broader refactor than the MCP surface should\n * carry: `create`, `update` and `deleteByIds` reach for `strapi.db`, `strapi.eventHub` and\n * `strapi.getModel`, `update` runs a multi-statement transaction, and every admin controller and\n * validator already depends on the ambient form.\n *\n * So the dependency is made explicit and asserted instead. Handlers call this in their factory\n * body — at handler construction, not per call — so a mismatch fails while the tool is being\n * registered rather than surfacing to an agent as tool output mid-conversation.\n *\n * A single-app server is unaffected: `createStrapi` assigns its instance to `global.strapi`, so\n * the two agree. If they ever diverge — a second Strapi instance in one process — this throws\n * rather than silently reading or writing the wrong app's media library.\n */\nexport const assertAmbientInstance = (strapi: Core.Strapi) => {\n if (strapi !== global.strapi) {\n throw new Error(\n 'The upload `folder` and `file` services are bound to the ambient `global.strapi`, but an ' +\n 'MCP handler was constructed with a different Strapi instance. Media queries would run ' +\n 'against the wrong app. Convert those services to factories before serving MCP from a ' +\n 'non-global instance.'\n );\n }\n};\n\n/**\n * Resolves the `folder` service for an MCP handler.\n *\n * A bare `getService('folder', strapi)` reads as instance-bound but is not — see\n * `assertAmbientInstance` for why. Handlers assert the instance once at construction; this keeps\n * the resolution behind a named helper so the call sites do not reintroduce the misleading form.\n */\nexport const getFolderService = (strapi: Core.Strapi) => getService('folder', strapi);\n"],"names":["assertAmbientInstance","strapi","global","Error","getFolderService","getService"],"mappings":";;;;AAIA;;;;;;;;;;;;;;;;;;;;;;;;;;IA2BO,MAAMA,qBAAAA,GAAwB,CAACC,MAAAA,GAAAA;IACpC,IAAIA,MAAAA,KAAWC,MAAAA,CAAOD,MAAM,EAAE;AAC5B,QAAA,MAAM,IAAIE,KAAAA,CACR,2FAAA,GACE,wFAAA,GACA,uFAAA,GACA,sBAAA,CAAA;AAEN,IAAA;AACF;AAEA;;;;;;AAMC,IACM,MAAMC,gBAAAA,GAAmB,CAACH,MAAAA,GAAwBI,gBAAAA,CAAW,UAAUJ,MAAAA;;;;;"}
1
+ {"version":3,"file":"ambient-instance.js","sources":["../../../server/src/mcp/ambient-instance.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\n\n/**\n * Asserts that an MCP handler's Strapi instance is the ambient `global.strapi`.\n *\n * Two of the upload plugin's services — `folder` and `file` — are registered as plain object\n * literals rather than factories (see `services/index.ts`), so their methods close over the\n * module-scope ambient `strapi` and query `global.strapi.db` regardless of which instance is\n * passed to `getService`. Passing an instance therefore selects the right plugin registry but\n * does *not* bind the queries to it.\n *\n * The folder tools reach `folder` directly. The asset write tools reach `file` transitively:\n * `upload.updateFileInfo` resolves it with a bare `getService('file')` (`services/upload.ts`),\n * and `file.getFolderPath` then queries the ambient `strapi.db`. So a handler that looks\n * instance-bound can still mix ambient reads with instance-bound writes.\n *\n * Threading an instance through both services is a broader refactor than the MCP surface should\n * carry: `create`, `update` and `deleteByIds` reach for `strapi.db`, `strapi.eventHub` and\n * `strapi.getModel`, `update` runs a multi-statement transaction, and every admin controller and\n * validator already depends on the ambient form.\n *\n * So the dependency is made explicit and asserted instead. `buildUploadMcpToolDefinitions`\n * wraps every tool's `createHandler` in this check, so it applies to the whole media surface by\n * construction rather than by each factory remembering to call it. It runs at handler\n * construction, not per call, so a mismatch fails while the tool is being registered rather\n * than surfacing to an agent as tool output mid-conversation.\n *\n * A single-app server is unaffected: `createStrapi` assigns its instance to `global.strapi`, so\n * the two agree. If they ever diverge — a second Strapi instance in one process — this throws\n * rather than silently reading or writing the wrong app's media library.\n */\nexport const assertAmbientInstance = (strapi: Core.Strapi) => {\n if (strapi !== global.strapi) {\n throw new Error(\n 'The upload `folder` and `file` services are bound to the ambient `global.strapi`, but an ' +\n 'MCP handler was constructed with a different Strapi instance. Media queries would run ' +\n 'against the wrong app. Convert those services to factories before serving MCP from a ' +\n 'non-global instance.'\n );\n }\n};\n\n/**\n * Resolves the `folder` service for an MCP handler.\n *\n * A bare `getService('folder', strapi)` reads as instance-bound but is not — see\n * `assertAmbientInstance` for why, and for where that is enforced. This keeps the resolution\n * behind a named helper so the call sites do not reintroduce the misleading form.\n */\nexport const getFolderService = (strapi: Core.Strapi) => getService('folder', strapi);\n"],"names":["assertAmbientInstance","strapi","global","Error","getFolderService","getService"],"mappings":";;;;AAIA;;;;;;;;;;;;;;;;;;;;;;;;;;;;IA6BO,MAAMA,qBAAAA,GAAwB,CAACC,MAAAA,GAAAA;IACpC,IAAIA,MAAAA,KAAWC,MAAAA,CAAOD,MAAM,EAAE;AAC5B,QAAA,MAAM,IAAIE,KAAAA,CACR,2FAAA,GACE,wFAAA,GACA,uFAAA,GACA,sBAAA,CAAA;AAEN,IAAA;AACF;AAEA;;;;;;AAMC,IACM,MAAMC,gBAAAA,GAAmB,CAACH,MAAAA,GAAwBI,gBAAAA,CAAW,UAAUJ,MAAAA;;;;;"}
@@ -19,9 +19,11 @@ import { getService } from '../utils/index.mjs';
19
19
  * `strapi.getModel`, `update` runs a multi-statement transaction, and every admin controller and
20
20
  * validator already depends on the ambient form.
21
21
  *
22
- * So the dependency is made explicit and asserted instead. Handlers call this in their factory
23
- * body — at handler construction, not per call — so a mismatch fails while the tool is being
24
- * registered rather than surfacing to an agent as tool output mid-conversation.
22
+ * So the dependency is made explicit and asserted instead. `buildUploadMcpToolDefinitions`
23
+ * wraps every tool's `createHandler` in this check, so it applies to the whole media surface by
24
+ * construction rather than by each factory remembering to call it. It runs at handler
25
+ * construction, not per call, so a mismatch fails while the tool is being registered rather
26
+ * than surfacing to an agent as tool output mid-conversation.
25
27
  *
26
28
  * A single-app server is unaffected: `createStrapi` assigns its instance to `global.strapi`, so
27
29
  * the two agree. If they ever diverge — a second Strapi instance in one process — this throws
@@ -35,8 +37,8 @@ import { getService } from '../utils/index.mjs';
35
37
  * Resolves the `folder` service for an MCP handler.
36
38
  *
37
39
  * A bare `getService('folder', strapi)` reads as instance-bound but is not — see
38
- * `assertAmbientInstance` for why. Handlers assert the instance once at construction; this keeps
39
- * the resolution behind a named helper so the call sites do not reintroduce the misleading form.
40
+ * `assertAmbientInstance` for why, and for where that is enforced. This keeps the resolution
41
+ * behind a named helper so the call sites do not reintroduce the misleading form.
40
42
  */ const getFolderService = (strapi)=>getService('folder', strapi);
41
43
 
42
44
  export { assertAmbientInstance, getFolderService };
@@ -1 +1 @@
1
- {"version":3,"file":"ambient-instance.mjs","sources":["../../../server/src/mcp/ambient-instance.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\n\n/**\n * Asserts that an MCP handler's Strapi instance is the ambient `global.strapi`.\n *\n * Two of the upload plugin's services — `folder` and `file` — are registered as plain object\n * literals rather than factories (see `services/index.ts`), so their methods close over the\n * module-scope ambient `strapi` and query `global.strapi.db` regardless of which instance is\n * passed to `getService`. Passing an instance therefore selects the right plugin registry but\n * does *not* bind the queries to it.\n *\n * The folder tools reach `folder` directly. The asset write tools reach `file` transitively:\n * `upload.updateFileInfo` resolves it with a bare `getService('file')` (`services/upload.ts`),\n * and `file.getFolderPath` then queries the ambient `strapi.db`. So a handler that looks\n * instance-bound can still mix ambient reads with instance-bound writes.\n *\n * Threading an instance through both services is a broader refactor than the MCP surface should\n * carry: `create`, `update` and `deleteByIds` reach for `strapi.db`, `strapi.eventHub` and\n * `strapi.getModel`, `update` runs a multi-statement transaction, and every admin controller and\n * validator already depends on the ambient form.\n *\n * So the dependency is made explicit and asserted instead. Handlers call this in their factory\n * body — at handler construction, not per call — so a mismatch fails while the tool is being\n * registered rather than surfacing to an agent as tool output mid-conversation.\n *\n * A single-app server is unaffected: `createStrapi` assigns its instance to `global.strapi`, so\n * the two agree. If they ever diverge — a second Strapi instance in one process — this throws\n * rather than silently reading or writing the wrong app's media library.\n */\nexport const assertAmbientInstance = (strapi: Core.Strapi) => {\n if (strapi !== global.strapi) {\n throw new Error(\n 'The upload `folder` and `file` services are bound to the ambient `global.strapi`, but an ' +\n 'MCP handler was constructed with a different Strapi instance. Media queries would run ' +\n 'against the wrong app. Convert those services to factories before serving MCP from a ' +\n 'non-global instance.'\n );\n }\n};\n\n/**\n * Resolves the `folder` service for an MCP handler.\n *\n * A bare `getService('folder', strapi)` reads as instance-bound but is not — see\n * `assertAmbientInstance` for why. Handlers assert the instance once at construction; this keeps\n * the resolution behind a named helper so the call sites do not reintroduce the misleading form.\n */\nexport const getFolderService = (strapi: Core.Strapi) => getService('folder', strapi);\n"],"names":["assertAmbientInstance","strapi","global","Error","getFolderService","getService"],"mappings":";;AAIA;;;;;;;;;;;;;;;;;;;;;;;;;;IA2BO,MAAMA,qBAAAA,GAAwB,CAACC,MAAAA,GAAAA;IACpC,IAAIA,MAAAA,KAAWC,MAAAA,CAAOD,MAAM,EAAE;AAC5B,QAAA,MAAM,IAAIE,KAAAA,CACR,2FAAA,GACE,wFAAA,GACA,uFAAA,GACA,sBAAA,CAAA;AAEN,IAAA;AACF;AAEA;;;;;;AAMC,IACM,MAAMC,gBAAAA,GAAmB,CAACH,MAAAA,GAAwBI,UAAAA,CAAW,UAAUJ,MAAAA;;;;"}
1
+ {"version":3,"file":"ambient-instance.mjs","sources":["../../../server/src/mcp/ambient-instance.ts"],"sourcesContent":["import type { Core } from '@strapi/types';\n\nimport { getService } from '../utils';\n\n/**\n * Asserts that an MCP handler's Strapi instance is the ambient `global.strapi`.\n *\n * Two of the upload plugin's services — `folder` and `file` — are registered as plain object\n * literals rather than factories (see `services/index.ts`), so their methods close over the\n * module-scope ambient `strapi` and query `global.strapi.db` regardless of which instance is\n * passed to `getService`. Passing an instance therefore selects the right plugin registry but\n * does *not* bind the queries to it.\n *\n * The folder tools reach `folder` directly. The asset write tools reach `file` transitively:\n * `upload.updateFileInfo` resolves it with a bare `getService('file')` (`services/upload.ts`),\n * and `file.getFolderPath` then queries the ambient `strapi.db`. So a handler that looks\n * instance-bound can still mix ambient reads with instance-bound writes.\n *\n * Threading an instance through both services is a broader refactor than the MCP surface should\n * carry: `create`, `update` and `deleteByIds` reach for `strapi.db`, `strapi.eventHub` and\n * `strapi.getModel`, `update` runs a multi-statement transaction, and every admin controller and\n * validator already depends on the ambient form.\n *\n * So the dependency is made explicit and asserted instead. `buildUploadMcpToolDefinitions`\n * wraps every tool's `createHandler` in this check, so it applies to the whole media surface by\n * construction rather than by each factory remembering to call it. It runs at handler\n * construction, not per call, so a mismatch fails while the tool is being registered rather\n * than surfacing to an agent as tool output mid-conversation.\n *\n * A single-app server is unaffected: `createStrapi` assigns its instance to `global.strapi`, so\n * the two agree. If they ever diverge — a second Strapi instance in one process — this throws\n * rather than silently reading or writing the wrong app's media library.\n */\nexport const assertAmbientInstance = (strapi: Core.Strapi) => {\n if (strapi !== global.strapi) {\n throw new Error(\n 'The upload `folder` and `file` services are bound to the ambient `global.strapi`, but an ' +\n 'MCP handler was constructed with a different Strapi instance. Media queries would run ' +\n 'against the wrong app. Convert those services to factories before serving MCP from a ' +\n 'non-global instance.'\n );\n }\n};\n\n/**\n * Resolves the `folder` service for an MCP handler.\n *\n * A bare `getService('folder', strapi)` reads as instance-bound but is not — see\n * `assertAmbientInstance` for why, and for where that is enforced. This keeps the resolution\n * behind a named helper so the call sites do not reintroduce the misleading form.\n */\nexport const getFolderService = (strapi: Core.Strapi) => getService('folder', strapi);\n"],"names":["assertAmbientInstance","strapi","global","Error","getFolderService","getService"],"mappings":";;AAIA;;;;;;;;;;;;;;;;;;;;;;;;;;;;IA6BO,MAAMA,qBAAAA,GAAwB,CAACC,MAAAA,GAAAA;IACpC,IAAIA,MAAAA,KAAWC,MAAAA,CAAOD,MAAM,EAAE;AAC5B,QAAA,MAAM,IAAIE,KAAAA,CACR,2FAAA,GACE,wFAAA,GACA,uFAAA,GACA,sBAAA,CAAA;AAEN,IAAA;AACF;AAEA;;;;;;AAMC,IACM,MAAMC,gBAAAA,GAAmB,CAACH,MAAAA,GAAwBI,UAAAA,CAAW,UAAUJ,MAAAA;;;;"}
@@ -152,9 +152,7 @@ var utils = require('../utils.js');
152
152
  *
153
153
  * `create` rather than the `update` the other folder tools use: creating a folder is the one
154
154
  * folder operation whose admin route gates on `assets.create`.
155
- */ const createMediaCreateFolderHandler = (strapi, context)=>{
156
- ambientInstance.assertAmbientInstance(strapi);
157
- return async ({ args })=>{
155
+ */ const createMediaCreateFolderHandler = (strapi, context)=>async ({ args })=>{
158
156
  const { name, parent = null } = args;
159
157
  permissions.assertMediaPermission(strapi, context, constants$1.ACTIONS.create, constants$1.FOLDER_MODEL_UID);
160
158
  await assertParentExists(strapi, parent);
@@ -169,7 +167,6 @@ var utils = require('../utils.js');
169
167
  data: await readFolderForOutput(strapi, created.id, created)
170
168
  });
171
169
  };
172
- };
173
170
  /**
174
171
  * `media_rename_folder` — changes a folder's name and nothing else.
175
172
  *
@@ -177,9 +174,7 @@ var utils = require('../utils.js');
177
174
  * `isUndefined(parent)`, and the name-only branch skips the transaction that rewrites descendant
178
175
  * paths. Passing the folder's existing parent would take the move branch and rewrite the whole
179
176
  * subtree to compute the identical paths.
180
- */ const createMediaRenameFolderHandler = (strapi, context)=>{
181
- ambientInstance.assertAmbientInstance(strapi);
182
- return async ({ args })=>{
177
+ */ const createMediaRenameFolderHandler = (strapi, context)=>async ({ args })=>{
183
178
  const { id, name } = args;
184
179
  permissions.assertMediaPermission(strapi, context, constants$1.ACTIONS.update, constants$1.FOLDER_MODEL_UID);
185
180
  const folder = await findFolderById(strapi, id, {
@@ -205,16 +200,13 @@ var utils = require('../utils.js');
205
200
  })
206
201
  });
207
202
  };
208
- };
209
203
  /**
210
204
  * `media_move_folder` — re-parents a folder, carrying its whole subtree with it.
211
205
  *
212
206
  * `folder.update()` recalculates the materialized `path` of every descendant folder and the
213
207
  * `folderPath` of every contained file inside a transaction, so the move is atomic and no
214
208
  * separate bookkeeping is needed here.
215
- */ const createMediaMoveFolderHandler = (strapi, context)=>{
216
- ambientInstance.assertAmbientInstance(strapi);
217
- return async ({ args })=>{
209
+ */ const createMediaMoveFolderHandler = (strapi, context)=>async ({ args })=>{
218
210
  const { id, parent } = args;
219
211
  permissions.assertMediaPermission(strapi, context, constants$1.ACTIONS.update, constants$1.FOLDER_MODEL_UID);
220
212
  const folder = await findFolderById(strapi, id);
@@ -235,7 +227,6 @@ var utils = require('../utils.js');
235
227
  data: await readFolderForOutput(strapi, id, moved ?? folder)
236
228
  });
237
229
  };
238
- };
239
230
  /**
240
231
  * `media_delete_folder` — previews or performs a cascading folder deletion.
241
232
  *
@@ -245,9 +236,7 @@ var utils = require('../utils.js');
245
236
  *
246
237
  * `dryRun` defaults to true (see the input schema): omitting the flag previews, and deleting
247
238
  * takes an explicit `dryRun: false`.
248
- */ const createMediaDeleteFolderHandler = (strapi, context)=>{
249
- ambientInstance.assertAmbientInstance(strapi);
250
- return async ({ args })=>{
239
+ */ const createMediaDeleteFolderHandler = (strapi, context)=>async ({ args })=>{
251
240
  const { ids, dryRun = true } = args;
252
241
  permissions.assertMediaPermission(strapi, context, constants$1.ACTIONS.update, constants$1.FOLDER_MODEL_UID);
253
242
  const matched = await strapi.db.query(constants$1.FOLDER_MODEL_UID).findMany({
@@ -299,7 +288,6 @@ var utils = require('../utils.js');
299
288
  totalFileNumber
300
289
  });
301
290
  };
302
- };
303
291
 
304
292
  exports.createMediaCreateFolderHandler = createMediaCreateFolderHandler;
305
293
  exports.createMediaDeleteFolderHandler = createMediaDeleteFolderHandler;