attocode-code-intel 0.1.0__py3-none-any.whl

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 (345) hide show
  1. attocode_code_intel-0.1.0.dist-info/METADATA +221 -0
  2. attocode_code_intel-0.1.0.dist-info/RECORD +345 -0
  3. attocode_code_intel-0.1.0.dist-info/WHEEL +4 -0
  4. attocode_code_intel-0.1.0.dist-info/entry_points.txt +2 -0
  5. attocode_code_intel-0.1.0.dist-info/licenses/LICENSE +21 -0
  6. attocode_intel/GUIDELINES.md +432 -0
  7. attocode_intel/__init__.py +52 -0
  8. attocode_intel/_internal/__init__.py +1 -0
  9. attocode_intel/_internal/errors/__init__.py +126 -0
  10. attocode_intel/_internal/integrations/__init__.py +1 -0
  11. attocode_intel/_internal/integrations/context/__init__.py +1 -0
  12. attocode_intel/_internal/integrations/context/architecture_drift.py +354 -0
  13. attocode_intel/_internal/integrations/context/ast_chunker.py +202 -0
  14. attocode_intel/_internal/integrations/context/ast_service.py +1483 -0
  15. attocode_intel/_internal/integrations/context/blob_oid.py +423 -0
  16. attocode_intel/_internal/integrations/context/cache_manifest.py +221 -0
  17. attocode_intel/_internal/integrations/context/cas.py +466 -0
  18. attocode_intel/_internal/integrations/context/code_analyzer.py +528 -0
  19. attocode_intel/_internal/integrations/context/codebase_ast.py +1461 -0
  20. attocode_intel/_internal/integrations/context/codebase_context.py +1736 -0
  21. attocode_intel/_internal/integrations/context/cross_mode.py +263 -0
  22. attocode_intel/_internal/integrations/context/cross_references.py +616 -0
  23. attocode_intel/_internal/integrations/context/embedding_rotation.py +597 -0
  24. attocode_intel/_internal/integrations/context/embeddings.py +282 -0
  25. attocode_intel/_internal/integrations/context/frecency.py +427 -0
  26. attocode_intel/_internal/integrations/context/fuzzy.py +320 -0
  27. attocode_intel/_internal/integrations/context/hierarchical_explorer.py +331 -0
  28. attocode_intel/_internal/integrations/context/hydration.py +90 -0
  29. attocode_intel/_internal/integrations/context/index_repair.py +87 -0
  30. attocode_intel/_internal/integrations/context/index_store.py +586 -0
  31. attocode_intel/_internal/integrations/context/memory_store.py +602 -0
  32. attocode_intel/_internal/integrations/context/module_resolution.py +52 -0
  33. attocode_intel/_internal/integrations/context/query_constraints.py +361 -0
  34. attocode_intel/_internal/integrations/context/query_history.py +417 -0
  35. attocode_intel/_internal/integrations/context/reranker.py +351 -0
  36. attocode_intel/_internal/integrations/context/semantic_search.py +2931 -0
  37. attocode_intel/_internal/integrations/context/syntax_evidence.py +94 -0
  38. attocode_intel/_internal/integrations/context/systemone_ranker.py +245 -0
  39. attocode_intel/_internal/integrations/context/temporal_coupling.py +411 -0
  40. attocode_intel/_internal/integrations/context/trigram_index.py +820 -0
  41. attocode_intel/_internal/integrations/context/trigram_regex.py +171 -0
  42. attocode_intel/_internal/integrations/context/ts_parser.py +2199 -0
  43. attocode_intel/_internal/integrations/context/vector_store.py +795 -0
  44. attocode_intel/_internal/integrations/feature_flags/__init__.py +357 -0
  45. attocode_intel/_internal/integrations/lsp/__init__.py +1 -0
  46. attocode_intel/_internal/integrations/lsp/client.py +1140 -0
  47. attocode_intel/_internal/integrations/mcp/__init__.py +1 -0
  48. attocode_intel/_internal/integrations/mcp/client.py +253 -0
  49. attocode_intel/_internal/integrations/security/__init__.py +1 -0
  50. attocode_intel/_internal/integrations/security/custom_rules.py +176 -0
  51. attocode_intel/_internal/integrations/security/dataflow.py +522 -0
  52. attocode_intel/_internal/integrations/security/dependency_audit.py +303 -0
  53. attocode_intel/_internal/integrations/security/matcher.py +44 -0
  54. attocode_intel/_internal/integrations/security/patterns.py +724 -0
  55. attocode_intel/_internal/integrations/security/scanner.py +351 -0
  56. attocode_intel/_internal/integrations/utilities/__init__.py +1 -0
  57. attocode_intel/_internal/integrations/utilities/ignore.py +64 -0
  58. attocode_intel/_internal/integrations/utilities/token_estimate.py +51 -0
  59. attocode_intel/_internal/tricks/__init__.py +1 -0
  60. attocode_intel/_internal/tricks/recursive_context.py +357 -0
  61. attocode_intel/_internal/types/__init__.py +1 -0
  62. attocode_intel/_internal/types/events.py +289 -0
  63. attocode_intel/_internal/types/severity.py +15 -0
  64. attocode_intel/_shared.py +341 -0
  65. attocode_intel/analysis_coverage.py +56 -0
  66. attocode_intel/api/__init__.py +1 -0
  67. attocode_intel/api/access.py +32 -0
  68. attocode_intel/api/app.py +247 -0
  69. attocode_intel/api/auth/__init__.py +128 -0
  70. attocode_intel/api/auth/api_keys.py +61 -0
  71. attocode_intel/api/auth/context.py +34 -0
  72. attocode_intel/api/auth/jwt.py +66 -0
  73. attocode_intel/api/auth/oauth.py +146 -0
  74. attocode_intel/api/auth/passwords.py +15 -0
  75. attocode_intel/api/deps.py +351 -0
  76. attocode_intel/api/knowledge_bridge.py +13 -0
  77. attocode_intel/api/mcp_transport.py +51 -0
  78. attocode_intel/api/middleware.py +411 -0
  79. attocode_intel/api/models.py +698 -0
  80. attocode_intel/api/providers/__init__.py +1 -0
  81. attocode_intel/api/providers/db_provider.py +1106 -0
  82. attocode_intel/api/providers/local_provider.py +476 -0
  83. attocode_intel/api/providers/remote_provider.py +740 -0
  84. attocode_intel/api/repository_source.py +21 -0
  85. attocode_intel/api/routes/__init__.py +1 -0
  86. attocode_intel/api/routes/_pin_helper.py +158 -0
  87. attocode_intel/api/routes/activity.py +148 -0
  88. attocode_intel/api/routes/adr.py +102 -0
  89. attocode_intel/api/routes/analysis.py +515 -0
  90. attocode_intel/api/routes/api_keys.py +170 -0
  91. attocode_intel/api/routes/auth.py +428 -0
  92. attocode_intel/api/routes/branches.py +262 -0
  93. attocode_intel/api/routes/cross_repo_search.py +198 -0
  94. attocode_intel/api/routes/embeddings.py +386 -0
  95. attocode_intel/api/routes/files.py +132 -0
  96. attocode_intel/api/routes/files_v2.py +388 -0
  97. attocode_intel/api/routes/gc.py +322 -0
  98. attocode_intel/api/routes/git_v2.py +433 -0
  99. attocode_intel/api/routes/graph.py +174 -0
  100. attocode_intel/api/routes/graph_viz.py +160 -0
  101. attocode_intel/api/routes/health.py +62 -0
  102. attocode_intel/api/routes/history.py +175 -0
  103. attocode_intel/api/routes/jobs.py +84 -0
  104. attocode_intel/api/routes/learning.py +205 -0
  105. attocode_intel/api/routes/lsp.py +272 -0
  106. attocode_intel/api/routes/notify.py +623 -0
  107. attocode_intel/api/routes/operations.py +27 -0
  108. attocode_intel/api/routes/orgs.py +924 -0
  109. attocode_intel/api/routes/preferences.py +100 -0
  110. attocode_intel/api/routes/presence.py +42 -0
  111. attocode_intel/api/routes/projects.py +116 -0
  112. attocode_intel/api/routes/repos.py +47 -0
  113. attocode_intel/api/routes/search.py +180 -0
  114. attocode_intel/api/routes/snapshots.py +614 -0
  115. attocode_intel/api/routes/webhooks.py +313 -0
  116. attocode_intel/api/routes/websocket.py +116 -0
  117. attocode_intel/api/static/graph.html +239 -0
  118. attocode_intel/api/utils.py +96 -0
  119. attocode_intel/artifacts/__init__.py +45 -0
  120. attocode_intel/artifacts/hashing.py +230 -0
  121. attocode_intel/artifacts/provenance.py +190 -0
  122. attocode_intel/artifacts/retrieval_pin.py +159 -0
  123. attocode_intel/audit.py +59 -0
  124. attocode_intel/bug_finder.py +206 -0
  125. attocode_intel/bundle.py +80 -0
  126. attocode_intel/catalog.py +242 -0
  127. attocode_intel/change_review.py +75 -0
  128. attocode_intel/cli.py +3062 -0
  129. attocode_intel/community.py +63 -0
  130. attocode_intel/confidence/__init__.py +144 -0
  131. attocode_intel/confidence/jev.py +234 -0
  132. attocode_intel/confidence/llm.py +330 -0
  133. attocode_intel/confidence/redact.py +44 -0
  134. attocode_intel/confidence/settings.py +74 -0
  135. attocode_intel/config.py +256 -0
  136. attocode_intel/crypto.py +31 -0
  137. attocode_intel/db/__init__.py +7 -0
  138. attocode_intel/db/base.py +33 -0
  139. attocode_intel/db/engine.py +61 -0
  140. attocode_intel/db/models.py +529 -0
  141. attocode_intel/entrypoint.py +185 -0
  142. attocode_intel/focused_evidence.py +130 -0
  143. attocode_intel/freshness.py +154 -0
  144. attocode_intel/gateway.py +734 -0
  145. attocode_intel/git/__init__.py +7 -0
  146. attocode_intel/git/credentials.py +75 -0
  147. attocode_intel/git/manager.py +493 -0
  148. attocode_intel/git/models.py +96 -0
  149. attocode_intel/git/storage.py +98 -0
  150. attocode_intel/graph_query_parser.py +761 -0
  151. attocode_intel/helpers.py +712 -0
  152. attocode_intel/indexing/__init__.py +29 -0
  153. attocode_intel/indexing/debouncer.py +136 -0
  154. attocode_intel/indexing/delta_indexer.py +151 -0
  155. attocode_intel/indexing/full_indexer.py +323 -0
  156. attocode_intel/indexing/incremental.py +240 -0
  157. attocode_intel/indexing/parser.py +403 -0
  158. attocode_intel/indexing/summarizer.py +264 -0
  159. attocode_intel/installer.py +1896 -0
  160. attocode_intel/knowledge.py +269 -0
  161. attocode_intel/local_knowledge.py +77 -0
  162. attocode_intel/migrations/alembic.ini +36 -0
  163. attocode_intel/migrations/env.py +71 -0
  164. attocode_intel/migrations/script.py.mako +27 -0
  165. attocode_intel/migrations/versions/001_initial_schema.py +219 -0
  166. attocode_intel/migrations/versions/002_branch_version_and_embeddings.py +61 -0
  167. attocode_intel/migrations/versions/003_embedding_uniqueness_and_cascade.py +51 -0
  168. attocode_intel/migrations/versions/004_audit_events.py +38 -0
  169. attocode_intel/migrations/versions/005_user_preferences.py +30 -0
  170. attocode_intel/migrations/versions/006_google_oauth.py +27 -0
  171. attocode_intel/migrations/versions/007_pgvector_embeddings.py +28 -0
  172. attocode_intel/migrations/versions/008_symbol_references.py +37 -0
  173. attocode_intel/migrations/versions/009_webhook_secret_encryption.py +25 -0
  174. attocode_intel/migrations/versions/010_add_commits_table.py +40 -0
  175. attocode_intel/migrations/versions/011_commit_changed_files.py +25 -0
  176. attocode_intel/migrations/versions/012_branch_merged_at.py +25 -0
  177. attocode_intel/migrations/versions/013_revoked_tokens.py +32 -0
  178. attocode_intel/migrations/versions/014_blame_hunks.py +40 -0
  179. attocode_intel/migrations/versions/015_commit_file_stats.py +40 -0
  180. attocode_intel/migrations/versions/016_embedding_provenance_columns.py +179 -0
  181. attocode_intel/migrations/versions/017_provenance_table.py +102 -0
  182. attocode_intel/migrations/versions/018_repo_snapshots.py +178 -0
  183. attocode_intel/migrations/versions/019_symref_caller.py +42 -0
  184. attocode_intel/migrations/versions/020_shared_knowledge.py +29 -0
  185. attocode_intel/onboarding.py +258 -0
  186. attocode_intel/output.py +178 -0
  187. attocode_intel/precision.py +133 -0
  188. attocode_intel/presence.py +160 -0
  189. attocode_intel/probe.py +110 -0
  190. attocode_intel/project_dir.py +97 -0
  191. attocode_intel/pubsub.py +113 -0
  192. attocode_intel/query_ranking.py +242 -0
  193. attocode_intel/readiness.py +972 -0
  194. attocode_intel/redis.py +51 -0
  195. attocode_intel/reference_pages.py +60 -0
  196. attocode_intel/remote.py +131 -0
  197. attocode_intel/repo_ranker.py +246 -0
  198. attocode_intel/request_context.py +82 -0
  199. attocode_intel/rules/__init__.py +28 -0
  200. attocode_intel/rules/ci.py +320 -0
  201. attocode_intel/rules/combinators.py +293 -0
  202. attocode_intel/rules/enricher.py +127 -0
  203. attocode_intel/rules/evolution.py +452 -0
  204. attocode_intel/rules/executor.py +531 -0
  205. attocode_intel/rules/filters/__init__.py +5 -0
  206. attocode_intel/rules/filters/pipeline.py +151 -0
  207. attocode_intel/rules/formatter.py +198 -0
  208. attocode_intel/rules/hygiene.py +242 -0
  209. attocode_intel/rules/importers/__init__.py +1 -0
  210. attocode_intel/rules/importers/semgrep.py +382 -0
  211. attocode_intel/rules/loader.py +292 -0
  212. attocode_intel/rules/marketplace.py +375 -0
  213. attocode_intel/rules/metavar.py +181 -0
  214. attocode_intel/rules/model.py +317 -0
  215. attocode_intel/rules/packs/__init__.py +1 -0
  216. attocode_intel/rules/packs/community/_license_templates/Apache-2.0.txt +176 -0
  217. attocode_intel/rules/packs/community/_license_templates/MIT.txt +21 -0
  218. attocode_intel/rules/packs/community/bandit-python/LICENSE +176 -0
  219. attocode_intel/rules/packs/community/bandit-python/NOTICE +13 -0
  220. attocode_intel/rules/packs/community/bandit-python/PORTING.md +23 -0
  221. attocode_intel/rules/packs/community/bandit-python/manifest.yaml +14 -0
  222. attocode_intel/rules/packs/community/bandit-python/rules/B105-hardcoded-password.yaml +23 -0
  223. attocode_intel/rules/packs/community/bandit-python/rules/B303-weak-md5.yaml +21 -0
  224. attocode_intel/rules/packs/community/bandit-python/rules/B304-weak-des.yaml +20 -0
  225. attocode_intel/rules/packs/community/bandit-python/rules/B307-use-of-eval.yaml +22 -0
  226. attocode_intel/rules/packs/community/bandit-python/rules/B324-weak-sha1.yaml +21 -0
  227. attocode_intel/rules/packs/community/bandit-python/rules/B501-no-cert-validation.yaml +23 -0
  228. attocode_intel/rules/packs/community/bandit-python/rules/B602-shell-true.yaml +22 -0
  229. attocode_intel/rules/packs/community/bandit-python/rules/B608-sqli.yaml +22 -0
  230. attocode_intel/rules/packs/community/eslint-typescript/LICENSE +21 -0
  231. attocode_intel/rules/packs/community/eslint-typescript/NOTICE +13 -0
  232. attocode_intel/rules/packs/community/eslint-typescript/PORTING.md +23 -0
  233. attocode_intel/rules/packs/community/eslint-typescript/manifest.yaml +14 -0
  234. attocode_intel/rules/packs/community/eslint-typescript/rules/eqeqeq.yaml +20 -0
  235. attocode_intel/rules/packs/community/eslint-typescript/rules/no-eval.yaml +22 -0
  236. attocode_intel/rules/packs/community/eslint-typescript/rules/no-implied-eval.yaml +20 -0
  237. attocode_intel/rules/packs/community/eslint-typescript/rules/no-new-func.yaml +21 -0
  238. attocode_intel/rules/packs/community/eslint-typescript/rules/no-throw-literal.yaml +19 -0
  239. attocode_intel/rules/packs/community/eslint-typescript/rules/no-var.yaml +20 -0
  240. attocode_intel/rules/packs/community/eslint-typescript/rules/no-with.yaml +18 -0
  241. attocode_intel/rules/packs/community/gosec-go/LICENSE +176 -0
  242. attocode_intel/rules/packs/community/gosec-go/NOTICE +13 -0
  243. attocode_intel/rules/packs/community/gosec-go/PORTING.md +23 -0
  244. attocode_intel/rules/packs/community/gosec-go/manifest.yaml +14 -0
  245. attocode_intel/rules/packs/community/gosec-go/rules/G101-hardcoded-credentials.yaml +22 -0
  246. attocode_intel/rules/packs/community/gosec-go/rules/G102-bind-all-interfaces.yaml +21 -0
  247. attocode_intel/rules/packs/community/gosec-go/rules/G103-unsafe-block.yaml +21 -0
  248. attocode_intel/rules/packs/community/gosec-go/rules/G201-sql-format.yaml +21 -0
  249. attocode_intel/rules/packs/community/gosec-go/rules/G304-file-inclusion.yaml +23 -0
  250. attocode_intel/rules/packs/community/gosec-go/rules/G401-weak-cipher.yaml +20 -0
  251. attocode_intel/rules/packs/community/gosec-go/rules/G402-tls-min-version.yaml +20 -0
  252. attocode_intel/rules/packs/community/gosec-go/rules/G501-md5-import.yaml +21 -0
  253. attocode_intel/rules/packs/examples/cpp/manifest.yaml +4 -0
  254. attocode_intel/rules/packs/examples/cpp/rules/security.yaml +90 -0
  255. attocode_intel/rules/packs/examples/cpp/rules/structural.yaml +42 -0
  256. attocode_intel/rules/packs/examples/csharp/manifest.yaml +4 -0
  257. attocode_intel/rules/packs/examples/csharp/rules/security.yaml +69 -0
  258. attocode_intel/rules/packs/examples/csharp/rules/structural.yaml +42 -0
  259. attocode_intel/rules/packs/examples/go/manifest.yaml +4 -0
  260. attocode_intel/rules/packs/examples/go/rules/performance.yaml +136 -0
  261. attocode_intel/rules/packs/examples/go/rules/security.yaml +48 -0
  262. attocode_intel/rules/packs/examples/go/rules/structural.yaml +58 -0
  263. attocode_intel/rules/packs/examples/go/taint/sanitizers.yaml +24 -0
  264. attocode_intel/rules/packs/examples/go/taint/sinks.yaml +51 -0
  265. attocode_intel/rules/packs/examples/go/taint/sources.yaml +26 -0
  266. attocode_intel/rules/packs/examples/java/manifest.yaml +4 -0
  267. attocode_intel/rules/packs/examples/java/rules/correctness.yaml +55 -0
  268. attocode_intel/rules/packs/examples/java/rules/structural.yaml +48 -0
  269. attocode_intel/rules/packs/examples/java/taint/sinks.yaml +37 -0
  270. attocode_intel/rules/packs/examples/java/taint/sources.yaml +21 -0
  271. attocode_intel/rules/packs/examples/kotlin/manifest.yaml +4 -0
  272. attocode_intel/rules/packs/examples/kotlin/rules/correctness.yaml +50 -0
  273. attocode_intel/rules/packs/examples/kotlin/rules/structural.yaml +38 -0
  274. attocode_intel/rules/packs/examples/php/manifest.yaml +4 -0
  275. attocode_intel/rules/packs/examples/php/rules/security.yaml +66 -0
  276. attocode_intel/rules/packs/examples/php/rules/structural.yaml +41 -0
  277. attocode_intel/rules/packs/examples/python/manifest.yaml +4 -0
  278. attocode_intel/rules/packs/examples/python/rules/performance.yaml +90 -0
  279. attocode_intel/rules/packs/examples/python/rules/structural.yaml +55 -0
  280. attocode_intel/rules/packs/examples/ruby/manifest.yaml +4 -0
  281. attocode_intel/rules/packs/examples/ruby/rules/security.yaml +73 -0
  282. attocode_intel/rules/packs/examples/ruby/rules/structural.yaml +41 -0
  283. attocode_intel/rules/packs/examples/rust/manifest.yaml +4 -0
  284. attocode_intel/rules/packs/examples/rust/rules/correctness.yaml +51 -0
  285. attocode_intel/rules/packs/examples/rust/rules/structural.yaml +49 -0
  286. attocode_intel/rules/packs/examples/typescript/manifest.yaml +4 -0
  287. attocode_intel/rules/packs/examples/typescript/rules/performance.yaml +70 -0
  288. attocode_intel/rules/packs/examples/typescript/rules/structural.yaml +48 -0
  289. attocode_intel/rules/packs/pack_loader.py +244 -0
  290. attocode_intel/rules/plugins/__init__.py +1 -0
  291. attocode_intel/rules/plugins/plugin_loader.py +132 -0
  292. attocode_intel/rules/profiling.py +332 -0
  293. attocode_intel/rules/registry.py +213 -0
  294. attocode_intel/rules/sarif.py +187 -0
  295. attocode_intel/rules/synthesis.py +420 -0
  296. attocode_intel/rules/testing.py +326 -0
  297. attocode_intel/server.py +734 -0
  298. attocode_intel/service.py +3416 -0
  299. attocode_intel/sharing.py +57 -0
  300. attocode_intel/storage/__init__.py +6 -0
  301. attocode_intel/storage/branch_overlay.py +352 -0
  302. attocode_intel/storage/content_store.py +220 -0
  303. attocode_intel/storage/dependency_store.py +143 -0
  304. attocode_intel/storage/diff_engine.py +187 -0
  305. attocode_intel/storage/embedding_store.py +594 -0
  306. attocode_intel/storage/provenance_store.py +137 -0
  307. attocode_intel/storage/security_scanner_db.py +164 -0
  308. attocode_intel/storage/symbol_store.py +160 -0
  309. attocode_intel/structural_evidence.py +144 -0
  310. attocode_intel/symbol_inspection.py +141 -0
  311. attocode_intel/symbol_links.py +167 -0
  312. attocode_intel/telemetry.py +42 -0
  313. attocode_intel/test_ranking.py +73 -0
  314. attocode_intel/testing/__init__.py +43 -0
  315. attocode_intel/testing/fixtures.py +122 -0
  316. attocode_intel/testing/helpers.py +75 -0
  317. attocode_intel/testing/mocks.py +99 -0
  318. attocode_intel/tools/__init__.py +2 -0
  319. attocode_intel/tools/adr_tools.py +628 -0
  320. attocode_intel/tools/analysis_tools.py +382 -0
  321. attocode_intel/tools/composite_tools.py +695 -0
  322. attocode_intel/tools/cross_mode_tools.py +173 -0
  323. attocode_intel/tools/dead_code_tools.py +582 -0
  324. attocode_intel/tools/distill_tools.py +353 -0
  325. attocode_intel/tools/frecency_tools.py +220 -0
  326. attocode_intel/tools/fuzzy_tools.py +255 -0
  327. attocode_intel/tools/history_tools.py +486 -0
  328. attocode_intel/tools/learning_tools.py +222 -0
  329. attocode_intel/tools/lsp_tools.py +218 -0
  330. attocode_intel/tools/maintenance_tools.py +1662 -0
  331. attocode_intel/tools/navigation_tools.py +220 -0
  332. attocode_intel/tools/overlay_tools.py +540 -0
  333. attocode_intel/tools/pin_store.py +432 -0
  334. attocode_intel/tools/pin_tools.py +266 -0
  335. attocode_intel/tools/query_constraints_tools.py +262 -0
  336. attocode_intel/tools/query_history_tools.py +158 -0
  337. attocode_intel/tools/readiness_tools.py +44 -0
  338. attocode_intel/tools/rule_tools.py +992 -0
  339. attocode_intel/tools/search_tools.py +770 -0
  340. attocode_intel/tools/snapshot_tools.py +624 -0
  341. attocode_intel/workers/__init__.py +1 -0
  342. attocode_intel/workers/job_utils.py +111 -0
  343. attocode_intel/workers/jobs.py +573 -0
  344. attocode_intel/workers/run.py +30 -0
  345. attocode_intel/workers/settings.py +61 -0
@@ -0,0 +1,242 @@
1
+ """One catalog for protocol schemas, profiles, and documentation."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from copy import deepcopy
6
+
7
+ from mcp.types import Tool, ToolAnnotations
8
+
9
+ INSTRUCTIONS = (
10
+ "If these tools are deferred (for example in Claude Code), load them with ToolSearch, for example "
11
+ "'attocode-code-intel inspect_symbol'. For a known symbol, call inspect_symbol. For unfamiliar behavior, "
12
+ "call bootstrap with a task_hint. Use search_symbols to find names, and impact_analysis and suggest_tests "
13
+ "to plan and check a change. Grep stays useful for literal text. Cite each excerpt range separately. "
14
+ "An incomplete index does not prove that a dependency is absent. {watch} Keep uncommitted code local."
15
+ )
16
+ # ponytail: two variants of one sentence; the server knows whether it watches files.
17
+ WATCHING = "The server watches the project, so it indexes your edits without a call."
18
+ NOT_WATCHING = "This server does not watch files: after edits, call notify_file_changed."
19
+ INSTRUCTIONS, INSTRUCTIONS_NO_WATCH = INSTRUCTIONS.format(watch=WATCHING), INSTRUCTIONS.format(watch=NOT_WATCHING)
20
+ DAILY = frozenset(
21
+ {
22
+ "bootstrap",
23
+ "project_summary",
24
+ "explore_codebase",
25
+ "search_symbols",
26
+ "inspect_symbol",
27
+ "semantic_search",
28
+ "fast_search",
29
+ "symbols",
30
+ "relevant_context",
31
+ "cross_references",
32
+ "dependencies",
33
+ "call_graph",
34
+ "impact_analysis",
35
+ "suggest_tests",
36
+ "review_change",
37
+ "notify_file_changed",
38
+ "hydration_status",
39
+ "recall",
40
+ "record_learning",
41
+ "list_learnings",
42
+ "learning_feedback",
43
+ }
44
+ )
45
+ # Remote daily keeps the learnings for team knowledge. A local daily session leaves them out:
46
+ # their schemas cost about 1,600 tokens in every model request.
47
+ LEARNING = frozenset({"recall", "record_learning", "list_learnings", "learning_feedback", "update_learning"})
48
+ WRITES = frozenset(
49
+ [
50
+ "notify_file_changed",
51
+ "record_adr",
52
+ "update_adr_status",
53
+ "pin_current",
54
+ "pin_delete",
55
+ "track_file_access",
56
+ "clear_frecency",
57
+ "record_learning",
58
+ "learning_feedback",
59
+ "update_learning",
60
+ "reindex",
61
+ "track_query_result",
62
+ "clear_query_history",
63
+ "migrate_cache",
64
+ "clear_symbols",
65
+ "clear_embeddings",
66
+ "clear_trigrams",
67
+ "clear_kw_index",
68
+ "clear_learnings",
69
+ "clear_adrs",
70
+ "clear_all",
71
+ "cas_clear",
72
+ "export_learnings",
73
+ "import_learnings",
74
+ "export_adrs_markdown",
75
+ "import_adrs_markdown",
76
+ "gc_run",
77
+ "embeddings_rotate_start",
78
+ "embeddings_rotate_step",
79
+ "embeddings_rotate_cutover",
80
+ "embeddings_rotate_gc_old",
81
+ "embeddings_rotate_abort",
82
+ "snapshot_create",
83
+ "snapshot_delete",
84
+ "snapshot_restore",
85
+ "overlay_create",
86
+ "overlay_activate",
87
+ "overlay_delete",
88
+ "install_pack",
89
+ "register_rule",
90
+ "rule_feedback",
91
+ "evolve_rules",
92
+ "synthesize_rule",
93
+ "rule_hygiene",
94
+ "install_community_pack",
95
+ "import_rules",
96
+ ]
97
+ )
98
+ REMOTE_WRITES = frozenset(
99
+ {"record_learning", "learning_feedback", "record_adr", "update_adr_status", "update_learning"}
100
+ )
101
+
102
+
103
+ def compact_schema(node, names=False):
104
+ """The input schema that a model reads: no pydantic titles, and no null branch for an optional argument.
105
+
106
+ NAMES marks a map of property names, whose keys are not schema keywords. Validation keeps the full
107
+ schema, so an explicit null stays valid.
108
+ """
109
+ if isinstance(node, list):
110
+ return [compact_schema(item) for item in node]
111
+ if not isinstance(node, dict):
112
+ return node
113
+ if names:
114
+ return {key: compact_schema(value) for key, value in node.items()}
115
+ node = {key: compact_schema(value, key in ("properties", "$defs", "definitions"))
116
+ for key, value in node.items() if key != "title"}
117
+ options = node.get("anyOf")
118
+ if (isinstance(options, list) and len(options) == 2 and {"type": "null"} in options
119
+ and "default" in node and node["default"] is None):
120
+ del node["anyOf"], node["default"]
121
+ node.update(next(option for option in options if option != {"type": "null"}))
122
+ return node
123
+
124
+
125
+ def remote_available(name):
126
+ return not is_write(name) or name in REMOTE_WRITES
127
+
128
+
129
+ def registered_tools():
130
+ from attocode_intel.server import mcp
131
+
132
+ return mcp._tool_manager._tools
133
+
134
+
135
+ def is_write(name: str) -> bool:
136
+ return name in WRITES
137
+
138
+
139
+ def tool_catalog(profile: str = "full", *, remote: bool = False) -> list[Tool]:
140
+ if profile not in ("daily", "full"):
141
+ raise ValueError("profile must be daily or full")
142
+ result = []
143
+ for name, tool in registered_tools().items():
144
+ if profile == "daily" and name not in DAILY:
145
+ continue
146
+ if remote and not remote_available(name):
147
+ continue
148
+ schema = deepcopy(tool.parameters)
149
+ schema.setdefault("properties", {}).update(
150
+ {
151
+ "workspace": {
152
+ "type": "string",
153
+ "description": "Local project path or authorized remote repository ID.",
154
+ },
155
+ "revision": {
156
+ "type": "string",
157
+ "description": "Remote branch or commit; omitted uses the default branch.",
158
+ },
159
+ }
160
+ )
161
+ schema["properties"]["max_tokens"] = {
162
+ "type": "integer",
163
+ "minimum": 1,
164
+ "maximum": 32000,
165
+ "default": 8000,
166
+ "description": "Maximum tokens in the complete readable response, including provenance.",
167
+ }
168
+ result.append(
169
+ Tool(
170
+ name=name,
171
+ description=tool.description,
172
+ inputSchema=schema,
173
+ annotations=ToolAnnotations(
174
+ readOnlyHint=not is_write(name),
175
+ destructiveHint=name.startswith(("clear_", "delete_"))
176
+ or name
177
+ in {"snapshot_delete", "snapshot_restore", "overlay_delete", "pin_delete"},
178
+ ),
179
+ )
180
+ )
181
+ result.extend(
182
+ [
183
+ Tool(
184
+ name="update_learning",
185
+ description="Edit or archive a repository learning.",
186
+ inputSchema={
187
+ "type": "object",
188
+ "required": ["learning_id"],
189
+ "properties": {
190
+ "learning_id": {"type": "integer"},
191
+ "description": {"type": "string"},
192
+ "details": {"type": "string"},
193
+ "status": {"type": "string", "enum": ["active", "archived"]},
194
+ "confidence": {"type": "number", "minimum": 0, "maximum": 1},
195
+ "workspace": {"type": "string"},
196
+ "revision": {"type": "string"},
197
+ },
198
+ },
199
+ annotations=ToolAnnotations(readOnlyHint=False),
200
+ ),
201
+ Tool(
202
+ name="cross_repo_search",
203
+ description="Search explicitly selected authorized repositories; results retain repository and commit provenance.",
204
+ inputSchema={
205
+ "type": "object",
206
+ "required": ["query", "workspaces"],
207
+ "properties": {
208
+ "query": {"type": "string"},
209
+ "workspaces": {
210
+ "type": "array",
211
+ "items": {"type": "string"},
212
+ "minItems": 1,
213
+ "maxItems": 20,
214
+ },
215
+ "top_k": {"type": "integer", "minimum": 1, "maximum": 50},
216
+ },
217
+ },
218
+ annotations=ToolAnnotations(readOnlyHint=True),
219
+ ),
220
+ ]
221
+ )
222
+ result.append(
223
+ Tool(
224
+ name="capabilities",
225
+ description="Available tools, profiles, workspace selection, and optional enhancements.",
226
+ inputSchema={
227
+ "type": "object",
228
+ "properties": {"workspace": {"type": "string"}, "revision": {"type": "string"}},
229
+ },
230
+ annotations=ToolAnnotations(readOnlyHint=True),
231
+ )
232
+ )
233
+ # Apply common arguments to synthetic tools too (knowledge and cross-repo search).
234
+ for tool in result:
235
+ tool.inputSchema.setdefault("properties", {}).setdefault("max_tokens", {
236
+ "type": "integer", "minimum": 1, "maximum": 32000, "default": 8000,
237
+ "description": "Readable response budget; daily MCP budgets the entire serialized result.",
238
+ })
239
+ if not remote: # local analysis always reads the working tree
240
+ tool.inputSchema["properties"].pop("revision", None)
241
+ local_daily = profile == "daily" and not remote
242
+ return [tool for tool in result if not (local_daily and tool.name in LEARNING)]
@@ -0,0 +1,75 @@
1
+ """Compose findings as data so incomplete passes cannot become a clean review."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from dataclasses import asdict
6
+ from pathlib import Path
7
+
8
+
9
+ def review(service, files, mode="full"):
10
+ from attocode_intel.tools.composite_tools import _git_modified_files
11
+
12
+ files = files if files is not None else _git_modified_files(service.project_dir)
13
+ if mode not in {"quick", "full"}:
14
+ raise ValueError("mode must be quick or full")
15
+ root = Path(service.project_dir)
16
+ selected = {str((root / path).resolve().relative_to(root)) for path in files}
17
+ findings, passes = [], []
18
+ if not selected:
19
+ return {
20
+ "files": [],
21
+ "findings": [],
22
+ "passes": [],
23
+ "complete": False,
24
+ "assessment": "No files selected; review did not run.",
25
+ }
26
+ try:
27
+ report = service.security_scan_data(mode="full")
28
+ for finding in report["findings"]:
29
+ path = str((root / finding["file_path"]).resolve().relative_to(root))
30
+ if path in selected:
31
+ findings.append({**finding, "file_path": path, "pass": "security"})
32
+ passes.append({"name": "security", "status": "completed"})
33
+ except Exception as exc:
34
+ passes.append({"name": "security", "status": "failed", "error": str(exc)})
35
+ if mode == "full":
36
+ try:
37
+ from attocode_intel import confidence
38
+ from attocode_intel.confidence.settings import workspace
39
+ from attocode_intel.rules.enricher import enrich_findings
40
+ from attocode_intel.rules.executor import execute_rules
41
+ from attocode_intel.rules.filters.pipeline import run_pipeline
42
+ from attocode_intel.tools.rule_tools import _collect_files, _get_registry
43
+
44
+ with workspace(service.project_dir):
45
+ rules = _get_registry().query(min_confidence=confidence.rule_threshold(0.5))
46
+ scanned = _collect_files(sorted(selected), "", service.project_dir)
47
+ result = run_pipeline(
48
+ execute_rules(scanned, rules, project_dir=service.project_dir), min_confidence=0.5,
49
+ project_dir=service.project_dir,
50
+ )
51
+ enrich_findings(result, project_dir=service.project_dir)
52
+ findings.extend(
53
+ {**asdict(finding), "file_path": finding.file, "pass": "rules"}
54
+ for finding in result
55
+ )
56
+ passes.append(
57
+ {
58
+ "name": "rules",
59
+ "status": "completed" if rules and scanned else "unavailable",
60
+ "files_scanned": len(scanned),
61
+ "confidence": {k: v for k, v in confidence.last_report().items() if k != "findings"},
62
+ }
63
+ )
64
+ except Exception as exc:
65
+ passes.append({"name": "rules", "status": "failed", "error": str(exc)})
66
+ complete = all(item["status"] == "completed" for item in passes)
67
+ return {
68
+ "files": sorted(selected),
69
+ "findings": findings,
70
+ "passes": passes,
71
+ "complete": complete,
72
+ "assessment": f"{len(findings)} findings from completed checks."
73
+ if complete
74
+ else "Review incomplete. Inspect the failed or unavailable passes.",
75
+ }