dirsql 0.3.125__tar.gz → 0.3.126__tar.gz

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 (206) hide show
  1. {dirsql-0.3.125 → dirsql-0.3.126}/Cargo.lock +1 -1
  2. {dirsql-0.3.125 → dirsql-0.3.126}/PKG-INFO +1 -1
  3. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/Cargo.toml +1 -1
  4. dirsql-0.3.126/packages/python/changelog.d/2026-07-24-hookless-table-config-error.md +3 -0
  5. dirsql-0.3.126/packages/python/e2e-attestations/feat-634-slice4-hookless-error.json +7 -0
  6. dirsql-0.3.126/packages/python/migrations.d/2026-07-24-hookless-table-config-error.md +51 -0
  7. dirsql-0.3.126/packages/rust/changelog.d/2026-07-24-hookless-table-config-error.md +3 -0
  8. dirsql-0.3.126/packages/rust/migrations.d/2026-07-24-hookless-table-config-error.md +51 -0
  9. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/config.rs +78 -26
  10. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/lib.rs +20 -25
  11. dirsql-0.3.125/packages/python/e2e-attestations/feat-634-core-remove-injection.json +0 -7
  12. {dirsql-0.3.125 → dirsql-0.3.126}/Cargo.toml +0 -0
  13. {dirsql-0.3.125 → dirsql-0.3.126}/README.md +0 -0
  14. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/__init__.py +0 -0
  15. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/_async.py +0 -0
  16. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/_dirsql.pyi +0 -0
  17. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/__init__.py +0 -0
  18. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/binary_path.py +0 -0
  19. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/discover_plugins/__init__.py +0 -0
  20. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/discover_plugins/discovered_fragments.py +0 -0
  21. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/discover_plugins/discovery_disabled.py +0 -0
  22. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/discover_plugins/fragment_path.py +0 -0
  23. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/discover_plugins/user_passed_config.py +0 -0
  24. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/discover_plugins/with_discovered_plugins.py +0 -0
  25. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/is_windows.py +0 -0
  26. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/main.py +0 -0
  27. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/cli/resolve_config_extensions.py +0 -0
  28. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/py.typed +0 -0
  29. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/resolve_config_extensions.py +0 -0
  30. {dirsql-0.3.125 → dirsql-0.3.126}/dirsql/resolve_extension.py +0 -0
  31. {dirsql-0.3.125 → dirsql-0.3.126}/docs/.claude/CLAUDE.md +0 -0
  32. {dirsql-0.3.125 → dirsql-0.3.126}/docs/.vitepress/config.ts +0 -0
  33. {dirsql-0.3.125 → dirsql-0.3.126}/docs/.vitepress/theme/index.ts +0 -0
  34. {dirsql-0.3.125 → dirsql-0.3.126}/docs/.vitepress/theme/lang.ts +0 -0
  35. {dirsql-0.3.125 → dirsql-0.3.126}/docs/AGENTS.md +0 -0
  36. {dirsql-0.3.125 → dirsql-0.3.126}/docs/explanation.md +0 -0
  37. {dirsql-0.3.125 → dirsql-0.3.126}/docs/getting-started.md +0 -0
  38. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/columns-from-paths.md +0 -0
  39. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/define-tables.md +0 -0
  40. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/embed.md +0 -0
  41. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/extract-from-contents.md +0 -0
  42. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/load-extension.md +0 -0
  43. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/parse-files-into-columns.md +0 -0
  44. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/persist.md +0 -0
  45. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/query-without-config.md +0 -0
  46. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/react-to-changes.md +0 -0
  47. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/search-by-meaning.md +0 -0
  48. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/skip-files.md +0 -0
  49. {dirsql-0.3.125 → dirsql-0.3.126}/docs/howto/write-a-plugin.md +0 -0
  50. {dirsql-0.3.125 → dirsql-0.3.126}/docs/index.md +0 -0
  51. {dirsql-0.3.125 → dirsql-0.3.126}/docs/migrations.md +0 -0
  52. {dirsql-0.3.125 → dirsql-0.3.126}/docs/package.json +0 -0
  53. {dirsql-0.3.125 → dirsql-0.3.126}/docs/pnpm-lock.yaml +0 -0
  54. {dirsql-0.3.125 → dirsql-0.3.126}/docs/pnpm-workspace.yaml +0 -0
  55. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/cli.md +0 -0
  56. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/columns.md +0 -0
  57. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/config.md +0 -0
  58. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/hooks.md +0 -0
  59. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/http-api.md +0 -0
  60. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/path-tables.md +0 -0
  61. {dirsql-0.3.125 → dirsql-0.3.126}/docs/reference/sdk.md +0 -0
  62. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/CHANGELOG.md +0 -0
  63. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/MIGRATIONS.md +0 -0
  64. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/README.md +0 -0
  65. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-13-drop-cwd-config-auto-detect.md +0 -0
  66. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-13-plugin-discovery.md +0 -0
  67. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-13-rename-extract-to-on-file.md +0 -0
  68. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-13-repeatable-config.md +0 -0
  69. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-13-sdk-default-baked-in-config.md +0 -0
  70. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-20-drop-implicit-files-table.md +0 -0
  71. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-21-remove-glob-captures.md +0 -0
  72. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/2026-07-24-remove-stat-fact-injection.md +0 -0
  73. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/changelog.d/README.md +0 -0
  74. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/conftest.py +0 -0
  75. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/.claude/CLAUDE.md +0 -0
  76. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/.vitepress/config.ts +0 -0
  77. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/.vitepress/theme/index.ts +0 -0
  78. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/.vitepress/theme/lang.ts +0 -0
  79. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/AGENTS.md +0 -0
  80. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/explanation.md +0 -0
  81. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/getting-started.md +0 -0
  82. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/columns-from-paths.md +0 -0
  83. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/define-tables.md +0 -0
  84. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/embed.md +0 -0
  85. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/extract-from-contents.md +0 -0
  86. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/load-extension.md +0 -0
  87. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/parse-files-into-columns.md +0 -0
  88. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/persist.md +0 -0
  89. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/query-without-config.md +0 -0
  90. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/react-to-changes.md +0 -0
  91. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/search-by-meaning.md +0 -0
  92. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/skip-files.md +0 -0
  93. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/howto/write-a-plugin.md +0 -0
  94. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/index.md +0 -0
  95. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/migrations.md +0 -0
  96. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/package.json +0 -0
  97. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/pnpm-lock.yaml +0 -0
  98. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/pnpm-workspace.yaml +0 -0
  99. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/cli.md +0 -0
  100. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/columns.md +0 -0
  101. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/config.md +0 -0
  102. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/hooks.md +0 -0
  103. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/http-api.md +0 -0
  104. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/path-tables.md +0 -0
  105. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/docs/reference/sdk.md +0 -0
  106. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/2026-07-13-drop-cwd-config-auto-detect.md +0 -0
  107. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/2026-07-13-rename-extract-to-on-file.md +0 -0
  108. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/2026-07-13-sdk-default-baked-in-config.md +0 -0
  109. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/2026-07-20-drop-implicit-files-table.md +0 -0
  110. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/2026-07-21-remove-glob-captures.md +0 -0
  111. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/2026-07-24-remove-stat-fact-injection.md +0 -0
  112. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/migrations.d/README.md +0 -0
  113. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/src/lib.rs +0 -0
  114. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/__init__.py +0 -0
  115. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/conftest.py +0 -0
  116. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/e2e/__init__.py +0 -0
  117. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/e2e/fixtures/dirsql_plugin_fixture/__init__.py +0 -0
  118. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/e2e/fixtures/dirsql_plugin_fixture/dirsql.toml +0 -0
  119. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/integration/__init__.py +0 -0
  120. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/integration/binding/__init__.py +0 -0
  121. {dirsql-0.3.125 → dirsql-0.3.126}/packages/python/tests/integration/hermetic/__init__.py +0 -0
  122. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/CHANGELOG.md +0 -0
  123. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/Cargo.toml +0 -0
  124. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/MIGRATIONS.md +0 -0
  125. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/README.md +0 -0
  126. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/benches/db_bench.rs +0 -0
  127. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/benches/differ_bench.rs +0 -0
  128. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/benches/matcher_bench.rs +0 -0
  129. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/benches/scanner_bench.rs +0 -0
  130. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-batch-ingest-transaction.md +0 -0
  131. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-chained-pre-post-query-hooks.md +0 -0
  132. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-drop-cwd-config-auto-detect.md +0 -0
  133. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-fan-out-file-table-matching.md +0 -0
  134. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-persist-wal.md +0 -0
  135. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-rename-extract-to-on-file.md +0 -0
  136. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-repeatable-builder-config.md +0 -0
  137. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-repeatable-cli-config.md +0 -0
  138. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-sdk-default-baked-in-config.md +0 -0
  139. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-13-subcommand-local-config-flags.md +0 -0
  140. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-19-path-table-query-fallback.md +0 -0
  141. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-19-path-table-vtab.md +0 -0
  142. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-20-drop-implicit-files-table.md +0 -0
  143. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-20-path-table-glob-semantics.md +0 -0
  144. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-20-schema-inference.md +0 -0
  145. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-21-on-file-flag.md +0 -0
  146. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-21-remove-glob-captures.md +0 -0
  147. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-23-init-escalation-example.md +0 -0
  148. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-23-query-default-cli.md +0 -0
  149. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/2026-07-24-remove-stat-fact-injection.md +0 -0
  150. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/changelog.d/README.md +0 -0
  151. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/explanation.md +0 -0
  152. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/getting-started.md +0 -0
  153. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/columns-from-paths.md +0 -0
  154. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/define-tables.md +0 -0
  155. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/embed.md +0 -0
  156. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/extract-from-contents.md +0 -0
  157. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/load-extension.md +0 -0
  158. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/parse-files-into-columns.md +0 -0
  159. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/persist.md +0 -0
  160. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/query-without-config.md +0 -0
  161. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/react-to-changes.md +0 -0
  162. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/search-by-meaning.md +0 -0
  163. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/skip-files.md +0 -0
  164. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/howto/write-a-plugin.md +0 -0
  165. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/index.md +0 -0
  166. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/migrations.md +0 -0
  167. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/cli.md +0 -0
  168. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/columns.md +0 -0
  169. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/config.md +0 -0
  170. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/hooks.md +0 -0
  171. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/http-api.md +0 -0
  172. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/path-tables.md +0 -0
  173. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/docs/reference/sdk.md +0 -0
  174. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-13-drop-cwd-config-auto-detect.md +0 -0
  175. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-13-fan-out-file-table-matching.md +0 -0
  176. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-13-persist-wal.md +0 -0
  177. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-13-rename-extract-to-on-file.md +0 -0
  178. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-13-sdk-default-baked-in-config.md +0 -0
  179. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-13-subcommand-local-config-flags.md +0 -0
  180. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-20-drop-implicit-files-table.md +0 -0
  181. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-20-path-table-glob-semantics.md +0 -0
  182. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-21-remove-glob-captures.md +0 -0
  183. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-23-init-escalation-example.md +0 -0
  184. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-23-query-default-cli.md +0 -0
  185. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/2026-07-24-remove-stat-fact-injection.md +0 -0
  186. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/migrations.d/README.md +0 -0
  187. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/bin/dirsql.rs +0 -0
  188. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/cli/execute.rs +0 -0
  189. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/cli/init.rs +0 -0
  190. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/cli/mod.rs +0 -0
  191. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/cli/router.rs +0 -0
  192. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/cli/serialize.rs +0 -0
  193. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/cli/server.rs +0 -0
  194. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/command.rs +0 -0
  195. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/db.rs +0 -0
  196. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/default_config.toml +0 -0
  197. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/differ.rs +0 -0
  198. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/infer.rs +0 -0
  199. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/matcher.rs +0 -0
  200. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/parsed_vtab.rs +0 -0
  201. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/path_table.rs +0 -0
  202. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/persist.rs +0 -0
  203. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/scanner.rs +0 -0
  204. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/vtab.rs +0 -0
  205. {dirsql-0.3.125 → dirsql-0.3.126}/packages/rust/src/watcher.rs +0 -0
  206. {dirsql-0.3.125 → dirsql-0.3.126}/pyproject.toml +0 -0
