@nhtio/adk 1.20260607.2 → 1.20260609.1

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 (521) hide show
  1. package/CHANGELOG.md +230 -0
  2. package/batteries/embeddings/openai/adapter.cjs +1 -1
  3. package/batteries/embeddings/openai/adapter.mjs +1 -1
  4. package/batteries/embeddings/openai/exceptions.cjs +1 -1
  5. package/batteries/embeddings/openai/exceptions.mjs +1 -1
  6. package/batteries/embeddings/openai/types.d.ts +7 -0
  7. package/batteries/embeddings/webllm/adapter.cjs +1 -1
  8. package/batteries/embeddings/webllm/adapter.mjs +1 -1
  9. package/batteries/embeddings/webllm/exceptions.cjs +1 -1
  10. package/batteries/embeddings/webllm/exceptions.mjs +1 -1
  11. package/batteries/llm/chat_common/helpers.d.ts +165 -0
  12. package/batteries/llm/chat_common/types.d.ts +309 -0
  13. package/batteries/llm/index.d.ts +5 -0
  14. package/batteries/llm/ollama/adapter.cjs +736 -0
  15. package/batteries/llm/ollama/adapter.cjs.map +1 -0
  16. package/batteries/llm/ollama/adapter.d.ts +64 -0
  17. package/batteries/llm/ollama/adapter.mjs +734 -0
  18. package/batteries/llm/ollama/adapter.mjs.map +1 -0
  19. package/batteries/llm/ollama/exceptions.cjs +105 -0
  20. package/batteries/llm/ollama/exceptions.cjs.map +1 -0
  21. package/batteries/llm/ollama/exceptions.d.ts +112 -0
  22. package/batteries/llm/ollama/exceptions.mjs +96 -0
  23. package/batteries/llm/ollama/exceptions.mjs.map +1 -0
  24. package/batteries/llm/ollama/helpers.cjs +487 -0
  25. package/batteries/llm/ollama/helpers.cjs.map +1 -0
  26. package/batteries/llm/ollama/helpers.d.ts +158 -0
  27. package/batteries/llm/ollama/helpers.mjs +450 -0
  28. package/batteries/llm/ollama/helpers.mjs.map +1 -0
  29. package/batteries/llm/ollama/index.d.ts +29 -0
  30. package/batteries/llm/ollama/types.cjs +2 -0
  31. package/batteries/llm/ollama/types.d.ts +334 -0
  32. package/batteries/llm/ollama/types.mjs +0 -0
  33. package/batteries/llm/ollama/validation.cjs +130 -0
  34. package/batteries/llm/ollama/validation.cjs.map +1 -0
  35. package/batteries/llm/ollama/validation.d.ts +31 -0
  36. package/batteries/llm/ollama/validation.mjs +127 -0
  37. package/batteries/llm/ollama/validation.mjs.map +1 -0
  38. package/batteries/llm/ollama.cjs +54 -0
  39. package/batteries/llm/ollama.mjs +6 -0
  40. package/batteries/llm/openai_chat_completions/adapter.cjs +36 -19
  41. package/batteries/llm/openai_chat_completions/adapter.cjs.map +1 -1
  42. package/batteries/llm/openai_chat_completions/adapter.mjs +23 -6
  43. package/batteries/llm/openai_chat_completions/adapter.mjs.map +1 -1
  44. package/batteries/llm/openai_chat_completions/exceptions.cjs +1 -1
  45. package/batteries/llm/openai_chat_completions/exceptions.mjs +1 -1
  46. package/batteries/llm/openai_chat_completions/helpers.cjs +80 -320
  47. package/batteries/llm/openai_chat_completions/helpers.cjs.map +1 -1
  48. package/batteries/llm/openai_chat_completions/helpers.d.ts +68 -144
  49. package/batteries/llm/openai_chat_completions/helpers.mjs +40 -280
  50. package/batteries/llm/openai_chat_completions/helpers.mjs.map +1 -1
  51. package/batteries/llm/openai_chat_completions/types.d.ts +273 -181
  52. package/batteries/llm/openai_chat_completions/validation.cjs +2 -2
  53. package/batteries/llm/openai_chat_completions/validation.cjs.map +1 -1
  54. package/batteries/llm/openai_chat_completions/validation.mjs +2 -2
  55. package/batteries/llm/openai_chat_completions/validation.mjs.map +1 -1
  56. package/batteries/llm/openai_chat_completions.cjs +29 -28
  57. package/batteries/llm/openai_chat_completions.mjs +2 -1
  58. package/batteries/llm/webllm_chat_completions/adapter.cjs +38 -19
  59. package/batteries/llm/webllm_chat_completions/adapter.cjs.map +1 -1
  60. package/batteries/llm/webllm_chat_completions/adapter.d.ts +18 -0
  61. package/batteries/llm/webllm_chat_completions/adapter.mjs +25 -6
  62. package/batteries/llm/webllm_chat_completions/adapter.mjs.map +1 -1
  63. package/batteries/llm/webllm_chat_completions/exceptions.cjs +1 -1
  64. package/batteries/llm/webllm_chat_completions/exceptions.mjs +1 -1
  65. package/batteries/llm/webllm_chat_completions/helpers.cjs +29 -28
  66. package/batteries/llm/webllm_chat_completions/helpers.mjs +2 -1
  67. package/batteries/llm/webllm_chat_completions/types.d.ts +21 -0
  68. package/batteries/llm/webllm_chat_completions/validation.cjs +13 -1
  69. package/batteries/llm/webllm_chat_completions/validation.cjs.map +1 -1
  70. package/batteries/llm/webllm_chat_completions/validation.d.ts +12 -0
  71. package/batteries/llm/webllm_chat_completions/validation.mjs +13 -1
  72. package/batteries/llm/webllm_chat_completions/validation.mjs.map +1 -1
  73. package/batteries/llm/webllm_chat_completions.cjs +29 -28
  74. package/batteries/llm/webllm_chat_completions.mjs +2 -1
  75. package/batteries/llm.cjs +44 -28
  76. package/batteries/llm.mjs +9 -4
  77. package/batteries/storage/flydrive.cjs +1 -1
  78. package/batteries/storage/flydrive.mjs +1 -1
  79. package/batteries/storage/in_memory/index.d.ts +1 -1
  80. package/batteries/storage/in_memory.cjs +2 -2
  81. package/batteries/storage/in_memory.cjs.map +1 -1
  82. package/batteries/storage/in_memory.mjs +2 -2
  83. package/batteries/storage/in_memory.mjs.map +1 -1
  84. package/batteries/storage/opfs/index.d.ts +19 -0
  85. package/batteries/storage/opfs.cjs +1 -1
  86. package/batteries/storage/opfs.cjs.map +1 -1
  87. package/batteries/storage/opfs.mjs +1 -1
  88. package/batteries/storage/opfs.mjs.map +1 -1
  89. package/batteries/tools/_shared/index.d.ts +121 -0
  90. package/batteries/tools/_shared.cjs +157 -0
  91. package/batteries/tools/_shared.cjs.map +1 -0
  92. package/batteries/tools/_shared.mjs +149 -0
  93. package/batteries/tools/_shared.mjs.map +1 -0
  94. package/batteries/tools/color.cjs +3 -2
  95. package/batteries/tools/color.cjs.map +1 -1
  96. package/batteries/tools/color.mjs +3 -2
  97. package/batteries/tools/color.mjs.map +1 -1
  98. package/batteries/tools/comparison.cjs +4 -3
  99. package/batteries/tools/comparison.cjs.map +1 -1
  100. package/batteries/tools/comparison.mjs +4 -3
  101. package/batteries/tools/comparison.mjs.map +1 -1
  102. package/batteries/tools/data_structure.cjs +30 -10
  103. package/batteries/tools/data_structure.cjs.map +1 -1
  104. package/batteries/tools/data_structure.mjs +30 -10
  105. package/batteries/tools/data_structure.mjs.map +1 -1
  106. package/batteries/tools/datetime_extended.cjs +5 -10
  107. package/batteries/tools/datetime_extended.cjs.map +1 -1
  108. package/batteries/tools/datetime_extended.mjs +5 -10
  109. package/batteries/tools/datetime_extended.mjs.map +1 -1
  110. package/batteries/tools/datetime_math.cjs +2 -2
  111. package/batteries/tools/datetime_math.mjs +2 -2
  112. package/batteries/tools/encoding.cjs +13 -4
  113. package/batteries/tools/encoding.cjs.map +1 -1
  114. package/batteries/tools/encoding.mjs +13 -4
  115. package/batteries/tools/encoding.mjs.map +1 -1
  116. package/batteries/tools/formatting.cjs +4 -4
  117. package/batteries/tools/formatting.cjs.map +1 -1
  118. package/batteries/tools/formatting.mjs +4 -4
  119. package/batteries/tools/formatting.mjs.map +1 -1
  120. package/batteries/tools/geo_basics.cjs +2 -2
  121. package/batteries/tools/geo_basics.mjs +2 -2
  122. package/batteries/tools/index.d.ts +3 -0
  123. package/batteries/tools/math.cjs +10 -8
  124. package/batteries/tools/math.cjs.map +1 -1
  125. package/batteries/tools/math.mjs +10 -8
  126. package/batteries/tools/math.mjs.map +1 -1
  127. package/batteries/tools/memory.cjs +5 -5
  128. package/batteries/tools/memory.mjs +5 -5
  129. package/batteries/tools/parsing.cjs +9 -5
  130. package/batteries/tools/parsing.cjs.map +1 -1
  131. package/batteries/tools/parsing.mjs +9 -5
  132. package/batteries/tools/parsing.mjs.map +1 -1
  133. package/batteries/tools/retrievables.cjs +4 -4
  134. package/batteries/tools/retrievables.mjs +4 -4
  135. package/batteries/tools/scrapper/exceptions.d.ts +21 -0
  136. package/batteries/tools/scrapper/index.d.ts +172 -0
  137. package/batteries/tools/scrapper/shared.d.ts +139 -0
  138. package/batteries/tools/scrapper.cjs +8 -0
  139. package/batteries/tools/scrapper.mjs +2 -0
  140. package/batteries/tools/searxng/exceptions.d.ts +21 -0
  141. package/batteries/tools/searxng/index.d.ts +177 -0
  142. package/batteries/tools/searxng.cjs +6 -0
  143. package/batteries/tools/searxng.mjs +2 -0
  144. package/batteries/tools/standing_instructions.cjs +4 -4
  145. package/batteries/tools/standing_instructions.mjs +4 -4
  146. package/batteries/tools/statistics.cjs +54 -43
  147. package/batteries/tools/statistics.cjs.map +1 -1
  148. package/batteries/tools/statistics.mjs +54 -43
  149. package/batteries/tools/statistics.mjs.map +1 -1
  150. package/batteries/tools/string_processing.cjs +5 -5
  151. package/batteries/tools/string_processing.cjs.map +1 -1
  152. package/batteries/tools/string_processing.mjs +5 -5
  153. package/batteries/tools/string_processing.mjs.map +1 -1
  154. package/batteries/tools/structured_data.cjs +8 -13
  155. package/batteries/tools/structured_data.cjs.map +1 -1
  156. package/batteries/tools/structured_data.mjs +8 -13
  157. package/batteries/tools/structured_data.mjs.map +1 -1
  158. package/batteries/tools/text_analysis.cjs +3 -3
  159. package/batteries/tools/text_analysis.mjs +3 -3
  160. package/batteries/tools/text_comparison.cjs +2 -2
  161. package/batteries/tools/text_comparison.mjs +2 -2
  162. package/batteries/tools/time.cjs +2 -2
  163. package/batteries/tools/time.mjs +2 -2
  164. package/batteries/tools/unit_conversion.cjs +10 -8
  165. package/batteries/tools/unit_conversion.cjs.map +1 -1
  166. package/batteries/tools/unit_conversion.mjs +10 -8
  167. package/batteries/tools/unit_conversion.mjs.map +1 -1
  168. package/batteries/tools/web_retrieval/index.d.ts +186 -0
  169. package/batteries/tools/web_retrieval.cjs +206 -0
  170. package/batteries/tools/web_retrieval.cjs.map +1 -0
  171. package/batteries/tools/web_retrieval.mjs +201 -0
  172. package/batteries/tools/web_retrieval.mjs.map +1 -0
  173. package/batteries/tools.cjs +15 -0
  174. package/batteries/tools.mjs +4 -1
  175. package/batteries/vector/arangodb/index.d.ts +2 -0
  176. package/batteries/vector/arangodb.cjs +2 -1
  177. package/batteries/vector/arangodb.cjs.map +1 -1
  178. package/batteries/vector/arangodb.mjs +2 -1
  179. package/batteries/vector/arangodb.mjs.map +1 -1
  180. package/batteries/vector/builder.cjs +31 -0
  181. package/batteries/vector/builder.cjs.map +1 -1
  182. package/batteries/vector/builder.d.ts +58 -0
  183. package/batteries/vector/builder.mjs +31 -0
  184. package/batteries/vector/builder.mjs.map +1 -1
  185. package/batteries/vector/chroma/index.d.ts +4 -0
  186. package/batteries/vector/chroma.cjs +3 -0
  187. package/batteries/vector/chroma.cjs.map +1 -1
  188. package/batteries/vector/chroma.mjs +3 -0
  189. package/batteries/vector/chroma.mjs.map +1 -1
  190. package/batteries/vector/clickhouse/index.d.ts +2 -0
  191. package/batteries/vector/clickhouse.cjs +2 -1
  192. package/batteries/vector/clickhouse.cjs.map +1 -1
  193. package/batteries/vector/clickhouse.mjs +2 -1
  194. package/batteries/vector/clickhouse.mjs.map +1 -1
  195. package/batteries/vector/cloudflare/index.d.ts +2 -0
  196. package/batteries/vector/cloudflare.cjs +2 -1
  197. package/batteries/vector/cloudflare.cjs.map +1 -1
  198. package/batteries/vector/cloudflare.mjs +2 -1
  199. package/batteries/vector/cloudflare.mjs.map +1 -1
  200. package/batteries/vector/conformance/index.d.ts +22 -0
  201. package/batteries/vector/conformance.cjs +22 -0
  202. package/batteries/vector/conformance.cjs.map +1 -1
  203. package/batteries/vector/conformance.mjs +22 -0
  204. package/batteries/vector/conformance.mjs.map +1 -1
  205. package/batteries/vector/contract.cjs +22 -0
  206. package/batteries/vector/contract.cjs.map +1 -1
  207. package/batteries/vector/contract.d.ts +51 -0
  208. package/batteries/vector/contract.mjs +22 -0
  209. package/batteries/vector/contract.mjs.map +1 -1
  210. package/batteries/vector/couchbase/index.d.ts +2 -0
  211. package/batteries/vector/couchbase.cjs +2 -1
  212. package/batteries/vector/couchbase.cjs.map +1 -1
  213. package/batteries/vector/couchbase.mjs +2 -1
  214. package/batteries/vector/couchbase.mjs.map +1 -1
  215. package/batteries/vector/duckdb/index.d.ts +2 -0
  216. package/batteries/vector/duckdb.cjs +2 -1
  217. package/batteries/vector/duckdb.cjs.map +1 -1
  218. package/batteries/vector/duckdb.mjs +2 -1
  219. package/batteries/vector/duckdb.mjs.map +1 -1
  220. package/batteries/vector/elasticsearch/index.d.ts +2 -0
  221. package/batteries/vector/elasticsearch.cjs +2 -1
  222. package/batteries/vector/elasticsearch.cjs.map +1 -1
  223. package/batteries/vector/elasticsearch.mjs +2 -1
  224. package/batteries/vector/elasticsearch.mjs.map +1 -1
  225. package/batteries/vector/exceptions.cjs +1 -1
  226. package/batteries/vector/exceptions.mjs +1 -1
  227. package/batteries/vector/factory.cjs +6 -0
  228. package/batteries/vector/factory.cjs.map +1 -1
  229. package/batteries/vector/factory.d.ts +14 -0
  230. package/batteries/vector/factory.mjs +6 -0
  231. package/batteries/vector/factory.mjs.map +1 -1
  232. package/batteries/vector/filters.cjs +22 -1
  233. package/batteries/vector/filters.cjs.map +1 -1
  234. package/batteries/vector/filters.d.ts +38 -0
  235. package/batteries/vector/filters.mjs +22 -1
  236. package/batteries/vector/filters.mjs.map +1 -1
  237. package/batteries/vector/helpers.cjs +13 -0
  238. package/batteries/vector/helpers.cjs.map +1 -1
  239. package/batteries/vector/helpers.d.ts +14 -0
  240. package/batteries/vector/helpers.mjs +13 -0
  241. package/batteries/vector/helpers.mjs.map +1 -1
  242. package/batteries/vector/hnswlib/index.d.ts +2 -0
  243. package/batteries/vector/hnswlib.cjs +2 -1
  244. package/batteries/vector/hnswlib.cjs.map +1 -1
  245. package/batteries/vector/hnswlib.mjs +2 -1
  246. package/batteries/vector/hnswlib.mjs.map +1 -1
  247. package/batteries/vector/in_memory/index.d.ts +1 -0
  248. package/batteries/vector/in_memory.cjs +1 -0
  249. package/batteries/vector/in_memory.cjs.map +1 -1
  250. package/batteries/vector/in_memory.mjs +1 -0
  251. package/batteries/vector/in_memory.mjs.map +1 -1
  252. package/batteries/vector/lancedb/index.d.ts +2 -0
  253. package/batteries/vector/lancedb.cjs +2 -1
  254. package/batteries/vector/lancedb.cjs.map +1 -1
  255. package/batteries/vector/lancedb.mjs +2 -1
  256. package/batteries/vector/lancedb.mjs.map +1 -1
  257. package/batteries/vector/mariadb/index.d.ts +2 -0
  258. package/batteries/vector/mariadb.cjs +2 -1
  259. package/batteries/vector/mariadb.cjs.map +1 -1
  260. package/batteries/vector/mariadb.mjs +2 -1
  261. package/batteries/vector/mariadb.mjs.map +1 -1
  262. package/batteries/vector/meilisearch/index.d.ts +2 -0
  263. package/batteries/vector/meilisearch.cjs +2 -1
  264. package/batteries/vector/meilisearch.cjs.map +1 -1
  265. package/batteries/vector/meilisearch.mjs +2 -1
  266. package/batteries/vector/meilisearch.mjs.map +1 -1
  267. package/batteries/vector/migrate.cjs +18 -1
  268. package/batteries/vector/migrate.cjs.map +1 -1
  269. package/batteries/vector/migrate.d.ts +31 -0
  270. package/batteries/vector/migrate.mjs +18 -1
  271. package/batteries/vector/migrate.mjs.map +1 -1
  272. package/batteries/vector/milvus/index.d.ts +5 -0
  273. package/batteries/vector/milvus.cjs +4 -0
  274. package/batteries/vector/milvus.cjs.map +1 -1
  275. package/batteries/vector/milvus.mjs +4 -0
  276. package/batteries/vector/milvus.mjs.map +1 -1
  277. package/batteries/vector/mongodb/index.d.ts +2 -0
  278. package/batteries/vector/mongodb.cjs +2 -1
  279. package/batteries/vector/mongodb.cjs.map +1 -1
  280. package/batteries/vector/mongodb.mjs +2 -1
  281. package/batteries/vector/mongodb.mjs.map +1 -1
  282. package/batteries/vector/neo4j/index.d.ts +2 -0
  283. package/batteries/vector/neo4j.cjs +2 -1
  284. package/batteries/vector/neo4j.cjs.map +1 -1
  285. package/batteries/vector/neo4j.mjs +2 -1
  286. package/batteries/vector/neo4j.mjs.map +1 -1
  287. package/batteries/vector/opensearch/index.d.ts +2 -0
  288. package/batteries/vector/opensearch.cjs +2 -1
  289. package/batteries/vector/opensearch.cjs.map +1 -1
  290. package/batteries/vector/opensearch.mjs +2 -1
  291. package/batteries/vector/opensearch.mjs.map +1 -1
  292. package/batteries/vector/oracle23ai/index.d.ts +2 -0
  293. package/batteries/vector/oracle23ai.cjs +2 -1
  294. package/batteries/vector/oracle23ai.cjs.map +1 -1
  295. package/batteries/vector/oracle23ai.mjs +2 -1
  296. package/batteries/vector/oracle23ai.mjs.map +1 -1
  297. package/batteries/vector/orama/index.d.ts +1 -0
  298. package/batteries/vector/orama.cjs +1 -0
  299. package/batteries/vector/orama.cjs.map +1 -1
  300. package/batteries/vector/orama.mjs +1 -0
  301. package/batteries/vector/orama.mjs.map +1 -1
  302. package/batteries/vector/pgvector/index.d.ts +9 -2
  303. package/batteries/vector/pgvector.cjs +4 -0
  304. package/batteries/vector/pgvector.cjs.map +1 -1
  305. package/batteries/vector/pgvector.mjs +4 -0
  306. package/batteries/vector/pgvector.mjs.map +1 -1
  307. package/batteries/vector/pinecone/index.d.ts +5 -0
  308. package/batteries/vector/pinecone.cjs +3 -1
  309. package/batteries/vector/pinecone.cjs.map +1 -1
  310. package/batteries/vector/pinecone.mjs +3 -1
  311. package/batteries/vector/pinecone.mjs.map +1 -1
  312. package/batteries/vector/plan.d.ts +27 -0
  313. package/batteries/vector/qdrant/index.d.ts +5 -0
  314. package/batteries/vector/qdrant.cjs +4 -0
  315. package/batteries/vector/qdrant.cjs.map +1 -1
  316. package/batteries/vector/qdrant.mjs +4 -0
  317. package/batteries/vector/qdrant.mjs.map +1 -1
  318. package/batteries/vector/redis/index.d.ts +2 -0
  319. package/batteries/vector/redis.cjs +2 -1
  320. package/batteries/vector/redis.cjs.map +1 -1
  321. package/batteries/vector/redis.mjs +2 -1
  322. package/batteries/vector/redis.mjs.map +1 -1
  323. package/batteries/vector/retrievable.cjs +9 -1
  324. package/batteries/vector/retrievable.cjs.map +1 -1
  325. package/batteries/vector/retrievable.mjs +9 -1
  326. package/batteries/vector/retrievable.mjs.map +1 -1
  327. package/batteries/vector/retrievable_glue.d.ts +21 -0
  328. package/batteries/vector/s3vectors/index.d.ts +2 -0
  329. package/batteries/vector/s3vectors.cjs +2 -1
  330. package/batteries/vector/s3vectors.cjs.map +1 -1
  331. package/batteries/vector/s3vectors.mjs +2 -1
  332. package/batteries/vector/s3vectors.mjs.map +1 -1
  333. package/batteries/vector/schema.cjs +28 -0
  334. package/batteries/vector/schema.cjs.map +1 -1
  335. package/batteries/vector/schema.d.ts +39 -0
  336. package/batteries/vector/schema.mjs +28 -0
  337. package/batteries/vector/schema.mjs.map +1 -1
  338. package/batteries/vector/solr/index.d.ts +2 -0
  339. package/batteries/vector/solr.cjs +2 -1
  340. package/batteries/vector/solr.cjs.map +1 -1
  341. package/batteries/vector/solr.mjs +2 -1
  342. package/batteries/vector/solr.mjs.map +1 -1
  343. package/batteries/vector/sqlite_vec/index.d.ts +6 -3
  344. package/batteries/vector/sqlite_vec.cjs +2 -0
  345. package/batteries/vector/sqlite_vec.cjs.map +1 -1
  346. package/batteries/vector/sqlite_vec.mjs +2 -0
  347. package/batteries/vector/sqlite_vec.mjs.map +1 -1
  348. package/batteries/vector/surrealdb/index.d.ts +2 -0
  349. package/batteries/vector/surrealdb.cjs +2 -1
  350. package/batteries/vector/surrealdb.cjs.map +1 -1
  351. package/batteries/vector/surrealdb.mjs +2 -1
  352. package/batteries/vector/surrealdb.mjs.map +1 -1
  353. package/batteries/vector/types.d.ts +27 -0
  354. package/batteries/vector/typesense/index.d.ts +2 -0
  355. package/batteries/vector/typesense.cjs +2 -1
  356. package/batteries/vector/typesense.cjs.map +1 -1
  357. package/batteries/vector/typesense.mjs +2 -1
  358. package/batteries/vector/typesense.mjs.map +1 -1
  359. package/batteries/vector/validation.cjs +14 -0
  360. package/batteries/vector/validation.cjs.map +1 -1
  361. package/batteries/vector/validation.d.ts +14 -0
  362. package/batteries/vector/validation.mjs +14 -0
  363. package/batteries/vector/validation.mjs.map +1 -1
  364. package/batteries/vector/vector_store_constructor.cjs +1 -1
  365. package/batteries/vector/vector_store_constructor.cjs.map +1 -1
  366. package/batteries/vector/vector_store_constructor.d.ts +1 -1
  367. package/batteries/vector/vector_store_constructor.mjs +1 -1
  368. package/batteries/vector/vector_store_constructor.mjs.map +1 -1
  369. package/batteries/vector/vespa/index.d.ts +2 -0
  370. package/batteries/vector/vespa.cjs +2 -1
  371. package/batteries/vector/vespa.cjs.map +1 -1
  372. package/batteries/vector/vespa.mjs +2 -1
  373. package/batteries/vector/vespa.mjs.map +1 -1
  374. package/batteries/vector/weaviate/index.d.ts +2 -0
  375. package/batteries/vector/weaviate.cjs +2 -1
  376. package/batteries/vector/weaviate.cjs.map +1 -1
  377. package/batteries/vector/weaviate.mjs +2 -1
  378. package/batteries/vector/weaviate.mjs.map +1 -1
  379. package/batteries.cjs +58 -28
  380. package/batteries.mjs +12 -5
  381. package/{common-BT0nfCi9.mjs → common-DYDUi99O.mjs} +9 -9
  382. package/common-DYDUi99O.mjs.map +1 -0
  383. package/{common-Cj8TaQ9U.js → common-DZl3ADJs.js} +9 -9
  384. package/common-DZl3ADJs.js.map +1 -0
  385. package/common.cjs +7 -7
  386. package/common.mjs +7 -7
  387. package/{dispatch_runner-DPcS7Y_M.mjs → dispatch_runner--ZhdDWRZ.mjs} +27 -5
  388. package/{dispatch_runner-DPcS7Y_M.mjs.map → dispatch_runner--ZhdDWRZ.mjs.map} +1 -1
  389. package/{dispatch_runner-BHBNupqp.js → dispatch_runner-nHDKkxye.js} +27 -5
  390. package/{dispatch_runner-BHBNupqp.js.map → dispatch_runner-nHDKkxye.js.map} +1 -1
  391. package/dispatch_runner.cjs +1 -1
  392. package/dispatch_runner.d.ts +1 -1
  393. package/dispatch_runner.mjs +1 -1
  394. package/eslint/rules/artifact_tool_forbids_artifact_constructor.cjs +1 -0
  395. package/eslint/rules/artifact_tool_forbids_artifact_constructor.cjs.map +1 -1
  396. package/eslint/rules/artifact_tool_forbids_artifact_constructor.d.ts +1 -0
  397. package/eslint/rules/artifact_tool_forbids_artifact_constructor.mjs +1 -0
  398. package/eslint/rules/artifact_tool_forbids_artifact_constructor.mjs.map +1 -1
  399. package/eslint/rules/no_model_in_tool_handler.cjs +1 -0
  400. package/eslint/rules/no_model_in_tool_handler.cjs.map +1 -1
  401. package/eslint/rules/no_model_in_tool_handler.d.ts +1 -0
  402. package/eslint/rules/no_model_in_tool_handler.mjs +1 -0
  403. package/eslint/rules/no_model_in_tool_handler.mjs.map +1 -1
  404. package/eslint/rules/require_validator_any_required.cjs +1 -0
  405. package/eslint/rules/require_validator_any_required.cjs.map +1 -1
  406. package/eslint/rules/require_validator_any_required.d.ts +1 -0
  407. package/eslint/rules/require_validator_any_required.mjs +1 -0
  408. package/eslint/rules/require_validator_any_required.mjs.map +1 -1
  409. package/eslint/rules/thought_payload_requires_replay_tag.cjs +1 -0
  410. package/eslint/rules/thought_payload_requires_replay_tag.cjs.map +1 -1
  411. package/eslint/rules/thought_payload_requires_replay_tag.d.ts +1 -0
  412. package/eslint/rules/thought_payload_requires_replay_tag.mjs +1 -0
  413. package/eslint/rules/thought_payload_requires_replay_tag.mjs.map +1 -1
  414. package/eslint/rules/token_encoding_requires_context_window.cjs +1 -0
  415. package/eslint/rules/token_encoding_requires_context_window.cjs.map +1 -1
  416. package/eslint/rules/token_encoding_requires_context_window.d.ts +1 -0
  417. package/eslint/rules/token_encoding_requires_context_window.mjs +1 -0
  418. package/eslint/rules/token_encoding_requires_context_window.mjs.map +1 -1
  419. package/eslint/rules.cjs +1 -1
  420. package/eslint/rules.mjs +1 -1
  421. package/eslint.cjs +2 -2
  422. package/eslint.mjs +2 -2
  423. package/{exceptions-BeWH2FwP.mjs → exceptions-BDhN0Xzr.mjs} +3 -2
  424. package/exceptions-BDhN0Xzr.mjs.map +1 -0
  425. package/{exceptions-CitH5wZI.js → exceptions-BRXrUKiW.js} +3 -2
  426. package/exceptions-BRXrUKiW.js.map +1 -0
  427. package/exceptions.cjs +2 -2
  428. package/exceptions.mjs +2 -2
  429. package/factories.cjs +1 -1
  430. package/factories.mjs +1 -1
  431. package/forge.cjs +4 -4
  432. package/forge.d.ts +1 -1
  433. package/forge.mjs +4 -4
  434. package/guards.cjs +9 -9
  435. package/guards.mjs +9 -9
  436. package/helpers-DSTFxTiC.js +497 -0
  437. package/helpers-DSTFxTiC.js.map +1 -0
  438. package/helpers-xhrQbMAG.mjs +306 -0
  439. package/helpers-xhrQbMAG.mjs.map +1 -0
  440. package/index.cjs +12 -12
  441. package/index.mjs +12 -12
  442. package/lib/classes/base_exception.d.ts +1 -0
  443. package/lib/classes/media.d.ts +10 -0
  444. package/lib/classes/retrievable.d.ts +1 -1
  445. package/lib/classes/spooled_json_artifact.d.ts +1 -1
  446. package/lib/classes/spooled_markdown_artifact.d.ts +1 -0
  447. package/lib/classes/tokenizable.d.ts +3 -0
  448. package/lib/classes/tool.d.ts +8 -0
  449. package/lib/classes/turn_gate.d.ts +6 -0
  450. package/lib/dispatch_runner.d.ts +4 -32
  451. package/lib/helpers/bignum.cjs +82 -0
  452. package/lib/helpers/bignum.cjs.map +1 -0
  453. package/lib/helpers/bignum.d.ts +52 -0
  454. package/lib/helpers/bignum.mjs +74 -0
  455. package/lib/helpers/bignum.mjs.map +1 -0
  456. package/lib/turn_runner.d.ts +1 -1
  457. package/lib/types/dispatch_runner.d.ts +83 -0
  458. package/lib/utils/exceptions.d.ts +1 -1
  459. package/lib/utils/retry.cjs.map +1 -1
  460. package/lib/utils/retry.d.ts +2 -0
  461. package/lib/utils/retry.mjs.map +1 -1
  462. package/mcp/adk-docs-corpus.json +1 -1
  463. package/package.json +259 -204
  464. package/{runtime-j92CNi5z.mjs → runtime-Bz5zA8wc.mjs} +2 -2
  465. package/{runtime-j92CNi5z.mjs.map → runtime-Bz5zA8wc.mjs.map} +1 -1
  466. package/{runtime-MFFcJrRv.js → runtime-DslE1aBw.js} +2 -2
  467. package/{runtime-MFFcJrRv.js.map → runtime-DslE1aBw.js.map} +1 -1
  468. package/scrapper-BHM1mCde.mjs +432 -0
  469. package/scrapper-BHM1mCde.mjs.map +1 -0
  470. package/scrapper-BeweWurk.js +462 -0
  471. package/scrapper-BeweWurk.js.map +1 -0
  472. package/searxng-BJFulNcK.mjs +247 -0
  473. package/searxng-BJFulNcK.mjs.map +1 -0
  474. package/searxng-B_D--V5q.js +265 -0
  475. package/searxng-B_D--V5q.js.map +1 -0
  476. package/skills/adk-assembly/SKILL.md +2 -2
  477. package/{spooled_artifact-CHoZgWwI.mjs → spooled_artifact-7eePq7JA.mjs} +5 -5
  478. package/{spooled_artifact-CHoZgWwI.mjs.map → spooled_artifact-7eePq7JA.mjs.map} +1 -1
  479. package/{spooled_artifact-BTq6Nzfy.js → spooled_artifact-DX8LLyUX.js} +5 -5
  480. package/{spooled_artifact-BTq6Nzfy.js.map → spooled_artifact-DX8LLyUX.js.map} +1 -1
  481. package/spooled_artifact.cjs +2 -2
  482. package/spooled_artifact.mjs +2 -2
  483. package/{spooled_markdown_artifact-CALSDxIx.js → spooled_markdown_artifact-ClX72lek.js} +4 -4
  484. package/spooled_markdown_artifact-ClX72lek.js.map +1 -0
  485. package/{spooled_markdown_artifact-Ci5UL7l4.mjs → spooled_markdown_artifact-wkrBF3oX.mjs} +4 -4
  486. package/spooled_markdown_artifact-wkrBF3oX.mjs.map +1 -0
  487. package/{thought-D34QQZZ9.mjs → thought-B_vxAiKU.mjs} +5 -5
  488. package/{thought-D34QQZZ9.mjs.map → thought-B_vxAiKU.mjs.map} +1 -1
  489. package/{thought-BbwhJ1wb.js → thought-DLwpF7MI.js} +5 -5
  490. package/{thought-BbwhJ1wb.js.map → thought-DLwpF7MI.js.map} +1 -1
  491. package/{tool-CVyZkFC7.js → tool-D5WGVIcI.js} +4 -4
  492. package/{tool-CVyZkFC7.js.map → tool-D5WGVIcI.js.map} +1 -1
  493. package/{tool-CMhaDRNd.mjs → tool-wMYMVl60.mjs} +4 -4
  494. package/{tool-CMhaDRNd.mjs.map → tool-wMYMVl60.mjs.map} +1 -1
  495. package/{tool_call-CV5qVNlb.mjs → tool_call-B4-_-vjG.mjs} +5 -5
  496. package/tool_call-B4-_-vjG.mjs.map +1 -0
  497. package/{tool_call-Db68hB7y.js → tool_call-DixVlW40.js} +5 -5
  498. package/tool_call-DixVlW40.js.map +1 -0
  499. package/{tool_registry-D1pSSlsd.mjs → tool_registry-791Vrjtf.mjs} +4 -3
  500. package/tool_registry-791Vrjtf.mjs.map +1 -0
  501. package/{tool_registry-DYUYqXvo.js → tool_registry-CKJPze3j.js} +4 -3
  502. package/tool_registry-CKJPze3j.js.map +1 -0
  503. package/{turn_runner-DqWHNP80.js → turn_runner-HXImLGIn.js} +7 -7
  504. package/turn_runner-HXImLGIn.js.map +1 -0
  505. package/{turn_runner-fg1Wc3dK.mjs → turn_runner-ZyYO-Kti.mjs} +7 -7
  506. package/turn_runner-ZyYO-Kti.mjs.map +1 -0
  507. package/turn_runner.cjs +1 -1
  508. package/turn_runner.mjs +1 -1
  509. package/types.d.ts +1 -1
  510. package/common-BT0nfCi9.mjs.map +0 -1
  511. package/common-Cj8TaQ9U.js.map +0 -1
  512. package/exceptions-BeWH2FwP.mjs.map +0 -1
  513. package/exceptions-CitH5wZI.js.map +0 -1
  514. package/spooled_markdown_artifact-CALSDxIx.js.map +0 -1
  515. package/spooled_markdown_artifact-Ci5UL7l4.mjs.map +0 -1
  516. package/tool_call-CV5qVNlb.mjs.map +0 -1
  517. package/tool_call-Db68hB7y.js.map +0 -1
  518. package/tool_registry-D1pSSlsd.mjs.map +0 -1
  519. package/tool_registry-DYUYqXvo.js.map +0 -1
  520. package/turn_runner-DqWHNP80.js.map +0 -1
  521. package/turn_runner-fg1Wc3dK.mjs.map +0 -1
@@ -1 +1 @@
1
- {"version":3,"file":"elasticsearch.mjs","names":["#opts","#client","#ensure","#dims","#body","#project"],"sources":["../../../src/batteries/vector/elasticsearch/index.ts"],"sourcesContent":["/**\n * @module @nhtio/adk/batteries/vector/elasticsearch\n *\n * Elasticsearch 8 adapter — each collection is an index with a `dense_vector` field; KNN uses ES8's\n * top-level `knn` search clause with an optional `filter`; the neutral filter tree compiles to bool/term/range\n * over `metadata.*`. Distinct from the opensearch adapter (which speaks OpenSearch's `knn_vector`/`query.knn` dialect).\n */\n\nimport { normalizeScore } from '../helpers'\nimport { BaseVectorStore } from '../contract'\nimport { validateRecords } from '../validation'\nimport { isInstanceOf } from '@nhtio/adk/guards'\nimport { isFilterCondition, isRawFilter, isFilterGroup } from '../filters'\nimport {\n E_VECTOR_STORE_DRIVER_UNAVAILABLE,\n E_VECTOR_STORE_CONNECTION_FAILED,\n E_VECTOR_STORE_COLLECTION_FAILED,\n E_VECTOR_STORE_UPSERT_FAILED,\n E_VECTOR_STORE_SEARCH_FAILED,\n E_VECTOR_STORE_DELETE_FAILED,\n E_VECTOR_STORE_DIMENSION_MISMATCH,\n E_VECTOR_STORE_UNSUPPORTED_OPERATION,\n E_VECTOR_STORE_UNSUPPORTED_FILTER_OPERATOR,\n} from '../exceptions'\nimport type { VectorFilter } from '../filters'\nimport type { SearchPlan, UpsertPlan, DeletePlan, CollectionSpec } from '../plan'\nimport type {\n VectorMatch,\n VectorStoreCapabilities,\n BaseVectorStoreOptions,\n VectorMetadata,\n DistanceMetric,\n} from '../types'\n\nexport interface ElasticsearchVectorStoreOptions extends BaseVectorStoreOptions {\n connection?: {\n node?: string // default 'http://localhost:9200'\n auth?: { username: string; password: string } | { apiKey: string }\n client?: unknown // BYO @elastic/elasticsearch Client; overrides node\n }\n}\n\nconst getElasticsearchClient = async () => {\n try {\n const mod = await import('@elastic/elasticsearch')\n return mod.Client\n } catch {\n throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE(['@elastic/elasticsearch'])\n }\n}\n\n// Elasticsearch similarity per metric.\nconst similarity = (metric: DistanceMetric): string =>\n metric === 'cosine' ? 'cosine' : metric === 'dot' ? 'dot_product' : 'l2_norm'\n\n/**\n * Compile the neutral filter tree to an Elasticsearch bool-query clause over `metadata.*`.\n * String values use the `.keyword` sub-field for exact match; numbers use range/term.\n */\nexport const translateElasticsearchFilter = (\n filter?: VectorFilter\n): Record<string, unknown> | undefined => {\n if (!filter) return undefined\n if (isRawFilter(filter)) {\n if (filter.$dialect === 'elasticsearch' || filter.$dialect === 'opensearch') {\n return filter.$raw as Record<string, unknown>\n }\n throw new E_VECTOR_STORE_UNSUPPORTED_FILTER_OPERATOR(['elasticsearch', String(filter.$dialect)])\n }\n if (isFilterCondition(filter)) {\n const { field, op, value } = filter\n const f = `metadata.${field}`\n const kw = `metadata.${field}.keyword`\n const term = (v: unknown) =>\n typeof v === 'number' || typeof v === 'boolean' ? { term: { [f]: v } } : { term: { [kw]: v } }\n switch (op) {\n case 'eq':\n return term(value)\n case 'ne':\n return { bool: { must_not: [term(value)] } }\n case 'gt':\n return { range: { [f]: { gt: value } } }\n case 'gte':\n return { range: { [f]: { gte: value } } }\n case 'lt':\n return { range: { [f]: { lt: value } } }\n case 'lte':\n return { range: { [f]: { lte: value } } }\n case 'in': {\n const arr = Array.isArray(value) ? value : [value]\n const allNum = arr.every((v) => typeof v === 'number' || typeof v === 'boolean')\n return { terms: { [allNum ? f : kw]: arr } }\n }\n case 'nin': {\n const arr = Array.isArray(value) ? value : [value]\n const allNum = arr.every((v) => typeof v === 'number' || typeof v === 'boolean')\n return { bool: { must_not: [{ terms: { [allNum ? f : kw]: arr } }] } }\n }\n case 'exists':\n return { exists: { field: f } }\n default:\n throw new E_VECTOR_STORE_UNSUPPORTED_FILTER_OPERATOR(['elasticsearch', op])\n }\n }\n if (isFilterGroup(filter)) {\n const { and, or, not } = filter\n if (and) {\n const must = and.map(translateElasticsearchFilter).filter(Boolean)\n return { bool: { must } }\n }\n if (or) {\n const should = or.map(translateElasticsearchFilter).filter(Boolean)\n return { bool: { should, minimum_should_match: 1 } }\n }\n if (not) {\n const inner = translateElasticsearchFilter(not)\n return inner ? { bool: { must_not: [inner] } } : undefined\n }\n }\n return undefined\n}\n\nexport class ElasticsearchVectorStore extends BaseVectorStore {\n readonly capabilities: VectorStoreCapabilities = {\n transactions: false,\n namedVectors: false,\n rename: false,\n rawSql: false,\n builtInEncoding: false,\n // Made strongly consistent by refreshing the index after every write (refresh: true /\n // explicit _refresh), so a write is visible to the next search. The option is a no-op.\n consistency: { configurable: false, default: 'strong', modes: ['strong'] },\n }\n\n #client: any | null = null\n #dims: Map<string, number> = new Map()\n\n get #opts(): ElasticsearchVectorStoreOptions {\n return this.options as ElasticsearchVectorStoreOptions\n }\n\n static isAvailable(): boolean {\n return typeof process !== 'undefined'\n }\n isAvailable(): boolean {\n return typeof process !== 'undefined'\n }\n\n async connect(): Promise<void> {\n if (this.#client) return\n const c = this.#opts.connection || {}\n if (c.client) {\n this.#client = c.client\n return\n }\n const Client = await getElasticsearchClient()\n try {\n this.#client = new Client({ node: c.node ?? 'http://localhost:9200', auth: c.auth })\n } catch (err) {\n throw new E_VECTOR_STORE_CONNECTION_FAILED([String(err)])\n }\n }\n\n async close(): Promise<void> {\n if (\n this.#client &&\n typeof this.#client.close === 'function' &&\n !this.#opts.connection?.client\n ) {\n await this.#client.close()\n }\n this.#client = null\n }\n\n async #ensure(): Promise<any> {\n if (!this.#client) await this.connect()\n return this.#client!\n }\n\n // Unwrap the {body}/direct response shape across client versions.\n #body(res: any): any {\n return res && res.body !== undefined ? res.body : res\n }\n\n async createCollection(spec: CollectionSpec, ifNotExists: boolean): Promise<void> {\n const client = await this.#ensure()\n this.#dims.set(spec.collection, spec.vector.dimensions)\n if (ifNotExists && (await this.hasCollection(spec.collection))) return\n try {\n await client.indices.create({\n index: spec.collection,\n mappings: {\n properties: {\n vec: {\n type: 'dense_vector',\n dims: spec.vector.dimensions,\n index: true,\n similarity: similarity(spec.vector.metric),\n },\n document: { type: 'text' },\n metadata: { type: 'object', enabled: true },\n },\n },\n })\n } catch (err) {\n throw new E_VECTOR_STORE_COLLECTION_FAILED(['createCollection', String(err)])\n }\n }\n\n async dropCollection(collection: string, ifExists: boolean): Promise<void> {\n const client = await this.#ensure()\n if (ifExists && !(await this.hasCollection(collection))) return\n try {\n await client.indices.delete({ index: collection })\n this.#dims.delete(collection)\n } catch (err) {\n const msg = String(err)\n if (ifExists && msg.includes('index_not_found')) return\n throw new E_VECTOR_STORE_COLLECTION_FAILED(['dropCollection', msg])\n }\n }\n\n async hasCollection(collection: string): Promise<boolean> {\n const client = await this.#ensure()\n try {\n const res = await client.indices.exists({ index: collection })\n const body = this.#body(res)\n return body === true || body === 200 || res?.statusCode === 200\n } catch {\n return false\n }\n }\n\n async renameCollection(_from: string, _to: string): Promise<void> {\n throw new E_VECTOR_STORE_UNSUPPORTED_OPERATION(['renameCollection', 'elasticsearch'])\n }\n\n async executeUpsert(plan: UpsertPlan): Promise<void> {\n if (plan.records.length === 0) return\n validateRecords(plan.records)\n const client = await this.#ensure()\n const expected = this.#opts.dimensions ?? this.#dims.get(plan.collection)\n try {\n const operations: any[] = []\n for (const r of plan.records) {\n let vector = r.vector\n if (!vector && r.document) {\n const [v] = await this.encode([r.document], 'document')\n vector = v\n }\n if (!vector) {\n throw new E_VECTOR_STORE_UPSERT_FAILED(['Record missing vector and document'])\n }\n if (expected !== undefined && vector.length !== expected) {\n throw new E_VECTOR_STORE_DIMENSION_MISMATCH([expected, vector.length])\n }\n operations.push({ index: { _index: plan.collection, _id: r.id } })\n operations.push({ vec: vector, document: r.document ?? '', metadata: r.metadata ?? {} })\n }\n await client.bulk({ operations, refresh: true })\n } catch (err) {\n if (\n isInstanceOf(err, 'E_VECTOR_STORE_DIMENSION_MISMATCH', E_VECTOR_STORE_DIMENSION_MISMATCH) ||\n isInstanceOf(err, 'E_VECTOR_STORE_UPSERT_FAILED', E_VECTOR_STORE_UPSERT_FAILED)\n ) {\n throw err\n }\n throw new E_VECTOR_STORE_UPSERT_FAILED([String(err)])\n }\n }\n\n async executeSearch(plan: SearchPlan): Promise<VectorMatch[]> {\n const client = await this.#ensure()\n const metric = this.#opts.metric ?? 'cosine'\n let queryVector: number[] | undefined\n if (plan.near) {\n if ('vector' in plan.near) {\n queryVector = plan.near.vector\n } else if ('serverText' in plan.near) {\n const [v] = await this.encode([plan.near.serverText], 'query')\n queryVector = v\n } else if ('id' in plan.near) {\n try {\n const res = await client.get({ index: plan.collection, id: plan.near.id })\n queryVector = this.#body(res)?._source?.vec as number[]\n } catch {\n queryVector = undefined\n }\n if (!queryVector) {\n throw new E_VECTOR_STORE_SEARCH_FAILED(['Referenced id not found: ' + plan.near.id])\n }\n }\n }\n\n const filter = translateElasticsearchFilter(plan.filter)\n const size = plan.topK\n const from = plan.offset ?? 0\n try {\n let res: any\n if (queryVector) {\n const knn: any = {\n field: 'vec',\n query_vector: queryVector,\n k: size + from,\n num_candidates: Math.max((size + from) * 10, 100),\n }\n if (filter) knn.filter = filter\n res = await client.search({ index: plan.collection, knn, size, from, _source: true })\n } else {\n res = await client.search({\n index: plan.collection,\n size,\n from,\n query: filter ?? { match_all: {} },\n })\n }\n const hits = this.#body(res)?.hits?.hits ?? []\n return hits.map((hit: any) => this.#project(hit, plan, metric, !!queryVector))\n } catch (err) {\n throw new E_VECTOR_STORE_SEARCH_FAILED([String(err)])\n }\n }\n\n #project(hit: any, plan: SearchPlan, metric: string, isKnn: boolean): VectorMatch {\n const proj = plan.projection\n const src = hit._source ?? {}\n const out: VectorMatch = {}\n if (proj.id) out.id = hit._id as string\n if (proj.vector && src.vec) out.vector = src.vec as number[]\n if (proj.document) out.document = src.document as string | undefined\n if (proj.metadata) out.metadata = (src.metadata ?? {}) as VectorMetadata\n if (isKnn && typeof hit._score === 'number') {\n // Elasticsearch cosine _score is already (sim+1)/2 ∈ [0,1]; normalize defensively to [0,1].\n out.score = normalizeScore(hit._score, metric as DistanceMetric, 'similarity')\n }\n return out\n }\n\n async executeDelete(plan: DeletePlan): Promise<void> {\n const client = await this.#ensure()\n try {\n if (plan.ids && plan.ids.length > 0) {\n const operations = plan.ids.map((id) => ({ delete: { _index: plan.collection, _id: id } }))\n await client.bulk({ operations, refresh: true })\n } else if (plan.filter) {\n const filter = translateElasticsearchFilter(plan.filter)\n await client.deleteByQuery({\n index: plan.collection,\n refresh: true,\n query: filter ?? { match_all: {} },\n })\n } else {\n await client.deleteByQuery({\n index: plan.collection,\n refresh: true,\n query: { match_all: {} },\n })\n }\n } catch (err) {\n throw new E_VECTOR_STORE_DELETE_FAILED([String(err)])\n }\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"elasticsearch.mjs","names":["#opts","#client","#ensure","#dims","#body","#project"],"sources":["../../../src/batteries/vector/elasticsearch/index.ts"],"sourcesContent":["/**\n * @module @nhtio/adk/batteries/vector/elasticsearch\n *\n * Elasticsearch 8 adapter — each collection is an index with a `dense_vector` field; KNN uses ES8's\n * top-level `knn` search clause with an optional `filter`; the neutral filter tree compiles to bool/term/range\n * over `metadata.*`. Distinct from the opensearch adapter (which speaks OpenSearch's `knn_vector`/`query.knn` dialect).\n */\n\nimport { normalizeScore } from '../helpers'\nimport { BaseVectorStore } from '../contract'\nimport { validateRecords } from '../validation'\nimport { isInstanceOf } from '@nhtio/adk/guards'\nimport { isFilterCondition, isRawFilter, isFilterGroup } from '../filters'\nimport {\n E_VECTOR_STORE_DRIVER_UNAVAILABLE,\n E_VECTOR_STORE_CONNECTION_FAILED,\n E_VECTOR_STORE_COLLECTION_FAILED,\n E_VECTOR_STORE_UPSERT_FAILED,\n E_VECTOR_STORE_SEARCH_FAILED,\n E_VECTOR_STORE_DELETE_FAILED,\n E_VECTOR_STORE_DIMENSION_MISMATCH,\n E_VECTOR_STORE_UNSUPPORTED_OPERATION,\n E_VECTOR_STORE_UNSUPPORTED_FILTER_OPERATOR,\n} from '../exceptions'\nimport type { VectorFilter } from '../filters'\nimport type { SearchPlan, UpsertPlan, DeletePlan, CollectionSpec } from '../plan'\nimport type {\n VectorMatch,\n VectorStoreCapabilities,\n BaseVectorStoreOptions,\n VectorMetadata,\n DistanceMetric,\n} from '../types'\n\nexport interface ElasticsearchVectorStoreOptions extends BaseVectorStoreOptions {\n /** Connection and authentication parameters for the backend. */\n connection?: {\n node?: string // default 'http://localhost:9200'\n auth?: { username: string; password: string } | { apiKey: string }\n client?: unknown // BYO @elastic/elasticsearch Client; overrides node\n }\n}\n\nconst getElasticsearchClient = async () => {\n try {\n const mod = await import('@elastic/elasticsearch')\n return mod.Client\n } catch {\n throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE(['@elastic/elasticsearch'])\n }\n}\n\n// Elasticsearch similarity per metric.\nconst similarity = (metric: DistanceMetric): string =>\n metric === 'cosine' ? 'cosine' : metric === 'dot' ? 'dot_product' : 'l2_norm'\n\n/**\n * Compile the neutral filter tree to an Elasticsearch bool-query clause over `metadata.*`.\n * String values use the `.keyword` sub-field for exact match; numbers use range/term.\n */\nexport const translateElasticsearchFilter = (\n filter?: VectorFilter\n): Record<string, unknown> | undefined => {\n if (!filter) return undefined\n if (isRawFilter(filter)) {\n if (filter.$dialect === 'elasticsearch' || filter.$dialect === 'opensearch') {\n return filter.$raw as Record<string, unknown>\n }\n throw new E_VECTOR_STORE_UNSUPPORTED_FILTER_OPERATOR(['elasticsearch', String(filter.$dialect)])\n }\n if (isFilterCondition(filter)) {\n const { field, op, value } = filter\n const f = `metadata.${field}`\n const kw = `metadata.${field}.keyword`\n const term = (v: unknown) =>\n typeof v === 'number' || typeof v === 'boolean' ? { term: { [f]: v } } : { term: { [kw]: v } }\n switch (op) {\n case 'eq':\n return term(value)\n case 'ne':\n return { bool: { must_not: [term(value)] } }\n case 'gt':\n return { range: { [f]: { gt: value } } }\n case 'gte':\n return { range: { [f]: { gte: value } } }\n case 'lt':\n return { range: { [f]: { lt: value } } }\n case 'lte':\n return { range: { [f]: { lte: value } } }\n case 'in': {\n const arr = Array.isArray(value) ? value : [value]\n const allNum = arr.every((v) => typeof v === 'number' || typeof v === 'boolean')\n return { terms: { [allNum ? f : kw]: arr } }\n }\n case 'nin': {\n const arr = Array.isArray(value) ? value : [value]\n const allNum = arr.every((v) => typeof v === 'number' || typeof v === 'boolean')\n return { bool: { must_not: [{ terms: { [allNum ? f : kw]: arr } }] } }\n }\n case 'exists':\n return { exists: { field: f } }\n default:\n throw new E_VECTOR_STORE_UNSUPPORTED_FILTER_OPERATOR(['elasticsearch', op])\n }\n }\n if (isFilterGroup(filter)) {\n const { and, or, not } = filter\n if (and) {\n const must = and.map(translateElasticsearchFilter).filter(Boolean)\n return { bool: { must } }\n }\n if (or) {\n const should = or.map(translateElasticsearchFilter).filter(Boolean)\n return { bool: { should, minimum_should_match: 1 } }\n }\n if (not) {\n const inner = translateElasticsearchFilter(not)\n return inner ? { bool: { must_not: [inner] } } : undefined\n }\n }\n return undefined\n}\n\nexport class ElasticsearchVectorStore extends BaseVectorStore {\n readonly capabilities: VectorStoreCapabilities = {\n transactions: false,\n namedVectors: false,\n rename: false,\n rawSql: false,\n builtInEncoding: false,\n // Made strongly consistent by refreshing the index after every write (refresh: true /\n // explicit _refresh), so a write is visible to the next search. The option is a no-op.\n consistency: { configurable: false, default: 'strong', modes: ['strong'] },\n }\n\n #client: any | null = null\n #dims: Map<string, number> = new Map()\n\n get #opts(): ElasticsearchVectorStoreOptions {\n return this.options as ElasticsearchVectorStoreOptions\n }\n\n /** Static availability probe: whether this adapter's runtime driver can load in the current environment. */\n static isAvailable(): boolean {\n return typeof process !== 'undefined'\n }\n isAvailable(): boolean {\n return typeof process !== 'undefined'\n }\n\n async connect(): Promise<void> {\n if (this.#client) return\n const c = this.#opts.connection || {}\n if (c.client) {\n this.#client = c.client\n return\n }\n const Client = await getElasticsearchClient()\n try {\n this.#client = new Client({ node: c.node ?? 'http://localhost:9200', auth: c.auth })\n } catch (err) {\n throw new E_VECTOR_STORE_CONNECTION_FAILED([String(err)])\n }\n }\n\n async close(): Promise<void> {\n if (\n this.#client &&\n typeof this.#client.close === 'function' &&\n !this.#opts.connection?.client\n ) {\n await this.#client.close()\n }\n this.#client = null\n }\n\n async #ensure(): Promise<any> {\n if (!this.#client) await this.connect()\n return this.#client!\n }\n\n // Unwrap the {body}/direct response shape across client versions.\n #body(res: any): any {\n return res && res.body !== undefined ? res.body : res\n }\n\n async createCollection(spec: CollectionSpec, ifNotExists: boolean): Promise<void> {\n const client = await this.#ensure()\n this.#dims.set(spec.collection, spec.vector.dimensions)\n if (ifNotExists && (await this.hasCollection(spec.collection))) return\n try {\n await client.indices.create({\n index: spec.collection,\n mappings: {\n properties: {\n vec: {\n type: 'dense_vector',\n dims: spec.vector.dimensions,\n index: true,\n similarity: similarity(spec.vector.metric),\n },\n document: { type: 'text' },\n metadata: { type: 'object', enabled: true },\n },\n },\n })\n } catch (err) {\n throw new E_VECTOR_STORE_COLLECTION_FAILED(['createCollection', String(err)])\n }\n }\n\n async dropCollection(collection: string, ifExists: boolean): Promise<void> {\n const client = await this.#ensure()\n if (ifExists && !(await this.hasCollection(collection))) return\n try {\n await client.indices.delete({ index: collection })\n this.#dims.delete(collection)\n } catch (err) {\n const msg = String(err)\n if (ifExists && msg.includes('index_not_found')) return\n throw new E_VECTOR_STORE_COLLECTION_FAILED(['dropCollection', msg])\n }\n }\n\n async hasCollection(collection: string): Promise<boolean> {\n const client = await this.#ensure()\n try {\n const res = await client.indices.exists({ index: collection })\n const body = this.#body(res)\n return body === true || body === 200 || res?.statusCode === 200\n } catch {\n return false\n }\n }\n\n async renameCollection(_from: string, _to: string): Promise<void> {\n throw new E_VECTOR_STORE_UNSUPPORTED_OPERATION(['renameCollection', 'elasticsearch'])\n }\n\n async executeUpsert(plan: UpsertPlan): Promise<void> {\n if (plan.records.length === 0) return\n validateRecords(plan.records)\n const client = await this.#ensure()\n const expected = this.#opts.dimensions ?? this.#dims.get(plan.collection)\n try {\n const operations: any[] = []\n for (const r of plan.records) {\n let vector = r.vector\n if (!vector && r.document) {\n const [v] = await this.encode([r.document], 'document')\n vector = v\n }\n if (!vector) {\n throw new E_VECTOR_STORE_UPSERT_FAILED(['Record missing vector and document'])\n }\n if (expected !== undefined && vector.length !== expected) {\n throw new E_VECTOR_STORE_DIMENSION_MISMATCH([expected, vector.length])\n }\n operations.push({ index: { _index: plan.collection, _id: r.id } })\n operations.push({ vec: vector, document: r.document ?? '', metadata: r.metadata ?? {} })\n }\n await client.bulk({ operations, refresh: true })\n } catch (err) {\n if (\n isInstanceOf(err, 'E_VECTOR_STORE_DIMENSION_MISMATCH', E_VECTOR_STORE_DIMENSION_MISMATCH) ||\n isInstanceOf(err, 'E_VECTOR_STORE_UPSERT_FAILED', E_VECTOR_STORE_UPSERT_FAILED)\n ) {\n throw err\n }\n throw new E_VECTOR_STORE_UPSERT_FAILED([String(err)])\n }\n }\n\n async executeSearch(plan: SearchPlan): Promise<VectorMatch[]> {\n const client = await this.#ensure()\n const metric = this.#opts.metric ?? 'cosine'\n let queryVector: number[] | undefined\n if (plan.near) {\n if ('vector' in plan.near) {\n queryVector = plan.near.vector\n } else if ('serverText' in plan.near) {\n const [v] = await this.encode([plan.near.serverText], 'query')\n queryVector = v\n } else if ('id' in plan.near) {\n try {\n const res = await client.get({ index: plan.collection, id: plan.near.id })\n queryVector = this.#body(res)?._source?.vec as number[]\n } catch {\n queryVector = undefined\n }\n if (!queryVector) {\n throw new E_VECTOR_STORE_SEARCH_FAILED(['Referenced id not found: ' + plan.near.id])\n }\n }\n }\n\n const filter = translateElasticsearchFilter(plan.filter)\n const size = plan.topK\n const from = plan.offset ?? 0\n try {\n let res: any\n if (queryVector) {\n const knn: any = {\n field: 'vec',\n query_vector: queryVector,\n k: size + from,\n num_candidates: Math.max((size + from) * 10, 100),\n }\n if (filter) knn.filter = filter\n res = await client.search({ index: plan.collection, knn, size, from, _source: true })\n } else {\n res = await client.search({\n index: plan.collection,\n size,\n from,\n query: filter ?? { match_all: {} },\n })\n }\n const hits = this.#body(res)?.hits?.hits ?? []\n return hits.map((hit: any) => this.#project(hit, plan, metric, !!queryVector))\n } catch (err) {\n throw new E_VECTOR_STORE_SEARCH_FAILED([String(err)])\n }\n }\n\n #project(hit: any, plan: SearchPlan, metric: string, isKnn: boolean): VectorMatch {\n const proj = plan.projection\n const src = hit._source ?? {}\n const out: VectorMatch = {}\n if (proj.id) out.id = hit._id as string\n if (proj.vector && src.vec) out.vector = src.vec as number[]\n if (proj.document) out.document = src.document as string | undefined\n if (proj.metadata) out.metadata = (src.metadata ?? {}) as VectorMetadata\n if (isKnn && typeof hit._score === 'number') {\n // Elasticsearch cosine _score is already (sim+1)/2 ∈ [0,1]; normalize defensively to [0,1].\n out.score = normalizeScore(hit._score, metric as DistanceMetric, 'similarity')\n }\n return out\n }\n\n async executeDelete(plan: DeletePlan): Promise<void> {\n const client = await this.#ensure()\n try {\n if (plan.ids && plan.ids.length > 0) {\n const operations = plan.ids.map((id) => ({ delete: { _index: plan.collection, _id: id } }))\n await client.bulk({ operations, refresh: true })\n } else if (plan.filter) {\n const filter = translateElasticsearchFilter(plan.filter)\n await client.deleteByQuery({\n index: plan.collection,\n refresh: true,\n query: filter ?? { match_all: {} },\n })\n } else {\n await client.deleteByQuery({\n index: plan.collection,\n refresh: true,\n query: { match_all: {} },\n })\n }\n } catch (err) {\n throw new E_VECTOR_STORE_DELETE_FAILED([String(err)])\n }\n }\n}\n"],"mappings":"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"}
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  require("../../chunk-Ble4zEEl.js");
3
- const require_exceptions = require("../../exceptions-CitH5wZI.js");
3
+ const require_exceptions = require("../../exceptions-BRXrUKiW.js");
4
4
  require("../../factories.cjs");
5
5
  //#region src/batteries/vector/exceptions.ts
6
6
  /**
@@ -1,4 +1,4 @@
1
- import { t as createException } from "../../exceptions-BeWH2FwP.mjs";
1
+ import { t as createException } from "../../exceptions-BDhN0Xzr.mjs";
2
2
  import "../../factories.mjs";
3
3
  //#region src/batteries/vector/exceptions.ts
4
4
  /**
@@ -18,6 +18,12 @@ var createVectorStore = async (config) => {
18
18
  if (typeof Ctor.isAvailable === "function" && !Ctor.isAvailable()) throw new require_batteries_vector_exceptions.E_VECTOR_STORE_DRIVER_UNAVAILABLE([Ctor.name || "unknown"]);
19
19
  return new Ctor(config.options).asCallable();
20
20
  };
21
+ /**
22
+ * Adapt an {@link EmbeddingsLike} object into a {@link VectorEncoderFn} for use as a store encoder.
23
+ *
24
+ * @param adapter - The embeddings adapter to wrap.
25
+ * @returns An encoder function forwarding to `adapter.embedMany`.
26
+ */
21
27
  var encoderFromEmbeddings = (adapter) => {
22
28
  return (texts, kind) => adapter.embedMany(texts, { kind });
23
29
  };
@@ -1 +1 @@
1
- {"version":3,"file":"factory.cjs","names":[],"sources":["../../../src/batteries/vector/factory.ts"],"sourcesContent":["/**\n * @module @nhtio/adk/batteries/vector/factory\n */\n\nimport { E_VECTOR_STORE_DRIVER_UNAVAILABLE } from './exceptions'\nimport { validateCreateConfig, resolveClientCtor } from './validation'\nimport type { CallableVectorStore, BaseVectorStore } from './contract'\nimport type { BaseVectorStoreOptions, VectorEncoderFn, EncodeKind } from './types'\n\n// The adapter class shape the factory accepts as 'client'.\nexport interface VectorStoreConstructor<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> {\n new (options: O): BaseVectorStore\n isAvailable?: () => boolean\n}\n\n/**\n * `client` is one of:\n * - the adapter class itself — `QdrantVectorStore`\n * - a sync resolver — `() => QdrantVectorStore`\n * - an async resolver / dynamic import — `() => import('…/qdrant').then(m => m.QdrantVectorStore)`\n * A resolver may also return a module namespace whose `default` is the class.\n */\nexport type VectorStoreClient<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> =\n | VectorStoreConstructor<O>\n | (() => VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> })\n | (() => Promise<VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> }>)\n\nexport interface CreateVectorStoreConfig<\n O extends BaseVectorStoreOptions = BaseVectorStoreOptions,\n> {\n client: VectorStoreClient<O>\n options: O\n}\n\n/**\n * Build a callable store. Validate config; resolve the `client` (class | sync resolver | async\n * resolver) to a BaseVectorStore subclass ctor; optional availability gate; construct; return\n * asCallable(). Async so that `client: () => import('…')` can lazily load the adapter (and its\n * driver) only when the store is actually created.\n */\nexport const createVectorStore = async <O extends BaseVectorStoreOptions = BaseVectorStoreOptions>(\n config: CreateVectorStoreConfig<O>\n): Promise<CallableVectorStore> => {\n validateCreateConfig(config)\n const Ctor = (await resolveClientCtor(config.client)) as VectorStoreConstructor<O>\n if (typeof Ctor.isAvailable === 'function' && !Ctor.isAvailable()) {\n throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE([Ctor.name || 'unknown'])\n }\n const instance = new Ctor(config.options)\n return instance.asCallable() as CallableVectorStore\n}\n\n// Helper: adapt an embeddings-battery-shaped object (has embedMany(texts, { kind })) into a VectorEncoderFn.\n// The embeddings adapters expose: embedMany(texts: string[], opts?: { kind?: 'query'|'document' }): Promise<number[][]>\nexport interface EmbeddingsLike {\n embedMany(texts: string[], opts?: { kind?: EncodeKind }): Promise<number[][]>\n}\nexport const encoderFromEmbeddings = (adapter: EmbeddingsLike): VectorEncoderFn => {\n return (texts: string[], kind: EncodeKind) => adapter.embedMany(texts, { kind })\n}\n"],"mappings":";;;;;;;;;;;;;;AAwCA,IAAa,oBAAoB,OAC/B,WACiC;CACjC,oCAAA,qBAAqB,MAAM;CAC3B,MAAM,OAAQ,MAAM,oCAAA,kBAAkB,OAAO,MAAM;CACnD,IAAI,OAAO,KAAK,gBAAgB,cAAc,CAAC,KAAK,YAAY,GAC9D,MAAM,IAAI,oCAAA,kCAAkC,CAAC,KAAK,QAAQ,SAAS,CAAC;CAGtE,OAAO,IADc,KAAK,OAAO,OAC1B,EAAS,WAAW;AAC7B;AAOA,IAAa,yBAAyB,YAA6C;CACjF,QAAQ,OAAiB,SAAqB,QAAQ,UAAU,OAAO,EAAE,KAAK,CAAC;AACjF"}
1
+ {"version":3,"file":"factory.cjs","names":[],"sources":["../../../src/batteries/vector/factory.ts"],"sourcesContent":["/**\n * @module @nhtio/adk/batteries/vector/factory\n */\n\nimport { E_VECTOR_STORE_DRIVER_UNAVAILABLE } from './exceptions'\nimport { validateCreateConfig, resolveClientCtor } from './validation'\nimport type { CallableVectorStore, BaseVectorStore } from './contract'\nimport type { BaseVectorStoreOptions, VectorEncoderFn, EncodeKind } from './types'\n\n/** The adapter class shape the factory accepts as `client` — a constructor with an optional availability probe. */\nexport interface VectorStoreConstructor<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> {\n /** Construct the adapter from its options. */\n new (options: O): BaseVectorStore\n /** Optional static probe: `false` short-circuits creation with a driver-unavailable error. */\n isAvailable?: () => boolean\n}\n\n/**\n * `client` is one of:\n * - the adapter class itself — `QdrantVectorStore`\n * - a sync resolver — `() => QdrantVectorStore`\n * - an async resolver / dynamic import — `() => import('…/qdrant').then(m => m.QdrantVectorStore)`\n * A resolver may also return a module namespace whose `default` is the class.\n */\nexport type VectorStoreClient<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> =\n | VectorStoreConstructor<O>\n | (() => VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> })\n | (() => Promise<VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> }>)\n\n/** Configuration accepted by {@link createVectorStore}: the adapter `client` plus its `options`. */\nexport interface CreateVectorStoreConfig<\n O extends BaseVectorStoreOptions = BaseVectorStoreOptions,\n> {\n /** The adapter class, or a (possibly async) resolver of it. See {@link VectorStoreClient}. */\n client: VectorStoreClient<O>\n /** Options passed to the resolved adapter's constructor. */\n options: O\n}\n\n/**\n * Build a callable store. Validate config; resolve the `client` (class | sync resolver | async\n * resolver) to a BaseVectorStore subclass ctor; optional availability gate; construct; return\n * asCallable(). Async so that `client: () => import('…')` can lazily load the adapter (and its\n * driver) only when the store is actually created.\n */\nexport const createVectorStore = async <O extends BaseVectorStoreOptions = BaseVectorStoreOptions>(\n config: CreateVectorStoreConfig<O>\n): Promise<CallableVectorStore> => {\n validateCreateConfig(config)\n const Ctor = (await resolveClientCtor(config.client)) as VectorStoreConstructor<O>\n if (typeof Ctor.isAvailable === 'function' && !Ctor.isAvailable()) {\n throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE([Ctor.name || 'unknown'])\n }\n const instance = new Ctor(config.options)\n return instance.asCallable() as CallableVectorStore\n}\n\n// Helper: adapt an embeddings-battery-shaped object (has embedMany(texts, { kind })) into a VectorEncoderFn.\n// The embeddings adapters expose: embedMany(texts: string[], opts?: { kind?: 'query'|'document' }): Promise<number[][]>\n/** The minimal shape of an embeddings-battery adapter usable as a vector encoder. */\nexport interface EmbeddingsLike {\n /** Embed a batch of texts, optionally hinting query vs. document encoding. */\n embedMany(texts: string[], opts?: { kind?: EncodeKind }): Promise<number[][]>\n}\n/**\n * Adapt an {@link EmbeddingsLike} object into a {@link VectorEncoderFn} for use as a store encoder.\n *\n * @param adapter - The embeddings adapter to wrap.\n * @returns An encoder function forwarding to `adapter.embedMany`.\n */\nexport const encoderFromEmbeddings = (adapter: EmbeddingsLike): VectorEncoderFn => {\n return (texts: string[], kind: EncodeKind) => adapter.embedMany(texts, { kind })\n}\n"],"mappings":";;;;;;;;;;;;;;AA6CA,IAAa,oBAAoB,OAC/B,WACiC;CACjC,oCAAA,qBAAqB,MAAM;CAC3B,MAAM,OAAQ,MAAM,oCAAA,kBAAkB,OAAO,MAAM;CACnD,IAAI,OAAO,KAAK,gBAAgB,cAAc,CAAC,KAAK,YAAY,GAC9D,MAAM,IAAI,oCAAA,kCAAkC,CAAC,KAAK,QAAQ,SAAS,CAAC;CAGtE,OAAO,IADc,KAAK,OAAO,OAC1B,EAAS,WAAW;AAC7B;;;;;;;AAeA,IAAa,yBAAyB,YAA6C;CACjF,QAAQ,OAAiB,SAAqB,QAAQ,UAAU,OAAO,EAAE,KAAK,CAAC;AACjF"}
@@ -3,8 +3,11 @@
3
3
  */
4
4
  import type { CallableVectorStore, BaseVectorStore } from "./contract";
5
5
  import type { BaseVectorStoreOptions, VectorEncoderFn, EncodeKind } from "./types";
6
+ /** The adapter class shape the factory accepts as `client` — a constructor with an optional availability probe. */
6
7
  export interface VectorStoreConstructor<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> {
8
+ /** Construct the adapter from its options. */
7
9
  new (options: O): BaseVectorStore;
10
+ /** Optional static probe: `false` short-circuits creation with a driver-unavailable error. */
8
11
  isAvailable?: () => boolean;
9
12
  }
10
13
  /**
@@ -19,8 +22,11 @@ export type VectorStoreClient<O extends BaseVectorStoreOptions = BaseVectorStore
19
22
  }) | (() => Promise<VectorStoreConstructor<O> | {
20
23
  default: VectorStoreConstructor<O>;
21
24
  }>);
25
+ /** Configuration accepted by {@link createVectorStore}: the adapter `client` plus its `options`. */
22
26
  export interface CreateVectorStoreConfig<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> {
27
+ /** The adapter class, or a (possibly async) resolver of it. See {@link VectorStoreClient}. */
23
28
  client: VectorStoreClient<O>;
29
+ /** Options passed to the resolved adapter's constructor. */
24
30
  options: O;
25
31
  }
26
32
  /**
@@ -30,9 +36,17 @@ export interface CreateVectorStoreConfig<O extends BaseVectorStoreOptions = Base
30
36
  * driver) only when the store is actually created.
31
37
  */
32
38
  export declare const createVectorStore: <O extends BaseVectorStoreOptions = BaseVectorStoreOptions>(config: CreateVectorStoreConfig<O>) => Promise<CallableVectorStore>;
39
+ /** The minimal shape of an embeddings-battery adapter usable as a vector encoder. */
33
40
  export interface EmbeddingsLike {
41
+ /** Embed a batch of texts, optionally hinting query vs. document encoding. */
34
42
  embedMany(texts: string[], opts?: {
35
43
  kind?: EncodeKind;
36
44
  }): Promise<number[][]>;
37
45
  }
46
+ /**
47
+ * Adapt an {@link EmbeddingsLike} object into a {@link VectorEncoderFn} for use as a store encoder.
48
+ *
49
+ * @param adapter - The embeddings adapter to wrap.
50
+ * @returns An encoder function forwarding to `adapter.embedMany`.
51
+ */
38
52
  export declare const encoderFromEmbeddings: (adapter: EmbeddingsLike) => VectorEncoderFn;
@@ -16,6 +16,12 @@ var createVectorStore = async (config) => {
16
16
  if (typeof Ctor.isAvailable === "function" && !Ctor.isAvailable()) throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE([Ctor.name || "unknown"]);
17
17
  return new Ctor(config.options).asCallable();
18
18
  };
19
+ /**
20
+ * Adapt an {@link EmbeddingsLike} object into a {@link VectorEncoderFn} for use as a store encoder.
21
+ *
22
+ * @param adapter - The embeddings adapter to wrap.
23
+ * @returns An encoder function forwarding to `adapter.embedMany`.
24
+ */
19
25
  var encoderFromEmbeddings = (adapter) => {
20
26
  return (texts, kind) => adapter.embedMany(texts, { kind });
21
27
  };
@@ -1 +1 @@
1
- {"version":3,"file":"factory.mjs","names":[],"sources":["../../../src/batteries/vector/factory.ts"],"sourcesContent":["/**\n * @module @nhtio/adk/batteries/vector/factory\n */\n\nimport { E_VECTOR_STORE_DRIVER_UNAVAILABLE } from './exceptions'\nimport { validateCreateConfig, resolveClientCtor } from './validation'\nimport type { CallableVectorStore, BaseVectorStore } from './contract'\nimport type { BaseVectorStoreOptions, VectorEncoderFn, EncodeKind } from './types'\n\n// The adapter class shape the factory accepts as 'client'.\nexport interface VectorStoreConstructor<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> {\n new (options: O): BaseVectorStore\n isAvailable?: () => boolean\n}\n\n/**\n * `client` is one of:\n * - the adapter class itself — `QdrantVectorStore`\n * - a sync resolver — `() => QdrantVectorStore`\n * - an async resolver / dynamic import — `() => import('…/qdrant').then(m => m.QdrantVectorStore)`\n * A resolver may also return a module namespace whose `default` is the class.\n */\nexport type VectorStoreClient<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> =\n | VectorStoreConstructor<O>\n | (() => VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> })\n | (() => Promise<VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> }>)\n\nexport interface CreateVectorStoreConfig<\n O extends BaseVectorStoreOptions = BaseVectorStoreOptions,\n> {\n client: VectorStoreClient<O>\n options: O\n}\n\n/**\n * Build a callable store. Validate config; resolve the `client` (class | sync resolver | async\n * resolver) to a BaseVectorStore subclass ctor; optional availability gate; construct; return\n * asCallable(). Async so that `client: () => import('…')` can lazily load the adapter (and its\n * driver) only when the store is actually created.\n */\nexport const createVectorStore = async <O extends BaseVectorStoreOptions = BaseVectorStoreOptions>(\n config: CreateVectorStoreConfig<O>\n): Promise<CallableVectorStore> => {\n validateCreateConfig(config)\n const Ctor = (await resolveClientCtor(config.client)) as VectorStoreConstructor<O>\n if (typeof Ctor.isAvailable === 'function' && !Ctor.isAvailable()) {\n throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE([Ctor.name || 'unknown'])\n }\n const instance = new Ctor(config.options)\n return instance.asCallable() as CallableVectorStore\n}\n\n// Helper: adapt an embeddings-battery-shaped object (has embedMany(texts, { kind })) into a VectorEncoderFn.\n// The embeddings adapters expose: embedMany(texts: string[], opts?: { kind?: 'query'|'document' }): Promise<number[][]>\nexport interface EmbeddingsLike {\n embedMany(texts: string[], opts?: { kind?: EncodeKind }): Promise<number[][]>\n}\nexport const encoderFromEmbeddings = (adapter: EmbeddingsLike): VectorEncoderFn => {\n return (texts: string[], kind: EncodeKind) => adapter.embedMany(texts, { kind })\n}\n"],"mappings":";;;;;;;;;;;;AAwCA,IAAa,oBAAoB,OAC/B,WACiC;CACjC,qBAAqB,MAAM;CAC3B,MAAM,OAAQ,MAAM,kBAAkB,OAAO,MAAM;CACnD,IAAI,OAAO,KAAK,gBAAgB,cAAc,CAAC,KAAK,YAAY,GAC9D,MAAM,IAAI,kCAAkC,CAAC,KAAK,QAAQ,SAAS,CAAC;CAGtE,OAAO,IADc,KAAK,OAAO,OAC1B,EAAS,WAAW;AAC7B;AAOA,IAAa,yBAAyB,YAA6C;CACjF,QAAQ,OAAiB,SAAqB,QAAQ,UAAU,OAAO,EAAE,KAAK,CAAC;AACjF"}
1
+ {"version":3,"file":"factory.mjs","names":[],"sources":["../../../src/batteries/vector/factory.ts"],"sourcesContent":["/**\n * @module @nhtio/adk/batteries/vector/factory\n */\n\nimport { E_VECTOR_STORE_DRIVER_UNAVAILABLE } from './exceptions'\nimport { validateCreateConfig, resolveClientCtor } from './validation'\nimport type { CallableVectorStore, BaseVectorStore } from './contract'\nimport type { BaseVectorStoreOptions, VectorEncoderFn, EncodeKind } from './types'\n\n/** The adapter class shape the factory accepts as `client` — a constructor with an optional availability probe. */\nexport interface VectorStoreConstructor<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> {\n /** Construct the adapter from its options. */\n new (options: O): BaseVectorStore\n /** Optional static probe: `false` short-circuits creation with a driver-unavailable error. */\n isAvailable?: () => boolean\n}\n\n/**\n * `client` is one of:\n * - the adapter class itself — `QdrantVectorStore`\n * - a sync resolver — `() => QdrantVectorStore`\n * - an async resolver / dynamic import — `() => import('…/qdrant').then(m => m.QdrantVectorStore)`\n * A resolver may also return a module namespace whose `default` is the class.\n */\nexport type VectorStoreClient<O extends BaseVectorStoreOptions = BaseVectorStoreOptions> =\n | VectorStoreConstructor<O>\n | (() => VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> })\n | (() => Promise<VectorStoreConstructor<O> | { default: VectorStoreConstructor<O> }>)\n\n/** Configuration accepted by {@link createVectorStore}: the adapter `client` plus its `options`. */\nexport interface CreateVectorStoreConfig<\n O extends BaseVectorStoreOptions = BaseVectorStoreOptions,\n> {\n /** The adapter class, or a (possibly async) resolver of it. See {@link VectorStoreClient}. */\n client: VectorStoreClient<O>\n /** Options passed to the resolved adapter's constructor. */\n options: O\n}\n\n/**\n * Build a callable store. Validate config; resolve the `client` (class | sync resolver | async\n * resolver) to a BaseVectorStore subclass ctor; optional availability gate; construct; return\n * asCallable(). Async so that `client: () => import('…')` can lazily load the adapter (and its\n * driver) only when the store is actually created.\n */\nexport const createVectorStore = async <O extends BaseVectorStoreOptions = BaseVectorStoreOptions>(\n config: CreateVectorStoreConfig<O>\n): Promise<CallableVectorStore> => {\n validateCreateConfig(config)\n const Ctor = (await resolveClientCtor(config.client)) as VectorStoreConstructor<O>\n if (typeof Ctor.isAvailable === 'function' && !Ctor.isAvailable()) {\n throw new E_VECTOR_STORE_DRIVER_UNAVAILABLE([Ctor.name || 'unknown'])\n }\n const instance = new Ctor(config.options)\n return instance.asCallable() as CallableVectorStore\n}\n\n// Helper: adapt an embeddings-battery-shaped object (has embedMany(texts, { kind })) into a VectorEncoderFn.\n// The embeddings adapters expose: embedMany(texts: string[], opts?: { kind?: 'query'|'document' }): Promise<number[][]>\n/** The minimal shape of an embeddings-battery adapter usable as a vector encoder. */\nexport interface EmbeddingsLike {\n /** Embed a batch of texts, optionally hinting query vs. document encoding. */\n embedMany(texts: string[], opts?: { kind?: EncodeKind }): Promise<number[][]>\n}\n/**\n * Adapt an {@link EmbeddingsLike} object into a {@link VectorEncoderFn} for use as a store encoder.\n *\n * @param adapter - The embeddings adapter to wrap.\n * @returns An encoder function forwarding to `adapter.embedMany`.\n */\nexport const encoderFromEmbeddings = (adapter: EmbeddingsLike): VectorEncoderFn => {\n return (texts: string[], kind: EncodeKind) => adapter.embedMany(texts, { kind })\n}\n"],"mappings":";;;;;;;;;;;;AA6CA,IAAa,oBAAoB,OAC/B,WACiC;CACjC,qBAAqB,MAAM;CAC3B,MAAM,OAAQ,MAAM,kBAAkB,OAAO,MAAM;CACnD,IAAI,OAAO,KAAK,gBAAgB,cAAc,CAAC,KAAK,YAAY,GAC9D,MAAM,IAAI,kCAAkC,CAAC,KAAK,QAAQ,SAAS,CAAC;CAGtE,OAAO,IADc,KAAK,OAAO,OAC1B,EAAS,WAAW;AAC7B;;;;;;;AAeA,IAAa,yBAAyB,YAA6C;CACjF,QAAQ,OAAiB,SAAqB,QAAQ,UAAU,OAAO,EAAE,KAAK,CAAC;AACjF"}
@@ -1,6 +1,6 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  require("../../chunk-Ble4zEEl.js");
3
- const require_tool_registry = require("../../tool_registry-DYUYqXvo.js");
3
+ const require_tool_registry = require("../../tool_registry-CKJPze3j.js");
4
4
  require("../../guards.cjs");
5
5
  let _nhtio_validation = require("@nhtio/validation");
6
6
  //#region src/batteries/vector/filters.ts
@@ -9,13 +9,23 @@ let _nhtio_validation = require("@nhtio/validation");
9
9
  *
10
10
  * @module @nhtio/adk/batteries/vector/filters
11
11
  */
12
+ /**
13
+ * Construct a {@link RawExpr} from literal text and optional positional `bindings`.
14
+ *
15
+ * @param sql - The raw expression text.
16
+ * @param bindings - Positional binding values.
17
+ */
12
18
  var raw = (sql, bindings = []) => ({
13
19
  __raw: sql,
14
20
  bindings
15
21
  });
22
+ /** Type guard: `true` if `v` is a {@link RawExpr}. */
16
23
  var isRawExpr = (v) => require_tool_registry.isObject(v) && typeof v.__raw === "string" && Array.isArray(v.bindings);
24
+ /** Type guard: `true` if `f` is a {@link FilterCondition}. */
17
25
  var isFilterCondition = (f) => typeof f.field === "string" && typeof f.op === "string";
26
+ /** Type guard: `true` if `f` is a {@link RawFilter}. */
18
27
  var isRawFilter = (f) => typeof f.$dialect === "string";
28
+ /** Type guard: `true` if `f` is a {@link FilterGroup} (neither a condition nor a raw filter). */
19
29
  var isFilterGroup = (f) => !isFilterCondition(f) && !isRawFilter(f);
20
30
  var rawFilterSchema = _nhtio_validation.validator.object({
21
31
  $dialect: _nhtio_validation.validator.string().required(),
@@ -27,6 +37,7 @@ var filterConditionSchema = _nhtio_validation.validator.object({
27
37
  op: _nhtio_validation.validator.string().valid("eq", "ne", "gt", "gte", "lt", "lte", "in", "nin", "exists", "contains").required(),
28
38
  value: _nhtio_validation.validator.alternatives(_nhtio_validation.validator.any(), _nhtio_validation.validator.array().items(_nhtio_validation.validator.any())).optional()
29
39
  });
40
+ /** Recursive validator schema for any {@link VectorFilter} (condition, raw, or nested group). */
30
41
  var vectorFilterSchema = _nhtio_validation.validator.alternatives(filterConditionSchema, rawFilterSchema, _nhtio_validation.validator.object({
31
42
  and: _nhtio_validation.validator.array().items(_nhtio_validation.validator.link("#vectorFilter")).optional(),
32
43
  or: _nhtio_validation.validator.array().items(_nhtio_validation.validator.link("#vectorFilter")).optional(),
@@ -42,6 +53,16 @@ var getField = (metadata, path) => {
42
53
  }
43
54
  return current;
44
55
  };
56
+ /**
57
+ * Evaluate a {@link VectorFilter} against a record's metadata in memory — the reference semantics
58
+ * adapters must match for client-side filtering and conformance.
59
+ *
60
+ * @param filter - The filter to evaluate.
61
+ * @param metadata - The record metadata to test.
62
+ * @returns `true` if the metadata satisfies the filter.
63
+ * @throws when the filter (or a nested value) is a raw expression, which the in-memory evaluator
64
+ * cannot interpret.
65
+ */
45
66
  var evaluateFilter = (filter, metadata) => {
46
67
  if (isRawFilter(filter)) throw new Error("raw filters are not evaluable by the in-memory filter evaluator");
47
68
  if (isFilterCondition(filter)) {
@@ -1 +1 @@
1
- {"version":3,"file":"filters.cjs","names":[],"sources":["../../../src/batteries/vector/filters.ts"],"sourcesContent":["/**\n * Filter types and evaluator for the vector battery.\n *\n * @module @nhtio/adk/batteries/vector/filters\n */\n\nimport { isObject } from '@nhtio/adk/guards'\nimport { validator } from '@nhtio/validation'\nimport type { VectorMetadata, VectorMetadataValue } from './types'\n\nexport type FilterOperator =\n | 'eq'\n | 'ne'\n | 'gt'\n | 'gte'\n | 'lt'\n | 'lte'\n | 'in'\n | 'nin'\n | 'exists'\n | 'contains'\n\nexport interface RawExpr {\n __raw: string\n bindings: unknown[]\n}\n\nexport const raw = (sql: string, bindings: unknown[] = []): RawExpr => ({ __raw: sql, bindings })\n\nexport const isRawExpr = (v: unknown): v is RawExpr =>\n isObject(v) && typeof v.__raw === 'string' && Array.isArray(v.bindings)\n\nexport interface FilterCondition {\n field: string\n op: FilterOperator\n value?: VectorMetadataValue | VectorMetadataValue[] | RawExpr\n}\nexport interface FilterGroup {\n and?: VectorFilter[]\n or?: VectorFilter[]\n not?: VectorFilter\n}\nexport interface RawFilter {\n $dialect: string\n $raw: string | unknown\n $bindings?: unknown[]\n}\nexport type VectorFilter = FilterCondition | FilterGroup | RawFilter\n\nexport const isFilterCondition = (f: VectorFilter): f is FilterCondition =>\n typeof (f as FilterCondition).field === 'string' && typeof (f as FilterCondition).op === 'string'\n\nexport const isRawFilter = (f: VectorFilter): f is RawFilter =>\n typeof (f as RawFilter).$dialect === 'string'\n\nexport const isFilterGroup = (f: VectorFilter): f is FilterGroup =>\n !isFilterCondition(f) && !isRawFilter(f)\n\nconst rawFilterSchema = validator.object<RawFilter>({\n $dialect: validator.string().required(),\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: $raw is any structured dialect payload; disposition is set by the .required() on the alternatives\n $raw: validator.alternatives(validator.string(), validator.any()).required(),\n // eslint-disable-next-line adk/require-validator-any-required -- item type-arg: bindings hold arbitrary values; disposition is set by .optional() on the array\n $bindings: validator.array().items(validator.any()).optional(),\n})\n\nconst filterConditionSchema = validator.object<FilterCondition>({\n field: validator.string().required(),\n op: validator\n .string()\n .valid('eq', 'ne', 'gt', 'gte', 'lt', 'lte', 'in', 'nin', 'exists', 'contains')\n .required(),\n value: validator\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: a filter value is any scalar or array of any; disposition is set by .optional() below\n .alternatives(validator.any(), validator.array().items(validator.any()))\n .optional(),\n})\n\nexport const vectorFilterSchema = validator\n .alternatives(\n filterConditionSchema,\n rawFilterSchema,\n validator\n .object<FilterGroup>({\n and: validator.array().items(validator.link('#vectorFilter')).optional(),\n or: validator.array().items(validator.link('#vectorFilter')).optional(),\n not: validator.link('#vectorFilter').optional(),\n })\n .unknown(false)\n )\n .id('vectorFilter')\n\nconst getField = (metadata: VectorMetadata, path: string): VectorMetadataValue | undefined => {\n const keys = path.split('.')\n let current: VectorMetadataValue | undefined = metadata\n for (const key of keys) {\n if (current === undefined || current === null) {\n return undefined\n }\n if (typeof current !== 'object') {\n return undefined\n }\n current = (current as Record<string, VectorMetadataValue>)[key]\n }\n return current\n}\n\nexport const evaluateFilter = (filter: VectorFilter, metadata: VectorMetadata): boolean => {\n if (isRawFilter(filter)) {\n throw new Error('raw filters are not evaluable by the in-memory filter evaluator')\n }\n\n if (isFilterCondition(filter)) {\n const { field, op, value } = filter\n const fieldVal = getField(metadata, field)\n\n if (isRawExpr(value)) {\n throw new Error('raw expressions are not evaluable by the in-memory filter evaluator')\n }\n\n switch (op) {\n case 'eq': {\n return fieldVal === value\n }\n\n case 'ne': {\n return fieldVal !== value\n }\n\n case 'gt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal > value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal > value\n }\n return false\n }\n\n case 'gte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal >= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal >= value\n }\n return false\n }\n\n case 'lt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal < value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal < value\n }\n return false\n }\n\n case 'lte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal <= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal <= value\n }\n return false\n }\n\n case 'in': {\n if (!Array.isArray(value)) {\n return false\n }\n return value.includes(fieldVal as never)\n }\n\n case 'nin': {\n if (!Array.isArray(value)) {\n return true\n }\n return !value.includes(fieldVal as never)\n }\n\n case 'exists': {\n const checkExists = value === undefined || value === true\n return checkExists ? fieldVal !== undefined : fieldVal === undefined\n }\n\n case 'contains': {\n if (fieldVal === undefined) {\n return false\n }\n if (Array.isArray(fieldVal)) {\n return fieldVal.includes(value as never)\n }\n if (typeof fieldVal === 'string') {\n return fieldVal.includes(String(value))\n }\n return false\n }\n\n default: {\n return false\n }\n }\n }\n\n if (isFilterGroup(filter)) {\n const { and, or, not } = filter\n\n if (and !== undefined) {\n return and.every((child) => evaluateFilter(child, metadata))\n }\n\n if (or !== undefined) {\n return or.some((child) => evaluateFilter(child, metadata))\n }\n\n if (not !== undefined) {\n return !evaluateFilter(not, metadata)\n }\n\n return true\n }\n\n return false\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"filters.cjs","names":[],"sources":["../../../src/batteries/vector/filters.ts"],"sourcesContent":["/**\n * Filter types and evaluator for the vector battery.\n *\n * @module @nhtio/adk/batteries/vector/filters\n */\n\nimport { isObject } from '@nhtio/adk/guards'\nimport { validator } from '@nhtio/validation'\nimport type { VectorMetadata, VectorMetadataValue } from './types'\n\n/** A comparison operator usable in a {@link FilterCondition}. */\nexport type FilterOperator =\n | 'eq'\n | 'ne'\n | 'gt'\n | 'gte'\n | 'lt'\n | 'lte'\n | 'in'\n | 'nin'\n | 'exists'\n | 'contains'\n\n/** A raw, adapter-dialect filter expression: literal text plus positional bindings. */\nexport interface RawExpr {\n /** The raw expression text. */\n __raw: string\n /** Positional binding values substituted into the expression. */\n bindings: unknown[]\n}\n\n/**\n * Construct a {@link RawExpr} from literal text and optional positional `bindings`.\n *\n * @param sql - The raw expression text.\n * @param bindings - Positional binding values.\n */\nexport const raw = (sql: string, bindings: unknown[] = []): RawExpr => ({ __raw: sql, bindings })\n\n/** Type guard: `true` if `v` is a {@link RawExpr}. */\nexport const isRawExpr = (v: unknown): v is RawExpr =>\n isObject(v) && typeof v.__raw === 'string' && Array.isArray(v.bindings)\n\n/** A single field comparison: `field op value`. */\nexport interface FilterCondition {\n /** The metadata field path (dot-separated for nested fields). */\n field: string\n /** The comparison operator. */\n op: FilterOperator\n /** The value(s) compared against, or a {@link RawExpr}; omitted for `exists`. */\n value?: VectorMetadataValue | VectorMetadataValue[] | RawExpr\n}\n/** A boolean combination of nested filters. Exactly one of `and`/`or`/`not` is meaningful. */\nexport interface FilterGroup {\n /** All nested filters must match. */\n and?: VectorFilter[]\n /** At least one nested filter must match. */\n or?: VectorFilter[]\n /** The nested filter must not match. */\n not?: VectorFilter\n}\n/** An adapter-dialect raw filter forwarded to the backend verbatim. */\nexport interface RawFilter {\n /** The dialect the raw expression is written in (e.g. `'sql'`). */\n $dialect: string\n /** The raw expression — a string, or a structured dialect-specific payload. */\n $raw: string | unknown\n /** Positional binding values for the raw expression. */\n $bindings?: unknown[]\n}\n/** Any filter node: a {@link FilterCondition}, a {@link FilterGroup}, or a {@link RawFilter}. */\nexport type VectorFilter = FilterCondition | FilterGroup | RawFilter\n\n/** Type guard: `true` if `f` is a {@link FilterCondition}. */\nexport const isFilterCondition = (f: VectorFilter): f is FilterCondition =>\n typeof (f as FilterCondition).field === 'string' && typeof (f as FilterCondition).op === 'string'\n\n/** Type guard: `true` if `f` is a {@link RawFilter}. */\nexport const isRawFilter = (f: VectorFilter): f is RawFilter =>\n typeof (f as RawFilter).$dialect === 'string'\n\n/** Type guard: `true` if `f` is a {@link FilterGroup} (neither a condition nor a raw filter). */\nexport const isFilterGroup = (f: VectorFilter): f is FilterGroup =>\n !isFilterCondition(f) && !isRawFilter(f)\n\nconst rawFilterSchema = validator.object<RawFilter>({\n $dialect: validator.string().required(),\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: $raw is any structured dialect payload; disposition is set by the .required() on the alternatives\n $raw: validator.alternatives(validator.string(), validator.any()).required(),\n // eslint-disable-next-line adk/require-validator-any-required -- item type-arg: bindings hold arbitrary values; disposition is set by .optional() on the array\n $bindings: validator.array().items(validator.any()).optional(),\n})\n\nconst filterConditionSchema = validator.object<FilterCondition>({\n field: validator.string().required(),\n op: validator\n .string()\n .valid('eq', 'ne', 'gt', 'gte', 'lt', 'lte', 'in', 'nin', 'exists', 'contains')\n .required(),\n value: validator\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: a filter value is any scalar or array of any; disposition is set by .optional() below\n .alternatives(validator.any(), validator.array().items(validator.any()))\n .optional(),\n})\n\n/** Recursive validator schema for any {@link VectorFilter} (condition, raw, or nested group). */\nexport const vectorFilterSchema = validator\n .alternatives(\n filterConditionSchema,\n rawFilterSchema,\n validator\n .object<FilterGroup>({\n and: validator.array().items(validator.link('#vectorFilter')).optional(),\n or: validator.array().items(validator.link('#vectorFilter')).optional(),\n not: validator.link('#vectorFilter').optional(),\n })\n .unknown(false)\n )\n .id('vectorFilter')\n\nconst getField = (metadata: VectorMetadata, path: string): VectorMetadataValue | undefined => {\n const keys = path.split('.')\n let current: VectorMetadataValue | undefined = metadata\n for (const key of keys) {\n if (current === undefined || current === null) {\n return undefined\n }\n if (typeof current !== 'object') {\n return undefined\n }\n current = (current as Record<string, VectorMetadataValue>)[key]\n }\n return current\n}\n\n/**\n * Evaluate a {@link VectorFilter} against a record's metadata in memory — the reference semantics\n * adapters must match for client-side filtering and conformance.\n *\n * @param filter - The filter to evaluate.\n * @param metadata - The record metadata to test.\n * @returns `true` if the metadata satisfies the filter.\n * @throws when the filter (or a nested value) is a raw expression, which the in-memory evaluator\n * cannot interpret.\n */\nexport const evaluateFilter = (filter: VectorFilter, metadata: VectorMetadata): boolean => {\n if (isRawFilter(filter)) {\n throw new Error('raw filters are not evaluable by the in-memory filter evaluator')\n }\n\n if (isFilterCondition(filter)) {\n const { field, op, value } = filter\n const fieldVal = getField(metadata, field)\n\n if (isRawExpr(value)) {\n throw new Error('raw expressions are not evaluable by the in-memory filter evaluator')\n }\n\n switch (op) {\n case 'eq': {\n return fieldVal === value\n }\n\n case 'ne': {\n return fieldVal !== value\n }\n\n case 'gt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal > value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal > value\n }\n return false\n }\n\n case 'gte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal >= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal >= value\n }\n return false\n }\n\n case 'lt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal < value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal < value\n }\n return false\n }\n\n case 'lte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal <= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal <= value\n }\n return false\n }\n\n case 'in': {\n if (!Array.isArray(value)) {\n return false\n }\n return value.includes(fieldVal as never)\n }\n\n case 'nin': {\n if (!Array.isArray(value)) {\n return true\n }\n return !value.includes(fieldVal as never)\n }\n\n case 'exists': {\n const checkExists = value === undefined || value === true\n return checkExists ? fieldVal !== undefined : fieldVal === undefined\n }\n\n case 'contains': {\n if (fieldVal === undefined) {\n return false\n }\n if (Array.isArray(fieldVal)) {\n return fieldVal.includes(value as never)\n }\n if (typeof fieldVal === 'string') {\n return fieldVal.includes(String(value))\n }\n return false\n }\n\n default: {\n return false\n }\n }\n }\n\n if (isFilterGroup(filter)) {\n const { and, or, not } = filter\n\n if (and !== undefined) {\n return and.every((child) => evaluateFilter(child, metadata))\n }\n\n if (or !== undefined) {\n return or.some((child) => evaluateFilter(child, metadata))\n }\n\n if (not !== undefined) {\n return !evaluateFilter(not, metadata)\n }\n\n return true\n }\n\n return false\n}\n"],"mappings":"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"}
@@ -4,31 +4,69 @@
4
4
  * @module @nhtio/adk/batteries/vector/filters
5
5
  */
6
6
  import type { VectorMetadata, VectorMetadataValue } from "./types";
7
+ /** A comparison operator usable in a {@link FilterCondition}. */
7
8
  export type FilterOperator = 'eq' | 'ne' | 'gt' | 'gte' | 'lt' | 'lte' | 'in' | 'nin' | 'exists' | 'contains';
9
+ /** A raw, adapter-dialect filter expression: literal text plus positional bindings. */
8
10
  export interface RawExpr {
11
+ /** The raw expression text. */
9
12
  __raw: string;
13
+ /** Positional binding values substituted into the expression. */
10
14
  bindings: unknown[];
11
15
  }
16
+ /**
17
+ * Construct a {@link RawExpr} from literal text and optional positional `bindings`.
18
+ *
19
+ * @param sql - The raw expression text.
20
+ * @param bindings - Positional binding values.
21
+ */
12
22
  export declare const raw: (sql: string, bindings?: unknown[]) => RawExpr;
23
+ /** Type guard: `true` if `v` is a {@link RawExpr}. */
13
24
  export declare const isRawExpr: (v: unknown) => v is RawExpr;
25
+ /** A single field comparison: `field op value`. */
14
26
  export interface FilterCondition {
27
+ /** The metadata field path (dot-separated for nested fields). */
15
28
  field: string;
29
+ /** The comparison operator. */
16
30
  op: FilterOperator;
31
+ /** The value(s) compared against, or a {@link RawExpr}; omitted for `exists`. */
17
32
  value?: VectorMetadataValue | VectorMetadataValue[] | RawExpr;
18
33
  }
34
+ /** A boolean combination of nested filters. Exactly one of `and`/`or`/`not` is meaningful. */
19
35
  export interface FilterGroup {
36
+ /** All nested filters must match. */
20
37
  and?: VectorFilter[];
38
+ /** At least one nested filter must match. */
21
39
  or?: VectorFilter[];
40
+ /** The nested filter must not match. */
22
41
  not?: VectorFilter;
23
42
  }
43
+ /** An adapter-dialect raw filter forwarded to the backend verbatim. */
24
44
  export interface RawFilter {
45
+ /** The dialect the raw expression is written in (e.g. `'sql'`). */
25
46
  $dialect: string;
47
+ /** The raw expression — a string, or a structured dialect-specific payload. */
26
48
  $raw: string | unknown;
49
+ /** Positional binding values for the raw expression. */
27
50
  $bindings?: unknown[];
28
51
  }
52
+ /** Any filter node: a {@link FilterCondition}, a {@link FilterGroup}, or a {@link RawFilter}. */
29
53
  export type VectorFilter = FilterCondition | FilterGroup | RawFilter;
54
+ /** Type guard: `true` if `f` is a {@link FilterCondition}. */
30
55
  export declare const isFilterCondition: (f: VectorFilter) => f is FilterCondition;
56
+ /** Type guard: `true` if `f` is a {@link RawFilter}. */
31
57
  export declare const isRawFilter: (f: VectorFilter) => f is RawFilter;
58
+ /** Type guard: `true` if `f` is a {@link FilterGroup} (neither a condition nor a raw filter). */
32
59
  export declare const isFilterGroup: (f: VectorFilter) => f is FilterGroup;
60
+ /** Recursive validator schema for any {@link VectorFilter} (condition, raw, or nested group). */
33
61
  export declare const vectorFilterSchema: import("@nhtio/validation").AlternativesSchema<any>;
62
+ /**
63
+ * Evaluate a {@link VectorFilter} against a record's metadata in memory — the reference semantics
64
+ * adapters must match for client-side filtering and conformance.
65
+ *
66
+ * @param filter - The filter to evaluate.
67
+ * @param metadata - The record metadata to test.
68
+ * @returns `true` if the metadata satisfies the filter.
69
+ * @throws when the filter (or a nested value) is a raw expression, which the in-memory evaluator
70
+ * cannot interpret.
71
+ */
34
72
  export declare const evaluateFilter: (filter: VectorFilter, metadata: VectorMetadata) => boolean;
@@ -1,4 +1,4 @@
1
- import { c as isObject } from "../../tool_registry-D1pSSlsd.mjs";
1
+ import { c as isObject } from "../../tool_registry-791Vrjtf.mjs";
2
2
  import "../../guards.mjs";
3
3
  import { validator } from "@nhtio/validation";
4
4
  //#region src/batteries/vector/filters.ts
@@ -7,13 +7,23 @@ import { validator } from "@nhtio/validation";
7
7
  *
8
8
  * @module @nhtio/adk/batteries/vector/filters
9
9
  */
10
+ /**
11
+ * Construct a {@link RawExpr} from literal text and optional positional `bindings`.
12
+ *
13
+ * @param sql - The raw expression text.
14
+ * @param bindings - Positional binding values.
15
+ */
10
16
  var raw = (sql, bindings = []) => ({
11
17
  __raw: sql,
12
18
  bindings
13
19
  });
20
+ /** Type guard: `true` if `v` is a {@link RawExpr}. */
14
21
  var isRawExpr = (v) => isObject(v) && typeof v.__raw === "string" && Array.isArray(v.bindings);
22
+ /** Type guard: `true` if `f` is a {@link FilterCondition}. */
15
23
  var isFilterCondition = (f) => typeof f.field === "string" && typeof f.op === "string";
24
+ /** Type guard: `true` if `f` is a {@link RawFilter}. */
16
25
  var isRawFilter = (f) => typeof f.$dialect === "string";
26
+ /** Type guard: `true` if `f` is a {@link FilterGroup} (neither a condition nor a raw filter). */
17
27
  var isFilterGroup = (f) => !isFilterCondition(f) && !isRawFilter(f);
18
28
  var rawFilterSchema = validator.object({
19
29
  $dialect: validator.string().required(),
@@ -25,6 +35,7 @@ var filterConditionSchema = validator.object({
25
35
  op: validator.string().valid("eq", "ne", "gt", "gte", "lt", "lte", "in", "nin", "exists", "contains").required(),
26
36
  value: validator.alternatives(validator.any(), validator.array().items(validator.any())).optional()
27
37
  });
38
+ /** Recursive validator schema for any {@link VectorFilter} (condition, raw, or nested group). */
28
39
  var vectorFilterSchema = validator.alternatives(filterConditionSchema, rawFilterSchema, validator.object({
29
40
  and: validator.array().items(validator.link("#vectorFilter")).optional(),
30
41
  or: validator.array().items(validator.link("#vectorFilter")).optional(),
@@ -40,6 +51,16 @@ var getField = (metadata, path) => {
40
51
  }
41
52
  return current;
42
53
  };
54
+ /**
55
+ * Evaluate a {@link VectorFilter} against a record's metadata in memory — the reference semantics
56
+ * adapters must match for client-side filtering and conformance.
57
+ *
58
+ * @param filter - The filter to evaluate.
59
+ * @param metadata - The record metadata to test.
60
+ * @returns `true` if the metadata satisfies the filter.
61
+ * @throws when the filter (or a nested value) is a raw expression, which the in-memory evaluator
62
+ * cannot interpret.
63
+ */
43
64
  var evaluateFilter = (filter, metadata) => {
44
65
  if (isRawFilter(filter)) throw new Error("raw filters are not evaluable by the in-memory filter evaluator");
45
66
  if (isFilterCondition(filter)) {
@@ -1 +1 @@
1
- {"version":3,"file":"filters.mjs","names":[],"sources":["../../../src/batteries/vector/filters.ts"],"sourcesContent":["/**\n * Filter types and evaluator for the vector battery.\n *\n * @module @nhtio/adk/batteries/vector/filters\n */\n\nimport { isObject } from '@nhtio/adk/guards'\nimport { validator } from '@nhtio/validation'\nimport type { VectorMetadata, VectorMetadataValue } from './types'\n\nexport type FilterOperator =\n | 'eq'\n | 'ne'\n | 'gt'\n | 'gte'\n | 'lt'\n | 'lte'\n | 'in'\n | 'nin'\n | 'exists'\n | 'contains'\n\nexport interface RawExpr {\n __raw: string\n bindings: unknown[]\n}\n\nexport const raw = (sql: string, bindings: unknown[] = []): RawExpr => ({ __raw: sql, bindings })\n\nexport const isRawExpr = (v: unknown): v is RawExpr =>\n isObject(v) && typeof v.__raw === 'string' && Array.isArray(v.bindings)\n\nexport interface FilterCondition {\n field: string\n op: FilterOperator\n value?: VectorMetadataValue | VectorMetadataValue[] | RawExpr\n}\nexport interface FilterGroup {\n and?: VectorFilter[]\n or?: VectorFilter[]\n not?: VectorFilter\n}\nexport interface RawFilter {\n $dialect: string\n $raw: string | unknown\n $bindings?: unknown[]\n}\nexport type VectorFilter = FilterCondition | FilterGroup | RawFilter\n\nexport const isFilterCondition = (f: VectorFilter): f is FilterCondition =>\n typeof (f as FilterCondition).field === 'string' && typeof (f as FilterCondition).op === 'string'\n\nexport const isRawFilter = (f: VectorFilter): f is RawFilter =>\n typeof (f as RawFilter).$dialect === 'string'\n\nexport const isFilterGroup = (f: VectorFilter): f is FilterGroup =>\n !isFilterCondition(f) && !isRawFilter(f)\n\nconst rawFilterSchema = validator.object<RawFilter>({\n $dialect: validator.string().required(),\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: $raw is any structured dialect payload; disposition is set by the .required() on the alternatives\n $raw: validator.alternatives(validator.string(), validator.any()).required(),\n // eslint-disable-next-line adk/require-validator-any-required -- item type-arg: bindings hold arbitrary values; disposition is set by .optional() on the array\n $bindings: validator.array().items(validator.any()).optional(),\n})\n\nconst filterConditionSchema = validator.object<FilterCondition>({\n field: validator.string().required(),\n op: validator\n .string()\n .valid('eq', 'ne', 'gt', 'gte', 'lt', 'lte', 'in', 'nin', 'exists', 'contains')\n .required(),\n value: validator\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: a filter value is any scalar or array of any; disposition is set by .optional() below\n .alternatives(validator.any(), validator.array().items(validator.any()))\n .optional(),\n})\n\nexport const vectorFilterSchema = validator\n .alternatives(\n filterConditionSchema,\n rawFilterSchema,\n validator\n .object<FilterGroup>({\n and: validator.array().items(validator.link('#vectorFilter')).optional(),\n or: validator.array().items(validator.link('#vectorFilter')).optional(),\n not: validator.link('#vectorFilter').optional(),\n })\n .unknown(false)\n )\n .id('vectorFilter')\n\nconst getField = (metadata: VectorMetadata, path: string): VectorMetadataValue | undefined => {\n const keys = path.split('.')\n let current: VectorMetadataValue | undefined = metadata\n for (const key of keys) {\n if (current === undefined || current === null) {\n return undefined\n }\n if (typeof current !== 'object') {\n return undefined\n }\n current = (current as Record<string, VectorMetadataValue>)[key]\n }\n return current\n}\n\nexport const evaluateFilter = (filter: VectorFilter, metadata: VectorMetadata): boolean => {\n if (isRawFilter(filter)) {\n throw new Error('raw filters are not evaluable by the in-memory filter evaluator')\n }\n\n if (isFilterCondition(filter)) {\n const { field, op, value } = filter\n const fieldVal = getField(metadata, field)\n\n if (isRawExpr(value)) {\n throw new Error('raw expressions are not evaluable by the in-memory filter evaluator')\n }\n\n switch (op) {\n case 'eq': {\n return fieldVal === value\n }\n\n case 'ne': {\n return fieldVal !== value\n }\n\n case 'gt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal > value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal > value\n }\n return false\n }\n\n case 'gte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal >= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal >= value\n }\n return false\n }\n\n case 'lt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal < value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal < value\n }\n return false\n }\n\n case 'lte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal <= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal <= value\n }\n return false\n }\n\n case 'in': {\n if (!Array.isArray(value)) {\n return false\n }\n return value.includes(fieldVal as never)\n }\n\n case 'nin': {\n if (!Array.isArray(value)) {\n return true\n }\n return !value.includes(fieldVal as never)\n }\n\n case 'exists': {\n const checkExists = value === undefined || value === true\n return checkExists ? fieldVal !== undefined : fieldVal === undefined\n }\n\n case 'contains': {\n if (fieldVal === undefined) {\n return false\n }\n if (Array.isArray(fieldVal)) {\n return fieldVal.includes(value as never)\n }\n if (typeof fieldVal === 'string') {\n return fieldVal.includes(String(value))\n }\n return false\n }\n\n default: {\n return false\n }\n }\n }\n\n if (isFilterGroup(filter)) {\n const { and, or, not } = filter\n\n if (and !== undefined) {\n return and.every((child) => evaluateFilter(child, metadata))\n }\n\n if (or !== undefined) {\n return or.some((child) => evaluateFilter(child, metadata))\n }\n\n if (not !== undefined) {\n return !evaluateFilter(not, metadata)\n }\n\n return true\n }\n\n return false\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"filters.mjs","names":[],"sources":["../../../src/batteries/vector/filters.ts"],"sourcesContent":["/**\n * Filter types and evaluator for the vector battery.\n *\n * @module @nhtio/adk/batteries/vector/filters\n */\n\nimport { isObject } from '@nhtio/adk/guards'\nimport { validator } from '@nhtio/validation'\nimport type { VectorMetadata, VectorMetadataValue } from './types'\n\n/** A comparison operator usable in a {@link FilterCondition}. */\nexport type FilterOperator =\n | 'eq'\n | 'ne'\n | 'gt'\n | 'gte'\n | 'lt'\n | 'lte'\n | 'in'\n | 'nin'\n | 'exists'\n | 'contains'\n\n/** A raw, adapter-dialect filter expression: literal text plus positional bindings. */\nexport interface RawExpr {\n /** The raw expression text. */\n __raw: string\n /** Positional binding values substituted into the expression. */\n bindings: unknown[]\n}\n\n/**\n * Construct a {@link RawExpr} from literal text and optional positional `bindings`.\n *\n * @param sql - The raw expression text.\n * @param bindings - Positional binding values.\n */\nexport const raw = (sql: string, bindings: unknown[] = []): RawExpr => ({ __raw: sql, bindings })\n\n/** Type guard: `true` if `v` is a {@link RawExpr}. */\nexport const isRawExpr = (v: unknown): v is RawExpr =>\n isObject(v) && typeof v.__raw === 'string' && Array.isArray(v.bindings)\n\n/** A single field comparison: `field op value`. */\nexport interface FilterCondition {\n /** The metadata field path (dot-separated for nested fields). */\n field: string\n /** The comparison operator. */\n op: FilterOperator\n /** The value(s) compared against, or a {@link RawExpr}; omitted for `exists`. */\n value?: VectorMetadataValue | VectorMetadataValue[] | RawExpr\n}\n/** A boolean combination of nested filters. Exactly one of `and`/`or`/`not` is meaningful. */\nexport interface FilterGroup {\n /** All nested filters must match. */\n and?: VectorFilter[]\n /** At least one nested filter must match. */\n or?: VectorFilter[]\n /** The nested filter must not match. */\n not?: VectorFilter\n}\n/** An adapter-dialect raw filter forwarded to the backend verbatim. */\nexport interface RawFilter {\n /** The dialect the raw expression is written in (e.g. `'sql'`). */\n $dialect: string\n /** The raw expression — a string, or a structured dialect-specific payload. */\n $raw: string | unknown\n /** Positional binding values for the raw expression. */\n $bindings?: unknown[]\n}\n/** Any filter node: a {@link FilterCondition}, a {@link FilterGroup}, or a {@link RawFilter}. */\nexport type VectorFilter = FilterCondition | FilterGroup | RawFilter\n\n/** Type guard: `true` if `f` is a {@link FilterCondition}. */\nexport const isFilterCondition = (f: VectorFilter): f is FilterCondition =>\n typeof (f as FilterCondition).field === 'string' && typeof (f as FilterCondition).op === 'string'\n\n/** Type guard: `true` if `f` is a {@link RawFilter}. */\nexport const isRawFilter = (f: VectorFilter): f is RawFilter =>\n typeof (f as RawFilter).$dialect === 'string'\n\n/** Type guard: `true` if `f` is a {@link FilterGroup} (neither a condition nor a raw filter). */\nexport const isFilterGroup = (f: VectorFilter): f is FilterGroup =>\n !isFilterCondition(f) && !isRawFilter(f)\n\nconst rawFilterSchema = validator.object<RawFilter>({\n $dialect: validator.string().required(),\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: $raw is any structured dialect payload; disposition is set by the .required() on the alternatives\n $raw: validator.alternatives(validator.string(), validator.any()).required(),\n // eslint-disable-next-line adk/require-validator-any-required -- item type-arg: bindings hold arbitrary values; disposition is set by .optional() on the array\n $bindings: validator.array().items(validator.any()).optional(),\n})\n\nconst filterConditionSchema = validator.object<FilterCondition>({\n field: validator.string().required(),\n op: validator\n .string()\n .valid('eq', 'ne', 'gt', 'gte', 'lt', 'lte', 'in', 'nin', 'exists', 'contains')\n .required(),\n value: validator\n // eslint-disable-next-line adk/require-validator-any-required -- value type-arg: a filter value is any scalar or array of any; disposition is set by .optional() below\n .alternatives(validator.any(), validator.array().items(validator.any()))\n .optional(),\n})\n\n/** Recursive validator schema for any {@link VectorFilter} (condition, raw, or nested group). */\nexport const vectorFilterSchema = validator\n .alternatives(\n filterConditionSchema,\n rawFilterSchema,\n validator\n .object<FilterGroup>({\n and: validator.array().items(validator.link('#vectorFilter')).optional(),\n or: validator.array().items(validator.link('#vectorFilter')).optional(),\n not: validator.link('#vectorFilter').optional(),\n })\n .unknown(false)\n )\n .id('vectorFilter')\n\nconst getField = (metadata: VectorMetadata, path: string): VectorMetadataValue | undefined => {\n const keys = path.split('.')\n let current: VectorMetadataValue | undefined = metadata\n for (const key of keys) {\n if (current === undefined || current === null) {\n return undefined\n }\n if (typeof current !== 'object') {\n return undefined\n }\n current = (current as Record<string, VectorMetadataValue>)[key]\n }\n return current\n}\n\n/**\n * Evaluate a {@link VectorFilter} against a record's metadata in memory — the reference semantics\n * adapters must match for client-side filtering and conformance.\n *\n * @param filter - The filter to evaluate.\n * @param metadata - The record metadata to test.\n * @returns `true` if the metadata satisfies the filter.\n * @throws when the filter (or a nested value) is a raw expression, which the in-memory evaluator\n * cannot interpret.\n */\nexport const evaluateFilter = (filter: VectorFilter, metadata: VectorMetadata): boolean => {\n if (isRawFilter(filter)) {\n throw new Error('raw filters are not evaluable by the in-memory filter evaluator')\n }\n\n if (isFilterCondition(filter)) {\n const { field, op, value } = filter\n const fieldVal = getField(metadata, field)\n\n if (isRawExpr(value)) {\n throw new Error('raw expressions are not evaluable by the in-memory filter evaluator')\n }\n\n switch (op) {\n case 'eq': {\n return fieldVal === value\n }\n\n case 'ne': {\n return fieldVal !== value\n }\n\n case 'gt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal > value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal > value\n }\n return false\n }\n\n case 'gte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal >= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal >= value\n }\n return false\n }\n\n case 'lt': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal < value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal < value\n }\n return false\n }\n\n case 'lte': {\n if (fieldVal === undefined || value === undefined) {\n return false\n }\n if (typeof fieldVal === 'number' && typeof value === 'number') {\n return fieldVal <= value\n }\n if (typeof fieldVal === 'string' && typeof value === 'string') {\n return fieldVal <= value\n }\n return false\n }\n\n case 'in': {\n if (!Array.isArray(value)) {\n return false\n }\n return value.includes(fieldVal as never)\n }\n\n case 'nin': {\n if (!Array.isArray(value)) {\n return true\n }\n return !value.includes(fieldVal as never)\n }\n\n case 'exists': {\n const checkExists = value === undefined || value === true\n return checkExists ? fieldVal !== undefined : fieldVal === undefined\n }\n\n case 'contains': {\n if (fieldVal === undefined) {\n return false\n }\n if (Array.isArray(fieldVal)) {\n return fieldVal.includes(value as never)\n }\n if (typeof fieldVal === 'string') {\n return fieldVal.includes(String(value))\n }\n return false\n }\n\n default: {\n return false\n }\n }\n }\n\n if (isFilterGroup(filter)) {\n const { and, or, not } = filter\n\n if (and !== undefined) {\n return and.every((child) => evaluateFilter(child, metadata))\n }\n\n if (or !== undefined) {\n return or.some((child) => evaluateFilter(child, metadata))\n }\n\n if (not !== undefined) {\n return !evaluateFilter(not, metadata)\n }\n\n return true\n }\n\n return false\n}\n"],"mappings":"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"}
@@ -1,7 +1,17 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  require("../../chunk-Ble4zEEl.js");
3
3
  //#region src/batteries/vector/helpers.ts
4
+ /** Clamp `n` into the inclusive `[0, 1]` range. */
4
5
  var clamp01 = (n) => Math.min(1, Math.max(0, n));
6
+ /**
7
+ * Normalize a backend's raw score into a `[0, 1]` similarity where higher is closer, accounting for
8
+ * the distance metric and whether the raw value is a similarity or a distance.
9
+ *
10
+ * @param raw - The backend's raw score.
11
+ * @param metric - The distance metric the score was computed under.
12
+ * @param kind - Whether `raw` is a similarity or a distance.
13
+ * @returns The normalized similarity in `[0, 1]`.
14
+ */
5
15
  var normalizeScore = (raw, metric, kind) => {
6
16
  if (metric === "cosine") if (kind === "similarity") return clamp01((raw + 1) / 2);
7
17
  else return clamp01((1 - raw + 1) / 2);
@@ -10,8 +20,11 @@ var normalizeScore = (raw, metric, kind) => {
10
20
  else if (metric === "euclidean") return clamp01(1 / (1 + Math.max(0, raw)));
11
21
  else return clamp01(raw);
12
22
  };
23
+ /** Look up the adapter-specific value for `metric` in a complete metric→value map. */
13
24
  var mapMetric = (metric, map) => map[metric];
25
+ /** `true` if `vector`'s length matches `expected` (or `expected` is undefined). */
14
26
  var dimensionsMatch = (vector, expected) => expected === void 0 ? true : vector.length === expected;
27
+ /** `true` if `vector` is an array of finite numbers (no NaN/Infinity). */
15
28
  var isFiniteVector = (vector) => Array.isArray(vector) && vector.every((n) => typeof n === "number" && Number.isFinite(n));
16
29
  //#endregion
17
30
  exports.clamp01 = clamp01;
@@ -1 +1 @@
1
- {"version":3,"file":"helpers.cjs","names":[],"sources":["../../../src/batteries/vector/helpers.ts"],"sourcesContent":["/**\n * Helper utilities for the vector storage provider battery.\n *\n * @module @nhtio/adk/batteries/vector/helpers\n */\n\nimport type { DistanceMetric } from './types'\n\nexport type ScoreKind = 'similarity' | 'distance'\n\nexport const clamp01 = (n: number): number => Math.min(1, Math.max(0, n))\n\nexport const normalizeScore = (raw: number, metric: DistanceMetric, kind: ScoreKind): number => {\n if (metric === 'cosine') {\n if (kind === 'similarity') {\n return clamp01((raw + 1) / 2)\n } else {\n const sim = 1 - raw\n return clamp01((sim + 1) / 2)\n }\n } else if (metric === 'dot') {\n if (kind === 'similarity') {\n return clamp01(1 / (1 + Math.exp(-raw)))\n } else {\n return clamp01(1 / (1 + Math.exp(raw)))\n }\n } else if (metric === 'euclidean') {\n const d = Math.max(0, raw)\n return clamp01(1 / (1 + d))\n } else {\n return clamp01(raw)\n }\n}\n\nexport const mapMetric = <T>(metric: DistanceMetric, map: Record<DistanceMetric, T>): T =>\n map[metric]\n\nexport const dimensionsMatch = (vector: number[], expected: number | undefined): boolean =>\n expected === undefined ? true : vector.length === expected\n\nexport const isFiniteVector = (vector: number[]): boolean =>\n Array.isArray(vector) && vector.every((n) => typeof n === 'number' && Number.isFinite(n))\n"],"mappings":";;;AAUA,IAAa,WAAW,MAAsB,KAAK,IAAI,GAAG,KAAK,IAAI,GAAG,CAAC,CAAC;AAExE,IAAa,kBAAkB,KAAa,QAAwB,SAA4B;CAC9F,IAAI,WAAW,UACb,IAAI,SAAS,cACX,OAAO,SAAS,MAAM,KAAK,CAAC;MAG5B,OAAO,SADK,IAAI,MACM,KAAK,CAAC;MAEzB,IAAI,WAAW,OACpB,IAAI,SAAS,cACX,OAAO,QAAQ,KAAK,IAAI,KAAK,IAAI,CAAC,GAAG,EAAE;MAEvC,OAAO,QAAQ,KAAK,IAAI,KAAK,IAAI,GAAG,EAAE;MAEnC,IAAI,WAAW,aAEpB,OAAO,QAAQ,KAAK,IADV,KAAK,IAAI,GAAG,GACE,EAAE;MAE1B,OAAO,QAAQ,GAAG;AAEtB;AAEA,IAAa,aAAgB,QAAwB,QACnD,IAAI;AAEN,IAAa,mBAAmB,QAAkB,aAChD,aAAa,KAAA,IAAY,OAAO,OAAO,WAAW;AAEpD,IAAa,kBAAkB,WAC7B,MAAM,QAAQ,MAAM,KAAK,OAAO,OAAO,MAAM,OAAO,MAAM,YAAY,OAAO,SAAS,CAAC,CAAC"}
1
+ {"version":3,"file":"helpers.cjs","names":[],"sources":["../../../src/batteries/vector/helpers.ts"],"sourcesContent":["/**\n * Helper utilities for the vector storage provider battery.\n *\n * @module @nhtio/adk/batteries/vector/helpers\n */\n\nimport type { DistanceMetric } from './types'\n\n/** Whether a raw backend score is a similarity (higher = closer) or a distance (lower = closer). */\nexport type ScoreKind = 'similarity' | 'distance'\n\n/** Clamp `n` into the inclusive `[0, 1]` range. */\nexport const clamp01 = (n: number): number => Math.min(1, Math.max(0, n))\n\n/**\n * Normalize a backend's raw score into a `[0, 1]` similarity where higher is closer, accounting for\n * the distance metric and whether the raw value is a similarity or a distance.\n *\n * @param raw - The backend's raw score.\n * @param metric - The distance metric the score was computed under.\n * @param kind - Whether `raw` is a similarity or a distance.\n * @returns The normalized similarity in `[0, 1]`.\n */\nexport const normalizeScore = (raw: number, metric: DistanceMetric, kind: ScoreKind): number => {\n if (metric === 'cosine') {\n if (kind === 'similarity') {\n return clamp01((raw + 1) / 2)\n } else {\n const sim = 1 - raw\n return clamp01((sim + 1) / 2)\n }\n } else if (metric === 'dot') {\n if (kind === 'similarity') {\n return clamp01(1 / (1 + Math.exp(-raw)))\n } else {\n return clamp01(1 / (1 + Math.exp(raw)))\n }\n } else if (metric === 'euclidean') {\n const d = Math.max(0, raw)\n return clamp01(1 / (1 + d))\n } else {\n return clamp01(raw)\n }\n}\n\n/** Look up the adapter-specific value for `metric` in a complete metric→value map. */\nexport const mapMetric = <T>(metric: DistanceMetric, map: Record<DistanceMetric, T>): T =>\n map[metric]\n\n/** `true` if `vector`'s length matches `expected` (or `expected` is undefined). */\nexport const dimensionsMatch = (vector: number[], expected: number | undefined): boolean =>\n expected === undefined ? true : vector.length === expected\n\n/** `true` if `vector` is an array of finite numbers (no NaN/Infinity). */\nexport const isFiniteVector = (vector: number[]): boolean =>\n Array.isArray(vector) && vector.every((n) => typeof n === 'number' && Number.isFinite(n))\n"],"mappings":";;;;AAYA,IAAa,WAAW,MAAsB,KAAK,IAAI,GAAG,KAAK,IAAI,GAAG,CAAC,CAAC;;;;;;;;;;AAWxE,IAAa,kBAAkB,KAAa,QAAwB,SAA4B;CAC9F,IAAI,WAAW,UACb,IAAI,SAAS,cACX,OAAO,SAAS,MAAM,KAAK,CAAC;MAG5B,OAAO,SADK,IAAI,MACM,KAAK,CAAC;MAEzB,IAAI,WAAW,OACpB,IAAI,SAAS,cACX,OAAO,QAAQ,KAAK,IAAI,KAAK,IAAI,CAAC,GAAG,EAAE;MAEvC,OAAO,QAAQ,KAAK,IAAI,KAAK,IAAI,GAAG,EAAE;MAEnC,IAAI,WAAW,aAEpB,OAAO,QAAQ,KAAK,IADV,KAAK,IAAI,GAAG,GACE,EAAE;MAE1B,OAAO,QAAQ,GAAG;AAEtB;;AAGA,IAAa,aAAgB,QAAwB,QACnD,IAAI;;AAGN,IAAa,mBAAmB,QAAkB,aAChD,aAAa,KAAA,IAAY,OAAO,OAAO,WAAW;;AAGpD,IAAa,kBAAkB,WAC7B,MAAM,QAAQ,MAAM,KAAK,OAAO,OAAO,MAAM,OAAO,MAAM,YAAY,OAAO,SAAS,CAAC,CAAC"}
@@ -4,9 +4,23 @@
4
4
  * @module @nhtio/adk/batteries/vector/helpers
5
5
  */
6
6
  import type { DistanceMetric } from "./types";
7
+ /** Whether a raw backend score is a similarity (higher = closer) or a distance (lower = closer). */
7
8
  export type ScoreKind = 'similarity' | 'distance';
9
+ /** Clamp `n` into the inclusive `[0, 1]` range. */
8
10
  export declare const clamp01: (n: number) => number;
11
+ /**
12
+ * Normalize a backend's raw score into a `[0, 1]` similarity where higher is closer, accounting for
13
+ * the distance metric and whether the raw value is a similarity or a distance.
14
+ *
15
+ * @param raw - The backend's raw score.
16
+ * @param metric - The distance metric the score was computed under.
17
+ * @param kind - Whether `raw` is a similarity or a distance.
18
+ * @returns The normalized similarity in `[0, 1]`.
19
+ */
9
20
  export declare const normalizeScore: (raw: number, metric: DistanceMetric, kind: ScoreKind) => number;
21
+ /** Look up the adapter-specific value for `metric` in a complete metric→value map. */
10
22
  export declare const mapMetric: <T>(metric: DistanceMetric, map: Record<DistanceMetric, T>) => T;
23
+ /** `true` if `vector`'s length matches `expected` (or `expected` is undefined). */
11
24
  export declare const dimensionsMatch: (vector: number[], expected: number | undefined) => boolean;
25
+ /** `true` if `vector` is an array of finite numbers (no NaN/Infinity). */
12
26
  export declare const isFiniteVector: (vector: number[]) => boolean;