@visulima/storage 1.0.0-alpha.9 → 1.0.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 (424) hide show
  1. package/CHANGELOG.md +555 -0
  2. package/LICENSE.md +237 -568
  3. package/README.md +82 -466
  4. package/dist/adapter/nuxt/module.d.ts +41 -34
  5. package/dist/adapter/nuxt/module.js +1 -93
  6. package/dist/adapter/nuxt/package.json +0 -6
  7. package/dist/ai/ai-sdk/index.d.ts +113 -0
  8. package/dist/ai/ai-sdk/index.js +1 -0
  9. package/dist/ai/claude/index.d.ts +177 -0
  10. package/dist/ai/claude/index.js +1 -0
  11. package/dist/ai/openai/index.d.ts +205 -0
  12. package/dist/ai/openai/index.js +1 -0
  13. package/dist/ai/tanstack/index.d.ts +115 -0
  14. package/dist/ai/tanstack/index.js +1 -0
  15. package/dist/handler/http/fetch/index.d.ts +303 -4
  16. package/dist/handler/http/fetch/index.js +1 -4
  17. package/dist/handler/http/hono/index.d.ts +73 -64
  18. package/dist/handler/http/hono/index.js +1 -65
  19. package/dist/handler/http/nextjs/index.d.ts +66 -58
  20. package/dist/handler/http/nextjs/index.js +1 -37
  21. package/dist/handler/http/node/index.d.ts +368 -4
  22. package/dist/handler/http/node/index.js +1 -8
  23. package/dist/handler/http/solid-start/index.d.ts +66 -57
  24. package/dist/handler/http/solid-start/index.js +1 -44
  25. package/dist/index.d.ts +106 -17
  26. package/dist/index.js +1 -13
  27. package/dist/openapi/index.d.ts +24 -5
  28. package/dist/openapi/index.js +1 -5
  29. package/dist/packem_shared/AbstractBaseStorage-Ba7cLu-t.js +1 -0
  30. package/dist/packem_shared/AwsLightFile-CpZrubaV.js +1 -0
  31. package/dist/packem_shared/AwsLightMetaStorage-DPqJ9LTr.js +1 -0
  32. package/dist/packem_shared/AwsLightStorage-DTBVxHXO.js +1 -0
  33. package/dist/packem_shared/AzureFile-DFSaVe25.js +1 -0
  34. package/dist/packem_shared/AzureSMetaStorage-ByzM6Aix.js +1 -0
  35. package/dist/packem_shared/AzureStorage-BFsD4qbF.js +1 -0
  36. package/dist/packem_shared/BaseTransformer-Buw5lX_3.js +1 -0
  37. package/dist/packem_shared/BoxFile-CseIoPW1.js +1 -0
  38. package/dist/packem_shared/BoxMetaStorage-DFwhEI9C.js +1 -0
  39. package/dist/packem_shared/BoxStorage-B_t-OVzf.js +1 -0
  40. package/dist/packem_shared/BunS3File-BcYmsz1n.js +1 -0
  41. package/dist/packem_shared/BunS3MetaStorage-DFwhEI9C.js +1 -0
  42. package/dist/packem_shared/BunS3Storage-CB_pZWlV.js +1 -0
  43. package/dist/packem_shared/BunnyFile-BgEOlcYI.js +1 -0
  44. package/dist/packem_shared/BunnyMetaStorage-DFwhEI9C.js +1 -0
  45. package/dist/packem_shared/BunnyStorage-CILSK4_Z.js +1 -0
  46. package/dist/packem_shared/CloudinaryFile-Bo5B-vM1.js +1 -0
  47. package/dist/packem_shared/CloudinaryMetaStorage-D_vNzewL.js +1 -0
  48. package/dist/packem_shared/CloudinaryStorage-DiCbdAi_.js +1 -0
  49. package/dist/packem_shared/DiskStorage-Kp5t3vnF.js +1 -0
  50. package/dist/packem_shared/DiskStorageWithChecksum-Bh6w-Iu8.js +1 -0
  51. package/dist/packem_shared/DropboxFile-BFb7eOzy.js +1 -0
  52. package/dist/packem_shared/DropboxMetaStorage-DFwhEI9C.js +1 -0
  53. package/dist/packem_shared/DropboxStorage-H8bd8hEz.js +1 -0
  54. package/dist/packem_shared/ERRORS-BIBxE2oR.js +1 -0
  55. package/dist/packem_shared/File-W8aOo15X.js +1 -0
  56. package/dist/packem_shared/Files-BA3mpDwz.js +1 -0
  57. package/dist/packem_shared/FirebaseFile-BLaBxa2A.js +1 -0
  58. package/dist/packem_shared/FirebaseMetaStorage-D_vNzewL.js +1 -0
  59. package/dist/packem_shared/FirebaseStorage-Dgk4XyMr.js +2 -0
  60. package/dist/packem_shared/FtpFile-ClWDYnt2.js +1 -0
  61. package/dist/packem_shared/FtpMetaStorage-DFwhEI9C.js +1 -0
  62. package/dist/packem_shared/FtpStorage-g_DjiR-C.js +1 -0
  63. package/dist/packem_shared/GCSConfig-BQ0OpVhe.js +1 -0
  64. package/dist/packem_shared/GCSFile-Cero7qZN.js +1 -0
  65. package/dist/packem_shared/GCSMetaStorage-3fLTlRd4.js +1 -0
  66. package/dist/packem_shared/GCStorage-DUfwVFd3.js +1 -0
  67. package/dist/packem_shared/GoogleDriveFile-DHpLhzg9.js +1 -0
  68. package/dist/packem_shared/GoogleDriveMetaStorage-DqkgoE46.js +1 -0
  69. package/dist/packem_shared/GoogleDriveStorage-D0-5egHE.js +1 -0
  70. package/dist/packem_shared/LocalMetaStorage-Bp5mVc76.js +1 -0
  71. package/dist/packem_shared/MediaTransformer-D2kUsklW.js +1 -0
  72. package/dist/packem_shared/MemoryMetaStorage-Ksgh9pe7.js +1 -0
  73. package/dist/packem_shared/MemoryStorage-DzSTdlAq.js +1 -0
  74. package/dist/packem_shared/MetaStorage-DPEUyWgN.js +1 -0
  75. package/dist/packem_shared/Metadata-B7CcBueg.js +1 -0
  76. package/dist/packem_shared/Multipart-Btj2mo9r.js +1 -0
  77. package/dist/packem_shared/Multipart-C4GpuHMU.js +1 -0
  78. package/dist/packem_shared/NetlifyBlobFile-DoFhkzaH.js +1 -0
  79. package/dist/packem_shared/NetlifyBlobMetaStorage-D_vNzewL.js +1 -0
  80. package/dist/packem_shared/NetlifyBlobStorage-DZdCmOVW.js +1 -0
  81. package/dist/packem_shared/NoOpMetrics-BLo6u4NY.js +1 -0
  82. package/dist/packem_shared/OneDriveFile-CNNJYI43.js +1 -0
  83. package/dist/packem_shared/OneDriveMetaStorage-DqkgoE46.js +1 -0
  84. package/dist/packem_shared/OneDriveStorage-CvJetV7_.js +1 -0
  85. package/dist/packem_shared/OpenTelemetryMetrics-DJDQsNKp.js +1 -0
  86. package/dist/packem_shared/PocketBaseFile-DpJpxl3e.js +1 -0
  87. package/dist/packem_shared/PocketBaseMetaStorage-CpvDRnSu.js +1 -0
  88. package/dist/packem_shared/PocketBaseStorage-BPil-koe.js +1 -0
  89. package/dist/packem_shared/Rest-BehVaxbl.js +1 -0
  90. package/dist/packem_shared/Rest-ymPCZkKR.js +1 -0
  91. package/dist/packem_shared/S3File-CpZrubaV.js +1 -0
  92. package/dist/packem_shared/S3MetaStorage-CMonflzp.js +1 -0
  93. package/dist/packem_shared/S3Storage-wslqssvr.js +1 -0
  94. package/dist/packem_shared/SftpFile-ClWDYnt2.js +1 -0
  95. package/dist/packem_shared/SftpMetaStorage-DFwhEI9C.js +1 -0
  96. package/dist/packem_shared/SftpStorage-BVbMtS2b.js +1 -0
  97. package/dist/packem_shared/SharePointFile-Blz9FS4h.js +1 -0
  98. package/dist/packem_shared/SharePointMetaStorage-DFwhEI9C.js +1 -0
  99. package/dist/packem_shared/SharePointStorage-DWjvR5oZ.js +1 -0
  100. package/dist/packem_shared/SupabaseFile-Bo5B-vM1.js +1 -0
  101. package/dist/packem_shared/SupabaseMetaStorage-DqkgoE46.js +1 -0
  102. package/dist/packem_shared/SupabaseStorage-BiKmYKb6.js +1 -0
  103. package/dist/packem_shared/TUS_RESUMABLE-CyTSRvPU.js +1 -0
  104. package/dist/packem_shared/Tus-BgbON_wQ.js +1 -0
  105. package/dist/packem_shared/Tus-v6jzkaIO.js +1 -0
  106. package/dist/packem_shared/UploadControl-DZJhI9Wh.js +1 -0
  107. package/dist/packem_shared/UploadThingFile-BTFMpcIA.js +1 -0
  108. package/dist/packem_shared/UploadThingMetaStorage-D_vNzewL.js +1 -0
  109. package/dist/packem_shared/UploadThingStorage-jrEnANC5.js +1 -0
  110. package/dist/packem_shared/ValidationError-3B06DFyE.js +1 -0
  111. package/dist/packem_shared/VercelBlobFile-CVQwKlZk.js +1 -0
  112. package/dist/packem_shared/VercelBlobMetaStorage-DFwhEI9C.js +1 -0
  113. package/dist/packem_shared/VercelBlobStorage-Y-cDgH30.js +1 -0
  114. package/dist/packem_shared/_commonjsHelpers-CWAkuNXM.js +1 -0
  115. package/dist/packem_shared/agentsCopyFile-Dl5iffdH.js +1 -0
  116. package/dist/packem_shared/akamai-DthkaFul.js +1 -0
  117. package/dist/packem_shared/alibaba-BEi25O1g.js +1 -0
  118. package/dist/packem_shared/approval-fVHwBp7u.js +1 -0
  119. package/dist/packem_shared/approval.d-CMAYH9GF.d.ts +75 -0
  120. package/dist/packem_shared/aws-light-meta-storage-DGrn72VJ.js +4 -0
  121. package/dist/packem_shared/azure-meta-storage-ClbEsfI4.js +1 -0
  122. package/dist/packem_shared/backblaze-m1N5NZ9q.js +1 -0
  123. package/dist/packem_shared/base-handler-core-EeV8gZck.js +1 -0
  124. package/dist/packem_shared/base-handler-fetch-CHzsgb7C.js +1 -0
  125. package/dist/packem_shared/base-handler-node-BjpW8pGi.js +1 -0
  126. package/dist/packem_shared/cache-Cw3QjoVN.js +1 -0
  127. package/dist/packem_shared/claudeCopyFile-BX9O4ORk.js +1 -0
  128. package/dist/packem_shared/cloudflare-CdUTErlo.js +1 -0
  129. package/dist/packem_shared/copyFile-49FtxXcm.js +1 -0
  130. package/dist/packem_shared/copyFile-BUPezT_c.js +1 -0
  131. package/dist/packem_shared/createResponsesFileTools-6Tvt2PNr.js +1 -0
  132. package/dist/packem_shared/createRetryWrapper-CxgiV_hH.js +1 -0
  133. package/dist/packem_shared/detect-file-type-BA7UBLKA.js +1 -0
  134. package/dist/packem_shared/digitalOcean-B2uB6pgz.js +1 -0
  135. package/dist/packem_shared/disk-storage-DIn-VnCh.js +1 -0
  136. package/dist/packem_shared/disk-storage-with-checksum.d-B-VGEsfl.d.ts +156 -0
  137. package/dist/packem_shared/executors-BDzMjc4y.js +1 -0
  138. package/dist/packem_shared/executors.d-BZP2rWo3.d.ts +69 -0
  139. package/dist/packem_shared/exoscale-BDa1Gjth.js +1 -0
  140. package/dist/packem_shared/filebase-CsFYJIwB.js +1 -0
  141. package/dist/packem_shared/files.d-CH0iLBNC.d.ts +655 -0
  142. package/dist/packem_shared/gcs-meta-storage-Dy37wCjI.js +1 -0
  143. package/dist/packem_shared/get-file-status-y3wTtDQs.js +1 -0
  144. package/dist/packem_shared/getFormatFromContentType-DCTTPQHm.js +1 -0
  145. package/dist/packem_shared/has-content-50BsqrWw.js +1 -0
  146. package/dist/packem_shared/headers-BAiAKekR.js +26 -0
  147. package/dist/packem_shared/hetzner-BGGFiRGD.js +1 -0
  148. package/dist/packem_shared/ibmCos-j-3TfJ5p.js +1 -0
  149. package/dist/packem_shared/idriveE2-C6pQ5pQ0.js +1 -0
  150. package/dist/packem_shared/index-nZWCQrSe.js +5 -0
  151. package/dist/packem_shared/internal-D_cZIFwI.js +1 -0
  152. package/dist/packem_shared/is-expired-CBEk6XBi.js +1 -0
  153. package/dist/packem_shared/local-meta-storage-C2T92TYb.js +11 -0
  154. package/dist/packem_shared/local-meta-storage.d-D9PBfkn6.d.ts +21 -0
  155. package/dist/packem_shared/media-transformer.d-Quf4ai47.d.ts +331 -0
  156. package/dist/packem_shared/memory-storage.d-4EU1cMt1.d.ts +101 -0
  157. package/dist/packem_shared/minio-NKquuBfS.js +1 -0
  158. package/dist/packem_shared/multipart-base-BOzY19lb.js +1 -0
  159. package/dist/packem_shared/oauth-refresh-EdGzlcOZ.js +1 -0
  160. package/dist/packem_shared/oracleCloud-DslqNpn6.js +1 -0
  161. package/dist/packem_shared/ovhCloud-CMHE6uLV.js +1 -0
  162. package/dist/packem_shared/part-match-D-9dGX42.js +1 -0
  163. package/dist/packem_shared/path-0oTTdkvl-BVg7lYf5.js +1 -0
  164. package/dist/packem_shared/posix-dirname-CfpH5wZi.js +1 -0
  165. package/dist/packem_shared/response-builder-CbSA8qPa.js +1 -0
  166. package/dist/packem_shared/rest-base-CynUg0mH.js +1 -0
  167. package/dist/packem_shared/restOpenApiSpec-Csv513qf.js +1 -0
  168. package/dist/packem_shared/s3-base-storage-DXZYN24h.js +1 -0
  169. package/dist/packem_shared/s3-base-storage.d-BQgP5B-t.d.ts +287 -0
  170. package/dist/packem_shared/scaleway-U1In3v70.js +1 -0
  171. package/dist/packem_shared/sharedErrorSchemaObject-YN65aAKj.js +1 -0
  172. package/dist/packem_shared/storage-Cyy73Y6r.js +1 -0
  173. package/dist/packem_shared/storage.d-CEM1upWM.d.ts +1176 -0
  174. package/dist/packem_shared/storj-Cb59q9kF.js +1 -0
  175. package/dist/packem_shared/sync-DhR3536K.js +1 -0
  176. package/dist/packem_shared/tencent-Q1y2GENc.js +1 -0
  177. package/dist/packem_shared/tigris-BELKoyyp.js +1 -0
  178. package/dist/packem_shared/transformOpenApiSpec-CIEAgpBD.js +1 -0
  179. package/dist/packem_shared/tus-base.d-DLzKE54M.d.ts +106 -0
  180. package/dist/packem_shared/tusOpenApiSpec-D96B03t5.js +1 -0
  181. package/dist/packem_shared/types.d-Bon9GVVe.d.ts +104 -0
  182. package/dist/packem_shared/types.d-CggTCgXr.d.ts +49 -0
  183. package/dist/packem_shared/types.d-CrUWY4On.d.ts +720 -0
  184. package/dist/packem_shared/update-size-DuNuLyxj.js +1 -0
  185. package/dist/packem_shared/vultr-B491cQ4e.js +1 -0
  186. package/dist/packem_shared/waitForStorage-ByQmG4xF.js +1 -0
  187. package/dist/packem_shared/wasabi-DFrwIoab.js +1 -0
  188. package/dist/packem_shared/xhrOpenApiSpec-DQR4h6M8.js +1 -0
  189. package/dist/packem_shared/yandex-CwzHuEKP.js +1 -0
  190. package/dist/storage/aws/clients/index.d.ts +612 -6
  191. package/dist/storage/aws/clients/index.js +1 -6
  192. package/dist/storage/aws/index.d.ts +332 -4
  193. package/dist/storage/aws/index.js +1 -3
  194. package/dist/storage/aws-light/index.d.ts +259 -4
  195. package/dist/storage/aws-light/index.js +1 -3
  196. package/dist/storage/azure/index.d.ts +236 -4
  197. package/dist/storage/azure/index.js +1 -3
  198. package/dist/storage/box/index.d.ts +189 -0
  199. package/dist/storage/box/index.js +1 -0
  200. package/dist/storage/bun-s3/index.d.ts +200 -0
  201. package/dist/storage/bun-s3/index.js +1 -0
  202. package/dist/storage/bunny/index.d.ts +119 -0
  203. package/dist/storage/bunny/index.js +1 -0
  204. package/dist/storage/cloudinary/index.d.ts +121 -0
  205. package/dist/storage/cloudinary/index.js +1 -0
  206. package/dist/storage/dropbox/index.d.ts +132 -0
  207. package/dist/storage/dropbox/index.js +1 -0
  208. package/dist/storage/firebase/index.d.ts +192 -0
  209. package/dist/storage/firebase/index.js +1 -0
  210. package/dist/storage/ftp/index.d.ts +91 -0
  211. package/dist/storage/ftp/index.js +1 -0
  212. package/dist/storage/gcs/index.d.ts +195 -5
  213. package/dist/storage/gcs/index.js +1 -4
  214. package/dist/storage/google-drive/index.d.ts +148 -0
  215. package/dist/storage/google-drive/index.js +1 -0
  216. package/dist/storage/local/index.d.ts +7 -4
  217. package/dist/storage/local/index.js +1 -3
  218. package/dist/storage/memory/index.d.ts +6 -0
  219. package/dist/storage/memory/index.js +1 -0
  220. package/dist/storage/netlify-blob/index.d.ts +147 -4
  221. package/dist/storage/netlify-blob/index.js +1 -3
  222. package/dist/storage/onedrive/index.d.ts +103 -0
  223. package/dist/storage/onedrive/index.js +1 -0
  224. package/dist/storage/pocketbase/index.d.ts +172 -0
  225. package/dist/storage/pocketbase/index.js +1 -0
  226. package/dist/storage/sftp/index.d.ts +92 -0
  227. package/dist/storage/sftp/index.js +1 -0
  228. package/dist/storage/sharepoint/index.d.ts +180 -0
  229. package/dist/storage/sharepoint/index.js +1 -0
  230. package/dist/storage/supabase/index.d.ts +115 -0
  231. package/dist/storage/supabase/index.js +1 -0
  232. package/dist/storage/uploadthing/index.d.ts +95 -0
  233. package/dist/storage/uploadthing/index.js +1 -0
  234. package/dist/storage/vercel-blob/index.d.ts +189 -4
  235. package/dist/storage/vercel-blob/index.js +1 -3
  236. package/dist/transformer/audio-transformer.d.ts +127 -125
  237. package/dist/transformer/audio-transformer.js +1 -278
  238. package/dist/transformer/image-transformer.d.ts +573 -568
  239. package/dist/transformer/image-transformer.js +1 -1100
  240. package/dist/transformer/index.d.ts +62 -5
  241. package/dist/transformer/index.js +1 -4
  242. package/dist/transformer/video-transformer.d.ts +144 -142
  243. package/dist/transformer/video-transformer.js +1 -310
  244. package/package.json +202 -51
  245. package/dist/handler/base/base-handler-core.d.ts +0 -91
  246. package/dist/handler/base/base-handler-fetch.d.ts +0 -76
  247. package/dist/handler/base/base-handler-node.d.ts +0 -137
  248. package/dist/handler/multipart/multipart-base.d.ts +0 -84
  249. package/dist/handler/multipart/multipart-fetch.d.ts +0 -64
  250. package/dist/handler/multipart/multipart.d.ts +0 -49
  251. package/dist/handler/rest/rest-base.d.ts +0 -106
  252. package/dist/handler/rest/rest-fetch.d.ts +0 -88
  253. package/dist/handler/rest/rest.d.ts +0 -93
  254. package/dist/handler/tus/tus-base.d.ts +0 -152
  255. package/dist/handler/tus/tus-fetch.d.ts +0 -72
  256. package/dist/handler/tus/tus.d.ts +0 -78
  257. package/dist/handler/types.d.ts +0 -53
  258. package/dist/handler/utils/request-parser.d.ts +0 -72
  259. package/dist/handler/utils/response-builder.d.ts +0 -83
  260. package/dist/handler/utils/storage-utils.d.ts +0 -10
  261. package/dist/handler/utils/stream-utils.d.ts +0 -29
  262. package/dist/handler/utils/upload-handlers.d.ts +0 -76
  263. package/dist/metrics/index.d.ts +0 -2
  264. package/dist/metrics/no-op-metrics.d.ts +0 -15
  265. package/dist/metrics/opentelemetry-metrics.d.ts +0 -55
  266. package/dist/openapi/rest.d.ts +0 -7
  267. package/dist/openapi/shared.d.ts +0 -13
  268. package/dist/openapi/transform.d.ts +0 -3
  269. package/dist/openapi/tus.d.ts +0 -7
  270. package/dist/openapi/xhr.d.ts +0 -7
  271. package/dist/packem_shared/AwsLightFile-tTneXZgG.js +0 -11
  272. package/dist/packem_shared/AwsLightMetaStorage-BWSOtVaN.js +0 -4
  273. package/dist/packem_shared/AwsLightStorage-Blv-GP4v.js +0 -133
  274. package/dist/packem_shared/AzureFile-CesgFzps.js +0 -8
  275. package/dist/packem_shared/AzureSMetaStorage-CFs-OYJT.js +0 -88
  276. package/dist/packem_shared/AzureStorage-B0v048hG.js +0 -357
  277. package/dist/packem_shared/BaseTransformer-C2gLib6v.js +0 -82
  278. package/dist/packem_shared/DiskStorage-Ck5yGQsq.js +0 -12
  279. package/dist/packem_shared/DiskStorageWithChecksum-BRl-V5x2.js +0 -238
  280. package/dist/packem_shared/ERRORS-D0apMqnc.js +0 -97
  281. package/dist/packem_shared/File-Bb3P23dr.js +0 -69
  282. package/dist/packem_shared/GCSConfig-vPP22kN6.js +0 -11
  283. package/dist/packem_shared/GCSFile-BIEunhAN.js +0 -8
  284. package/dist/packem_shared/GCSMetaStorage-CHZKMe7N.js +0 -7
  285. package/dist/packem_shared/GCStorage-C-gAuP0j.js +0 -406
  286. package/dist/packem_shared/LocalMetaStorage-CZHhKkMd.js +0 -7
  287. package/dist/packem_shared/MediaTransformer-D6658DL1.js +0 -1197
  288. package/dist/packem_shared/MetaStorage-pECeFOad.js +0 -46
  289. package/dist/packem_shared/Metadata-DRLXeJ0F.js +0 -89
  290. package/dist/packem_shared/Multipart-CRV21AUU.js +0 -128
  291. package/dist/packem_shared/Multipart-D2ryPMjD.js +0 -163
  292. package/dist/packem_shared/NetlifyBlobFile-CXzyjqrD.js +0 -14
  293. package/dist/packem_shared/NetlifyBlobMetaStorage-DxZ5aDvD.js +0 -9
  294. package/dist/packem_shared/NetlifyBlobStorage-CLPtjHqd.js +0 -376
  295. package/dist/packem_shared/NoOpMetrics-DhAk5rXc.js +0 -10
  296. package/dist/packem_shared/OpenTelemetryMetrics-BnxhqIaH.js +0 -67
  297. package/dist/packem_shared/Rest-DcxBMBjU.js +0 -228
  298. package/dist/packem_shared/Rest-DjwU3puo.js +0 -267
  299. package/dist/packem_shared/S3File-DZiyk9Qt.js +0 -11
  300. package/dist/packem_shared/S3MetaStorage-Dz9aDabA.js +0 -76
  301. package/dist/packem_shared/S3Storage-DHmTk-hU.js +0 -316
  302. package/dist/packem_shared/TUS_RESUMABLE-Dtfsffnj.js +0 -434
  303. package/dist/packem_shared/Tus-DFVlZHaX.js +0 -200
  304. package/dist/packem_shared/Tus-DaN0FmOy.js +0 -195
  305. package/dist/packem_shared/ValidationError-BfF1aE4h.js +0 -26
  306. package/dist/packem_shared/VercelBlobFile-BCg4aTEq.js +0 -18
  307. package/dist/packem_shared/VercelBlobMetaStorage-Bd9F-VFm.js +0 -9
  308. package/dist/packem_shared/VercelBlobStorage-DD9LMOS6.js +0 -261
  309. package/dist/packem_shared/_commonjsHelpers-BqLXS_qQ.js +0 -5
  310. package/dist/packem_shared/aws-light-meta-storage-DKJBgbR6.js +0 -446
  311. package/dist/packem_shared/backblaze-BlMnIcBC.js +0 -20
  312. package/dist/packem_shared/base-handler-core-BoAqTyz7.js +0 -303
  313. package/dist/packem_shared/base-handler-fetch-D4u2xits.js +0 -291
  314. package/dist/packem_shared/base-handler-node-DGzcHHAy.js +0 -730
  315. package/dist/packem_shared/cache-B88MXQ_2.js +0 -18
  316. package/dist/packem_shared/cloudflare-Bi1q8wXE.js +0 -21
  317. package/dist/packem_shared/defaultCloudStorageFileNameValidation-DUuacjWv.js +0 -11
  318. package/dist/packem_shared/digitalOcean-CWQRJM3L.js +0 -21
  319. package/dist/packem_shared/disk-storage-CD47QI30.js +0 -810
  320. package/dist/packem_shared/gcs-meta-storage-CJ8Uts_d.js +0 -158
  321. package/dist/packem_shared/has-content-CY66ehMK.js +0 -3
  322. package/dist/packem_shared/headers-YLRp1dLo.js +0 -1318
  323. package/dist/packem_shared/is-expired-CTThU1q5.js +0 -8
  324. package/dist/packem_shared/isRetryableError-Dycp7127.js +0 -82
  325. package/dist/packem_shared/isValidMediaType-BeDgiObq.js +0 -35
  326. package/dist/packem_shared/local-meta-storage-By-3SNBI.js +0 -649
  327. package/dist/packem_shared/minio-C2YBZQOw.js +0 -22
  328. package/dist/packem_shared/multipart-base-C994naBi.js +0 -102
  329. package/dist/packem_shared/part-match-BMNqHDYD.js +0 -96
  330. package/dist/packem_shared/path-CR6YkPXX-7R1-9CMk.js +0 -161
  331. package/dist/packem_shared/response-builder-BtnRiBUI.js +0 -45
  332. package/dist/packem_shared/rest-base-D9URIFkc.js +0 -457
  333. package/dist/packem_shared/restOpenApiSpec-D1JC_Jto.js +0 -800
  334. package/dist/packem_shared/s3-base-storage-C1DIHTYY.js +0 -510
  335. package/dist/packem_shared/sharedGet-Cpo7QUyu.js +0 -1019
  336. package/dist/packem_shared/storage-C6NSXb8h.js +0 -1175
  337. package/dist/packem_shared/tigris-Hac8TKnX.js +0 -21
  338. package/dist/packem_shared/transformOpenApiSpec-DWM5WtnN.js +0 -975
  339. package/dist/packem_shared/tusOpenApiSpec-mBZkl7he.js +0 -740
  340. package/dist/packem_shared/update-size-CCGm6i1J.js +0 -8
  341. package/dist/packem_shared/validator-BeX_lJet.js +0 -78
  342. package/dist/packem_shared/waitForStorage-Cscw85sx.js +0 -18
  343. package/dist/packem_shared/wasabi-DIyflHSd.js +0 -21
  344. package/dist/packem_shared/xhrOpenApiSpec-B1V5Dxrj.js +0 -264
  345. package/dist/storage/aws/clients/backblaze.d.ts +0 -12
  346. package/dist/storage/aws/clients/cloudflare.d.ts +0 -13
  347. package/dist/storage/aws/clients/digital-ocean.d.ts +0 -12
  348. package/dist/storage/aws/clients/minio.d.ts +0 -13
  349. package/dist/storage/aws/clients/tigris.d.ts +0 -12
  350. package/dist/storage/aws/clients/types.d.ts +0 -95
  351. package/dist/storage/aws/clients/wasabi.d.ts +0 -12
  352. package/dist/storage/aws/s3-base-storage.d.ts +0 -248
  353. package/dist/storage/aws/s3-client-adapter.d.ts +0 -110
  354. package/dist/storage/aws/s3-file.d.ts +0 -10
  355. package/dist/storage/aws/s3-meta-storage.d.ts +0 -15
  356. package/dist/storage/aws/s3-storage.d.ts +0 -70
  357. package/dist/storage/aws/types.d.ts +0 -119
  358. package/dist/storage/aws-light/aws-light-api-adapter.d.ts +0 -130
  359. package/dist/storage/aws-light/aws-light-file.d.ts +0 -10
  360. package/dist/storage/aws-light/aws-light-meta-storage.d.ts +0 -19
  361. package/dist/storage/aws-light/aws-light-storage.d.ts +0 -65
  362. package/dist/storage/aws-light/types.d.ts +0 -37
  363. package/dist/storage/azure/azure-file.d.ts +0 -6
  364. package/dist/storage/azure/azure-meta-storage.d.ts +0 -15
  365. package/dist/storage/azure/azure-storage.d.ts +0 -69
  366. package/dist/storage/azure/types.d.ts +0 -62
  367. package/dist/storage/gcs/fetch-error.d.ts +0 -11
  368. package/dist/storage/gcs/gcs-config.d.ts +0 -2
  369. package/dist/storage/gcs/gcs-file.d.ts +0 -6
  370. package/dist/storage/gcs/gcs-meta-storage.d.ts +0 -27
  371. package/dist/storage/gcs/gcs-storage.d.ts +0 -91
  372. package/dist/storage/gcs/types.d.ts +0 -55
  373. package/dist/storage/gcs/utils.d.ts +0 -7
  374. package/dist/storage/local/disk-storage-with-checksum.d.ts +0 -15
  375. package/dist/storage/local/disk-storage.d.ts +0 -135
  376. package/dist/storage/local/local-meta-storage.d.ts +0 -32
  377. package/dist/storage/meta-storage.d.ts +0 -30
  378. package/dist/storage/netlify-blob/netlify-blob-file.d.ts +0 -12
  379. package/dist/storage/netlify-blob/netlify-blob-meta-storage.d.ts +0 -7
  380. package/dist/storage/netlify-blob/netlify-blob-storage.d.ts +0 -93
  381. package/dist/storage/netlify-blob/types.d.ts +0 -30
  382. package/dist/storage/storage.d.ts +0 -353
  383. package/dist/storage/types.d.ts +0 -221
  384. package/dist/storage/utils/file/file.d.ts +0 -25
  385. package/dist/storage/utils/file/get-file-status.d.ts +0 -9
  386. package/dist/storage/utils/file/has-content.d.ts +0 -9
  387. package/dist/storage/utils/file/index.d.ts +0 -10
  388. package/dist/storage/utils/file/is-expired.d.ts +0 -8
  389. package/dist/storage/utils/file/metadata.d.ts +0 -18
  390. package/dist/storage/utils/file/part-match.d.ts +0 -11
  391. package/dist/storage/utils/file/types.d.ts +0 -37
  392. package/dist/storage/utils/file/update-metadata.d.ts +0 -10
  393. package/dist/storage/utils/file/update-size.d.ts +0 -10
  394. package/dist/storage/vercel-blob/types.d.ts +0 -32
  395. package/dist/storage/vercel-blob/vercel-blob-file.d.ts +0 -16
  396. package/dist/storage/vercel-blob/vercel-blob-meta-storage.d.ts +0 -7
  397. package/dist/storage/vercel-blob/vercel-blob-storage.d.ts +0 -76
  398. package/dist/transformer/base-transformer.d.ts +0 -63
  399. package/dist/transformer/media-transformer.d.ts +0 -332
  400. package/dist/transformer/types.d.ts +0 -652
  401. package/dist/transformer/utils.d.ts +0 -33
  402. package/dist/transformer/validation-error.d.ts +0 -23
  403. package/dist/utils/cache.d.ts +0 -32
  404. package/dist/utils/chunked-upload.d.ts +0 -65
  405. package/dist/utils/detect-file-type.d.ts +0 -28
  406. package/dist/utils/errors.d.ts +0 -74
  407. package/dist/utils/file-path-url-matcher.d.ts +0 -18
  408. package/dist/utils/headers.d.ts +0 -111
  409. package/dist/utils/http.d.ts +0 -92
  410. package/dist/utils/locker.d.ts +0 -26
  411. package/dist/utils/pipes/stream-checksum.d.ts +0 -47
  412. package/dist/utils/pipes/stream-length.d.ts +0 -22
  413. package/dist/utils/primitives/get-last-one.d.ts +0 -3
  414. package/dist/utils/primitives/is-record.d.ts +0 -2
  415. package/dist/utils/primitives/map-values.d.ts +0 -9
  416. package/dist/utils/primitives/pick.d.ts +0 -2
  417. package/dist/utils/primitives/to-milliseconds.d.ts +0 -12
  418. package/dist/utils/primitives/to-seconds.d.ts +0 -12
  419. package/dist/utils/range-checksum.d.ts +0 -33
  420. package/dist/utils/range-hasher.d.ts +0 -46
  421. package/dist/utils/retry.d.ts +0 -64
  422. package/dist/utils/types.d.ts +0 -108
  423. package/dist/utils/validation-error.d.ts +0 -22
  424. package/dist/utils/validator.d.ts +0 -36