@@ -500,7 +500,7 @@ dependencies = [
500
500
 
501
501
  [[package]]
502
502
  name = "dirsql-py-ext"
503
- version = "0.3.125"
503
+ version = "0.3.126"
504
504
  dependencies = [
505
505
  "dirsql",
506
506
  "pyo3",
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: dirsql
3
- Version: 0.3.125
3
+ Version: 0.3.126
4
4
  Summary: Ephemeral SQL index over a local directory
5
5
  Keywords: sql,filesystem,directory,sqlite,index
6
6
  Author: Kevin Scott
@@ -4,7 +4,7 @@ name = "dirsql-py-ext"
4
4
  # pypi/maturin handler can rewrite it via `write-version` before
5
5
  # `maturin build`. `pyproject.toml` declares `dynamic = ["version"]`
6
6
  # and maturin reads this field. Mirrors `packages/rust/Cargo.toml`.
7
- version = "0.3.125"
7
+ version = "0.3.126"
8
8
  # abi3 note: the `abi3-py311` pyo3 feature (below) builds ONE stable-ABI
9
9
  # `cp311-abi3` wheel per platform that loads on every CPython >= 3.11
10
10
  # (matching `pyproject.toml`'s `requires-python = ">=3.11"`), instead of
@@ -0,0 +1,3 @@
1
+ **Changed**
2
+
3
+ - **A `[[table]]` with no `on-file` hook is now a config-load error.** After the stat-fact injection layer was removed, a hook-less named table emitted no columns of its own, so every row was all-NULL. Loading such a config (`DirSQL(config=…)` / `.ready()`) now raises, with a message pointing at the fix: add an `on-file` hook that emits the columns, or, for stat columns with no code, query the path directly with a path-table (`FROM './'`). This completes the fact-removal epic (#624). (#634)
@@ -0,0 +1,7 @@
1
+ {
2
+ "command": "just test-e2e",
3
+ "ran_at": 1784908753,
4
+ "exit_code": 0,
5
+ "commit": "f07fcf90987684b0edc4fd44f57f5003d329bd74",
6
+ "branch": "feat/634-slice4-hookless-error"
7
+ }
@@ -0,0 +1,51 @@
1
+ ### Hook-less `[[table]]` is now a config error (#634)
2
+
3
+ #### Summary
4
+
5
+ A `[[table]]` with no `on-file` hook previously loaded fine and — after the
6
+ stat-fact injection layer was removed — produced rows that were all-NULL.
7
+ Loading such a config through the Python SDK (`DirSQL(config=…)`, awaited via
8
+ `.ready()`) now raises. No API signature changes — this is a load-time
9
+ validation change surfaced from the core.
10
+
11
+ #### Required changes
12
+
13
+ | Before (loaded, all-NULL rows) | After (raises) | Fix |
14
+ | ------------------------------ | -------------- | --- |
15
+ | `.dirsql.toml` `[[table]]` with `ddl` + `glob` but no `on-file` | `.ready()` raises `[[table]] '<glob>' has no on-file hook …` | Add an `on-file` hook that emits the declared columns. |
16
+ | You only wanted stat columns and wrote no hook code | `.ready()` raises | Drop the `[[table]]` and query the path directly: `SELECT path, size, mtime FROM './'` (globbable: `FROM './**/*.md'`). |
17
+
18
+ #### Deprecations removed
19
+
20
+ _None._
21
+
22
+ #### Behavior changes without code changes
23
+
24
+ - A `[[table]]` with no `on-file` hook, which used to load (and, after injection
25
+ removal, yield all-NULL rows), now raises at config load, with an error naming
26
+ the offending glob and pointing at the `FROM './'` path-table replacement.
27
+
28
+ #### Verification
29
+
30
+ ```python
31
+ import asyncio
32
+ from dirsql import DirSQL
33
+
34
+ # .dirsql.toml with a hook-less table:
35
+ # [[table]]
36
+ # ddl = "CREATE TABLE files (path TEXT, size INTEGER)"
37
+ # glob = "**/*.md"
38
+
39
+ db = DirSQL(config=".dirsql.toml")
40
+ # Before this change: await db.ready() succeeded; SELECT * FROM files -> all-NULL rows.
41
+ # After this change:
42
+ try:
43
+ asyncio.run(db.ready())
44
+ except Exception as e:
45
+ print(e) # -> ... has no on-file hook ... query the path directly: `FROM './'`
46
+
47
+ # Replacement with no hook code — query the path directly (no config):
48
+ db2 = DirSQL(root=".")
49
+ asyncio.run(db2.ready())
50
+ print(asyncio.run(db2.query("SELECT path, size FROM './**/*.md'")))
51
+ ```
@@ -0,0 +1,3 @@
1
+ **Changed**
2
+
3
+ - **A `[[table]]` with no `on-file` hook is now a load error.** After the stat-fact injection layer was removed, a hook-less named table emitted no columns of its own, so every row was all-NULL — useless and surprising. `load_config_str` (and every path that loads a config, including `DirSQL::from_config_path` and the CLI's `-c`) now rejects such a table with a message pointing at the fix: add an `on-file` hook that emits the columns, or, for stat columns with no code, query the path directly with a path-table (`FROM './'`). This completes the fact-removal epic (#624). (#634)
@@ -0,0 +1,51 @@
1
+ ### Hook-less `[[table]]` is now a config error (#634)
2
+
3
+ #### Summary
4
+
5
+ A `[[table]]` (or SDK-registered table) with no `on-file` hook previously
6
+ loaded fine and — after the stat-fact injection layer was removed — produced
7
+ rows that were all-NULL. dirsql now rejects a hook-less table at config load
8
+ (`ConfigError::HooklessTable`), so the failure is loud and actionable instead
9
+ of a silently useless table. No API signature changes — this is a
10
+ load-time validation change. `TableConfig.on_file` is now `String` (was
11
+ `Option<String>`) since a parsed table always carries a hook.
12
+
13
+ #### Required changes
14
+
15
+ | Before (loaded, all-NULL rows) | After (load error) | Fix |
16
+ | ------------------------------ | ------------------ | --- |
17
+ | `[[table]]` declares `ddl` + `glob` but no `on-file` | Load fails: `[[table]] '<glob>' has no on-file hook …` | Add an `on-file` hook that emits the declared columns, e.g. `on-file = 'rel=${1#"$2"/}; jq -n --arg path "$rel" '\''[{path:$path}]'\'''`. |
18
+ | You only wanted stat columns and wrote no hook code | Load fails | Drop the `[[table]]` and query the path directly with a path-table: `SELECT path, size, mtime FROM './'` (globbable: `FROM './**/*.md'`). |
19
+
20
+ #### Deprecations removed
21
+
22
+ _None._
23
+
24
+ #### Behavior changes without code changes
25
+
26
+ - A `[[table]]` with no `on-file` hook, which used to load (and, after injection
27
+ removal, yield all-NULL rows), now fails at config load with an error naming
28
+ the offending glob and pointing at the `FROM './'` path-table replacement.
29
+
30
+ #### Verification
31
+
32
+ ```bash
33
+ # .dirsql.toml with a hook-less table:
34
+ # [[table]]
35
+ # ddl = "CREATE TABLE files (path TEXT, size INTEGER)"
36
+ # glob = "**/*.md"
37
+
38
+ # Before this change:
39
+ dirsql query "SELECT * FROM files" -c ./.dirsql.toml
40
+ # -> [] or all-NULL rows (loaded, but useless)
41
+
42
+ # After this change:
43
+ dirsql query "SELECT * FROM files" -c ./.dirsql.toml
44
+ # -> error: [[table]] '**/*.md' has no on-file hook, so every row would be
45
+ # all-NULL. Add an `on-file` hook that emits the columns, or, for stat
46
+ # columns with no code, query the path directly: `FROM './'`
47
+
48
+ # Replacement with no hook code — query the path directly:
49
+ dirsql query "SELECT path, size FROM './**/*.md'"
50
+ # -> rows with real path/size, no config needed
51
+ ```
@@ -21,6 +21,13 @@ pub enum ConfigError {
21
21
  #[error("Field '{0}' must not be empty")]
22
22
  EmptyField(&'static str),
23
23
 
24
+ #[error(
25
+ "[[table]] '{glob}' has no on-file hook, so every row would be all-NULL. \
26
+ Add an `on-file` hook that emits the columns, or, for stat columns with \
27
+ no code, query the path directly: `FROM './'`"
28
+ )]
29
+ HooklessTable { glob: String },
30
+
24
31
  #[error("Field '{field}' must be a positive number of seconds, got {value}")]
25
32
  InvalidTimeout { field: &'static str, value: i64 },
26
33
 
@@ -221,11 +228,12 @@ pub struct TableConfig {
221
228
  pub ddl: String,
222
229
  pub glob: String,
223
230
  pub strict: Option<bool>,
224
- /// Optional per-file command (`on-file`). When set, each matched file's
225
- /// rows come from running this command (which reads the file and prints a
226
- /// JSON array of row objects) instead of the empty filesystem-facts-only
227
- /// row. See `dirsql::command` for the execution contract.
228
- pub on_file: Option<String>,
231
+ /// The required per-file command (`on-file`). Each matched file's rows come
232
+ /// from running this command, which reads the file and prints a JSON array
233
+ /// of row objects. A table without it would emit no columns of its own
234
+ /// every row all-NULL — so it is rejected at load. See `dirsql::command`
235
+ /// for the execution contract.
236
+ pub on_file: String,
229
237
  }
230
238
 
231
239
  #[derive(Deserialize)]
@@ -323,7 +331,8 @@ pub fn load_config_str(content: &str) -> Result<Config> {
323
331
  Some(cmd) if cmd.trim().is_empty() => {
324
332
  return Err(ConfigError::EmptyField("on-file"));
325
333
  }
326
- other => other,
334
+ Some(cmd) => cmd,
335
+ None => return Err(ConfigError::HooklessTable { glob }),
327
336
  };
328
337
 
329
338
  tables.push(TableConfig {
@@ -367,10 +376,12 @@ ignore = ["node_modules/**", ".git/**"]
367
376
  [[table]]
368
377
  ddl = "CREATE TABLE comments (thread_id TEXT, path TEXT)"
369
378
  glob = "_comments/{thread_id}/index.jsonl"
379
+ on-file = "cat {path}"
370
380
 
371
381
  [[table]]
372
382
  ddl = "CREATE TABLE items (path TEXT, size INTEGER)"
373
383
  glob = "catalog/*.json"
384
+ on-file = "cat {path}"
374
385
  strict = true
375
386
  "#;
376
387
  let config = load_config_str(toml).unwrap();
@@ -391,6 +402,7 @@ strict = true
391
402
  let toml = r#"
392
403
  [[table]]
393
404
  glob = "*.json"
405
+ on-file = "cat {path}"
394
406
  "#;
395
407
  let err = load_config_str(toml).unwrap_err();
396
408
  assert!(err.to_string().contains("ddl"));
@@ -438,6 +450,7 @@ ignore = ["*.tmp"]
438
450
  [[table]]
439
451
  ddl = "CREATE TABLE t (x TEXT)"
440
452
  glob = "*.json"
453
+ on-file = "cat {path}"
441
454
  "#;
442
455
  let config = load_config_str(toml).unwrap();
443
456
  assert!(config.ignore.is_empty());
@@ -478,14 +491,17 @@ persist_path = "/var/cache/dirsql.db"
478
491
  [[table]]
479
492
  ddl = "CREATE TABLE a (path TEXT)"
480
493
  glob = "a/*.json"
494
+ on-file = "cat {path}"
481
495
 
482
496
  [[table]]
483
497
  ddl = "CREATE TABLE b (path TEXT)"
484
498
  glob = "b/*.csv"
499
+ on-file = "cat {path}"
485
500
 
486
501
  [[table]]
487
502
  ddl = "CREATE TABLE c (path TEXT)"
488
503
  glob = "c/*.yaml"
504
+ on-file = "cat {path}"
489
505
  "#;
490
506
  let config = load_config_str(toml).unwrap();
491
507
  assert_eq!(config.tables.len(), 3);
@@ -502,6 +518,7 @@ glob = "c/*.yaml"
502
518
  [[table]]
503
519
  ddl = "CREATE TABLE t (path TEXT)"
504
520
  glob = "*.json"
521
+ on-file = "cat {path}"
505
522
  format = "json"
506
523
  "#;
507
524
  let err = load_config_str(toml).unwrap_err();
@@ -568,6 +585,7 @@ entrypoint = "sqlite3_vec_init"
568
585
  [[table]]
569
586
  ddl = "CREATE TABLE t (path TEXT)"
570
587
  glob = "*.json"
588
+ on-file = "cat {path}"
571
589
  "#;
572
590
  let config = load_config_str(toml).unwrap();
573
591
  assert_eq!(config.extensions.len(), 1);
@@ -608,6 +626,7 @@ entrypoint = "sqlite3_x_init"
608
626
  [[table]]
609
627
  ddl = "CREATE TABLE t (path TEXT)"
610
628
  glob = "*.json"
629
+ on-file = "cat {path}"
611
630
  "#;
612
631
  let config = load_config_str(toml).unwrap();
613
632
  assert!(config.extensions.is_empty());
@@ -639,20 +658,26 @@ on-file = "uv run python extract_papers.py {path}"
639
658
  let config = load_config_str(toml).unwrap();
640
659
  assert_eq!(config.tables.len(), 1);
641
660
  assert_eq!(
642
- config.tables[0].on_file.as_deref(),
643
- Some("uv run python extract_papers.py {path}")
661
+ config.tables[0].on_file,
662
+ "uv run python extract_papers.py {path}"
644
663
  );
645
664
  }
646
665
 
647
666
  #[test]
648
- fn on_file_absent_is_none() {
667
+ fn on_file_absent_is_a_hookless_load_error() {
649
668
  let toml = r#"
650
669
  [[table]]
651
670
  ddl = "CREATE TABLE t (path TEXT)"
652
671
  glob = "*.json"
653
672
  "#;
654
- let config = load_config_str(toml).unwrap();
655
- assert!(config.tables[0].on_file.is_none());
673
+ let err = load_config_str(toml).unwrap_err();
674
+ assert!(
675
+ matches!(&err, ConfigError::HooklessTable { glob } if glob == "*.json"),
676
+ "got: {err:?}"
677
+ );
678
+ let msg = err.to_string();
679
+ assert!(msg.contains("on-file"), "got: {msg}");
680
+ assert!(msg.contains("FROM './'"), "got: {msg}");
656
681
  }
657
682
 
658
683
  #[test]
@@ -679,6 +704,7 @@ pre-query = "uv run python to_sql.py {args}"
679
704
  [[table]]
680
705
  ddl = "CREATE TABLE t (path TEXT)"
681
706
  glob = "*.json"
707
+ on-file = "cat {path}"
682
708
  "#;
683
709
  let config = load_config_str(toml).unwrap();
684
710
  assert_eq!(
@@ -693,6 +719,7 @@ glob = "*.json"
693
719
  [[table]]
694
720
  ddl = "CREATE TABLE t (path TEXT)"
695
721
  glob = "*.json"
722
+ on-file = "cat {path}"
696
723
  "#;
697
724
  let config = load_config_str(toml).unwrap();
698
725
  assert!(config.pre_query.is_none());
@@ -720,6 +747,7 @@ post-query = "jq '{results: .}'"
720
747
  [[table]]
721
748
  ddl = "CREATE TABLE t (path TEXT)"
722
749
  glob = "*.json"
750
+ on-file = "cat {path}"
723
751
  "#;
724
752
  let config = load_config_str(toml).unwrap();
725
753
  assert_eq!(config.post_query.as_deref(), Some("jq '{results: .}'"));
@@ -731,6 +759,7 @@ glob = "*.json"
731
759
  [[table]]
732
760
  ddl = "CREATE TABLE t (path TEXT)"
733
761
  glob = "*.json"
762
+ on-file = "cat {path}"
734
763
  "#;
735
764
  let config = load_config_str(toml).unwrap();
736
765
  assert!(config.post_query.is_none());
@@ -778,6 +807,7 @@ entrypoint = "sqlite3_vec_init"
778
807
  [[table]]
779
808
  ddl = "CREATE TABLE t (path TEXT)"
780
809
  glob = "*.json"
810
+ on-file = "cat {path}"
781
811
  "#);
782
812
  let merged = combine_configs(&[(src("/proj/.dirsql.toml"), config.clone())]).unwrap();
783
813
  assert_eq!(merged.ignore, config.ignore);
@@ -795,15 +825,18 @@ glob = "*.json"
795
825
  [[table]]
796
826
  ddl = "CREATE TABLE a (path TEXT)"
797
827
  glob = "a/*.json"
828
+ on-file = "cat {path}"
798
829
 
799
830
  [[table]]
800
831
  ddl = "CREATE TABLE b (path TEXT)"
801
832
  glob = "b/*.json"
833
+ on-file = "cat {path}"
802
834
  "#);
803
835
  let b = cfg(r#"
804
836
  [[table]]
805
837
  ddl = "CREATE TABLE c (path TEXT)"
806
838
  glob = "c/*.json"
839
+ on-file = "cat {path}"
807
840
  "#);
808
841
  let merged = combine_configs(&[(src("/a"), a), (src("/b"), b)]).unwrap();
809
842
  let ddls: Vec<&str> = merged.tables.iter().map(|t| t.ddl.as_str()).collect();
@@ -848,8 +881,12 @@ glob = "c/*.json"
848
881
 
849
882
  #[test]
850
883
  fn combine_duplicate_table_name_errors_naming_both_sources() {
851
- let a = cfg("[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\n");
852
- let b = cfg("[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\n");
884
+ let a = cfg(
885
+ "[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\non-file = \"cat {path}\"\n",
886
+ );
887
+ let b = cfg(
888
+ "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\non-file = \"cat {path}\"\n",
889
+ );
853
890
  let err = combine_configs(&[
854
891
  (src("/proj/.dirsql.toml"), a),
855
892
  (src("/plugin/frag.toml"), b),
@@ -878,8 +915,8 @@ glob = "c/*.json"
878
915
  // The single-entry identity path runs no collision check, exactly like
879
916
  // a plain single-config load.
880
917
  let config = cfg(concat!(
881
- "[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\n",
882
- "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\n",
918
+ "[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\non-file = \"cat {path}\"\n",
919
+ "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\non-file = \"cat {path}\"\n",
883
920
  ));
884
921
  let merged = combine_configs(&[(src("/a"), config)]).unwrap();
885
922
  assert_eq!(merged.tables.len(), 2);
@@ -888,8 +925,8 @@ glob = "c/*.json"
888
925
  #[test]
889
926
  fn combine_intra_config_duplicate_in_multi_merge_errors() {
890
927
  let a = cfg(concat!(
891
- "[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\n",
892
- "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\n",
928
+ "[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\non-file = \"cat {path}\"\n",
929
+ "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\non-file = \"cat {path}\"\n",
893
930
  ));
894
931
  let b = cfg("[dirsql]\nignore = [\"c/**\"]\n");
895
932
  let err = combine_configs(&[(src("/a"), a), (src("/b"), b)]).unwrap_err();
@@ -909,8 +946,12 @@ glob = "c/*.json"
909
946
 
910
947
  #[test]
911
948
  fn combine_duplicate_table_name_detected_through_quoting() {
912
- let a = cfg("[[table]]\nddl = 'CREATE TABLE \"t\" (x TEXT)'\nglob = \"a/*.json\"\n");
913
- let b = cfg("[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\n");
949
+ let a = cfg(
950
+ "[[table]]\nddl = 'CREATE TABLE \"t\" (x TEXT)'\nglob = \"a/*.json\"\non-file = \"cat {path}\"\n",
951
+ );
952
+ let b = cfg(
953
+ "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\non-file = \"cat {path}\"\n",
954
+ );
914
955
  let err = combine_configs(&[(src("/a"), a), (src("/b"), b)]).unwrap_err();
915
956
  assert!(
916
957
  matches!(&err, ConfigError::DuplicateTable { name, .. } if name == "t"),
@@ -920,8 +961,12 @@ glob = "c/*.json"
920
961
 
921
962
  #[test]
922
963
  fn combine_unparseable_ddl_concatenates_without_collision_check() {
923
- let a = cfg("[[table]]\nddl = \"not a create table\"\nglob = \"a/*.json\"\n");
924
- let b = cfg("[[table]]\nddl = \"also not a create table\"\nglob = \"b/*.json\"\n");
964
+ let a = cfg(
965
+ "[[table]]\nddl = \"not a create table\"\nglob = \"a/*.json\"\non-file = \"cat {path}\"\n",
966
+ );
967
+ let b = cfg(
968
+ "[[table]]\nddl = \"also not a create table\"\nglob = \"b/*.json\"\non-file = \"cat {path}\"\n",
969
+ );
925
970
  let merged = combine_configs(&[(src("/a"), a), (src("/b"), b)]).unwrap();
926
971
  assert_eq!(merged.tables.len(), 2);
927
972
  }
@@ -967,8 +1012,12 @@ glob = "c/*.json"
967
1012
 
968
1013
  #[test]
969
1014
  fn combine_error_display_includes_package_source_verbatim() {
970
- let a = cfg("[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\n");
971
- let b = cfg("[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\n");
1015
+ let a = cfg(
1016
+ "[[table]]\nddl = \"CREATE TABLE t (x TEXT)\"\nglob = \"a/*.json\"\non-file = \"cat {path}\"\n",
1017
+ );
1018
+ let b = cfg(
1019
+ "[[table]]\nddl = \"CREATE TABLE t (y TEXT)\"\nglob = \"b/*.json\"\non-file = \"cat {path}\"\n",
1020
+ );
972
1021
  let err = combine_configs(&[
973
1022
  (src("/proj/.dirsql.toml"), a),
974
1023
  (Source::Package("dirsql-plugin-notes".to_string()), b),
@@ -982,11 +1031,13 @@ glob = "c/*.json"
982
1031
  #[test]
983
1032
  fn combine_three_configs_concatenates_across_all() {
984
1033
  let a = cfg(
985
- "[dirsql]\nignore = [\"a/**\"]\n\n[[table]]\nddl = \"CREATE TABLE a (x TEXT)\"\nglob = \"a/*\"\n",
1034
+ "[dirsql]\nignore = [\"a/**\"]\n\n[[table]]\nddl = \"CREATE TABLE a (x TEXT)\"\nglob = \"a/*\"\non-file = \"cat {path}\"\n",
1035
+ );
1036
+ let b = cfg(
1037
+ "[[table]]\nddl = \"CREATE TABLE b (x TEXT)\"\nglob = \"b/*\"\non-file = \"cat {path}\"\n",
986
1038
  );
987
- let b = cfg("[[table]]\nddl = \"CREATE TABLE b (x TEXT)\"\nglob = \"b/*\"\n");
988
1039
  let c = cfg(
989
- "[dirsql]\nignore = [\"c/**\"]\n\n[[table]]\nddl = \"CREATE TABLE c (x TEXT)\"\nglob = \"c/*\"\n",
1040
+ "[dirsql]\nignore = [\"c/**\"]\n\n[[table]]\nddl = \"CREATE TABLE c (x TEXT)\"\nglob = \"c/*\"\non-file = \"cat {path}\"\n",
990
1041
  );
991
1042
  let merged = combine_configs(&[(src("/a"), a), (src("/b"), b), (src("/c"), c)]).unwrap();
992
1043
  assert_eq!(merged.ignore, vec!["a/**", "c/**"]);
@@ -1026,6 +1077,7 @@ hook-timeout = 300
1026
1077
  [[table]]
1027
1078
  ddl = "CREATE TABLE t (x TEXT)"
1028
1079
  glob = "*.json"
1080
+ on-file = "cat {path}"
1029
1081
  "#;
1030
1082
  let config = load_config_str(toml).unwrap();
1031
1083
  assert!(config.hook_timeout.is_none());
@@ -1490,28 +1490,17 @@ fn build_tables_from_config(
1490
1490
  let mut tables = Vec::with_capacity(cfg.tables.len());
1491
1491
 
1492
1492
  for table_cfg in &cfg.tables {
1493
- let mut table = match &table_cfg.on_file {
1494
- Some(command) => {
1495
- let command = command.clone();
1496
- let config_dir = config_dir.to_path_buf();
1497
- let root = root.to_path_buf();
1498
- // `Table::new` (infallible): `run_on_file` isolates its own
1499
- // errors to an empty row set so one bad file never aborts the
1500
- // scan (the scan aborts on an on_file `Err`).
1501
- Table::new(
1502
- table_cfg.ddl.clone(),
1503
- table_cfg.glob.clone(),
1504
- move |abs_path: &str| {
1505
- run_on_file(&command, abs_path, &config_dir, &root, timeout)
1506
- },
1507
- )
1508
- }
1509
- None => Table::new(
1510
- table_cfg.ddl.clone(),
1511
- table_cfg.glob.clone(),
1512
- |_path: &str| vec![Row::new()],
1513
- ),
1514
- };
1493
+ let command = table_cfg.on_file.clone();
1494
+ let config_dir = config_dir.to_path_buf();
1495
+ let root = root.to_path_buf();
1496
+ // `Table::new` (infallible): `run_on_file` isolates its own errors to an
1497
+ // empty row set so one bad file never aborts the scan (the scan aborts
1498
+ // on an on_file `Err`).
1499
+ let mut table = Table::new(
1500
+ table_cfg.ddl.clone(),
1501
+ table_cfg.glob.clone(),
1502
+ move |abs_path: &str| run_on_file(&command, abs_path, &config_dir, &root, timeout),
1503
+ );
1515
1504
 
1516
1505
  if table_cfg.strict == Some(true) {
1517
1506
  table.strict = true;
@@ -3091,11 +3080,12 @@ mod internal_tests {
3091
3080
  }
3092
3081
 
3093
3082
  #[test]
3094
- fn build_tables_from_config_creates_plain_and_on_file_tables() {
3083
+ fn build_tables_from_config_creates_on_file_tables() {
3095
3084
  let cfg = config::load_config_str(concat!(
3096
3085
  "[[table]]\n",
3097
3086
  "ddl = \"CREATE TABLE a (x TEXT)\"\n",
3098
- "glob = \"*.a\"\n\n",
3087
+ "glob = \"*.a\"\n",
3088
+ "on-file = \"printf '[{\\\"x\\\":1}]'\"\n\n",
3099
3089
  "[[table]]\n",
3100
3090
  "ddl = \"CREATE TABLE b (y TEXT)\"\n",
3101
3091
  "glob = \"*.b\"\n",
@@ -3112,7 +3102,12 @@ mod internal_tests {
3112
3102
  )
3113
3103
  .unwrap();
3114
3104
  assert_eq!(tables.len(), 2);
3115
- assert_eq!((tables[0].on_file)("/whatever").unwrap().len(), 1);
3105
+ assert_eq!(
3106
+ (tables[0].on_file)(&dir.path().join("f.a").to_string_lossy())
3107
+ .unwrap()
3108
+ .len(),
3109
+ 1
3110
+ );
3116
3111
  assert!(tables[1].strict, "on-file table preserves strict flag");
3117
3112
  }
3118
3113
 
@@ -1,7 +0,0 @@
1
- {
2
- "command": "just test-e2e",
3
- "ran_at": 1784902229,
4
- "exit_code": 0,
5
- "commit": "7571e0d010b096821bfc99b1f893db2b320347dc",
6
- "branch": "feat/634-core-remove-injection"
7
- }
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes