enya-agent 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (389) hide show
  1. package/.env.example +20 -0
  2. package/.github/workflows/ci.yml +70 -0
  3. package/.github/workflows/publish.yml +250 -0
  4. package/.gitmodules +3 -0
  5. package/Cargo.lock +3584 -0
  6. package/Cargo.toml +97 -0
  7. package/crates/enact/Cargo.toml +27 -0
  8. package/crates/enact/src/lib.rs +60 -0
  9. package/crates/enact-a2a/Cargo.toml +25 -0
  10. package/crates/enact-a2a/src/lib.rs +411 -0
  11. package/crates/enact-channels/Cargo.toml +64 -0
  12. package/crates/enact-channels/examples/README.md +80 -0
  13. package/crates/enact-channels/examples/channel_bot.rs +169 -0
  14. package/crates/enact-channels/examples/telegram-echo.rs +34 -0
  15. package/crates/enact-channels/examples/whatsapp-echo.rs +142 -0
  16. package/crates/enact-channels/src/config.rs +213 -0
  17. package/crates/enact-channels/src/lib.rs +25 -0
  18. package/crates/enact-channels/src/runtime.rs +237 -0
  19. package/crates/enact-channels/src/security/mod.rs +5 -0
  20. package/crates/enact-channels/src/security/pairing.rs +205 -0
  21. package/crates/enact-channels/src/teams.rs +601 -0
  22. package/crates/enact-channels/src/telegram.rs +2833 -0
  23. package/crates/enact-channels/src/traits.rs +200 -0
  24. package/crates/enact-channels/src/webhook.rs +262 -0
  25. package/crates/enact-channels/src/whatsapp.rs +310 -0
  26. package/crates/enact-cli/Cargo.toml +40 -0
  27. package/crates/enact-cli/src/commands/doctor.rs +62 -0
  28. package/crates/enact-cli/src/commands/mod.rs +3 -0
  29. package/crates/enact-cli/src/commands/run.rs +69 -0
  30. package/crates/enact-cli/src/commands/serve.rs +81 -0
  31. package/crates/enact-cli/src/config.rs +2 -0
  32. package/crates/enact-cli/src/main.rs +79 -0
  33. package/crates/enact-config/Cargo.toml +36 -0
  34. package/crates/enact-config/ENV_VAR_MAPPING.md +135 -0
  35. package/crates/enact-config/QUICK_REFERENCE.md +92 -0
  36. package/crates/enact-config/README.md +107 -0
  37. package/crates/enact-config/TESTING.md +161 -0
  38. package/crates/enact-config/examples/test-env-vars.rs +100 -0
  39. package/crates/enact-config/src/config.rs +399 -0
  40. package/crates/enact-config/src/encrypted_store.rs +211 -0
  41. package/crates/enact-config/src/lib.rs +298 -0
  42. package/crates/enact-config/src/secrets.rs +149 -0
  43. package/crates/enact-config/src/sync.rs +260 -0
  44. package/crates/enact-config/test-env-vars.sh +34 -0
  45. package/crates/enact-config/tests/README.md +99 -0
  46. package/crates/enact-config/tests/config_integration_test.rs +202 -0
  47. package/crates/enact-config/tests/security_test.rs +140 -0
  48. package/crates/enact-context/Cargo.toml +41 -0
  49. package/crates/enact-context/src/budget.rs +314 -0
  50. package/crates/enact-context/src/calibrator.rs +535 -0
  51. package/crates/enact-context/src/compactor.rs +392 -0
  52. package/crates/enact-context/src/condenser.rs +826 -0
  53. package/crates/enact-context/src/lib.rs +94 -0
  54. package/crates/enact-context/src/segment.rs +238 -0
  55. package/crates/enact-context/src/step_context.rs +645 -0
  56. package/crates/enact-context/src/token_counter.rs +148 -0
  57. package/crates/enact-context/src/window.rs +372 -0
  58. package/crates/enact-core/Cargo.toml +42 -0
  59. package/crates/enact-core/README.md +98 -0
  60. package/crates/enact-core/src/background/executor.rs +524 -0
  61. package/crates/enact-core/src/background/mod.rs +48 -0
  62. package/crates/enact-core/src/background/target_binding.rs +390 -0
  63. package/crates/enact-core/src/background/trigger.rs +511 -0
  64. package/crates/enact-core/src/callable/callable.rs +152 -0
  65. package/crates/enact-core/src/callable/composite.rs +817 -0
  66. package/crates/enact-core/src/callable/graph.rs +104 -0
  67. package/crates/enact-core/src/callable/llm.rs +211 -0
  68. package/crates/enact-core/src/callable/mod.rs +64 -0
  69. package/crates/enact-core/src/callable/registry.rs +206 -0
  70. package/crates/enact-core/src/context/execution_context.rs +757 -0
  71. package/crates/enact-core/src/context/invocation.rs +99 -0
  72. package/crates/enact-core/src/context/mod.rs +50 -0
  73. package/crates/enact-core/src/context/tenant.rs +175 -0
  74. package/crates/enact-core/src/context/trace.rs +127 -0
  75. package/crates/enact-core/src/flow/conditional.rs +293 -0
  76. package/crates/enact-core/src/flow/mod.rs +43 -0
  77. package/crates/enact-core/src/flow/parallel.rs +437 -0
  78. package/crates/enact-core/src/flow/repeat.rs +534 -0
  79. package/crates/enact-core/src/flow/sequential.rs +248 -0
  80. package/crates/enact-core/src/graph/checkpoint.rs +79 -0
  81. package/crates/enact-core/src/graph/checkpoint_store.rs +76 -0
  82. package/crates/enact-core/src/graph/compiled.rs +189 -0
  83. package/crates/enact-core/src/graph/edge.rs +59 -0
  84. package/crates/enact-core/src/graph/graph_schema.rs +218 -0
  85. package/crates/enact-core/src/graph/loader.rs +155 -0
  86. package/crates/enact-core/src/graph/mod.rs +18 -0
  87. package/crates/enact-core/src/graph/node/function.rs +49 -0
  88. package/crates/enact-core/src/graph/node/mod.rs +48 -0
  89. package/crates/enact-core/src/graph/schema.rs +62 -0
  90. package/crates/enact-core/src/inbox/message.rs +405 -0
  91. package/crates/enact-core/src/inbox/mod.rs +31 -0
  92. package/crates/enact-core/src/inbox/store.rs +355 -0
  93. package/crates/enact-core/src/kernel/artifact/filesystem.rs +546 -0
  94. package/crates/enact-core/src/kernel/artifact/metadata.rs +283 -0
  95. package/crates/enact-core/src/kernel/artifact/mod.rs +27 -0
  96. package/crates/enact-core/src/kernel/artifact/store.rs +427 -0
  97. package/crates/enact-core/src/kernel/enforcement.rs +1315 -0
  98. package/crates/enact-core/src/kernel/error.rs +1200 -0
  99. package/crates/enact-core/src/kernel/event.rs +1394 -0
  100. package/crates/enact-core/src/kernel/execution_model.rs +831 -0
  101. package/crates/enact-core/src/kernel/execution_state.rs +189 -0
  102. package/crates/enact-core/src/kernel/execution_strategy.rs +117 -0
  103. package/crates/enact-core/src/kernel/ids.rs +2086 -0
  104. package/crates/enact-core/src/kernel/interrupt.rs +125 -0
  105. package/crates/enact-core/src/kernel/kernel.rs +1283 -0
  106. package/crates/enact-core/src/kernel/mod.rs +205 -0
  107. package/crates/enact-core/src/kernel/persistence/event_store.rs +270 -0
  108. package/crates/enact-core/src/kernel/persistence/message_store.rs +908 -0
  109. package/crates/enact-core/src/kernel/persistence/mod.rs +102 -0
  110. package/crates/enact-core/src/kernel/persistence/state_store.rs +228 -0
  111. package/crates/enact-core/src/kernel/persistence/vector_store.rs +299 -0
  112. package/crates/enact-core/src/kernel/reducer.rs +808 -0
  113. package/crates/enact-core/src/kernel/replay.rs +153 -0
  114. package/crates/enact-core/src/lib.rs +413 -0
  115. package/crates/enact-core/src/memory/episodic.rs +0 -0
  116. package/crates/enact-core/src/memory/mod.rs +6 -0
  117. package/crates/enact-core/src/memory/semantic.rs +0 -0
  118. package/crates/enact-core/src/memory/trait.rs +0 -0
  119. package/crates/enact-core/src/memory/vector_db.rs +0 -0
  120. package/crates/enact-core/src/memory/working.rs +0 -0
  121. package/crates/enact-core/src/policy/execution_policy.rs +292 -0
  122. package/crates/enact-core/src/policy/filters.rs +458 -0
  123. package/crates/enact-core/src/policy/input_processor.rs +407 -0
  124. package/crates/enact-core/src/policy/long_running.rs +134 -0
  125. package/crates/enact-core/src/policy/mod.rs +193 -0
  126. package/crates/enact-core/src/policy/pii_input.rs +274 -0
  127. package/crates/enact-core/src/policy/tenant_policy.rs +453 -0
  128. package/crates/enact-core/src/policy/tool_policy.rs +407 -0
  129. package/crates/enact-core/src/providers/mod.rs +63 -0
  130. package/crates/enact-core/src/providers/trait.rs +292 -0
  131. package/crates/enact-core/src/runner/callbacks.rs +6 -0
  132. package/crates/enact-core/src/runner/execution_runner.rs +476 -0
  133. package/crates/enact-core/src/runner/loop.rs +117 -0
  134. package/crates/enact-core/src/runner/mod.rs +58 -0
  135. package/crates/enact-core/src/runner/protected_runner.rs +280 -0
  136. package/crates/enact-core/src/signal/inmemory.rs +231 -0
  137. package/crates/enact-core/src/signal/mod.rs +108 -0
  138. package/crates/enact-core/src/streaming/event_logger.rs +195 -0
  139. package/crates/enact-core/src/streaming/event_stream.rs +1423 -0
  140. package/crates/enact-core/src/streaming/mod.rs +108 -0
  141. package/crates/enact-core/src/streaming/pause_cancel.rs +0 -0
  142. package/crates/enact-core/src/streaming/protected_emitter.rs +173 -0
  143. package/crates/enact-core/src/streaming/protection/context.rs +136 -0
  144. package/crates/enact-core/src/streaming/protection/encryption.rs +289 -0
  145. package/crates/enact-core/src/streaming/protection/mod.rs +43 -0
  146. package/crates/enact-core/src/streaming/protection/pii_protection.rs +243 -0
  147. package/crates/enact-core/src/streaming/protection/processor.rs +166 -0
  148. package/crates/enact-core/src/streaming/sse.rs +0 -0
  149. package/crates/enact-core/src/telemetry/exporter.rs +0 -0
  150. package/crates/enact-core/src/telemetry/init.rs +0 -0
  151. package/crates/enact-core/src/telemetry/mod.rs +49 -0
  152. package/crates/enact-core/src/telemetry/spans.rs +245 -0
  153. package/crates/enact-core/src/tool/agent_tool.rs +177 -0
  154. package/crates/enact-core/src/tool/browser/mod.rs +0 -0
  155. package/crates/enact-core/src/tool/browser/webdriver.rs +0 -0
  156. package/crates/enact-core/src/tool/cost.rs +247 -0
  157. package/crates/enact-core/src/tool/discovery.rs +0 -0
  158. package/crates/enact-core/src/tool/dispatcher.rs +347 -0
  159. package/crates/enact-core/src/tool/filesystem.rs +231 -0
  160. package/crates/enact-core/src/tool/function.rs +99 -0
  161. package/crates/enact-core/src/tool/git.rs +162 -0
  162. package/crates/enact-core/src/tool/http.rs +214 -0
  163. package/crates/enact-core/src/tool/mcp/client.rs +0 -0
  164. package/crates/enact-core/src/tool/mcp/mod.rs +0 -0
  165. package/crates/enact-core/src/tool/mod.rs +51 -0
  166. package/crates/enact-core/src/tool/reasoning/debugging.rs +0 -0
  167. package/crates/enact-core/src/tool/reasoning/mcts.rs +0 -0
  168. package/crates/enact-core/src/tool/reasoning/mod.rs +0 -0
  169. package/crates/enact-core/src/tool/reasoning/sequential.rs +0 -0
  170. package/crates/enact-core/src/tool/sandbox/dagger.rs +0 -0
  171. package/crates/enact-core/src/tool/sandbox/mod.rs +0 -0
  172. package/crates/enact-core/src/tool/shell.rs +147 -0
  173. package/crates/enact-core/src/tool/trait.rs +33 -0
  174. package/crates/enact-core/src/tool/web_search.rs +277 -0
  175. package/crates/enact-core/src/util/config.rs +0 -0
  176. package/crates/enact-core/src/util/errors.rs +0 -0
  177. package/crates/enact-core/src/util/mod.rs +6 -0
  178. package/crates/enact-core/tests/airgapped_e2e_test.rs +291 -0
  179. package/crates/enact-core/tests/e2e_agentic_loop.rs +119 -0
  180. package/crates/enact-core/tests/e2e_test.rs +259 -0
  181. package/crates/enact-core/tests/graph_test.rs +130 -0
  182. package/crates/enact-core/tests/stream_event_id_validation.rs +435 -0
  183. package/crates/enact-cron/Cargo.toml +28 -0
  184. package/crates/enact-cron/src/lib.rs +44 -0
  185. package/crates/enact-cron/src/schedule.rs +156 -0
  186. package/crates/enact-cron/src/store.rs +589 -0
  187. package/crates/enact-cron/src/types.rs +148 -0
  188. package/crates/enact-gateway/Cargo.toml +31 -0
  189. package/crates/enact-gateway/README.md +30 -0
  190. package/crates/enact-gateway/examples/whatsapp-gateway-runner-mock.rs +59 -0
  191. package/crates/enact-gateway/examples/whatsapp-gateway.rs +42 -0
  192. package/crates/enact-gateway/src/lib.rs +582 -0
  193. package/crates/enact-mcp/Cargo.toml +24 -0
  194. package/crates/enact-mcp/src/lib.rs +178 -0
  195. package/crates/enact-memory/Cargo.toml +25 -0
  196. package/crates/enact-memory/src/backend.rs +20 -0
  197. package/crates/enact-memory/src/chunker.rs +230 -0
  198. package/crates/enact-memory/src/embeddings.rs +221 -0
  199. package/crates/enact-memory/src/lib.rs +67 -0
  200. package/crates/enact-memory/src/markdown.rs +127 -0
  201. package/crates/enact-memory/src/none.rs +61 -0
  202. package/crates/enact-memory/src/sqlite.rs +276 -0
  203. package/crates/enact-memory/src/traits.rs +65 -0
  204. package/crates/enact-memory/src/vector.rs +198 -0
  205. package/crates/enact-oauth/Cargo.toml +27 -0
  206. package/crates/enact-oauth/src/lib.rs +584 -0
  207. package/crates/enact-observability/Cargo.toml +22 -0
  208. package/crates/enact-observability/src/lib.rs +197 -0
  209. package/crates/enact-providers/Cargo.toml +33 -0
  210. package/crates/enact-providers/examples/hello-agent.rs +33 -0
  211. package/crates/enact-providers/src/anthropic.rs +182 -0
  212. package/crates/enact-providers/src/azure.rs +96 -0
  213. package/crates/enact-providers/src/bridge.rs +221 -0
  214. package/crates/enact-providers/src/gemini.rs +227 -0
  215. package/crates/enact-providers/src/http.rs +78 -0
  216. package/crates/enact-providers/src/lib.rs +53 -0
  217. package/crates/enact-providers/src/openai_compatible.rs +167 -0
  218. package/crates/enact-providers/src/openrouter.rs +33 -0
  219. package/crates/enact-runner/Cargo.toml +24 -0
  220. package/crates/enact-runner/README.md +76 -0
  221. package/crates/enact-runner/src/compaction.rs +225 -0
  222. package/crates/enact-runner/src/config.rs +118 -0
  223. package/crates/enact-runner/src/lib.rs +63 -0
  224. package/crates/enact-runner/src/loop_driver.rs +414 -0
  225. package/crates/enact-runner/src/parser.rs +421 -0
  226. package/crates/enact-runner/src/retry.rs +262 -0
  227. package/crates/enact-runner/tests/integration.rs +278 -0
  228. package/crates/enact-security/Cargo.toml +22 -0
  229. package/crates/enact-security/src/audit.rs +375 -0
  230. package/crates/enact-security/src/lib.rs +37 -0
  231. package/crates/enact-security/src/policy.rs +406 -0
  232. package/crates/enact-skills/Cargo.toml +25 -0
  233. package/crates/enact-skills/src/lib.rs +506 -0
  234. package/crates/enact-tools/Cargo.toml +22 -0
  235. package/crates/enact-tools/src/file_read.rs +166 -0
  236. package/crates/enact-tools/src/file_write.rs +216 -0
  237. package/crates/enact-tools/src/git_operations.rs +513 -0
  238. package/crates/enact-tools/src/http_request.rs +417 -0
  239. package/crates/enact-tools/src/lib.rs +104 -0
  240. package/crates/enact-tools/src/security.rs +227 -0
  241. package/crates/enact-tools/src/shell.rs +191 -0
  242. package/crates/enact-tools/src/traits.rs +159 -0
  243. package/docs/Makefile +74 -0
  244. package/docs/config.toml +62 -0
  245. package/docs/content/_index.md +174 -0
  246. package/docs/content/a2a/_index.md +431 -0
  247. package/docs/content/api/_index.md +323 -0
  248. package/docs/content/channels/_index.md +160 -0
  249. package/docs/content/channels/teams.md +205 -0
  250. package/docs/content/channels/telegram.md +182 -0
  251. package/docs/content/channels/webhook.md +423 -0
  252. package/docs/content/channels/whatsapp.md +240 -0
  253. package/docs/content/cli/_index.md +261 -0
  254. package/docs/content/concepts/_index.md +273 -0
  255. package/docs/content/configuration/_index.md +241 -0
  256. package/docs/content/cron/_index.md +248 -0
  257. package/docs/content/developers/_index.md +278 -0
  258. package/docs/content/getting-started/_index.md +180 -0
  259. package/docs/content/installation/_index.md +186 -0
  260. package/docs/content/installation/uninstall.md +101 -0
  261. package/docs/content/installation/updating.md +120 -0
  262. package/docs/content/mcp/_index.md +215 -0
  263. package/docs/content/memory/_index.md +163 -0
  264. package/docs/content/oauth/_index.md +515 -0
  265. package/docs/content/providers/_index.md +206 -0
  266. package/docs/content/roadmap/_index.md +199 -0
  267. package/docs/content/security/_index.md +219 -0
  268. package/docs/content/skills/_index.md +228 -0
  269. package/docs/content/tools/_index.md +485 -0
  270. package/docs/content/troubleshooting/_index.md +259 -0
  271. package/docs/content/yaml-schema/_index.md +294 -0
  272. package/docs/static/giallo-dark.css +91 -0
  273. package/docs/static/giallo-light.css +91 -0
  274. package/docs/themes/tanuki/.github/workflows/deploy.yml +44 -0
  275. package/docs/themes/tanuki/LICENSE +21 -0
  276. package/docs/themes/tanuki/README.md +166 -0
  277. package/docs/themes/tanuki/examples/blog/config.toml +58 -0
  278. package/docs/themes/tanuki/examples/blog/content/_index.md +4 -0
  279. package/docs/themes/tanuki/examples/blog/content/about.md +33 -0
  280. package/docs/themes/tanuki/examples/blog/content/blog/_index.md +7 -0
  281. package/docs/themes/tanuki/examples/blog/content/blog/api-design-best-practices.md +245 -0
  282. package/docs/themes/tanuki/examples/blog/content/blog/building-accessible-websites.md +147 -0
  283. package/docs/themes/tanuki/examples/blog/content/blog/css-grid-vs-flexbox.md +165 -0
  284. package/docs/themes/tanuki/examples/blog/content/blog/customizing-catppuccin-colors.md +137 -0
  285. package/docs/themes/tanuki/examples/blog/content/blog/dark-mode-best-practices.md +82 -0
  286. package/docs/themes/tanuki/examples/blog/content/blog/docker-essentials.md +301 -0
  287. package/docs/themes/tanuki/examples/blog/content/blog/getting-started-with-zola.md +129 -0
  288. package/docs/themes/tanuki/examples/blog/content/blog/git-workflow-for-content.md +112 -0
  289. package/docs/themes/tanuki/examples/blog/content/blog/introduction-to-webassembly.md +183 -0
  290. package/docs/themes/tanuki/examples/blog/content/blog/modern-javascript-features.md +234 -0
  291. package/docs/themes/tanuki/examples/blog/content/blog/testing-strategies.md +311 -0
  292. package/docs/themes/tanuki/examples/blog/content/blog/typography-for-developers.md +104 -0
  293. package/docs/themes/tanuki/examples/blog/content/blog/welcome-to-tanuki.md +67 -0
  294. package/docs/themes/tanuki/examples/blog/content/blog/why-static-sites.md +85 -0
  295. package/docs/themes/tanuki/examples/blog/content/projects.md +64 -0
  296. package/docs/themes/tanuki/examples/book/config.toml +17 -0
  297. package/docs/themes/tanuki/examples/book/content/_index.md +12 -0
  298. package/docs/themes/tanuki/examples/book/content/chapter-1.md +90 -0
  299. package/docs/themes/tanuki/examples/book/content/chapter-2.md +143 -0
  300. package/docs/themes/tanuki/examples/book/content/chapter-3.md +217 -0
  301. package/docs/themes/tanuki/examples/book/content/chapter-4.md +224 -0
  302. package/docs/themes/tanuki/examples/book/content/chapter-5.md +297 -0
  303. package/docs/themes/tanuki/examples/book/content/print.md +6 -0
  304. package/docs/themes/tanuki/examples/docs/config.toml +28 -0
  305. package/docs/themes/tanuki/examples/docs/content/_index.md +20 -0
  306. package/docs/themes/tanuki/examples/docs/content/components.md +156 -0
  307. package/docs/themes/tanuki/examples/docs/content/configuration.md +94 -0
  308. package/docs/themes/tanuki/examples/docs/content/customization.md +202 -0
  309. package/docs/themes/tanuki/examples/docs/content/deployment.md +204 -0
  310. package/docs/themes/tanuki/examples/docs/content/installation.md +59 -0
  311. package/docs/themes/tanuki/examples/docs/content/print.md +6 -0
  312. package/docs/themes/tanuki/examples/docs/static/img/tanuki-icon.avif +0 -0
  313. package/docs/themes/tanuki/examples/index.html +2104 -0
  314. package/docs/themes/tanuki/mise.toml +108 -0
  315. package/docs/themes/tanuki/sass/base/_catppuccin.scss +164 -0
  316. package/docs/themes/tanuki/sass/base/_fonts.scss +64 -0
  317. package/docs/themes/tanuki/sass/base/_reset.scss +152 -0
  318. package/docs/themes/tanuki/sass/base/_typography.scss +523 -0
  319. package/docs/themes/tanuki/sass/components/_buttons.scss +209 -0
  320. package/docs/themes/tanuki/sass/components/_code.scss +457 -0
  321. package/docs/themes/tanuki/sass/components/_landing.scss +633 -0
  322. package/docs/themes/tanuki/sass/components/_layout.scss +294 -0
  323. package/docs/themes/tanuki/sass/components/_navigation.scss +1200 -0
  324. package/docs/themes/tanuki/sass/components/_print.scss +237 -0
  325. package/docs/themes/tanuki/sass/components/_search.scss +224 -0
  326. package/docs/themes/tanuki/sass/components/_sidebar.scss +473 -0
  327. package/docs/themes/tanuki/sass/components/_theme-toggle.scss +186 -0
  328. package/docs/themes/tanuki/sass/modes/_blog.scss +366 -0
  329. package/docs/themes/tanuki/sass/modes/_product.scss +875 -0
  330. package/docs/themes/tanuki/sass/modes/_raskell.scss +1696 -0
  331. package/docs/themes/tanuki/sass/patterns/_buttons.scss +183 -0
  332. package/docs/themes/tanuki/sass/patterns/_cards.scss +144 -0
  333. package/docs/themes/tanuki/sass/patterns/_index.scss +9 -0
  334. package/docs/themes/tanuki/sass/patterns/_lists.scss +259 -0
  335. package/docs/themes/tanuki/sass/patterns/_sections.scss +243 -0
  336. package/docs/themes/tanuki/sass/style.scss +47 -0
  337. package/docs/themes/tanuki/sass/tokens/_colors.scss +139 -0
  338. package/docs/themes/tanuki/sass/tokens/_spacing.scss +100 -0
  339. package/docs/themes/tanuki/sass/tokens/_typography.scss +186 -0
  340. package/docs/themes/tanuki/screenshot.png +0 -0
  341. package/docs/themes/tanuki/sentinel.kdl +59 -0
  342. package/docs/themes/tanuki/static/elasticlunr.min.js +10 -0
  343. package/docs/themes/tanuki/static/fonts/GEIST-LICENSE.txt +92 -0
  344. package/docs/themes/tanuki/static/fonts/Geist-Variable.woff2 +0 -0
  345. package/docs/themes/tanuki/static/fonts/GeistMono-Variable.woff2 +0 -0
  346. package/docs/themes/tanuki/static/img/tanuki-icon.avif +0 -0
  347. package/docs/themes/tanuki/static/img/tanuki-icon.png +0 -0
  348. package/docs/themes/tanuki/static/js/anchors.js +18 -0
  349. package/docs/themes/tanuki/static/js/app.js +274 -0
  350. package/docs/themes/tanuki/static/js/code.js +394 -0
  351. package/docs/themes/tanuki/static/js/navigation.js +778 -0
  352. package/docs/themes/tanuki/static/js/scroll-to-top.js +33 -0
  353. package/docs/themes/tanuki/static/js/search-raskell.js +240 -0
  354. package/docs/themes/tanuki/static/js/search.js +215 -0
  355. package/docs/themes/tanuki/static/js/theme.js +169 -0
  356. package/docs/themes/tanuki/static/syntax-dark.css +151 -0
  357. package/docs/themes/tanuki/static/syntax-light.css +151 -0
  358. package/docs/themes/tanuki/static/wasm/sentinel_playground_wasm.js +486 -0
  359. package/docs/themes/tanuki/static/wasm/sentinel_playground_wasm_bg.wasm +0 -0
  360. package/docs/themes/tanuki/templates/404.html +52 -0
  361. package/docs/themes/tanuki/templates/base.html +428 -0
  362. package/docs/themes/tanuki/templates/blog.html +66 -0
  363. package/docs/themes/tanuki/templates/home.html +108 -0
  364. package/docs/themes/tanuki/templates/index.html +178 -0
  365. package/docs/themes/tanuki/templates/landing.html +168 -0
  366. package/docs/themes/tanuki/templates/macros/nav.html +128 -0
  367. package/docs/themes/tanuki/templates/macros/posts.html +101 -0
  368. package/docs/themes/tanuki/templates/macros/ui.html +159 -0
  369. package/docs/themes/tanuki/templates/page.html +135 -0
  370. package/docs/themes/tanuki/templates/partials/footer.html +38 -0
  371. package/docs/themes/tanuki/templates/partials/header.html +366 -0
  372. package/docs/themes/tanuki/templates/partials/nav-buttons.html +55 -0
  373. package/docs/themes/tanuki/templates/partials/nav-overlay.html +81 -0
  374. package/docs/themes/tanuki/templates/partials/page-toc-panel.html +43 -0
  375. package/docs/themes/tanuki/templates/partials/search.html +52 -0
  376. package/docs/themes/tanuki/templates/partials/sidebar.html +107 -0
  377. package/docs/themes/tanuki/templates/partials/theme-toggle.html +35 -0
  378. package/docs/themes/tanuki/templates/partials/toc-overlay.html +146 -0
  379. package/docs/themes/tanuki/templates/partials/version-picker.html +38 -0
  380. package/docs/themes/tanuki/templates/print.html +244 -0
  381. package/docs/themes/tanuki/templates/section.html +186 -0
  382. package/docs/themes/tanuki/templates/taxonomy_list.html +18 -0
  383. package/docs/themes/tanuki/templates/taxonomy_single.html +31 -0
  384. package/docs/themes/tanuki/theme.toml +58 -0
  385. package/examples/hello-agent.rs +55 -0
  386. package/package.json +36 -0
  387. package/proto/config.proto +60 -0
  388. package/proto/events.proto +0 -0
  389. package/proto/runtime.proto +215 -0
