@cj-tech-master/excelts 4.0.0 → 4.0.1-canary.20260104072032.0453bbe

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 (633) hide show
  1. package/README.md +2 -2
  2. package/README_zh.md +2 -2
  3. package/dist/browser/index.browser.d.ts +25 -0
  4. package/dist/browser/index.browser.js +40 -0
  5. package/dist/browser/index.d.ts +23 -0
  6. package/dist/browser/index.js +35 -0
  7. package/dist/browser/modules/archive/byte-queue.d.ts +18 -0
  8. package/dist/browser/modules/archive/byte-queue.js +125 -0
  9. package/dist/browser/modules/archive/compress.base.d.ts +98 -0
  10. package/dist/browser/modules/archive/compress.base.js +173 -0
  11. package/dist/browser/modules/archive/compress.browser.d.ts +57 -0
  12. package/dist/browser/modules/archive/compress.browser.js +93 -0
  13. package/dist/browser/modules/archive/compress.d.ts +44 -0
  14. package/dist/browser/modules/archive/compress.js +86 -0
  15. package/dist/browser/modules/archive/crc32.base.d.ts +25 -0
  16. package/dist/browser/modules/archive/crc32.base.js +51 -0
  17. package/dist/browser/modules/archive/crc32.browser.d.ts +30 -0
  18. package/dist/browser/modules/archive/crc32.browser.js +32 -0
  19. package/dist/browser/modules/archive/crc32.d.ts +59 -0
  20. package/dist/browser/modules/archive/crc32.js +97 -0
  21. package/dist/browser/modules/archive/defaults.d.ts +4 -0
  22. package/dist/browser/modules/archive/defaults.js +3 -0
  23. package/dist/browser/modules/archive/deflate-fallback.d.ts +39 -0
  24. package/dist/browser/modules/archive/deflate-fallback.js +564 -0
  25. package/dist/browser/modules/archive/extract.d.ts +94 -0
  26. package/dist/browser/modules/archive/extract.js +106 -0
  27. package/dist/browser/modules/archive/index.base.d.ts +11 -0
  28. package/dist/browser/modules/archive/index.base.js +13 -0
  29. package/dist/browser/modules/archive/index.browser.d.ts +11 -0
  30. package/dist/browser/modules/archive/index.browser.js +17 -0
  31. package/dist/browser/modules/archive/index.d.ts +11 -0
  32. package/dist/browser/modules/archive/index.js +15 -0
  33. package/dist/browser/modules/archive/parse.base.d.ts +198 -0
  34. package/dist/browser/modules/archive/parse.base.js +610 -0
  35. package/dist/browser/modules/archive/parse.browser.d.ts +22 -0
  36. package/dist/browser/modules/archive/parse.browser.js +564 -0
  37. package/dist/browser/modules/archive/parse.d.ts +16 -0
  38. package/dist/browser/modules/archive/parse.js +94 -0
  39. package/dist/browser/modules/archive/streaming-compress.base.d.ts +36 -0
  40. package/dist/browser/modules/archive/streaming-compress.base.js +9 -0
  41. package/dist/browser/modules/archive/streaming-compress.browser.d.ts +26 -0
  42. package/dist/browser/modules/archive/streaming-compress.browser.js +296 -0
  43. package/dist/browser/modules/archive/streaming-compress.d.ts +22 -0
  44. package/dist/browser/modules/archive/streaming-compress.js +68 -0
  45. package/dist/browser/modules/archive/streaming-zip.d.ts +120 -0
  46. package/dist/browser/modules/archive/streaming-zip.js +407 -0
  47. package/dist/browser/modules/archive/utils/binary.d.ts +24 -0
  48. package/dist/browser/modules/archive/utils/binary.js +69 -0
  49. package/dist/browser/modules/archive/utils/bytes.d.ts +7 -0
  50. package/dist/browser/modules/archive/utils/bytes.js +101 -0
  51. package/dist/browser/modules/archive/utils/parse-buffer.d.ts +18 -0
  52. package/dist/browser/modules/archive/utils/parse-buffer.js +55 -0
  53. package/dist/browser/modules/archive/utils/text.d.ts +20 -0
  54. package/dist/browser/modules/archive/utils/text.js +33 -0
  55. package/dist/browser/modules/archive/utils/timestamps.d.ts +28 -0
  56. package/dist/browser/modules/archive/utils/timestamps.js +48 -0
  57. package/dist/browser/modules/archive/utils/zip-extra-fields.d.ts +19 -0
  58. package/dist/browser/modules/archive/utils/zip-extra-fields.js +72 -0
  59. package/dist/browser/modules/archive/utils/zip-extra.d.ts +18 -0
  60. package/dist/browser/modules/archive/utils/zip-extra.js +68 -0
  61. package/dist/browser/modules/archive/zip-builder.d.ts +117 -0
  62. package/dist/browser/modules/archive/zip-builder.js +292 -0
  63. package/dist/browser/modules/archive/zip-constants.d.ts +18 -0
  64. package/dist/browser/modules/archive/zip-constants.js +23 -0
  65. package/dist/browser/modules/archive/zip-entry-info.d.ts +29 -0
  66. package/dist/browser/modules/archive/zip-entry-info.js +6 -0
  67. package/dist/browser/modules/archive/zip-entry-metadata.d.ts +23 -0
  68. package/dist/browser/modules/archive/zip-entry-metadata.js +24 -0
  69. package/dist/browser/modules/archive/zip-parser.d.ts +62 -0
  70. package/dist/browser/modules/archive/zip-parser.js +332 -0
  71. package/dist/browser/modules/archive/zip-records.d.ts +43 -0
  72. package/dist/browser/modules/archive/zip-records.js +84 -0
  73. package/dist/browser/modules/csv/csv-core.d.ts +215 -0
  74. package/dist/browser/modules/csv/csv-core.js +723 -0
  75. package/dist/browser/modules/csv/csv-number.d.ts +3 -0
  76. package/dist/browser/modules/csv/csv-number.js +20 -0
  77. package/dist/browser/modules/csv/csv-stream.d.ts +121 -0
  78. package/dist/browser/modules/csv/csv-stream.js +703 -0
  79. package/dist/browser/modules/csv/csv.browser.d.ts +60 -0
  80. package/dist/browser/modules/csv/csv.browser.js +265 -0
  81. package/dist/browser/modules/csv/csv.d.ts +14 -0
  82. package/dist/browser/modules/csv/csv.js +29 -0
  83. package/dist/browser/modules/excel/anchor.d.ts +33 -0
  84. package/dist/browser/modules/excel/anchor.js +97 -0
  85. package/dist/browser/modules/excel/cell.d.ts +138 -0
  86. package/dist/browser/modules/excel/cell.js +946 -0
  87. package/dist/browser/modules/excel/column.d.ts +122 -0
  88. package/dist/browser/modules/excel/column.js +358 -0
  89. package/dist/browser/modules/excel/data-validations.d.ts +11 -0
  90. package/dist/browser/modules/excel/data-validations.js +43 -0
  91. package/dist/browser/modules/excel/defined-names.d.ts +37 -0
  92. package/dist/browser/modules/excel/defined-names.js +214 -0
  93. package/dist/browser/modules/excel/enums.d.ts +62 -0
  94. package/dist/browser/modules/excel/enums.js +58 -0
  95. package/dist/browser/modules/excel/image.d.ts +64 -0
  96. package/dist/browser/modules/excel/image.js +60 -0
  97. package/dist/browser/modules/excel/note.d.ts +29 -0
  98. package/dist/browser/modules/excel/note.js +61 -0
  99. package/dist/browser/modules/excel/pivot-table.d.ts +152 -0
  100. package/dist/browser/modules/excel/pivot-table.js +237 -0
  101. package/dist/browser/modules/excel/range.d.ts +62 -0
  102. package/dist/browser/modules/excel/range.js +280 -0
  103. package/dist/browser/modules/excel/row.d.ts +127 -0
  104. package/dist/browser/modules/excel/row.js +441 -0
  105. package/dist/browser/modules/excel/stream/hyperlink-reader.d.ts +33 -0
  106. package/dist/browser/modules/excel/stream/hyperlink-reader.js +84 -0
  107. package/dist/browser/modules/excel/stream/sheet-comments-writer.d.ts +26 -0
  108. package/dist/browser/modules/excel/stream/sheet-comments-writer.js +101 -0
  109. package/dist/browser/modules/excel/stream/sheet-rels-writer.d.ts +45 -0
  110. package/dist/browser/modules/excel/stream/sheet-rels-writer.js +91 -0
  111. package/dist/browser/modules/excel/stream/workbook-reader.browser.d.ts +169 -0
  112. package/dist/browser/modules/excel/stream/workbook-reader.browser.js +443 -0
  113. package/dist/browser/modules/excel/stream/workbook-reader.d.ts +24 -0
  114. package/dist/browser/modules/excel/stream/workbook-reader.js +50 -0
  115. package/dist/browser/modules/excel/stream/workbook-writer.browser.d.ts +147 -0
  116. package/dist/browser/modules/excel/stream/workbook-writer.browser.js +356 -0
  117. package/dist/browser/modules/excel/stream/workbook-writer.d.ts +31 -0
  118. package/dist/browser/modules/excel/stream/workbook-writer.js +52 -0
  119. package/dist/browser/modules/excel/stream/worksheet-reader.d.ts +61 -0
  120. package/dist/browser/modules/excel/stream/worksheet-reader.js +367 -0
  121. package/dist/browser/modules/excel/stream/worksheet-writer.d.ts +140 -0
  122. package/dist/browser/modules/excel/stream/worksheet-writer.js +613 -0
  123. package/dist/browser/modules/excel/table.d.ts +81 -0
  124. package/dist/browser/modules/excel/table.js +412 -0
  125. package/dist/browser/modules/excel/types.d.ts +518 -0
  126. package/dist/browser/modules/excel/types.js +22 -0
  127. package/dist/browser/modules/excel/utils/cell-format.d.ts +32 -0
  128. package/dist/browser/modules/excel/utils/cell-format.js +814 -0
  129. package/dist/browser/modules/excel/utils/cell-matrix.d.ts +37 -0
  130. package/dist/browser/modules/excel/utils/cell-matrix.js +180 -0
  131. package/dist/browser/modules/excel/utils/col-cache.d.ts +36 -0
  132. package/dist/browser/modules/excel/utils/col-cache.js +278 -0
  133. package/dist/browser/modules/excel/utils/copy-style.d.ts +5 -0
  134. package/dist/browser/modules/excel/utils/copy-style.js +43 -0
  135. package/dist/browser/modules/excel/utils/encryptor.browser.d.ts +19 -0
  136. package/dist/browser/modules/excel/utils/encryptor.browser.js +46 -0
  137. package/dist/browser/modules/excel/utils/encryptor.d.ts +9 -0
  138. package/dist/browser/modules/excel/utils/encryptor.js +35 -0
  139. package/dist/browser/modules/excel/utils/iterate-stream.d.ts +14 -0
  140. package/dist/browser/modules/excel/utils/iterate-stream.js +55 -0
  141. package/dist/browser/modules/excel/utils/ooxml-paths.d.ts +64 -0
  142. package/dist/browser/modules/excel/utils/ooxml-paths.js +209 -0
  143. package/dist/browser/modules/excel/utils/parse-sax.d.ts +113 -0
  144. package/dist/browser/modules/excel/utils/parse-sax.js +1206 -0
  145. package/dist/browser/modules/excel/utils/shared-formula.d.ts +2 -0
  146. package/dist/browser/modules/excel/utils/shared-formula.js +36 -0
  147. package/dist/browser/modules/excel/utils/shared-strings.d.ts +12 -0
  148. package/dist/browser/modules/excel/utils/shared-strings.js +29 -0
  149. package/dist/browser/modules/excel/utils/sheet-utils.d.ts +190 -0
  150. package/dist/browser/modules/excel/utils/sheet-utils.js +674 -0
  151. package/dist/browser/modules/excel/utils/stream-buf.d.ts +126 -0
  152. package/dist/browser/modules/excel/utils/stream-buf.js +452 -0
  153. package/dist/browser/modules/excel/utils/string-buf.d.ts +29 -0
  154. package/dist/browser/modules/excel/utils/string-buf.js +75 -0
  155. package/dist/browser/modules/excel/utils/under-dash.d.ts +7 -0
  156. package/dist/browser/modules/excel/utils/under-dash.js +166 -0
  157. package/dist/browser/modules/excel/utils/xml-stream.d.ts +34 -0
  158. package/dist/browser/modules/excel/utils/xml-stream.js +179 -0
  159. package/dist/browser/modules/excel/workbook.d.ts +195 -0
  160. package/dist/browser/modules/excel/workbook.js +314 -0
  161. package/dist/browser/modules/excel/worksheet.d.ts +333 -0
  162. package/dist/browser/modules/excel/worksheet.js +924 -0
  163. package/dist/browser/modules/excel/xlsx/defaultnumformats.d.ts +12 -0
  164. package/dist/browser/modules/excel/xlsx/defaultnumformats.js +149 -0
  165. package/dist/browser/modules/excel/xlsx/rel-type.d.ts +19 -0
  166. package/dist/browser/modules/excel/xlsx/rel-type.js +19 -0
  167. package/dist/browser/modules/excel/xlsx/xform/base-xform.d.ts +33 -0
  168. package/dist/browser/modules/excel/xlsx/xform/base-xform.js +135 -0
  169. package/dist/browser/modules/excel/xlsx/xform/book/defined-name-xform.d.ts +17 -0
  170. package/dist/browser/modules/excel/xlsx/xform/book/defined-name-xform.js +124 -0
  171. package/dist/browser/modules/excel/xlsx/xform/book/sheet-xform.d.ts +14 -0
  172. package/dist/browser/modules/excel/xlsx/xform/book/sheet-xform.js +30 -0
  173. package/dist/browser/modules/excel/xlsx/xform/book/workbook-calc-properties-xform.d.ts +11 -0
  174. package/dist/browser/modules/excel/xlsx/xform/book/workbook-calc-properties-xform.js +21 -0
  175. package/dist/browser/modules/excel/xlsx/xform/book/workbook-pivot-cache-xform.d.ts +12 -0
  176. package/dist/browser/modules/excel/xlsx/xform/book/workbook-pivot-cache-xform.js +24 -0
  177. package/dist/browser/modules/excel/xlsx/xform/book/workbook-properties-xform.d.ts +11 -0
  178. package/dist/browser/modules/excel/xlsx/xform/book/workbook-properties-xform.js +24 -0
  179. package/dist/browser/modules/excel/xlsx/xform/book/workbook-view-xform.d.ts +17 -0
  180. package/dist/browser/modules/excel/xlsx/xform/book/workbook-view-xform.js +46 -0
  181. package/dist/browser/modules/excel/xlsx/xform/book/workbook-xform.d.ts +23 -0
  182. package/dist/browser/modules/excel/xlsx/xform/book/workbook-xform.js +234 -0
  183. package/dist/browser/modules/excel/xlsx/xform/comment/comment-xform.d.ts +28 -0
  184. package/dist/browser/modules/excel/xlsx/xform/comment/comment-xform.js +76 -0
  185. package/dist/browser/modules/excel/xlsx/xform/comment/comments-xform.d.ts +21 -0
  186. package/dist/browser/modules/excel/xlsx/xform/comment/comments-xform.js +72 -0
  187. package/dist/browser/modules/excel/xlsx/xform/comment/style/vml-position-xform.d.ts +16 -0
  188. package/dist/browser/modules/excel/xlsx/xform/comment/style/vml-position-xform.js +34 -0
  189. package/dist/browser/modules/excel/xlsx/xform/comment/style/vml-protection-xform.d.ts +14 -0
  190. package/dist/browser/modules/excel/xlsx/xform/comment/style/vml-protection-xform.js +30 -0
  191. package/dist/browser/modules/excel/xlsx/xform/comment/vml-anchor-xform.d.ts +27 -0
  192. package/dist/browser/modules/excel/xlsx/xform/comment/vml-anchor-xform.js +55 -0
  193. package/dist/browser/modules/excel/xlsx/xform/comment/vml-client-data-xform.d.ts +35 -0
  194. package/dist/browser/modules/excel/xlsx/xform/comment/vml-client-data-xform.js +82 -0
  195. package/dist/browser/modules/excel/xlsx/xform/comment/vml-notes-xform.d.ts +24 -0
  196. package/dist/browser/modules/excel/xlsx/xform/comment/vml-notes-xform.js +96 -0
  197. package/dist/browser/modules/excel/xlsx/xform/comment/vml-shape-xform.d.ts +25 -0
  198. package/dist/browser/modules/excel/xlsx/xform/comment/vml-shape-xform.js +83 -0
  199. package/dist/browser/modules/excel/xlsx/xform/comment/vml-textbox-xform.d.ts +23 -0
  200. package/dist/browser/modules/excel/xlsx/xform/comment/vml-textbox-xform.js +60 -0
  201. package/dist/browser/modules/excel/xlsx/xform/composite-xform.d.ts +11 -0
  202. package/dist/browser/modules/excel/xlsx/xform/composite-xform.js +48 -0
  203. package/dist/browser/modules/excel/xlsx/xform/core/app-heading-pairs-xform.d.ts +8 -0
  204. package/dist/browser/modules/excel/xlsx/xform/core/app-heading-pairs-xform.js +24 -0
  205. package/dist/browser/modules/excel/xlsx/xform/core/app-titles-of-parts-xform.d.ts +8 -0
  206. package/dist/browser/modules/excel/xlsx/xform/core/app-titles-of-parts-xform.js +21 -0
  207. package/dist/browser/modules/excel/xlsx/xform/core/app-xform.d.ts +26 -0
  208. package/dist/browser/modules/excel/xlsx/xform/core/app-xform.js +83 -0
  209. package/dist/browser/modules/excel/xlsx/xform/core/content-types-xform.d.ts +11 -0
  210. package/dist/browser/modules/excel/xlsx/xform/core/content-types-xform.js +122 -0
  211. package/dist/browser/modules/excel/xlsx/xform/core/core-xform.d.ts +42 -0
  212. package/dist/browser/modules/excel/xlsx/xform/core/core-xform.js +124 -0
  213. package/dist/browser/modules/excel/xlsx/xform/core/relationship-xform.d.ts +14 -0
  214. package/dist/browser/modules/excel/xlsx/xform/core/relationship-xform.js +20 -0
  215. package/dist/browser/modules/excel/xlsx/xform/core/relationships-xform.d.ts +14 -0
  216. package/dist/browser/modules/excel/xlsx/xform/core/relationships-xform.js +62 -0
  217. package/dist/browser/modules/excel/xlsx/xform/drawing/base-cell-anchor-xform.d.ts +13 -0
  218. package/dist/browser/modules/excel/xlsx/xform/drawing/base-cell-anchor-xform.js +44 -0
  219. package/dist/browser/modules/excel/xlsx/xform/drawing/blip-fill-xform.d.ts +16 -0
  220. package/dist/browser/modules/excel/xlsx/xform/drawing/blip-fill-xform.js +57 -0
  221. package/dist/browser/modules/excel/xlsx/xform/drawing/blip-xform.d.ts +14 -0
  222. package/dist/browser/modules/excel/xlsx/xform/drawing/blip-xform.js +40 -0
  223. package/dist/browser/modules/excel/xlsx/xform/drawing/c-nv-pic-pr-xform.d.ts +9 -0
  224. package/dist/browser/modules/excel/xlsx/xform/drawing/c-nv-pic-pr-xform.js +32 -0
  225. package/dist/browser/modules/excel/xlsx/xform/drawing/c-nv-pr-xform.d.ts +18 -0
  226. package/dist/browser/modules/excel/xlsx/xform/drawing/c-nv-pr-xform.js +59 -0
  227. package/dist/browser/modules/excel/xlsx/xform/drawing/cell-position-xform.d.ts +24 -0
  228. package/dist/browser/modules/excel/xlsx/xform/drawing/cell-position-xform.js +68 -0
  229. package/dist/browser/modules/excel/xlsx/xform/drawing/drawing-xform.d.ts +24 -0
  230. package/dist/browser/modules/excel/xlsx/xform/drawing/drawing-xform.js +96 -0
  231. package/dist/browser/modules/excel/xlsx/xform/drawing/ext-lst-xform.d.ts +9 -0
  232. package/dist/browser/modules/excel/xlsx/xform/drawing/ext-lst-xform.js +37 -0
  233. package/dist/browser/modules/excel/xlsx/xform/drawing/ext-xform.d.ts +20 -0
  234. package/dist/browser/modules/excel/xlsx/xform/drawing/ext-xform.js +34 -0
  235. package/dist/browser/modules/excel/xlsx/xform/drawing/hlink-click-xform.d.ts +11 -0
  236. package/dist/browser/modules/excel/xlsx/xform/drawing/hlink-click-xform.js +39 -0
  237. package/dist/browser/modules/excel/xlsx/xform/drawing/nv-pic-pr-xform.d.ts +15 -0
  238. package/dist/browser/modules/excel/xlsx/xform/drawing/nv-pic-pr-xform.js +56 -0
  239. package/dist/browser/modules/excel/xlsx/xform/drawing/one-cell-anchor-xform.d.ts +20 -0
  240. package/dist/browser/modules/excel/xlsx/xform/drawing/one-cell-anchor-xform.js +52 -0
  241. package/dist/browser/modules/excel/xlsx/xform/drawing/pic-xform.d.ts +22 -0
  242. package/dist/browser/modules/excel/xlsx/xform/drawing/pic-xform.js +64 -0
  243. package/dist/browser/modules/excel/xlsx/xform/drawing/sp-pr.d.ts +32 -0
  244. package/dist/browser/modules/excel/xlsx/xform/drawing/sp-pr.js +17 -0
  245. package/dist/browser/modules/excel/xlsx/xform/drawing/two-cell-anchor-xform.d.ts +20 -0
  246. package/dist/browser/modules/excel/xlsx/xform/drawing/two-cell-anchor-xform.js +51 -0
  247. package/dist/browser/modules/excel/xlsx/xform/list-xform.d.ts +32 -0
  248. package/dist/browser/modules/excel/xlsx/xform/list-xform.js +89 -0
  249. package/dist/browser/modules/excel/xlsx/xform/pivot-table/cache-field-xform.d.ts +42 -0
  250. package/dist/browser/modules/excel/xlsx/xform/pivot-table/cache-field-xform.js +128 -0
  251. package/dist/browser/modules/excel/xlsx/xform/pivot-table/cache-field.d.ts +15 -0
  252. package/dist/browser/modules/excel/xlsx/xform/pivot-table/cache-field.js +78 -0
  253. package/dist/browser/modules/excel/xlsx/xform/pivot-table/pivot-cache-definition-xform.d.ts +60 -0
  254. package/dist/browser/modules/excel/xlsx/xform/pivot-table/pivot-cache-definition-xform.js +179 -0
  255. package/dist/browser/modules/excel/xlsx/xform/pivot-table/pivot-cache-records-xform.d.ts +73 -0
  256. package/dist/browser/modules/excel/xlsx/xform/pivot-table/pivot-cache-records-xform.js +234 -0
  257. package/dist/browser/modules/excel/xlsx/xform/pivot-table/pivot-table-xform.d.ts +119 -0
  258. package/dist/browser/modules/excel/xlsx/xform/pivot-table/pivot-table-xform.js +624 -0
  259. package/dist/browser/modules/excel/xlsx/xform/sheet/auto-filter-xform.d.ts +8 -0
  260. package/dist/browser/modules/excel/xlsx/xform/sheet/auto-filter-xform.js +34 -0
  261. package/dist/browser/modules/excel/xlsx/xform/sheet/cell-xform.d.ts +17 -0
  262. package/dist/browser/modules/excel/xlsx/xform/sheet/cell-xform.js +460 -0
  263. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/cf-rule-xform.d.ts +41 -0
  264. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/cf-rule-xform.js +259 -0
  265. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/cfvo-xform.d.ts +8 -0
  266. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/cfvo-xform.js +22 -0
  267. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/color-scale-xform.d.ts +13 -0
  268. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/color-scale-xform.js +35 -0
  269. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/conditional-formatting-xform.d.ts +9 -0
  270. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/conditional-formatting-xform.js +37 -0
  271. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/conditional-formattings-xform.d.ts +16 -0
  272. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/conditional-formattings-xform.js +74 -0
  273. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/databar-xform.d.ts +13 -0
  274. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/databar-xform.js +39 -0
  275. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/ext-lst-ref-xform.d.ts +9 -0
  276. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/ext-lst-ref-xform.js +67 -0
  277. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/formula-xform.d.ts +9 -0
  278. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/formula-xform.js +19 -0
  279. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/icon-set-xform.d.ts +11 -0
  280. package/dist/browser/modules/excel/xlsx/xform/sheet/cf/icon-set-xform.js +37 -0
  281. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/cf-icon-ext-xform.d.ts +10 -0
  282. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/cf-icon-ext-xform.js +22 -0
  283. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/cf-rule-ext-xform.d.ts +23 -0
  284. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/cf-rule-ext-xform.js +80 -0
  285. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/cfvo-ext-xform.d.ts +13 -0
  286. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/cfvo-ext-xform.js +35 -0
  287. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/conditional-formatting-ext-xform.d.ts +16 -0
  288. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/conditional-formatting-ext-xform.js +48 -0
  289. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/conditional-formattings-ext-xform.d.ts +13 -0
  290. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/conditional-formattings-ext-xform.js +40 -0
  291. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/databar-ext-xform.d.ts +29 -0
  292. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/databar-ext-xform.js +69 -0
  293. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/f-ext-xform.d.ts +9 -0
  294. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/f-ext-xform.js +19 -0
  295. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/icon-set-ext-xform.d.ts +20 -0
  296. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/icon-set-ext-xform.js +60 -0
  297. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/sqref-ext-xform.d.ts +9 -0
  298. package/dist/browser/modules/excel/xlsx/xform/sheet/cf-ext/sqref-ext-xform.js +19 -0
  299. package/dist/browser/modules/excel/xlsx/xform/sheet/col-breaks-xform.d.ts +16 -0
  300. package/dist/browser/modules/excel/xlsx/xform/sheet/col-breaks-xform.js +35 -0
  301. package/dist/browser/modules/excel/xlsx/xform/sheet/col-xform.d.ts +22 -0
  302. package/dist/browser/modules/excel/xlsx/xform/sheet/col-xform.js +75 -0
  303. package/dist/browser/modules/excel/xlsx/xform/sheet/data-validations-xform.d.ts +12 -0
  304. package/dist/browser/modules/excel/xlsx/xform/sheet/data-validations-xform.js +269 -0
  305. package/dist/browser/modules/excel/xlsx/xform/sheet/dimension-xform.d.ts +10 -0
  306. package/dist/browser/modules/excel/xlsx/xform/sheet/dimension-xform.js +23 -0
  307. package/dist/browser/modules/excel/xlsx/xform/sheet/drawing-xform.d.ts +12 -0
  308. package/dist/browser/modules/excel/xlsx/xform/sheet/drawing-xform.js +27 -0
  309. package/dist/browser/modules/excel/xlsx/xform/sheet/ext-lst-xform.d.ts +16 -0
  310. package/dist/browser/modules/excel/xlsx/xform/sheet/ext-lst-xform.js +66 -0
  311. package/dist/browser/modules/excel/xlsx/xform/sheet/header-footer-xform.d.ts +20 -0
  312. package/dist/browser/modules/excel/xlsx/xform/sheet/header-footer-xform.js +124 -0
  313. package/dist/browser/modules/excel/xlsx/xform/sheet/hyperlink-xform.d.ts +16 -0
  314. package/dist/browser/modules/excel/xlsx/xform/sheet/hyperlink-xform.js +47 -0
  315. package/dist/browser/modules/excel/xlsx/xform/sheet/merge-cell-xform.d.ts +9 -0
  316. package/dist/browser/modules/excel/xlsx/xform/sheet/merge-cell-xform.js +21 -0
  317. package/dist/browser/modules/excel/xlsx/xform/sheet/merges.d.ts +14 -0
  318. package/dist/browser/modules/excel/xlsx/xform/sheet/merges.js +50 -0
  319. package/dist/browser/modules/excel/xlsx/xform/sheet/outline-properties-xform.d.ts +13 -0
  320. package/dist/browser/modules/excel/xlsx/xform/sheet/outline-properties-xform.js +36 -0
  321. package/dist/browser/modules/excel/xlsx/xform/sheet/page-breaks-xform.d.ts +14 -0
  322. package/dist/browser/modules/excel/xlsx/xform/sheet/page-breaks-xform.js +33 -0
  323. package/dist/browser/modules/excel/xlsx/xform/sheet/page-margins-xform.d.ts +17 -0
  324. package/dist/browser/modules/excel/xlsx/xform/sheet/page-margins-xform.js +42 -0
  325. package/dist/browser/modules/excel/xlsx/xform/sheet/page-setup-properties-xform.d.ts +12 -0
  326. package/dist/browser/modules/excel/xlsx/xform/sheet/page-setup-properties-xform.js +29 -0
  327. package/dist/browser/modules/excel/xlsx/xform/sheet/page-setup-xform.d.ts +27 -0
  328. package/dist/browser/modules/excel/xlsx/xform/sheet/page-setup-xform.js +96 -0
  329. package/dist/browser/modules/excel/xlsx/xform/sheet/picture-xform.d.ts +12 -0
  330. package/dist/browser/modules/excel/xlsx/xform/sheet/picture-xform.js +27 -0
  331. package/dist/browser/modules/excel/xlsx/xform/sheet/print-options-xform.d.ts +15 -0
  332. package/dist/browser/modules/excel/xlsx/xform/sheet/print-options-xform.js +41 -0
  333. package/dist/browser/modules/excel/xlsx/xform/sheet/row-breaks-xform.d.ts +10 -0
  334. package/dist/browser/modules/excel/xlsx/xform/sheet/row-breaks-xform.js +29 -0
  335. package/dist/browser/modules/excel/xlsx/xform/sheet/row-xform.d.ts +37 -0
  336. package/dist/browser/modules/excel/xlsx/xform/sheet/row-xform.js +152 -0
  337. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-format-properties-xform.d.ts +16 -0
  338. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-format-properties-xform.js +49 -0
  339. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-properties-xform.d.ts +19 -0
  340. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-properties-xform.js +82 -0
  341. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-protection-xform.d.ts +31 -0
  342. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-protection-xform.js +80 -0
  343. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-view-xform.d.ts +32 -0
  344. package/dist/browser/modules/excel/xlsx/xform/sheet/sheet-view-xform.js +193 -0
  345. package/dist/browser/modules/excel/xlsx/xform/sheet/table-part-xform.d.ts +12 -0
  346. package/dist/browser/modules/excel/xlsx/xform/sheet/table-part-xform.js +27 -0
  347. package/dist/browser/modules/excel/xlsx/xform/sheet/worksheet-xform.d.ts +21 -0
  348. package/dist/browser/modules/excel/xlsx/xform/sheet/worksheet-xform.js +518 -0
  349. package/dist/browser/modules/excel/xlsx/xform/simple/boolean-xform.d.ts +15 -0
  350. package/dist/browser/modules/excel/xlsx/xform/simple/boolean-xform.js +24 -0
  351. package/dist/browser/modules/excel/xlsx/xform/simple/date-xform.d.ts +22 -0
  352. package/dist/browser/modules/excel/xlsx/xform/simple/date-xform.js +65 -0
  353. package/dist/browser/modules/excel/xlsx/xform/simple/float-xform.d.ts +18 -0
  354. package/dist/browser/modules/excel/xlsx/xform/simple/float-xform.js +47 -0
  355. package/dist/browser/modules/excel/xlsx/xform/simple/integer-xform.d.ts +20 -0
  356. package/dist/browser/modules/excel/xlsx/xform/simple/integer-xform.js +52 -0
  357. package/dist/browser/modules/excel/xlsx/xform/simple/string-xform.d.ts +18 -0
  358. package/dist/browser/modules/excel/xlsx/xform/simple/string-xform.js +47 -0
  359. package/dist/browser/modules/excel/xlsx/xform/static-xform.d.ts +17 -0
  360. package/dist/browser/modules/excel/xlsx/xform/static-xform.js +55 -0
  361. package/dist/browser/modules/excel/xlsx/xform/strings/phonetic-text-xform.d.ts +20 -0
  362. package/dist/browser/modules/excel/xlsx/xform/strings/phonetic-text-xform.js +86 -0
  363. package/dist/browser/modules/excel/xlsx/xform/strings/rich-text-xform.d.ts +25 -0
  364. package/dist/browser/modules/excel/xlsx/xform/strings/rich-text-xform.js +77 -0
  365. package/dist/browser/modules/excel/xlsx/xform/strings/shared-string-xform.d.ts +17 -0
  366. package/dist/browser/modules/excel/xlsx/xform/strings/shared-string-xform.js +90 -0
  367. package/dist/browser/modules/excel/xlsx/xform/strings/shared-strings-xform.d.ts +27 -0
  368. package/dist/browser/modules/excel/xlsx/xform/strings/shared-strings-xform.js +109 -0
  369. package/dist/browser/modules/excel/xlsx/xform/strings/text-xform.d.ts +10 -0
  370. package/dist/browser/modules/excel/xlsx/xform/strings/text-xform.js +36 -0
  371. package/dist/browser/modules/excel/xlsx/xform/style/alignment-xform.d.ts +18 -0
  372. package/dist/browser/modules/excel/xlsx/xform/style/alignment-xform.js +152 -0
  373. package/dist/browser/modules/excel/xlsx/xform/style/border-xform.d.ts +49 -0
  374. package/dist/browser/modules/excel/xlsx/xform/style/border-xform.js +188 -0
  375. package/dist/browser/modules/excel/xlsx/xform/style/color-xform.d.ts +17 -0
  376. package/dist/browser/modules/excel/xlsx/xform/style/color-xform.js +61 -0
  377. package/dist/browser/modules/excel/xlsx/xform/style/dxf-xform.d.ts +23 -0
  378. package/dist/browser/modules/excel/xlsx/xform/style/dxf-xform.js +92 -0
  379. package/dist/browser/modules/excel/xlsx/xform/style/fill-xform.d.ts +85 -0
  380. package/dist/browser/modules/excel/xlsx/xform/style/fill-xform.js +312 -0
  381. package/dist/browser/modules/excel/xlsx/xform/style/font-xform.d.ts +35 -0
  382. package/dist/browser/modules/excel/xlsx/xform/style/font-xform.js +100 -0
  383. package/dist/browser/modules/excel/xlsx/xform/style/numfmt-xform.d.ts +18 -0
  384. package/dist/browser/modules/excel/xlsx/xform/style/numfmt-xform.js +50 -0
  385. package/dist/browser/modules/excel/xlsx/xform/style/protection-xform.d.ts +13 -0
  386. package/dist/browser/modules/excel/xlsx/xform/style/protection-xform.js +49 -0
  387. package/dist/browser/modules/excel/xlsx/xform/style/style-xform.d.ts +30 -0
  388. package/dist/browser/modules/excel/xlsx/xform/style/style-xform.js +108 -0
  389. package/dist/browser/modules/excel/xlsx/xform/style/styles-xform.d.ts +46 -0
  390. package/dist/browser/modules/excel/xlsx/xform/style/styles-xform.js +484 -0
  391. package/dist/browser/modules/excel/xlsx/xform/style/underline-xform.d.ts +14 -0
  392. package/dist/browser/modules/excel/xlsx/xform/style/underline-xform.js +38 -0
  393. package/dist/browser/modules/excel/xlsx/xform/table/auto-filter-xform.d.ts +21 -0
  394. package/dist/browser/modules/excel/xlsx/xform/table/auto-filter-xform.js +70 -0
  395. package/dist/browser/modules/excel/xlsx/xform/table/custom-filter-xform.d.ts +15 -0
  396. package/dist/browser/modules/excel/xlsx/xform/table/custom-filter-xform.js +31 -0
  397. package/dist/browser/modules/excel/xlsx/xform/table/filter-column-xform.d.ts +24 -0
  398. package/dist/browser/modules/excel/xlsx/xform/table/filter-column-xform.js +87 -0
  399. package/dist/browser/modules/excel/xlsx/xform/table/filter-xform.d.ts +14 -0
  400. package/dist/browser/modules/excel/xlsx/xform/table/filter-xform.js +29 -0
  401. package/dist/browser/modules/excel/xlsx/xform/table/table-column-xform.d.ts +21 -0
  402. package/dist/browser/modules/excel/xlsx/xform/table/table-column-xform.js +41 -0
  403. package/dist/browser/modules/excel/xlsx/xform/table/table-style-info-xform.d.ts +18 -0
  404. package/dist/browser/modules/excel/xlsx/xform/table/table-style-info-xform.js +44 -0
  405. package/dist/browser/modules/excel/xlsx/xform/table/table-xform.d.ts +33 -0
  406. package/dist/browser/modules/excel/xlsx/xform/table/table-xform.js +126 -0
  407. package/dist/browser/modules/excel/xlsx/xlsx.browser.d.ts +208 -0
  408. package/dist/browser/modules/excel/xlsx/xlsx.browser.js +1152 -0
  409. package/dist/browser/modules/excel/xlsx/xlsx.d.ts +24 -0
  410. package/dist/browser/modules/excel/xlsx/xlsx.js +239 -0
  411. package/dist/browser/modules/excel/xlsx/xml/theme1.d.ts +1 -0
  412. package/dist/browser/modules/excel/xlsx/xml/theme1.js +1 -0
  413. package/dist/browser/modules/stream/base-transform.d.ts +68 -0
  414. package/dist/browser/modules/stream/base-transform.js +160 -0
  415. package/dist/browser/modules/stream/buffered-stream.d.ts +94 -0
  416. package/dist/browser/modules/stream/buffered-stream.js +277 -0
  417. package/dist/browser/modules/stream/chunked-builder.d.ts +97 -0
  418. package/dist/browser/modules/stream/chunked-builder.js +165 -0
  419. package/dist/browser/modules/stream/event-emitter.d.ts +30 -0
  420. package/dist/browser/modules/stream/event-emitter.js +239 -0
  421. package/dist/browser/modules/stream/index.browser.d.ts +22 -0
  422. package/dist/browser/modules/stream/index.browser.js +25 -0
  423. package/dist/browser/modules/stream/index.d.ts +49 -0
  424. package/dist/browser/modules/stream/index.js +52 -0
  425. package/dist/browser/modules/stream/pull-stream.d.ts +67 -0
  426. package/dist/browser/modules/stream/pull-stream.js +204 -0
  427. package/dist/browser/modules/stream/shared.d.ts +54 -0
  428. package/dist/browser/modules/stream/shared.js +156 -0
  429. package/dist/browser/modules/stream/streams.browser.d.ts +936 -0
  430. package/dist/browser/modules/stream/streams.browser.js +3297 -0
  431. package/dist/browser/modules/stream/streams.d.ts +282 -0
  432. package/dist/browser/modules/stream/streams.js +940 -0
  433. package/dist/browser/modules/stream/types.d.ts +238 -0
  434. package/dist/browser/modules/stream/types.js +7 -0
  435. package/dist/browser/modules/stream/utils.d.ts +24 -0
  436. package/dist/browser/modules/stream/utils.js +85 -0
  437. package/dist/browser/utils/browser.d.ts +9 -0
  438. package/dist/browser/utils/browser.js +49 -0
  439. package/dist/browser/utils/datetime.d.ts +56 -0
  440. package/dist/browser/utils/datetime.js +493 -0
  441. package/dist/browser/utils/env.d.ts +14 -0
  442. package/dist/browser/utils/env.js +18 -0
  443. package/dist/browser/utils/utils.base.d.ts +49 -0
  444. package/dist/browser/utils/utils.base.js +275 -0
  445. package/dist/browser/utils/utils.browser.d.ts +6 -0
  446. package/dist/browser/utils/utils.browser.js +12 -0
  447. package/dist/browser/utils/utils.d.ts +6 -0
  448. package/dist/browser/utils/utils.js +19 -0
  449. package/dist/browser/utils/uuid.d.ts +11 -0
  450. package/dist/browser/utils/uuid.js +55 -0
  451. package/dist/cjs/modules/excel/table.js +8 -1
  452. package/dist/esm/modules/excel/table.js +8 -1
  453. package/dist/{browser → iife}/excelts.iife.js +6 -2
  454. package/dist/iife/excelts.iife.js.map +1 -0
  455. package/dist/{browser → iife}/excelts.iife.min.js +2 -2
  456. package/dist/types/index.browser.d.ts +20 -20
  457. package/dist/types/index.d.ts +23 -23
  458. package/dist/types/modules/archive/compress.browser.d.ts +1 -1
  459. package/dist/types/modules/archive/compress.d.ts +2 -2
  460. package/dist/types/modules/archive/crc32.browser.d.ts +1 -1
  461. package/dist/types/modules/archive/crc32.d.ts +1 -1
  462. package/dist/types/modules/archive/defaults.d.ts +1 -1
  463. package/dist/types/modules/archive/extract.d.ts +2 -2
  464. package/dist/types/modules/archive/index.base.d.ts +4 -4
  465. package/dist/types/modules/archive/index.browser.d.ts +5 -5
  466. package/dist/types/modules/archive/index.d.ts +5 -5
  467. package/dist/types/modules/archive/parse.base.d.ts +3 -3
  468. package/dist/types/modules/archive/parse.browser.d.ts +2 -2
  469. package/dist/types/modules/archive/parse.d.ts +3 -3
  470. package/dist/types/modules/archive/streaming-compress.browser.d.ts +2 -2
  471. package/dist/types/modules/archive/streaming-compress.d.ts +2 -2
  472. package/dist/types/modules/archive/streaming-zip.d.ts +2 -2
  473. package/dist/types/modules/archive/zip-builder.d.ts +2 -2
  474. package/dist/types/modules/archive/zip-entry-metadata.d.ts +1 -1
  475. package/dist/types/modules/archive/zip-parser.d.ts +1 -1
  476. package/dist/types/modules/csv/csv-stream.d.ts +3 -3
  477. package/dist/types/modules/csv/csv.browser.d.ts +9 -9
  478. package/dist/types/modules/csv/csv.d.ts +4 -4
  479. package/dist/types/modules/excel/anchor.d.ts +1 -1
  480. package/dist/types/modules/excel/cell.d.ts +7 -7
  481. package/dist/types/modules/excel/column.d.ts +3 -3
  482. package/dist/types/modules/excel/defined-names.d.ts +4 -4
  483. package/dist/types/modules/excel/image.d.ts +2 -2
  484. package/dist/types/modules/excel/pivot-table.d.ts +1 -1
  485. package/dist/types/modules/excel/range.d.ts +1 -1
  486. package/dist/types/modules/excel/row.d.ts +3 -3
  487. package/dist/types/modules/excel/stream/hyperlink-reader.d.ts +2 -2
  488. package/dist/types/modules/excel/stream/workbook-reader.browser.d.ts +6 -6
  489. package/dist/types/modules/excel/stream/workbook-reader.d.ts +5 -5
  490. package/dist/types/modules/excel/stream/workbook-writer.browser.d.ts +8 -8
  491. package/dist/types/modules/excel/stream/workbook-writer.d.ts +2 -2
  492. package/dist/types/modules/excel/stream/worksheet-reader.d.ts +6 -6
  493. package/dist/types/modules/excel/stream/worksheet-writer.d.ts +9 -9
  494. package/dist/types/modules/excel/table.d.ts +2 -2
  495. package/dist/types/modules/excel/utils/col-cache.d.ts +1 -1
  496. package/dist/types/modules/excel/utils/sheet-utils.d.ts +3 -3
  497. package/dist/types/modules/excel/utils/stream-buf.d.ts +2 -2
  498. package/dist/types/modules/excel/workbook.d.ts +9 -9
  499. package/dist/types/modules/excel/worksheet.d.ts +10 -10
  500. package/dist/types/modules/excel/xlsx/xform/base-xform.d.ts +1 -1
  501. package/dist/types/modules/excel/xlsx/xform/book/defined-name-xform.d.ts +1 -1
  502. package/dist/types/modules/excel/xlsx/xform/book/sheet-xform.d.ts +1 -1
  503. package/dist/types/modules/excel/xlsx/xform/book/workbook-calc-properties-xform.d.ts +1 -1
  504. package/dist/types/modules/excel/xlsx/xform/book/workbook-pivot-cache-xform.d.ts +1 -1
  505. package/dist/types/modules/excel/xlsx/xform/book/workbook-properties-xform.d.ts +1 -1
  506. package/dist/types/modules/excel/xlsx/xform/book/workbook-view-xform.d.ts +1 -1
  507. package/dist/types/modules/excel/xlsx/xform/book/workbook-xform.d.ts +2 -2
  508. package/dist/types/modules/excel/xlsx/xform/comment/comment-xform.d.ts +2 -2
  509. package/dist/types/modules/excel/xlsx/xform/comment/comments-xform.d.ts +2 -2
  510. package/dist/types/modules/excel/xlsx/xform/comment/style/vml-position-xform.d.ts +1 -1
  511. package/dist/types/modules/excel/xlsx/xform/comment/style/vml-protection-xform.d.ts +1 -1
  512. package/dist/types/modules/excel/xlsx/xform/comment/vml-anchor-xform.d.ts +1 -1
  513. package/dist/types/modules/excel/xlsx/xform/comment/vml-client-data-xform.d.ts +1 -1
  514. package/dist/types/modules/excel/xlsx/xform/comment/vml-notes-xform.d.ts +1 -1
  515. package/dist/types/modules/excel/xlsx/xform/comment/vml-shape-xform.d.ts +1 -1
  516. package/dist/types/modules/excel/xlsx/xform/comment/vml-textbox-xform.d.ts +1 -1
  517. package/dist/types/modules/excel/xlsx/xform/composite-xform.d.ts +1 -1
  518. package/dist/types/modules/excel/xlsx/xform/core/app-heading-pairs-xform.d.ts +1 -1
  519. package/dist/types/modules/excel/xlsx/xform/core/app-titles-of-parts-xform.d.ts +1 -1
  520. package/dist/types/modules/excel/xlsx/xform/core/app-xform.d.ts +1 -1
  521. package/dist/types/modules/excel/xlsx/xform/core/content-types-xform.d.ts +1 -1
  522. package/dist/types/modules/excel/xlsx/xform/core/core-xform.d.ts +1 -1
  523. package/dist/types/modules/excel/xlsx/xform/core/relationship-xform.d.ts +1 -1
  524. package/dist/types/modules/excel/xlsx/xform/core/relationships-xform.d.ts +1 -1
  525. package/dist/types/modules/excel/xlsx/xform/drawing/base-cell-anchor-xform.d.ts +1 -1
  526. package/dist/types/modules/excel/xlsx/xform/drawing/blip-fill-xform.d.ts +2 -2
  527. package/dist/types/modules/excel/xlsx/xform/drawing/blip-xform.d.ts +1 -1
  528. package/dist/types/modules/excel/xlsx/xform/drawing/c-nv-pic-pr-xform.d.ts +1 -1
  529. package/dist/types/modules/excel/xlsx/xform/drawing/c-nv-pr-xform.d.ts +1 -1
  530. package/dist/types/modules/excel/xlsx/xform/drawing/cell-position-xform.d.ts +2 -2
  531. package/dist/types/modules/excel/xlsx/xform/drawing/drawing-xform.d.ts +1 -1
  532. package/dist/types/modules/excel/xlsx/xform/drawing/ext-lst-xform.d.ts +1 -1
  533. package/dist/types/modules/excel/xlsx/xform/drawing/ext-xform.d.ts +1 -1
  534. package/dist/types/modules/excel/xlsx/xform/drawing/hlink-click-xform.d.ts +1 -1
  535. package/dist/types/modules/excel/xlsx/xform/drawing/nv-pic-pr-xform.d.ts +1 -1
  536. package/dist/types/modules/excel/xlsx/xform/drawing/one-cell-anchor-xform.d.ts +1 -1
  537. package/dist/types/modules/excel/xlsx/xform/drawing/pic-xform.d.ts +1 -1
  538. package/dist/types/modules/excel/xlsx/xform/drawing/two-cell-anchor-xform.d.ts +1 -1
  539. package/dist/types/modules/excel/xlsx/xform/list-xform.d.ts +1 -1
  540. package/dist/types/modules/excel/xlsx/xform/pivot-table/cache-field-xform.d.ts +1 -1
  541. package/dist/types/modules/excel/xlsx/xform/pivot-table/pivot-cache-definition-xform.d.ts +3 -3
  542. package/dist/types/modules/excel/xlsx/xform/pivot-table/pivot-cache-records-xform.d.ts +2 -2
  543. package/dist/types/modules/excel/xlsx/xform/pivot-table/pivot-table-xform.d.ts +1 -1
  544. package/dist/types/modules/excel/xlsx/xform/sheet/auto-filter-xform.d.ts +1 -1
  545. package/dist/types/modules/excel/xlsx/xform/sheet/cell-xform.d.ts +1 -1
  546. package/dist/types/modules/excel/xlsx/xform/sheet/cf/cf-rule-xform.d.ts +6 -6
  547. package/dist/types/modules/excel/xlsx/xform/sheet/cf/cfvo-xform.d.ts +1 -1
  548. package/dist/types/modules/excel/xlsx/xform/sheet/cf/color-scale-xform.d.ts +3 -3
  549. package/dist/types/modules/excel/xlsx/xform/sheet/cf/conditional-formatting-xform.d.ts +1 -1
  550. package/dist/types/modules/excel/xlsx/xform/sheet/cf/conditional-formattings-xform.d.ts +2 -2
  551. package/dist/types/modules/excel/xlsx/xform/sheet/cf/databar-xform.d.ts +3 -3
  552. package/dist/types/modules/excel/xlsx/xform/sheet/cf/ext-lst-ref-xform.d.ts +1 -1
  553. package/dist/types/modules/excel/xlsx/xform/sheet/cf/formula-xform.d.ts +1 -1
  554. package/dist/types/modules/excel/xlsx/xform/sheet/cf/icon-set-xform.d.ts +2 -2
  555. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/cf-icon-ext-xform.d.ts +1 -1
  556. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/cf-rule-ext-xform.d.ts +3 -3
  557. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/cfvo-ext-xform.d.ts +2 -2
  558. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/conditional-formatting-ext-xform.d.ts +3 -3
  559. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/conditional-formattings-ext-xform.d.ts +2 -2
  560. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/databar-ext-xform.d.ts +3 -3
  561. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/f-ext-xform.d.ts +1 -1
  562. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/icon-set-ext-xform.d.ts +3 -3
  563. package/dist/types/modules/excel/xlsx/xform/sheet/cf-ext/sqref-ext-xform.d.ts +1 -1
  564. package/dist/types/modules/excel/xlsx/xform/sheet/col-breaks-xform.d.ts +1 -1
  565. package/dist/types/modules/excel/xlsx/xform/sheet/col-xform.d.ts +1 -1
  566. package/dist/types/modules/excel/xlsx/xform/sheet/data-validations-xform.d.ts +1 -1
  567. package/dist/types/modules/excel/xlsx/xform/sheet/dimension-xform.d.ts +1 -1
  568. package/dist/types/modules/excel/xlsx/xform/sheet/drawing-xform.d.ts +1 -1
  569. package/dist/types/modules/excel/xlsx/xform/sheet/ext-lst-xform.d.ts +1 -1
  570. package/dist/types/modules/excel/xlsx/xform/sheet/header-footer-xform.d.ts +1 -1
  571. package/dist/types/modules/excel/xlsx/xform/sheet/hyperlink-xform.d.ts +1 -1
  572. package/dist/types/modules/excel/xlsx/xform/sheet/merge-cell-xform.d.ts +1 -1
  573. package/dist/types/modules/excel/xlsx/xform/sheet/outline-properties-xform.d.ts +1 -1
  574. package/dist/types/modules/excel/xlsx/xform/sheet/page-breaks-xform.d.ts +1 -1
  575. package/dist/types/modules/excel/xlsx/xform/sheet/page-margins-xform.d.ts +1 -1
  576. package/dist/types/modules/excel/xlsx/xform/sheet/page-setup-properties-xform.d.ts +1 -1
  577. package/dist/types/modules/excel/xlsx/xform/sheet/page-setup-xform.d.ts +1 -1
  578. package/dist/types/modules/excel/xlsx/xform/sheet/picture-xform.d.ts +1 -1
  579. package/dist/types/modules/excel/xlsx/xform/sheet/print-options-xform.d.ts +1 -1
  580. package/dist/types/modules/excel/xlsx/xform/sheet/row-breaks-xform.d.ts +1 -1
  581. package/dist/types/modules/excel/xlsx/xform/sheet/row-xform.d.ts +1 -1
  582. package/dist/types/modules/excel/xlsx/xform/sheet/sheet-format-properties-xform.d.ts +1 -1
  583. package/dist/types/modules/excel/xlsx/xform/sheet/sheet-properties-xform.d.ts +1 -1
  584. package/dist/types/modules/excel/xlsx/xform/sheet/sheet-protection-xform.d.ts +1 -1
  585. package/dist/types/modules/excel/xlsx/xform/sheet/sheet-view-xform.d.ts +1 -1
  586. package/dist/types/modules/excel/xlsx/xform/sheet/table-part-xform.d.ts +1 -1
  587. package/dist/types/modules/excel/xlsx/xform/sheet/worksheet-xform.d.ts +1 -1
  588. package/dist/types/modules/excel/xlsx/xform/simple/boolean-xform.d.ts +1 -1
  589. package/dist/types/modules/excel/xlsx/xform/simple/date-xform.d.ts +1 -1
  590. package/dist/types/modules/excel/xlsx/xform/simple/float-xform.d.ts +1 -1
  591. package/dist/types/modules/excel/xlsx/xform/simple/integer-xform.d.ts +1 -1
  592. package/dist/types/modules/excel/xlsx/xform/simple/string-xform.d.ts +1 -1
  593. package/dist/types/modules/excel/xlsx/xform/static-xform.d.ts +1 -1
  594. package/dist/types/modules/excel/xlsx/xform/strings/phonetic-text-xform.d.ts +1 -1
  595. package/dist/types/modules/excel/xlsx/xform/strings/rich-text-xform.d.ts +3 -3
  596. package/dist/types/modules/excel/xlsx/xform/strings/shared-string-xform.d.ts +1 -1
  597. package/dist/types/modules/excel/xlsx/xform/strings/shared-strings-xform.d.ts +2 -2
  598. package/dist/types/modules/excel/xlsx/xform/strings/text-xform.d.ts +1 -1
  599. package/dist/types/modules/excel/xlsx/xform/style/alignment-xform.d.ts +1 -1
  600. package/dist/types/modules/excel/xlsx/xform/style/border-xform.d.ts +2 -2
  601. package/dist/types/modules/excel/xlsx/xform/style/color-xform.d.ts +1 -1
  602. package/dist/types/modules/excel/xlsx/xform/style/dxf-xform.d.ts +1 -1
  603. package/dist/types/modules/excel/xlsx/xform/style/fill-xform.d.ts +2 -2
  604. package/dist/types/modules/excel/xlsx/xform/style/font-xform.d.ts +1 -1
  605. package/dist/types/modules/excel/xlsx/xform/style/numfmt-xform.d.ts +1 -1
  606. package/dist/types/modules/excel/xlsx/xform/style/protection-xform.d.ts +1 -1
  607. package/dist/types/modules/excel/xlsx/xform/style/style-xform.d.ts +3 -3
  608. package/dist/types/modules/excel/xlsx/xform/style/styles-xform.d.ts +2 -2
  609. package/dist/types/modules/excel/xlsx/xform/style/underline-xform.d.ts +1 -1
  610. package/dist/types/modules/excel/xlsx/xform/table/auto-filter-xform.d.ts +2 -2
  611. package/dist/types/modules/excel/xlsx/xform/table/custom-filter-xform.d.ts +1 -1
  612. package/dist/types/modules/excel/xlsx/xform/table/filter-column-xform.d.ts +2 -2
  613. package/dist/types/modules/excel/xlsx/xform/table/filter-xform.d.ts +1 -1
  614. package/dist/types/modules/excel/xlsx/xform/table/table-column-xform.d.ts +1 -1
  615. package/dist/types/modules/excel/xlsx/xform/table/table-style-info-xform.d.ts +1 -1
  616. package/dist/types/modules/excel/xlsx/xform/table/table-xform.d.ts +1 -1
  617. package/dist/types/modules/excel/xlsx/xlsx.browser.d.ts +3 -3
  618. package/dist/types/modules/excel/xlsx/xlsx.d.ts +1 -1
  619. package/dist/types/modules/stream/base-transform.d.ts +1 -1
  620. package/dist/types/modules/stream/buffered-stream.d.ts +1 -1
  621. package/dist/types/modules/stream/index.browser.d.ts +8 -8
  622. package/dist/types/modules/stream/index.d.ts +8 -8
  623. package/dist/types/modules/stream/pull-stream.d.ts +1 -1
  624. package/dist/types/modules/stream/streams.browser.d.ts +4 -4
  625. package/dist/types/modules/stream/streams.d.ts +3 -3
  626. package/dist/types/modules/stream/utils.d.ts +1 -1
  627. package/dist/types/utils/utils.browser.d.ts +1 -1
  628. package/dist/types/utils/utils.d.ts +1 -1
  629. package/package.json +10 -6
  630. package/dist/browser/excelts.esm.js +0 -24621
  631. package/dist/browser/excelts.esm.js.map +0 -1
  632. package/dist/browser/excelts.esm.min.js +0 -148
  633. package/dist/browser/excelts.iife.js.map +0 -1