@@ -1,1197 +0,0 @@
1
- import { createHash } from 'node:crypto';
2
- import mime from 'mime';
3
- import { N as NoOpCache } from './cache-B88MXQ_2.js';
4
- import { isKnownContentType } from './isValidMediaType-BeDgiObq.js';
5
- import ValidationError from './ValidationError-BfF1aE4h.js';
6
-
7
- class MediaTransformer {
8
- /**
9
- * Creates a new MediaTransformer instance.
10
- * @param storage The storage backend for retrieving and storing media files.
11
- * @param config Configuration options for the media transformer including transformer classes and settings.
12
- * @throws Error if no transformer classes are provided in the configuration.
13
- */
14
- constructor(storage, config = {}) {
15
- this.storage = storage;
16
- this.logger = config.logger || this.storage.logger;
17
- this.config = {
18
- audioBitrate: 128e3,
19
- // 128 kbps
20
- audioCodec: "aac",
21
- cache: config.cache ?? new NoOpCache(),
22
- cacheTtl: 3600,
23
- // 1 hour
24
- maxAudioSize: 100 * 1024 * 1024,
25
- // 100MB
26
- maxImageSize: 10 * 1024 * 1024,
27
- // 10MB
28
- maxVideoSize: 500 * 1024 * 1024,
29
- // 500MB
30
- saveTransformedFiles: false,
31
- // Save transformed files to storage
32
- supportedAudioFormats: [],
33
- supportedImageFormats: [],
34
- supportedVideoFormats: [],
35
- videoBitrate: 2e6,
36
- // 2 Mbps
37
- videoCodec: "avc",
38
- ...config
39
- };
40
- if (config.ImageTransformer) {
41
- if (!Array.isArray(this.config.supportedImageFormats) || this.config.supportedImageFormats.length === 0) {
42
- this.config.supportedImageFormats = ["jpeg", "png", "webp", "avif", "tiff", "gif", "svg"];
43
- }
44
- this.imageTransformer = new config.ImageTransformer(this.storage, {
45
- cache: this.config.cache,
46
- cacheTtl: this.config.cacheTtl,
47
- logger: this.logger,
48
- maxImageSize: this.config.maxImageSize,
49
- supportedFormats: this.config.supportedImageFormats
50
- });
51
- }
52
- if (config.VideoTransformer) {
53
- if (!Array.isArray(this.config.supportedVideoFormats) || this.config.supportedVideoFormats.length === 0) {
54
- this.config.supportedVideoFormats = ["mp4", "webm", "mkv", "avi", "mov", "flv", "wmv"];
55
- }
56
- this.videoTransformer = new config.VideoTransformer(this.storage, {
57
- cache: this.config.cache,
58
- cacheTtl: this.config.cacheTtl,
59
- defaultBitrate: this.config.videoBitrate,
60
- defaultCodec: this.config.videoCodec,
61
- logger: this.logger,
62
- maxVideoSize: this.config.maxVideoSize,
63
- supportedFormats: this.config.supportedVideoFormats
64
- });
65
- }
66
- if (config.AudioTransformer) {
67
- if (!Array.isArray(this.config.supportedAudioFormats) || this.config.supportedAudioFormats.length === 0) {
68
- this.config.supportedAudioFormats = ["mp3", "wav", "ogg", "aac", "flac", "m4a", "wma", "aiff"];
69
- }
70
- this.audioTransformer = new config.AudioTransformer(this.storage, {
71
- cache: this.config.cache,
72
- cacheTtl: this.config.cacheTtl,
73
- defaultBitrate: this.config.audioBitrate,
74
- defaultCodec: this.config.audioCodec,
75
- logger: this.logger,
76
- maxAudioSize: this.config.maxAudioSize,
77
- supportedFormats: this.config.supportedAudioFormats
78
- });
79
- }
80
- if (config.AudioTransformer === void 0 && config.ImageTransformer === void 0 && config.VideoTransformer === void 0) {
81
- throw new Error(
82
- "MediaTransformer initialization failed: No transformers are configured. At least one transformer (AudioTransformer, ImageTransformer, or VideoTransformer) must be provided in the configuration to enable media processing functionality."
83
- );
84
- }
85
- }
86
- imageTransformer;
87
- videoTransformer;
88
- audioTransformer;
89
- config;
90
- logger;
91
- supportedFormats() {
92
- return [...this.config.supportedAudioFormats, ...this.config.supportedImageFormats, ...this.config.supportedVideoFormats];
93
- }
94
- /**
95
- * Handles media transformation based on query parameters.
96
- * @param fileId File identifier.
97
- * @param query Query parameters for transformation.
98
- * @returns Unified transformation result.
99
- */
100
- async handle(fileId, query) {
101
- const parsedQuery = this.parseQuery(query);
102
- const fileQuery = { id: fileId };
103
- const file = await this.storage.get(fileQuery);
104
- const mediaType = this.detectMediaType(file.contentType);
105
- this.validateQueryParameters(parsedQuery, mediaType);
106
- if (this.config.saveTransformedFiles && this.hasTransformations(parsedQuery)) {
107
- const transformedFileId = this.generateTransformedFileId(fileId, parsedQuery, mediaType);
108
- try {
109
- const transformedFile = await this.storage.get({ id: transformedFileId });
110
- this.logger?.debug?.(`Serving cached transformed file: ${transformedFileId}`);
111
- return this.createMediaTransformResult(transformedFile, mediaType, file);
112
- } catch {
113
- this.logger?.debug?.(`Transformed file not found, processing: ${transformedFileId}`);
114
- }
115
- }
116
- let result;
117
- switch (mediaType) {
118
- case "audio": {
119
- if (!this.audioTransformer) {
120
- throw new Error(
121
- "Audio transformer not available. Please install audio transformation dependencies or provide an audio transformer instance."
122
- );
123
- }
124
- result = await this.handleAudioTransformation(fileId, parsedQuery);
125
- break;
126
- }
127
- case "image": {
128
- if (!this.imageTransformer) {
129
- throw new Error(
130
- "Image transformer not available. Please install image transformation dependencies or provide an image transformer instance."
131
- );
132
- }
133
- result = await this.handleImageTransformation(fileId, parsedQuery);
134
- break;
135
- }
136
- case "video": {
137
- if (!this.videoTransformer) {
138
- throw new Error(
139
- "Video transformer not available. Please install video transformation dependencies or provide a video transformer instance."
140
- );
141
- }
142
- result = await this.handleVideoTransformation(fileId, parsedQuery);
143
- break;
144
- }
145
- default: {
146
- throw new Error(`Unsupported media type: ${file.contentType}`);
147
- }
148
- }
149
- if (this.config.saveTransformedFiles && this.hasTransformations(parsedQuery)) {
150
- await this.saveTransformedFile(result, fileId, parsedQuery, mediaType);
151
- }
152
- return result;
153
- }
154
- /**
155
- * Fetches media transformation with URL query string support.
156
- * @param fileId File identifier.
157
- * @param queryString URL query string (e.g., "width=800&height=600&format=webp").
158
- * @returns Unified transformation result.
159
- */
160
- async fetch(fileId, queryString) {
161
- const query = new URLSearchParams(queryString);
162
- return this.handle(fileId, query);
163
- }
164
- /**
165
- * Clears cache for a specific file across all transformers.
166
- * @param fileId Optional file identifier to clear cache for. If omitted, clears all cache.
167
- */
168
- clearCache(fileId) {
169
- this.imageTransformer?.clearCache(fileId);
170
- this.videoTransformer?.clearCache(fileId);
171
- this.audioTransformer?.clearCache(fileId);
172
- }
173
- /**
174
- * Clears all saved transformed files from storage.
175
- * @remarks This is a maintenance operation and may take time for large numbers of files.
176
- */
177
- async clearSavedTransformedFiles() {
178
- if (!this.config.saveTransformedFiles) {
179
- return;
180
- }
181
- try {
182
- this.logger?.warn?.("clearSavedTransformedFiles requires custom storage implementation to find and delete transformed files");
183
- } catch (error) {
184
- this.logger?.error?.(`Failed to clear saved transformed files: ${error}`);
185
- }
186
- }
187
- /**
188
- * Clears saved transformed files for a specific original file.
189
- * @param originalFileId Original file identifier to clear transformed files for.
190
- */
191
- async clearSavedTransformedFilesForFile(originalFileId) {
192
- if (!this.config.saveTransformedFiles) {
193
- return;
194
- }
195
- try {
196
- this.logger?.warn?.("clearSavedTransformedFilesForFile requires custom storage implementation");
197
- } catch (error) {
198
- this.logger?.error?.(`Failed to clear saved transformed files for ${originalFileId}: ${error}`);
199
- }
200
- }
201
- /**
202
- * Gets cache statistics (combined from all transformers).
203
- * @returns Cache statistics for audio, image, and video transformers.
204
- */
205
- getCacheStats() {
206
- const stats = {
207
- audio: this.audioTransformer?.getCacheStats(),
208
- image: this.imageTransformer?.getCacheStats(),
209
- video: this.videoTransformer?.getCacheStats()
210
- };
211
- if (stats.image === void 0)
212
- delete stats.image;
213
- if (stats.video === void 0)
214
- delete stats.video;
215
- if (stats.audio === void 0)
216
- delete stats.audio;
217
- return stats;
218
- }
219
- /**
220
- * Validates query parameters for the given media type.
221
- * @param query The query parameters to validate.
222
- * @param mediaType The media type being validated ('image', 'video', or 'audio').
223
- * @throws {ValidationError} When invalid parameters are provided.
224
- */
225
- validateQueryParameters(query, mediaType) {
226
- switch (mediaType) {
227
- case "audio": {
228
- this.validateAudioQueryParameters(query);
229
- break;
230
- }
231
- case "image": {
232
- this.validateImageQueryParameters(query);
233
- break;
234
- }
235
- case "video": {
236
- this.validateVideoQueryParameters(query);
237
- break;
238
- }
239
- }
240
- }
241
- /**
242
- * Validates query parameters for image transformations. Checks for invalid video/audio-only parameters, invalid fit values, invalid rotation angles, invalid formats, and incomplete crop parameter sets.
243
- * @param query Query parameters to validate.
244
- * @throws {ValidationError} When validation fails.
245
- */
246
- // eslint-disable-next-line class-methods-use-this
247
- validateImageQueryParameters(query) {
248
- const allowedParameters = /* @__PURE__ */ new Set([
249
- "alphaQuality",
250
- "angle",
251
- "background",
252
- "bandbool",
253
- "blur",
254
- "boolean",
255
- "brightness",
256
- "channel",
257
- "clahe",
258
- "colourspace",
259
- "compressionLevel",
260
- "convolve",
261
- "cropHeight",
262
- "cropWidth",
263
- "delay",
264
- "dilate",
265
- "effort",
266
- "erode",
267
- "extractChannel",
268
- "fastShrinkOnLoad",
269
- "fit",
270
- "flatten",
271
- "flip",
272
- "flop",
273
- "format",
274
- "frameRate",
275
- "gamma",
276
- "grayscale",
277
- "greyscale",
278
- "height",
279
- "hue",
280
- "joinChannel",
281
- "kernel",
282
- "left",
283
- "lightness",
284
- "linear",
285
- "loop",
286
- "maxSlope",
287
- "median",
288
- "modulate",
289
- "negate",
290
- "normalise",
291
- "normalize",
292
- "position",
293
- "quality",
294
- "recombine",
295
- "saturation",
296
- "sharpen",
297
- "threshold",
298
- "tint",
299
- "top",
300
- "unflatten",
301
- "width",
302
- "withoutEnlargement",
303
- "withoutReduction"
304
- ]);
305
- const videoAudioOnlyParameters = /* @__PURE__ */ new Set(["bitrate", "codec", "frameRate", "keyFrameInterval", "numberOfChannels", "sampleRate"]);
306
- const invalidParameters = [];
307
- for (const parameter of videoAudioOnlyParameters) {
308
- if (query[parameter] !== void 0) {
309
- invalidParameters.push(parameter);
310
- }
311
- }
312
- if (invalidParameters.length > 0) {
313
- const sortedInvalidParameters = [...invalidParameters].toSorted();
314
- throw new ValidationError(
315
- `Invalid query parameters for image transformation: ${sortedInvalidParameters.join(", ")}. Images support: ${[...allowedParameters].toSorted().join(", ")}. Video/audio parameters (${sortedInvalidParameters.join(", ")}) are not supported for images.`,
316
- "INVALID_PARAMS_FOR_IMAGE",
317
- "image",
318
- sortedInvalidParameters,
319
- [...allowedParameters].toSorted()
320
- );
321
- }
322
- if (query.fit && !["contain", "cover", "fill", "inside", "outside"].includes(query.fit)) {
323
- throw new ValidationError(
324
- `Invalid fit value: "${query.fit}". Supported values: "cover", "contain", "fill", "inside", "outside"`,
325
- "INVALID_FIT_VALUE",
326
- "image",
327
- ["fit"],
328
- ["cover", "contain", "fill", "inside", "outside"]
329
- );
330
- }
331
- if (query.format && !["avif", "gif", "jpeg", "png", "tiff", "webp"].includes(query.format)) {
332
- throw new ValidationError(
333
- `Invalid format for image: "${query.format}". Supported formats: jpeg, png, webp, avif, tiff, gif`,
334
- "INVALID_FORMAT",
335
- "image",
336
- ["format"],
337
- ["jpeg", "png", "webp", "avif", "tiff", "gif"]
338
- );
339
- }
340
- const cropParameters = ["left", "top", "cropWidth", "cropHeight"];
341
- const providedCropParameters = cropParameters.filter((parameter) => query[parameter] !== void 0);
342
- if (providedCropParameters.length > 0 && providedCropParameters.length !== cropParameters.length) {
343
- throw new ValidationError(
344
- `Incomplete crop parameters: ${providedCropParameters.join(", ")}. All crop parameters must be provided: left, top, cropWidth, cropHeight`,
345
- "INCOMPLETE_CROP_PARAMS",
346
- "image",
347
- providedCropParameters,
348
- cropParameters
349
- );
350
- }
351
- }
352
- /**
353
- * Validates query parameters for video transformations. Checks for invalid audio-only parameters, invalid fit values, invalid rotation angles, invalid codecs, invalid formats, incomplete crop parameter sets, and invalid numeric values.
354
- * @param query Query parameters to validate.
355
- * @throws {ValidationError} When validation fails.
356
- */
357
- // eslint-disable-next-line class-methods-use-this
358
- validateVideoQueryParameters(query) {
359
- const allowedParameters = /* @__PURE__ */ new Set([
360
- "angle",
361
- "background",
362
- "bitrate",
363
- "codec",
364
- "cropHeight",
365
- "cropWidth",
366
- "fit",
367
- "format",
368
- "frameRate",
369
- "height",
370
- "keyFrameInterval",
371
- "left",
372
- "position",
373
- "quality",
374
- "top",
375
- "width",
376
- "withoutEnlargement",
377
- "withoutReduction"
378
- ]);
379
- const audioOnlyParameters = /* @__PURE__ */ new Set(["numberOfChannels", "sampleRate"]);
380
- const invalidParameters = [];
381
- for (const parameter of audioOnlyParameters) {
382
- if (query[parameter] !== void 0) {
383
- invalidParameters.push(parameter);
384
- }
385
- }
386
- if (invalidParameters.length > 0) {
387
- const sortedInvalidParameters = [...invalidParameters].toSorted();
388
- throw new ValidationError(
389
- `Invalid query parameters for video transformation: ${sortedInvalidParameters.join(", ")}. Videos support: ${[...allowedParameters].toSorted().join(", ")}. Audio-only parameters (${sortedInvalidParameters.join(", ")}) are not supported for videos.`,
390
- "INVALID_PARAMS_FOR_VIDEO",
391
- "video",
392
- sortedInvalidParameters,
393
- [...allowedParameters].toSorted()
394
- );
395
- }
396
- if (query.fit && !["contain", "cover", "fill", "inside", "outside"].includes(query.fit)) {
397
- throw new ValidationError(
398
- `Invalid fit value: "${query.fit}". Supported values: "cover", "contain", "fill", "inside", "outside"`,
399
- "INVALID_FIT_VALUE",
400
- "video",
401
- ["fit"],
402
- ["cover", "contain", "fill", "inside", "outside"]
403
- );
404
- }
405
- if (query.codec && !["av1", "avc", "hevc", "vp8", "vp9"].includes(query.codec)) {
406
- throw new ValidationError(
407
- `Invalid codec for video: "${query.codec}". Supported codecs: avc, hevc, vp8, vp9, av1`,
408
- "INVALID_VIDEO_CODEC",
409
- "video",
410
- ["codec"],
411
- ["avc", "hevc", "vp8", "vp9", "av1"]
412
- );
413
- }
414
- if (query.format && !["mkv", "mp4", "ogg", "webm"].includes(query.format)) {
415
- throw new ValidationError(
416
- `Invalid format for video: "${query.format}". Supported formats: mp4, webm, mkv, ogg`,
417
- "INVALID_VIDEO_FORMAT",
418
- "video",
419
- ["format"],
420
- ["mp4", "webm", "mkv", "ogg"]
421
- );
422
- }
423
- const cropParameters = ["left", "top", "cropWidth", "cropHeight"];
424
- const providedCropParameters = cropParameters.filter((parameter) => query[parameter] !== void 0);
425
- if (providedCropParameters.length > 0 && providedCropParameters.length !== cropParameters.length) {
426
- throw new ValidationError(
427
- `Incomplete crop parameters: ${providedCropParameters.join(", ")}. All crop parameters must be provided: left, top, cropWidth, cropHeight`,
428
- "INCOMPLETE_CROP_PARAMS",
429
- "video",
430
- providedCropParameters,
431
- cropParameters
432
- );
433
- }
434
- if (query.width !== void 0 && (typeof query.width !== "number" || query.width <= 0)) {
435
- throw new ValidationError(`Invalid width: ${query.width}. Must be a positive number.`, "INVALID_WIDTH", "video", ["width"], []);
436
- }
437
- if (query.height !== void 0 && (typeof query.height !== "number" || query.height <= 0)) {
438
- throw new ValidationError(`Invalid height: ${query.height}. Must be a positive number.`, "INVALID_HEIGHT", "video", ["height"], []);
439
- }
440
- if (query.bitrate !== void 0 && (typeof query.bitrate !== "number" || query.bitrate <= 0)) {
441
- throw new ValidationError(`Invalid bitrate: ${query.bitrate}. Must be a positive number.`, "INVALID_BITRATE", "video", ["bitrate"], []);
442
- }
443
- if (query.frameRate !== void 0 && (typeof query.frameRate !== "number" || query.frameRate <= 0)) {
444
- throw new ValidationError(`Invalid frameRate: ${query.frameRate}. Must be a positive number.`, "INVALID_FRAME_RATE", "video", ["frameRate"], []);
445
- }
446
- if (query.keyFrameInterval !== void 0 && (typeof query.keyFrameInterval !== "number" || query.keyFrameInterval <= 0)) {
447
- throw new ValidationError(
448
- `Invalid keyFrameInterval: ${query.keyFrameInterval}. Must be a positive number.`,
449
- "INVALID_KEY_FRAME_INTERVAL",
450
- "video",
451
- ["keyFrameInterval"],
452
- []
453
- );
454
- }
455
- }
456
- /**
457
- * Generates a unique ID for transformed files based on original file and transformations.
458
- * @param originalFileId The original file identifier.
459
- * @param query The transformation query parameters.
460
- * @param mediaType The media type (image, video, audio).
461
- * @returns Unique deterministic identifier for the transformed file.
462
- * @private
463
- */
464
- // eslint-disable-next-line class-methods-use-this
465
- generateTransformedFileId(originalFileId, query, mediaType) {
466
- const transformParameters = Object.keys(query).filter((key) => query[key] !== void 0).toSorted().map((key) => `${key}:${query[key]}`).join("|");
467
- const hashInput = `${originalFileId}|${mediaType}|${transformParameters}`;
468
- const hash = createHash("sha256").update(hashInput).digest("hex").slice(0, 16);
469
- return `${originalFileId}_transformed_${hash}`;
470
- }
471
- /**
472
- * Checks if the query contains any transformations.
473
- * @param query The transformation query parameters.
474
- * @returns True if any transformations are requested.
475
- * @private
476
- */
477
- hasTransformations(query) {
478
- return this.hasImageTransformations(query) || this.hasVideoTransformations(query) || this.hasAudioTransformations(query);
479
- }
480
- /**
481
- * Creates a MediaTransformResult from a stored transformed file.
482
- * @param storedFile The stored transformed file.
483
- * @param mediaType The media type (image, video, audio).
484
- * @param originalFile The original file information.
485
- * @returns Media transformation result with metadata.
486
- * @private
487
- */
488
- createMediaTransformResult(storedFile, mediaType, originalFile) {
489
- const baseResult = {
490
- buffer: storedFile.content,
491
- format: this.getFormatFromContentType(storedFile.contentType || ""),
492
- mediaType,
493
- originalFile,
494
- size: storedFile.content.length
495
- };
496
- switch (mediaType) {
497
- case "audio": {
498
- return {
499
- ...baseResult,
500
- bitrate: storedFile.bitrate,
501
- duration: storedFile.duration,
502
- mediaType: "audio",
503
- numberOfChannels: storedFile.numberOfChannels,
504
- sampleRate: storedFile.sampleRate
505
- };
506
- }
507
- case "image": {
508
- return {
509
- ...baseResult,
510
- height: storedFile.height,
511
- mediaType: "image",
512
- width: storedFile.width
513
- };
514
- }
515
- case "video": {
516
- return {
517
- ...baseResult,
518
- bitrate: storedFile.bitrate,
519
- duration: storedFile.duration,
520
- height: storedFile.height,
521
- mediaType: "video",
522
- width: storedFile.width
523
- };
524
- }
525
- default: {
526
- return baseResult;
527
- }
528
- }
529
- }
530
- /**
531
- * Extracts format from content type.
532
- * @param contentType MIME content type string.
533
- * @returns Format string extracted from content type.
534
- * @private
535
- */
536
- // eslint-disable-next-line class-methods-use-this
537
- getFormatFromContentType(contentType) {
538
- if (!contentType) {
539
- return "";
540
- }
541
- const extension = mime.getExtension(contentType);
542
- return extension || "application/octet-stream";
543
- }
544
- /**
545
- * Saves transformed file to storage.
546
- * @param result The transformation result to save.
547
- * @param originalFileId The original file identifier.
548
- * @param query The transformation query parameters.
549
- * @param mediaType The media type (image, video, audio).
550
- * @returns Promise that resolves when file is saved.
551
- * @private
552
- */
553
- async saveTransformedFile(result, originalFileId, query, mediaType) {
554
- try {
555
- const transformedFileId = this.generateTransformedFileId(originalFileId, query, mediaType);
556
- const metadata = {
557
- format: result.format,
558
- mediaType,
559
- originalFileId,
560
- size: result.size,
561
- transformation: query,
562
- transformedAt: (/* @__PURE__ */ new Date()).toISOString()
563
- };
564
- if (mediaType === "image" && result.width && result.height) {
565
- metadata.width = result.width;
566
- metadata.height = result.height;
567
- } else if (mediaType === "video" && result.width && result.height) {
568
- metadata.width = result.width;
569
- metadata.height = result.height;
570
- metadata.duration = result.duration;
571
- metadata.bitrate = result.bitrate;
572
- } else if (mediaType === "audio") {
573
- metadata.duration = result.duration;
574
- metadata.numberOfChannels = result.numberOfChannels;
575
- metadata.sampleRate = result.sampleRate;
576
- metadata.bitrate = result.bitrate;
577
- }
578
- await this.storage.create({
579
- contentType: mime.getType(result.format) ?? void 0,
580
- metadata,
581
- originalName: `${transformedFileId}.${result.format}`,
582
- size: result.size
583
- });
584
- this.logger?.debug?.(`Saved transformed file: ${transformedFileId}`);
585
- } catch (error) {
586
- this.logger?.error?.(`Failed to save transformed file: ${error}`);
587
- }
588
- }
589
- /**
590
- * Validates query parameters for audio transformations. Checks for invalid video-only parameters, invalid codecs, invalid formats, and invalid numeric values.
591
- * @param query Query parameters to validate.
592
- * @throws {ValidationError} When validation fails.
593
- */
594
- // eslint-disable-next-line class-methods-use-this
595
- validateAudioQueryParameters(query) {
596
- const allowedParameters = /* @__PURE__ */ new Set(["bitrate", "codec", "format", "numberOfChannels", "quality", "sampleRate"]);
597
- const videoOnlyParameters = /* @__PURE__ */ new Set([
598
- "angle",
599
- "background",
600
- "cropHeight",
601
- "cropWidth",
602
- "fit",
603
- "frameRate",
604
- "height",
605
- "keyFrameInterval",
606
- "left",
607
- "position",
608
- "top",
609
- "width",
610
- "withoutEnlargement",
611
- "withoutReduction"
612
- ]);
613
- const invalidParameters = [];
614
- for (const parameter of videoOnlyParameters) {
615
- if (query[parameter] !== void 0) {
616
- invalidParameters.push(parameter);
617
- }
618
- }
619
- if (invalidParameters.length > 0) {
620
- const sortedInvalidParameters = [...invalidParameters].toSorted();
621
- throw new ValidationError(
622
- `Invalid query parameters for audio transformation: ${sortedInvalidParameters.join(", ")}. Audio supports: ${[...allowedParameters].toSorted().join(", ")}. Video-only parameters (${sortedInvalidParameters.join(", ")}) are not supported for audio.`,
623
- "INVALID_PARAMS_FOR_AUDIO",
624
- "audio",
625
- sortedInvalidParameters,
626
- [...allowedParameters].toSorted()
627
- );
628
- }
629
- if (query.codec && !["aac", "flac", "mp3", "opus", "vorbis"].includes(query.codec)) {
630
- throw new ValidationError(
631
- `Invalid codec for audio: "${query.codec}". Supported codecs: aac, opus, mp3, vorbis, flac`,
632
- "INVALID_AUDIO_CODEC",
633
- "audio",
634
- ["codec"],
635
- ["aac", "opus", "mp3", "vorbis", "flac"]
636
- );
637
- }
638
- if (query.format && !["aac", "flac", "mp3", "ogg", "wav"].includes(query.format)) {
639
- throw new ValidationError(
640
- `Invalid format for audio: "${query.format}". Supported formats: mp3, wav, ogg, aac, flac`,
641
- "INVALID_AUDIO_FORMAT",
642
- "audio",
643
- ["format"],
644
- ["mp3", "wav", "ogg", "aac", "flac"]
645
- );
646
- }
647
- if (query.bitrate !== void 0 && (typeof query.bitrate !== "number" || query.bitrate <= 0)) {
648
- throw new ValidationError(`Invalid bitrate: ${query.bitrate}. Must be a positive number.`, "INVALID_BITRATE", "audio", ["bitrate"], []);
649
- }
650
- if (query.numberOfChannels !== void 0 && (typeof query.numberOfChannels !== "number" || query.numberOfChannels <= 0 || query.numberOfChannels > 8)) {
651
- throw new ValidationError(
652
- `Invalid numberOfChannels: ${query.numberOfChannels}. Must be a number between 1 and 8.`,
653
- "INVALID_CHANNEL_COUNT",
654
- "audio",
655
- ["numberOfChannels"],
656
- ["1", "2", "3", "4", "5", "6", "7", "8"]
657
- );
658
- }
659
- if (query.sampleRate !== void 0) {
660
- const validSampleRates = [8e3, 11025, 16e3, 22050, 32e3, 44100, 48e3, 88200, 96e3, 192e3];
661
- if (typeof query.sampleRate !== "number" || !validSampleRates.includes(query.sampleRate)) {
662
- throw new ValidationError(
663
- `Invalid sampleRate: ${query.sampleRate}. Supported sample rates: ${validSampleRates.join(", ")}`,
664
- "INVALID_SAMPLE_RATE",
665
- "audio",
666
- ["sampleRate"],
667
- validSampleRates.map(String)
668
- );
669
- }
670
- }
671
- }
672
- /**
673
- * Handles image transformation.
674
- * @param fileId The file identifier.
675
- * @param query The transformation query parameters.
676
- * @returns Promise resolving to media transformation result.
677
- * @private
678
- */
679
- async handleImageTransformation(fileId, query) {
680
- const steps = [];
681
- if (this.hasImageTransformations(query)) {
682
- if (query.width || query.height || query.fit) {
683
- steps.push({
684
- options: {
685
- fit: query.fit,
686
- height: query.height,
687
- position: query.position,
688
- width: query.width,
689
- withoutEnlargement: query.withoutEnlargement,
690
- withoutReduction: query.withoutReduction
691
- },
692
- type: "resize"
693
- });
694
- }
695
- if (query.left !== void 0 && query.top !== void 0 && query.cropWidth && query.cropHeight) {
696
- steps.push({
697
- options: {
698
- height: query.cropHeight,
699
- left: query.left,
700
- top: query.top,
701
- width: query.cropWidth
702
- },
703
- type: "crop"
704
- });
705
- }
706
- if (query.angle) {
707
- steps.push({
708
- options: {
709
- angle: query.angle,
710
- background: query.background
711
- },
712
- type: "rotate"
713
- });
714
- }
715
- if (query.format) {
716
- steps.push({
717
- options: {
718
- format: query.format,
719
- quality: query.quality
720
- },
721
- type: "format"
722
- });
723
- } else if (query.quality) {
724
- steps.push({
725
- options: {
726
- quality: query.quality
727
- },
728
- type: "quality"
729
- });
730
- }
731
- }
732
- const result = steps.length > 0 ? await this.imageTransformer.transform(fileId, steps) : await this.imageTransformer.transform(fileId, []);
733
- return this.convertImageResult(result);
734
- }
735
- /**
736
- * Handles video transformation.
737
- * @param fileId The file identifier.
738
- * @param query The transformation query parameters.
739
- * @returns Promise resolving to media transformation result.
740
- * @private
741
- */
742
- async handleVideoTransformation(fileId, query) {
743
- const steps = [];
744
- if (this.hasVideoTransformations(query)) {
745
- if (query.width || query.height || query.fit) {
746
- steps.push({
747
- options: {
748
- fit: query.fit,
749
- height: query.height,
750
- position: query.position,
751
- width: query.width,
752
- withoutEnlargement: query.withoutEnlargement,
753
- withoutReduction: query.withoutReduction
754
- },
755
- type: "resize"
756
- });
757
- }
758
- if (query.left !== void 0 && query.top !== void 0 && query.cropWidth && query.cropHeight) {
759
- steps.push({
760
- options: {
761
- height: Number(query.cropHeight),
762
- left: query.left,
763
- top: query.top,
764
- width: query.cropWidth
765
- },
766
- type: "crop"
767
- });
768
- }
769
- if (query.angle) {
770
- steps.push({
771
- options: {
772
- angle: query.angle,
773
- background: query.background
774
- },
775
- type: "rotate"
776
- });
777
- }
778
- if (query.codec || query.bitrate) {
779
- steps.push({
780
- options: {
781
- bitrate: query.bitrate || query.quality,
782
- codec: query.codec,
783
- frameRate: query.frameRate,
784
- keyFrameInterval: query.keyFrameInterval
785
- },
786
- type: "codec"
787
- });
788
- }
789
- if (query.format) {
790
- steps.push({
791
- options: {
792
- format: query.format
793
- },
794
- type: "format"
795
- });
796
- }
797
- }
798
- const result = steps.length > 0 ? await this.videoTransformer.transform(fileId, steps) : await this.videoTransformer.transform(fileId, []);
799
- return this.convertVideoResult(result);
800
- }
801
- /**
802
- * Handles audio transformation.
803
- * @param fileId The file identifier.
804
- * @param query The transformation query parameters.
805
- * @returns Promise resolving to media transformation result.
806
- * @private
807
- */
808
- async handleAudioTransformation(fileId, query) {
809
- const steps = [];
810
- if (this.hasAudioTransformations(query)) {
811
- if (query.sampleRate) {
812
- steps.push({
813
- options: {
814
- sampleRate: query.sampleRate
815
- },
816
- type: "resample"
817
- });
818
- }
819
- if (query.numberOfChannels) {
820
- steps.push({
821
- options: {
822
- numberOfChannels: query.numberOfChannels
823
- },
824
- type: "channels"
825
- });
826
- }
827
- if (query.codec || query.bitrate) {
828
- steps.push({
829
- options: {
830
- bitrate: query.bitrate || query.quality,
831
- codec: query.codec
832
- },
833
- type: "codec"
834
- });
835
- }
836
- if (query.format) {
837
- steps.push({
838
- options: {
839
- format: query.format
840
- },
841
- type: "format"
842
- });
843
- }
844
- }
845
- const result = steps.length > 0 ? await this.audioTransformer.transform(fileId, steps) : await this.audioTransformer.transform(fileId, []);
846
- return this.convertAudioResult(result);
847
- }
848
- /**
849
- * Parses query parameters from various input formats.
850
- * @param query Query parameters in various formats.
851
- * @returns Normalized MediaTransformQuery object.
852
- * @private
853
- */
854
- parseQuery(query) {
855
- if (typeof query === "string") {
856
- return this.parseURLSearchParams(new URLSearchParams(query));
857
- }
858
- if (query instanceof URLSearchParams) {
859
- return this.parseURLSearchParams(query);
860
- }
861
- const transformQuery = query;
862
- if (query.left) {
863
- transformQuery.left = Number.parseInt(query.left, 10);
864
- }
865
- if (query.top) {
866
- transformQuery.top = Number.parseInt(query.top, 10);
867
- }
868
- if (query.cropWidth) {
869
- transformQuery.cropWidth = Number.parseInt(query.cropWidth, 10);
870
- }
871
- if (query.cropHeight) {
872
- transformQuery.cropHeight = Number.parseInt(query.cropHeight, 10);
873
- }
874
- if (query.angle) {
875
- transformQuery.angle = Number.parseInt(query.angle, 10);
876
- }
877
- if (query.quality) {
878
- transformQuery.quality = Number.parseInt(query.quality, 10);
879
- }
880
- if (query.width) {
881
- transformQuery.width = Number.parseInt(query.width, 10);
882
- }
883
- if (query.height) {
884
- transformQuery.height = Number.parseInt(query.height, 10);
885
- }
886
- if (query.bitrate) {
887
- transformQuery.bitrate = Number.parseInt(query.bitrate, 10);
888
- }
889
- if (query.frameRate) {
890
- transformQuery.frameRate = Number.parseInt(query.frameRate, 10);
891
- }
892
- if (query.keyFrameInterval) {
893
- transformQuery.keyFrameInterval = Number.parseInt(query.keyFrameInterval, 10);
894
- }
895
- if (query.numberOfChannels) {
896
- transformQuery.numberOfChannels = Number.parseInt(query.numberOfChannels, 10);
897
- }
898
- if (query.sampleRate) {
899
- transformQuery.sampleRate = Number.parseInt(query.sampleRate, 10);
900
- }
901
- return transformQuery;
902
- }
903
- /**
904
- * Parses boolean parameter from string.
905
- * @param value String value to parse.
906
- * @returns Boolean value or undefined.
907
- * @private
908
- */
909
- // eslint-disable-next-line class-methods-use-this
910
- parseBooleanParameter(value) {
911
- if (value === null)
912
- return void 0;
913
- return value === "true" || value === "1";
914
- }
915
- /**
916
- * Parses URLSearchParams into MediaTransformQuery.
917
- * @param parameters URL search parameters object.
918
- * @returns MediaTransformQuery object with parsed parameters.
919
- * @private
920
- */
921
- parseURLSearchParams(parameters) {
922
- const query = {};
923
- if (parameters.has("format")) {
924
- query.format = parameters.get("format") ?? void 0;
925
- }
926
- if (parameters.has("quality")) {
927
- query.quality = parameters.get("quality") ? Number.parseInt(parameters.get("quality"), 10) : void 0;
928
- }
929
- if (parameters.has("width")) {
930
- query.width = parameters.get("width") ? Number.parseInt(parameters.get("width"), 10) : void 0;
931
- }
932
- if (parameters.has("height")) {
933
- query.height = parameters.get("height") ? Number.parseInt(parameters.get("height"), 10) : void 0;
934
- }
935
- if (parameters.has("fit")) {
936
- const fitValue = parameters.get("fit");
937
- if (fitValue && ["contain", "cover", "fill", "inside", "outside"].includes(fitValue)) {
938
- query.fit = fitValue;
939
- }
940
- }
941
- if (parameters.has("position")) {
942
- query.position = parameters.get("position") ?? void 0;
943
- }
944
- if (parameters.has("withoutEnlargement")) {
945
- const value = parameters.get("withoutEnlargement");
946
- query.withoutEnlargement = value === "true" ? true : void 0;
947
- }
948
- if (parameters.has("withoutReduction")) {
949
- const value = parameters.get("withoutReduction");
950
- query.withoutReduction = value === "true" ? true : void 0;
951
- }
952
- if (parameters.has("left")) {
953
- query.left = parameters.get("left") ? Number.parseInt(parameters.get("left"), 10) : void 0;
954
- }
955
- if (parameters.has("top")) {
956
- query.top = parameters.get("top") ? Number.parseInt(parameters.get("top"), 10) : void 0;
957
- }
958
- if (parameters.has("cropWidth")) {
959
- query.cropWidth = parameters.get("cropWidth") ? Number.parseInt(parameters.get("cropWidth"), 10) : void 0;
960
- }
961
- if (parameters.has("cropHeight")) {
962
- query.cropHeight = parameters.get("cropHeight") ? Number.parseInt(parameters.get("cropHeight"), 10) : void 0;
963
- }
964
- if (parameters.has("angle")) {
965
- const angleValue = parameters.get("angle") ? Number.parseInt(parameters.get("angle"), 10) : void 0;
966
- if (angleValue !== void 0) {
967
- query.angle = angleValue;
968
- }
969
- }
970
- if (parameters.has("background")) {
971
- query.background = parameters.get("background") ?? void 0;
972
- }
973
- if (parameters.has("blur")) {
974
- query.blur = this.parseBooleanParameter(parameters.get("blur"));
975
- }
976
- if (parameters.has("sharpen")) {
977
- query.sharpen = this.parseBooleanParameter(parameters.get("sharpen"));
978
- }
979
- if (parameters.has("median")) {
980
- query.median = parameters.get("median") ? Number.parseInt(parameters.get("median"), 10) : void 0;
981
- }
982
- if (parameters.has("clahe")) {
983
- query.clahe = this.parseBooleanParameter(parameters.get("clahe"));
984
- }
985
- if (parameters.has("threshold")) {
986
- query.threshold = parameters.get("threshold") ? Number.parseInt(parameters.get("threshold"), 10) : void 0;
987
- }
988
- if (parameters.has("gamma")) {
989
- query.gamma = this.parseBooleanParameter(parameters.get("gamma"));
990
- }
991
- if (parameters.has("negate")) {
992
- query.negate = this.parseBooleanParameter(parameters.get("negate"));
993
- }
994
- if (parameters.has("normalise") || parameters.has("normalize")) {
995
- query.normalise = this.parseBooleanParameter(parameters.get("normalise")) || this.parseBooleanParameter(parameters.get("normalize"));
996
- }
997
- if (parameters.has("flatten")) {
998
- query.flatten = this.parseBooleanParameter(parameters.get("flatten"));
999
- }
1000
- if (parameters.has("unflatten")) {
1001
- query.unflatten = this.parseBooleanParameter(parameters.get("unflatten"));
1002
- }
1003
- if (parameters.has("flip")) {
1004
- query.flip = this.parseBooleanParameter(parameters.get("flip"));
1005
- }
1006
- if (parameters.has("flop")) {
1007
- query.flop = this.parseBooleanParameter(parameters.get("flop"));
1008
- }
1009
- if (parameters.has("affine")) {
1010
- query.affine = this.parseBooleanParameter(parameters.get("affine"));
1011
- }
1012
- if (parameters.has("dilate")) {
1013
- query.dilate = this.parseBooleanParameter(parameters.get("dilate"));
1014
- }
1015
- if (parameters.has("erode")) {
1016
- query.erode = this.parseBooleanParameter(parameters.get("erode"));
1017
- }
1018
- if (parameters.has("pipelineColourspace")) {
1019
- query.pipelineColourspace = this.parseBooleanParameter(parameters.get("pipelineColourspace"));
1020
- }
1021
- if (parameters.has("toColourspace")) {
1022
- query.toColourspace = this.parseBooleanParameter(parameters.get("toColourspace"));
1023
- }
1024
- if (parameters.has("removeAlpha")) {
1025
- query.removeAlpha = this.parseBooleanParameter(parameters.get("removeAlpha"));
1026
- }
1027
- if (parameters.has("ensureAlpha")) {
1028
- query.ensureAlpha = this.parseBooleanParameter(parameters.get("ensureAlpha"));
1029
- }
1030
- if (parameters.has("greyscale") || parameters.has("grayscale")) {
1031
- query.greyscale = this.parseBooleanParameter(parameters.get("greyscale")) || this.parseBooleanParameter(parameters.get("grayscale"));
1032
- }
1033
- if (parameters.has("modulate")) {
1034
- query.modulate = this.parseBooleanParameter(parameters.get("modulate"));
1035
- }
1036
- if (parameters.has("tint")) {
1037
- query.tint = this.parseBooleanParameter(parameters.get("tint"));
1038
- }
1039
- if (parameters.has("brightness")) {
1040
- query.brightness = parameters.get("brightness") ? Number.parseFloat(parameters.get("brightness")) : void 0;
1041
- }
1042
- if (parameters.has("saturation")) {
1043
- query.saturation = parameters.get("saturation") ? Number.parseFloat(parameters.get("saturation")) : void 0;
1044
- }
1045
- if (parameters.has("hue")) {
1046
- query.hue = parameters.get("hue") ? Number.parseInt(parameters.get("hue"), 10) : void 0;
1047
- }
1048
- if (parameters.has("lightness")) {
1049
- query.lightness = parameters.get("lightness") ? Number.parseInt(parameters.get("lightness"), 10) : void 0;
1050
- }
1051
- if (parameters.has("kernel")) {
1052
- query.kernel = parameters.get("kernel") ?? void 0;
1053
- }
1054
- if (parameters.has("fastShrinkOnLoad")) {
1055
- query.fastShrinkOnLoad = parameters.get("fastShrinkOnLoad") === "true";
1056
- }
1057
- if (parameters.has("codec")) {
1058
- const codecValue = parameters.get("codec");
1059
- const validCodecs = ["avc", "hevc", "vp8", "vp9", "av1", "aac", "opus", "mp3", "vorbis", "flac"];
1060
- if (codecValue && validCodecs.includes(codecValue)) {
1061
- query.codec = codecValue;
1062
- }
1063
- }
1064
- if (parameters.has("bitrate")) {
1065
- query.bitrate = parameters.get("bitrate") ? Number.parseInt(parameters.get("bitrate"), 10) : void 0;
1066
- }
1067
- if (parameters.has("frameRate")) {
1068
- query.frameRate = parameters.get("frameRate") ? Number.parseInt(parameters.get("frameRate"), 10) : void 0;
1069
- }
1070
- if (parameters.has("keyFrameInterval")) {
1071
- query.keyFrameInterval = parameters.get("keyFrameInterval") ? Number.parseInt(parameters.get("keyFrameInterval"), 10) : void 0;
1072
- }
1073
- if (parameters.has("numberOfChannels")) {
1074
- query.numberOfChannels = parameters.get("numberOfChannels") ? Number.parseInt(parameters.get("numberOfChannels"), 10) : void 0;
1075
- }
1076
- if (parameters.has("sampleRate")) {
1077
- query.sampleRate = parameters.get("sampleRate") ? Number.parseInt(parameters.get("sampleRate"), 10) : void 0;
1078
- }
1079
- return query;
1080
- }
1081
- /**
1082
- * Detects media type from MIME type.
1083
- * @param contentType MIME content type string.
1084
- * @returns Detected media type.
1085
- * @throws Error if content type is missing or unsupported.
1086
- * @private
1087
- */
1088
- // eslint-disable-next-line class-methods-use-this
1089
- detectMediaType(contentType) {
1090
- if (!contentType) {
1091
- throw new Error("Cannot detect media type: no content type provided");
1092
- }
1093
- if (!isKnownContentType(contentType)) {
1094
- throw new Error(`Unknown or invalid content type: ${contentType}`);
1095
- }
1096
- if (contentType.startsWith("image/")) {
1097
- return "image";
1098
- }
1099
- if (contentType.startsWith("video/")) {
1100
- return "video";
1101
- }
1102
- if (contentType.startsWith("audio/")) {
1103
- return "audio";
1104
- }
1105
- throw new Error(`Unsupported media type for content type: ${contentType}`);
1106
- }
1107
- /**
1108
- * Checks if query has image transformations.
1109
- * @param query The transformation query parameters.
1110
- * @returns True if image transformations are requested.
1111
- * @private
1112
- */
1113
- // eslint-disable-next-line class-methods-use-this
1114
- hasImageTransformations(query) {
1115
- return !!(query.width || query.height || query.fit || query.position || query.withoutEnlargement || query.withoutReduction || query.left !== void 0 || query.top !== void 0 || query.cropWidth || query.cropHeight || query.angle !== void 0 || query.background || query.blur || query.sharpen || query.median || query.clahe || query.threshold !== void 0 || query.gamma || query.negate || query.normalise || query.flatten || query.unflatten || query.flip || query.flop || query.greyscale || query.modulate || query.tint || query.brightness !== void 0 || query.saturation !== void 0 || query.hue !== void 0 || query.lightness !== void 0 || query.kernel || query.fastShrinkOnLoad || query.affine || query.dilate || query.erode || query.pipelineColourspace || query.toColourspace || query.removeAlpha || query.ensureAlpha || query.format || query.quality);
1116
- }
1117
- /**
1118
- * Checks if query has video transformations.
1119
- * @param query The transformation query parameters.
1120
- * @returns True if video transformations are requested.
1121
- * @private
1122
- */
1123
- // eslint-disable-next-line class-methods-use-this
1124
- hasVideoTransformations(query) {
1125
- return !!(query.width || query.height || query.fit || query.position || query.withoutEnlargement || query.withoutReduction || query.left !== void 0 || query.top !== void 0 || query.cropWidth || query.cropHeight || query.angle || query.background || query.codec || query.bitrate || query.frameRate || query.keyFrameInterval || query.format || query.quality);
1126
- }
1127
- /**
1128
- * Checks if query has audio transformations.
1129
- * @param query The transformation query parameters.
1130
- * @returns True if audio transformations are requested.
1131
- * @private
1132
- */
1133
- // eslint-disable-next-line class-methods-use-this
1134
- hasAudioTransformations(query) {
1135
- return !!(query.sampleRate || query.numberOfChannels || query.codec || query.bitrate || query.format || query.quality);
1136
- }
1137
- /**
1138
- * Converts ImageTransformer result to unified format.
1139
- * @param result The image transformation result.
1140
- * @returns Unified media transformation result.
1141
- * @private
1142
- */
1143
- // eslint-disable-next-line class-methods-use-this
1144
- convertImageResult(result) {
1145
- return {
1146
- buffer: result.buffer,
1147
- format: result.format,
1148
- height: result.height,
1149
- mediaType: "image",
1150
- originalFile: result.originalFile,
1151
- size: result.size,
1152
- width: result.width
1153
- };
1154
- }
1155
- /**
1156
- * Converts VideoTransformer result to unified format.
1157
- * @param result The video transformation result.
1158
- * @returns Unified media transformation result.
1159
- * @private
1160
- */
1161
- // eslint-disable-next-line class-methods-use-this
1162
- convertVideoResult(result) {
1163
- return {
1164
- bitrate: result.bitrate,
1165
- buffer: result.buffer,
1166
- duration: result.duration,
1167
- format: result.format,
1168
- height: result.height,
1169
- mediaType: "video",
1170
- originalFile: result.originalFile,
1171
- size: result.size,
1172
- width: result.width
1173
- };
1174
- }
1175
- /**
1176
- * Converts AudioTransformer result to unified format.
1177
- * @param result The audio transformation result.
1178
- * @returns Unified media transformation result.
1179
- * @private
1180
- */
1181
- // eslint-disable-next-line class-methods-use-this
1182
- convertAudioResult(result) {
1183
- return {
1184
- bitrate: result.bitrate,
1185
- buffer: result.buffer,
1186
- duration: result.duration,
1187
- format: result.format,
1188
- mediaType: "audio",
1189
- numberOfChannels: result.numberOfChannels,
1190
- originalFile: result.originalFile,
1191
- sampleRate: result.sampleRate,
1192
- size: result.size
1193
- };
1194
- }
1195
- }
1196
-
1197
- export { MediaTransformer as default };