@@ -0,0 +1,135 @@
1
+ # ENACT_* Environment Variable Mapping
2
+
3
+ This document maps common environment variables to their `ENACT_*` equivalents for use with the `enact-config` system.
4
+
5
+ ## Provider API Keys (Secrets)
6
+
7
+ These are stored as secrets and can be set via `ENACT_*` environment variables:
8
+
9
+ | Original Env Var | Config Key | ENACT_* Equivalent | Notes |
10
+ |-----------------|------------|-------------------|-------|
11
+ | `GOOGLE_GENERATIVE_AI_API_KEY` | `providers.google.apiKey` | `ENACT_PROVIDERS_GOOGLE_APIKEY` | Google AI API key |
12
+ | `OPENAI_API_KEY` | `providers.openai.apiKey` | `ENACT_PROVIDERS_OPENAI_APIKEY` | OpenAI API key |
13
+ | `AZURE_OPENAI_API_KEY` | `providers.azure.apiKey` | `ENACT_PROVIDERS_AZURE_APIKEY` | Azure OpenAI API key |
14
+ | `ANTHROPIC_API_KEY` | `providers.anthropic.apiKey` | `ENACT_PROVIDERS_ANTHROPIC_APIKEY` | Anthropic API key |
15
+
16
+ ## Provider Configuration (Settings)
17
+
18
+ These are stored as settings in the encrypted config file:
19
+
20
+ | Original Env Var | Config Key | ENACT_* Equivalent | Notes |
21
+ |-----------------|------------|-------------------|-------|
22
+ | `AZURE_OPENAI_API_ENDPOINT` | `providers.azure.endpoint` | `ENACT_PROVIDERS_AZURE_ENDPOINT` | Azure OpenAI endpoint URL |
23
+ | `AZURE_OPENAI_DEPLOYMENT` | `providers.azure.deployment_name` | `ENACT_PROVIDERS_AZURE_DEPLOYMENT_NAME` | Azure deployment name |
24
+ | `AZURE_OPENAI_API_VERSION` | `providers.azure.api_version` | `ENACT_PROVIDERS_AZURE_API_VERSION` | Azure API version (default: 2024-02-15-preview) |
25
+ | `OLLAMA_BASE_URL` | `providers.ollama.base_url` | `ENACT_PROVIDERS_OLLAMA_BASE_URL` | Ollama base URL (default: http://localhost:11434) |
26
+ | `OPENAI_BASE_URL` | `providers.openai.base_url` | `ENACT_PROVIDERS_OPENAI_BASE_URL` | OpenAI base URL (default: https://api.openai.com/v1) |
27
+ | `OPENAI_ORGANIZATION` | `providers.openai.organization` | `ENACT_PROVIDERS_OPENAI_ORGANIZATION` | OpenAI organization ID |
28
+ | `ANTHROPIC_BASE_URL` | `providers.anthropic.base_url` | `ENACT_PROVIDERS_ANTHROPIC_BASE_URL` | Anthropic base URL (default: https://api.anthropic.com) |
29
+ | `GOOGLE_BASE_URL` | `providers.google.base_url` | `ENACT_PROVIDERS_GOOGLE_BASE_URL` | Google base URL (default: https://generativelanguage.googleapis.com/v1) |
30
+
31
+ ## Complete Mapping from env.reference.bk
32
+
33
+ Based on your `env.reference.bk` file, here are the mappings for variables that can be used with `enact-config`:
34
+
35
+ ### Provider Secrets (API Keys)
36
+ ```bash
37
+ # Google AI
38
+ ENACT_PROVIDERS_GOOGLE_APIKEY=${GOOGLE_GENERATIVE_AI_API_KEY}
39
+
40
+ # OpenAI
41
+ ENACT_PROVIDERS_OPENAI_APIKEY=${OPENAI_API_KEY}
42
+
43
+ # Azure OpenAI
44
+ ENACT_PROVIDERS_AZURE_APIKEY=${AZURE_OPENAI_API_KEY}
45
+
46
+ # Anthropic (if you have ANTHROPIC_API_KEY)
47
+ ENACT_PROVIDERS_ANTHROPIC_APIKEY=${ANTHROPIC_API_KEY}
48
+ ```
49
+
50
+ ### Provider Settings
51
+ ```bash
52
+ # Azure OpenAI Configuration
53
+ ENACT_PROVIDERS_AZURE_ENDPOINT=${AZURE_OPENAI_API_ENDPOINT}
54
+ ENACT_PROVIDERS_AZURE_DEPLOYMENT_NAME=${AZURE_OPENAI_DEPLOYMENT}
55
+ ENACT_PROVIDERS_AZURE_API_VERSION=${AZURE_OPENAI_API_VERSION}
56
+
57
+ # Ollama
58
+ ENACT_PROVIDERS_OLLAMA_BASE_URL=${OLLAMA_BASE_URL}
59
+
60
+ # OpenAI (if custom base URL or organization)
61
+ ENACT_PROVIDERS_OPENAI_BASE_URL=${OPENAI_BASE_URL} # if set
62
+ ENACT_PROVIDERS_OPENAI_ORGANIZATION=${OPENAI_ORGANIZATION} # if set
63
+ ```
64
+
65
+ ## Example .env File for Development
66
+
67
+ Create a `.env` file with `ENACT_*` variables:
68
+
69
+ ```bash
70
+ # Provider API Keys (Secrets)
71
+ ENACT_PROVIDERS_GOOGLE_APIKEY=your-google-api-key
72
+ ENACT_PROVIDERS_OPENAI_APIKEY=your-openai-api-key
73
+ ENACT_PROVIDERS_AZURE_APIKEY=your-azure-api-key
74
+ ENACT_PROVIDERS_ANTHROPIC_APIKEY=your-anthropic-api-key
75
+
76
+ # Azure OpenAI Configuration
77
+ ENACT_PROVIDERS_AZURE_ENDPOINT=https://your-resource.openai.azure.com
78
+ ENACT_PROVIDERS_AZURE_DEPLOYMENT_NAME=gpt-4o
79
+ ENACT_PROVIDERS_AZURE_API_VERSION=2024-02-15-preview
80
+
81
+ # Ollama (Local LLM)
82
+ ENACT_PROVIDERS_OLLAMA_BASE_URL=http://localhost:11434
83
+ ```
84
+
85
+ ## Variables NOT Supported by enact-config
86
+
87
+ The following variables from your `env.reference.bk` are **NOT** handled by `enact-config` and should be set as regular environment variables:
88
+
89
+ - Database/Storage: `POSTGRES_URL`, `POSTGRES_USER`, `POSTGRES_PASSWORD`, `REDIS_URL`, etc.
90
+ - Auth: `BETTER_AUTH_SECRET`, `BETTER_AUTH_URL`, `MICROSOFT_CLIENT_ID`, etc.
91
+ - Application-specific: `NODE_ENV`, `VITE_API_URL`, `TAURI_DEV_URL`, etc.
92
+ - Logging: `LOG_LEVEL`, `LOG_FILE_DIR`, etc.
93
+ - Tools: `TAVILY_API_KEY`, `FIRECRAWL_API_KEY`, `QDRANT_API_KEY`, etc.
94
+ - Other services: `NEO4J_URI`, `MINIO_ENDPOINT`, `LANGFUSE_SECRET_KEY`, etc.
95
+
96
+ These should continue to be set as regular environment variables (without the `ENACT_` prefix) as they're used by other parts of your application.
97
+
98
+ ## Usage
99
+
100
+ ### Option 1: Set in .env file
101
+ ```bash
102
+ # Create .env file
103
+ cat > .env << EOF
104
+ ENACT_PROVIDERS_AZURE_APIKEY=your-key-here
105
+ ENACT_PROVIDERS_AZURE_ENDPOINT=https://your-resource.openai.azure.com
106
+ EOF
107
+
108
+ # Load with dotenvy (if using)
109
+ dotenvy::dotenv().ok();
110
+ ```
111
+
112
+ ### Option 2: Set as system environment variables
113
+ ```bash
114
+ export ENACT_PROVIDERS_AZURE_APIKEY=your-key-here
115
+ export ENACT_PROVIDERS_AZURE_ENDPOINT=https://your-resource.openai.azure.com
116
+ ```
117
+
118
+ ### Option 3: Set in shell session
119
+ ```bash
120
+ ENACT_PROVIDERS_AZURE_APIKEY=your-key-here cargo run
121
+ ```
122
+
123
+ ## Key Conversion Rules
124
+
125
+ The conversion from config key to environment variable name follows these rules:
126
+
127
+ 1. **Convert to uppercase**: `providers` → `PROVIDERS`
128
+ 2. **Replace dots with underscores**: `azure.apiKey` → `AZURE_APIKEY`
129
+ 3. **Prefix with `ENACT_`**: `PROVIDERS_AZURE_APIKEY` → `ENACT_PROVIDERS_AZURE_APIKEY`
130
+
131
+ Examples:
132
+ - `providers.azure.apiKey` → `ENACT_PROVIDERS_AZURE_APIKEY`
133
+ - `providers.azure.deployment_name` → `ENACT_PROVIDERS_AZURE_DEPLOYMENT_NAME`
134
+ - `providers.openai.organization` → `ENACT_PROVIDERS_OPENAI_ORGANIZATION`
135
+
@@ -0,0 +1,92 @@
1
+ # Quick Reference: ENACT_* Environment Variables
2
+
3
+ ## Provider API Keys (Secrets) - Use ENACT_* prefix
4
+
5
+ | Your .env Variable | ENACT_* Equivalent |
6
+ |-------------------|-------------------|
7
+ | `GOOGLE_GENERATIVE_AI_API_KEY` | `ENACT_PROVIDERS_GOOGLE_APIKEY` |
8
+ | `OPENAI_API_KEY` | `ENACT_PROVIDERS_OPENAI_APIKEY` |
9
+ | `AZURE_OPENAI_API_KEY` | `ENACT_PROVIDERS_AZURE_APIKEY` |
10
+ | `OPENROUTER_API_KEY` | *(Not directly supported - use OpenAI provider)* |
11
+
12
+ ## Provider Configuration - Use ENACT_* prefix
13
+
14
+ | Your .env Variable | ENACT_* Equivalent |
15
+ |-------------------|-------------------|
16
+ | `AZURE_OPENAI_API_ENDPOINT` | `ENACT_PROVIDERS_AZURE_ENDPOINT` |
17
+ | `AZURE_OPENAI_API_VERSION` | `ENACT_PROVIDERS_AZURE_API_VERSION` |
18
+ | `AZURE_OPENAI_DEPLOYMENT` | `ENACT_PROVIDERS_AZURE_DEPLOYMENT_NAME` |
19
+ | `OLLAMA_BASE_URL` | `ENACT_PROVIDERS_OLLAMA_BASE_URL` |
20
+
21
+ ## Variables NOT in enact-config (keep as-is)
22
+
23
+ These variables should remain as regular environment variables (no ENACT_ prefix):
24
+ - `NODE_ENV`
25
+ - `POSTGRES_URL`, `POSTGRES_USER`, `POSTGRES_PASSWORD`
26
+ - `REDIS_URL`, `REDIS_PASSWORD`, `REDIS_USER`
27
+ - `BETTER_AUTH_SECRET`, `BETTER_AUTH_URL`, `BETTER_AUTH_TRUSTED_ORIGINS`
28
+ - `MICROSOFT_CLIENT_ID`, `MICROSOFT_TENANT_ID`
29
+ - `DISABLE_EMAIL_SIGN_IN`, `DISABLE_SIGN_UP`
30
+ - `NOT_ALLOW_ADD_MCP_SERVERS`
31
+ - `BYPASS_AUTH`
32
+ - `FILE_STORAGE_TYPE`, `AZURE_STORAGE_CONTAINER_NAME`, `AZURE_STORAGE_CONNECTION_STRING`
33
+ - `LOG_LEVEL`, `LOG_FILE_DIR`, `LOG_FILE_NAME`, etc.
34
+ - `TAVILY_API_KEY`, `FIRECRAWL_API_KEY`
35
+ - `WEB_SEARCH_PROVIDER_PREFERENCE`
36
+ - `MEM0_CONFIG_FILE`, `MEM0_ENABLED`, `MEM0_VECTOR_STORE_PROVIDER`
37
+ - `MINIO_*` variables
38
+ - `LANGFUSE_*` variables
39
+ - `NEO4J_*` variables
40
+ - `AZURE_DOCUMENT_INTELLIGENCE_*` variables
41
+ - `AZURE_AI_SERVICE_*`, `AZURE_STT_*`, `AZURE_TTS_*`, `AZURE_SPEECH_*` variables
42
+ - `QDRANT_*` variables
43
+ - `FORCE_COLOR`
44
+ - `MOCK_OPENAI`
45
+ - `ENABLE_STREAM_LOGGING`, `VERBOSE_STREAM_LOGGING`
46
+ - `ENABLE_FILE_TRACES`
47
+ - `VITE_API_URL`
48
+ - `USE_DOCKER_EXECUTOR`
49
+ - `AI_SDK_LOG_WARNINGS`
50
+ - `TAURI_*` variables
51
+ - `NEXT_PUBLIC_*` variables
52
+ - `E2E_DEFAULT_MODEL`
53
+ - `ENABLE_REAL_LLM_E2E`
54
+ - `ENABLE_GRAPHRAG`
55
+
56
+ ## Example Migration
57
+
58
+ ### Before (.env):
59
+ ```bash
60
+ GOOGLE_GENERATIVE_AI_API_KEY=****
61
+ OPENAI_API_KEY=****
62
+ AZURE_OPENAI_API_KEY=****
63
+ AZURE_OPENAI_API_ENDPOINT=https://conf-foundry.openai.azure.com/openai/deployments/
64
+ AZURE_OPENAI_API_VERSION=2024-02-15-preview
65
+ AZURE_OPENAI_DEPLOYMENT=gpt-4.1-nano
66
+ OLLAMA_BASE_URL=http://localhost:11434/api
67
+ ```
68
+
69
+ ### After (.env with ENACT_*):
70
+ ```bash
71
+ # Provider secrets (for enact-config)
72
+ ENACT_PROVIDERS_GOOGLE_APIKEY=****
73
+ ENACT_PROVIDERS_OPENAI_APIKEY=****
74
+ ENACT_PROVIDERS_AZURE_APIKEY=****
75
+
76
+ # Provider settings (for enact-config)
77
+ ENACT_PROVIDERS_AZURE_ENDPOINT=https://conf-foundry.openai.azure.com/openai/deployments/
78
+ ENACT_PROVIDERS_AZURE_API_VERSION=2024-02-15-preview
79
+ ENACT_PROVIDERS_AZURE_DEPLOYMENT_NAME=gpt-4.1-nano
80
+ ENACT_PROVIDERS_OLLAMA_BASE_URL=http://localhost:11434/api
81
+
82
+ # Keep all other variables as-is (no ENACT_ prefix)
83
+ NODE_ENV=development
84
+ POSTGRES_URL=postgres://postgres:postgres@localhost:5432/enact
85
+ # ... etc
86
+ ```
87
+
88
+
89
+
90
+
91
+
92
+
@@ -0,0 +1,107 @@
1
+ # enact-config
2
+
3
+ Unified configuration management for Enact with secure storage and cloud sync.
4
+
5
+ ## Features
6
+
7
+ - **Environment Variables**: Read secrets from `ENACT_*` environment variables (great for `.env` files in development)
8
+ - **OS Keychain**: Secure storage for secrets (API keys, tokens, credentials) with fallback support
9
+ - **Encrypted File Storage**: AES-256-GCM encrypted storage for settings
10
+ - **Cloud Sync**: Automatic configuration synchronization (respects air-gapped mode)
11
+ - **Multi-platform**: Works on macOS, Linux, and Windows
12
+
13
+ ## Usage
14
+
15
+ ```rust
16
+ use enact_config::{ConfigManager, default_config_path};
17
+
18
+ let config_path = default_config_path()?;
19
+ let manager = ConfigManager::new(config_path).await?;
20
+
21
+ // Load configuration
22
+ let config = manager.load().await?;
23
+
24
+ // Set a secret (stored in keychain)
25
+ manager.set_secret("providers.azure.apiKey", "your-api-key").await?;
26
+
27
+ // Save configuration
28
+ manager.save(&config).await?;
29
+ ```
30
+
31
+ ## Configuration Structure
32
+
33
+ Configuration is split into:
34
+ - **Secrets**: Stored in OS keychain (API keys, tokens, credentials) or environment variables
35
+ - **Settings**: Stored in encrypted file (feature flags, timeouts, preferences, storage backends, tool engines)
36
+
37
+ ## Environment Variable Support
38
+
39
+ The configuration manager automatically checks **all global environment variables** starting with `ENACT_*` before falling back to the OS keychain. This includes:
40
+
41
+ - System-wide environment variables
42
+ - User-level environment variables
43
+ - Shell session variables
44
+ - Variables from `.env` files (if loaded via `dotenvy` or similar)
45
+
46
+ No `.env` file is required - any `ENACT_*` environment variable set in your environment will be automatically detected and used.
47
+
48
+ ### Key to Environment Variable Mapping
49
+
50
+ Keys are converted to environment variable names by:
51
+ - Converting to uppercase
52
+ - Replacing dots with underscores
53
+ - Prefixing with `ENACT_`
54
+
55
+ ### Examples
56
+
57
+ | Key | Environment Variable |
58
+ |-----|---------------------|
59
+ | `providers.azure.apiKey` | `ENACT_PROVIDERS_AZURE_APIKEY` |
60
+ | `providers.anthropic.apiKey` | `ENACT_PROVIDERS_ANTHROPIC_APIKEY` |
61
+ | `providers.openai.apiKey` | `ENACT_PROVIDERS_OPENAI_APIKEY` |
62
+
63
+ ### Setting Environment Variables
64
+
65
+ You can set `ENACT_*` environment variables in any of these ways:
66
+
67
+ **1. System-wide or user-level (persistent):**
68
+ ```bash
69
+ # In ~/.bashrc, ~/.zshrc, or system-wide config
70
+ export ENACT_PROVIDERS_AZURE_APIKEY=your-azure-api-key
71
+ export ENACT_PROVIDERS_ANTHROPIC_APIKEY=your-anthropic-api-key
72
+ ```
73
+
74
+ **2. Current shell session:**
75
+ ```bash
76
+ export ENACT_PROVIDERS_AZURE_APIKEY=your-azure-api-key
77
+ ```
78
+
79
+ **3. Using `.env` files (optional, for convenience):**
80
+
81
+ Create a `.env` file in your project root:
82
+ ```bash
83
+ ENACT_PROVIDERS_AZURE_APIKEY=your-azure-api-key
84
+ ENACT_PROVIDERS_ANTHROPIC_APIKEY=your-anthropic-api-key
85
+ ENACT_PROVIDERS_OPENAI_APIKEY=your-openai-api-key
86
+ ```
87
+
88
+ Then load it in your application (optional - only needed if using `.env` files):
89
+ ```rust
90
+ // Example with dotenvy (add to your Cargo.toml if needed)
91
+ dotenvy::dotenv().ok();
92
+ ```
93
+
94
+ **4. Programmatically:**
95
+ ```rust
96
+ std::env::set_var("ENACT_PROVIDERS_AZURE_APIKEY", "your-azure-api-key");
97
+ ```
98
+
99
+ The `ConfigManager` automatically checks **all** of these sources - no additional configuration needed. Environment variables work out of the box without any `.env` file loader.
100
+
101
+ ## Air-Gapped Mode
102
+
103
+ When `runtime.mode === "airgapped"`:
104
+ - Cloud sync is disabled
105
+ - Network access is blocked
106
+ - Only local features are available
107
+
@@ -0,0 +1,161 @@
1
+ # Testing ENACT_* Environment Variable Support
2
+
3
+ This guide shows you how to test the environment variable functionality in `enact-config`.
4
+
5
+ ## Quick Test Methods
6
+
7
+ ### 1. Run Unit Tests
8
+
9
+ The simplest way to test is to run the existing unit tests:
10
+
11
+ ```bash
12
+ # Run all keychain tests
13
+ cargo test -p enact-config keychain::tests --lib
14
+
15
+ # Run specific test
16
+ cargo test -p enact-config keychain::tests::test_get_from_env_var --lib -- --nocapture
17
+ ```
18
+
19
+ ### 2. Test with Environment Variables
20
+
21
+ Set environment variables and run tests:
22
+
23
+ ```bash
24
+ # Test with inline environment variable
25
+ ENACT_PROVIDERS_AZURE_APIKEY=test-key-123 \
26
+ cargo test -p enact-config keychain::tests::test_get_from_env_var --lib -- --nocapture
27
+ ```
28
+
29
+ ### 3. Use the Example Program
30
+
31
+ Run the example program to see it in action:
32
+
33
+ ```bash
34
+ # Without environment variables (shows fallback behavior)
35
+ cargo run --example test-env-vars
36
+
37
+ # With environment variables
38
+ ENACT_PROVIDERS_AZURE_APIKEY=my-azure-key \
39
+ ENACT_PROVIDERS_ANTHROPIC_APIKEY=my-anthropic-key \
40
+ ENACT_PROVIDERS_OPENAI_APIKEY=my-openai-key \
41
+ cargo run --example test-env-vars
42
+ ```
43
+
44
+ ### 4. Use the Test Script
45
+
46
+ Run the provided test script:
47
+
48
+ ```bash
49
+ cd crates/enact-config
50
+ ./test-env-vars.sh
51
+ ```
52
+
53
+ ## Manual Testing
54
+
55
+ ### Test 1: Environment Variable Takes Precedence
56
+
57
+ ```bash
58
+ # Set an environment variable
59
+ export ENACT_PROVIDERS_AZURE_APIKEY=from-env-123
60
+
61
+ # In Rust code or REPL:
62
+ use enact_config::ConfigManager;
63
+ let manager = ConfigManager::new("/tmp/test_config.encrypted").await?;
64
+ let value = manager.get_secret("providers.azure.apiKey").await?;
65
+ // Should return Some("from-env-123")
66
+ ```
67
+
68
+ ### Test 2: Fallback to Keychain
69
+
70
+ ```bash
71
+ # Don't set the environment variable
72
+ unset ENACT_PROVIDERS_AZURE_APIKEY
73
+
74
+ # Set in keychain
75
+ let manager = ConfigManager::new("/tmp/test_config.encrypted").await?;
76
+ manager.set_secret("providers.azure.apiKey", "from-keychain").await?;
77
+ let value = manager.get_secret("providers.azure.apiKey").await?;
78
+ // Should return Some("from-keychain")
79
+ ```
80
+
81
+ ### Test 3: Test Key Conversion
82
+
83
+ The key `providers.azure.apiKey` should map to `ENACT_PROVIDERS_AZURE_APIKEY`:
84
+
85
+ ```bash
86
+ # Test the conversion
87
+ export ENACT_PROVIDERS_AZURE_APIKEY=test-value
88
+ cargo test -p enact-config keychain::tests::test_key_to_env_var_name --lib
89
+ ```
90
+
91
+ ## Testing Different Sources
92
+
93
+ ### System-wide Environment Variables
94
+
95
+ ```bash
96
+ # Set system-wide (requires admin on some systems)
97
+ sudo export ENACT_PROVIDERS_AZURE_APIKEY=system-wide-key
98
+
99
+ # Or add to /etc/environment (Linux) or ~/.zshrc/~/.bashrc
100
+ echo 'export ENACT_PROVIDERS_AZURE_APIKEY=my-key' >> ~/.zshrc
101
+ source ~/.zshrc
102
+ ```
103
+
104
+ ### Shell Session Variables
105
+
106
+ ```bash
107
+ # Set for current session
108
+ export ENACT_PROVIDERS_AZURE_APIKEY=session-key
109
+
110
+ # Verify
111
+ echo $ENACT_PROVIDERS_AZURE_APIKEY
112
+ ```
113
+
114
+ ### .env File (with dotenvy)
115
+
116
+ ```bash
117
+ # Create .env file
118
+ cat > .env << EOF
119
+ ENACT_PROVIDERS_AZURE_APIKEY=dotenv-key
120
+ ENACT_PROVIDERS_ANTHROPIC_APIKEY=anthropic-key
121
+ EOF
122
+
123
+ # In your Rust code, load it:
124
+ dotenvy::dotenv().ok();
125
+ ```
126
+
127
+ ## Expected Behavior
128
+
129
+ 1. **Environment variables are checked first** - Any `ENACT_*` env var takes precedence
130
+ 2. **Fallback to keychain** - If env var not found, uses OS keychain
131
+ 3. **Mock keychain in tests** - Tests use in-memory mock, but env vars still take precedence
132
+ 4. **All global env vars work** - System-wide, user-level, session, and .env-loaded vars all work
133
+
134
+ ## Troubleshooting
135
+
136
+ ### Environment variable not being picked up?
137
+
138
+ 1. Check the variable name matches exactly (uppercase, underscores):
139
+ ```bash
140
+ echo $ENACT_PROVIDERS_AZURE_APIKEY
141
+ ```
142
+
143
+ 2. Verify it's in the process environment:
144
+ ```bash
145
+ env | grep ENACT
146
+ ```
147
+
148
+ 3. Make sure you're not in a subshell that doesn't have the variable
149
+
150
+ ### Test failing?
151
+
152
+ 1. Clean up any leftover environment variables:
153
+ ```bash
154
+ unset ENACT_PROVIDERS_AZURE_APIKEY
155
+ ```
156
+
157
+ 2. Run tests in isolation:
158
+ ```bash
159
+ cargo test --lib -- --test-threads=1
160
+ ```
161
+
@@ -0,0 +1,100 @@
1
+ //! Example: Testing environment variable support
2
+ //!
3
+ //! This example demonstrates how to test the ENACT_* environment variable support.
4
+ //!
5
+ //! Run with:
6
+ //! cargo run --example test-env-vars
7
+ //!
8
+ //! Or set environment variables and run:
9
+ //! ENACT_PROVIDERS_AZURE_APIKEY=test-key-123 cargo run --example test-env-vars
10
+
11
+ use enact_config::ConfigManager;
12
+ use std::env;
13
+
14
+ #[tokio::main]
15
+ async fn main() -> anyhow::Result<()> {
16
+ // Initialize tracing for debug output
17
+ tracing_subscriber::fmt::init();
18
+
19
+ println!("Testing ENACT_* environment variable support\n");
20
+
21
+ // Create a temporary config manager (uses mock keychain in tests)
22
+ let temp_dir = tempfile::tempdir()?;
23
+ let config_path = temp_dir.path().join("test_config.encrypted");
24
+ let manager = ConfigManager::new(&config_path).await?;
25
+
26
+ let test_key = "providers.azure.apiKey";
27
+ let env_var_name = "ENACT_PROVIDERS_AZURE_APIKEY";
28
+
29
+ println!("Test key: {}", test_key);
30
+ println!("Expected env var: {}\n", env_var_name);
31
+
32
+ // Test 1: Check if environment variable is set
33
+ match env::var(env_var_name) {
34
+ Ok(value) => {
35
+ println!("✓ Environment variable {} is set: {}", env_var_name, value);
36
+
37
+ // Try to retrieve via ConfigManager
38
+ match manager.get_secret(test_key).await? {
39
+ Some(retrieved) => {
40
+ println!("✓ ConfigManager retrieved value: {}", retrieved);
41
+ if retrieved == value {
42
+ println!("✓ SUCCESS: Environment variable is being used correctly!");
43
+ } else {
44
+ println!("✗ ERROR: Retrieved value doesn't match environment variable");
45
+ }
46
+ }
47
+ None => {
48
+ println!("✗ ERROR: ConfigManager returned None despite env var being set");
49
+ }
50
+ }
51
+ }
52
+ Err(_) => {
53
+ println!("⚠ Environment variable {} is not set", env_var_name);
54
+ println!("\nTo test, set it and run again:");
55
+ println!(" {}=your-test-value cargo run --example test-env-vars", env_var_name);
56
+
57
+ // Test fallback to keychain
58
+ println!("\nTesting fallback to keychain...");
59
+ manager.set_secret(test_key, "keychain-value").await?;
60
+ match manager.get_secret(test_key).await? {
61
+ Some(value) => {
62
+ println!("✓ Fallback to keychain works: {}", value);
63
+ }
64
+ None => {
65
+ println!("✗ Fallback to keychain failed");
66
+ }
67
+ }
68
+ }
69
+ }
70
+
71
+ // Test 2: Test with multiple provider keys
72
+ println!("\n--- Testing multiple provider keys ---");
73
+ let test_keys = vec![
74
+ ("providers.azure.apiKey", "ENACT_PROVIDERS_AZURE_APIKEY"),
75
+ ("providers.anthropic.apiKey", "ENACT_PROVIDERS_ANTHROPIC_APIKEY"),
76
+ ("providers.openai.apiKey", "ENACT_PROVIDERS_OPENAI_APIKEY"),
77
+ ];
78
+
79
+ for (key, env_var) in test_keys {
80
+ match env::var(env_var) {
81
+ Ok(value) => {
82
+ println!("✓ {} = {}", env_var, value);
83
+ if let Ok(Some(retrieved)) = manager.get_secret(key).await {
84
+ if retrieved == value {
85
+ println!(" ✓ ConfigManager retrieved correctly");
86
+ } else {
87
+ println!(" ✗ Mismatch: got {}", retrieved);
88
+ }
89
+ }
90
+ }
91
+ Err(_) => {
92
+ println!("⚠ {} not set", env_var);
93
+ }
94
+ }
95
+ }
96
+
97
+ println!("\n--- Test complete ---");
98
+ Ok(())
99
+ }
100
+