@@ -0,0 +1,3297 @@
1
+ /**
2
+ * Native Stream Implementation - Browser
3
+ *
4
+ * Uses Web Streams API (ReadableStream, WritableStream, TransformStream)
5
+ * for true native streaming in browsers.
6
+ *
7
+ * Supported browsers:
8
+ * - Chrome >= 89
9
+ * - Firefox >= 102
10
+ * - Safari >= 14.1
11
+ * - Edge >= 89
12
+ */
13
+ import { EventEmitter } from "./event-emitter.js";
14
+ import { PullStream as StandalonePullStream } from "./pull-stream.js";
15
+ import { BufferedStream as StandaloneBufferedStream, StringChunk as StandaloneStringChunk, BufferChunk as StandaloneBufferChunk } from "./buffered-stream.js";
16
+ import { concatUint8Arrays, getTextDecoder, textDecoder } from "./shared.js";
17
+ // =============================================================================
18
+ // Readable Stream Wrapper
19
+ // =============================================================================
20
+ /**
21
+ * A wrapper around Web ReadableStream that provides Node.js-like API
22
+ */
23
+ export class Readable extends EventEmitter {
24
+ constructor(options) {
25
+ super();
26
+ this._reader = null;
27
+ this._buffer = [];
28
+ this._bufferIndex = 0;
29
+ this._unshiftBuffer = [];
30
+ this._bufferSize = 0;
31
+ this._reading = false;
32
+ this._ended = false;
33
+ this._destroyed = false;
34
+ this._errored = null;
35
+ this._closed = false;
36
+ this._paused = true;
37
+ this._flowing = false;
38
+ this._pipeTo = [];
39
+ this._pipeListeners = new Map();
40
+ this._encoding = null;
41
+ this._decoder = null;
42
+ this._didRead = false;
43
+ this._aborted = false;
44
+ // Whether this stream uses push() mode (true) or Web Stream mode (false)
45
+ this._pushMode = false;
46
+ // Whether this stream was created from an external Web Stream (true) or is controllable (false)
47
+ this._webStreamMode = false;
48
+ this.objectMode = options?.objectMode ?? false;
49
+ this.readableHighWaterMark = options?.highWaterMark ?? 16384;
50
+ this.autoDestroy = options?.autoDestroy ?? true;
51
+ this.emitClose = options?.emitClose ?? true;
52
+ // Store user-provided read function
53
+ if (options?.read) {
54
+ this._read = options.read.bind(this);
55
+ this._pushMode = true; // User will call push()
56
+ }
57
+ if (options?.stream) {
58
+ this._stream = options.stream;
59
+ this._webStreamMode = true; // Created from external Web Stream
60
+ }
61
+ else {
62
+ // Create a controllable stream
63
+ let controller;
64
+ this._stream = new ReadableStream({
65
+ start: ctrl => {
66
+ controller = ctrl;
67
+ },
68
+ pull: async () => {
69
+ // Signal that more data can be pushed
70
+ this.emit("drain");
71
+ },
72
+ cancel: reason => {
73
+ this._ended = true;
74
+ this._aborted = true;
75
+ if (this.emitClose) {
76
+ this.emit("close");
77
+ }
78
+ }
79
+ });
80
+ // Expose controller for push/end
81
+ this._controller = controller;
82
+ }
83
+ }
84
+ /**
85
+ * Create a Readable from an iterable (static factory method)
86
+ */
87
+ static from(iterable, options) {
88
+ const readable = new Readable({ ...options, objectMode: options?.objectMode ?? true });
89
+ (async () => {
90
+ try {
91
+ for await (const chunk of iterable) {
92
+ if (!readable.push(chunk)) {
93
+ // Backpressure
94
+ await new Promise(resolve => setTimeout(resolve, 0));
95
+ }
96
+ }
97
+ readable.push(null);
98
+ }
99
+ catch (err) {
100
+ readable.destroy(err);
101
+ }
102
+ })();
103
+ return readable;
104
+ }
105
+ /**
106
+ * Check if a stream has been disturbed (read from)
107
+ */
108
+ static isDisturbed(stream) {
109
+ return stream._didRead || stream._ended || stream._destroyed;
110
+ }
111
+ /**
112
+ * Convert a Web ReadableStream to Node.js Readable
113
+ */
114
+ static fromWeb(webStream, options) {
115
+ return new Readable({ ...options, stream: webStream });
116
+ }
117
+ /**
118
+ * Convert a Node.js Readable to Web ReadableStream
119
+ */
120
+ static toWeb(nodeStream) {
121
+ return nodeStream.webStream;
122
+ }
123
+ /**
124
+ * Push data to the stream (when using controllable stream)
125
+ */
126
+ push(chunk) {
127
+ if (this._destroyed) {
128
+ return false;
129
+ }
130
+ // Mark as push mode when push() is called
131
+ this._pushMode = true;
132
+ const controller = this._controller;
133
+ if (chunk === null) {
134
+ // Prevent duplicate end handling
135
+ if (this._ended) {
136
+ return false;
137
+ }
138
+ this._ended = true;
139
+ if (controller) {
140
+ try {
141
+ controller.close();
142
+ }
143
+ catch {
144
+ // Controller may already be closed
145
+ }
146
+ }
147
+ this.emit("end");
148
+ // Note: Don't call destroy() here, let the stream be consumed naturally
149
+ // The reader will return done:true when it finishes reading
150
+ return false;
151
+ }
152
+ if (this._flowing) {
153
+ // In flowing mode, emit data directly without buffering or enqueueing
154
+ // const chunkStr = chunk instanceof Uint8Array ? new TextDecoder().decode(chunk.slice(0, 50)) : String(chunk).slice(0, 50);
155
+ // console.log(`[Readable#${this._id}.push FLOWING] emit data size:${(chunk as any).length || (chunk as any).byteLength} start:"${chunkStr}"`);
156
+ this.emit("data", chunk);
157
+ // Check if stream was paused during emit (backpressure from consumer)
158
+ if (!this._flowing) {
159
+ return false;
160
+ }
161
+ // After emitting data, call _read again if available (Node.js behavior)
162
+ if (this._read && !this._ended) {
163
+ queueMicrotask(() => {
164
+ if (this._flowing && !this._ended && !this._destroyed) {
165
+ this._read(this.readableHighWaterMark);
166
+ }
167
+ });
168
+ }
169
+ // In flowing mode, return true (no backpressure since data is immediately consumed)
170
+ return true;
171
+ }
172
+ else {
173
+ // In paused mode, buffer for later
174
+ const wasEmpty = this._bufferedLength() === 0;
175
+ // const chunkStrBuf = chunk instanceof Uint8Array ? new TextDecoder().decode((chunk as Uint8Array).slice(0, 50)) : String(chunk).slice(0, 50);
176
+ // console.log(`[Readable#${this._id}.push PAUSED->BUFFER] buffer len:${this._buffer.length}->${this._buffer.length + 1} start:"${chunkStrBuf}"`);
177
+ this._buffer.push(chunk);
178
+ if (!this.objectMode) {
179
+ this._bufferSize += this._getChunkSize(chunk);
180
+ }
181
+ // NOTE: Do NOT enqueue to Web Stream controller here!
182
+ // In push mode, _buffer is the only source of data for data events.
183
+ // Web Stream is only used for async iteration when not in push mode.
184
+ // Enqueueing here would cause data duplication when _startReading is also running.
185
+ // Emit readable event when buffer goes from empty to having data
186
+ if (wasEmpty) {
187
+ queueMicrotask(() => this.emit("readable"));
188
+ }
189
+ // Return false if buffer exceeds high water mark (backpressure signal)
190
+ // Fast path for object mode - just count items
191
+ if (this.objectMode) {
192
+ return this._bufferedLength() < this.readableHighWaterMark;
193
+ }
194
+ // For binary mode, use tracked buffer size (O(1))
195
+ return this._bufferSize < this.readableHighWaterMark;
196
+ }
197
+ }
198
+ /**
199
+ * Put a chunk back at the front of the buffer
200
+ * Note: unshift is allowed even after end, as it's used to put back already read data
201
+ */
202
+ unshift(chunk) {
203
+ if (this._destroyed) {
204
+ return;
205
+ }
206
+ this._bufferUnshift(chunk);
207
+ if (!this.objectMode) {
208
+ this._bufferSize += this._getChunkSize(chunk);
209
+ }
210
+ }
211
+ /**
212
+ * Read data from the stream
213
+ */
214
+ read(size) {
215
+ this._didRead = true;
216
+ if (this._bufferedLength() > 0) {
217
+ if (this.objectMode || size === undefined) {
218
+ const chunk = this._bufferShift();
219
+ if (!this.objectMode) {
220
+ this._bufferSize -= this._getChunkSize(chunk);
221
+ }
222
+ return this._applyEncoding(chunk);
223
+ }
224
+ // For binary mode, handle size
225
+ const chunk = this._bufferShift();
226
+ if (!this.objectMode) {
227
+ this._bufferSize -= this._getChunkSize(chunk);
228
+ }
229
+ return this._applyEncoding(chunk);
230
+ }
231
+ return null;
232
+ }
233
+ _bufferedLength() {
234
+ return this._unshiftBuffer.length + (this._buffer.length - this._bufferIndex);
235
+ }
236
+ _bufferPeek() {
237
+ const unshiftLen = this._unshiftBuffer.length;
238
+ if (unshiftLen > 0) {
239
+ return this._unshiftBuffer[unshiftLen - 1];
240
+ }
241
+ return this._bufferIndex < this._buffer.length ? this._buffer[this._bufferIndex] : null;
242
+ }
243
+ _bufferShift() {
244
+ if (this._unshiftBuffer.length > 0) {
245
+ return this._unshiftBuffer.pop();
246
+ }
247
+ const chunk = this._buffer[this._bufferIndex++];
248
+ // Fast reset when emptied
249
+ if (this._bufferIndex === this._buffer.length) {
250
+ this._buffer.length = 0;
251
+ this._bufferIndex = 0;
252
+ return chunk;
253
+ }
254
+ // Occasionally compact to avoid unbounded growth of the unused prefix
255
+ if (this._bufferIndex > 1024 && this._bufferIndex * 2 > this._buffer.length) {
256
+ this._buffer = this._buffer.slice(this._bufferIndex);
257
+ this._bufferIndex = 0;
258
+ }
259
+ return chunk;
260
+ }
261
+ _bufferUnshift(chunk) {
262
+ if (this._bufferIndex === 0) {
263
+ // Avoid O(n) Array.unshift() by using a small front stack.
264
+ // Semantics: last unshifted chunk is returned first.
265
+ this._unshiftBuffer.push(chunk);
266
+ return;
267
+ }
268
+ this._bufferIndex--;
269
+ this._buffer[this._bufferIndex] = chunk;
270
+ }
271
+ _getChunkSize(chunk) {
272
+ // Keep semantics aligned with previous implementation:
273
+ // - Uint8Array counts by byteLength
274
+ // - other types count as 1
275
+ return chunk instanceof Uint8Array ? chunk.byteLength : 1;
276
+ }
277
+ /**
278
+ * Set encoding for string output
279
+ */
280
+ setEncoding(encoding) {
281
+ this._encoding = encoding;
282
+ // Fast path: reuse cached utf-8 decoder; otherwise lazy-create on first decode.
283
+ if (encoding === "utf-8" || encoding === "utf8") {
284
+ this._decoder = textDecoder;
285
+ }
286
+ else {
287
+ this._decoder = null;
288
+ }
289
+ return this;
290
+ }
291
+ _applyEncoding(chunk) {
292
+ if (this._encoding && chunk instanceof Uint8Array) {
293
+ // Use cached decoder instances (module-level for utf-8, cached per encoding otherwise).
294
+ if (!this._decoder) {
295
+ this._decoder = getTextDecoder(this._encoding);
296
+ }
297
+ return this._decoder.decode(chunk);
298
+ }
299
+ return chunk;
300
+ }
301
+ /**
302
+ * Wrap an old-style stream
303
+ */
304
+ wrap(stream) {
305
+ stream.on("data", (chunk) => {
306
+ if (!this.push(chunk)) {
307
+ stream.pause();
308
+ }
309
+ });
310
+ stream.on("end", () => this.push(null));
311
+ stream.on("error", (err) => this.destroy(err));
312
+ stream.on("close", () => this.destroy());
313
+ return this;
314
+ }
315
+ /**
316
+ * Pause the stream
317
+ */
318
+ pause() {
319
+ this._paused = true;
320
+ this._flowing = false;
321
+ return this;
322
+ }
323
+ /**
324
+ * Resume the stream
325
+ */
326
+ resume() {
327
+ this._paused = false;
328
+ this._flowing = true;
329
+ // Emit any buffered data first
330
+ while (this._bufferedLength() > 0 && this._flowing) {
331
+ const chunk = this._bufferShift();
332
+ if (!this.objectMode) {
333
+ this._bufferSize -= this._getChunkSize(chunk);
334
+ }
335
+ this.emit("data", chunk);
336
+ }
337
+ // If already ended, emit end event
338
+ if (this._ended && this._bufferedLength() === 0) {
339
+ this.emit("end");
340
+ }
341
+ else if (this._read) {
342
+ // Call user-provided read function asynchronously
343
+ // This allows multiple pipe() calls to register before data flows
344
+ queueMicrotask(() => {
345
+ if (this._flowing && !this._ended && !this._destroyed) {
346
+ this._read(this.readableHighWaterMark);
347
+ }
348
+ });
349
+ }
350
+ else if (this._webStreamMode && !this._pushMode) {
351
+ // Only start reading from underlying Web Stream if:
352
+ // 1. Stream was created from external Web Stream (_webStreamMode)
353
+ // 2. Not in push mode (no one called push() yet)
354
+ this._startReading();
355
+ }
356
+ return this;
357
+ }
358
+ /**
359
+ * Override on() to automatically resume when 'data' listener is added
360
+ * This matches Node.js behavior where adding a 'data' listener puts
361
+ * the stream into flowing mode.
362
+ */
363
+ on(event, listener) {
364
+ super.on(event, listener);
365
+ // When a 'data' listener is added, switch to flowing mode
366
+ if (event === "data") {
367
+ this.resume();
368
+ }
369
+ return this;
370
+ }
371
+ /**
372
+ * Check if paused
373
+ */
374
+ isPaused() {
375
+ return this._paused;
376
+ }
377
+ /**
378
+ * Pipe to a writable stream, transform stream, or duplex stream
379
+ */
380
+ pipe(destination) {
381
+ // IMPORTANT:
382
+ // Do not rely on `instanceof` here.
383
+ // In bundled/minified builds, multiple copies of this module can exist,
384
+ // causing `instanceof Transform/Writable/Duplex` to fail even when the object
385
+ // is a valid destination.
386
+ const dest = destination;
387
+ // Get the actual writable target.
388
+ // Prefer internal `_writable` (Transform/Duplex wrappers), else treat the destination as writable-like.
389
+ const candidate = dest?._writable ?? dest;
390
+ const hasWrite = typeof candidate?.write === "function";
391
+ const hasEnd = typeof candidate?.end === "function";
392
+ const hasOn = typeof candidate?.on === "function";
393
+ const hasOnce = typeof candidate?.once === "function";
394
+ const hasOff = typeof candidate?.off === "function";
395
+ if (!hasWrite || !hasEnd || (!hasOnce && !hasOn) || (!hasOff && !candidate?.removeListener)) {
396
+ throw new Error("Readable.pipe: invalid destination");
397
+ }
398
+ const target = candidate;
399
+ this._pipeTo.push(target);
400
+ // Create listeners that we can later remove
401
+ const dataListener = (chunk) => {
402
+ const canWrite = target.write(chunk);
403
+ if (!canWrite) {
404
+ this.pause();
405
+ if (typeof target.once === "function") {
406
+ target.once("drain", () => this.resume());
407
+ }
408
+ else {
409
+ const resumeOnce = () => {
410
+ if (typeof target.off === "function") {
411
+ target.off("drain", resumeOnce);
412
+ }
413
+ else if (typeof target.removeListener === "function") {
414
+ target.removeListener("drain", resumeOnce);
415
+ }
416
+ this.resume();
417
+ };
418
+ target.on("drain", resumeOnce);
419
+ }
420
+ }
421
+ };
422
+ const endListener = () => {
423
+ target.end();
424
+ };
425
+ const errorListener = (err) => {
426
+ if (typeof target.destroy === "function") {
427
+ target.destroy(err);
428
+ }
429
+ else {
430
+ // Best-effort: forward error to the destination if it supports events.
431
+ target.emit?.("error", err);
432
+ }
433
+ };
434
+ // Store listeners for later removal in unpipe
435
+ this._pipeListeners.set(target, {
436
+ data: dataListener,
437
+ end: endListener,
438
+ error: errorListener
439
+ });
440
+ this.on("data", dataListener);
441
+ this.once("end", endListener);
442
+ this.once("error", errorListener);
443
+ this.resume();
444
+ return destination;
445
+ }
446
+ /**
447
+ * Unpipe from destination
448
+ */
449
+ unpipe(destination) {
450
+ if (destination) {
451
+ const idx = this._pipeTo.indexOf(destination);
452
+ if (idx !== -1) {
453
+ this._pipeTo.splice(idx, 1);
454
+ }
455
+ // Remove the listeners
456
+ const listeners = this._pipeListeners.get(destination);
457
+ if (listeners) {
458
+ this.off("data", listeners.data);
459
+ this.off("end", listeners.end);
460
+ this.off("error", listeners.error);
461
+ this._pipeListeners.delete(destination);
462
+ }
463
+ }
464
+ else {
465
+ // Unpipe all
466
+ for (const target of this._pipeTo) {
467
+ const listeners = this._pipeListeners.get(target);
468
+ if (listeners) {
469
+ this.off("data", listeners.data);
470
+ this.off("end", listeners.end);
471
+ this.off("error", listeners.error);
472
+ this._pipeListeners.delete(target);
473
+ }
474
+ }
475
+ this._pipeTo = [];
476
+ }
477
+ // Pause the stream after unpipe
478
+ this.pause();
479
+ return this;
480
+ }
481
+ /**
482
+ * Destroy the stream
483
+ */
484
+ destroy(error) {
485
+ if (this._destroyed) {
486
+ return this;
487
+ }
488
+ this._destroyed = true;
489
+ this._ended = true;
490
+ if (error) {
491
+ this._errored = error;
492
+ this.emit("error", error);
493
+ }
494
+ if (this._reader) {
495
+ this._reader.cancel().catch(() => { });
496
+ }
497
+ this._closed = true;
498
+ this.emit("close");
499
+ return this;
500
+ }
501
+ /**
502
+ * Get the underlying Web ReadableStream
503
+ */
504
+ get webStream() {
505
+ return this._stream;
506
+ }
507
+ get readable() {
508
+ return !this._destroyed && !this._ended;
509
+ }
510
+ get readableEnded() {
511
+ return this._ended;
512
+ }
513
+ get readableLength() {
514
+ return this._bufferedLength();
515
+ }
516
+ /** Whether the stream has been destroyed */
517
+ get destroyed() {
518
+ return this._destroyed;
519
+ }
520
+ /** The error that destroyed the stream, or null */
521
+ get errored() {
522
+ return this._errored;
523
+ }
524
+ /** Whether the stream has been closed */
525
+ get closed() {
526
+ return this._closed;
527
+ }
528
+ /** Whether the stream is in flowing mode */
529
+ get readableFlowing() {
530
+ if (!this._paused && !this._ended) {
531
+ return this._flowing;
532
+ }
533
+ return this._flowing ? true : null;
534
+ }
535
+ /** Whether the stream was aborted */
536
+ get readableAborted() {
537
+ return this._aborted;
538
+ }
539
+ /** Whether read() has ever been called */
540
+ get readableDidRead() {
541
+ return this._didRead;
542
+ }
543
+ /** Current encoding or null */
544
+ get readableEncoding() {
545
+ return this._encoding;
546
+ }
547
+ /** Returns array of objects containing info about buffered data */
548
+ get readableObjectMode() {
549
+ return this.objectMode;
550
+ }
551
+ /**
552
+ * Get the internal buffer state (for debugging)
553
+ * Returns array of objects with length and chunk info
554
+ */
555
+ get readableBuffer() {
556
+ return {
557
+ length: this._bufferedLength(),
558
+ head: this._bufferPeek()
559
+ };
560
+ }
561
+ async _startReading() {
562
+ if (this._reading || this._destroyed || !this._flowing) {
563
+ return;
564
+ }
565
+ this._reading = true;
566
+ try {
567
+ if (!this._reader) {
568
+ this._reader = this._stream.getReader();
569
+ }
570
+ while (this._flowing && !this._destroyed && !this._pushMode) {
571
+ const { done, value } = await this._reader.read();
572
+ // Check _pushMode again after async read - if push() was called, stop reading
573
+ if (this._pushMode) {
574
+ break;
575
+ }
576
+ if (done) {
577
+ this._ended = true;
578
+ this.emit("end");
579
+ break;
580
+ }
581
+ if (value !== undefined) {
582
+ // In flowing mode, emit data directly without buffering
583
+ // Only buffer if not flowing (paused mode)
584
+ if (this._flowing) {
585
+ this.emit("data", value);
586
+ }
587
+ else {
588
+ this._buffer.push(value);
589
+ if (!this.objectMode) {
590
+ this._bufferSize += this._getChunkSize(value);
591
+ }
592
+ }
593
+ }
594
+ }
595
+ }
596
+ catch (err) {
597
+ this.emit("error", err);
598
+ }
599
+ finally {
600
+ this._reading = false;
601
+ }
602
+ }
603
+ /**
604
+ * Async iterator support
605
+ * Uses Web Stream reader for non-push mode, event-based for push mode
606
+ */
607
+ async *[Symbol.asyncIterator]() {
608
+ // First yield any buffered data
609
+ while (this._bufferedLength() > 0) {
610
+ const chunk = this._bufferShift();
611
+ if (!this.objectMode) {
612
+ this._bufferSize -= this._getChunkSize(chunk);
613
+ }
614
+ yield chunk;
615
+ }
616
+ // If already ended, we're done
617
+ if (this._ended) {
618
+ return;
619
+ }
620
+ // For controllable streams (not created from external Web Stream),
621
+ // use event-based iteration since data comes from push() calls
622
+ if (!this._webStreamMode) {
623
+ // Create a promise-based queue for incoming data
624
+ const dataQueue = [];
625
+ let resolveNext = null;
626
+ let rejectNext = null;
627
+ let done = false;
628
+ let streamError = null;
629
+ let dataQueueIndex = 0;
630
+ const dataHandler = (chunk) => {
631
+ if (resolveNext) {
632
+ resolveNext(chunk);
633
+ resolveNext = null;
634
+ rejectNext = null;
635
+ }
636
+ else {
637
+ dataQueue.push(chunk);
638
+ }
639
+ };
640
+ const endHandler = () => {
641
+ done = true;
642
+ if (resolveNext) {
643
+ resolveNext(null);
644
+ resolveNext = null;
645
+ rejectNext = null;
646
+ }
647
+ };
648
+ const errorHandler = (err) => {
649
+ done = true;
650
+ streamError = err;
651
+ if (rejectNext) {
652
+ rejectNext(err);
653
+ resolveNext = null;
654
+ rejectNext = null;
655
+ }
656
+ };
657
+ const closeHandler = () => {
658
+ // If stream closed without end event (e.g., after destroy()),
659
+ // treat it as done
660
+ done = true;
661
+ if (resolveNext) {
662
+ resolveNext(null);
663
+ resolveNext = null;
664
+ rejectNext = null;
665
+ }
666
+ };
667
+ this.on("data", dataHandler);
668
+ this.on("end", endHandler);
669
+ this.on("error", errorHandler);
670
+ this.on("close", closeHandler);
671
+ try {
672
+ // Enter flowing mode
673
+ this.resume();
674
+ while (!done || dataQueueIndex < dataQueue.length) {
675
+ // Check for error before processing
676
+ if (streamError) {
677
+ throw streamError;
678
+ }
679
+ if (dataQueueIndex < dataQueue.length) {
680
+ const chunk = dataQueue[dataQueueIndex++];
681
+ if (dataQueueIndex >= 1024 && dataQueueIndex * 2 >= dataQueue.length) {
682
+ dataQueue.splice(0, dataQueueIndex);
683
+ dataQueueIndex = 0;
684
+ }
685
+ yield chunk;
686
+ }
687
+ else if (!done) {
688
+ const chunk = await new Promise((resolve, reject) => {
689
+ resolveNext = resolve;
690
+ rejectNext = reject;
691
+ });
692
+ if (chunk !== null) {
693
+ yield chunk;
694
+ }
695
+ }
696
+ }
697
+ // Check for error after loop
698
+ if (streamError) {
699
+ throw streamError;
700
+ }
701
+ }
702
+ finally {
703
+ this.off("data", dataHandler);
704
+ this.off("end", endHandler);
705
+ this.off("error", errorHandler);
706
+ this.off("close", closeHandler);
707
+ }
708
+ return;
709
+ }
710
+ // For Web Stream mode, use the underlying reader
711
+ if (!this._reader) {
712
+ this._reader = this._stream.getReader();
713
+ }
714
+ try {
715
+ while (true) {
716
+ const { done, value } = await this._reader.read();
717
+ if (done) {
718
+ break;
719
+ }
720
+ yield value;
721
+ }
722
+ }
723
+ finally {
724
+ this._reader.releaseLock();
725
+ }
726
+ }
727
+ /**
728
+ * Explicit iterator method (same as Symbol.asyncIterator)
729
+ */
730
+ iterator(options) {
731
+ const destroyOnReturn = options?.destroyOnReturn ?? true;
732
+ const iterator = this[Symbol.asyncIterator]();
733
+ if (!destroyOnReturn) {
734
+ return iterator;
735
+ }
736
+ // Wrap to handle early return
737
+ return {
738
+ next: async () => {
739
+ return iterator.next();
740
+ },
741
+ return: async (value) => {
742
+ this.destroy();
743
+ return { done: true, value };
744
+ },
745
+ [Symbol.asyncIterator]() {
746
+ return this;
747
+ }
748
+ };
749
+ }
750
+ // =========================================================================
751
+ // Async Iterator Helper Methods (Node.js 16.6+)
752
+ // =========================================================================
753
+ /**
754
+ * Map each chunk through an async function
755
+ */
756
+ async *map(fn, options) {
757
+ const signal = options?.signal;
758
+ for await (const chunk of this) {
759
+ if (signal?.aborted) {
760
+ throw new Error("AbortError");
761
+ }
762
+ yield await fn(chunk, { signal });
763
+ }
764
+ }
765
+ /**
766
+ * Filter chunks through an async predicate
767
+ */
768
+ async *filter(fn, options) {
769
+ const signal = options?.signal;
770
+ for await (const chunk of this) {
771
+ if (signal?.aborted) {
772
+ throw new Error("AbortError");
773
+ }
774
+ if (await fn(chunk, { signal })) {
775
+ yield chunk;
776
+ }
777
+ }
778
+ }
779
+ /**
780
+ * FlatMap each chunk
781
+ */
782
+ async *flatMap(fn, options) {
783
+ const signal = options?.signal;
784
+ for await (const chunk of this) {
785
+ if (signal?.aborted) {
786
+ throw new Error("AbortError");
787
+ }
788
+ const result = await fn(chunk, { signal });
789
+ for await (const item of result) {
790
+ yield item;
791
+ }
792
+ }
793
+ }
794
+ /**
795
+ * Take the first n chunks
796
+ */
797
+ async *take(limit, options) {
798
+ const signal = options?.signal;
799
+ let count = 0;
800
+ for await (const chunk of this) {
801
+ if (signal?.aborted) {
802
+ throw new Error("AbortError");
803
+ }
804
+ if (count >= limit) {
805
+ break;
806
+ }
807
+ yield chunk;
808
+ count++;
809
+ }
810
+ }
811
+ /**
812
+ * Drop the first n chunks
813
+ */
814
+ async *drop(limit, options) {
815
+ const signal = options?.signal;
816
+ let count = 0;
817
+ for await (const chunk of this) {
818
+ if (signal?.aborted) {
819
+ throw new Error("AbortError");
820
+ }
821
+ if (count >= limit) {
822
+ yield chunk;
823
+ }
824
+ count++;
825
+ }
826
+ }
827
+ async reduce(fn, initial, options) {
828
+ const signal = options?.signal;
829
+ let accumulator = initial;
830
+ let first = true;
831
+ for await (const chunk of this) {
832
+ if (signal?.aborted) {
833
+ throw new Error("AbortError");
834
+ }
835
+ if (first && accumulator === undefined) {
836
+ accumulator = chunk;
837
+ first = false;
838
+ }
839
+ else {
840
+ accumulator = await fn(accumulator, chunk, { signal });
841
+ }
842
+ }
843
+ if (accumulator === undefined) {
844
+ throw new TypeError("Reduce of empty stream with no initial value");
845
+ }
846
+ return accumulator;
847
+ }
848
+ /**
849
+ * Check if every chunk passes a predicate
850
+ */
851
+ async every(fn, options) {
852
+ const signal = options?.signal;
853
+ for await (const chunk of this) {
854
+ if (signal?.aborted) {
855
+ throw new Error("AbortError");
856
+ }
857
+ if (!(await fn(chunk, { signal }))) {
858
+ return false;
859
+ }
860
+ }
861
+ return true;
862
+ }
863
+ /**
864
+ * Check if some chunk passes a predicate
865
+ */
866
+ async some(fn, options) {
867
+ const signal = options?.signal;
868
+ for await (const chunk of this) {
869
+ if (signal?.aborted) {
870
+ throw new Error("AbortError");
871
+ }
872
+ if (await fn(chunk, { signal })) {
873
+ return true;
874
+ }
875
+ }
876
+ return false;
877
+ }
878
+ /**
879
+ * Find first chunk that passes predicate
880
+ */
881
+ async find(fn, options) {
882
+ const signal = options?.signal;
883
+ for await (const chunk of this) {
884
+ if (signal?.aborted) {
885
+ throw new Error("AbortError");
886
+ }
887
+ if (await fn(chunk, { signal })) {
888
+ return chunk;
889
+ }
890
+ }
891
+ return undefined;
892
+ }
893
+ /**
894
+ * Execute function for each chunk (like forEach)
895
+ */
896
+ async forEach(fn, options) {
897
+ const signal = options?.signal;
898
+ for await (const chunk of this) {
899
+ if (signal?.aborted) {
900
+ throw new Error("AbortError");
901
+ }
902
+ await fn(chunk, { signal });
903
+ }
904
+ }
905
+ /**
906
+ * Collect all chunks into an array
907
+ */
908
+ async toArray(options) {
909
+ const signal = options?.signal;
910
+ const result = [];
911
+ for await (const chunk of this) {
912
+ if (signal?.aborted) {
913
+ throw new Error("AbortError");
914
+ }
915
+ result.push(chunk);
916
+ }
917
+ return result;
918
+ }
919
+ /**
920
+ * Yield [index, value] pairs
921
+ */
922
+ async *asIndexedPairs(options) {
923
+ const signal = options?.signal;
924
+ let index = 0;
925
+ for await (const chunk of this) {
926
+ if (signal?.aborted) {
927
+ throw new Error("AbortError");
928
+ }
929
+ yield [index++, chunk];
930
+ }
931
+ }
932
+ compose(stream) {
933
+ if (typeof stream === "function") {
934
+ // It's an async generator function
935
+ const output = stream(this);
936
+ return Readable.from(output);
937
+ }
938
+ // It's a Duplex stream
939
+ this.pipe(stream);
940
+ return stream;
941
+ }
942
+ }
943
+ // =============================================================================
944
+ // Writable Stream Wrapper
945
+ // =============================================================================
946
+ /**
947
+ * A wrapper around Web WritableStream that provides Node.js-like API
948
+ */
949
+ export class Writable extends EventEmitter {
950
+ constructor(options) {
951
+ super();
952
+ this._writer = null;
953
+ this._ended = false;
954
+ this._finished = false;
955
+ this._destroyed = false;
956
+ this._errored = null;
957
+ this._closed = false;
958
+ this._pendingWrites = 0;
959
+ this._writableLength = 0;
960
+ this._corked = 0;
961
+ this._corkedChunks = [];
962
+ this._defaultEncoding = "utf8";
963
+ this._aborted = false;
964
+ this.objectMode = options?.objectMode ?? false;
965
+ this.writableHighWaterMark = options?.highWaterMark ?? 16384;
966
+ this.autoDestroy = options?.autoDestroy ?? true;
967
+ this.emitClose = options?.emitClose ?? true;
968
+ this._defaultEncoding = options?.defaultEncoding ?? "utf8";
969
+ // Store user-provided write function
970
+ if (options?.write) {
971
+ this._writeFunc = options.write.bind(this);
972
+ }
973
+ // Store user-provided final function
974
+ if (options?.final) {
975
+ this._finalFunc = options.final.bind(this);
976
+ }
977
+ if (options?.stream) {
978
+ this._stream = options.stream;
979
+ }
980
+ else {
981
+ // Create bound references to instance properties/methods for use in WritableStream callbacks
982
+ const getWriteFunc = () => this._writeFunc;
983
+ const getFinalFunc = () => this._finalFunc;
984
+ const getDefaultEncoding = () => this._defaultEncoding;
985
+ const setFinished = (value) => {
986
+ this._finished = value;
987
+ };
988
+ const setAborted = (value) => {
989
+ this._aborted = value;
990
+ };
991
+ const emitEvent = this.emit.bind(this);
992
+ const getEmitClose = () => this.emitClose;
993
+ const callWrite = (chunk) => this._write?.(chunk);
994
+ this._stream = new WritableStream({
995
+ write: async (chunk) => {
996
+ // Use user-provided write function or default behavior
997
+ const writeFunc = getWriteFunc();
998
+ if (writeFunc) {
999
+ await new Promise((resolve, reject) => {
1000
+ writeFunc(chunk, getDefaultEncoding(), err => {
1001
+ if (err) {
1002
+ reject(err);
1003
+ }
1004
+ else {
1005
+ resolve();
1006
+ }
1007
+ });
1008
+ });
1009
+ }
1010
+ else {
1011
+ // Override this in subclasses
1012
+ callWrite(chunk);
1013
+ }
1014
+ },
1015
+ close: async () => {
1016
+ // Call final function if provided
1017
+ const finalFunc = getFinalFunc();
1018
+ if (finalFunc) {
1019
+ await new Promise((resolve, reject) => {
1020
+ finalFunc(err => {
1021
+ if (err) {
1022
+ reject(err);
1023
+ }
1024
+ else {
1025
+ resolve();
1026
+ }
1027
+ });
1028
+ });
1029
+ }
1030
+ setFinished(true);
1031
+ emitEvent("finish");
1032
+ if (getEmitClose()) {
1033
+ emitEvent("close");
1034
+ }
1035
+ },
1036
+ abort: reason => {
1037
+ setAborted(true);
1038
+ emitEvent("error", reason);
1039
+ }
1040
+ });
1041
+ }
1042
+ }
1043
+ /**
1044
+ * Set default encoding for string writes
1045
+ */
1046
+ setDefaultEncoding(encoding) {
1047
+ this._defaultEncoding = encoding;
1048
+ return this;
1049
+ }
1050
+ /**
1051
+ * Buffer writes until uncork() is called
1052
+ */
1053
+ cork() {
1054
+ this._corked++;
1055
+ }
1056
+ /**
1057
+ * Flush buffered writes from cork()
1058
+ */
1059
+ uncork() {
1060
+ if (this._corked > 0) {
1061
+ this._corked--;
1062
+ }
1063
+ if (this._corked === 0) {
1064
+ // Flush all corked chunks
1065
+ const chunks = this._corkedChunks;
1066
+ this._corkedChunks = [];
1067
+ for (const { chunk, callback } of chunks) {
1068
+ this._doWrite(chunk, callback);
1069
+ }
1070
+ }
1071
+ }
1072
+ write(chunk, encodingOrCallback, callback) {
1073
+ if (this._destroyed || this._ended) {
1074
+ const err = new Error("Cannot write after stream destroyed/ended");
1075
+ const cb = typeof encodingOrCallback === "function" ? encodingOrCallback : callback;
1076
+ cb?.(err);
1077
+ return false;
1078
+ }
1079
+ const cb = typeof encodingOrCallback === "function" ? encodingOrCallback : callback;
1080
+ // If corked, buffer the write
1081
+ if (this._corked > 0) {
1082
+ this._corkedChunks.push({ chunk, callback: cb });
1083
+ const chunkSize = this._getChunkSize(chunk);
1084
+ this._writableLength += chunkSize;
1085
+ return this._writableLength < this.writableHighWaterMark;
1086
+ }
1087
+ return this._doWrite(chunk, cb);
1088
+ }
1089
+ _doWrite(chunk, callback) {
1090
+ // Track pending writes for writableLength
1091
+ const chunkSize = this._getChunkSize(chunk);
1092
+ this._pendingWrites++;
1093
+ this._writableLength += chunkSize;
1094
+ this._getWriter()
1095
+ .write(chunk)
1096
+ .then(() => {
1097
+ this._pendingWrites--;
1098
+ this._writableLength -= chunkSize;
1099
+ this.emit("drain");
1100
+ callback?.(null);
1101
+ })
1102
+ .catch(err => {
1103
+ this._pendingWrites--;
1104
+ this._writableLength -= chunkSize;
1105
+ this.emit("error", err);
1106
+ callback?.(err);
1107
+ });
1108
+ // Return false if we've exceeded high water mark (for backpressure)
1109
+ return this._writableLength < this.writableHighWaterMark;
1110
+ }
1111
+ _getChunkSize(chunk) {
1112
+ if (this.objectMode) {
1113
+ return 1;
1114
+ }
1115
+ if (chunk instanceof Uint8Array) {
1116
+ return chunk.byteLength;
1117
+ }
1118
+ if (typeof chunk === "string") {
1119
+ return chunk.length;
1120
+ }
1121
+ return 0;
1122
+ }
1123
+ end(chunkOrCallback, encodingOrCallback, callback) {
1124
+ if (this._ended) {
1125
+ return this;
1126
+ }
1127
+ this._ended = true;
1128
+ const chunk = typeof chunkOrCallback !== "function" ? chunkOrCallback : undefined;
1129
+ const cb = typeof chunkOrCallback === "function"
1130
+ ? chunkOrCallback
1131
+ : typeof encodingOrCallback === "function"
1132
+ ? encodingOrCallback
1133
+ : callback;
1134
+ const finish = async () => {
1135
+ try {
1136
+ if (chunk !== undefined) {
1137
+ await this._getWriter().write(chunk);
1138
+ }
1139
+ await this._getWriter().close();
1140
+ this._finished = true;
1141
+ this.emit("finish");
1142
+ if (cb) {
1143
+ cb();
1144
+ }
1145
+ }
1146
+ catch (err) {
1147
+ this.emit("error", err);
1148
+ }
1149
+ };
1150
+ finish();
1151
+ return this;
1152
+ }
1153
+ /**
1154
+ * Destroy the stream
1155
+ */
1156
+ destroy(error) {
1157
+ if (this._destroyed) {
1158
+ return this;
1159
+ }
1160
+ this._destroyed = true;
1161
+ this._ended = true;
1162
+ if (error) {
1163
+ this._errored = error;
1164
+ this.emit("error", error);
1165
+ }
1166
+ if (this._writer) {
1167
+ this._writer.abort(error).catch(() => { });
1168
+ }
1169
+ this._closed = true;
1170
+ this.emit("close");
1171
+ return this;
1172
+ }
1173
+ /**
1174
+ * Get the underlying Web WritableStream
1175
+ */
1176
+ get webStream() {
1177
+ return this._stream;
1178
+ }
1179
+ get writable() {
1180
+ return !this._destroyed && !this._ended;
1181
+ }
1182
+ get writableEnded() {
1183
+ return this._ended;
1184
+ }
1185
+ get writableFinished() {
1186
+ return this._finished;
1187
+ }
1188
+ get writableLength() {
1189
+ return this._writableLength;
1190
+ }
1191
+ /** Whether the stream has been destroyed */
1192
+ get destroyed() {
1193
+ return this._destroyed;
1194
+ }
1195
+ /** The error that destroyed the stream, or null */
1196
+ get errored() {
1197
+ return this._errored;
1198
+ }
1199
+ /** Whether the stream has been closed */
1200
+ get closed() {
1201
+ return this._closed;
1202
+ }
1203
+ /** Whether the stream needs drain (writableLength exceeds high water mark) */
1204
+ get writableNeedDrain() {
1205
+ return this._writableLength >= this.writableHighWaterMark;
1206
+ }
1207
+ /** How many times cork() has been called without uncork() */
1208
+ get writableCorked() {
1209
+ return this._corked;
1210
+ }
1211
+ /** Whether the stream was aborted */
1212
+ get writableAborted() {
1213
+ return this._aborted;
1214
+ }
1215
+ /** Whether the stream is in object mode */
1216
+ get writableObjectMode() {
1217
+ return this.objectMode;
1218
+ }
1219
+ /** Get default encoding */
1220
+ get defaultEncoding() {
1221
+ return this._defaultEncoding;
1222
+ }
1223
+ /**
1224
+ * Get the internal buffer state (for debugging)
1225
+ * Returns array of objects with length and chunk info
1226
+ */
1227
+ get writableBuffer() {
1228
+ return {
1229
+ length: this._corkedChunks.length,
1230
+ head: this._corkedChunks.length > 0 ? this._corkedChunks[0].chunk : null
1231
+ };
1232
+ }
1233
+ /**
1234
+ * Write multiple chunks at once (batch write).
1235
+ * Override in subclass to implement custom batch write logic.
1236
+ */
1237
+ _writev(chunks, callback) {
1238
+ // Default implementation: write each chunk individually
1239
+ let i = 0;
1240
+ const writeNext = () => {
1241
+ if (i >= chunks.length) {
1242
+ callback(null);
1243
+ return;
1244
+ }
1245
+ const { chunk } = chunks[i++];
1246
+ this._doWrite(chunk, err => {
1247
+ if (err) {
1248
+ callback(err);
1249
+ return;
1250
+ }
1251
+ // Continue to next chunk
1252
+ writeNext();
1253
+ });
1254
+ };
1255
+ writeNext();
1256
+ }
1257
+ /**
1258
+ * Batch write multiple chunks
1259
+ */
1260
+ writev(chunks, callback) {
1261
+ if (this._destroyed || this._ended) {
1262
+ const err = new Error("Cannot write after stream destroyed/ended");
1263
+ callback?.(err);
1264
+ return false;
1265
+ }
1266
+ this._writev(chunks, callback ?? (() => { }));
1267
+ // Return backpressure indicator
1268
+ return this._writableLength < this.writableHighWaterMark;
1269
+ }
1270
+ _getWriter() {
1271
+ if (!this._writer) {
1272
+ this._writer = this._stream.getWriter();
1273
+ }
1274
+ return this._writer;
1275
+ }
1276
+ // =========================================================================
1277
+ // Static Methods (Node.js compatibility)
1278
+ // =========================================================================
1279
+ /**
1280
+ * Convert a Web WritableStream to Node.js Writable
1281
+ */
1282
+ static fromWeb(webStream, options) {
1283
+ return new Writable({ ...options, stream: webStream });
1284
+ }
1285
+ /**
1286
+ * Convert a Node.js Writable to Web WritableStream
1287
+ */
1288
+ static toWeb(nodeStream) {
1289
+ return nodeStream.webStream;
1290
+ }
1291
+ }
1292
+ // =============================================================================
1293
+ // Cross-environment stream normalization
1294
+ // =============================================================================
1295
+ /**
1296
+ * Normalize a user-provided writable into this module's Writable.
1297
+ * Keeps Web/Node branching at the stream-module boundary.
1298
+ */
1299
+ export function normalizeWritable(stream) {
1300
+ if (stream instanceof Writable) {
1301
+ return stream;
1302
+ }
1303
+ // Web WritableStream
1304
+ if (stream?.getWriter) {
1305
+ return new Writable({ stream: stream });
1306
+ }
1307
+ // Already a Node-like writable (e.g. StreamBuf)
1308
+ return stream;
1309
+ }
1310
+ // =============================================================================
1311
+ // Transform Stream Wrapper
1312
+ // =============================================================================
1313
+ /**
1314
+ * A wrapper around Web TransformStream that provides Node.js-like API
1315
+ */
1316
+ export class Transform extends EventEmitter {
1317
+ /**
1318
+ * Push data to the readable side (Node.js compatibility)
1319
+ * Can be called from within transform callback
1320
+ */
1321
+ push(chunk) {
1322
+ if (chunk === null) {
1323
+ return false;
1324
+ }
1325
+ if (this._transformController) {
1326
+ // If we're in a transform callback, enqueue directly
1327
+ this._transformController.enqueue(chunk);
1328
+ }
1329
+ else {
1330
+ // Otherwise buffer for later
1331
+ this._pushBuffer.push(chunk);
1332
+ }
1333
+ return true;
1334
+ }
1335
+ constructor(options) {
1336
+ super();
1337
+ this._ended = false;
1338
+ this._destroyed = false;
1339
+ this._errored = false;
1340
+ // Buffer for Node.js style push() calls during transform
1341
+ this._pushBuffer = [];
1342
+ // Controller for enqueueing pushed data (set during transform execution)
1343
+ this._transformController = null;
1344
+ // Buffer for writes that occur after end() but before writable is closed
1345
+ this._pendingEndWrites = [];
1346
+ // Whether end() has been called but writable not yet closed
1347
+ this._endPending = false;
1348
+ // Track if we've already set up data forwarding
1349
+ this._dataForwardingSetup = false;
1350
+ /** @internal - whether we have a data event consumer */
1351
+ this._hasDataConsumer = false;
1352
+ /** @internal - whether we're auto-consuming the readable */
1353
+ this._readableConsuming = false;
1354
+ /** @internal - buffer for auto-consumed data */
1355
+ this._autoConsumedBuffer = [];
1356
+ this._autoConsumedBufferIndex = 0;
1357
+ /** @internal - whether auto-consume has ended */
1358
+ this._autoConsumeEnded = false;
1359
+ /** @internal - promise that resolves when auto-consume finishes */
1360
+ this._autoConsumePromise = null;
1361
+ this.objectMode = options?.objectMode ?? false;
1362
+ const userTransform = options?.transform;
1363
+ const userFlush = options?.flush;
1364
+ // Create bound references for use in TransformStream callbacks
1365
+ const setController = (ctrl) => {
1366
+ this._transformController = ctrl;
1367
+ };
1368
+ const emitEvent = (event, ...args) => {
1369
+ if (event === "error") {
1370
+ // Only emit error once to prevent duplicate events
1371
+ if (this._errored) {
1372
+ return false;
1373
+ }
1374
+ this._errored = true;
1375
+ // Also destroy the writable to prevent further writes
1376
+ this._writable.destroy(args[0]);
1377
+ }
1378
+ return this.emit(event, ...args);
1379
+ };
1380
+ const getInstance = () => this;
1381
+ // Check if subclass overrides _transform (for Node.js compatibility)
1382
+ // We need to check this at runtime since the subclass constructor runs after super()
1383
+ const hasSubclassTransform = () => {
1384
+ // If userTransform was provided in options, use that
1385
+ if (userTransform) {
1386
+ return false;
1387
+ }
1388
+ // Check if _transform is overridden (not the base class no-op)
1389
+ const proto = Object.getPrototypeOf(this);
1390
+ return proto._transform !== Transform.prototype._transform;
1391
+ };
1392
+ const hasSubclassFlush = () => {
1393
+ if (userFlush) {
1394
+ return false;
1395
+ }
1396
+ const proto = Object.getPrototypeOf(this);
1397
+ return proto._flush !== Transform.prototype._flush;
1398
+ };
1399
+ this._stream = new TransformStream({
1400
+ transform: async (chunk, controller) => {
1401
+ // Skip processing if already errored
1402
+ if (this._errored) {
1403
+ return;
1404
+ }
1405
+ try {
1406
+ // Set controller for push() to use
1407
+ setController(controller);
1408
+ // Check for subclass _transform override first
1409
+ if (hasSubclassTransform()) {
1410
+ // Call subclass _transform method (Node.js style)
1411
+ // _transform signature is (chunk, encoding, callback)
1412
+ await new Promise((resolve, reject) => {
1413
+ this._transform(chunk, "utf8", (err, data) => {
1414
+ if (err) {
1415
+ reject(err);
1416
+ }
1417
+ else {
1418
+ if (data !== undefined) {
1419
+ controller.enqueue(data);
1420
+ }
1421
+ resolve();
1422
+ }
1423
+ });
1424
+ });
1425
+ }
1426
+ else if (userTransform) {
1427
+ const transformParamCount = userTransform.length;
1428
+ if (transformParamCount >= 3) {
1429
+ // Node.js style: transform(chunk, encoding, callback)
1430
+ await new Promise((resolve, reject) => {
1431
+ userTransform.call(getInstance(), chunk, "utf8", (err, data) => {
1432
+ if (err) {
1433
+ reject(err);
1434
+ }
1435
+ else {
1436
+ if (data !== undefined) {
1437
+ controller.enqueue(data);
1438
+ }
1439
+ resolve();
1440
+ }
1441
+ });
1442
+ });
1443
+ }
1444
+ else if (transformParamCount === 2) {
1445
+ await new Promise((resolve, reject) => {
1446
+ userTransform.call(getInstance(), chunk, (err, data) => {
1447
+ if (err) {
1448
+ reject(err);
1449
+ }
1450
+ else {
1451
+ if (data !== undefined) {
1452
+ controller.enqueue(data);
1453
+ }
1454
+ resolve();
1455
+ }
1456
+ });
1457
+ });
1458
+ }
1459
+ else {
1460
+ // Simple style: transform(chunk) => result
1461
+ const result = userTransform.call(getInstance(), chunk);
1462
+ if (result && typeof result.then === "function") {
1463
+ const awaitedResult = await result;
1464
+ if (awaitedResult !== undefined) {
1465
+ controller.enqueue(awaitedResult);
1466
+ }
1467
+ }
1468
+ else {
1469
+ if (result !== undefined) {
1470
+ controller.enqueue(result);
1471
+ }
1472
+ }
1473
+ }
1474
+ }
1475
+ else {
1476
+ // Default: pass through
1477
+ controller.enqueue(chunk);
1478
+ }
1479
+ }
1480
+ catch (err) {
1481
+ controller.error(err);
1482
+ emitEvent("error", err);
1483
+ }
1484
+ finally {
1485
+ setController(null);
1486
+ }
1487
+ },
1488
+ flush: async (controller) => {
1489
+ try {
1490
+ setController(controller);
1491
+ // Check for subclass _flush override first
1492
+ if (hasSubclassFlush()) {
1493
+ await new Promise((resolve, reject) => {
1494
+ this._flush((err, data) => {
1495
+ if (err) {
1496
+ reject(err);
1497
+ }
1498
+ else {
1499
+ if (data !== undefined) {
1500
+ controller.enqueue(data);
1501
+ }
1502
+ resolve();
1503
+ }
1504
+ });
1505
+ });
1506
+ }
1507
+ else if (userFlush) {
1508
+ const flushParamCount = userFlush.length;
1509
+ if (flushParamCount >= 1) {
1510
+ // Node.js style: flush(callback)
1511
+ await new Promise((resolve, reject) => {
1512
+ userFlush.call(getInstance(), (err, data) => {
1513
+ if (err) {
1514
+ reject(err);
1515
+ }
1516
+ else {
1517
+ if (data !== undefined) {
1518
+ controller.enqueue(data);
1519
+ }
1520
+ resolve();
1521
+ }
1522
+ });
1523
+ });
1524
+ }
1525
+ else {
1526
+ // Simple style: flush() => result
1527
+ const result = userFlush.call(getInstance());
1528
+ if (result && typeof result.then === "function") {
1529
+ const awaitedResult = await result;
1530
+ if (awaitedResult !== undefined && awaitedResult !== null) {
1531
+ controller.enqueue(awaitedResult);
1532
+ }
1533
+ }
1534
+ else {
1535
+ if (result !== undefined && result !== null) {
1536
+ controller.enqueue(result);
1537
+ }
1538
+ }
1539
+ }
1540
+ }
1541
+ // No flush defined - nothing to do
1542
+ }
1543
+ catch (err) {
1544
+ controller.error(err);
1545
+ emitEvent("error", err);
1546
+ }
1547
+ finally {
1548
+ setController(null);
1549
+ }
1550
+ }
1551
+ });
1552
+ this._readable = new Readable({
1553
+ stream: this._stream.readable,
1554
+ objectMode: this.objectMode
1555
+ });
1556
+ this._writable = new Writable({
1557
+ stream: this._stream.writable,
1558
+ objectMode: this.objectMode
1559
+ });
1560
+ // Forward non-data events (data forwarding is lazy to avoid premature flowing)
1561
+ this._readable.on("end", () => this.emit("end"));
1562
+ // Only forward errors if not already errored (to prevent duplicate events)
1563
+ this._readable.on("error", err => {
1564
+ if (!this._errored) {
1565
+ this._errored = true;
1566
+ this.emit("error", err);
1567
+ }
1568
+ });
1569
+ this._writable.on("finish", () => this.emit("finish"));
1570
+ this._writable.on("drain", () => this.emit("drain"));
1571
+ // Only forward errors if not already errored (to prevent duplicate events)
1572
+ this._writable.on("error", err => {
1573
+ if (!this._errored) {
1574
+ this._errored = true;
1575
+ this.emit("error", err);
1576
+ }
1577
+ });
1578
+ }
1579
+ /**
1580
+ * Override on to start flowing when data listener is added
1581
+ */
1582
+ on(event, listener) {
1583
+ // Set up data forwarding when first external data listener is added
1584
+ if (event === "data" && !this._dataForwardingSetup) {
1585
+ this._dataForwardingSetup = true;
1586
+ this._readable.on("data", data => this.emit("data", data));
1587
+ }
1588
+ super.on(event, listener);
1589
+ // When data listener is added, mark as having consumer
1590
+ // and start the readable in flowing mode
1591
+ if (event === "data") {
1592
+ this._hasDataConsumer = true;
1593
+ this._readable.resume();
1594
+ }
1595
+ return this;
1596
+ }
1597
+ write(chunk, encodingOrCallback, callback) {
1598
+ const cb = typeof encodingOrCallback === "function" ? encodingOrCallback : callback;
1599
+ if (this._destroyed || this._errored) {
1600
+ const err = new Error(this._errored ? "Cannot write after stream errored" : "Cannot write after stream destroyed");
1601
+ queueMicrotask(() => this.emit("error", err));
1602
+ cb?.(err);
1603
+ return false;
1604
+ }
1605
+ // Ensure readable is being consumed to allow transform to execute
1606
+ // This matches Node.js behavior where transform executes immediately on write
1607
+ // Only auto-consume if no explicit consumer (data listener or pipe)
1608
+ if (!this._readableConsuming && !this._hasDataConsumer) {
1609
+ this._readableConsuming = true;
1610
+ this._startAutoConsume();
1611
+ }
1612
+ // If end() was called but writable not yet closed, buffer the write
1613
+ // This allows writes during data event handlers to be processed
1614
+ if (this._endPending) {
1615
+ this._pendingEndWrites.push({ chunk, callback: cb });
1616
+ return true;
1617
+ }
1618
+ return this._writable.write(chunk, cb);
1619
+ }
1620
+ /** @internal - auto-consume readable to allow transform to execute */
1621
+ _startAutoConsume() {
1622
+ this._autoConsumePromise = (async () => {
1623
+ try {
1624
+ for await (const chunk of this._readable) {
1625
+ // Buffer the data for later retrieval
1626
+ this._autoConsumedBuffer.push(chunk);
1627
+ // Also emit data event for listeners
1628
+ this.emit("data", chunk);
1629
+ }
1630
+ this._autoConsumeEnded = true;
1631
+ this.emit("end");
1632
+ }
1633
+ catch (err) {
1634
+ this.emit("error", err);
1635
+ }
1636
+ })();
1637
+ }
1638
+ end(chunkOrCallback, encodingOrCallback, callback) {
1639
+ if (this._ended) {
1640
+ return this;
1641
+ }
1642
+ this._ended = true;
1643
+ this._endPending = true;
1644
+ const chunk = typeof chunkOrCallback === "function" ? undefined : chunkOrCallback;
1645
+ const cb = typeof chunkOrCallback === "function"
1646
+ ? chunkOrCallback
1647
+ : typeof encodingOrCallback === "function"
1648
+ ? encodingOrCallback
1649
+ : callback;
1650
+ if (cb) {
1651
+ this.once("finish", cb);
1652
+ }
1653
+ if (chunk !== undefined) {
1654
+ this._writable.write(chunk);
1655
+ }
1656
+ // Use setTimeout(0) instead of queueMicrotask to ensure all transform
1657
+ // processing and data events complete before we close the writable.
1658
+ // Microtasks run before the TransformStream processes data.
1659
+ setTimeout(() => {
1660
+ // Process any writes that occurred during data events
1661
+ for (const { chunk: pendingChunk, callback } of this._pendingEndWrites) {
1662
+ this._writable.write(pendingChunk, callback);
1663
+ }
1664
+ this._pendingEndWrites = [];
1665
+ this._endPending = false;
1666
+ this._writable.end();
1667
+ }, 0);
1668
+ return this;
1669
+ }
1670
+ /**
1671
+ * Read from the transform stream
1672
+ */
1673
+ read(size) {
1674
+ return this._readable.read(size);
1675
+ }
1676
+ /**
1677
+ * Pipe to another stream (writable, transform, or duplex)
1678
+ */
1679
+ pipe(destination) {
1680
+ // Mark as having consumer to prevent auto-consume conflict
1681
+ this._hasDataConsumer = true;
1682
+ return this._readable.pipe(destination);
1683
+ }
1684
+ /**
1685
+ * Unpipe from destination
1686
+ */
1687
+ unpipe(destination) {
1688
+ this._readable.unpipe(destination);
1689
+ return this;
1690
+ }
1691
+ /**
1692
+ * Check if paused
1693
+ */
1694
+ isPaused() {
1695
+ return this._readable.isPaused();
1696
+ }
1697
+ /**
1698
+ * Resume reading from the readable side
1699
+ */
1700
+ resume() {
1701
+ this._readable.resume();
1702
+ return this;
1703
+ }
1704
+ /**
1705
+ * Pause reading from the readable side
1706
+ */
1707
+ pause() {
1708
+ this._readable.pause();
1709
+ return this;
1710
+ }
1711
+ /**
1712
+ * Destroy the stream
1713
+ */
1714
+ destroy(error) {
1715
+ if (this._destroyed) {
1716
+ return;
1717
+ }
1718
+ this._destroyed = true;
1719
+ this._readable.destroy(error);
1720
+ this._writable.destroy(error);
1721
+ queueMicrotask(() => this.emit("close"));
1722
+ }
1723
+ /**
1724
+ * Get the underlying Web TransformStream
1725
+ */
1726
+ get webStream() {
1727
+ return this._stream;
1728
+ }
1729
+ get readable() {
1730
+ return this._readable.readable;
1731
+ }
1732
+ get writable() {
1733
+ return this._writable.writable;
1734
+ }
1735
+ get readableEnded() {
1736
+ return this._readable.readableEnded;
1737
+ }
1738
+ get writableEnded() {
1739
+ return this._writable.writableEnded;
1740
+ }
1741
+ get writableFinished() {
1742
+ return this._writable.writableFinished;
1743
+ }
1744
+ get readableLength() {
1745
+ return this._readable.readableLength;
1746
+ }
1747
+ get writableLength() {
1748
+ return this._writable.writableLength;
1749
+ }
1750
+ get readableHighWaterMark() {
1751
+ return this._readable.readableHighWaterMark;
1752
+ }
1753
+ get writableHighWaterMark() {
1754
+ return this._writable.writableHighWaterMark;
1755
+ }
1756
+ get readableObjectMode() {
1757
+ return this._readable.readableObjectMode ?? this._readable.objectMode;
1758
+ }
1759
+ get readableFlowing() {
1760
+ return this._readable.readableFlowing;
1761
+ }
1762
+ get destroyed() {
1763
+ return this._destroyed;
1764
+ }
1765
+ /**
1766
+ * Async iterator support
1767
+ */
1768
+ async *[Symbol.asyncIterator]() {
1769
+ // If auto-consume is running, wait for it to finish and use its buffer
1770
+ if (this._autoConsumePromise) {
1771
+ await this._autoConsumePromise;
1772
+ // Yield all buffered data
1773
+ while (this._autoConsumedBufferIndex < this._autoConsumedBuffer.length) {
1774
+ yield this._autoConsumedBuffer[this._autoConsumedBufferIndex++];
1775
+ }
1776
+ // Reset when drained to avoid prefix growth
1777
+ this._autoConsumedBuffer.length = 0;
1778
+ this._autoConsumedBufferIndex = 0;
1779
+ return;
1780
+ }
1781
+ // Otherwise delegate to readable's iterator
1782
+ yield* this._readable[Symbol.asyncIterator]();
1783
+ }
1784
+ // =========================================================================
1785
+ // Static Methods (Node.js compatibility)
1786
+ // =========================================================================
1787
+ /**
1788
+ * Convert a Web TransformStream to Node.js Transform
1789
+ */
1790
+ static fromWeb(webStream, options) {
1791
+ const transform = new Transform(options);
1792
+ // Connect the web stream - set the internal _stream property
1793
+ transform._stream = webStream;
1794
+ // Replace internal streams with the ones from the web stream
1795
+ const newReadable = Readable.fromWeb(webStream.readable, { objectMode: options?.objectMode });
1796
+ const newWritable = Writable.fromWeb(webStream.writable, { objectMode: options?.objectMode });
1797
+ // Remove old event listeners before replacing
1798
+ transform._readable.removeAllListeners();
1799
+ transform._writable.removeAllListeners();
1800
+ transform._readable = newReadable;
1801
+ transform._writable = newWritable;
1802
+ // Re-connect event forwarding
1803
+ newReadable.on("data", (data) => transform.emit("data", data));
1804
+ newReadable.on("end", () => transform.emit("end"));
1805
+ newReadable.on("error", (err) => transform.emit("error", err));
1806
+ newWritable.on("finish", () => transform.emit("finish"));
1807
+ newWritable.on("drain", () => transform.emit("drain"));
1808
+ newWritable.on("error", (err) => transform.emit("error", err));
1809
+ return transform;
1810
+ }
1811
+ /**
1812
+ * Convert a Node.js Transform to Web TransformStream
1813
+ */
1814
+ static toWeb(nodeStream) {
1815
+ return nodeStream.webStream;
1816
+ }
1817
+ // =========================================================================
1818
+ // Base Class Methods (for subclass override detection)
1819
+ // =========================================================================
1820
+ /**
1821
+ * Base transform method - can be overridden by subclasses.
1822
+ * Default behavior: pass through chunk unchanged.
1823
+ */
1824
+ _transform(chunk, encoding, callback) {
1825
+ // Default: pass through unchanged
1826
+ callback(null, chunk);
1827
+ }
1828
+ /**
1829
+ * Base flush method - can be overridden by subclasses.
1830
+ * Called when the stream ends to allow final processing.
1831
+ */
1832
+ _flush(callback) {
1833
+ // Default: no-op
1834
+ callback();
1835
+ }
1836
+ }
1837
+ // =============================================================================
1838
+ // Duplex Stream
1839
+ // =============================================================================
1840
+ /**
1841
+ * A duplex stream that combines readable and writable
1842
+ */
1843
+ export class Duplex extends EventEmitter {
1844
+ /**
1845
+ * Create a Duplex stream from various sources
1846
+ */
1847
+ static from(source) {
1848
+ // If it's already a Duplex, return as-is
1849
+ if (source instanceof Duplex) {
1850
+ return source;
1851
+ }
1852
+ const forwardReadableToDuplex = (readable, duplex) => {
1853
+ const sink = new Writable({
1854
+ objectMode: duplex.readableObjectMode,
1855
+ write(chunk, _encoding, callback) {
1856
+ duplex.push(chunk);
1857
+ callback();
1858
+ },
1859
+ final(callback) {
1860
+ duplex.push(null);
1861
+ callback();
1862
+ }
1863
+ });
1864
+ readable.on("error", err => duplex.emit("error", err));
1865
+ readable.pipe(sink);
1866
+ };
1867
+ // If it has readable and/or writable properties
1868
+ if (typeof source === "object" &&
1869
+ source !== null &&
1870
+ "readable" in source &&
1871
+ "writable" in source) {
1872
+ const duplex = new Duplex();
1873
+ const pair = source;
1874
+ if (pair.readable) {
1875
+ forwardReadableToDuplex(pair.readable, duplex);
1876
+ }
1877
+ if (pair.writable) {
1878
+ return new Duplex({
1879
+ objectMode: duplex.writableObjectMode,
1880
+ write(chunk, encoding, callback) {
1881
+ pair.writable.write(chunk, encoding, callback);
1882
+ },
1883
+ final(callback) {
1884
+ pair.writable.end(callback);
1885
+ }
1886
+ });
1887
+ }
1888
+ return duplex;
1889
+ }
1890
+ // If it's an iterable
1891
+ if (typeof source === "object" &&
1892
+ source !== null &&
1893
+ (Symbol.asyncIterator in source || Symbol.iterator in source)) {
1894
+ const readable = Readable.from(source);
1895
+ const duplex = new Duplex();
1896
+ forwardReadableToDuplex(readable, duplex);
1897
+ return duplex;
1898
+ }
1899
+ // If it's a Readable
1900
+ if (source instanceof Readable) {
1901
+ const duplex = new Duplex();
1902
+ forwardReadableToDuplex(source, duplex);
1903
+ return duplex;
1904
+ }
1905
+ // If it's a Writable
1906
+ if (source instanceof Writable) {
1907
+ return new Duplex({
1908
+ objectMode: true,
1909
+ write(chunk, encoding, callback) {
1910
+ source.write(chunk, encoding, callback);
1911
+ },
1912
+ final(callback) {
1913
+ source.end(callback);
1914
+ }
1915
+ });
1916
+ }
1917
+ throw new Error("Duplex.from: unsupported source type");
1918
+ }
1919
+ /**
1920
+ * Create a Duplex from a Web ReadableWritablePair
1921
+ */
1922
+ static fromWeb(pair, options) {
1923
+ const duplex = new Duplex(options);
1924
+ // Replace internal streams
1925
+ duplex._readable = new Readable({ stream: pair.readable });
1926
+ duplex._writable = new Writable({ stream: pair.writable });
1927
+ return duplex;
1928
+ }
1929
+ /**
1930
+ * Convert a Node.js Duplex to Web ReadableWritablePair
1931
+ */
1932
+ static toWeb(duplex) {
1933
+ return {
1934
+ readable: duplex._readable.webStream,
1935
+ writable: duplex._writable.webStream
1936
+ };
1937
+ }
1938
+ constructor(options) {
1939
+ super();
1940
+ // Track if we've already set up data forwarding
1941
+ this._dataForwardingSetup = false;
1942
+ this.allowHalfOpen = options?.allowHalfOpen ?? true;
1943
+ // Support shorthand objectMode option
1944
+ const objectMode = options?.objectMode ?? false;
1945
+ this.readableObjectMode = options?.readableObjectMode ?? objectMode;
1946
+ this.writableObjectMode = options?.writableObjectMode ?? objectMode;
1947
+ this._readable = new Readable({
1948
+ highWaterMark: options?.readableHighWaterMark,
1949
+ objectMode: this.readableObjectMode,
1950
+ read: options?.read?.bind(this)
1951
+ });
1952
+ this._writable = new Writable({
1953
+ highWaterMark: options?.writableHighWaterMark,
1954
+ objectMode: this.writableObjectMode,
1955
+ write: options?.write?.bind(this),
1956
+ final: options?.final?.bind(this)
1957
+ });
1958
+ // Forward non-data events (data forwarding is lazy to avoid premature flowing)
1959
+ this._readable.on("end", () => {
1960
+ this.emit("end");
1961
+ // If not allowHalfOpen, end the writable side too
1962
+ if (!this.allowHalfOpen) {
1963
+ this._writable.end();
1964
+ }
1965
+ });
1966
+ this._readable.on("error", err => this.emit("error", err));
1967
+ this._writable.on("finish", () => this.emit("finish"));
1968
+ this._writable.on("drain", () => this.emit("drain"));
1969
+ this._writable.on("close", () => {
1970
+ // If not allowHalfOpen, destroy the readable side too
1971
+ if (!this.allowHalfOpen && !this._readable.destroyed) {
1972
+ this._readable.destroy();
1973
+ }
1974
+ });
1975
+ }
1976
+ /**
1977
+ * Override on() to set up data forwarding lazily
1978
+ */
1979
+ on(event, listener) {
1980
+ // Set up data forwarding when first external data listener is added
1981
+ if (event === "data" && !this._dataForwardingSetup) {
1982
+ this._dataForwardingSetup = true;
1983
+ this._readable.on("data", chunk => this.emit("data", chunk));
1984
+ }
1985
+ return super.on(event, listener);
1986
+ }
1987
+ /**
1988
+ * Push data to readable side
1989
+ */
1990
+ push(chunk) {
1991
+ return this._readable.push(chunk);
1992
+ }
1993
+ /**
1994
+ * Put a chunk back at the front of the buffer (readable side)
1995
+ */
1996
+ unshift(chunk) {
1997
+ this._readable.unshift(chunk);
1998
+ }
1999
+ /**
2000
+ * Read from readable side
2001
+ */
2002
+ read(size) {
2003
+ return this._readable.read(size);
2004
+ }
2005
+ write(chunk, encodingOrCallback, callback) {
2006
+ const cb = typeof encodingOrCallback === "function" ? encodingOrCallback : callback;
2007
+ return this._writable.write(chunk, cb);
2008
+ }
2009
+ end(chunkOrCallback, encodingOrCallback, callback) {
2010
+ const chunk = typeof chunkOrCallback === "function" ? undefined : chunkOrCallback;
2011
+ const cb = typeof chunkOrCallback === "function"
2012
+ ? chunkOrCallback
2013
+ : typeof encodingOrCallback === "function"
2014
+ ? encodingOrCallback
2015
+ : callback;
2016
+ if (cb) {
2017
+ this.once("finish", cb);
2018
+ }
2019
+ if (chunk !== undefined) {
2020
+ this._writable.write(chunk);
2021
+ }
2022
+ this._writable.end();
2023
+ return this;
2024
+ }
2025
+ /**
2026
+ * Cork the writable side
2027
+ */
2028
+ cork() {
2029
+ this._writable.cork();
2030
+ }
2031
+ /**
2032
+ * Uncork the writable side
2033
+ */
2034
+ uncork() {
2035
+ this._writable.uncork();
2036
+ }
2037
+ /**
2038
+ * Set encoding for readable side
2039
+ */
2040
+ setEncoding(encoding) {
2041
+ this._readable.setEncoding(encoding);
2042
+ return this;
2043
+ }
2044
+ /**
2045
+ * Set default encoding for writable side
2046
+ */
2047
+ setDefaultEncoding(encoding) {
2048
+ this._writable.setDefaultEncoding(encoding);
2049
+ return this;
2050
+ }
2051
+ /**
2052
+ * Pipe readable side to destination
2053
+ */
2054
+ pipe(destination) {
2055
+ if (destination instanceof Transform) {
2056
+ this._readable.pipe(destination._writable);
2057
+ return destination;
2058
+ }
2059
+ this._readable.pipe(destination);
2060
+ return destination;
2061
+ }
2062
+ /**
2063
+ * Unpipe from destination
2064
+ */
2065
+ unpipe(destination) {
2066
+ this._readable.unpipe(destination);
2067
+ return this;
2068
+ }
2069
+ /**
2070
+ * Pause the readable side
2071
+ */
2072
+ pause() {
2073
+ this._readable.pause();
2074
+ return this;
2075
+ }
2076
+ /**
2077
+ * Resume the readable side
2078
+ */
2079
+ resume() {
2080
+ this._readable.resume();
2081
+ return this;
2082
+ }
2083
+ /**
2084
+ * Check if paused
2085
+ */
2086
+ isPaused() {
2087
+ return this._readable.isPaused();
2088
+ }
2089
+ /**
2090
+ * Destroy both sides
2091
+ */
2092
+ destroy(error) {
2093
+ this._readable.destroy(error);
2094
+ this._writable.destroy(error);
2095
+ return this;
2096
+ }
2097
+ get readable() {
2098
+ return this._readable.readable;
2099
+ }
2100
+ get writable() {
2101
+ return this._writable.writable;
2102
+ }
2103
+ get readableEnded() {
2104
+ return this._readable.readableEnded;
2105
+ }
2106
+ get writableEnded() {
2107
+ return this._writable.writableEnded;
2108
+ }
2109
+ get writableFinished() {
2110
+ return this._writable.writableFinished;
2111
+ }
2112
+ get readableLength() {
2113
+ return this._readable.readableLength;
2114
+ }
2115
+ get writableLength() {
2116
+ return this._writable.writableLength;
2117
+ }
2118
+ get readableHighWaterMark() {
2119
+ return this._readable.readableHighWaterMark;
2120
+ }
2121
+ get writableHighWaterMark() {
2122
+ return this._writable.writableHighWaterMark;
2123
+ }
2124
+ get destroyed() {
2125
+ return this._readable.destroyed && this._writable.destroyed;
2126
+ }
2127
+ get writableCorked() {
2128
+ return this._writable.writableCorked;
2129
+ }
2130
+ get writableNeedDrain() {
2131
+ return this._writable.writableNeedDrain;
2132
+ }
2133
+ /**
2134
+ * Async iterator support
2135
+ */
2136
+ [Symbol.asyncIterator]() {
2137
+ return this._readable[Symbol.asyncIterator]();
2138
+ }
2139
+ }
2140
+ // =============================================================================
2141
+ // PassThrough Stream
2142
+ // =============================================================================
2143
+ /**
2144
+ * A passthrough stream that passes data through unchanged
2145
+ */
2146
+ export class PassThrough extends Transform {
2147
+ constructor(options) {
2148
+ super({
2149
+ ...options,
2150
+ transform: chunk => chunk
2151
+ });
2152
+ }
2153
+ }
2154
+ // =============================================================================
2155
+ // Collector Stream
2156
+ // =============================================================================
2157
+ /**
2158
+ * A writable stream that collects all chunks
2159
+ */
2160
+ export class Collector extends Writable {
2161
+ constructor(options) {
2162
+ const collectedChunks = [];
2163
+ super({
2164
+ ...options,
2165
+ stream: new WritableStream({
2166
+ write: chunk => {
2167
+ collectedChunks.push(chunk);
2168
+ },
2169
+ close: () => {
2170
+ // Finished
2171
+ }
2172
+ })
2173
+ });
2174
+ this.chunks = [];
2175
+ this.chunks = collectedChunks;
2176
+ }
2177
+ write(chunk, encodingOrCallback, callback) {
2178
+ if (this.writableEnded || this.writableFinished) {
2179
+ const err = new Error("write after end");
2180
+ this.emit("error", err);
2181
+ return false;
2182
+ }
2183
+ const cb = typeof encodingOrCallback === "function" ? encodingOrCallback : callback;
2184
+ // Synchronously push to chunks
2185
+ this.chunks.push(chunk);
2186
+ cb?.(null);
2187
+ return true;
2188
+ }
2189
+ /**
2190
+ * Get all collected data as a single Uint8Array (for binary mode)
2191
+ */
2192
+ toUint8Array() {
2193
+ const chunks = this.chunks;
2194
+ const len = chunks.length;
2195
+ if (len === 0) {
2196
+ return new Uint8Array(0);
2197
+ }
2198
+ if (len === 1 && chunks[0] instanceof Uint8Array) {
2199
+ return chunks[0];
2200
+ }
2201
+ // If chunks are Uint8Arrays, concatenate them
2202
+ if (chunks[0] instanceof Uint8Array) {
2203
+ return concatUint8Arrays(chunks);
2204
+ }
2205
+ throw new Error("Collector contains non-binary data");
2206
+ }
2207
+ /**
2208
+ * Get all collected data as a string
2209
+ */
2210
+ toString() {
2211
+ const chunks = this.chunks;
2212
+ const len = chunks.length;
2213
+ if (len === 0) {
2214
+ return "";
2215
+ }
2216
+ const first = chunks[0];
2217
+ if (typeof first === "string") {
2218
+ if (len === 1) {
2219
+ return first;
2220
+ }
2221
+ return chunks.join("");
2222
+ }
2223
+ return textDecoder.decode(this.toUint8Array());
2224
+ }
2225
+ get isFinished() {
2226
+ // Use inherited writable property
2227
+ return this.writableFinished;
2228
+ }
2229
+ }
2230
+ // =============================================================================
2231
+ // PullStream / BufferedStream / DataChunk helpers
2232
+ // =============================================================================
2233
+ export class PullStream extends StandalonePullStream {
2234
+ // Keep constructor signature aligned with streams.browser.ts public API
2235
+ constructor(options) {
2236
+ super(options);
2237
+ }
2238
+ }
2239
+ export class StringChunk extends StandaloneStringChunk {
2240
+ }
2241
+ export class BufferChunk extends StandaloneBufferChunk {
2242
+ }
2243
+ export class BufferedStream extends StandaloneBufferedStream {
2244
+ constructor(options) {
2245
+ super(options);
2246
+ }
2247
+ }
2248
+ // =============================================================================
2249
+ // Stream Creation Functions
2250
+ // =============================================================================
2251
+ /**
2252
+ * Create a readable stream with custom read implementation
2253
+ */
2254
+ export function createReadable(options) {
2255
+ const readable = new Readable(options);
2256
+ // Override read behavior if provided
2257
+ if (options?.read) {
2258
+ const originalRead = readable.read.bind(readable);
2259
+ readable.read = function (size) {
2260
+ options.read(size ?? 16384);
2261
+ return originalRead(size);
2262
+ };
2263
+ }
2264
+ return readable;
2265
+ }
2266
+ /**
2267
+ * Create a readable stream from an async iterable
2268
+ */
2269
+ export function createReadableFromAsyncIterable(iterable, options) {
2270
+ const readable = new Readable({ ...options, objectMode: options?.objectMode ?? true });
2271
+ (async () => {
2272
+ try {
2273
+ for await (const chunk of iterable) {
2274
+ if (!readable.push(chunk)) {
2275
+ // Backpressure - wait a bit
2276
+ await new Promise(resolve => setTimeout(resolve, 0));
2277
+ }
2278
+ }
2279
+ readable.push(null);
2280
+ }
2281
+ catch (err) {
2282
+ readable.destroy(err);
2283
+ }
2284
+ })();
2285
+ return readable;
2286
+ }
2287
+ /**
2288
+ * Create a readable stream from an array
2289
+ */
2290
+ export function createReadableFromArray(data, options) {
2291
+ let index = 0;
2292
+ const readable = new Readable({
2293
+ ...options,
2294
+ objectMode: options?.objectMode ?? true,
2295
+ read() {
2296
+ // Push data when read is called
2297
+ while (index < data.length) {
2298
+ if (!this.push(data[index++])) {
2299
+ // Backpressure - wait for next read
2300
+ return;
2301
+ }
2302
+ }
2303
+ // All data pushed, end the stream
2304
+ this.push(null);
2305
+ }
2306
+ });
2307
+ return readable;
2308
+ }
2309
+ /**
2310
+ * Create a writable stream with custom write implementation
2311
+ */
2312
+ export function createWritable(options) {
2313
+ // Create a custom WritableStream with user's handlers
2314
+ const stream = new WritableStream({
2315
+ write: async (chunk) => {
2316
+ if (options?.write) {
2317
+ return new Promise((resolve, reject) => {
2318
+ options.write(chunk, "utf8", err => {
2319
+ if (err) {
2320
+ reject(err);
2321
+ }
2322
+ else {
2323
+ resolve();
2324
+ }
2325
+ });
2326
+ });
2327
+ }
2328
+ },
2329
+ close: async () => {
2330
+ if (options?.final) {
2331
+ return new Promise((resolve, reject) => {
2332
+ options.final(err => {
2333
+ if (err) {
2334
+ reject(err);
2335
+ }
2336
+ else {
2337
+ resolve();
2338
+ }
2339
+ });
2340
+ });
2341
+ }
2342
+ }
2343
+ });
2344
+ return new Writable({ ...options, stream });
2345
+ }
2346
+ /**
2347
+ * Create a transform stream from a transform function
2348
+ */
2349
+ export function createTransform(transformFn, options) {
2350
+ return new Transform({
2351
+ ...options,
2352
+ transform: transformFn,
2353
+ flush: options?.flush
2354
+ });
2355
+ }
2356
+ /**
2357
+ * Create a collector stream
2358
+ */
2359
+ export function createCollector(options) {
2360
+ return new Collector(options);
2361
+ }
2362
+ /**
2363
+ * Create a passthrough stream
2364
+ */
2365
+ export function createPassThrough(options) {
2366
+ return new PassThrough(options);
2367
+ }
2368
+ /**
2369
+ * Create a pull stream
2370
+ */
2371
+ export function createPullStream(options) {
2372
+ return new PullStream(options);
2373
+ }
2374
+ /**
2375
+ * Create a buffered stream
2376
+ */
2377
+ export function createBufferedStream(options) {
2378
+ return new BufferedStream(options);
2379
+ }
2380
+ const isReadableStream = (value) => !!value && typeof value === "object" && typeof value.getReader === "function";
2381
+ const isAsyncIterable = (value) => {
2382
+ if (!value || (typeof value !== "object" && typeof value !== "function")) {
2383
+ return false;
2384
+ }
2385
+ return typeof value[Symbol.asyncIterator] === "function";
2386
+ };
2387
+ const isWritableStream = (value) => !!value && typeof value === "object" && typeof value.getWriter === "function";
2388
+ const isTransformStream = (value) => !!value &&
2389
+ typeof value === "object" &&
2390
+ !!value.readable &&
2391
+ !!value.writable &&
2392
+ isReadableStream(value.readable) &&
2393
+ isWritableStream(value.writable);
2394
+ const isPipelineOptions = (value) => {
2395
+ if (!value || typeof value !== "object") {
2396
+ return false;
2397
+ }
2398
+ // IMPORTANT:
2399
+ // Do NOT use `"end" in obj` here because streams have `.end()` and would be
2400
+ // misclassified as options, breaking argument parsing and potentially hanging.
2401
+ if (typeof value.pipe === "function" ||
2402
+ typeof value.write === "function" ||
2403
+ typeof value.end === "function" ||
2404
+ typeof value.getReader === "function" ||
2405
+ typeof value.getWriter === "function") {
2406
+ return false;
2407
+ }
2408
+ return (Object.prototype.hasOwnProperty.call(value, "signal") ||
2409
+ Object.prototype.hasOwnProperty.call(value, "end"));
2410
+ };
2411
+ const toBrowserPipelineStream = (stream) => {
2412
+ if (stream instanceof Readable ||
2413
+ stream instanceof Writable ||
2414
+ stream instanceof Transform ||
2415
+ stream instanceof Duplex) {
2416
+ return stream;
2417
+ }
2418
+ if (isTransformStream(stream)) {
2419
+ return Transform.fromWeb(stream);
2420
+ }
2421
+ if (isReadableStream(stream)) {
2422
+ return Readable.fromWeb(stream);
2423
+ }
2424
+ if (isWritableStream(stream)) {
2425
+ return Writable.fromWeb(stream);
2426
+ }
2427
+ return stream;
2428
+ };
2429
+ /**
2430
+ * Pipeline streams together with proper error handling and cleanup.
2431
+ * Supports both callback and promise-based usage like Node.js.
2432
+ *
2433
+ * @example
2434
+ * // Promise usage
2435
+ * await pipeline(source, transform, destination);
2436
+ *
2437
+ * @example
2438
+ * // With options
2439
+ * await pipeline(source, transform, destination, { signal: controller.signal });
2440
+ *
2441
+ * @example
2442
+ * // Callback usage
2443
+ * pipeline(source, transform, destination, (err) => {
2444
+ * if (err) console.error('Pipeline failed', err);
2445
+ * });
2446
+ */
2447
+ export function pipeline(...args) {
2448
+ // Parse arguments
2449
+ let streams;
2450
+ let options = {};
2451
+ let callback;
2452
+ const lastArg = args[args.length - 1];
2453
+ if (typeof lastArg === "function") {
2454
+ // Callback style: pipeline(s1, s2, s3, callback)
2455
+ callback = lastArg;
2456
+ streams = args.slice(0, -1);
2457
+ }
2458
+ else if (isPipelineOptions(lastArg)) {
2459
+ // Options style: pipeline(s1, s2, s3, { signal })
2460
+ options = lastArg;
2461
+ streams = args.slice(0, -1);
2462
+ }
2463
+ else {
2464
+ // No callback or options: pipeline(s1, s2, s3)
2465
+ streams = args;
2466
+ }
2467
+ const promise = new Promise((resolve, reject) => {
2468
+ if (streams.length < 2) {
2469
+ const err = new Error("Pipeline requires at least 2 streams");
2470
+ reject(err);
2471
+ return;
2472
+ }
2473
+ const normalized = streams.map(toBrowserPipelineStream);
2474
+ const source = normalized[0];
2475
+ const destination = normalized[normalized.length - 1];
2476
+ const transforms = normalized.slice(1, -1);
2477
+ let completed = false;
2478
+ const allStreams = [source, ...transforms, destination];
2479
+ const cleanup = (error) => {
2480
+ if (completed) {
2481
+ return;
2482
+ }
2483
+ completed = true;
2484
+ // Destroy all streams on error
2485
+ if (error) {
2486
+ for (const stream of allStreams) {
2487
+ if (typeof stream.destroy === "function") {
2488
+ stream.destroy(error);
2489
+ }
2490
+ }
2491
+ reject(error);
2492
+ }
2493
+ else {
2494
+ resolve();
2495
+ }
2496
+ };
2497
+ // Handle abort signal
2498
+ if (options.signal) {
2499
+ if (options.signal.aborted) {
2500
+ cleanup(new Error("Pipeline aborted"));
2501
+ return;
2502
+ }
2503
+ options.signal.addEventListener("abort", () => {
2504
+ cleanup(new Error("Pipeline aborted"));
2505
+ });
2506
+ }
2507
+ // Chain the streams
2508
+ let current = source;
2509
+ for (const transform of transforms) {
2510
+ current.pipe(transform);
2511
+ current = transform;
2512
+ }
2513
+ // Pipe to destination
2514
+ if (options.end !== false) {
2515
+ current.pipe(destination);
2516
+ }
2517
+ else {
2518
+ // Don't end destination
2519
+ current.on("data", chunk => destination.write(chunk));
2520
+ }
2521
+ // Handle completion
2522
+ destination.on("finish", () => cleanup());
2523
+ // Handle errors on all streams
2524
+ for (const stream of allStreams) {
2525
+ stream.on("error", (err) => cleanup(err));
2526
+ }
2527
+ });
2528
+ // If callback provided, use it
2529
+ if (callback) {
2530
+ promise.then(() => callback(null)).catch(err => callback(err));
2531
+ }
2532
+ return promise;
2533
+ }
2534
+ /**
2535
+ * Wait for a stream to finish, close, or error.
2536
+ * Node.js compatible with support for options and callbacks.
2537
+ *
2538
+ * @example
2539
+ * // Promise usage
2540
+ * await finished(stream);
2541
+ *
2542
+ * @example
2543
+ * // With options
2544
+ * await finished(stream, { readable: false }); // Only wait for writable side
2545
+ *
2546
+ * @example
2547
+ * // Callback usage
2548
+ * finished(stream, (err) => {
2549
+ * if (err) console.error('Stream error', err);
2550
+ * });
2551
+ */
2552
+ export function finished(stream, optionsOrCallback, callback) {
2553
+ let options = {};
2554
+ let cb;
2555
+ if (typeof optionsOrCallback === "function") {
2556
+ cb = optionsOrCallback;
2557
+ }
2558
+ else if (optionsOrCallback) {
2559
+ options = optionsOrCallback;
2560
+ cb = callback;
2561
+ }
2562
+ const promise = new Promise((resolve, reject) => {
2563
+ const normalizedStream = toBrowserPipelineStream(stream);
2564
+ let resolved = false;
2565
+ const done = (err) => {
2566
+ if (resolved) {
2567
+ return;
2568
+ }
2569
+ resolved = true;
2570
+ if (err && !options.error) {
2571
+ reject(err);
2572
+ }
2573
+ else {
2574
+ resolve();
2575
+ }
2576
+ };
2577
+ // Handle abort signal
2578
+ if (options.signal) {
2579
+ if (options.signal.aborted) {
2580
+ done(new Error("Aborted"));
2581
+ return;
2582
+ }
2583
+ options.signal.addEventListener("abort", () => {
2584
+ done(new Error("Aborted"));
2585
+ });
2586
+ }
2587
+ const checkReadable = options.readable !== false;
2588
+ const checkWritable = options.writable !== false;
2589
+ // Already finished?
2590
+ if (checkReadable && normalizedStream.readableEnded) {
2591
+ done();
2592
+ return;
2593
+ }
2594
+ if (checkWritable && normalizedStream.writableFinished) {
2595
+ done();
2596
+ return;
2597
+ }
2598
+ // Listen for events
2599
+ if (checkWritable) {
2600
+ normalizedStream.on("finish", () => done());
2601
+ }
2602
+ if (checkReadable) {
2603
+ normalizedStream.on("end", () => done());
2604
+ }
2605
+ normalizedStream.on("error", (err) => done(err));
2606
+ normalizedStream.on("close", () => done());
2607
+ });
2608
+ // If callback provided, use it
2609
+ if (cb) {
2610
+ promise.then(() => cb(null)).catch(err => cb(err));
2611
+ }
2612
+ return promise;
2613
+ }
2614
+ // =============================================================================
2615
+ // Utility Functions
2616
+ // =============================================================================
2617
+ /**
2618
+ * Convert a stream to a promise that resolves when finished
2619
+ */
2620
+ export async function streamToPromise(stream) {
2621
+ return finished(stream);
2622
+ }
2623
+ /**
2624
+ * Collect all data from a readable stream into a Uint8Array
2625
+ * (Browser equivalent of Node.js streamToBuffer)
2626
+ */
2627
+ export async function streamToUint8Array(stream) {
2628
+ let iterable;
2629
+ if (isReadableStream(stream)) {
2630
+ iterable = Readable.fromWeb(stream);
2631
+ }
2632
+ else if (isAsyncIterable(stream)) {
2633
+ iterable = stream;
2634
+ }
2635
+ else {
2636
+ throw new Error("streamToUint8Array: unsupported stream type");
2637
+ }
2638
+ const chunks = [];
2639
+ let totalLength = 0;
2640
+ for await (const chunk of iterable) {
2641
+ chunks.push(chunk);
2642
+ totalLength += chunk.length;
2643
+ }
2644
+ // Fast paths
2645
+ const len = chunks.length;
2646
+ if (len === 0) {
2647
+ return new Uint8Array(0);
2648
+ }
2649
+ if (len === 1) {
2650
+ return chunks[0];
2651
+ }
2652
+ // Use precalculated total length
2653
+ const result = new Uint8Array(totalLength);
2654
+ let offset = 0;
2655
+ for (let i = 0; i < len; i++) {
2656
+ result.set(chunks[i], offset);
2657
+ offset += chunks[i].length;
2658
+ }
2659
+ return result;
2660
+ }
2661
+ /**
2662
+ * Alias for streamToUint8Array (Node.js compatibility)
2663
+ */
2664
+ export const streamToBuffer = streamToUint8Array;
2665
+ /**
2666
+ * Collect all data from a readable stream into a string
2667
+ */
2668
+ export async function streamToString(stream, encoding) {
2669
+ const buffer = await streamToUint8Array(stream);
2670
+ return getTextDecoder(encoding).decode(buffer);
2671
+ }
2672
+ /**
2673
+ * Drain a stream (consume all data without processing)
2674
+ */
2675
+ export async function drainStream(stream) {
2676
+ let iterable;
2677
+ if (isReadableStream(stream)) {
2678
+ iterable = Readable.fromWeb(stream);
2679
+ }
2680
+ else if (isAsyncIterable(stream)) {
2681
+ iterable = stream;
2682
+ }
2683
+ else {
2684
+ throw new Error("drainStream: unsupported stream type");
2685
+ }
2686
+ for await (const _chunk of iterable) {
2687
+ // Consume data
2688
+ }
2689
+ }
2690
+ /**
2691
+ * Copy from a readable stream to a writable stream
2692
+ */
2693
+ export async function copyStream(source, destination) {
2694
+ return pipeline(source, destination);
2695
+ }
2696
+ // =============================================================================
2697
+ // Type Guards
2698
+ // =============================================================================
2699
+ /**
2700
+ * Check if an object is a transform stream
2701
+ */
2702
+ export function isTransform(obj) {
2703
+ if (obj == null) {
2704
+ return false;
2705
+ }
2706
+ if (obj instanceof Transform) {
2707
+ return true;
2708
+ }
2709
+ const o = obj;
2710
+ return (typeof o.read === "function" &&
2711
+ typeof o.pipe === "function" &&
2712
+ typeof o.write === "function" &&
2713
+ typeof o.end === "function" &&
2714
+ typeof o._transform === "function");
2715
+ }
2716
+ /**
2717
+ * Check if an object is a duplex stream
2718
+ * Note: In Node.js, Transform extends Duplex, so Transform is also a Duplex
2719
+ */
2720
+ export function isDuplex(obj) {
2721
+ if (obj == null) {
2722
+ return false;
2723
+ }
2724
+ if (obj instanceof Duplex || obj instanceof Transform) {
2725
+ return true;
2726
+ }
2727
+ const o = obj;
2728
+ return (typeof o.read === "function" &&
2729
+ typeof o.pipe === "function" &&
2730
+ typeof o.write === "function" &&
2731
+ typeof o.end === "function");
2732
+ }
2733
+ /**
2734
+ * Check if an object is any kind of stream
2735
+ */
2736
+ export function isStream(obj) {
2737
+ if (obj == null) {
2738
+ return false;
2739
+ }
2740
+ if (obj instanceof Readable || obj instanceof Writable) {
2741
+ return true;
2742
+ }
2743
+ const o = obj;
2744
+ return ((typeof o.read === "function" && typeof o.pipe === "function") ||
2745
+ (typeof o.write === "function" && typeof o.end === "function"));
2746
+ }
2747
+ // =============================================================================
2748
+ // Additional Utility Functions (Node.js Compatibility)
2749
+ // =============================================================================
2750
+ /**
2751
+ * Add abort signal handling to any stream
2752
+ */
2753
+ export function addAbortSignal(signal, stream) {
2754
+ if (signal.aborted) {
2755
+ stream.destroy(new Error("Aborted"));
2756
+ return stream;
2757
+ }
2758
+ const onAbort = () => {
2759
+ stream.destroy(new Error("Aborted"));
2760
+ };
2761
+ signal.addEventListener("abort", onAbort, { once: true });
2762
+ // Clean up when stream is destroyed
2763
+ stream.on("close", () => {
2764
+ signal.removeEventListener("abort", onAbort);
2765
+ });
2766
+ return stream;
2767
+ }
2768
+ /**
2769
+ * Create a duplex stream from a pair of readable and writable streams
2770
+ */
2771
+ export function createDuplex(options) {
2772
+ const readableObjectMode = options?.readableObjectMode ?? options?.objectMode;
2773
+ const writableObjectMode = options?.writableObjectMode ?? options?.objectMode;
2774
+ const duplex = new Duplex({
2775
+ allowHalfOpen: options?.allowHalfOpen,
2776
+ readableHighWaterMark: options?.readableHighWaterMark,
2777
+ writableHighWaterMark: options?.writableHighWaterMark,
2778
+ readableObjectMode,
2779
+ writableObjectMode
2780
+ });
2781
+ // If custom readable/writable provided, pipe them
2782
+ if (options?.readable) {
2783
+ const readable = options.readable;
2784
+ readable.on?.("data", (chunk) => duplex.push(chunk));
2785
+ readable.on?.("end", () => duplex.push(null));
2786
+ readable.on?.("error", (err) => duplex.destroy(err));
2787
+ }
2788
+ if (options?.writable) {
2789
+ const writable = options.writable;
2790
+ duplex.on("data", (chunk) => writable.write?.(chunk));
2791
+ duplex.on("finish", () => writable.end?.());
2792
+ }
2793
+ // If custom read/write/final provided, override methods
2794
+ if (options?.write) {
2795
+ const _originalWrite = duplex.write.bind(duplex); // Keep bound reference for potential future use
2796
+ duplex.write = function (chunk, encodingOrCallback, callback) {
2797
+ const encoding = typeof encodingOrCallback === "string" ? encodingOrCallback : "utf8";
2798
+ const cb = typeof encodingOrCallback === "function" ? encodingOrCallback : (callback ?? (() => { }));
2799
+ options.write.call(duplex, chunk, encoding, cb);
2800
+ return true;
2801
+ };
2802
+ }
2803
+ if (options?.final) {
2804
+ const originalEnd = duplex.end.bind(duplex);
2805
+ duplex.end = function (chunkOrCallback, encodingOrCallback, callback) {
2806
+ const cb = typeof chunkOrCallback === "function"
2807
+ ? chunkOrCallback
2808
+ : typeof encodingOrCallback === "function"
2809
+ ? encodingOrCallback
2810
+ : (callback ?? (() => { }));
2811
+ if (chunkOrCallback !== undefined && typeof chunkOrCallback !== "function") {
2812
+ duplex.write(chunkOrCallback);
2813
+ }
2814
+ // Call custom final handler
2815
+ options.final.call(duplex, (err) => {
2816
+ if (err) {
2817
+ duplex.emit("error", err);
2818
+ }
2819
+ else {
2820
+ duplex.emit("finish");
2821
+ }
2822
+ // Call original end to properly close writable side
2823
+ originalEnd();
2824
+ cb();
2825
+ });
2826
+ return duplex;
2827
+ };
2828
+ }
2829
+ if (options?.destroy) {
2830
+ const originalDestroy = duplex.destroy.bind(duplex);
2831
+ duplex.destroy = function (error) {
2832
+ options.destroy.call(duplex, error ?? null, (err) => {
2833
+ if (err) {
2834
+ duplex.emit("error", err);
2835
+ originalDestroy(err);
2836
+ }
2837
+ else {
2838
+ originalDestroy(error);
2839
+ }
2840
+ });
2841
+ return duplex;
2842
+ };
2843
+ }
2844
+ return duplex;
2845
+ }
2846
+ /**
2847
+ * Create a readable stream from a generator function
2848
+ */
2849
+ export function createReadableFromGenerator(generator, options) {
2850
+ const readable = new Readable({ ...options, objectMode: options?.objectMode ?? true });
2851
+ (async () => {
2852
+ try {
2853
+ for await (const chunk of generator()) {
2854
+ if (!readable.push(chunk)) {
2855
+ // Backpressure
2856
+ await new Promise(resolve => setTimeout(resolve, 0));
2857
+ }
2858
+ }
2859
+ readable.push(null);
2860
+ }
2861
+ catch (err) {
2862
+ readable.destroy(err);
2863
+ }
2864
+ })();
2865
+ return readable;
2866
+ }
2867
+ /**
2868
+ * Create a readable stream from a Promise
2869
+ */
2870
+ export function createReadableFromPromise(promise, options) {
2871
+ const readable = new Readable({ ...options, objectMode: options?.objectMode ?? true });
2872
+ promise
2873
+ .then(value => {
2874
+ readable.push(value);
2875
+ readable.push(null);
2876
+ })
2877
+ .catch(err => {
2878
+ readable.destroy(err);
2879
+ });
2880
+ return readable;
2881
+ }
2882
+ /**
2883
+ * Compose multiple transform streams into one
2884
+ * Data flows through each transform in sequence
2885
+ */
2886
+ export function compose(...transforms) {
2887
+ const len = transforms.length;
2888
+ if (len === 0) {
2889
+ return new Transform({
2890
+ objectMode: true,
2891
+ transform: chunk => chunk
2892
+ });
2893
+ }
2894
+ const isNativeTransform = (stream) => stream instanceof Transform;
2895
+ if (len === 1 && isNativeTransform(transforms[0])) {
2896
+ return transforms[0];
2897
+ }
2898
+ // Chain the transforms: first → second → ... → last
2899
+ const first = transforms[0];
2900
+ const last = transforms[len - 1];
2901
+ // Pipe all transforms together
2902
+ for (let i = 0; i < len - 1; i++) {
2903
+ transforms[i].pipe(transforms[i + 1]);
2904
+ }
2905
+ class ComposedTransform extends Transform {
2906
+ constructor() {
2907
+ super(...arguments);
2908
+ this._dataForwarding = false;
2909
+ this._endForwarding = false;
2910
+ }
2911
+ on(event, listener) {
2912
+ if (event === "data" && !this._dataForwarding) {
2913
+ this._dataForwarding = true;
2914
+ last.on("data", (chunk) => this.emit("data", chunk));
2915
+ }
2916
+ if (event === "end" && !this._endForwarding) {
2917
+ this._endForwarding = true;
2918
+ last.on("end", () => this.emit("end"));
2919
+ }
2920
+ return super.on(event, listener);
2921
+ }
2922
+ write(chunk, encodingOrCallback, callback) {
2923
+ if (typeof encodingOrCallback === "function") {
2924
+ return first.write(chunk, encodingOrCallback);
2925
+ }
2926
+ return first.write(chunk, encodingOrCallback, callback);
2927
+ }
2928
+ end(chunkOrCallback, encodingOrCallback, callback) {
2929
+ if (typeof chunkOrCallback === "function") {
2930
+ first.end(chunkOrCallback);
2931
+ return this;
2932
+ }
2933
+ if (typeof encodingOrCallback === "function") {
2934
+ first.end(chunkOrCallback, encodingOrCallback);
2935
+ return this;
2936
+ }
2937
+ first.end(chunkOrCallback, encodingOrCallback, callback);
2938
+ return this;
2939
+ }
2940
+ pipe(destination) {
2941
+ return last.pipe(destination);
2942
+ }
2943
+ destroy(error) {
2944
+ for (const t of transforms) {
2945
+ t.destroy(error);
2946
+ }
2947
+ super.destroy(error);
2948
+ }
2949
+ read(size) {
2950
+ return typeof last.read === "function" ? last.read(size) : null;
2951
+ }
2952
+ async *[Symbol.asyncIterator]() {
2953
+ const it = last?.[Symbol.asyncIterator]?.();
2954
+ if (it) {
2955
+ for await (const chunk of it) {
2956
+ yield chunk;
2957
+ }
2958
+ return;
2959
+ }
2960
+ yield* super[Symbol.asyncIterator]();
2961
+ }
2962
+ }
2963
+ const composed = new ComposedTransform({
2964
+ objectMode: first?.objectMode ?? true,
2965
+ transform: chunk => chunk
2966
+ });
2967
+ // Forward errors from any transform
2968
+ for (const t of transforms) {
2969
+ t.on("error", (err) => {
2970
+ composed.emit("error", err);
2971
+ });
2972
+ }
2973
+ // Reflect underlying readability/writability like the previous duck-typed wrapper
2974
+ Object.defineProperty(composed, "readable", {
2975
+ get: () => last.readable
2976
+ });
2977
+ Object.defineProperty(composed, "writable", {
2978
+ get: () => first.writable
2979
+ });
2980
+ return composed;
2981
+ }
2982
+ /**
2983
+ * Wait for multiple streams to finish
2984
+ */
2985
+ export async function finishedAll(streams) {
2986
+ const len = streams.length;
2987
+ if (len === 0) {
2988
+ return;
2989
+ }
2990
+ if (len === 1) {
2991
+ await finished(streams[0]);
2992
+ return;
2993
+ }
2994
+ // Pre-allocate promise array
2995
+ const promises = new Array(len);
2996
+ for (let i = 0; i < len; i++) {
2997
+ promises[i] = finished(streams[i]);
2998
+ }
2999
+ await Promise.all(promises);
3000
+ }
3001
+ // Reusable empty push callback for createEmptyReadable
3002
+ const pushNull = (readable) => {
3003
+ readable.push(null);
3004
+ };
3005
+ /**
3006
+ * Create a readable stream that emits nothing and immediately ends
3007
+ */
3008
+ export function createEmptyReadable(options) {
3009
+ const readable = new Readable(options);
3010
+ queueMicrotask(() => pushNull(readable));
3011
+ return readable;
3012
+ }
3013
+ // Reusable null write handler
3014
+ const nullWriteHandler = {
3015
+ write: () => {
3016
+ // Discard
3017
+ }
3018
+ };
3019
+ /**
3020
+ * Create a writable stream that discards all data (like /dev/null)
3021
+ */
3022
+ export function createNullWritable(options) {
3023
+ return new Writable({
3024
+ ...options,
3025
+ stream: new WritableStream(nullWriteHandler)
3026
+ });
3027
+ }
3028
+ /**
3029
+ * Promisified version of once for events
3030
+ */
3031
+ export function once(emitter, event, options) {
3032
+ return new Promise((resolve, reject) => {
3033
+ let onAbort;
3034
+ let resolved = false;
3035
+ const cleanup = () => {
3036
+ if (resolved) {
3037
+ return;
3038
+ }
3039
+ resolved = true;
3040
+ emitter.off(event, onEvent);
3041
+ emitter.off("error", onError);
3042
+ if (onAbort && options?.signal) {
3043
+ options.signal.removeEventListener("abort", onAbort);
3044
+ }
3045
+ };
3046
+ const onEvent = (...args) => {
3047
+ cleanup();
3048
+ resolve(args);
3049
+ };
3050
+ const onError = (err) => {
3051
+ cleanup();
3052
+ reject(err);
3053
+ };
3054
+ emitter.once(event, onEvent);
3055
+ emitter.once("error", onError);
3056
+ if (options?.signal) {
3057
+ if (options.signal.aborted) {
3058
+ cleanup();
3059
+ reject(new Error("Aborted"));
3060
+ return;
3061
+ }
3062
+ onAbort = () => {
3063
+ cleanup();
3064
+ reject(new Error("Aborted"));
3065
+ };
3066
+ options.signal.addEventListener("abort", onAbort);
3067
+ }
3068
+ });
3069
+ }
3070
+ /**
3071
+ * Convert a callback-based stream operation to a promise
3072
+ */
3073
+ export function promisify(fn) {
3074
+ return new Promise((resolve, reject) => {
3075
+ fn((error, result) => {
3076
+ if (error) {
3077
+ reject(error);
3078
+ }
3079
+ else {
3080
+ resolve(result);
3081
+ }
3082
+ });
3083
+ });
3084
+ }
3085
+ // =============================================================================
3086
+ // Default High Water Mark Management
3087
+ // =============================================================================
3088
+ let _defaultHighWaterMark = 16384; // 16KB default
3089
+ let _defaultHighWaterMarkObjectMode = 16; // 16 objects default
3090
+ /**
3091
+ * Get the default high water mark for streams
3092
+ */
3093
+ export function getDefaultHighWaterMark(objectMode) {
3094
+ return objectMode ? _defaultHighWaterMarkObjectMode : _defaultHighWaterMark;
3095
+ }
3096
+ /**
3097
+ * Set the default high water mark for streams
3098
+ */
3099
+ export function setDefaultHighWaterMark(objectMode, value) {
3100
+ if (objectMode) {
3101
+ _defaultHighWaterMarkObjectMode = value;
3102
+ }
3103
+ else {
3104
+ _defaultHighWaterMark = value;
3105
+ }
3106
+ }
3107
+ // =============================================================================
3108
+ // Stream State Inspection Functions
3109
+ // =============================================================================
3110
+ /**
3111
+ * Check if a stream has been destroyed
3112
+ */
3113
+ export function isDestroyed(stream) {
3114
+ return !!stream?.destroyed;
3115
+ }
3116
+ /**
3117
+ * Check if a readable stream has been disturbed (read from)
3118
+ */
3119
+ export function isDisturbed(stream) {
3120
+ if (stream instanceof Readable) {
3121
+ return Readable.isDisturbed(stream);
3122
+ }
3123
+ if (stream instanceof Duplex) {
3124
+ return Readable.isDisturbed(stream._readable);
3125
+ }
3126
+ const s = stream;
3127
+ return (s?.readableDidRead === true ||
3128
+ s?._didRead === true ||
3129
+ s?._ended === true ||
3130
+ s?._destroyed === true);
3131
+ }
3132
+ /**
3133
+ * Check if a stream has an error
3134
+ */
3135
+ export function isErrored(stream) {
3136
+ const err = stream?.errored;
3137
+ return err !== null && err !== undefined;
3138
+ }
3139
+ /**
3140
+ * Check if a stream is readable
3141
+ */
3142
+ export function isReadable(stream) {
3143
+ if (stream == null) {
3144
+ return false;
3145
+ }
3146
+ if (stream instanceof Readable || stream instanceof Transform) {
3147
+ return true;
3148
+ }
3149
+ if (stream instanceof Duplex) {
3150
+ return stream._readable instanceof Readable;
3151
+ }
3152
+ const o = stream;
3153
+ return typeof o.read === "function" && typeof o.pipe === "function";
3154
+ }
3155
+ /**
3156
+ * Check if a stream is writable
3157
+ */
3158
+ export function isWritable(stream) {
3159
+ if (stream == null) {
3160
+ return false;
3161
+ }
3162
+ if (stream instanceof Writable || stream instanceof Transform) {
3163
+ return true;
3164
+ }
3165
+ if (stream instanceof Duplex) {
3166
+ return stream._writable instanceof Writable;
3167
+ }
3168
+ const o = stream;
3169
+ return typeof o.write === "function" && typeof o.end === "function";
3170
+ }
3171
+ // =============================================================================
3172
+ // Duplex Pair
3173
+ // =============================================================================
3174
+ /**
3175
+ * Create a pair of connected Duplex streams
3176
+ * Data written to one stream can be read from the other
3177
+ */
3178
+ export function duplexPair(options) {
3179
+ const stream1 = new Duplex(options);
3180
+ const stream2 = new Duplex(options);
3181
+ // Override write to push to the other stream's readable
3182
+ stream1.write = function (chunk) {
3183
+ // Push to stream2's readable side
3184
+ stream2.push(chunk);
3185
+ return true;
3186
+ };
3187
+ stream2.write = function (chunk) {
3188
+ // Push to stream1's readable side
3189
+ stream1.push(chunk);
3190
+ return true;
3191
+ };
3192
+ // Override end to signal EOF to the other stream
3193
+ const originalEnd1 = stream1.end.bind(stream1);
3194
+ const originalEnd2 = stream2.end.bind(stream2);
3195
+ stream1.end = function (chunk) {
3196
+ if (chunk !== undefined && typeof chunk !== "function") {
3197
+ stream2.push(chunk);
3198
+ }
3199
+ stream2.push(null);
3200
+ return originalEnd1(typeof chunk === "function" ? chunk : undefined);
3201
+ };
3202
+ stream2.end = function (chunk) {
3203
+ if (chunk !== undefined && typeof chunk !== "function") {
3204
+ stream1.push(chunk);
3205
+ }
3206
+ stream1.push(null);
3207
+ return originalEnd2(typeof chunk === "function" ? chunk : undefined);
3208
+ };
3209
+ return [stream1, stream2];
3210
+ }
3211
+ // =============================================================================
3212
+ // Stream Consumers (like stream.consumers in Node.js)
3213
+ // =============================================================================
3214
+ // Helper function to collect stream chunks with total length tracking
3215
+ async function collectStreamChunks(stream) {
3216
+ const chunks = [];
3217
+ let totalLength = 0;
3218
+ let iterable;
3219
+ if (isReadableStream(stream)) {
3220
+ iterable = Readable.fromWeb(stream);
3221
+ }
3222
+ else if (isAsyncIterable(stream)) {
3223
+ iterable = stream;
3224
+ }
3225
+ else {
3226
+ throw new Error("collectStreamChunks: unsupported stream type");
3227
+ }
3228
+ for await (const chunk of iterable) {
3229
+ chunks.push(chunk);
3230
+ totalLength += chunk.length;
3231
+ }
3232
+ return { chunks, totalLength };
3233
+ }
3234
+ // Helper to concatenate with known length (faster)
3235
+ function concatWithLength(chunks, totalLength) {
3236
+ const len = chunks.length;
3237
+ if (len === 0) {
3238
+ return new Uint8Array(0);
3239
+ }
3240
+ if (len === 1) {
3241
+ return chunks[0];
3242
+ }
3243
+ const result = new Uint8Array(totalLength);
3244
+ let offset = 0;
3245
+ for (let i = 0; i < len; i++) {
3246
+ result.set(chunks[i], offset);
3247
+ offset += chunks[i].length;
3248
+ }
3249
+ return result;
3250
+ }
3251
+ export const consumers = {
3252
+ /**
3253
+ * Consume entire stream as ArrayBuffer
3254
+ */
3255
+ async arrayBuffer(stream) {
3256
+ const { chunks, totalLength } = await collectStreamChunks(stream);
3257
+ const combined = concatWithLength(chunks, totalLength);
3258
+ return combined.buffer.slice(combined.byteOffset, combined.byteOffset + combined.byteLength);
3259
+ },
3260
+ /**
3261
+ * Consume entire stream as Blob
3262
+ */
3263
+ async blob(stream, options) {
3264
+ const { chunks } = await collectStreamChunks(stream);
3265
+ return new Blob(chunks, options);
3266
+ },
3267
+ /**
3268
+ * Consume entire stream as Buffer (Uint8Array in browser)
3269
+ */
3270
+ async buffer(stream) {
3271
+ const { chunks, totalLength } = await collectStreamChunks(stream);
3272
+ return concatWithLength(chunks, totalLength);
3273
+ },
3274
+ /**
3275
+ * Consume entire stream as JSON
3276
+ */
3277
+ async json(stream) {
3278
+ const text = await consumers.text(stream);
3279
+ return JSON.parse(text);
3280
+ },
3281
+ /**
3282
+ * Consume entire stream as text
3283
+ */
3284
+ async text(stream, encoding) {
3285
+ const { chunks, totalLength } = await collectStreamChunks(stream);
3286
+ const combined = concatWithLength(chunks, totalLength);
3287
+ const decoder = encoding ? getTextDecoder(encoding) : textDecoder;
3288
+ return decoder.decode(combined);
3289
+ }
3290
+ };
3291
+ // =============================================================================
3292
+ // Promises API (like stream/promises in Node.js)
3293
+ // =============================================================================
3294
+ export const promises = {
3295
+ pipeline,
3296
+ finished
3297
+ };