netra-artifacts 0.1.0-alpha.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (479) hide show
  1. package/CHANGELOG.md +25 -0
  2. package/LICENSE +21 -0
  3. package/README.md +239 -0
  4. package/dist/artifacts/artifactEnvelope.d.ts +46 -0
  5. package/dist/artifacts/artifactEnvelope.d.ts.map +1 -0
  6. package/dist/artifacts/artifactEnvelope.js +217 -0
  7. package/dist/artifacts/artifactEnvelope.js.map +1 -0
  8. package/dist/artifacts/artifactStatus.d.ts +9 -0
  9. package/dist/artifacts/artifactStatus.d.ts.map +1 -0
  10. package/dist/artifacts/artifactStatus.js +10 -0
  11. package/dist/artifacts/artifactStatus.js.map +1 -0
  12. package/dist/artifacts/artifactStore.d.ts +15 -0
  13. package/dist/artifacts/artifactStore.d.ts.map +1 -0
  14. package/dist/artifacts/artifactStore.js +35 -0
  15. package/dist/artifacts/artifactStore.js.map +1 -0
  16. package/dist/artifacts/htmlArtifact.d.ts +10 -0
  17. package/dist/artifacts/htmlArtifact.d.ts.map +1 -0
  18. package/dist/artifacts/htmlArtifact.js +20 -0
  19. package/dist/artifacts/htmlArtifact.js.map +1 -0
  20. package/dist/artifacts/index.d.ts +5 -0
  21. package/dist/artifacts/index.d.ts.map +1 -0
  22. package/dist/artifacts/index.js +5 -0
  23. package/dist/artifacts/index.js.map +1 -0
  24. package/dist/circuit-breaker/circuitBreaker.d.ts +35 -0
  25. package/dist/circuit-breaker/circuitBreaker.d.ts.map +1 -0
  26. package/dist/circuit-breaker/circuitBreaker.js +59 -0
  27. package/dist/circuit-breaker/circuitBreaker.js.map +1 -0
  28. package/dist/circuit-breaker/index.d.ts +3 -0
  29. package/dist/circuit-breaker/index.d.ts.map +1 -0
  30. package/dist/circuit-breaker/index.js +3 -0
  31. package/dist/circuit-breaker/index.js.map +1 -0
  32. package/dist/circuit-breaker/memoryCircuitStore.d.ts +24 -0
  33. package/dist/circuit-breaker/memoryCircuitStore.d.ts.map +1 -0
  34. package/dist/circuit-breaker/memoryCircuitStore.js +12 -0
  35. package/dist/circuit-breaker/memoryCircuitStore.js.map +1 -0
  36. package/dist/classifier/classifierPrompt.d.ts +7 -0
  37. package/dist/classifier/classifierPrompt.d.ts.map +1 -0
  38. package/dist/classifier/classifierPrompt.js +43 -0
  39. package/dist/classifier/classifierPrompt.js.map +1 -0
  40. package/dist/classifier/classifyMode.d.ts +21 -0
  41. package/dist/classifier/classifyMode.d.ts.map +1 -0
  42. package/dist/classifier/classifyMode.js +50 -0
  43. package/dist/classifier/classifyMode.js.map +1 -0
  44. package/dist/classifier/index.d.ts +4 -0
  45. package/dist/classifier/index.d.ts.map +1 -0
  46. package/dist/classifier/index.js +4 -0
  47. package/dist/classifier/index.js.map +1 -0
  48. package/dist/classifier/rules.d.ts +13 -0
  49. package/dist/classifier/rules.d.ts.map +1 -0
  50. package/dist/classifier/rules.js +118 -0
  51. package/dist/classifier/rules.js.map +1 -0
  52. package/dist/client/ArtifactChat.d.ts +15 -0
  53. package/dist/client/ArtifactChat.d.ts.map +1 -0
  54. package/dist/client/ArtifactChat.js +62 -0
  55. package/dist/client/ArtifactChat.js.map +1 -0
  56. package/dist/client/ArtifactMessage.d.ts +24 -0
  57. package/dist/client/ArtifactMessage.d.ts.map +1 -0
  58. package/dist/client/ArtifactMessage.js +29 -0
  59. package/dist/client/ArtifactMessage.js.map +1 -0
  60. package/dist/client/MarkdownMessage.d.ts +12 -0
  61. package/dist/client/MarkdownMessage.d.ts.map +1 -0
  62. package/dist/client/MarkdownMessage.js +141 -0
  63. package/dist/client/MarkdownMessage.js.map +1 -0
  64. package/dist/client/index.d.ts +8 -0
  65. package/dist/client/index.d.ts.map +1 -0
  66. package/dist/client/index.js +8 -0
  67. package/dist/client/index.js.map +1 -0
  68. package/dist/client/useArtifactStream.d.ts +9 -0
  69. package/dist/client/useArtifactStream.d.ts.map +1 -0
  70. package/dist/client/useArtifactStream.js +210 -0
  71. package/dist/client/useArtifactStream.js.map +1 -0
  72. package/dist/client.d.ts +2 -0
  73. package/dist/client.d.ts.map +1 -0
  74. package/dist/client.js +4 -0
  75. package/dist/client.js.map +1 -0
  76. package/dist/constants/defaults.d.ts +17 -0
  77. package/dist/constants/defaults.d.ts.map +1 -0
  78. package/dist/constants/defaults.js +38 -0
  79. package/dist/constants/defaults.js.map +1 -0
  80. package/dist/constants/events.d.ts +16 -0
  81. package/dist/constants/events.d.ts.map +1 -0
  82. package/dist/constants/events.js +16 -0
  83. package/dist/constants/events.js.map +1 -0
  84. package/dist/constants/index.d.ts +4 -0
  85. package/dist/constants/index.d.ts.map +1 -0
  86. package/dist/constants/index.js +4 -0
  87. package/dist/constants/index.js.map +1 -0
  88. package/dist/constants/sandbox.d.ts +19 -0
  89. package/dist/constants/sandbox.d.ts.map +1 -0
  90. package/dist/constants/sandbox.js +24 -0
  91. package/dist/constants/sandbox.js.map +1 -0
  92. package/dist/core/createArtifactResponse.d.ts +5 -0
  93. package/dist/core/createArtifactResponse.d.ts.map +1 -0
  94. package/dist/core/createArtifactResponse.js +16 -0
  95. package/dist/core/createArtifactResponse.js.map +1 -0
  96. package/dist/core/createArtifactStream.d.ts +9 -0
  97. package/dist/core/createArtifactStream.d.ts.map +1 -0
  98. package/dist/core/createArtifactStream.js +34 -0
  99. package/dist/core/createArtifactStream.js.map +1 -0
  100. package/dist/core/createIds.d.ts +3 -0
  101. package/dist/core/createIds.d.ts.map +1 -0
  102. package/dist/core/createIds.js +13 -0
  103. package/dist/core/createIds.js.map +1 -0
  104. package/dist/core/index.d.ts +6 -0
  105. package/dist/core/index.d.ts.map +1 -0
  106. package/dist/core/index.js +6 -0
  107. package/dist/core/index.js.map +1 -0
  108. package/dist/core/lifecycle.d.ts +35 -0
  109. package/dist/core/lifecycle.d.ts.map +1 -0
  110. package/dist/core/lifecycle.js +81 -0
  111. package/dist/core/lifecycle.js.map +1 -0
  112. package/dist/core/parseArtifactEnvelope.d.ts +2 -0
  113. package/dist/core/parseArtifactEnvelope.d.ts.map +1 -0
  114. package/dist/core/parseArtifactEnvelope.js +3 -0
  115. package/dist/core/parseArtifactEnvelope.js.map +1 -0
  116. package/dist/errors/ArtifactParseError.d.ts +10 -0
  117. package/dist/errors/ArtifactParseError.d.ts.map +1 -0
  118. package/dist/errors/ArtifactParseError.js +10 -0
  119. package/dist/errors/ArtifactParseError.js.map +1 -0
  120. package/dist/errors/ClassificationError.d.ts +13 -0
  121. package/dist/errors/ClassificationError.d.ts.map +1 -0
  122. package/dist/errors/ClassificationError.js +13 -0
  123. package/dist/errors/ClassificationError.js.map +1 -0
  124. package/dist/errors/StreamError.d.ts +11 -0
  125. package/dist/errors/StreamError.d.ts.map +1 -0
  126. package/dist/errors/StreamError.js +11 -0
  127. package/dist/errors/StreamError.js.map +1 -0
  128. package/dist/errors/index.d.ts +4 -0
  129. package/dist/errors/index.d.ts.map +1 -0
  130. package/dist/errors/index.js +4 -0
  131. package/dist/errors/index.js.map +1 -0
  132. package/dist/iframe/HtmlArtifactCard.d.ts +9 -0
  133. package/dist/iframe/HtmlArtifactCard.d.ts.map +1 -0
  134. package/dist/iframe/HtmlArtifactCard.js +117 -0
  135. package/dist/iframe/HtmlArtifactCard.js.map +1 -0
  136. package/dist/iframe/HtmlArtifactCodeView.d.ts +7 -0
  137. package/dist/iframe/HtmlArtifactCodeView.d.ts.map +1 -0
  138. package/dist/iframe/HtmlArtifactCodeView.js +20 -0
  139. package/dist/iframe/HtmlArtifactCodeView.js.map +1 -0
  140. package/dist/iframe/HtmlArtifactModal.d.ts +16 -0
  141. package/dist/iframe/HtmlArtifactModal.d.ts.map +1 -0
  142. package/dist/iframe/HtmlArtifactModal.js +99 -0
  143. package/dist/iframe/HtmlArtifactModal.js.map +1 -0
  144. package/dist/iframe/HtmlArtifactPreview.d.ts +15 -0
  145. package/dist/iframe/HtmlArtifactPreview.d.ts.map +1 -0
  146. package/dist/iframe/HtmlArtifactPreview.js +214 -0
  147. package/dist/iframe/HtmlArtifactPreview.js.map +1 -0
  148. package/dist/iframe/HtmlArtifactToolbar.d.ts +20 -0
  149. package/dist/iframe/HtmlArtifactToolbar.d.ts.map +1 -0
  150. package/dist/iframe/HtmlArtifactToolbar.js +14 -0
  151. package/dist/iframe/HtmlArtifactToolbar.js.map +1 -0
  152. package/dist/iframe/iframeSizing.d.ts +22 -0
  153. package/dist/iframe/iframeSizing.d.ts.map +1 -0
  154. package/dist/iframe/iframeSizing.js +74 -0
  155. package/dist/iframe/iframeSizing.js.map +1 -0
  156. package/dist/iframe/iframeSrcDoc.d.ts +34 -0
  157. package/dist/iframe/iframeSrcDoc.d.ts.map +1 -0
  158. package/dist/iframe/iframeSrcDoc.js +236 -0
  159. package/dist/iframe/iframeSrcDoc.js.map +1 -0
  160. package/dist/iframe/index.d.ts +15 -0
  161. package/dist/iframe/index.d.ts.map +1 -0
  162. package/dist/iframe/index.js +9 -0
  163. package/dist/iframe/index.js.map +1 -0
  164. package/dist/iframe/styles.d.ts +10 -0
  165. package/dist/iframe/styles.d.ts.map +1 -0
  166. package/dist/iframe/styles.js +181 -0
  167. package/dist/iframe/styles.js.map +1 -0
  168. package/dist/index.d.ts +18 -0
  169. package/dist/index.d.ts.map +1 -0
  170. package/dist/index.js +22 -0
  171. package/dist/index.js.map +1 -0
  172. package/dist/prompts/htmlArtifactPrompt.d.ts +15 -0
  173. package/dist/prompts/htmlArtifactPrompt.d.ts.map +1 -0
  174. package/dist/prompts/htmlArtifactPrompt.js +248 -0
  175. package/dist/prompts/htmlArtifactPrompt.js.map +1 -0
  176. package/dist/prompts/index.d.ts +4 -0
  177. package/dist/prompts/index.d.ts.map +1 -0
  178. package/dist/prompts/index.js +4 -0
  179. package/dist/prompts/index.js.map +1 -0
  180. package/dist/prompts/markdownPrompt.d.ts +3 -0
  181. package/dist/prompts/markdownPrompt.d.ts.map +1 -0
  182. package/dist/prompts/markdownPrompt.js +10 -0
  183. package/dist/prompts/markdownPrompt.js.map +1 -0
  184. package/dist/prompts/systemPrompt.d.ts +3 -0
  185. package/dist/prompts/systemPrompt.d.ts.map +1 -0
  186. package/dist/prompts/systemPrompt.js +3 -0
  187. package/dist/prompts/systemPrompt.js.map +1 -0
  188. package/dist/sanitizer/dangerousPatterns.d.ts +41 -0
  189. package/dist/sanitizer/dangerousPatterns.d.ts.map +1 -0
  190. package/dist/sanitizer/dangerousPatterns.js +41 -0
  191. package/dist/sanitizer/dangerousPatterns.js.map +1 -0
  192. package/dist/sanitizer/index.d.ts +4 -0
  193. package/dist/sanitizer/index.d.ts.map +1 -0
  194. package/dist/sanitizer/index.js +4 -0
  195. package/dist/sanitizer/index.js.map +1 -0
  196. package/dist/sanitizer/sanitizeConfig.d.ts +4 -0
  197. package/dist/sanitizer/sanitizeConfig.d.ts.map +1 -0
  198. package/dist/sanitizer/sanitizeConfig.js +10 -0
  199. package/dist/sanitizer/sanitizeConfig.js.map +1 -0
  200. package/dist/sanitizer/sanitizeHtml.d.ts +20 -0
  201. package/dist/sanitizer/sanitizeHtml.d.ts.map +1 -0
  202. package/dist/sanitizer/sanitizeHtml.js +81 -0
  203. package/dist/sanitizer/sanitizeHtml.js.map +1 -0
  204. package/dist/server/config.d.ts +6 -0
  205. package/dist/server/config.d.ts.map +1 -0
  206. package/dist/server/config.js +68 -0
  207. package/dist/server/config.js.map +1 -0
  208. package/dist/server/createArtifactStreamResponse.d.ts +9 -0
  209. package/dist/server/createArtifactStreamResponse.d.ts.map +1 -0
  210. package/dist/server/createArtifactStreamResponse.js +104 -0
  211. package/dist/server/createArtifactStreamResponse.js.map +1 -0
  212. package/dist/server/createHtmlArtifactStream.d.ts +30 -0
  213. package/dist/server/createHtmlArtifactStream.d.ts.map +1 -0
  214. package/dist/server/createHtmlArtifactStream.js +115 -0
  215. package/dist/server/createHtmlArtifactStream.js.map +1 -0
  216. package/dist/server/createMarkdownStream.d.ts +13 -0
  217. package/dist/server/createMarkdownStream.d.ts.map +1 -0
  218. package/dist/server/createMarkdownStream.js +27 -0
  219. package/dist/server/createMarkdownStream.js.map +1 -0
  220. package/dist/server/createSseResponse.d.ts +7 -0
  221. package/dist/server/createSseResponse.d.ts.map +1 -0
  222. package/dist/server/createSseResponse.js +11 -0
  223. package/dist/server/createSseResponse.js.map +1 -0
  224. package/dist/server/index.d.ts +12 -0
  225. package/dist/server/index.d.ts.map +1 -0
  226. package/dist/server/index.js +12 -0
  227. package/dist/server/index.js.map +1 -0
  228. package/dist/server.d.ts +2 -0
  229. package/dist/server.d.ts.map +1 -0
  230. package/dist/server.js +3 -0
  231. package/dist/server.js.map +1 -0
  232. package/dist/stream/assembleDocument.d.ts +42 -0
  233. package/dist/stream/assembleDocument.d.ts.map +1 -0
  234. package/dist/stream/assembleDocument.js +104 -0
  235. package/dist/stream/assembleDocument.js.map +1 -0
  236. package/dist/stream/buffering.d.ts +37 -0
  237. package/dist/stream/buffering.d.ts.map +1 -0
  238. package/dist/stream/buffering.js +97 -0
  239. package/dist/stream/buffering.js.map +1 -0
  240. package/dist/stream/debounce.d.ts +12 -0
  241. package/dist/stream/debounce.d.ts.map +1 -0
  242. package/dist/stream/debounce.js +36 -0
  243. package/dist/stream/debounce.js.map +1 -0
  244. package/dist/stream/decoder.d.ts +17 -0
  245. package/dist/stream/decoder.d.ts.map +1 -0
  246. package/dist/stream/decoder.js +71 -0
  247. package/dist/stream/decoder.js.map +1 -0
  248. package/dist/stream/encoder.d.ts +12 -0
  249. package/dist/stream/encoder.d.ts.map +1 -0
  250. package/dist/stream/encoder.js +19 -0
  251. package/dist/stream/encoder.js.map +1 -0
  252. package/dist/stream/events.d.ts +20 -0
  253. package/dist/stream/events.d.ts.map +1 -0
  254. package/dist/stream/events.js +65 -0
  255. package/dist/stream/events.js.map +1 -0
  256. package/dist/stream/index.d.ts +9 -0
  257. package/dist/stream/index.d.ts.map +1 -0
  258. package/dist/stream/index.js +9 -0
  259. package/dist/stream/index.js.map +1 -0
  260. package/dist/stream/predictiveHtmlParser.d.ts +52 -0
  261. package/dist/stream/predictiveHtmlParser.d.ts.map +1 -0
  262. package/dist/stream/predictiveHtmlParser.js +252 -0
  263. package/dist/stream/predictiveHtmlParser.js.map +1 -0
  264. package/dist/stream/sse.d.ts +7 -0
  265. package/dist/stream/sse.d.ts.map +1 -0
  266. package/dist/stream/sse.js +33 -0
  267. package/dist/stream/sse.js.map +1 -0
  268. package/dist/types/artifact.d.ts +88 -0
  269. package/dist/types/artifact.d.ts.map +1 -0
  270. package/dist/types/artifact.js +2 -0
  271. package/dist/types/artifact.js.map +1 -0
  272. package/dist/types/client.d.ts +98 -0
  273. package/dist/types/client.d.ts.map +1 -0
  274. package/dist/types/client.js +2 -0
  275. package/dist/types/client.js.map +1 -0
  276. package/dist/types/config.d.ts +23 -0
  277. package/dist/types/config.d.ts.map +1 -0
  278. package/dist/types/config.js +2 -0
  279. package/dist/types/config.js.map +1 -0
  280. package/dist/types/errors.d.ts +9 -0
  281. package/dist/types/errors.d.ts.map +1 -0
  282. package/dist/types/errors.js +2 -0
  283. package/dist/types/errors.js.map +1 -0
  284. package/dist/types/index.d.ts +7 -0
  285. package/dist/types/index.d.ts.map +1 -0
  286. package/dist/types/index.js +2 -0
  287. package/dist/types/index.js.map +1 -0
  288. package/dist/types/server.d.ts +111 -0
  289. package/dist/types/server.d.ts.map +1 -0
  290. package/dist/types/server.js +2 -0
  291. package/dist/types/server.js.map +1 -0
  292. package/dist/types/stream.d.ts +60 -0
  293. package/dist/types/stream.d.ts.map +1 -0
  294. package/dist/types/stream.js +7 -0
  295. package/dist/types/stream.js.map +1 -0
  296. package/dist/utils/index.d.ts +6 -0
  297. package/dist/utils/index.d.ts.map +1 -0
  298. package/dist/utils/index.js +6 -0
  299. package/dist/utils/index.js.map +1 -0
  300. package/dist/utils/invariant.d.ts +6 -0
  301. package/dist/utils/invariant.d.ts.map +1 -0
  302. package/dist/utils/invariant.js +10 -0
  303. package/dist/utils/invariant.js.map +1 -0
  304. package/dist/utils/isBrowser.d.ts +3 -0
  305. package/dist/utils/isBrowser.d.ts.map +1 -0
  306. package/dist/utils/isBrowser.js +3 -0
  307. package/dist/utils/isBrowser.js.map +1 -0
  308. package/dist/utils/mergeConfig.d.ts +6 -0
  309. package/dist/utils/mergeConfig.d.ts.map +1 -0
  310. package/dist/utils/mergeConfig.js +17 -0
  311. package/dist/utils/mergeConfig.js.map +1 -0
  312. package/dist/utils/noop.d.ts +3 -0
  313. package/dist/utils/noop.d.ts.map +1 -0
  314. package/dist/utils/noop.js +3 -0
  315. package/dist/utils/noop.js.map +1 -0
  316. package/dist/utils/safeJsonParse.d.ts +7 -0
  317. package/dist/utils/safeJsonParse.d.ts.map +1 -0
  318. package/dist/utils/safeJsonParse.js +62 -0
  319. package/dist/utils/safeJsonParse.js.map +1 -0
  320. package/dist-cjs/artifacts/artifactEnvelope.js +224 -0
  321. package/dist-cjs/artifacts/artifactEnvelope.js.map +1 -0
  322. package/dist-cjs/artifacts/artifactStatus.js +14 -0
  323. package/dist-cjs/artifacts/artifactStatus.js.map +1 -0
  324. package/dist-cjs/artifacts/artifactStore.js +39 -0
  325. package/dist-cjs/artifacts/artifactStore.js.map +1 -0
  326. package/dist-cjs/artifacts/htmlArtifact.js +24 -0
  327. package/dist-cjs/artifacts/htmlArtifact.js.map +1 -0
  328. package/dist-cjs/artifacts/index.js +21 -0
  329. package/dist-cjs/artifacts/index.js.map +1 -0
  330. package/dist-cjs/circuit-breaker/circuitBreaker.js +63 -0
  331. package/dist-cjs/circuit-breaker/circuitBreaker.js.map +1 -0
  332. package/dist-cjs/circuit-breaker/index.js +19 -0
  333. package/dist-cjs/circuit-breaker/index.js.map +1 -0
  334. package/dist-cjs/circuit-breaker/memoryCircuitStore.js +16 -0
  335. package/dist-cjs/circuit-breaker/memoryCircuitStore.js.map +1 -0
  336. package/dist-cjs/classifier/classifierPrompt.js +47 -0
  337. package/dist-cjs/classifier/classifierPrompt.js.map +1 -0
  338. package/dist-cjs/classifier/classifyMode.js +53 -0
  339. package/dist-cjs/classifier/classifyMode.js.map +1 -0
  340. package/dist-cjs/classifier/index.js +20 -0
  341. package/dist-cjs/classifier/index.js.map +1 -0
  342. package/dist-cjs/classifier/rules.js +121 -0
  343. package/dist-cjs/classifier/rules.js.map +1 -0
  344. package/dist-cjs/client/ArtifactChat.js +98 -0
  345. package/dist-cjs/client/ArtifactChat.js.map +1 -0
  346. package/dist-cjs/client/ArtifactMessage.js +32 -0
  347. package/dist-cjs/client/ArtifactMessage.js.map +1 -0
  348. package/dist-cjs/client/MarkdownMessage.js +177 -0
  349. package/dist-cjs/client/MarkdownMessage.js.map +1 -0
  350. package/dist-cjs/client/index.js +20 -0
  351. package/dist-cjs/client/index.js.map +1 -0
  352. package/dist-cjs/client/useArtifactStream.js +246 -0
  353. package/dist-cjs/client/useArtifactStream.js.map +1 -0
  354. package/dist-cjs/client.js +20 -0
  355. package/dist-cjs/client.js.map +1 -0
  356. package/dist-cjs/constants/defaults.js +41 -0
  357. package/dist-cjs/constants/defaults.js.map +1 -0
  358. package/dist-cjs/constants/events.js +19 -0
  359. package/dist-cjs/constants/events.js.map +1 -0
  360. package/dist-cjs/constants/index.js +20 -0
  361. package/dist-cjs/constants/index.js.map +1 -0
  362. package/dist-cjs/constants/sandbox.js +27 -0
  363. package/dist-cjs/constants/sandbox.js.map +1 -0
  364. package/dist-cjs/core/createArtifactResponse.js +20 -0
  365. package/dist-cjs/core/createArtifactResponse.js.map +1 -0
  366. package/dist-cjs/core/createArtifactStream.js +37 -0
  367. package/dist-cjs/core/createArtifactStream.js.map +1 -0
  368. package/dist-cjs/core/createIds.js +17 -0
  369. package/dist-cjs/core/createIds.js.map +1 -0
  370. package/dist-cjs/core/index.js +22 -0
  371. package/dist-cjs/core/index.js.map +1 -0
  372. package/dist-cjs/core/lifecycle.js +86 -0
  373. package/dist-cjs/core/lifecycle.js.map +1 -0
  374. package/dist-cjs/core/parseArtifactEnvelope.js +8 -0
  375. package/dist-cjs/core/parseArtifactEnvelope.js.map +1 -0
  376. package/dist-cjs/errors/ArtifactParseError.js +14 -0
  377. package/dist-cjs/errors/ArtifactParseError.js.map +1 -0
  378. package/dist-cjs/errors/ClassificationError.js +17 -0
  379. package/dist-cjs/errors/ClassificationError.js.map +1 -0
  380. package/dist-cjs/errors/StreamError.js +15 -0
  381. package/dist-cjs/errors/StreamError.js.map +1 -0
  382. package/dist-cjs/errors/index.js +20 -0
  383. package/dist-cjs/errors/index.js.map +1 -0
  384. package/dist-cjs/iframe/HtmlArtifactCard.js +153 -0
  385. package/dist-cjs/iframe/HtmlArtifactCard.js.map +1 -0
  386. package/dist-cjs/iframe/HtmlArtifactCodeView.js +23 -0
  387. package/dist-cjs/iframe/HtmlArtifactCodeView.js.map +1 -0
  388. package/dist-cjs/iframe/HtmlArtifactModal.js +135 -0
  389. package/dist-cjs/iframe/HtmlArtifactModal.js.map +1 -0
  390. package/dist-cjs/iframe/HtmlArtifactPreview.js +250 -0
  391. package/dist-cjs/iframe/HtmlArtifactPreview.js.map +1 -0
  392. package/dist-cjs/iframe/HtmlArtifactToolbar.js +17 -0
  393. package/dist-cjs/iframe/HtmlArtifactToolbar.js.map +1 -0
  394. package/dist-cjs/iframe/iframeSizing.js +77 -0
  395. package/dist-cjs/iframe/iframeSizing.js.map +1 -0
  396. package/dist-cjs/iframe/iframeSrcDoc.js +241 -0
  397. package/dist-cjs/iframe/iframeSrcDoc.js.map +1 -0
  398. package/dist-cjs/iframe/index.js +22 -0
  399. package/dist-cjs/iframe/index.js.map +1 -0
  400. package/dist-cjs/iframe/styles.js +218 -0
  401. package/dist-cjs/iframe/styles.js.map +1 -0
  402. package/dist-cjs/index.js +52 -0
  403. package/dist-cjs/index.js.map +1 -0
  404. package/dist-cjs/package.json +3 -0
  405. package/dist-cjs/prompts/htmlArtifactPrompt.js +252 -0
  406. package/dist-cjs/prompts/htmlArtifactPrompt.js.map +1 -0
  407. package/dist-cjs/prompts/index.js +20 -0
  408. package/dist-cjs/prompts/index.js.map +1 -0
  409. package/dist-cjs/prompts/markdownPrompt.js +13 -0
  410. package/dist-cjs/prompts/markdownPrompt.js.map +1 -0
  411. package/dist-cjs/prompts/systemPrompt.js +6 -0
  412. package/dist-cjs/prompts/systemPrompt.js.map +1 -0
  413. package/dist-cjs/sanitizer/dangerousPatterns.js +44 -0
  414. package/dist-cjs/sanitizer/dangerousPatterns.js.map +1 -0
  415. package/dist-cjs/sanitizer/index.js +43 -0
  416. package/dist-cjs/sanitizer/index.js.map +1 -0
  417. package/dist-cjs/sanitizer/sanitizeConfig.js +13 -0
  418. package/dist-cjs/sanitizer/sanitizeConfig.js.map +1 -0
  419. package/dist-cjs/sanitizer/sanitizeHtml.js +86 -0
  420. package/dist-cjs/sanitizer/sanitizeHtml.js.map +1 -0
  421. package/dist-cjs/server/config.js +72 -0
  422. package/dist-cjs/server/config.js.map +1 -0
  423. package/dist-cjs/server/createArtifactStreamResponse.js +107 -0
  424. package/dist-cjs/server/createArtifactStreamResponse.js.map +1 -0
  425. package/dist-cjs/server/createHtmlArtifactStream.js +119 -0
  426. package/dist-cjs/server/createHtmlArtifactStream.js.map +1 -0
  427. package/dist-cjs/server/createMarkdownStream.js +31 -0
  428. package/dist-cjs/server/createMarkdownStream.js.map +1 -0
  429. package/dist-cjs/server/createSseResponse.js +14 -0
  430. package/dist-cjs/server/createSseResponse.js.map +1 -0
  431. package/dist-cjs/server/index.js +34 -0
  432. package/dist-cjs/server/index.js.map +1 -0
  433. package/dist-cjs/server.js +19 -0
  434. package/dist-cjs/server.js.map +1 -0
  435. package/dist-cjs/stream/assembleDocument.js +109 -0
  436. package/dist-cjs/stream/assembleDocument.js.map +1 -0
  437. package/dist-cjs/stream/buffering.js +102 -0
  438. package/dist-cjs/stream/buffering.js.map +1 -0
  439. package/dist-cjs/stream/debounce.js +39 -0
  440. package/dist-cjs/stream/debounce.js.map +1 -0
  441. package/dist-cjs/stream/decoder.js +75 -0
  442. package/dist-cjs/stream/decoder.js.map +1 -0
  443. package/dist-cjs/stream/encoder.js +24 -0
  444. package/dist-cjs/stream/encoder.js.map +1 -0
  445. package/dist-cjs/stream/events.js +69 -0
  446. package/dist-cjs/stream/events.js.map +1 -0
  447. package/dist-cjs/stream/index.js +25 -0
  448. package/dist-cjs/stream/index.js.map +1 -0
  449. package/dist-cjs/stream/predictiveHtmlParser.js +256 -0
  450. package/dist-cjs/stream/predictiveHtmlParser.js.map +1 -0
  451. package/dist-cjs/stream/sse.js +36 -0
  452. package/dist-cjs/stream/sse.js.map +1 -0
  453. package/dist-cjs/types/artifact.js +3 -0
  454. package/dist-cjs/types/artifact.js.map +1 -0
  455. package/dist-cjs/types/client.js +3 -0
  456. package/dist-cjs/types/client.js.map +1 -0
  457. package/dist-cjs/types/config.js +3 -0
  458. package/dist-cjs/types/config.js.map +1 -0
  459. package/dist-cjs/types/errors.js +3 -0
  460. package/dist-cjs/types/errors.js.map +1 -0
  461. package/dist-cjs/types/index.js +3 -0
  462. package/dist-cjs/types/index.js.map +1 -0
  463. package/dist-cjs/types/server.js +3 -0
  464. package/dist-cjs/types/server.js.map +1 -0
  465. package/dist-cjs/types/stream.js +8 -0
  466. package/dist-cjs/types/stream.js.map +1 -0
  467. package/dist-cjs/utils/index.js +22 -0
  468. package/dist-cjs/utils/index.js.map +1 -0
  469. package/dist-cjs/utils/invariant.js +13 -0
  470. package/dist-cjs/utils/invariant.js.map +1 -0
  471. package/dist-cjs/utils/isBrowser.js +6 -0
  472. package/dist-cjs/utils/isBrowser.js.map +1 -0
  473. package/dist-cjs/utils/mergeConfig.js +20 -0
  474. package/dist-cjs/utils/mergeConfig.js.map +1 -0
  475. package/dist-cjs/utils/noop.js +7 -0
  476. package/dist-cjs/utils/noop.js.map +1 -0
  477. package/dist-cjs/utils/safeJsonParse.js +65 -0
  478. package/dist-cjs/utils/safeJsonParse.js.map +1 -0
  479. package/package.json +115 -0
@@ -0,0 +1,248 @@
1
+ import { BASE_SYSTEM_PROMPT } from "./systemPrompt.js";
2
+ import { SYSTEM_FONT_STACK } from "../constants/defaults.js";
3
+ function buildOutputFormat(presentation) {
4
+ if (presentation === "seamless") {
5
+ return `You are answering in HTML_ARTIFACT mode. Output EXACTLY two sections and nothing else:
6
+
7
+ <assistant_message>
8
+ A short (1-2 sentence) chat message. Mention the aesthetic direction you chose, naturally.
9
+ </assistant_message>
10
+
11
+ <html_artifact title="A concise human-readable title">
12
+ <!DOCTYPE html>
13
+ <html lang="en" style="background:transparent;margin:0;padding:0;">
14
+ <head>
15
+ <meta charset="UTF-8" />
16
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
17
+ <title>...</title>
18
+ </head>
19
+ <body style="background:transparent;margin:0;padding:0;">
20
+ <!-- content with inline style attributes on elements; do not output any <style> tag -->
21
+ </body>
22
+ </html>
23
+ </html_artifact>`;
24
+ }
25
+ return `You are answering in HTML_ARTIFACT mode. Output EXACTLY two sections and nothing else:
26
+
27
+ <assistant_message>
28
+ A short (1-2 sentence) chat message. Mention the aesthetic direction you chose, naturally.
29
+ </assistant_message>
30
+
31
+ <html_artifact title="A concise human-readable title">
32
+ <!DOCTYPE html>
33
+ <html lang="en" style="margin:0;padding:0">
34
+ <head>
35
+ <meta charset="UTF-8" />
36
+ <meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover" />
37
+ <title>...</title>
38
+ </head>
39
+ <body style="margin:0; /* declare your OWN design tokens + page background inline here (e.g. --bg/--fg/--accent), then set background + color from them. Pick the palette that best fits — light, dark, or vivid; never plain white-on-white */">
40
+ <!-- content with ALL styling inline via style="" on each element; no <style> tag. Make it fully responsive with intrinsic CSS (see responsive rules). -->
41
+ </body>
42
+ </html>
43
+ </html_artifact>`;
44
+ }
45
+ const HARD_RULES = `HARD RULES — the artifact renders in a sandboxed iframe with NO JavaScript:
46
+ - Output a COMPLETE, valid HTML document (<!DOCTYPE html>, <html>, <head>, <body>, meta charset, meta viewport).
47
+ - You are already in HTML_ARTIFACT mode. ALWAYS emit the <html_artifact> block. Never answer with explanation-only prose, even if the user says "check", "test", "show", "demo", or repeats the request messily.
48
+ - 100% static HTML + CSS. NO JavaScript, NO <script>, NO event handlers (onclick/onload/...), NO javascript: URLs, NO external JS.
49
+ - NO markdown code fences. NO prose outside <assistant_message>. NO placeholders ("data will load here") — PRECOMPUTE and write every value directly into the HTML.
50
+ - Reset body margins (body{margin:0}). Avoid fixed body heights and fixed/overlay positioning that breaks inside an iframe. Content flows top-to-bottom and is fully responsive.
51
+ - Semantic HTML and accessible labels (label/for, alt text, aria where helpful). Maintain strong color contrast.`;
52
+ function buildInlineOnlyRule() {
53
+ return `INLINE CSS ONLY — THIS IS A HARD CONSTRAINT FOR EVERY ARTIFACT (read carefully):
54
+ Any <style> tag you write is DELETED before the artifact renders. CSS placed in a <style> tag, a :root block, or any stylesheet rule WILL NOT APPLY and your design will appear broken/unstyled. The ONLY styling that survives is a style="" attribute on the element it affects. Keep markup bare-minimum.
55
+
56
+ ALLOWED:
57
+ - A style="" attribute on every element you want to style.
58
+ - CSS custom properties declared inline on <html style="--bg:...;--fg:...;..."> and referenced from descendants via var(), e.g. style="color:var(--fg)".
59
+ - Inline layout — this is how you make it responsive WITHOUT media queries:
60
+ - Fluid grid that reflows by itself: style="display:grid;gap:16px;grid-template-columns:repeat(auto-fit,minmax(min(100%,240px),1fr))"
61
+ - Wrapping rows / navs: style="display:flex;flex-wrap:wrap;gap:12px;align-items:center"
62
+ - Fluid type/space with clamp(): style="font-size:clamp(1.5rem,1rem+3vw,3rem)"
63
+ - Wide tables/timelines: wrap in style="overflow-x:auto" so they scroll instead of overflowing the page.
64
+ - SVG via presentation attributes (fill, stroke, …) and inline style="" on SVG nodes.
65
+ - <link> to Google Fonts in <head> (font loading only); apply font-family inline.
66
+
67
+ FORBIDDEN (none work without a stylesheet — never emit them):
68
+ - <style> tags anywhere. :root{} blocks. Class/ID/element/attribute CSS selectors.
69
+ - @media, @keyframes, @font-face, @supports, @container.
70
+ - Pseudo-classes/elements: :hover, :focus, :active, ::before, ::after, ::marker.
71
+ - "Utility classes" (Tailwind-style) — class="" does NOTHING here; style inline. Omit class attributes.
72
+ - A click-toggle "burger" menu (needs a stylesheet/JS). For navs, use a single wrapping/scrolling row instead (flex-wrap, or overflow-x:auto).
73
+
74
+ CONCRETE RESPONSIVE PATTERN (inline auto-fit grid — reflows from 3-up to 1-up by itself):
75
+ <div style="display:grid;gap:14px;grid-template-columns:repeat(auto-fit,minmax(min(100%,240px),1fr))">
76
+ <div style="padding:18px 20px;border-radius:16px;background:rgba(255,255,255,0.05);border:1px solid rgba(255,255,255,0.10)">
77
+ <div style="font-size:13px;letter-spacing:.04em;color:var(--muted,rgba(255,255,255,.55))">Revenue</div>
78
+ <div style="font-size:clamp(24px,2vw+16px,34px);font-weight:700;color:var(--fg,#f4f4f8)">$48.9K</div>
79
+ <div style="font-size:13px;color:#34d399">▲ 4.2%</div>
80
+ </div>
81
+ </div>
82
+ Every property is on the element. Do this for the entire artifact.`;
83
+ }
84
+ const DESIGN_DIRECTION = `DESIGN DIRECTION — make it genuinely beautiful, not generic. Avoid "AI slop" at all costs.
85
+
86
+ 1. COMMIT TO A BOLD, COHESIVE AESTHETIC. Pick ONE clear direction that fits the content and execute it precisely. Examples to draw from (do not always pick the same one — vary across generations): editorial/magazine, refined luxury, brutalist/raw, retro-futuristic, organic/natural, soft pastel, industrial/utilitarian, art-deco/geometric, dark premium, warm minimal. Intentionality beats intensity.
87
+
88
+ 2. DESIGN TOKENS FIRST. Declare your token system INLINE on <html style="--bg:...;--fg:...;--accent:...;--space:...;--radius:..."> (never a :root block or <style> tag) and reference everywhere via var(). A dominant color + 1-2 sharp accents, a spacing scale, radii, shadows. Pick light OR dark deliberately; do not default to white.
89
+
90
+ 3. ANTI-SLOP — NEVER do these:
91
+ - NO purple/violet gradients on white (the #1 AI cliché).
92
+ - NO uniform rounded corners on everything; vary radii with intent.
93
+ - NO everything-centered layouts. Use real composition.
94
+ - NO generic system/Inter/Arial/Roboto-only typography.
95
+
96
+ 4. SPATIAL COMPOSITION. Use asymmetry, overlap, a clear visual hierarchy, deliberate negative space OR controlled density. Break the grid intentionally. Strong type scale: large confident headings, comfortable body, small-caps/labels where fitting.
97
+
98
+ 5. DEPTH & ATMOSPHERE. Don't settle for flat solid fills. Add tasteful depth: layered subtle gradients or gradient meshes (radial-gradient), soft grain/noise via SVG data-URI background, fine 1px hairlines, dramatic-but-tasteful shadows, glassmorphism only where it earns it. Keep it refined.
99
+
100
+ 6. MOTION. CSS animation (@keyframes) and hover need a stylesheet, which isn't available (inline-only) — DO NOT rely on them. Win with strong STATIC craft: confident type scale, layered depth, gradients, shadows, precise spacing.
101
+
102
+ 7. REAL CONTENT. Use realistic, specific, precomputed data (names, numbers, dates, copy). Never lorem ipsum, never "Item 1 / Item 2".
103
+
104
+ DATA VISUALS (no JS, no chart libraries): use SVG (paths, bars, polylines, arcs), CSS bars, conic-gradient donuts, linear-gradient progress, semantic tables, stat cards, timelines, funnels, comparison cards — all with precomputed values.
105
+ ACCORDIONS: native <details><summary>…</summary>…</details>, styled with CSS only.`;
106
+ function buildFontRule(allowExternalFonts) {
107
+ if (allowExternalFonts) {
108
+ return `TYPOGRAPHY — use DISTINCTIVE fonts (this is what separates premium from slop):
109
+ - Load fonts from Google Fonts only, via <link> in <head> (e.g. <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin><link href="https://fonts.googleapis.com/css2?family=...&display=swap" rel="stylesheet">). Other external resources are blocked.
110
+ - Pair a CHARACTERFUL display/heading font with a clean, readable body font. Forbidden as primary fonts: Inter, Roboto, Arial, plain system stacks.
111
+ - Strong, varied pairings to consider (pick one that matches the aesthetic; vary across generations): "Fraunces" + "Inter Tight"; "Clash Display"-style → use "Bricolage Grotesque" + "Newsreader"; "Space Grotesk" + "Spline Sans" (use sparingly); "Instrument Serif" + "Geist"; "Libre Caslon Display" + "Public Sans"; "Sora" + "IBM Plex Sans"; "DM Serif Display" + "DM Sans"; "Syne" + "Manrope".
112
+ - LIMIT to AT MOST 3 font styles total per artifact (e.g. one display + one body, each in up to ~2 weights). Pick ONE pairing and commit; do not scatter many families/weights. Apply font-family inline on elements.
113
+ - Always include a robust fallback in font-family (serif/sans-serif). Set sensible font sizes with clamp() for fluid scaling.`;
114
+ }
115
+ return `TYPOGRAPHY: external fonts are disabled — build character through scale, weight, letter-spacing, and small-caps using this system stack only (at most 3 distinct text styles total):\nfont-family: ${SYSTEM_FONT_STACK};`;
116
+ }
117
+ function buildFormRule(allowForms) {
118
+ if (allowForms) {
119
+ return `FORMS: native HTML controls only (form, label, input, textarea, select, button) with native validation (required, pattern, min, max, type=email/tel/...). Style inputs to match the aesthetic — custom focus states, generous hit areas. No JavaScript validation.`;
120
+ }
121
+ return `FORMS: avoid interactive controls; present information as polished static content.`;
122
+ }
123
+ function buildStyleProfileRule(profile) {
124
+ if (!profile) {
125
+ return `STYLE PROFILE: none specified — YOU choose a bold, context-appropriate aesthetic and a distinctive color + type system. Do not play it safe and do not default to a light, centered, purple-on-white layout.`;
126
+ }
127
+ const parts = [];
128
+ if (profile.aesthetic)
129
+ parts.push(`aesthetic: ${profile.aesthetic}`);
130
+ if (profile.mood)
131
+ parts.push(`mood: ${profile.mood}`);
132
+ if (profile.density)
133
+ parts.push(`density: ${profile.density}`);
134
+ if (profile.radius)
135
+ parts.push(`base radius: ${profile.radius}`);
136
+ if (profile.font)
137
+ parts.push(`type feel: ${profile.font}`);
138
+ if (profile.colorScheme)
139
+ parts.push(`color scheme: ${profile.colorScheme}`);
140
+ if (profile.visualComplexity)
141
+ parts.push(`visual complexity: ${profile.visualComplexity}`);
142
+ return `STYLE PROFILE — honor these as the creative brief, then push further: ${parts.join(", ")}. Translate them into a concrete palette, type pairing, spacing, and motion. Make it feel intentionally designed for THIS content.`;
143
+ }
144
+ function buildThemeRule(theme, presentation) {
145
+ if (!theme)
146
+ return "";
147
+ const tokens = [];
148
+ if (theme.colorScheme)
149
+ tokens.push(`color scheme: ${theme.colorScheme}`);
150
+ if (theme.background)
151
+ tokens.push(`page background: ${theme.background}`);
152
+ if (theme.foreground)
153
+ tokens.push(`text/foreground: ${theme.foreground}`);
154
+ if (theme.primary)
155
+ tokens.push(`primary/brand: ${theme.primary}`);
156
+ if (theme.accent)
157
+ tokens.push(`accent: ${theme.accent}`);
158
+ if (theme.muted)
159
+ tokens.push(`muted text: ${theme.muted}`);
160
+ if (theme.border)
161
+ tokens.push(`borders/hairlines: ${theme.border}`);
162
+ if (theme.surface)
163
+ tokens.push(`surfaces/cards: ${theme.surface}`);
164
+ if (theme.radius)
165
+ tokens.push(`base radius: ${theme.radius}`);
166
+ if (theme.fontFamily)
167
+ tokens.push(`font family: ${theme.fontFamily}`);
168
+ if (presentation === "seamless") {
169
+ return `HOST THEME — this artifact is embedded INSIDE a host application, not shown standalone. Match the host's visual system precisely so it looks native and consistent. Put these host values directly into the <html style="..."> custom properties and stay strictly within this palette — do NOT introduce clashing or unrelated colors:
170
+ - ${tokens.join("\n- ")}${theme.notes ? `\n- brand notes: ${theme.notes}` : ""}
171
+ Use these values through inline style attributes only, e.g. style="color:var(--foreground);border-color:var(--border);background:rgba(255,255,255,0.045)". Do not create a :root block or <style> tag.`;
172
+ }
173
+ return `HOST THEME — this artifact is embedded INSIDE a host application, not shown standalone. Match the host's visual system precisely so it looks native and consistent. Build your :root tokens from these exact values and stay strictly within this palette — do NOT introduce clashing or unrelated colors:
174
+ - ${tokens.join("\n- ")}${theme.notes ? `\n- brand notes: ${theme.notes}` : ""}
175
+ These host values are also available inside the iframe as CSS variables: --background, --foreground, --primary, --accent, --muted, --border, --surface, --radius, --font. Prefer referencing them (e.g. color: var(--foreground)) so the artifact tracks the host theme. Apply your design craft WITHIN these constraints — cohesive, on-brand, never off-palette.`;
176
+ }
177
+ function buildPresentationRule(presentation) {
178
+ if (presentation !== "seamless")
179
+ return "";
180
+ return `SEAMLESS / EMBEDDED RENDERING (critical) — this artifact is dropped directly into the page flow as if it were native chat content:
181
+ - If the user asks to test/check/show "camouflage", "transparent background", "generative UI", or "all combinations", create a rich visual showcase of multiple UI combinations inside the transparent shell. Do not explain the property; demonstrate it visually.
182
+ - TRANSPARENT background everywhere at the top level: html{background:transparent} and body{background:transparent;margin:0}. NEVER paint a page/background color, white sheet, or gradient on html or body.
183
+ - For camouflage/seamless requests, put ALL styling directly on elements with inline style="" attributes. Do not output a <style> tag.
184
+ - Do NOT wrap the whole artifact in an outer card/sheet/panel/frame/border/box-shadow/"window". The single outermost element must have NO background of its own — the host surface shows through. (Inner cards/sections for actual content are fine and encouraged.)
185
+ - This is a DARK host UI. Use the host theme colors above: light text on the transparent dark surface. NEVER use a light/white background or dark-text-on-white — that would look like a pasted white box. If you need contrast, use subtle translucent surfaces (e.g. rgba(255,255,255,0.05)), not opaque white.
186
+ - Keep it compact and content-sized: no min-height:100vh, no full-viewport hero. Occupy only the height the content needs and flow inline.`;
187
+ }
188
+ function buildArtifactIdentityRule(presentation) {
189
+ if (presentation === "seamless") {
190
+ return `CAMOUFLAGE QUALITY BAR:
191
+ - The outer document and first wrapper must be transparent, but the artifact must still feel designed. Put the visual identity INSIDE the transparent shell: translucent panels, CSS/SVG charts, accent gradients, badges, cards, timelines, and dense real content.
192
+ - The artifact is its own custom object, not a copy of the host website. Host theme values are guardrails for contrast and embedding only; choose a distinct dark, premium artifact palette and composition when the request asks for a custom UI/artifact.
193
+ - Never use an opaque full-page white/light background. Never rely on the host page as the only design. The result should read as a polished artifact embedded in the chat, not a pasted webpage screenshot.`;
194
+ }
195
+ return `ARTIFACT QUALITY BAR: when rendering a standalone artifact, give it its own complete visual world: deliberate page background, palette, typography, composition, and data. It should not merely clone the host website theme unless explicitly requested.`;
196
+ }
197
+ const IMAGES_RULE = `IMAGES — when the design needs a photo/illustration (hero, avatar, card media, gallery, background), use Picsum random placeholders (the ONLY allowed external image host):
198
+ - URL: https://picsum.photos/{width}/{height} — e.g. <img src="https://picsum.photos/1920/1080" …>.
199
+ - For DIFFERENT images across multiple slots, add a unique seed: https://picsum.photos/seed/{word}/{width}/{height} (same seed = same image, so vary the word per slot, e.g. /seed/nova/800/600, /seed/atlas/800/600). For avatars use a square like /seed/amy/96/96.
200
+ - Request a size close to the rendered size (don't fetch 1920×1080 for a thumbnail) so it streams fast.
201
+ - Always responsive + shift-free: style="display:block;width:100%;height:auto;object-fit:cover" and set aspect-ratio (e.g. aspect-ratio:16/9 or 1/1). Give every image meaningful alt text.
202
+ - Do NOT hotlink any other image host; only picsum.photos.`;
203
+ const STREAMING_RULE = `STREAM-FRIENDLY OUTPUT (so the UI paints instantly and never blocks) — the artifact renders progressively as you stream it:
204
+ - Keep <head> TINY: only <meta> tags and (optionally) a single Google Fonts <link>. Put NOTHING in <head> that must finish before content shows — no big CSS block, no token sheet. A large head buffers the whole document before anything paints.
205
+ - ALL styling is inline on body elements, so each element paints the moment its tokens arrive. This is the main reason styling is inline, not just a constraint.
206
+ - Write the body TOP-TO-BOTTOM in visual order, most important content first (header → key content → details), so the very first streamed tokens already render something meaningful.
207
+ - Declare shared tokens once on <html style="--…"> (it streams first, in one short tag), then reference via var() inline below.`;
208
+ const RESPONSIVE_RULE = `FORCE RESPONSIVE — the artifact MUST look perfect at any width (the viewer can preview it at phone / tablet / desktop), with NO horizontal page overflow:
209
+ - Fluid & intrinsic (works inline, zero media queries): clamp() for type + spacing; repeat(auto-fit,minmax(min(100%,X),1fr)) for any grid of cards/stats/features; flex-wrap for rows and navs; %/fr/ch for sizing; gap (never margins) for rhythm.
210
+ - NEVER overflow horizontally: no fixed px widths on containers; use width:100%/max-width with min(100%,…). Long words → overflow-wrap:break-word. Wide tables/timelines/charts/carousels → wrap in a box with overflow-x:auto so THAT scrolls, not the page.
211
+ - Media: img/svg/video → max-width:100%; height:auto; display:block. Reserve space with aspect-ratio.
212
+ - Tap targets ≥ 44px. Use 100dvh/100svh (never 100vh) if a full-height region is truly needed; prefer content height.
213
+ - Result: fills its frame on desktop, reflows to one clean column on phones — automatically, no breakpoints, no burger toggle (use a wrapping/scrolling nav instead).`;
214
+ /** Build the HTML-artifact system prompt, tuned by style profile and flags. */
215
+ export function buildHtmlArtifactPrompt(options = {}) {
216
+ const { styleProfile, allowExternalFonts = false, allowForms = true, theme, presentation, } = options;
217
+ return [
218
+ BASE_SYSTEM_PROMPT,
219
+ "",
220
+ buildOutputFormat(presentation),
221
+ "",
222
+ HARD_RULES,
223
+ "",
224
+ buildInlineOnlyRule(),
225
+ "",
226
+ STREAMING_RULE,
227
+ "",
228
+ RESPONSIVE_RULE,
229
+ "",
230
+ IMAGES_RULE,
231
+ "",
232
+ DESIGN_DIRECTION,
233
+ "",
234
+ buildFontRule(allowExternalFonts),
235
+ buildFormRule(allowForms),
236
+ buildStyleProfileRule(styleProfile),
237
+ buildThemeRule(theme, presentation),
238
+ buildPresentationRule(presentation),
239
+ buildArtifactIdentityRule(presentation),
240
+ "",
241
+ "Think like a senior product designer with a strong point of view. Do not hold back — show what an exceptional, hand-crafted interface looks like — while honoring the host theme and rendering constraints above.",
242
+ ]
243
+ .filter(Boolean)
244
+ .join("\n");
245
+ }
246
+ /** Default prompt with no style profile, system fonts, forms allowed. */
247
+ export const HTML_ARTIFACT_SYSTEM_PROMPT = buildHtmlArtifactPrompt();
248
+ //# sourceMappingURL=htmlArtifactPrompt.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"htmlArtifactPrompt.js","sourceRoot":"","sources":["../../src/prompts/htmlArtifactPrompt.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ export * from "./systemPrompt.js";
2
+ export * from "./markdownPrompt.js";
3
+ export * from "./htmlArtifactPrompt.js";
4
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/prompts/index.ts"],"names":[],"mappings":"AAAA,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,cAAc,yBAAyB,CAAC"}
@@ -0,0 +1,4 @@
1
+ export * from "./systemPrompt.js";
2
+ export * from "./markdownPrompt.js";
3
+ export * from "./htmlArtifactPrompt.js";
4
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/prompts/index.ts"],"names":[],"mappings":"AAAA,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,cAAc,yBAAyB,CAAC"}
@@ -0,0 +1,3 @@
1
+ /** System prompt for plain markdown chat answers. */
2
+ export declare const MARKDOWN_SYSTEM_PROMPT = "You are a helpful assistant that answers either as markdown text or as a single self-contained static HTML/CSS artifact. You never mix the two: a response is entirely one mode. You write clearly, accurately, and concisely.\n\nYou are answering in MARKDOWN mode. Reply with a normal, well-structured markdown message:\n- Use headings, lists, and tables where they help.\n- Use fenced code blocks for code.\n- Be direct and avoid filler.\n- Do NOT emit any <assistant_message> or <html_artifact> tags in this mode \u2014 just write the markdown answer.";
3
+ //# sourceMappingURL=markdownPrompt.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"markdownPrompt.d.ts","sourceRoot":"","sources":["../../src/prompts/markdownPrompt.ts"],"names":[],"mappings":"AAEA,qDAAqD;AACrD,eAAO,MAAM,sBAAsB,2iBAM0E,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { BASE_SYSTEM_PROMPT } from "./systemPrompt.js";
2
+ /** System prompt for plain markdown chat answers. */
3
+ export const MARKDOWN_SYSTEM_PROMPT = `${BASE_SYSTEM_PROMPT}
4
+
5
+ You are answering in MARKDOWN mode. Reply with a normal, well-structured markdown message:
6
+ - Use headings, lists, and tables where they help.
7
+ - Use fenced code blocks for code.
8
+ - Be direct and avoid filler.
9
+ - Do NOT emit any <assistant_message> or <html_artifact> tags in this mode — just write the markdown answer.`;
10
+ //# sourceMappingURL=markdownPrompt.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"markdownPrompt.js","sourceRoot":"","sources":["../../src/prompts/markdownPrompt.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AAEvD,qDAAqD;AACrD,MAAM,CAAC,MAAM,sBAAsB,GAAG,GAAG,kBAAkB;;;;;;6GAMkD,CAAC"}
@@ -0,0 +1,3 @@
1
+ /** Shared preamble identifying the assistant and its two output modes. */
2
+ export declare const BASE_SYSTEM_PROMPT = "You are a helpful assistant that answers either as markdown text or as a single self-contained static HTML/CSS artifact. You never mix the two: a response is entirely one mode. You write clearly, accurately, and concisely.";
3
+ //# sourceMappingURL=systemPrompt.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"systemPrompt.d.ts","sourceRoot":"","sources":["../../src/prompts/systemPrompt.ts"],"names":[],"mappings":"AAAA,0EAA0E;AAC1E,eAAO,MAAM,kBAAkB,mOAAmO,CAAC"}
@@ -0,0 +1,3 @@
1
+ /** Shared preamble identifying the assistant and its two output modes. */
2
+ export const BASE_SYSTEM_PROMPT = `You are a helpful assistant that answers either as markdown text or as a single self-contained static HTML/CSS artifact. You never mix the two: a response is entirely one mode. You write clearly, accurately, and concisely.`;
3
+ //# sourceMappingURL=systemPrompt.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"systemPrompt.js","sourceRoot":"","sources":["../../src/prompts/systemPrompt.ts"],"names":[],"mappings":"AAAA,0EAA0E;AAC1E,MAAM,CAAC,MAAM,kBAAkB,GAAG,gOAAgO,CAAC"}
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Regex building blocks for the static-HTML sanitizer. These are deliberately
3
+ * conservative: the sanitizer's job is to guarantee that no JavaScript can run
4
+ * inside the artifact iframe, regardless of how creative the model gets.
5
+ *
6
+ * The sanitizer is regex-based on purpose: it must run identically on the
7
+ * server (Node) and the client (browser) with zero DOM dependency.
8
+ */
9
+ /** `<script>...</script>`, including attributes and across newlines. */
10
+ export declare const SCRIPT_BLOCK: RegExp;
11
+ /** A dangling/self-closed `<script ...>` with no closing tag. */
12
+ export declare const SCRIPT_OPEN: RegExp;
13
+ /** `<iframe>`, `<object>`, `<embed>`, `<base>`, `<frame>`, `<frameset>`. */
14
+ export declare const EMBED_BLOCK: RegExp;
15
+ export declare const EMBED_OPEN: RegExp;
16
+ /** `<meta http-equiv="refresh" ...>` — used for redirect/navigation tricks. */
17
+ export declare const META_REFRESH: RegExp;
18
+ /**
19
+ * Inline event-handler attributes (`onclick`, `onload`, `onerror`, ...).
20
+ * Matches quoted, single-quoted, and unquoted values.
21
+ */
22
+ export declare const EVENT_HANDLER_ATTR: RegExp;
23
+ /** `javascript:` / `vbscript:` / `data:text/html` protocol URLs in attributes. */
24
+ export declare const DANGEROUS_URL_ATTR: RegExp;
25
+ /** `style="...:expression(...)..."` — legacy IE script-in-CSS vector. */
26
+ export declare const CSS_EXPRESSION: RegExp;
27
+ /** External stylesheet links: `<link rel="stylesheet" ...>`. */
28
+ export declare const STYLESHEET_LINK: RegExp;
29
+ /** Any `<link>` pointing at an http(s) resource (fonts, preconnect, etc.). */
30
+ export declare const EXTERNAL_LINK: RegExp;
31
+ /** `@import url(...)` inside CSS. */
32
+ export declare const CSS_IMPORT: RegExp;
33
+ /** `<style>...</style>` blocks. */
34
+ export declare const STYLE_BLOCK: RegExp;
35
+ /** Inline `style="..."` attributes. */
36
+ export declare const INLINE_STYLE_ATTR: RegExp;
37
+ /** `<svg>...</svg>` blocks. */
38
+ export declare const SVG_BLOCK: RegExp;
39
+ /** Form-related tags (open + close), used when forms are disallowed. */
40
+ export declare const FORM_TAGS: RegExp;
41
+ //# sourceMappingURL=dangerousPatterns.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dangerousPatterns.d.ts","sourceRoot":"","sources":["../../src/sanitizer/dangerousPatterns.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,wEAAwE;AACxE,eAAO,MAAM,YAAY,QAA2C,CAAC;AACrE,iEAAiE;AACjE,eAAO,MAAM,WAAW,QAAyB,CAAC;AAElD,4EAA4E;AAC5E,eAAO,MAAM,WAAW,QAC4C,CAAC;AACrE,eAAO,MAAM,UAAU,QACoC,CAAC;AAE5D,+EAA+E;AAC/E,eAAO,MAAM,YAAY,QAA2D,CAAC;AAErF;;;GAGG;AACH,eAAO,MAAM,kBAAkB,QACoB,CAAC;AAEpD,kFAAkF;AAClF,eAAO,MAAM,kBAAkB,QACoL,CAAC;AAEpN,yEAAyE;AACzE,eAAO,MAAM,cAAc,QAAsB,CAAC;AAElD,gEAAgE;AAChE,eAAO,MAAM,eAAe,QAC0B,CAAC;AACvD,8EAA8E;AAC9E,eAAO,MAAM,aAAa,QAAoB,CAAC;AAE/C,qCAAqC;AACrC,eAAO,MAAM,UAAU,QAAuB,CAAC;AAE/C,mCAAmC;AACnC,eAAO,MAAM,WAAW,QAAyC,CAAC;AAElE,uCAAuC;AACvC,eAAO,MAAM,iBAAiB,QAAyC,CAAC;AAExE,+BAA+B;AAC/B,eAAO,MAAM,SAAS,QAAqC,CAAC;AAE5D,wEAAwE;AACxE,eAAO,MAAM,SAAS,QAC4E,CAAC"}
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Regex building blocks for the static-HTML sanitizer. These are deliberately
3
+ * conservative: the sanitizer's job is to guarantee that no JavaScript can run
4
+ * inside the artifact iframe, regardless of how creative the model gets.
5
+ *
6
+ * The sanitizer is regex-based on purpose: it must run identically on the
7
+ * server (Node) and the client (browser) with zero DOM dependency.
8
+ */
9
+ /** `<script>...</script>`, including attributes and across newlines. */
10
+ export const SCRIPT_BLOCK = /<script\b[^>]*>[\s\S]*?<\/script\s*>/gi;
11
+ /** A dangling/self-closed `<script ...>` with no closing tag. */
12
+ export const SCRIPT_OPEN = /<script\b[^>]*\/?>/gi;
13
+ /** `<iframe>`, `<object>`, `<embed>`, `<base>`, `<frame>`, `<frameset>`. */
14
+ export const EMBED_BLOCK = /<(iframe|object|embed|frame|frameset)\b[^>]*>[\s\S]*?<\/\1\s*>/gi;
15
+ export const EMBED_OPEN = /<(iframe|object|embed|frame|frameset|base)\b[^>]*\/?>/gi;
16
+ /** `<meta http-equiv="refresh" ...>` — used for redirect/navigation tricks. */
17
+ export const META_REFRESH = /<meta\b[^>]*http-equiv\s*=\s*["']?refresh["']?[^>]*>/gi;
18
+ /**
19
+ * Inline event-handler attributes (`onclick`, `onload`, `onerror`, ...).
20
+ * Matches quoted, single-quoted, and unquoted values.
21
+ */
22
+ export const EVENT_HANDLER_ATTR = /\s+on[a-z]+\s*=\s*(?:"[^"]*"|'[^']*'|[^\s>]+)/gi;
23
+ /** `javascript:` / `vbscript:` / `data:text/html` protocol URLs in attributes. */
24
+ export const DANGEROUS_URL_ATTR = /\s+(href|src|action|formaction|xlink:href|background|poster)\s*=\s*(?:"\s*(?:javascript|vbscript|data:text\/html)[^"]*"|'\s*(?:javascript|vbscript|data:text\/html)[^']*'|\s*(?:javascript|vbscript):[^\s>]*)/gi;
25
+ /** `style="...:expression(...)..."` — legacy IE script-in-CSS vector. */
26
+ export const CSS_EXPRESSION = /expression\s*\(/gi;
27
+ /** External stylesheet links: `<link rel="stylesheet" ...>`. */
28
+ export const STYLESHEET_LINK = /<link\b[^>]*rel\s*=\s*["']?stylesheet["']?[^>]*>/gi;
29
+ /** Any `<link>` pointing at an http(s) resource (fonts, preconnect, etc.). */
30
+ export const EXTERNAL_LINK = /<link\b[^>]*>/gi;
31
+ /** `@import url(...)` inside CSS. */
32
+ export const CSS_IMPORT = /@import\b[^;]+;?/gi;
33
+ /** `<style>...</style>` blocks. */
34
+ export const STYLE_BLOCK = /<style\b[^>]*>[\s\S]*?<\/style\s*>/gi;
35
+ /** Inline `style="..."` attributes. */
36
+ export const INLINE_STYLE_ATTR = /\s+style\s*=\s*(?:"[^"]*"|'[^']*')/gi;
37
+ /** `<svg>...</svg>` blocks. */
38
+ export const SVG_BLOCK = /<svg\b[^>]*>[\s\S]*?<\/svg\s*>/gi;
39
+ /** Form-related tags (open + close), used when forms are disallowed. */
40
+ export const FORM_TAGS = /<\/?(form|input|button|label|textarea|select|option|fieldset|legend|datalist|output)\b[^>]*>/gi;
41
+ //# sourceMappingURL=dangerousPatterns.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dangerousPatterns.js","sourceRoot":"","sources":["../../src/sanitizer/dangerousPatterns.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,wEAAwE;AACxE,MAAM,CAAC,MAAM,YAAY,GAAG,wCAAwC,CAAC;AACrE,iEAAiE;AACjE,MAAM,CAAC,MAAM,WAAW,GAAG,sBAAsB,CAAC;AAElD,4EAA4E;AAC5E,MAAM,CAAC,MAAM,WAAW,GACtB,kEAAkE,CAAC;AACrE,MAAM,CAAC,MAAM,UAAU,GACrB,yDAAyD,CAAC;AAE5D,+EAA+E;AAC/E,MAAM,CAAC,MAAM,YAAY,GAAG,wDAAwD,CAAC;AAErF;;;GAGG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAC7B,iDAAiD,CAAC;AAEpD,kFAAkF;AAClF,MAAM,CAAC,MAAM,kBAAkB,GAC7B,iNAAiN,CAAC;AAEpN,yEAAyE;AACzE,MAAM,CAAC,MAAM,cAAc,GAAG,mBAAmB,CAAC;AAElD,gEAAgE;AAChE,MAAM,CAAC,MAAM,eAAe,GAC1B,oDAAoD,CAAC;AACvD,8EAA8E;AAC9E,MAAM,CAAC,MAAM,aAAa,GAAG,iBAAiB,CAAC;AAE/C,qCAAqC;AACrC,MAAM,CAAC,MAAM,UAAU,GAAG,oBAAoB,CAAC;AAE/C,mCAAmC;AACnC,MAAM,CAAC,MAAM,WAAW,GAAG,sCAAsC,CAAC;AAElE,uCAAuC;AACvC,MAAM,CAAC,MAAM,iBAAiB,GAAG,sCAAsC,CAAC;AAExE,+BAA+B;AAC/B,MAAM,CAAC,MAAM,SAAS,GAAG,kCAAkC,CAAC;AAE5D,wEAAwE;AACxE,MAAM,CAAC,MAAM,SAAS,GACpB,gGAAgG,CAAC"}
@@ -0,0 +1,4 @@
1
+ export * from "./sanitizeHtml.js";
2
+ export * from "./sanitizeConfig.js";
3
+ export * as dangerousPatterns from "./dangerousPatterns.js";
4
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/sanitizer/index.ts"],"names":[],"mappings":"AAAA,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,OAAO,KAAK,iBAAiB,MAAM,wBAAwB,CAAC"}
@@ -0,0 +1,4 @@
1
+ export * from "./sanitizeHtml.js";
2
+ export * from "./sanitizeConfig.js";
3
+ export * as dangerousPatterns from "./dangerousPatterns.js";
4
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/sanitizer/index.ts"],"names":[],"mappings":"AAAA,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,OAAO,KAAK,iBAAiB,MAAM,wBAAwB,CAAC"}
@@ -0,0 +1,4 @@
1
+ import type { SanitizeOptions } from "../types/config.js";
2
+ /** Resolve partial sanitize options against the static-safe defaults. */
3
+ export declare function resolveSanitizeOptions(options?: SanitizeOptions): Required<SanitizeOptions>;
4
+ //# sourceMappingURL=sanitizeConfig.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sanitizeConfig.d.ts","sourceRoot":"","sources":["../../src/sanitizer/sanitizeConfig.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAE1D,yEAAyE;AACzE,wBAAgB,sBAAsB,CACpC,OAAO,CAAC,EAAE,eAAe,GACxB,QAAQ,CAAC,eAAe,CAAC,CAK3B"}
@@ -0,0 +1,10 @@
1
+ import { DEFAULT_SANITIZE_OPTIONS } from "../constants/defaults.js";
2
+ import { mergeConfig } from "../utils/mergeConfig.js";
3
+ /** Resolve partial sanitize options against the static-safe defaults. */
4
+ export function resolveSanitizeOptions(options) {
5
+ const merged = mergeConfig(DEFAULT_SANITIZE_OPTIONS, options);
6
+ // Scripts are never allowed, no matter what a caller passes.
7
+ merged.allowScripts = false;
8
+ return merged;
9
+ }
10
+ //# sourceMappingURL=sanitizeConfig.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sanitizeConfig.js","sourceRoot":"","sources":["../../src/sanitizer/sanitizeConfig.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,wBAAwB,EAAE,MAAM,0BAA0B,CAAC;AACpE,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAC;AAGtD,yEAAyE;AACzE,MAAM,UAAU,sBAAsB,CACpC,OAAyB;IAEzB,MAAM,MAAM,GAAG,WAAW,CAAC,wBAAwB,EAAE,OAAO,CAAC,CAAC;IAC9D,6DAA6D;IAC7D,MAAM,CAAC,YAAY,GAAG,KAAK,CAAC;IAC5B,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,20 @@
1
+ import type { SanitizeOptions } from "../types/config.js";
2
+ export interface SanitizeResult {
3
+ html: string;
4
+ /** True if any dangerous content was stripped. */
5
+ modified: boolean;
6
+ /** True if the sanitizer crashed and returned an escaped fallback. */
7
+ failedOpen: boolean;
8
+ }
9
+ /**
10
+ * Strip everything that could execute or load JavaScript from an HTML string,
11
+ * keeping static markup, CSS, SVG, and forms according to `options`.
12
+ *
13
+ * Fail-open: if anything throws, we return the input HTML-escaped inside a
14
+ * `<pre>` so the iframe shows inert text rather than crashing the render.
15
+ */
16
+ export declare function sanitizeHtml(input: string, options?: SanitizeOptions): SanitizeResult;
17
+ /** Convenience wrapper returning only the sanitized string. */
18
+ export declare function sanitize(input: string, options?: SanitizeOptions): string;
19
+ export declare function escapeHtml(input: string): string;
20
+ //# sourceMappingURL=sanitizeHtml.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sanitizeHtml.d.ts","sourceRoot":"","sources":["../../src/sanitizer/sanitizeHtml.ts"],"names":[],"mappings":"AAkBA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AAU1D,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,MAAM,CAAC;IACb,kDAAkD;IAClD,QAAQ,EAAE,OAAO,CAAC;IAClB,sEAAsE;IACtE,UAAU,EAAE,OAAO,CAAC;CACrB;AAED;;;;;;GAMG;AACH,wBAAgB,YAAY,CAC1B,KAAK,EAAE,MAAM,EACb,OAAO,CAAC,EAAE,eAAe,GACxB,cAAc,CA6DhB;AAED,+DAA+D;AAC/D,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,eAAe,GAAG,MAAM,CAEzE;AAED,wBAAgB,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAOhD"}
@@ -0,0 +1,81 @@
1
+ import { resolveSanitizeOptions } from "./sanitizeConfig.js";
2
+ import { CSS_EXPRESSION, CSS_IMPORT, DANGEROUS_URL_ATTR, EMBED_BLOCK, EMBED_OPEN, EVENT_HANDLER_ATTR, EXTERNAL_LINK, FORM_TAGS, INLINE_STYLE_ATTR, META_REFRESH, SCRIPT_BLOCK, SCRIPT_OPEN, STYLE_BLOCK, STYLESHEET_LINK, SVG_BLOCK, } from "./dangerousPatterns.js";
3
+ // A <link> is kept under allowExternalFonts only if its href starts with a
4
+ // Google Fonts host (covers stylesheet links and preconnect hints).
5
+ const ALLOWED_FONT_LINK = /href\s*=\s*["']https:\/\/fonts\.(googleapis|gstatic)\.com/i;
6
+ // An @import is kept only if it targets the Google Fonts CSS host.
7
+ const ALLOWED_FONT_IMPORT = /@import\s+(?:url\()?\s*["']?https:\/\/fonts\.googleapis\.com/i;
8
+ /**
9
+ * Strip everything that could execute or load JavaScript from an HTML string,
10
+ * keeping static markup, CSS, SVG, and forms according to `options`.
11
+ *
12
+ * Fail-open: if anything throws, we return the input HTML-escaped inside a
13
+ * `<pre>` so the iframe shows inert text rather than crashing the render.
14
+ */
15
+ export function sanitizeHtml(input, options) {
16
+ const opts = resolveSanitizeOptions(options);
17
+ try {
18
+ if (typeof input !== "string") {
19
+ return { html: "", modified: false, failedOpen: false };
20
+ }
21
+ let html = input;
22
+ const before = html;
23
+ // 1. Scripts — always removed.
24
+ html = html.replace(SCRIPT_BLOCK, "").replace(SCRIPT_OPEN, "");
25
+ // 2. Nested browsing contexts & navigation tricks — always removed.
26
+ html = html
27
+ .replace(EMBED_BLOCK, "")
28
+ .replace(EMBED_OPEN, "")
29
+ .replace(META_REFRESH, "");
30
+ // 3. Inline event handlers — always removed.
31
+ html = html.replace(EVENT_HANDLER_ATTR, "");
32
+ // 4. javascript:/vbscript:/data:text/html URLs — always removed.
33
+ html = html.replace(DANGEROUS_URL_ATTR, "");
34
+ // 5. CSS expression() — always removed.
35
+ html = html.replace(CSS_EXPRESSION, "void(");
36
+ // 6. External CSS / fonts.
37
+ if (opts.allowExternalFonts) {
38
+ // Keep ONLY links/imports pointing at the Google Fonts hosts; strip the
39
+ // rest. This permits distinctive typography without opening a hole for
40
+ // arbitrary external stylesheets.
41
+ html = html
42
+ .replace(EXTERNAL_LINK, (tag) => ALLOWED_FONT_LINK.test(tag) ? tag : "")
43
+ .replace(CSS_IMPORT, (imp) => ALLOWED_FONT_IMPORT.test(imp) ? imp : "");
44
+ }
45
+ else {
46
+ html = html.replace(STYLESHEET_LINK, "").replace(CSS_IMPORT, "");
47
+ // Remove any remaining <link> (preconnect/font links) too.
48
+ html = html.replace(EXTERNAL_LINK, "");
49
+ }
50
+ // 7. Optional element classes.
51
+ if (!opts.allowStyleTags)
52
+ html = html.replace(STYLE_BLOCK, "");
53
+ if (!opts.allowInlineStyles)
54
+ html = html.replace(INLINE_STYLE_ATTR, "");
55
+ if (!opts.allowSvg)
56
+ html = html.replace(SVG_BLOCK, "");
57
+ if (!opts.allowForms)
58
+ html = html.replace(FORM_TAGS, "");
59
+ return { html, modified: html !== before, failedOpen: false };
60
+ }
61
+ catch {
62
+ return {
63
+ html: `<pre>${escapeHtml(String(input))}</pre>`,
64
+ modified: true,
65
+ failedOpen: true,
66
+ };
67
+ }
68
+ }
69
+ /** Convenience wrapper returning only the sanitized string. */
70
+ export function sanitize(input, options) {
71
+ return sanitizeHtml(input, options).html;
72
+ }
73
+ export function escapeHtml(input) {
74
+ return input
75
+ .replace(/&/g, "&amp;")
76
+ .replace(/</g, "&lt;")
77
+ .replace(/>/g, "&gt;")
78
+ .replace(/"/g, "&quot;")
79
+ .replace(/'/g, "&#39;");
80
+ }
81
+ //# sourceMappingURL=sanitizeHtml.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sanitizeHtml.js","sourceRoot":"","sources":["../../src/sanitizer/sanitizeHtml.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,6 @@
1
+ import type { CoreMessage, CreateArtifactStreamResponseOptions, ResolvedServerConfig } from "../types/server.js";
2
+ /** Fill in defaults and precompute the prompts for a request. */
3
+ export declare function resolveServerConfig(options: CreateArtifactStreamResponseOptions): ResolvedServerConfig;
4
+ /** Extract the latest user message text for classification. */
5
+ export declare function latestUserText(messages: CoreMessage[]): string;
6
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/server/config.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EACV,WAAW,EACX,mCAAmC,EACnC,oBAAoB,EACrB,MAAM,oBAAoB,CAAC;AAE5B,iEAAiE;AACjE,wBAAgB,mBAAmB,CACjC,OAAO,EAAE,mCAAmC,GAC3C,oBAAoB,CA2CtB;AAED,+DAA+D;AAC/D,wBAAgB,cAAc,CAAC,QAAQ,EAAE,WAAW,EAAE,GAAG,MAAM,CAO9D"}