@wener/common 2.0.3 → 2.0.6

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 (312) hide show
  1. package/lib/ai/qwen3vl/index.js +1 -1
  2. package/lib/ai/qwen3vl/utils.js +15 -15
  3. package/lib/ai/qwen3vl/utils.js.map +1 -1
  4. package/lib/ai/vision/DocLayoutElementTypeSchema.js +22 -22
  5. package/lib/ai/vision/ImageAnnotationSchema.js +63 -47
  6. package/lib/ai/vision/index.js +2 -2
  7. package/lib/ai/vision/resolveImageAnnotation.js +81 -95
  8. package/lib/cn/ChineseResidentIdNo.js +55 -41
  9. package/lib/cn/ChineseResidentIdNo.js.map +1 -1
  10. package/lib/cn/ChineseResidentIdNo.mod.js +6 -1
  11. package/lib/cn/ChineseResidentIdNo.test.js +22 -21
  12. package/lib/cn/DivisionCode.js +220 -235
  13. package/lib/cn/DivisionCode.mod.js +6 -1
  14. package/lib/cn/DivisionCode.test.js +92 -121
  15. package/lib/cn/Mod11.js +18 -37
  16. package/lib/cn/Mod11.js.map +1 -1
  17. package/lib/cn/Mod31.js +23 -41
  18. package/lib/cn/UnifiedSocialCreditCode.js +143 -137
  19. package/lib/cn/UnifiedSocialCreditCode.mod.js +6 -1
  20. package/lib/cn/UnifiedSocialCreditCode.test.js +21 -15
  21. package/lib/cn/formatChineseAmount.js +46 -71
  22. package/lib/cn/index.js +6 -6
  23. package/lib/cn/mod.js +5 -3
  24. package/lib/cn/parseChineseNumber.js +81 -85
  25. package/lib/cn/parseChineseNumber.test.js +183 -261
  26. package/lib/cn/pinyin/cartesianProduct.js +19 -19
  27. package/lib/cn/pinyin/cartesianProduct.test.js +78 -178
  28. package/lib/cn/pinyin/loader.js +13 -11
  29. package/lib/cn/pinyin/preload.js +2 -1
  30. package/lib/cn/pinyin/toPinyin.test.js +149 -161
  31. package/lib/cn/pinyin/toPinyinPure.js +28 -23
  32. package/lib/cn/pinyin/transform.js +11 -11
  33. package/lib/cn/types.d.js +2 -2
  34. package/lib/consola/createStandardConsolaReporter.js +14 -15
  35. package/lib/consola/formatLogObject.js +149 -133
  36. package/lib/consola/formatLogObject.js.map +1 -1
  37. package/lib/consola/formatLogObject.test.js +167 -178
  38. package/lib/consola/index.js +2 -2
  39. package/lib/data/formatSort.js +14 -12
  40. package/lib/data/formatSort.test.js +33 -33
  41. package/lib/data/index.js +3 -3
  42. package/lib/data/maybeNumber.js +23 -23
  43. package/lib/data/maybeNumber.js.map +1 -1
  44. package/lib/data/parseSort.js +75 -68
  45. package/lib/data/parseSort.test.js +196 -187
  46. package/lib/data/resolvePagination.js +38 -39
  47. package/lib/data/resolvePagination.test.js +228 -218
  48. package/lib/data/types.d.js +2 -2
  49. package/lib/data/types.d.js.map +1 -1
  50. package/lib/dayjs/dayjs.js +20 -20
  51. package/lib/dayjs/formatDuration.js +56 -56
  52. package/lib/dayjs/formatDuration.js.map +1 -1
  53. package/lib/dayjs/formatDuration.test.js +63 -77
  54. package/lib/dayjs/index.js +4 -4
  55. package/lib/dayjs/parseDuration.js +21 -26
  56. package/lib/dayjs/parseRelativeTime.js +65 -66
  57. package/lib/dayjs/parseRelativeTime.test.js +227 -243
  58. package/lib/dayjs/resolveRelativeTime.js +74 -144
  59. package/lib/dayjs/resolveRelativeTime.js.map +1 -1
  60. package/lib/dayjs/resolveRelativeTime.test.js +296 -307
  61. package/lib/decimal/index.js +1 -1
  62. package/lib/decimal/parseDecimal.js +12 -12
  63. package/lib/drain3/Drain.js +321 -0
  64. package/lib/drain3/Drain.js.map +1 -0
  65. package/lib/drain3/LogCluster.js +38 -0
  66. package/lib/drain3/LogCluster.js.map +1 -0
  67. package/lib/drain3/Node.js +39 -0
  68. package/lib/drain3/Node.js.map +1 -0
  69. package/lib/drain3/TemplateMiner.js +205 -0
  70. package/lib/drain3/TemplateMiner.js.map +1 -0
  71. package/lib/drain3/index.js +31 -0
  72. package/lib/drain3/index.js.map +1 -0
  73. package/lib/drain3/persistence/FilePersistence.js +24 -0
  74. package/lib/drain3/persistence/FilePersistence.js.map +1 -0
  75. package/lib/drain3/persistence/MemoryPersistence.js +18 -0
  76. package/lib/drain3/persistence/MemoryPersistence.js.map +1 -0
  77. package/lib/drain3/persistence/PersistenceHandler.js +5 -0
  78. package/lib/drain3/persistence/PersistenceHandler.js.map +1 -0
  79. package/lib/drain3/types.js +7 -0
  80. package/lib/drain3/types.js.map +1 -0
  81. package/lib/emittery/emitter.js +7 -7
  82. package/lib/emittery/index.js +1 -1
  83. package/lib/foundation/schema/SexType.js +15 -12
  84. package/lib/foundation/schema/index.js +1 -1
  85. package/lib/foundation/schema/parseSexType.js +15 -16
  86. package/lib/foundation/schema/types.js +8 -6
  87. package/lib/fs/FileSystemError.js +18 -18
  88. package/lib/fs/IFileSystem.d.js +2 -2
  89. package/lib/fs/IFileSystem.d.js.map +1 -1
  90. package/lib/fs/MemoryFileSystem.test.js +172 -181
  91. package/lib/fs/createBrowserFileSystem.js +222 -233
  92. package/lib/fs/createBrowserFileSystem.js.map +1 -1
  93. package/lib/fs/createMemoryFileSystem.js +473 -510
  94. package/lib/fs/createMemoryFileSystem.js.map +1 -1
  95. package/lib/fs/createSandboxFileSystem.js +102 -101
  96. package/lib/fs/createSandboxFileSystem.js.map +1 -1
  97. package/lib/fs/createWebDavFileSystem.js +162 -132
  98. package/lib/fs/createWebDavFileSystem.js.map +1 -1
  99. package/lib/fs/createWebFileSystem.js +202 -0
  100. package/lib/fs/createWebFileSystem.js.map +1 -0
  101. package/lib/fs/findMimeType.js +14 -14
  102. package/lib/fs/findMimeType.js.map +1 -1
  103. package/lib/fs/index.js +7 -7
  104. package/lib/fs/index.js.map +1 -1
  105. package/lib/fs/minio/createMinioFileSystem.js +977 -0
  106. package/lib/fs/minio/createMinioFileSystem.js.map +1 -0
  107. package/lib/fs/minio/index.js +2 -0
  108. package/lib/fs/minio/index.js.map +1 -0
  109. package/lib/fs/orpc/FileSystemContract.js +57 -57
  110. package/lib/fs/orpc/createContractClientFileSystem.js +88 -88
  111. package/lib/fs/orpc/createContractClientFileSystem.js.map +1 -1
  112. package/lib/fs/orpc/index.js +2 -2
  113. package/lib/fs/orpc/server/createFileSystemContractImpl.js +62 -60
  114. package/lib/fs/orpc/server/createFileSystemContractImpl.js.map +1 -1
  115. package/lib/fs/orpc/server/index.js +1 -1
  116. package/lib/fs/s3/createS3MiniFileSystem.js +756 -689
  117. package/lib/fs/s3/createS3MiniFileSystem.js.map +1 -1
  118. package/lib/fs/s3/index.js +1 -1
  119. package/lib/fs/s3/s3mini.test.js +524 -553
  120. package/lib/fs/scandir.js +56 -56
  121. package/lib/fs/server/createDatabaseFileSystem.js +834 -741
  122. package/lib/fs/server/createDatabaseFileSystem.js.map +1 -1
  123. package/lib/fs/server/createNodeFileSystem.js +407 -380
  124. package/lib/fs/server/createNodeFileSystem.js.map +1 -1
  125. package/lib/fs/server/dbfs.test.js +201 -214
  126. package/lib/fs/server/index.js +1 -1
  127. package/lib/fs/server/loadTestDatabase.js +40 -43
  128. package/lib/fs/tests/runFileSystemTest.js +352 -315
  129. package/lib/fs/tests/runFileSystemTest.js.map +1 -1
  130. package/lib/fs/types.js +17 -20
  131. package/lib/fs/utils/getFileUrl.js +24 -30
  132. package/lib/fs/utils.js +17 -17
  133. package/lib/fs/utils.js.map +1 -1
  134. package/lib/fs/webdav/index.js +2 -0
  135. package/lib/fs/webdav/index.js.map +1 -0
  136. package/lib/index.js +2 -2
  137. package/lib/jsonschema/JsonSchema.js +216 -155
  138. package/lib/jsonschema/JsonSchema.js.map +1 -1
  139. package/lib/jsonschema/JsonSchema.test.js +123 -124
  140. package/lib/jsonschema/forEachJsonSchema.js +41 -41
  141. package/lib/jsonschema/forEachJsonSchema.js.map +1 -1
  142. package/lib/jsonschema/index.js +2 -2
  143. package/lib/jsonschema/types.d.js +2 -2
  144. package/lib/jsonschema/types.d.js.map +1 -1
  145. package/lib/meta/defineFileType.js +32 -38
  146. package/lib/meta/defineInit.js +39 -35
  147. package/lib/meta/defineMetadata.js +37 -34
  148. package/lib/meta/defineMetadata.js.map +1 -1
  149. package/lib/meta/defineMetadata.test.js +13 -12
  150. package/lib/meta/index.js +3 -3
  151. package/lib/orpc/createOpenApiContractClient.js +26 -24
  152. package/lib/orpc/createOpenApiContractClient.js.map +1 -1
  153. package/lib/orpc/createRpcContractClient.js +37 -31
  154. package/lib/orpc/index.js +2 -2
  155. package/lib/orpc/resolveLinkPlugins.js +25 -25
  156. package/lib/password/PHC.js +187 -189
  157. package/lib/password/PHC.js.map +1 -1
  158. package/lib/password/PHC.test.js +517 -535
  159. package/lib/password/Password.js +85 -80
  160. package/lib/password/Password.test.js +330 -364
  161. package/lib/password/createArgon2PasswordAlgorithm.js +50 -51
  162. package/lib/password/createArgon2PasswordAlgorithm.js.map +1 -1
  163. package/lib/password/createBase64PasswordAlgorithm.js +11 -11
  164. package/lib/password/createBase64PasswordAlgorithm.js.map +1 -1
  165. package/lib/password/createBcryptPasswordAlgorithm.js +20 -18
  166. package/lib/password/createBcryptPasswordAlgorithm.js.map +1 -1
  167. package/lib/password/createPBKDF2PasswordAlgorithm.js +65 -52
  168. package/lib/password/createPBKDF2PasswordAlgorithm.js.map +1 -1
  169. package/lib/password/createScryptPasswordAlgorithm.js +74 -63
  170. package/lib/password/createScryptPasswordAlgorithm.js.map +1 -1
  171. package/lib/password/index.js +5 -5
  172. package/lib/password/server/index.js +1 -1
  173. package/lib/resource/Identifiable.js +2 -2
  174. package/lib/resource/ListQuery.js +42 -42
  175. package/lib/resource/ListQuery.js.map +1 -1
  176. package/lib/resource/getTitleOfResource.js +5 -5
  177. package/lib/resource/index.js +2 -2
  178. package/lib/resource/index.js.map +1 -1
  179. package/lib/resource/schema/AnyResourceSchema.js +91 -89
  180. package/lib/resource/schema/BaseResourceSchema.js +26 -26
  181. package/lib/resource/schema/ResourceActionType.js +117 -115
  182. package/lib/resource/schema/ResourceStatus.js +94 -92
  183. package/lib/resource/schema/ResourceType.js +25 -23
  184. package/lib/resource/schema/index.js +5 -5
  185. package/lib/resource/schema/types.js +86 -55
  186. package/lib/resource/schema/types.test.js +16 -13
  187. package/lib/s3/formatS3Url.js +60 -60
  188. package/lib/s3/formatS3Url.js.map +1 -1
  189. package/lib/s3/formatS3Url.test.js +238 -261
  190. package/lib/s3/index.js +2 -2
  191. package/lib/s3/parseS3Url.js +61 -60
  192. package/lib/s3/parseS3Url.js.map +1 -1
  193. package/lib/s3/parseS3Url.test.js +270 -269
  194. package/lib/schema/SchemaRegistry.js +41 -42
  195. package/lib/schema/SchemaRegistry.js.map +1 -1
  196. package/lib/schema/SchemaRegistry.mod.js +1 -1
  197. package/lib/schema/TypeSchema.d.js +2 -2
  198. package/lib/schema/TypeSchema.d.js.map +1 -1
  199. package/lib/schema/createSchemaData.js +113 -67
  200. package/lib/schema/createSchemaData.js.map +1 -1
  201. package/lib/schema/findJsonSchemaByPath.js +28 -23
  202. package/lib/schema/findJsonSchemaByPath.js.map +1 -1
  203. package/lib/schema/formatZodError.js +113 -134
  204. package/lib/schema/formatZodError.js.map +1 -1
  205. package/lib/schema/formatZodError.test.js +192 -195
  206. package/lib/schema/getSchemaCache.js +7 -7
  207. package/lib/schema/getSchemaOptions.js +17 -16
  208. package/lib/schema/index.js +6 -6
  209. package/lib/schema/toJsonSchema.js +196 -190
  210. package/lib/schema/toJsonSchema.js.map +1 -1
  211. package/lib/schema/toJsonSchema.test.js +34 -26
  212. package/lib/schema/validate.js +106 -97
  213. package/lib/schema/validate.js.map +1 -1
  214. package/lib/tools/generateSchema.js +40 -40
  215. package/lib/tools/renderJsonSchemaToMarkdownDoc.js +74 -74
  216. package/lib/utils/buildBaseUrl.js +8 -8
  217. package/lib/utils/buildRedactorFormSchema.js +55 -54
  218. package/lib/utils/buildRedactorFormSchema.js.map +1 -1
  219. package/lib/utils/getEstimateProcessTime.js +24 -19
  220. package/lib/utils/index.js +3 -3
  221. package/lib/utils/resolveFeatureOptions.js +9 -9
  222. package/package.json +37 -18
  223. package/src/ai/qwen3vl/utils.ts +1 -1
  224. package/src/ai/vision/index.ts +2 -2
  225. package/src/cn/ChineseResidentIdNo.ts +1 -1
  226. package/src/cn/Mod11.ts +1 -1
  227. package/src/cn/__snapshots__/ChineseResidentIdNo.test.ts.snap +1 -1
  228. package/src/cn/__snapshots__/UnifiedSocialCreditCode.test.ts.snap +0 -23
  229. package/src/cn/index.ts +1 -2
  230. package/src/cn/parseChineseNumber.test.ts +4 -4
  231. package/src/consola/formatLogObject.ts +6 -6
  232. package/src/consola/index.ts +1 -1
  233. package/src/data/index.ts +3 -4
  234. package/src/data/maybeNumber.ts +1 -1
  235. package/src/data/parseSort.test.ts +0 -1
  236. package/src/data/resolvePagination.ts +2 -2
  237. package/src/data/types.d.ts +2 -2
  238. package/src/dayjs/formatDuration.ts +10 -11
  239. package/src/dayjs/index.ts +1 -1
  240. package/src/dayjs/parseRelativeTime.ts +1 -1
  241. package/src/dayjs/resolveRelativeTime.ts +11 -14
  242. package/src/drain3/Drain.test.ts +378 -0
  243. package/src/drain3/Drain.ts +394 -0
  244. package/src/drain3/LogCluster.ts +46 -0
  245. package/src/drain3/Node.ts +53 -0
  246. package/src/drain3/TemplateMiner.ts +246 -0
  247. package/src/drain3/index.ts +34 -0
  248. package/src/drain3/persistence/FilePersistence.ts +24 -0
  249. package/src/drain3/persistence/MemoryPersistence.ts +23 -0
  250. package/src/drain3/persistence/PersistenceHandler.ts +19 -0
  251. package/src/drain3/types.ts +75 -0
  252. package/src/fs/IFileSystem.d.ts +1 -2
  253. package/src/fs/createBrowserFileSystem.ts +7 -5
  254. package/src/fs/createMemoryFileSystem.ts +9 -13
  255. package/src/fs/createSandboxFileSystem.ts +1 -1
  256. package/src/fs/createWebDavFileSystem.ts +30 -17
  257. package/src/fs/createWebFileSystem.ts +242 -0
  258. package/src/fs/findMimeType.ts +1 -4
  259. package/src/fs/index.ts +5 -5
  260. package/src/fs/minio/createMinioFileSystem.ts +1148 -0
  261. package/src/fs/minio/index.ts +1 -0
  262. package/src/fs/orpc/createContractClientFileSystem.ts +5 -5
  263. package/src/fs/orpc/server/createFileSystemContractImpl.ts +1 -1
  264. package/src/fs/s3/createS3MiniFileSystem.ts +120 -79
  265. package/src/fs/s3/s3fs.test.ts +441 -0
  266. package/src/fs/s3/s3mini.test.ts +2 -2
  267. package/src/fs/server/createDatabaseFileSystem.ts +78 -114
  268. package/src/fs/server/createNodeFileSystem.ts +32 -13
  269. package/src/fs/server/dbfs.test.ts +13 -8
  270. package/src/fs/server/index.ts +1 -0
  271. package/src/fs/server/loadTestDatabase.ts +8 -119
  272. package/src/fs/tests/runFileSystemTest.ts +29 -28
  273. package/src/fs/utils.ts +1 -1
  274. package/src/fs/webdav/index.ts +1 -0
  275. package/src/jsonschema/JsonSchema.ts +5 -5
  276. package/src/jsonschema/forEachJsonSchema.ts +1 -1
  277. package/src/jsonschema/index.ts +1 -1
  278. package/src/jsonschema/types.d.ts +1 -1
  279. package/src/meta/defineMetadata.ts +1 -1
  280. package/src/meta/index.ts +2 -3
  281. package/src/orm/createSqliteDialect.ts +17 -0
  282. package/src/orm/index.ts +1 -0
  283. package/src/orpc/createOpenApiContractClient.ts +3 -3
  284. package/src/orpc/index.ts +1 -1
  285. package/src/password/PHC.ts +3 -3
  286. package/src/password/createArgon2PasswordAlgorithm.ts +2 -2
  287. package/src/password/createBase64PasswordAlgorithm.ts +2 -2
  288. package/src/password/createBcryptPasswordAlgorithm.ts +4 -2
  289. package/src/password/createPBKDF2PasswordAlgorithm.ts +2 -2
  290. package/src/password/createScryptPasswordAlgorithm.ts +4 -4
  291. package/src/password/index.ts +2 -2
  292. package/src/resource/ListQuery.ts +4 -1
  293. package/src/resource/index.ts +3 -3
  294. package/src/resource/schema/index.ts +4 -4
  295. package/src/s3/formatS3Url.test.ts +1 -1
  296. package/src/s3/formatS3Url.ts +2 -2
  297. package/src/s3/index.ts +1 -1
  298. package/src/s3/parseS3Url.ts +1 -1
  299. package/src/schema/SchemaRegistry.ts +2 -2
  300. package/src/schema/TypeSchema.d.ts +6 -6
  301. package/src/schema/createSchemaData.ts +5 -5
  302. package/src/schema/findJsonSchemaByPath.ts +5 -5
  303. package/src/schema/formatZodError.test.ts +2 -1
  304. package/src/schema/formatZodError.ts +50 -62
  305. package/src/schema/index.ts +5 -5
  306. package/src/schema/toJsonSchema.ts +6 -6
  307. package/src/schema/validate.ts +2 -2
  308. package/src/utils/buildRedactorFormSchema.ts +4 -4
  309. package/src/utils/formatNumber.ts +18 -0
  310. package/src/utils/formatPercent.ts +17 -0
  311. package/src/utils/index.ts +3 -3
  312. package/src/utils/resolveFeatureOptions.ts +1 -1
@@ -1,262 +1,239 @@
1
- import { describe, expect, it } from "vitest";
2
- import { formatS3Url } from "./formatS3Url.js";
3
- describe("formatS3Url", function () {
4
- it("should format basic S3 URL with default endpoint", function () {
5
- var options = {
6
- endpoint: "s3.amazonaws.com"
7
- };
8
- var result = formatS3Url(options);
9
- expect(result).toBe("https://s3.amazonaws.com/");
10
- });
11
- it("should format S3 URL with custom endpoint", function () {
12
- var options = {
13
- endpoint: "custom-s3.com"
14
- };
15
- var result = formatS3Url(options);
16
- expect(result).toBe("https://custom-s3.com/");
17
- });
18
- it("should format S3 URL with HTTP protocol", function () {
19
- var options = {
20
- endpoint: "s3.amazonaws.com",
21
- useSsl: false
22
- };
23
- var result = formatS3Url(options);
24
- expect(result).toBe("http://s3.amazonaws.com/");
25
- });
26
- it("should format S3 URL with port", function () {
27
- var options = {
28
- endpoint: "s3.amazonaws.com",
29
- port: 9000
30
- };
31
- var result = formatS3Url(options);
32
- expect(result).toBe("https://s3.amazonaws.com:9000/");
33
- });
34
- it("should format S3 URL with bucket in path style", function () {
35
- var options = {
36
- endpoint: "s3.amazonaws.com",
37
- bucket: "my-bucket",
38
- pathStyle: true
39
- };
40
- var result = formatS3Url(options);
41
- expect(result).toBe("https://s3.amazonaws.com/my-bucket/");
42
- });
43
- it("should format S3 URL with bucket in virtual hosted style", function () {
44
- var options = {
45
- endpoint: "s3.amazonaws.com",
46
- bucket: "my-bucket",
47
- pathStyle: false
48
- };
49
- var result = formatS3Url(options);
50
- expect(result).toBe("https://my-bucket.s3.amazonaws.com/");
51
- });
52
- it("should format S3 URL with credentials", function () {
53
- var options = {
54
- endpoint: "s3.amazonaws.com",
55
- accessKeyId: "user",
56
- secretAccessKey: "pass"
57
- };
58
- var result = formatS3Url(options, {
59
- credentials: true
60
- });
61
- expect(result).toBe("https://user:pass@s3.amazonaws.com/");
62
- });
63
- it("should format S3 URL with credentials and special characters", function () {
64
- var options = {
65
- endpoint: "s3.amazonaws.com",
66
- accessKeyId: "user@example.com",
67
- secretAccessKey: "pass/word"
68
- };
69
- var result = formatS3Url(options, {
70
- credentials: true
71
- });
72
- expect(result).toBe("https://user%40example.com:pass%2Fword@s3.amazonaws.com/");
73
- });
74
- it("should format S3 URL with region in query parameters", function () {
75
- var options = {
76
- endpoint: "s3.amazonaws.com",
77
- region: "us-east-1"
78
- };
79
- var result = formatS3Url(options, {
80
- useParams: true
81
- });
82
- expect(result).toBe("https://s3.amazonaws.com/?region=us-east-1");
83
- });
84
- it("should format S3 URL with pathStyle in query parameters", function () {
85
- var options = {
86
- endpoint: "s3.amazonaws.com",
87
- pathStyle: true
88
- };
89
- var result = formatS3Url(options, {
90
- useParams: true
91
- });
92
- expect(result).toBe("https://s3.amazonaws.com/?pathStyle=true");
93
- });
94
- it("should format S3 URL with all parameters", function () {
95
- var options = {
96
- endpoint: "s3.amazonaws.com",
97
- accessKeyId: "user",
98
- secretAccessKey: "pass",
99
- region: "us-east-1",
100
- port: 9000,
101
- bucket: "my-bucket",
102
- pathStyle: true,
103
- useSsl: true
104
- };
105
- var result = formatS3Url(options, {
106
- credentials: true,
107
- useParams: true
108
- });
109
- expect(result).toBe("https://user:pass@s3.amazonaws.com:9000/my-bucket/?region=us-east-1&pathStyle=true");
110
- });
111
- it("should handle full URL as endpoint", function () {
112
- var options = {
113
- endpoint: "https://custom-s3.com:9000",
114
- bucket: "my-bucket",
115
- pathStyle: true
116
- };
117
- var result = formatS3Url(options);
118
- expect(result).toBe("https://custom-s3.com:9000/my-bucket/");
119
- });
120
- it("should handle complex virtual hosted style with existing bucket in hostname", function () {
121
- var options = {
122
- endpoint: "my-bucket.s3.amazonaws.com",
123
- bucket: "my-bucket",
124
- pathStyle: false
125
- };
126
- var result = formatS3Url(options);
127
- expect(result).toBe("https://my-bucket.s3.amazonaws.com/");
128
- });
129
- it("should throw error for missing endpoint", function () {
130
- var options = {};
131
- expect(function () {
132
- return formatS3Url(options);
133
- }).toThrow("Endpoint is required");
134
- });
135
- it("should handle endpoint without protocol by adding https://", function () {
136
- var options = {
137
- endpoint: "custom-s3.com"
138
- };
139
- var result = formatS3Url(options);
140
- expect(result).toBe("https://custom-s3.com/");
141
- });
142
- it("should throw error for missing credentials when credentials=true", function () {
143
- var options = {
144
- endpoint: "s3.amazonaws.com",
145
- accessKeyId: "user"
146
- };
147
- expect(function () {
148
- return formatS3Url(options, {
149
- credentials: true
150
- });
151
- }).toThrow("Access Key ID and Secret Access Key are required for credentials");
152
- });
153
- it("should throw error for invalid port", function () {
154
- var options = {
155
- endpoint: "s3.amazonaws.com",
156
- port: 99999
157
- };
158
- expect(function () {
159
- return formatS3Url(options);
160
- }).toThrow("Port must be a valid number between 1 and 65535");
161
- });
162
- it("should throw error for invalid bucket name", function () {
163
- var options = {
164
- endpoint: "s3.amazonaws.com",
165
- bucket: "Invalid Bucket Name"
166
- };
167
- expect(function () {
168
- return formatS3Url(options);
169
- }).toThrow("Invalid bucket name: Invalid Bucket Name");
170
- });
171
- it("should throw error for bucket name with consecutive dots", function () {
172
- var options = {
173
- endpoint: "s3.amazonaws.com",
174
- bucket: "my..bucket"
175
- };
176
- expect(function () {
177
- return formatS3Url(options);
178
- }).toThrow("Invalid bucket name: my..bucket");
179
- });
180
- it("should throw error for bucket name with hyphen at start", function () {
181
- var options = {
182
- endpoint: "s3.amazonaws.com",
183
- bucket: "-mybucket"
184
- };
185
- expect(function () {
186
- return formatS3Url(options);
187
- }).toThrow("Invalid bucket name: -mybucket");
188
- });
189
- it("should throw error for bucket name with hyphen at end", function () {
190
- var options = {
191
- endpoint: "s3.amazonaws.com",
192
- bucket: "mybucket-"
193
- };
194
- expect(function () {
195
- return formatS3Url(options);
196
- }).toThrow("Invalid bucket name: mybucket-");
197
- });
198
- it("should handle bucket name with dot-hyphen (currently allowed)", function () {
199
- var options = {
200
- endpoint: "s3.amazonaws.com",
201
- bucket: "my.bucket-name",
202
- pathStyle: true
203
- };
204
- var result = formatS3Url(options);
205
- expect(result).toBe("https://s3.amazonaws.com/my.bucket-name/");
206
- });
207
- it("should throw error for bucket name that is too short", function () {
208
- var options = {
209
- endpoint: "s3.amazonaws.com",
210
- bucket: "ab"
211
- };
212
- expect(function () {
213
- return formatS3Url(options);
214
- }).toThrow("Invalid bucket name: ab");
215
- });
216
- it("should throw error for bucket name that is too long", function () {
217
- var options = {
218
- endpoint: "s3.amazonaws.com",
219
- bucket: "a".repeat(64)
220
- };
221
- expect(function () {
222
- return formatS3Url(options);
223
- }).toThrow("Invalid bucket name: " + "a".repeat(64));
224
- });
225
- it("should handle valid bucket names with various formats", function () {
226
- var validBuckets = [
227
- "my-bucket",
228
- "my.bucket",
229
- "mybucket123",
230
- "123bucket",
231
- "test-bucket-123"
232
- ];
233
- validBuckets.forEach(function (bucket) {
234
- var options = {
235
- endpoint: "s3.amazonaws.com",
236
- bucket: bucket,
237
- pathStyle: true
238
- };
239
- expect(function () {
240
- return formatS3Url(options);
241
- }).not.toThrow();
242
- });
243
- });
244
- it("should handle pathname concatenation correctly in path style", function () {
245
- var options = {
246
- endpoint: "https://s3.amazonaws.com/path/to/something",
247
- bucket: "my-bucket",
248
- pathStyle: true
249
- };
250
- var result = formatS3Url(options);
251
- expect(result).toBe("https://s3.amazonaws.com/my-bucket/path/to/something");
252
- });
253
- it("should handle URL with existing pathname in virtual hosted style", function () {
254
- var options = {
255
- endpoint: "https://s3.amazonaws.com/path/to/something",
256
- bucket: "my-bucket",
257
- pathStyle: false
258
- };
259
- var result = formatS3Url(options);
260
- expect(result).toBe("https://my-bucket.s3.amazonaws.com/path/to/something");
261
- });
1
+ import { describe, expect, it } from 'vitest';
2
+ import { formatS3Url } from './formatS3Url.js';
3
+
4
+ describe('formatS3Url', () => {
5
+ it('should format basic S3 URL with default endpoint', () => {
6
+ var options = {
7
+ endpoint: 's3.amazonaws.com',
8
+ };
9
+ var result = formatS3Url(options);
10
+ expect(result).toBe('https://s3.amazonaws.com/');
11
+ });
12
+ it('should format S3 URL with custom endpoint', () => {
13
+ var options = {
14
+ endpoint: 'custom-s3.com',
15
+ };
16
+ var result = formatS3Url(options);
17
+ expect(result).toBe('https://custom-s3.com/');
18
+ });
19
+ it('should format S3 URL with HTTP protocol', () => {
20
+ var options = {
21
+ endpoint: 's3.amazonaws.com',
22
+ useSsl: false,
23
+ };
24
+ var result = formatS3Url(options);
25
+ expect(result).toBe('http://s3.amazonaws.com/');
26
+ });
27
+ it('should format S3 URL with port', () => {
28
+ var options = {
29
+ endpoint: 's3.amazonaws.com',
30
+ port: 9000,
31
+ };
32
+ var result = formatS3Url(options);
33
+ expect(result).toBe('https://s3.amazonaws.com:9000/');
34
+ });
35
+ it('should format S3 URL with bucket in path style', () => {
36
+ var options = {
37
+ endpoint: 's3.amazonaws.com',
38
+ bucket: 'my-bucket',
39
+ pathStyle: true,
40
+ };
41
+ var result = formatS3Url(options);
42
+ expect(result).toBe('https://s3.amazonaws.com/my-bucket/');
43
+ });
44
+ it('should format S3 URL with bucket in virtual hosted style', () => {
45
+ var options = {
46
+ endpoint: 's3.amazonaws.com',
47
+ bucket: 'my-bucket',
48
+ pathStyle: false,
49
+ };
50
+ var result = formatS3Url(options);
51
+ expect(result).toBe('https://my-bucket.s3.amazonaws.com/');
52
+ });
53
+ it('should format S3 URL with credentials', () => {
54
+ var options = {
55
+ endpoint: 's3.amazonaws.com',
56
+ accessKeyId: 'user',
57
+ secretAccessKey: 'pass',
58
+ };
59
+ var result = formatS3Url(options, {
60
+ credentials: true,
61
+ });
62
+ expect(result).toBe('https://user:pass@s3.amazonaws.com/');
63
+ });
64
+ it('should format S3 URL with credentials and special characters', () => {
65
+ var options = {
66
+ endpoint: 's3.amazonaws.com',
67
+ accessKeyId: 'user@example.com',
68
+ secretAccessKey: 'pass/word',
69
+ };
70
+ var result = formatS3Url(options, {
71
+ credentials: true,
72
+ });
73
+ expect(result).toBe('https://user%40example.com:pass%2Fword@s3.amazonaws.com/');
74
+ });
75
+ it('should format S3 URL with region in query parameters', () => {
76
+ var options = {
77
+ endpoint: 's3.amazonaws.com',
78
+ region: 'us-east-1',
79
+ };
80
+ var result = formatS3Url(options, {
81
+ useParams: true,
82
+ });
83
+ expect(result).toBe('https://s3.amazonaws.com/?region=us-east-1');
84
+ });
85
+ it('should format S3 URL with pathStyle in query parameters', () => {
86
+ var options = {
87
+ endpoint: 's3.amazonaws.com',
88
+ pathStyle: true,
89
+ };
90
+ var result = formatS3Url(options, {
91
+ useParams: true,
92
+ });
93
+ expect(result).toBe('https://s3.amazonaws.com/?pathStyle=true');
94
+ });
95
+ it('should format S3 URL with all parameters', () => {
96
+ var options = {
97
+ endpoint: 's3.amazonaws.com',
98
+ accessKeyId: 'user',
99
+ secretAccessKey: 'pass',
100
+ region: 'us-east-1',
101
+ port: 9000,
102
+ bucket: 'my-bucket',
103
+ pathStyle: true,
104
+ useSsl: true,
105
+ };
106
+ var result = formatS3Url(options, {
107
+ credentials: true,
108
+ useParams: true,
109
+ });
110
+ expect(result).toBe('https://user:pass@s3.amazonaws.com:9000/my-bucket/?region=us-east-1&pathStyle=true');
111
+ });
112
+ it('should handle full URL as endpoint', () => {
113
+ var options = {
114
+ endpoint: 'https://custom-s3.com:9000',
115
+ bucket: 'my-bucket',
116
+ pathStyle: true,
117
+ };
118
+ var result = formatS3Url(options);
119
+ expect(result).toBe('https://custom-s3.com:9000/my-bucket/');
120
+ });
121
+ it('should handle complex virtual hosted style with existing bucket in hostname', () => {
122
+ var options = {
123
+ endpoint: 'my-bucket.s3.amazonaws.com',
124
+ bucket: 'my-bucket',
125
+ pathStyle: false,
126
+ };
127
+ var result = formatS3Url(options);
128
+ expect(result).toBe('https://my-bucket.s3.amazonaws.com/');
129
+ });
130
+ it('should throw error for missing endpoint', () => {
131
+ var options = {};
132
+ expect(() => formatS3Url(options)).toThrow('Endpoint is required');
133
+ });
134
+ it('should handle endpoint without protocol by adding https://', () => {
135
+ var options = {
136
+ endpoint: 'custom-s3.com',
137
+ };
138
+ var result = formatS3Url(options);
139
+ expect(result).toBe('https://custom-s3.com/');
140
+ });
141
+ it('should throw error for missing credentials when credentials=true', () => {
142
+ var options = {
143
+ endpoint: 's3.amazonaws.com',
144
+ accessKeyId: 'user',
145
+ };
146
+ expect(() =>
147
+ formatS3Url(options, {
148
+ credentials: true,
149
+ }),
150
+ ).toThrow('Access Key ID and Secret Access Key are required for credentials');
151
+ });
152
+ it('should throw error for invalid port', () => {
153
+ var options = {
154
+ endpoint: 's3.amazonaws.com',
155
+ port: 99999,
156
+ };
157
+ expect(() => formatS3Url(options)).toThrow('Port must be a valid number between 1 and 65535');
158
+ });
159
+ it('should throw error for invalid bucket name', () => {
160
+ var options = {
161
+ endpoint: 's3.amazonaws.com',
162
+ bucket: 'Invalid Bucket Name',
163
+ };
164
+ expect(() => formatS3Url(options)).toThrow('Invalid bucket name: Invalid Bucket Name');
165
+ });
166
+ it('should throw error for bucket name with consecutive dots', () => {
167
+ var options = {
168
+ endpoint: 's3.amazonaws.com',
169
+ bucket: 'my..bucket',
170
+ };
171
+ expect(() => formatS3Url(options)).toThrow('Invalid bucket name: my..bucket');
172
+ });
173
+ it('should throw error for bucket name with hyphen at start', () => {
174
+ var options = {
175
+ endpoint: 's3.amazonaws.com',
176
+ bucket: '-mybucket',
177
+ };
178
+ expect(() => formatS3Url(options)).toThrow('Invalid bucket name: -mybucket');
179
+ });
180
+ it('should throw error for bucket name with hyphen at end', () => {
181
+ var options = {
182
+ endpoint: 's3.amazonaws.com',
183
+ bucket: 'mybucket-',
184
+ };
185
+ expect(() => formatS3Url(options)).toThrow('Invalid bucket name: mybucket-');
186
+ });
187
+ it('should handle bucket name with dot-hyphen (currently allowed)', () => {
188
+ var options = {
189
+ endpoint: 's3.amazonaws.com',
190
+ bucket: 'my.bucket-name',
191
+ pathStyle: true,
192
+ };
193
+ var result = formatS3Url(options);
194
+ expect(result).toBe('https://s3.amazonaws.com/my.bucket-name/');
195
+ });
196
+ it('should throw error for bucket name that is too short', () => {
197
+ var options = {
198
+ endpoint: 's3.amazonaws.com',
199
+ bucket: 'ab',
200
+ };
201
+ expect(() => formatS3Url(options)).toThrow('Invalid bucket name: ab');
202
+ });
203
+ it('should throw error for bucket name that is too long', () => {
204
+ var options = {
205
+ endpoint: 's3.amazonaws.com',
206
+ bucket: 'a'.repeat(64),
207
+ };
208
+ expect(() => formatS3Url(options)).toThrow('Invalid bucket name: ' + 'a'.repeat(64));
209
+ });
210
+ it('should handle valid bucket names with various formats', () => {
211
+ var validBuckets = ['my-bucket', 'my.bucket', 'mybucket123', '123bucket', 'test-bucket-123'];
212
+ validBuckets.forEach((bucket) => {
213
+ var options = {
214
+ endpoint: 's3.amazonaws.com',
215
+ bucket: bucket,
216
+ pathStyle: true,
217
+ };
218
+ expect(() => formatS3Url(options)).not.toThrow();
219
+ });
220
+ });
221
+ it('should handle pathname concatenation correctly in path style', () => {
222
+ var options = {
223
+ endpoint: 'https://s3.amazonaws.com/path/to/something',
224
+ bucket: 'my-bucket',
225
+ pathStyle: true,
226
+ };
227
+ var result = formatS3Url(options);
228
+ expect(result).toBe('https://s3.amazonaws.com/my-bucket/path/to/something');
229
+ });
230
+ it('should handle URL with existing pathname in virtual hosted style', () => {
231
+ var options = {
232
+ endpoint: 'https://s3.amazonaws.com/path/to/something',
233
+ bucket: 'my-bucket',
234
+ pathStyle: false,
235
+ };
236
+ var result = formatS3Url(options);
237
+ expect(result).toBe('https://my-bucket.s3.amazonaws.com/path/to/something');
238
+ });
262
239
  });
package/lib/s3/index.js CHANGED
@@ -1,3 +1,3 @@
1
- export { parseS3Url } from "./parseS3Url.js";
2
- export { formatS3Url } from "./formatS3Url.js";
1
+ export { formatS3Url } from './formatS3Url.js';
2
+ export { parseS3Url } from './parseS3Url.js';
3
3
  //# sourceMappingURL=index.js.map
@@ -1,65 +1,66 @@
1
- import { parseBoolean } from "@wener/utils";
1
+ import { parseBoolean } from '@wener/utils';
2
+
2
3
  function isValidIpAddress(hostname) {
3
- const ipv4Regex = /^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/;
4
- const ipv6Regex = /^\[([0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}]$/;
5
- return ipv4Regex.test(hostname) || ipv6Regex.test(hostname);
4
+ const ipv4Regex = /^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/;
5
+ const ipv6Regex = /^\[([0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}]$/;
6
+ return ipv4Regex.test(hostname) || ipv6Regex.test(hostname);
6
7
  }
7
8
  export function parseS3Url({ url = process.env.S3_URL, ...rest } = {}) {
8
- if (!url) return undefined;
9
- const normalizedUrl = url.startsWith('s3://') ? url.replace(/^s3:\/\//, 'https://') : url;
10
- let parsed;
11
- try {
12
- parsed = new URL(normalizedUrl);
13
- } catch (error) {
14
- throw new Error(`Invalid S3 URL: ${url}`);
15
- }
16
- const pathStyleParam = parsed.searchParams.get('pathStyle');
17
- let pathStyle = rest.pathStyle;
18
- pathStyle ??= parseBoolean(pathStyleParam, true);
19
- // Auto-detect path style for IP addresses
20
- if (pathStyle === undefined && isValidIpAddress(parsed.hostname)) {
21
- pathStyle = true;
22
- }
23
- const result = {
24
- accessKeyId: parsed.username || undefined,
25
- secretAccessKey: parsed.password || undefined,
26
- endpoint: parsed.hostname,
27
- port: parsed.port ? Number(parsed.port) : undefined,
28
- useSsl: parsed.protocol === 'https:',
29
- region: parsed.searchParams.get('region') || undefined,
30
- pathStyle
31
- };
32
- if (!result.port) {
33
- if (result.useSsl) {
34
- result.port = 443;
35
- } else {
36
- result.port = 80;
37
- }
38
- }
39
- const pathSegments = parsed.pathname.split('/').filter(Boolean);
40
- const awsVirtualHostMatch = parsed.hostname.match(/^(.*?)\.s3[.-]([a-z0-9-]+)?\.?amazonaws\.com$/);
41
- if (result.pathStyle) {
42
- result.bucket = pathSegments[0];
43
- } else if (awsVirtualHostMatch) {
44
- result.bucket = awsVirtualHostMatch[1];
45
- result.endpoint = parsed.hostname;
46
- if (!result.region && awsVirtualHostMatch[2]) {
47
- result.region = awsVirtualHostMatch[2];
48
- }
49
- result.pathStyle = false;
50
- } else {
51
- result.bucket = pathSegments[0];
52
- if (result.pathStyle === undefined) {
53
- result.pathStyle = true;
54
- }
55
- }
56
- // Type-safe property assignment
57
- for (const [key, value] of Object.entries(rest)){
58
- if (value !== undefined && value !== null && key in result) {
59
- result[key] = value;
60
- }
61
- }
62
- return result;
9
+ if (!url) return undefined;
10
+ const normalizedUrl = url.startsWith('s3://') ? url.replace(/^s3:\/\//, 'https://') : url;
11
+ let parsed;
12
+ try {
13
+ parsed = new URL(normalizedUrl);
14
+ } catch (_error) {
15
+ throw new Error(`Invalid S3 URL: ${url}`);
16
+ }
17
+ const pathStyleParam = parsed.searchParams.get('pathStyle');
18
+ let pathStyle = rest.pathStyle;
19
+ pathStyle ??= parseBoolean(pathStyleParam, true);
20
+ // Auto-detect path style for IP addresses
21
+ if (pathStyle === undefined && isValidIpAddress(parsed.hostname)) {
22
+ pathStyle = true;
23
+ }
24
+ const result = {
25
+ accessKeyId: parsed.username || undefined,
26
+ secretAccessKey: parsed.password || undefined,
27
+ endpoint: parsed.hostname,
28
+ port: parsed.port ? Number(parsed.port) : undefined,
29
+ useSsl: parsed.protocol === 'https:',
30
+ region: parsed.searchParams.get('region') || undefined,
31
+ pathStyle,
32
+ };
33
+ if (!result.port) {
34
+ if (result.useSsl) {
35
+ result.port = 443;
36
+ } else {
37
+ result.port = 80;
38
+ }
39
+ }
40
+ const pathSegments = parsed.pathname.split('/').filter(Boolean);
41
+ const awsVirtualHostMatch = parsed.hostname.match(/^(.*?)\.s3[.-]([a-z0-9-]+)?\.?amazonaws\.com$/);
42
+ if (result.pathStyle) {
43
+ result.bucket = pathSegments[0];
44
+ } else if (awsVirtualHostMatch) {
45
+ result.bucket = awsVirtualHostMatch[1];
46
+ result.endpoint = parsed.hostname;
47
+ if (!result.region && awsVirtualHostMatch[2]) {
48
+ result.region = awsVirtualHostMatch[2];
49
+ }
50
+ result.pathStyle = false;
51
+ } else {
52
+ result.bucket = pathSegments[0];
53
+ if (result.pathStyle === undefined) {
54
+ result.pathStyle = true;
55
+ }
56
+ }
57
+ // Type-safe property assignment
58
+ for (const [key, value] of Object.entries(rest)) {
59
+ if (value !== undefined && value !== null && key in result) {
60
+ result[key] = value;
61
+ }
62
+ }
63
+ return result;
63
64
  }
64
65
 
65
- //# sourceMappingURL=parseS3Url.js.map
66
+ //# sourceMappingURL=parseS3Url.js.map