@nodetool-ai/base-nodes 0.7.0-rc.11

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 (353) hide show
  1. package/dist/index.d.ts +72 -0
  2. package/dist/index.d.ts.map +1 -0
  3. package/dist/index.js +270 -0
  4. package/dist/index.js.map +1 -0
  5. package/dist/lib/audio-wav.d.ts +66 -0
  6. package/dist/lib/audio-wav.d.ts.map +1 -0
  7. package/dist/lib/audio-wav.js +215 -0
  8. package/dist/lib/audio-wav.js.map +1 -0
  9. package/dist/nodes/agents.d.ts +253 -0
  10. package/dist/nodes/agents.d.ts.map +1 -0
  11. package/dist/nodes/agents.js +2784 -0
  12. package/dist/nodes/agents.js.map +1 -0
  13. package/dist/nodes/anthropic.d.ts +26 -0
  14. package/dist/nodes/anthropic.d.ts.map +1 -0
  15. package/dist/nodes/anthropic.js +133 -0
  16. package/dist/nodes/anthropic.js.map +1 -0
  17. package/dist/nodes/apify.d.ts +120 -0
  18. package/dist/nodes/apify.d.ts.map +1 -0
  19. package/dist/nodes/apify.js +618 -0
  20. package/dist/nodes/apify.js.map +1 -0
  21. package/dist/nodes/audio.d.ts +301 -0
  22. package/dist/nodes/audio.d.ts.map +1 -0
  23. package/dist/nodes/audio.js +1274 -0
  24. package/dist/nodes/audio.js.map +1 -0
  25. package/dist/nodes/code-node.d.ts +34 -0
  26. package/dist/nodes/code-node.d.ts.map +1 -0
  27. package/dist/nodes/code-node.js +343 -0
  28. package/dist/nodes/code-node.js.map +1 -0
  29. package/dist/nodes/code.d.ts +301 -0
  30. package/dist/nodes/code.d.ts.map +1 -0
  31. package/dist/nodes/code.js +850 -0
  32. package/dist/nodes/code.js.map +1 -0
  33. package/dist/nodes/compare.d.ts +18 -0
  34. package/dist/nodes/compare.d.ts.map +1 -0
  35. package/dist/nodes/compare.js +122 -0
  36. package/dist/nodes/compare.js.map +1 -0
  37. package/dist/nodes/constant.d.ts +315 -0
  38. package/dist/nodes/constant.d.ts.map +1 -0
  39. package/dist/nodes/constant.js +715 -0
  40. package/dist/nodes/constant.js.map +1 -0
  41. package/dist/nodes/control.d.ts +83 -0
  42. package/dist/nodes/control.d.ts.map +1 -0
  43. package/dist/nodes/control.js +212 -0
  44. package/dist/nodes/control.js.map +1 -0
  45. package/dist/nodes/data.d.ts +369 -0
  46. package/dist/nodes/data.d.ts.map +1 -0
  47. package/dist/nodes/data.js +1590 -0
  48. package/dist/nodes/data.js.map +1 -0
  49. package/dist/nodes/document.d.ts +134 -0
  50. package/dist/nodes/document.d.ts.map +1 -0
  51. package/dist/nodes/document.js +984 -0
  52. package/dist/nodes/document.js.map +1 -0
  53. package/dist/nodes/extended-placeholders.d.ts +6 -0
  54. package/dist/nodes/extended-placeholders.d.ts.map +1 -0
  55. package/dist/nodes/extended-placeholders.js +19 -0
  56. package/dist/nodes/extended-placeholders.js.map +1 -0
  57. package/dist/nodes/gemini.d.ts +109 -0
  58. package/dist/nodes/gemini.d.ts.map +1 -0
  59. package/dist/nodes/gemini.js +861 -0
  60. package/dist/nodes/gemini.js.map +1 -0
  61. package/dist/nodes/generators.d.ts +84 -0
  62. package/dist/nodes/generators.d.ts.map +1 -0
  63. package/dist/nodes/generators.js +937 -0
  64. package/dist/nodes/generators.js.map +1 -0
  65. package/dist/nodes/image.d.ts +232 -0
  66. package/dist/nodes/image.d.ts.map +1 -0
  67. package/dist/nodes/image.js +1395 -0
  68. package/dist/nodes/image.js.map +1 -0
  69. package/dist/nodes/input.d.ts +445 -0
  70. package/dist/nodes/input.d.ts.map +1 -0
  71. package/dist/nodes/input.js +1459 -0
  72. package/dist/nodes/input.js.map +1 -0
  73. package/dist/nodes/kie-dynamic.d.ts +31 -0
  74. package/dist/nodes/kie-dynamic.d.ts.map +1 -0
  75. package/dist/nodes/kie-dynamic.js +270 -0
  76. package/dist/nodes/kie-dynamic.js.map +1 -0
  77. package/dist/nodes/lib-audio-dsp.d.ts +85 -0
  78. package/dist/nodes/lib-audio-dsp.d.ts.map +1 -0
  79. package/dist/nodes/lib-audio-dsp.js +450 -0
  80. package/dist/nodes/lib-audio-dsp.js.map +1 -0
  81. package/dist/nodes/lib-audio-effects.d.ts +116 -0
  82. package/dist/nodes/lib-audio-effects.d.ts.map +1 -0
  83. package/dist/nodes/lib-audio-effects.js +905 -0
  84. package/dist/nodes/lib-audio-effects.js.map +1 -0
  85. package/dist/nodes/lib-browser.d.ts +99 -0
  86. package/dist/nodes/lib-browser.d.ts.map +1 -0
  87. package/dist/nodes/lib-browser.js +692 -0
  88. package/dist/nodes/lib-browser.js.map +1 -0
  89. package/dist/nodes/lib-charts.d.ts +20 -0
  90. package/dist/nodes/lib-charts.d.ts.map +1 -0
  91. package/dist/nodes/lib-charts.js +245 -0
  92. package/dist/nodes/lib-charts.js.map +1 -0
  93. package/dist/nodes/lib-datetime.d.ts +108 -0
  94. package/dist/nodes/lib-datetime.d.ts.map +1 -0
  95. package/dist/nodes/lib-datetime.js +421 -0
  96. package/dist/nodes/lib-datetime.js.map +1 -0
  97. package/dist/nodes/lib-doc-convert.d.ts +19 -0
  98. package/dist/nodes/lib-doc-convert.d.ts.map +1 -0
  99. package/dist/nodes/lib-doc-convert.js +257 -0
  100. package/dist/nodes/lib-doc-convert.js.map +1 -0
  101. package/dist/nodes/lib-doc-transform.d.ts +39 -0
  102. package/dist/nodes/lib-doc-transform.d.ts.map +1 -0
  103. package/dist/nodes/lib-doc-transform.js +335 -0
  104. package/dist/nodes/lib-doc-transform.js.map +1 -0
  105. package/dist/nodes/lib-docx.d.ts +106 -0
  106. package/dist/nodes/lib-docx.d.ts.map +1 -0
  107. package/dist/nodes/lib-docx.js +595 -0
  108. package/dist/nodes/lib-docx.js.map +1 -0
  109. package/dist/nodes/lib-epub.d.ts +55 -0
  110. package/dist/nodes/lib-epub.d.ts.map +1 -0
  111. package/dist/nodes/lib-epub.js +220 -0
  112. package/dist/nodes/lib-epub.js.map +1 -0
  113. package/dist/nodes/lib-excel.d.ts +74 -0
  114. package/dist/nodes/lib-excel.d.ts.map +1 -0
  115. package/dist/nodes/lib-excel.js +448 -0
  116. package/dist/nodes/lib-excel.js.map +1 -0
  117. package/dist/nodes/lib-graphql.d.ts +66 -0
  118. package/dist/nodes/lib-graphql.d.ts.map +1 -0
  119. package/dist/nodes/lib-graphql.js +333 -0
  120. package/dist/nodes/lib-graphql.js.map +1 -0
  121. package/dist/nodes/lib-grid.d.ts +27 -0
  122. package/dist/nodes/lib-grid.d.ts.map +1 -0
  123. package/dist/nodes/lib-grid.js +172 -0
  124. package/dist/nodes/lib-grid.js.map +1 -0
  125. package/dist/nodes/lib-html-parse.d.ts +108 -0
  126. package/dist/nodes/lib-html-parse.d.ts.map +1 -0
  127. package/dist/nodes/lib-html-parse.js +365 -0
  128. package/dist/nodes/lib-html-parse.js.map +1 -0
  129. package/dist/nodes/lib-http.d.ts +98 -0
  130. package/dist/nodes/lib-http.d.ts.map +1 -0
  131. package/dist/nodes/lib-http.js +267 -0
  132. package/dist/nodes/lib-http.js.map +1 -0
  133. package/dist/nodes/lib-image-color-grading.d.ts +3 -0
  134. package/dist/nodes/lib-image-color-grading.d.ts.map +1 -0
  135. package/dist/nodes/lib-image-color-grading.js +1386 -0
  136. package/dist/nodes/lib-image-color-grading.js.map +1 -0
  137. package/dist/nodes/lib-image-draw.d.ts +3 -0
  138. package/dist/nodes/lib-image-draw.d.ts.map +1 -0
  139. package/dist/nodes/lib-image-draw.js +470 -0
  140. package/dist/nodes/lib-image-draw.js.map +1 -0
  141. package/dist/nodes/lib-image-enhance.d.ts +3 -0
  142. package/dist/nodes/lib-image-enhance.d.ts.map +1 -0
  143. package/dist/nodes/lib-image-enhance.js +731 -0
  144. package/dist/nodes/lib-image-enhance.js.map +1 -0
  145. package/dist/nodes/lib-image-filter.d.ts +3 -0
  146. package/dist/nodes/lib-image-filter.d.ts.map +1 -0
  147. package/dist/nodes/lib-image-filter.js +684 -0
  148. package/dist/nodes/lib-image-filter.js.map +1 -0
  149. package/dist/nodes/lib-image-utils.d.ts +24 -0
  150. package/dist/nodes/lib-image-utils.d.ts.map +1 -0
  151. package/dist/nodes/lib-image-utils.js +150 -0
  152. package/dist/nodes/lib-image-utils.js.map +1 -0
  153. package/dist/nodes/lib-mail.d.ts +74 -0
  154. package/dist/nodes/lib-mail.d.ts.map +1 -0
  155. package/dist/nodes/lib-mail.js +452 -0
  156. package/dist/nodes/lib-mail.js.map +1 -0
  157. package/dist/nodes/lib-markdown.d.ts +70 -0
  158. package/dist/nodes/lib-markdown.d.ts.map +1 -0
  159. package/dist/nodes/lib-markdown.js +236 -0
  160. package/dist/nodes/lib-markdown.js.map +1 -0
  161. package/dist/nodes/lib-nlp.d.ts +98 -0
  162. package/dist/nodes/lib-nlp.d.ts.map +1 -0
  163. package/dist/nodes/lib-nlp.js +374 -0
  164. package/dist/nodes/lib-nlp.js.map +1 -0
  165. package/dist/nodes/lib-notion.d.ts +99 -0
  166. package/dist/nodes/lib-notion.d.ts.map +1 -0
  167. package/dist/nodes/lib-notion.js +601 -0
  168. package/dist/nodes/lib-notion.js.map +1 -0
  169. package/dist/nodes/lib-ocr.d.ts +31 -0
  170. package/dist/nodes/lib-ocr.d.ts.map +1 -0
  171. package/dist/nodes/lib-ocr.js +143 -0
  172. package/dist/nodes/lib-ocr.js.map +1 -0
  173. package/dist/nodes/lib-os.d.ts +312 -0
  174. package/dist/nodes/lib-os.d.ts.map +1 -0
  175. package/dist/nodes/lib-os.js +909 -0
  176. package/dist/nodes/lib-os.js.map +1 -0
  177. package/dist/nodes/lib-pdf.d.ts +142 -0
  178. package/dist/nodes/lib-pdf.d.ts.map +1 -0
  179. package/dist/nodes/lib-pdf.js +871 -0
  180. package/dist/nodes/lib-pdf.js.map +1 -0
  181. package/dist/nodes/lib-pptx.d.ts +29 -0
  182. package/dist/nodes/lib-pptx.d.ts.map +1 -0
  183. package/dist/nodes/lib-pptx.js +122 -0
  184. package/dist/nodes/lib-pptx.js.map +1 -0
  185. package/dist/nodes/lib-rss.d.ts +31 -0
  186. package/dist/nodes/lib-rss.d.ts.map +1 -0
  187. package/dist/nodes/lib-rss.js +163 -0
  188. package/dist/nodes/lib-rss.js.map +1 -0
  189. package/dist/nodes/lib-s3.d.ts +112 -0
  190. package/dist/nodes/lib-s3.d.ts.map +1 -0
  191. package/dist/nodes/lib-s3.js +521 -0
  192. package/dist/nodes/lib-s3.js.map +1 -0
  193. package/dist/nodes/lib-secret.d.ts +15 -0
  194. package/dist/nodes/lib-secret.d.ts.map +1 -0
  195. package/dist/nodes/lib-secret.js +42 -0
  196. package/dist/nodes/lib-secret.js.map +1 -0
  197. package/dist/nodes/lib-sqlite.d.ts +102 -0
  198. package/dist/nodes/lib-sqlite.d.ts.map +1 -0
  199. package/dist/nodes/lib-sqlite.js +532 -0
  200. package/dist/nodes/lib-sqlite.js.map +1 -0
  201. package/dist/nodes/lib-supabase.d.ts +86 -0
  202. package/dist/nodes/lib-supabase.d.ts.map +1 -0
  203. package/dist/nodes/lib-supabase.js +425 -0
  204. package/dist/nodes/lib-supabase.js.map +1 -0
  205. package/dist/nodes/lib-svg.d.ts +199 -0
  206. package/dist/nodes/lib-svg.d.ts.map +1 -0
  207. package/dist/nodes/lib-svg.js +1027 -0
  208. package/dist/nodes/lib-svg.js.map +1 -0
  209. package/dist/nodes/lib-tensorflow.d.ts +71 -0
  210. package/dist/nodes/lib-tensorflow.d.ts.map +1 -0
  211. package/dist/nodes/lib-tensorflow.js +351 -0
  212. package/dist/nodes/lib-tensorflow.js.map +1 -0
  213. package/dist/nodes/lib-twilio.d.ts +71 -0
  214. package/dist/nodes/lib-twilio.d.ts.map +1 -0
  215. package/dist/nodes/lib-twilio.js +469 -0
  216. package/dist/nodes/lib-twilio.js.map +1 -0
  217. package/dist/nodes/lib-validate.d.ts +84 -0
  218. package/dist/nodes/lib-validate.d.ts.map +1 -0
  219. package/dist/nodes/lib-validate.js +215 -0
  220. package/dist/nodes/lib-validate.js.map +1 -0
  221. package/dist/nodes/lib-video-download.d.ts +26 -0
  222. package/dist/nodes/lib-video-download.d.ts.map +1 -0
  223. package/dist/nodes/lib-video-download.js +299 -0
  224. package/dist/nodes/lib-video-download.js.map +1 -0
  225. package/dist/nodes/messaging.d.ts +88 -0
  226. package/dist/nodes/messaging.d.ts.map +1 -0
  227. package/dist/nodes/messaging.js +418 -0
  228. package/dist/nodes/messaging.js.map +1 -0
  229. package/dist/nodes/mistral.d.ts +83 -0
  230. package/dist/nodes/mistral.d.ts.map +1 -0
  231. package/dist/nodes/mistral.js +450 -0
  232. package/dist/nodes/mistral.js.map +1 -0
  233. package/dist/nodes/model3d/analysis.d.ts +13 -0
  234. package/dist/nodes/model3d/analysis.d.ts.map +1 -0
  235. package/dist/nodes/model3d/analysis.js +36 -0
  236. package/dist/nodes/model3d/analysis.js.map +1 -0
  237. package/dist/nodes/model3d/base.d.ts +11 -0
  238. package/dist/nodes/model3d/base.d.ts.map +1 -0
  239. package/dist/nodes/model3d/base.js +20 -0
  240. package/dist/nodes/model3d/base.js.map +1 -0
  241. package/dist/nodes/model3d/boolean-ops.d.ts +2 -0
  242. package/dist/nodes/model3d/boolean-ops.d.ts.map +1 -0
  243. package/dist/nodes/model3d/boolean-ops.js +172 -0
  244. package/dist/nodes/model3d/boolean-ops.js.map +1 -0
  245. package/dist/nodes/model3d/cleanup.d.ts +47 -0
  246. package/dist/nodes/model3d/cleanup.d.ts.map +1 -0
  247. package/dist/nodes/model3d/cleanup.js +136 -0
  248. package/dist/nodes/model3d/cleanup.js.map +1 -0
  249. package/dist/nodes/model3d/convert.d.ts +14 -0
  250. package/dist/nodes/model3d/convert.d.ts.map +1 -0
  251. package/dist/nodes/model3d/convert.js +64 -0
  252. package/dist/nodes/model3d/convert.js.map +1 -0
  253. package/dist/nodes/model3d/defaults.d.ts +34 -0
  254. package/dist/nodes/model3d/defaults.d.ts.map +1 -0
  255. package/dist/nodes/model3d/defaults.js +28 -0
  256. package/dist/nodes/model3d/defaults.js.map +1 -0
  257. package/dist/nodes/model3d/document-ops.d.ts +4 -0
  258. package/dist/nodes/model3d/document-ops.d.ts.map +1 -0
  259. package/dist/nodes/model3d/document-ops.js +40 -0
  260. package/dist/nodes/model3d/document-ops.js.map +1 -0
  261. package/dist/nodes/model3d/generation.d.ts +39 -0
  262. package/dist/nodes/model3d/generation.d.ts.map +1 -0
  263. package/dist/nodes/model3d/generation.js +179 -0
  264. package/dist/nodes/model3d/generation.js.map +1 -0
  265. package/dist/nodes/model3d/glb.d.ts +29 -0
  266. package/dist/nodes/model3d/glb.d.ts.map +1 -0
  267. package/dist/nodes/model3d/glb.js +255 -0
  268. package/dist/nodes/model3d/glb.js.map +1 -0
  269. package/dist/nodes/model3d/index.d.ts +20 -0
  270. package/dist/nodes/model3d/index.d.ts.map +1 -0
  271. package/dist/nodes/model3d/index.js +38 -0
  272. package/dist/nodes/model3d/index.js.map +1 -0
  273. package/dist/nodes/model3d/io.d.ts +38 -0
  274. package/dist/nodes/model3d/io.d.ts.map +1 -0
  275. package/dist/nodes/model3d/io.js +162 -0
  276. package/dist/nodes/model3d/io.js.map +1 -0
  277. package/dist/nodes/model3d/mesh-ops.d.ts +40 -0
  278. package/dist/nodes/model3d/mesh-ops.d.ts.map +1 -0
  279. package/dist/nodes/model3d/mesh-ops.js +775 -0
  280. package/dist/nodes/model3d/mesh-ops.js.map +1 -0
  281. package/dist/nodes/model3d/nodes.d.ts +2 -0
  282. package/dist/nodes/model3d/nodes.d.ts.map +1 -0
  283. package/dist/nodes/model3d/nodes.js +2 -0
  284. package/dist/nodes/model3d/nodes.js.map +1 -0
  285. package/dist/nodes/model3d/ops.d.ts +37 -0
  286. package/dist/nodes/model3d/ops.d.ts.map +1 -0
  287. package/dist/nodes/model3d/ops.js +137 -0
  288. package/dist/nodes/model3d/ops.js.map +1 -0
  289. package/dist/nodes/model3d/transforms.d.ts +49 -0
  290. package/dist/nodes/model3d/transforms.d.ts.map +1 -0
  291. package/dist/nodes/model3d/transforms.js +142 -0
  292. package/dist/nodes/model3d/transforms.js.map +1 -0
  293. package/dist/nodes/model3d/types.d.ts +81 -0
  294. package/dist/nodes/model3d/types.d.ts.map +1 -0
  295. package/dist/nodes/model3d/types.js +2 -0
  296. package/dist/nodes/model3d/types.js.map +1 -0
  297. package/dist/nodes/model3d/utils.d.ts +34 -0
  298. package/dist/nodes/model3d/utils.d.ts.map +1 -0
  299. package/dist/nodes/model3d/utils.js +185 -0
  300. package/dist/nodes/model3d/utils.js.map +1 -0
  301. package/dist/nodes/model3d.d.ts +2 -0
  302. package/dist/nodes/model3d.d.ts.map +1 -0
  303. package/dist/nodes/model3d.js +2 -0
  304. package/dist/nodes/model3d.js.map +1 -0
  305. package/dist/nodes/openai.d.ts +172 -0
  306. package/dist/nodes/openai.d.ts.map +1 -0
  307. package/dist/nodes/openai.js +1294 -0
  308. package/dist/nodes/openai.js.map +1 -0
  309. package/dist/nodes/output.d.ts +29 -0
  310. package/dist/nodes/output.d.ts.map +1 -0
  311. package/dist/nodes/output.js +87 -0
  312. package/dist/nodes/output.js.map +1 -0
  313. package/dist/nodes/sandbox.d.ts +67 -0
  314. package/dist/nodes/sandbox.d.ts.map +1 -0
  315. package/dist/nodes/sandbox.js +681 -0
  316. package/dist/nodes/sandbox.js.map +1 -0
  317. package/dist/nodes/search.d.ts +117 -0
  318. package/dist/nodes/search.d.ts.map +1 -0
  319. package/dist/nodes/search.js +607 -0
  320. package/dist/nodes/search.js.map +1 -0
  321. package/dist/nodes/team.d.ts +74 -0
  322. package/dist/nodes/team.d.ts.map +1 -0
  323. package/dist/nodes/team.js +304 -0
  324. package/dist/nodes/team.js.map +1 -0
  325. package/dist/nodes/text-extra.d.ts +633 -0
  326. package/dist/nodes/text-extra.d.ts.map +1 -0
  327. package/dist/nodes/text-extra.js +2226 -0
  328. package/dist/nodes/text-extra.js.map +1 -0
  329. package/dist/nodes/tool-agents.d.ts +334 -0
  330. package/dist/nodes/tool-agents.d.ts.map +1 -0
  331. package/dist/nodes/tool-agents.js +1861 -0
  332. package/dist/nodes/tool-agents.js.map +1 -0
  333. package/dist/nodes/triggers.d.ts +107 -0
  334. package/dist/nodes/triggers.d.ts.map +1 -0
  335. package/dist/nodes/triggers.js +706 -0
  336. package/dist/nodes/triggers.js.map +1 -0
  337. package/dist/nodes/vector.d.ts +168 -0
  338. package/dist/nodes/vector.d.ts.map +1 -0
  339. package/dist/nodes/vector.js +1121 -0
  340. package/dist/nodes/vector.js.map +1 -0
  341. package/dist/nodes/video.d.ts +387 -0
  342. package/dist/nodes/video.d.ts.map +1 -0
  343. package/dist/nodes/video.js +2361 -0
  344. package/dist/nodes/video.js.map +1 -0
  345. package/dist/nodes/workflow.d.ts +24 -0
  346. package/dist/nodes/workflow.d.ts.map +1 -0
  347. package/dist/nodes/workflow.js +146 -0
  348. package/dist/nodes/workflow.js.map +1 -0
  349. package/dist/nodes/workspace.d.ts +203 -0
  350. package/dist/nodes/workspace.d.ts.map +1 -0
  351. package/dist/nodes/workspace.js +795 -0
  352. package/dist/nodes/workspace.js.map +1 -0
  353. package/package.json +103 -0
@@ -0,0 +1,1395 @@
1
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
2
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
6
+ };
7
+ import { BaseNode, prop } from "@nodetool-ai/node-sdk";
8
+ import { promises as fs } from "node:fs";
9
+ import path from "node:path";
10
+ import { fileURLToPath } from "node:url";
11
+ import sharp from "sharp";
12
+ function toBytes(data) {
13
+ if (!data)
14
+ return new Uint8Array();
15
+ if (data instanceof Uint8Array)
16
+ return data;
17
+ return Uint8Array.from(Buffer.from(data, "base64"));
18
+ }
19
+ function imageBytes(image) {
20
+ if (!image || typeof image !== "object")
21
+ return new Uint8Array();
22
+ return toBytes(image.data);
23
+ }
24
+ async function imageBytesAsync(image, context) {
25
+ if (!image || typeof image !== "object")
26
+ return new Uint8Array();
27
+ const ref = image;
28
+ if (ref.data)
29
+ return toBytes(ref.data);
30
+ if (typeof ref.uri === "string" && ref.uri) {
31
+ if (context?.storage) {
32
+ const stored = await context.storage.retrieve(ref.uri);
33
+ if (stored !== null)
34
+ return new Uint8Array(stored);
35
+ }
36
+ if (ref.uri.startsWith("file://")) {
37
+ return new Uint8Array(await fs.readFile(filePath(ref.uri)));
38
+ }
39
+ if (ref.uri.startsWith("http://") || ref.uri.startsWith("https://")) {
40
+ const response = await fetch(ref.uri);
41
+ return new Uint8Array(await response.arrayBuffer());
42
+ }
43
+ }
44
+ return new Uint8Array();
45
+ }
46
+ function filePath(uriOrPath) {
47
+ if (uriOrPath.startsWith("file://")) {
48
+ try {
49
+ return fileURLToPath(new URL(uriOrPath));
50
+ }
51
+ catch {
52
+ // Fallback for non-standard URIs like file://C:\path
53
+ return uriOrPath.slice("file://".length);
54
+ }
55
+ }
56
+ return uriOrPath;
57
+ }
58
+ function dateName(name) {
59
+ const now = new Date();
60
+ const pad = (v) => String(v).padStart(2, "0");
61
+ return name
62
+ .replaceAll("%Y", String(now.getFullYear()))
63
+ .replaceAll("%m", pad(now.getMonth() + 1))
64
+ .replaceAll("%d", pad(now.getDate()))
65
+ .replaceAll("%H", pad(now.getHours()))
66
+ .replaceAll("%M", pad(now.getMinutes()))
67
+ .replaceAll("%S", pad(now.getSeconds()));
68
+ }
69
+ function imageRef(data, extras = {}) {
70
+ return {
71
+ type: "image",
72
+ data: Buffer.from(data).toString("base64"),
73
+ ...extras
74
+ };
75
+ }
76
+ function inferImageMime(uri, bytes) {
77
+ const lower = (uri ?? "").toLowerCase();
78
+ if (lower.endsWith(".jpg") || lower.endsWith(".jpeg"))
79
+ return "image/jpeg";
80
+ if (lower.endsWith(".webp"))
81
+ return "image/webp";
82
+ if (lower.endsWith(".gif"))
83
+ return "image/gif";
84
+ if (lower.endsWith(".bmp"))
85
+ return "image/bmp";
86
+ if (bytes.length < 4)
87
+ return "image/unknown";
88
+ if (bytes[0] === 0xff && bytes[1] === 0xd8)
89
+ return "image/jpeg";
90
+ if (bytes[0] === 0x47 && bytes[1] === 0x49)
91
+ return "image/gif";
92
+ if (bytes[0] === 0x42 && bytes[1] === 0x4d)
93
+ return "image/bmp";
94
+ if (bytes[0] === 0x52 && bytes[1] === 0x49 && bytes[8] === 0x57)
95
+ return "image/webp";
96
+ if (bytes[0] === 0x89 &&
97
+ bytes[1] === 0x50 &&
98
+ bytes[2] === 0x4e &&
99
+ bytes[3] === 0x47) {
100
+ return "image/png";
101
+ }
102
+ return "image/unknown";
103
+ }
104
+ function getModelConfig(props) {
105
+ const model = (props.model ?? {});
106
+ return {
107
+ providerId: typeof model.provider === "string" ? model.provider : "",
108
+ modelId: typeof model.id === "string" ? model.id : ""
109
+ };
110
+ }
111
+ const IMAGE_ASPECT_RATIOS = {
112
+ "21:9": [21, 9],
113
+ "16:9": [16, 9],
114
+ "3:2": [3, 2],
115
+ "7:5": [7, 5],
116
+ "4:3": [4, 3],
117
+ "5:4": [5, 4],
118
+ "1:1": [1, 1],
119
+ "9:16": [9, 16],
120
+ "2:3": [2, 3],
121
+ "5:7": [5, 7],
122
+ "3:4": [3, 4],
123
+ "4:5": [4, 5]
124
+ };
125
+ const IMAGE_RESOLUTION_PX = {
126
+ "1K": 1024,
127
+ "2K": 2048,
128
+ "4K": 4096
129
+ };
130
+ function resolveImageSize(resolution, aspectRatio) {
131
+ const base = IMAGE_RESOLUTION_PX[resolution] ?? 1024;
132
+ const [aw, ah] = IMAGE_ASPECT_RATIOS[aspectRatio] ?? [1, 1];
133
+ if (aw >= ah) {
134
+ const height = base;
135
+ const width = Math.round((height * aw) / ah);
136
+ return { width, height };
137
+ }
138
+ const width = base;
139
+ const height = Math.round((width * ah) / aw);
140
+ return { width, height };
141
+ }
142
+ const IMAGE_ASPECT_RATIO_VALUES = Object.keys(IMAGE_ASPECT_RATIOS);
143
+ const IMAGE_RESOLUTION_VALUES = Object.keys(IMAGE_RESOLUTION_PX);
144
+ const IMAGE_EDIT_STRENGTH_VALUES = [0.25, 0.5, 0.65, 0.75, 0.85, 1.0];
145
+ function hasProviderSupport(context, providerId, modelId) {
146
+ return (!!context &&
147
+ typeof context.runProviderPrediction === "function" &&
148
+ !!providerId &&
149
+ !!modelId);
150
+ }
151
+ async function metadataFor(bytes) {
152
+ try {
153
+ const md = await sharp(bytes).metadata();
154
+ return {
155
+ width: md.width ?? undefined,
156
+ height: md.height ?? undefined
157
+ };
158
+ }
159
+ catch {
160
+ return { width: undefined, height: undefined };
161
+ }
162
+ }
163
+ async function transformImage(image, operation, context) {
164
+ const bytes = await imageBytesAsync(image, context);
165
+ if (bytes.length === 0) {
166
+ return imageRef(bytes, {
167
+ uri: image.uri ?? "",
168
+ width: image.width ?? undefined,
169
+ height: image.height ?? undefined
170
+ });
171
+ }
172
+ try {
173
+ const outputBytes = await operation(sharp(bytes, { failOn: "none" }), bytes).toBuffer();
174
+ const meta = await metadataFor(outputBytes);
175
+ return imageRef(outputBytes, {
176
+ uri: image.uri ?? "",
177
+ mimeType: inferImageMime(image.uri, outputBytes),
178
+ width: meta.width,
179
+ height: meta.height
180
+ });
181
+ }
182
+ catch {
183
+ return imageRef(bytes, {
184
+ uri: image.uri ?? "",
185
+ width: image.width ?? undefined,
186
+ height: image.height ?? undefined
187
+ });
188
+ }
189
+ }
190
+ export class LoadImageFileNode extends BaseNode {
191
+ static nodeType = "nodetool.image.LoadImageFile";
192
+ static title = "Load Image File";
193
+ static description = "Read an image file from disk.\n image, input, load, file";
194
+ static metadataOutputTypes = {
195
+ output: "image"
196
+ };
197
+ async process() {
198
+ const p = filePath(String(this.path ?? ""));
199
+ const data = new Uint8Array(await fs.readFile(p));
200
+ const meta = await metadataFor(data);
201
+ return {
202
+ output: imageRef(data, {
203
+ uri: `file://${p}`,
204
+ mimeType: inferImageMime(p, data),
205
+ width: meta.width,
206
+ height: meta.height
207
+ })
208
+ };
209
+ }
210
+ }
211
+ __decorate([
212
+ prop({
213
+ type: "str",
214
+ default: "",
215
+ title: "Path",
216
+ description: "Path to the image file to read"
217
+ })
218
+ ], LoadImageFileNode.prototype, "path", void 0);
219
+ export class LoadImageFolderNode extends BaseNode {
220
+ static nodeType = "nodetool.image.LoadImageFolder";
221
+ static title = "Load Image Folder";
222
+ static description = "Load all images from a folder, optionally including subfolders.\n image, load, folder, files";
223
+ static metadataOutputTypes = {
224
+ image: "image",
225
+ path: "str",
226
+ images: "list"
227
+ };
228
+ static isStreamingOutput = true;
229
+ async process() {
230
+ const collected = [];
231
+ for await (const item of this._loadImages()) {
232
+ collected.push(item.image);
233
+ }
234
+ return {
235
+ image: collected[0] ?? {},
236
+ name: "",
237
+ images: collected
238
+ };
239
+ }
240
+ async *_loadImages() {
241
+ const raw = this.folder;
242
+ const folder = typeof raw === "string" && raw.length > 0
243
+ ? raw.startsWith("file:")
244
+ ? filePath(raw)
245
+ : raw
246
+ : typeof raw === "object" && raw !== null && typeof raw.uri === "string" && raw.uri.length > 0
247
+ ? filePath(raw.uri)
248
+ : "";
249
+ if (!folder)
250
+ return;
251
+ const extensions = Array.isArray(this.extensions)
252
+ ? this.extensions.map((e) => String(e).toLowerCase())
253
+ : [".png", ".jpg", ".jpeg", ".bmp", ".gif", ".webp", ".tiff"];
254
+ const patternStr = String(this.pattern ?? "");
255
+ const patternRegex = patternStr
256
+ ? new RegExp("^" +
257
+ patternStr
258
+ .replace(/[.+^${}()|[\]\\]/g, "\\$&")
259
+ .replace(/\*/g, ".*")
260
+ .replace(/\?/g, ".") +
261
+ "$", "i")
262
+ : null;
263
+ const files = [];
264
+ const collect = async (dir) => {
265
+ let entries;
266
+ try {
267
+ entries = await fs.readdir(dir, { withFileTypes: true });
268
+ }
269
+ catch {
270
+ // directory does not exist or is not accessible
271
+ return;
272
+ }
273
+ for (const entry of entries) {
274
+ if (entry.isDirectory() && this.include_subdirectories) {
275
+ await collect(path.join(dir, entry.name));
276
+ }
277
+ else if (entry.isFile()) {
278
+ files.push({ fullPath: path.join(dir, entry.name), name: entry.name });
279
+ }
280
+ }
281
+ };
282
+ await collect(folder);
283
+ for (const file of files) {
284
+ const ext = path.extname(file.name).toLowerCase();
285
+ if (!extensions.includes(ext))
286
+ continue;
287
+ if (patternRegex && !patternRegex.test(file.name))
288
+ continue;
289
+ const data = new Uint8Array(await fs.readFile(file.fullPath));
290
+ const meta = await metadataFor(data);
291
+ yield {
292
+ image: imageRef(data, {
293
+ uri: `file://${file.fullPath}`,
294
+ mimeType: inferImageMime(file.fullPath, data),
295
+ width: meta.width,
296
+ height: meta.height
297
+ }),
298
+ name: file.name
299
+ };
300
+ }
301
+ }
302
+ async *genProcess() {
303
+ const collected = [];
304
+ for await (const item of this._loadImages()) {
305
+ collected.push(item.image);
306
+ yield item;
307
+ }
308
+ yield { images: collected };
309
+ }
310
+ }
311
+ __decorate([
312
+ prop({
313
+ type: "str",
314
+ default: "",
315
+ title: "Folder",
316
+ description: "Folder to scan for images"
317
+ })
318
+ ], LoadImageFolderNode.prototype, "folder", void 0);
319
+ __decorate([
320
+ prop({
321
+ type: "bool",
322
+ default: false,
323
+ title: "Include Subdirectories",
324
+ description: "Include images in subfolders"
325
+ })
326
+ ], LoadImageFolderNode.prototype, "include_subdirectories", void 0);
327
+ __decorate([
328
+ prop({
329
+ type: "list[str]",
330
+ default: [".png", ".jpg", ".jpeg", ".bmp", ".gif", ".webp", ".tiff"],
331
+ title: "Extensions",
332
+ description: "Image file extensions to include"
333
+ })
334
+ ], LoadImageFolderNode.prototype, "extensions", void 0);
335
+ __decorate([
336
+ prop({
337
+ type: "str",
338
+ default: "",
339
+ title: "Pattern",
340
+ description: "Pattern to match image files"
341
+ })
342
+ ], LoadImageFolderNode.prototype, "pattern", void 0);
343
+ export class SaveImageFileImageNode extends BaseNode {
344
+ static nodeType = "nodetool.image.SaveImageFile";
345
+ static title = "Save Image File";
346
+ static description = "Write an image to disk.\n image, output, save, file";
347
+ static metadataOutputTypes = {
348
+ output: "image"
349
+ };
350
+ async process() {
351
+ const folder = String(this.folder ?? ".");
352
+ const filename = dateName(String(this.filename ?? "image.png"));
353
+ let p = filePath(path.resolve(folder, filename));
354
+ await fs.mkdir(path.dirname(p), { recursive: true });
355
+ if (!this.overwrite) {
356
+ const ext = path.extname(p);
357
+ const base = p.slice(0, p.length - ext.length);
358
+ let counter = 1;
359
+ while (true) {
360
+ try {
361
+ await fs.access(p);
362
+ p = `${base}_${counter}${ext}`;
363
+ counter++;
364
+ }
365
+ catch {
366
+ break;
367
+ }
368
+ }
369
+ }
370
+ await fs.writeFile(p, imageBytes(this.image));
371
+ return { output: p };
372
+ }
373
+ }
374
+ __decorate([
375
+ prop({
376
+ type: "image",
377
+ default: {
378
+ type: "image",
379
+ uri: "",
380
+ asset_id: null,
381
+ data: null,
382
+ metadata: null
383
+ },
384
+ title: "Image",
385
+ description: "The image to save"
386
+ })
387
+ ], SaveImageFileImageNode.prototype, "image", void 0);
388
+ __decorate([
389
+ prop({
390
+ type: "str",
391
+ default: "",
392
+ title: "Folder",
393
+ description: "Folder where the file will be saved"
394
+ })
395
+ ], SaveImageFileImageNode.prototype, "folder", void 0);
396
+ __decorate([
397
+ prop({
398
+ type: "str",
399
+ default: "",
400
+ title: "Filename",
401
+ description: "\n The name of the image file.\n You can use time and date variables to create unique names:\n %Y - Year\n %m - Month\n %d - Day\n %H - Hour\n %M - Minute\n %S - Second\n "
402
+ })
403
+ ], SaveImageFileImageNode.prototype, "filename", void 0);
404
+ __decorate([
405
+ prop({
406
+ type: "bool",
407
+ default: false,
408
+ title: "Overwrite",
409
+ description: "Overwrite the file if it already exists, otherwise file will be renamed"
410
+ })
411
+ ], SaveImageFileImageNode.prototype, "overwrite", void 0);
412
+ export class LoadImageAssetsNode extends BaseNode {
413
+ static nodeType = "nodetool.image.LoadImageAssets";
414
+ static title = "Load Image Assets";
415
+ static description = "Load images from an asset folder.\n load, image, file, import";
416
+ static metadataOutputTypes = {
417
+ image: "image",
418
+ name: "str",
419
+ images: "list"
420
+ };
421
+ static isStreamingOutput = true;
422
+ async process() {
423
+ const loader = new LoadImageFolderNode();
424
+ loader.assign({ folder: this.folder ?? "." });
425
+ const result = await loader.process();
426
+ return result;
427
+ }
428
+ async *genProcess() {
429
+ const loader = new LoadImageFolderNode();
430
+ loader.assign({ folder: this.folder ?? "." });
431
+ for await (const item of loader.genProcess()) {
432
+ yield item;
433
+ }
434
+ }
435
+ }
436
+ __decorate([
437
+ prop({
438
+ type: "folder",
439
+ default: {
440
+ type: "folder",
441
+ uri: "",
442
+ asset_id: null,
443
+ data: null,
444
+ metadata: null
445
+ },
446
+ title: "Folder",
447
+ description: "The asset folder to load the images from."
448
+ })
449
+ ], LoadImageAssetsNode.prototype, "folder", void 0);
450
+ export class SaveImageNode extends BaseNode {
451
+ static nodeType = "nodetool.image.SaveImage";
452
+ static title = "Save Image Asset";
453
+ static description = "Save an image to specified asset folder with customizable name format.\n save, image, folder, naming";
454
+ static metadataOutputTypes = {
455
+ output: "image"
456
+ };
457
+ async process(context) {
458
+ const bytes = await imageBytesAsync(this.image, context);
459
+ if (bytes.length === 0)
460
+ throw new Error("The input image is not connected.");
461
+ const name = dateName(String(this.name ?? "image.png"));
462
+ const mime = inferImageMime(undefined, bytes);
463
+ const meta = await metadataFor(bytes);
464
+ // Create asset via context (persists to DB + storage)
465
+ if (context && typeof context.createAsset === "function") {
466
+ const folderRef = this.folder;
467
+ const parentId = folderRef?.asset_id ?? null;
468
+ const asset = (await context.createAsset({
469
+ name,
470
+ contentType: mime === "image/unknown" ? "image/png" : mime,
471
+ content: bytes,
472
+ parentId,
473
+ nodeId: this.__node_id || null
474
+ }));
475
+ const assetId = asset.id;
476
+ const ext = name.includes(".") ? name.slice(name.lastIndexOf(".")) : ".png";
477
+ return {
478
+ output: imageRef(bytes, {
479
+ uri: `asset://${assetId}${ext}`,
480
+ mimeType: mime,
481
+ width: meta.width,
482
+ height: meta.height
483
+ })
484
+ };
485
+ }
486
+ // Fallback: write to filesystem
487
+ const folder = typeof this.folder === "string" ? this.folder : ".";
488
+ const full = path.resolve(folder, name);
489
+ await fs.mkdir(path.dirname(full), { recursive: true });
490
+ await fs.writeFile(full, bytes);
491
+ return {
492
+ output: imageRef(bytes, {
493
+ uri: `file://${full}`,
494
+ mimeType: mime,
495
+ width: meta.width,
496
+ height: meta.height
497
+ })
498
+ };
499
+ }
500
+ }
501
+ __decorate([
502
+ prop({
503
+ type: "image",
504
+ default: {
505
+ type: "image",
506
+ uri: "",
507
+ asset_id: null,
508
+ data: null,
509
+ metadata: null
510
+ },
511
+ title: "Image",
512
+ description: "The image to save."
513
+ })
514
+ ], SaveImageNode.prototype, "image", void 0);
515
+ __decorate([
516
+ prop({
517
+ type: "folder",
518
+ default: {
519
+ type: "folder",
520
+ uri: "",
521
+ asset_id: null,
522
+ data: null,
523
+ metadata: null
524
+ },
525
+ title: "Folder",
526
+ description: "The asset folder to save the image in."
527
+ })
528
+ ], SaveImageNode.prototype, "folder", void 0);
529
+ __decorate([
530
+ prop({
531
+ type: "str",
532
+ default: "%Y-%m-%d_%H-%M-%S.png",
533
+ title: "Name",
534
+ description: "\n Name of the output file.\n You can use time and date variables to create unique names:\n %Y - Year\n %m - Month\n %d - Day\n %H - Hour\n %M - Minute\n %S - Second\n "
535
+ })
536
+ ], SaveImageNode.prototype, "name", void 0);
537
+ export class GetMetadataNode extends BaseNode {
538
+ static nodeType = "nodetool.image.GetMetadata";
539
+ static title = "Get Metadata";
540
+ static description = "Get metadata about the input image.\n metadata, properties, analysis, information";
541
+ static metadataOutputTypes = {
542
+ format: "str",
543
+ mode: "str",
544
+ width: "int",
545
+ height: "int",
546
+ channels: "int"
547
+ };
548
+ async process(context) {
549
+ const image = (this.image ?? {});
550
+ const bytes = await imageBytesAsync(image, context);
551
+ try {
552
+ const md = await sharp(bytes).metadata();
553
+ const formatMap = {
554
+ jpeg: "JPEG",
555
+ png: "PNG",
556
+ webp: "WEBP",
557
+ gif: "GIF",
558
+ tiff: "TIFF",
559
+ svg: "SVG",
560
+ heif: "HEIF",
561
+ avif: "AVIF",
562
+ raw: "RAW"
563
+ };
564
+ const channelsToMode = {
565
+ 1: "L",
566
+ 2: "LA",
567
+ 3: "RGB",
568
+ 4: "RGBA"
569
+ };
570
+ return {
571
+ format: formatMap[md.format ?? ""] ?? (md.format ?? "unknown").toUpperCase(),
572
+ mode: channelsToMode[md.channels ?? 3] ?? "RGB",
573
+ width: md.width ?? 0,
574
+ height: md.height ?? 0,
575
+ channels: md.channels ?? 0
576
+ };
577
+ }
578
+ catch {
579
+ return {
580
+ format: "unknown",
581
+ mode: "RGB",
582
+ width: image.width ?? 0,
583
+ height: image.height ?? 0,
584
+ channels: 0
585
+ };
586
+ }
587
+ }
588
+ }
589
+ __decorate([
590
+ prop({
591
+ type: "image",
592
+ default: {
593
+ type: "image",
594
+ uri: "",
595
+ asset_id: null,
596
+ data: null,
597
+ metadata: null
598
+ },
599
+ title: "Image",
600
+ description: "The input image."
601
+ })
602
+ ], GetMetadataNode.prototype, "image", void 0);
603
+ export class BatchToListNode extends BaseNode {
604
+ static nodeType = "nodetool.image.BatchToList";
605
+ static title = "Batch To List";
606
+ static description = "Convert an image batch to a list of image references.\n batch, list, images, processing";
607
+ static metadataOutputTypes = {
608
+ output: "list[image]"
609
+ };
610
+ async process() {
611
+ const batch = this.batch;
612
+ if (!batch) {
613
+ throw new Error("Batch input is empty.");
614
+ }
615
+ const batchObj = batch;
616
+ if (batchObj.data == null) {
617
+ throw new Error("Batch data is null.");
618
+ }
619
+ if (!Array.isArray(batchObj.data)) {
620
+ // Single image ref — wrap in list
621
+ return { output: [batch] };
622
+ }
623
+ // Unwrap batch data into individual ImageRefs
624
+ const output = batchObj.data.map((item) => {
625
+ if (item instanceof Uint8Array || typeof item === "string") {
626
+ return imageRef(toBytes(item));
627
+ }
628
+ return item;
629
+ });
630
+ return { output };
631
+ }
632
+ }
633
+ __decorate([
634
+ prop({
635
+ type: "image",
636
+ default: {
637
+ type: "image",
638
+ uri: "",
639
+ asset_id: null,
640
+ data: null,
641
+ metadata: null
642
+ },
643
+ title: "Batch",
644
+ description: "The batch of images to convert."
645
+ })
646
+ ], BatchToListNode.prototype, "batch", void 0);
647
+ export class ImagesToListNode extends BaseNode {
648
+ static nodeType = "nodetool.image.ImagesToList";
649
+ static title = "Images To List";
650
+ static description = "Convert all dynamic properties to a list of image references.\n list, images, processing";
651
+ static metadataOutputTypes = {
652
+ output: "list[image]"
653
+ };
654
+ static isDynamic = true;
655
+ async process() {
656
+ const out = [];
657
+ for (const [, value] of this.dynamicProps) {
658
+ if (value == null)
659
+ continue;
660
+ if (Array.isArray(value)) {
661
+ for (const item of value) {
662
+ if (item != null)
663
+ out.push(item);
664
+ }
665
+ }
666
+ else {
667
+ out.push(value);
668
+ }
669
+ }
670
+ return { output: out };
671
+ }
672
+ }
673
+ class TransformImageNode extends BaseNode {
674
+ transformMeta() {
675
+ const image = (this.image ?? {});
676
+ return {
677
+ width: Number(this.width ?? image.width ?? 0) || null,
678
+ height: Number(this.height ?? image.height ?? 0) || null
679
+ };
680
+ }
681
+ }
682
+ export class PasteNode extends TransformImageNode {
683
+ static nodeType = "nodetool.image.Paste";
684
+ static title = "Paste";
685
+ static description = "Paste one image onto another at specified coordinates.\n paste, composite, positioning, overlay";
686
+ static metadataOutputTypes = {
687
+ output: "image"
688
+ };
689
+ async process(context) {
690
+ const image = (this.image ?? {});
691
+ const paste = (this.paste ?? {});
692
+ const left = Math.max(0, Number(this.left ?? 0));
693
+ const top = Math.max(0, Number(this.top ?? 0));
694
+ const baseBytes = await imageBytesAsync(image, context);
695
+ const overlayBytes = await imageBytesAsync(paste, context);
696
+ if (baseBytes.length === 0 || overlayBytes.length === 0) {
697
+ return {
698
+ output: imageRef(baseBytes, {
699
+ uri: image.uri ?? "",
700
+ ...this.transformMeta()
701
+ })
702
+ };
703
+ }
704
+ try {
705
+ const outputBytes = await sharp(baseBytes, { failOn: "none" })
706
+ .composite([{ input: Buffer.from(overlayBytes), left, top }])
707
+ .toBuffer();
708
+ const meta = await metadataFor(outputBytes);
709
+ return {
710
+ output: imageRef(outputBytes, {
711
+ uri: image.uri ?? "",
712
+ mimeType: inferImageMime(image.uri, outputBytes),
713
+ width: meta.width,
714
+ height: meta.height
715
+ })
716
+ };
717
+ }
718
+ catch {
719
+ return {
720
+ output: imageRef(baseBytes, {
721
+ uri: image.uri ?? "",
722
+ ...this.transformMeta()
723
+ })
724
+ };
725
+ }
726
+ }
727
+ }
728
+ __decorate([
729
+ prop({
730
+ type: "image",
731
+ default: {
732
+ type: "image",
733
+ uri: "",
734
+ asset_id: null,
735
+ data: null,
736
+ metadata: null
737
+ },
738
+ title: "Image",
739
+ description: "The image to paste into."
740
+ })
741
+ ], PasteNode.prototype, "image", void 0);
742
+ __decorate([
743
+ prop({
744
+ type: "image",
745
+ default: {
746
+ type: "image",
747
+ uri: "",
748
+ asset_id: null,
749
+ data: null,
750
+ metadata: null
751
+ },
752
+ title: "Paste",
753
+ description: "The image to paste."
754
+ })
755
+ ], PasteNode.prototype, "paste", void 0);
756
+ __decorate([
757
+ prop({
758
+ type: "int",
759
+ default: 0,
760
+ title: "Left",
761
+ description: "The left coordinate.",
762
+ min: 0,
763
+ max: 4096
764
+ })
765
+ ], PasteNode.prototype, "left", void 0);
766
+ __decorate([
767
+ prop({
768
+ type: "int",
769
+ default: 0,
770
+ title: "Top",
771
+ description: "The top coordinate.",
772
+ min: 0,
773
+ max: 4096
774
+ })
775
+ ], PasteNode.prototype, "top", void 0);
776
+ export class ScaleNode extends TransformImageNode {
777
+ static nodeType = "nodetool.image.Scale";
778
+ static title = "Scale";
779
+ static description = "Enlarge or shrink an image by a scale factor.\n image, resize, scale";
780
+ static metadataOutputTypes = {
781
+ output: "image"
782
+ };
783
+ async process(context) {
784
+ const image = (this.image ?? {});
785
+ const requestedScale = Number(this.scale ?? 0);
786
+ const targetWidth = 0;
787
+ const targetHeight = 0;
788
+ const scale = requestedScale > 0
789
+ ? requestedScale
790
+ : targetWidth > 0 && (image.width ?? 0) > 0
791
+ ? targetWidth / Number(image.width)
792
+ : targetHeight > 0 && (image.height ?? 0) > 0
793
+ ? targetHeight / Number(image.height)
794
+ : 1;
795
+ const output = (await transformImage(image, (instance) => {
796
+ const fallbackWidth = image.width ?? 1;
797
+ const fallbackHeight = image.height ?? 1;
798
+ return instance.resize({
799
+ width: Math.max(1, Math.round(fallbackWidth * scale)),
800
+ height: Math.max(1, Math.round(fallbackHeight * scale))
801
+ });
802
+ }, context));
803
+ const fallbackWidth = targetWidth > 0
804
+ ? targetWidth
805
+ : image.width != null
806
+ ? Math.max(1, Math.round(Number(image.width) * scale))
807
+ : null;
808
+ const fallbackHeight = targetHeight > 0
809
+ ? targetHeight
810
+ : image.height != null
811
+ ? Math.max(1, Math.round(Number(image.height) * scale))
812
+ : null;
813
+ return {
814
+ output: {
815
+ ...output,
816
+ width: fallbackWidth ?? output.width,
817
+ height: fallbackHeight ?? output.height
818
+ }
819
+ };
820
+ }
821
+ }
822
+ __decorate([
823
+ prop({
824
+ type: "image",
825
+ default: {
826
+ type: "image",
827
+ uri: "",
828
+ asset_id: null,
829
+ data: null,
830
+ metadata: null
831
+ },
832
+ title: "Image",
833
+ description: "The image to scale."
834
+ })
835
+ ], ScaleNode.prototype, "image", void 0);
836
+ __decorate([
837
+ prop({
838
+ type: "float",
839
+ default: 1,
840
+ title: "Scale",
841
+ description: "The scale factor.",
842
+ min: 0,
843
+ max: 10
844
+ })
845
+ ], ScaleNode.prototype, "scale", void 0);
846
+ export class ResizeNode extends TransformImageNode {
847
+ static nodeType = "nodetool.image.Resize";
848
+ static title = "Resize";
849
+ static description = "Change image dimensions to specified width and height.\n image, resize";
850
+ static metadataOutputTypes = {
851
+ output: "image"
852
+ };
853
+ async process(context) {
854
+ const image = (this.image ?? {});
855
+ const width = Number(this.width ?? image.width ?? 0) || null;
856
+ const height = Number(this.height ?? image.height ?? 0) || null;
857
+ const output = (await transformImage(image, (instance) => instance.resize(width ?? undefined, height ?? undefined), context));
858
+ return {
859
+ output: {
860
+ ...output,
861
+ width: output.width ?? width,
862
+ height: output.height ?? height
863
+ }
864
+ };
865
+ }
866
+ }
867
+ __decorate([
868
+ prop({
869
+ type: "image",
870
+ default: {
871
+ type: "image",
872
+ uri: "",
873
+ asset_id: null,
874
+ data: null,
875
+ metadata: null
876
+ },
877
+ title: "Image",
878
+ description: "The image to resize."
879
+ })
880
+ ], ResizeNode.prototype, "image", void 0);
881
+ __decorate([
882
+ prop({
883
+ type: "int",
884
+ default: 512,
885
+ title: "Width",
886
+ description: "The target width.",
887
+ min: 0,
888
+ max: 4096
889
+ })
890
+ ], ResizeNode.prototype, "width", void 0);
891
+ __decorate([
892
+ prop({
893
+ type: "int",
894
+ default: 512,
895
+ title: "Height",
896
+ description: "The target height.",
897
+ min: 0,
898
+ max: 4096
899
+ })
900
+ ], ResizeNode.prototype, "height", void 0);
901
+ export class CropNode extends TransformImageNode {
902
+ static nodeType = "nodetool.image.Crop";
903
+ static title = "Crop";
904
+ static description = "Crop an image to specified coordinates.\n image, crop";
905
+ static metadataOutputTypes = {
906
+ output: "image"
907
+ };
908
+ async process(context) {
909
+ const image = (this.image ?? {});
910
+ const left = Math.max(0, Number(this.left ?? 0));
911
+ const top = Math.max(0, Number(this.top ?? 0));
912
+ const right = Number(this.right ?? image.width ?? 0);
913
+ const bottom = Number(this.bottom ?? image.height ?? 0);
914
+ const width = Math.max(1, right - left);
915
+ const height = Math.max(1, bottom - top);
916
+ const output = (await transformImage(image, (instance) => instance.extract({ left, top, width, height }), context));
917
+ return {
918
+ output: {
919
+ ...output,
920
+ width: output.width ?? width,
921
+ height: output.height ?? height
922
+ }
923
+ };
924
+ }
925
+ }
926
+ __decorate([
927
+ prop({
928
+ type: "image",
929
+ default: {
930
+ type: "image",
931
+ uri: "",
932
+ asset_id: null,
933
+ data: null,
934
+ metadata: null
935
+ },
936
+ title: "Image",
937
+ description: "The image to crop."
938
+ })
939
+ ], CropNode.prototype, "image", void 0);
940
+ __decorate([
941
+ prop({
942
+ type: "int",
943
+ default: 0,
944
+ title: "Left",
945
+ description: "The left coordinate.",
946
+ min: 0,
947
+ max: 4096
948
+ })
949
+ ], CropNode.prototype, "left", void 0);
950
+ __decorate([
951
+ prop({
952
+ type: "int",
953
+ default: 0,
954
+ title: "Top",
955
+ description: "The top coordinate.",
956
+ min: 0,
957
+ max: 4096
958
+ })
959
+ ], CropNode.prototype, "top", void 0);
960
+ __decorate([
961
+ prop({
962
+ type: "int",
963
+ default: 512,
964
+ title: "Right",
965
+ description: "The right coordinate.",
966
+ min: 0,
967
+ max: 4096
968
+ })
969
+ ], CropNode.prototype, "right", void 0);
970
+ __decorate([
971
+ prop({
972
+ type: "int",
973
+ default: 512,
974
+ title: "Bottom",
975
+ description: "The bottom coordinate.",
976
+ min: 0,
977
+ max: 4096
978
+ })
979
+ ], CropNode.prototype, "bottom", void 0);
980
+ export class FitNode extends TransformImageNode {
981
+ static nodeType = "nodetool.image.Fit";
982
+ static title = "Fit";
983
+ static description = "Resize an image to fit within specified dimensions while preserving aspect ratio.\n image, resize, fit";
984
+ static metadataOutputTypes = {
985
+ output: "image"
986
+ };
987
+ async process(context) {
988
+ const image = (this.image ?? {});
989
+ const width = Math.max(1, Number(this.width ?? image.width ?? 512));
990
+ const height = Math.max(1, Number(this.height ?? image.height ?? 512));
991
+ const output = (await transformImage(image, (instance) => instance.resize(width, height, { fit: "cover", position: "centre" }), context));
992
+ return {
993
+ output: {
994
+ ...output,
995
+ width: output.width ?? width,
996
+ height: output.height ?? height
997
+ }
998
+ };
999
+ }
1000
+ }
1001
+ __decorate([
1002
+ prop({
1003
+ type: "image",
1004
+ default: {
1005
+ type: "image",
1006
+ uri: "",
1007
+ asset_id: null,
1008
+ data: null,
1009
+ metadata: null
1010
+ },
1011
+ title: "Image",
1012
+ description: "The image to fit."
1013
+ })
1014
+ ], FitNode.prototype, "image", void 0);
1015
+ __decorate([
1016
+ prop({
1017
+ type: "int",
1018
+ default: 512,
1019
+ title: "Width",
1020
+ description: "Width to fit to.",
1021
+ min: 1,
1022
+ max: 4096
1023
+ })
1024
+ ], FitNode.prototype, "width", void 0);
1025
+ __decorate([
1026
+ prop({
1027
+ type: "int",
1028
+ default: 512,
1029
+ title: "Height",
1030
+ description: "Height to fit to.",
1031
+ min: 1,
1032
+ max: 4096
1033
+ })
1034
+ ], FitNode.prototype, "height", void 0);
1035
+ export class TextToImageNode extends BaseNode {
1036
+ static nodeType = "nodetool.image.TextToImage";
1037
+ static title = "Text To Image";
1038
+ static description = "Generate images from text prompts using any supported image provider. Automatically routes to the appropriate backend (HuggingFace, FAL, MLX).\n image, generation, AI, text-to-image, t2i";
1039
+ static metadataOutputTypes = {
1040
+ output: "image"
1041
+ };
1042
+ static basicFields = [
1043
+ "model",
1044
+ "prompt",
1045
+ "aspect_ratio",
1046
+ "resolution"
1047
+ ];
1048
+ static exposeAsTool = true;
1049
+ static autoSaveAsset = true;
1050
+ async process(context) {
1051
+ const prompt = String(this.prompt ?? "");
1052
+ const aspectRatio = String(this.aspect_ratio ?? "1:1");
1053
+ const resolution = String(this.resolution ?? "1K");
1054
+ const { width, height } = resolveImageSize(resolution, aspectRatio);
1055
+ const { providerId, modelId } = getModelConfig(this.serialize());
1056
+ if (!hasProviderSupport(context, providerId, modelId)) {
1057
+ throw new Error("No provider available for text-to-image generation.");
1058
+ }
1059
+ const output = (await context.runProviderPrediction({
1060
+ provider: providerId,
1061
+ capability: "text_to_image",
1062
+ model: modelId,
1063
+ params: {
1064
+ prompt,
1065
+ width,
1066
+ height,
1067
+ aspect_ratio: aspectRatio,
1068
+ resolution,
1069
+ negative_prompt: this.negative_prompt
1070
+ }
1071
+ }));
1072
+ const meta = await metadataFor(output);
1073
+ return {
1074
+ output: imageRef(output, {
1075
+ mimeType: inferImageMime(undefined, output),
1076
+ width: meta.width ?? width,
1077
+ height: meta.height ?? height
1078
+ })
1079
+ };
1080
+ }
1081
+ }
1082
+ __decorate([
1083
+ prop({
1084
+ type: "image_model",
1085
+ default: {
1086
+ type: "image_model",
1087
+ provider: "huggingface_fal_ai",
1088
+ id: "fal-ai/flux/schnell",
1089
+ name: "FLUX.1 Schnell",
1090
+ path: null,
1091
+ supported_tasks: []
1092
+ },
1093
+ title: "Model",
1094
+ description: "The image generation model to use"
1095
+ })
1096
+ ], TextToImageNode.prototype, "model", void 0);
1097
+ __decorate([
1098
+ prop({
1099
+ type: "str",
1100
+ default: "A cat holding a sign that says hello world",
1101
+ title: "Prompt",
1102
+ description: "Text prompt describing the desired image"
1103
+ })
1104
+ ], TextToImageNode.prototype, "prompt", void 0);
1105
+ __decorate([
1106
+ prop({
1107
+ type: "str",
1108
+ default: "",
1109
+ title: "Negative Prompt",
1110
+ description: "Text prompt describing what to avoid in the image"
1111
+ })
1112
+ ], TextToImageNode.prototype, "negative_prompt", void 0);
1113
+ __decorate([
1114
+ prop({
1115
+ type: "str",
1116
+ default: "1:1",
1117
+ title: "Aspect Ratio",
1118
+ description: "Aspect ratio of the generated image",
1119
+ values: IMAGE_ASPECT_RATIO_VALUES,
1120
+ json_schema_extra: { type: "media_aspect_ratio_image" }
1121
+ })
1122
+ ], TextToImageNode.prototype, "aspect_ratio", void 0);
1123
+ __decorate([
1124
+ prop({
1125
+ type: "str",
1126
+ default: "1K",
1127
+ title: "Resolution",
1128
+ description: "Output resolution (short edge in pixels)",
1129
+ values: IMAGE_RESOLUTION_VALUES,
1130
+ json_schema_extra: { type: "media_resolution_image" }
1131
+ })
1132
+ ], TextToImageNode.prototype, "resolution", void 0);
1133
+ __decorate([
1134
+ prop({
1135
+ type: "int",
1136
+ default: 0,
1137
+ title: "Timeout Seconds",
1138
+ description: "Timeout in seconds for API calls (0 = use provider default)",
1139
+ min: 0,
1140
+ max: 3600
1141
+ })
1142
+ ], TextToImageNode.prototype, "timeout_seconds", void 0);
1143
+ export class ImageToImageNode extends BaseNode {
1144
+ static nodeType = "nodetool.image.ImageToImage";
1145
+ static title = "Image To Image";
1146
+ static description = "Transform images using text prompts with any supported image provider. Automatically routes to the appropriate backend (HuggingFace, FAL, MLX).\n image, transformation, AI, image-to-image, i2i";
1147
+ static metadataOutputTypes = {
1148
+ output: "image"
1149
+ };
1150
+ static basicFields = [
1151
+ "model",
1152
+ "image",
1153
+ "prompt",
1154
+ "strength",
1155
+ "aspect_ratio",
1156
+ "resolution"
1157
+ ];
1158
+ static autoSaveAsset = true;
1159
+ static exposeAsTool = true;
1160
+ async process(context) {
1161
+ const image = (this.image ?? {});
1162
+ const bytes = await imageBytesAsync(image, context);
1163
+ if (bytes.length === 0) {
1164
+ throw new Error("The input image is empty.");
1165
+ }
1166
+ const aspectRatio = String(this.aspect_ratio ?? "1:1");
1167
+ const resolution = String(this.resolution ?? "1K");
1168
+ const { width, height } = resolveImageSize(resolution, aspectRatio);
1169
+ const { providerId, modelId } = getModelConfig(this.serialize());
1170
+ if (!hasProviderSupport(context, providerId, modelId)) {
1171
+ throw new Error("No provider available for image-to-image generation.");
1172
+ }
1173
+ const output = (await context.runProviderPrediction({
1174
+ provider: providerId,
1175
+ capability: "image_to_image",
1176
+ model: modelId,
1177
+ params: {
1178
+ image: bytes,
1179
+ prompt: String(this.prompt ?? ""),
1180
+ negative_prompt: this.negative_prompt,
1181
+ target_width: width,
1182
+ target_height: height,
1183
+ aspect_ratio: aspectRatio,
1184
+ resolution,
1185
+ strength: this.strength,
1186
+ scheduler: this.scheduler
1187
+ }
1188
+ }));
1189
+ const meta = await metadataFor(output);
1190
+ return {
1191
+ output: imageRef(output, {
1192
+ uri: image.uri ?? "",
1193
+ mimeType: inferImageMime(image.uri, output),
1194
+ width: meta.width,
1195
+ height: meta.height
1196
+ })
1197
+ };
1198
+ }
1199
+ }
1200
+ __decorate([
1201
+ prop({
1202
+ type: "image_model",
1203
+ default: {
1204
+ type: "image_model",
1205
+ provider: "huggingface_fal_ai",
1206
+ id: "fal-ai/flux/dev",
1207
+ name: "FLUX.1 Dev",
1208
+ path: null,
1209
+ supported_tasks: []
1210
+ },
1211
+ title: "Model",
1212
+ description: "The image generation model to use"
1213
+ })
1214
+ ], ImageToImageNode.prototype, "model", void 0);
1215
+ __decorate([
1216
+ prop({
1217
+ type: "image",
1218
+ default: {
1219
+ type: "image",
1220
+ uri: "",
1221
+ asset_id: null,
1222
+ data: null,
1223
+ metadata: null
1224
+ },
1225
+ title: "Image",
1226
+ description: "Input image to transform"
1227
+ })
1228
+ ], ImageToImageNode.prototype, "image", void 0);
1229
+ __decorate([
1230
+ prop({
1231
+ type: "str",
1232
+ default: "A photorealistic version of the input image",
1233
+ title: "Prompt",
1234
+ description: "Text prompt describing the desired transformation"
1235
+ })
1236
+ ], ImageToImageNode.prototype, "prompt", void 0);
1237
+ __decorate([
1238
+ prop({
1239
+ type: "str",
1240
+ default: "",
1241
+ title: "Negative Prompt",
1242
+ description: "Text prompt describing what to avoid"
1243
+ })
1244
+ ], ImageToImageNode.prototype, "negative_prompt", void 0);
1245
+ __decorate([
1246
+ prop({
1247
+ type: "float",
1248
+ default: 0.65,
1249
+ title: "Strength",
1250
+ description: "How much to transform the input image (subtle = minor edit, strong = major edit)",
1251
+ values: IMAGE_EDIT_STRENGTH_VALUES,
1252
+ json_schema_extra: { type: "media_strength" }
1253
+ })
1254
+ ], ImageToImageNode.prototype, "strength", void 0);
1255
+ __decorate([
1256
+ prop({
1257
+ type: "str",
1258
+ default: "1:1",
1259
+ title: "Aspect Ratio",
1260
+ description: "Aspect ratio of the output image",
1261
+ values: IMAGE_ASPECT_RATIO_VALUES,
1262
+ json_schema_extra: { type: "media_aspect_ratio_image" }
1263
+ })
1264
+ ], ImageToImageNode.prototype, "aspect_ratio", void 0);
1265
+ __decorate([
1266
+ prop({
1267
+ type: "str",
1268
+ default: "1K",
1269
+ title: "Resolution",
1270
+ description: "Output resolution (short edge in pixels)",
1271
+ values: IMAGE_RESOLUTION_VALUES,
1272
+ json_schema_extra: { type: "media_resolution_image" }
1273
+ })
1274
+ ], ImageToImageNode.prototype, "resolution", void 0);
1275
+ __decorate([
1276
+ prop({
1277
+ type: "str",
1278
+ default: "",
1279
+ title: "Scheduler",
1280
+ description: "Scheduler to use (provider-specific)"
1281
+ })
1282
+ ], ImageToImageNode.prototype, "scheduler", void 0);
1283
+ __decorate([
1284
+ prop({
1285
+ type: "int",
1286
+ default: 0,
1287
+ title: "Timeout Seconds",
1288
+ description: "Timeout in seconds for API calls (0 = use provider default)",
1289
+ min: 0,
1290
+ max: 3600
1291
+ })
1292
+ ], ImageToImageNode.prototype, "timeout_seconds", void 0);
1293
+ export class RotateNode extends TransformImageNode {
1294
+ static nodeType = "nodetool.image.Rotate";
1295
+ static title = "Rotate";
1296
+ static description = "Rotate an image by a specified angle in degrees.\n image, rotate, angle, transform, orientation";
1297
+ static metadataOutputTypes = {
1298
+ output: "image"
1299
+ };
1300
+ async process(context) {
1301
+ const image = (this.image ?? {});
1302
+ const angle = Number(this.angle ?? 0);
1303
+ if (angle === 0) {
1304
+ const bytes = await imageBytesAsync(image, context);
1305
+ return {
1306
+ output: imageRef(bytes, {
1307
+ uri: image.uri ?? "",
1308
+ width: image.width ?? undefined,
1309
+ height: image.height ?? undefined
1310
+ })
1311
+ };
1312
+ }
1313
+ return transformImage(image, (instance) => instance.rotate(angle, { background: { r: 0, g: 0, b: 0, alpha: 0 } }), context);
1314
+ }
1315
+ }
1316
+ __decorate([
1317
+ prop({
1318
+ type: "image",
1319
+ default: {
1320
+ type: "image",
1321
+ uri: "",
1322
+ asset_id: null,
1323
+ data: null,
1324
+ metadata: null
1325
+ },
1326
+ title: "Image",
1327
+ description: "The image to rotate."
1328
+ })
1329
+ ], RotateNode.prototype, "image", void 0);
1330
+ __decorate([
1331
+ prop({
1332
+ type: "float",
1333
+ default: 0,
1334
+ title: "Angle",
1335
+ description: "Rotation angle in degrees (clockwise).",
1336
+ min: -360,
1337
+ max: 360
1338
+ })
1339
+ ], RotateNode.prototype, "angle", void 0);
1340
+ export class FlipNode extends TransformImageNode {
1341
+ static nodeType = "nodetool.image.Flip";
1342
+ static title = "Flip";
1343
+ static description = "Flip an image horizontally or vertically.\n image, flip, mirror, horizontal, vertical, transform";
1344
+ static metadataOutputTypes = {
1345
+ output: "image"
1346
+ };
1347
+ async process(context) {
1348
+ const image = (this.image ?? {});
1349
+ const direction = String(this.direction ?? "horizontal");
1350
+ return transformImage(image, (instance) => direction === "vertical" ? instance.flip() : instance.flop(), context);
1351
+ }
1352
+ }
1353
+ __decorate([
1354
+ prop({
1355
+ type: "image",
1356
+ default: {
1357
+ type: "image",
1358
+ uri: "",
1359
+ asset_id: null,
1360
+ data: null,
1361
+ metadata: null
1362
+ },
1363
+ title: "Image",
1364
+ description: "The image to flip."
1365
+ })
1366
+ ], FlipNode.prototype, "image", void 0);
1367
+ __decorate([
1368
+ prop({
1369
+ type: "str",
1370
+ default: "horizontal",
1371
+ title: "Direction",
1372
+ description: "Flip direction.",
1373
+ values: ["horizontal", "vertical"]
1374
+ })
1375
+ ], FlipNode.prototype, "direction", void 0);
1376
+ export const IMAGE_NODES = [
1377
+ LoadImageFileNode,
1378
+ LoadImageFolderNode,
1379
+ SaveImageFileImageNode,
1380
+ LoadImageAssetsNode,
1381
+ SaveImageNode,
1382
+ GetMetadataNode,
1383
+ BatchToListNode,
1384
+ ImagesToListNode,
1385
+ PasteNode,
1386
+ ScaleNode,
1387
+ ResizeNode,
1388
+ CropNode,
1389
+ FitNode,
1390
+ RotateNode,
1391
+ FlipNode,
1392
+ TextToImageNode,
1393
+ ImageToImageNode
1394
+ ];
1395
+ //# sourceMappingURL=image.js.map