agentforge-graph 0.3.2__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 (151) hide show
  1. agentforge_graph/__init__.py +6 -0
  2. agentforge_graph/chunking/__init__.py +12 -0
  3. agentforge_graph/chunking/cast.py +159 -0
  4. agentforge_graph/chunking/chunk.py +19 -0
  5. agentforge_graph/chunking/tokens.py +15 -0
  6. agentforge_graph/cli.py +607 -0
  7. agentforge_graph/config.py +259 -0
  8. agentforge_graph/core/__init__.py +54 -0
  9. agentforge_graph/core/conformance.py +270 -0
  10. agentforge_graph/core/contracts.py +163 -0
  11. agentforge_graph/core/kinds.py +68 -0
  12. agentforge_graph/core/models.py +134 -0
  13. agentforge_graph/core/provenance.py +62 -0
  14. agentforge_graph/core/symbols.py +116 -0
  15. agentforge_graph/embed/__init__.py +28 -0
  16. agentforge_graph/embed/base.py +22 -0
  17. agentforge_graph/embed/bedrock.py +85 -0
  18. agentforge_graph/embed/fake.py +34 -0
  19. agentforge_graph/embed/openai.py +67 -0
  20. agentforge_graph/embed/pipeline.py +184 -0
  21. agentforge_graph/embed/registry.py +66 -0
  22. agentforge_graph/embed/report.py +15 -0
  23. agentforge_graph/enrich/__init__.py +70 -0
  24. agentforge_graph/enrich/anthropic.py +38 -0
  25. agentforge_graph/enrich/anthropic_client.py +109 -0
  26. agentforge_graph/enrich/bedrock.py +24 -0
  27. agentforge_graph/enrich/bedrock_client.py +115 -0
  28. agentforge_graph/enrich/bedrock_summarizer.py +23 -0
  29. agentforge_graph/enrich/claude.py +172 -0
  30. agentforge_graph/enrich/enricher.py +108 -0
  31. agentforge_graph/enrich/governs.py +173 -0
  32. agentforge_graph/enrich/governs_enricher.py +152 -0
  33. agentforge_graph/enrich/heuristics.py +224 -0
  34. agentforge_graph/enrich/judge.py +63 -0
  35. agentforge_graph/enrich/registry.py +133 -0
  36. agentforge_graph/enrich/report.py +60 -0
  37. agentforge_graph/enrich/summarizer.py +62 -0
  38. agentforge_graph/enrich/summary_enricher.py +211 -0
  39. agentforge_graph/enrich/taxonomy.py +38 -0
  40. agentforge_graph/frameworks/__init__.py +29 -0
  41. agentforge_graph/frameworks/base.py +75 -0
  42. agentforge_graph/frameworks/detect.py +124 -0
  43. agentforge_graph/frameworks/extractor.py +63 -0
  44. agentforge_graph/frameworks/orm.py +93 -0
  45. agentforge_graph/frameworks/packs/_js_ast.py +56 -0
  46. agentforge_graph/frameworks/packs/_python_ast.py +157 -0
  47. agentforge_graph/frameworks/packs/django/__init__.py +240 -0
  48. agentforge_graph/frameworks/packs/django/models.scm +7 -0
  49. agentforge_graph/frameworks/packs/express/__init__.py +133 -0
  50. agentforge_graph/frameworks/packs/express/routes.scm +8 -0
  51. agentforge_graph/frameworks/packs/fastapi/__init__.py +210 -0
  52. agentforge_graph/frameworks/packs/fastapi/depends.scm +6 -0
  53. agentforge_graph/frameworks/packs/fastapi/routes.scm +10 -0
  54. agentforge_graph/frameworks/packs/flask/__init__.py +143 -0
  55. agentforge_graph/frameworks/packs/flask/routes.scm +11 -0
  56. agentforge_graph/frameworks/packs/nestjs/__init__.py +205 -0
  57. agentforge_graph/frameworks/packs/nestjs/routes.scm +6 -0
  58. agentforge_graph/frameworks/packs/spring/__init__.py +267 -0
  59. agentforge_graph/frameworks/packs/spring/routes.scm +6 -0
  60. agentforge_graph/frameworks/packs/sqlalchemy/__init__.py +250 -0
  61. agentforge_graph/frameworks/packs/sqlalchemy/models.scm +7 -0
  62. agentforge_graph/frameworks/registry.py +44 -0
  63. agentforge_graph/ingest/__init__.py +30 -0
  64. agentforge_graph/ingest/codegraph.py +847 -0
  65. agentforge_graph/ingest/extractor.py +353 -0
  66. agentforge_graph/ingest/incremental/__init__.py +25 -0
  67. agentforge_graph/ingest/incremental/detect.py +118 -0
  68. agentforge_graph/ingest/incremental/dirty.py +61 -0
  69. agentforge_graph/ingest/incremental/indexer.py +218 -0
  70. agentforge_graph/ingest/incremental/meta.py +72 -0
  71. agentforge_graph/ingest/incremental/ports.py +39 -0
  72. agentforge_graph/ingest/pack.py +160 -0
  73. agentforge_graph/ingest/packs/__init__.py +34 -0
  74. agentforge_graph/ingest/packs/cpp/__init__.py +35 -0
  75. agentforge_graph/ingest/packs/cpp/references.scm +15 -0
  76. agentforge_graph/ingest/packs/cpp/structure.scm +49 -0
  77. agentforge_graph/ingest/packs/csharp/__init__.py +35 -0
  78. agentforge_graph/ingest/packs/csharp/references.scm +12 -0
  79. agentforge_graph/ingest/packs/csharp/structure.scm +45 -0
  80. agentforge_graph/ingest/packs/go/__init__.py +38 -0
  81. agentforge_graph/ingest/packs/go/references.scm +12 -0
  82. agentforge_graph/ingest/packs/go/structure.scm +64 -0
  83. agentforge_graph/ingest/packs/java/__init__.py +35 -0
  84. agentforge_graph/ingest/packs/java/references.scm +12 -0
  85. agentforge_graph/ingest/packs/java/structure.scm +38 -0
  86. agentforge_graph/ingest/packs/javascript/__init__.py +34 -0
  87. agentforge_graph/ingest/packs/javascript/references.scm +11 -0
  88. agentforge_graph/ingest/packs/javascript/structure.scm +166 -0
  89. agentforge_graph/ingest/packs/php/__init__.py +35 -0
  90. agentforge_graph/ingest/packs/php/references.scm +15 -0
  91. agentforge_graph/ingest/packs/php/structure.scm +44 -0
  92. agentforge_graph/ingest/packs/python/__init__.py +25 -0
  93. agentforge_graph/ingest/packs/python/references.scm +14 -0
  94. agentforge_graph/ingest/packs/python/structure.scm +57 -0
  95. agentforge_graph/ingest/packs/ruby/__init__.py +37 -0
  96. agentforge_graph/ingest/packs/ruby/references.scm +12 -0
  97. agentforge_graph/ingest/packs/ruby/structure.scm +37 -0
  98. agentforge_graph/ingest/packs/rust/__init__.py +39 -0
  99. agentforge_graph/ingest/packs/rust/references.scm +12 -0
  100. agentforge_graph/ingest/packs/rust/structure.scm +46 -0
  101. agentforge_graph/ingest/packs/typescript/__init__.py +31 -0
  102. agentforge_graph/ingest/packs/typescript/references.scm +11 -0
  103. agentforge_graph/ingest/packs/typescript/structure.scm +99 -0
  104. agentforge_graph/ingest/pipeline.py +134 -0
  105. agentforge_graph/ingest/report.py +84 -0
  106. agentforge_graph/ingest/resolver.py +467 -0
  107. agentforge_graph/ingest/source.py +79 -0
  108. agentforge_graph/knowledge/__init__.py +28 -0
  109. agentforge_graph/knowledge/adr.py +136 -0
  110. agentforge_graph/knowledge/commits.py +152 -0
  111. agentforge_graph/knowledge/ingest.py +312 -0
  112. agentforge_graph/knowledge/mentions.py +71 -0
  113. agentforge_graph/knowledge/report.py +32 -0
  114. agentforge_graph/main.py +21 -0
  115. agentforge_graph/providers.py +36 -0
  116. agentforge_graph/repomap/__init__.py +14 -0
  117. agentforge_graph/repomap/rank.py +161 -0
  118. agentforge_graph/repomap/render.py +55 -0
  119. agentforge_graph/repomap/repomap.py +66 -0
  120. agentforge_graph/retrieve/__init__.py +21 -0
  121. agentforge_graph/retrieve/pack.py +76 -0
  122. agentforge_graph/retrieve/rerank.py +251 -0
  123. agentforge_graph/retrieve/retriever.py +286 -0
  124. agentforge_graph/retrieve/scoring.py +36 -0
  125. agentforge_graph/serve/__init__.py +19 -0
  126. agentforge_graph/serve/engine.py +204 -0
  127. agentforge_graph/serve/http_runner.py +133 -0
  128. agentforge_graph/serve/server.py +110 -0
  129. agentforge_graph/serve/tools.py +307 -0
  130. agentforge_graph/store/__init__.py +32 -0
  131. agentforge_graph/store/_rowmap.py +102 -0
  132. agentforge_graph/store/errors.py +22 -0
  133. agentforge_graph/store/facade.py +89 -0
  134. agentforge_graph/store/kuzu_store.py +380 -0
  135. agentforge_graph/store/lance_store.py +146 -0
  136. agentforge_graph/store/neo4j_store.py +294 -0
  137. agentforge_graph/store/pgvector_store.py +170 -0
  138. agentforge_graph/store/registry.py +45 -0
  139. agentforge_graph/temporal/__init__.py +36 -0
  140. agentforge_graph/temporal/backfill.py +338 -0
  141. agentforge_graph/temporal/events.py +82 -0
  142. agentforge_graph/temporal/index.py +190 -0
  143. agentforge_graph/temporal/mining.py +190 -0
  144. agentforge_graph/temporal/recorder.py +114 -0
  145. agentforge_graph/temporal/store.py +282 -0
  146. agentforge_graph-0.3.2.dist-info/METADATA +291 -0
  147. agentforge_graph-0.3.2.dist-info/RECORD +151 -0
  148. agentforge_graph-0.3.2.dist-info/WHEEL +4 -0
  149. agentforge_graph-0.3.2.dist-info/entry_points.txt +3 -0
  150. agentforge_graph-0.3.2.dist-info/licenses/LICENSE +202 -0
  151. agentforge_graph-0.3.2.dist-info/licenses/NOTICE +14 -0
@@ -0,0 +1,45 @@
1
+ ; C# structure queries (feat-002, pack-csharp).
2
+ ; Namespace-prefix import model: `using App.Geo` names a *namespace* (not a class),
3
+ ; so it resolves to every in-repo file declaring that namespace.
4
+
5
+ ; --- namespace (block or file-scoped) ---
6
+ (namespace_declaration
7
+ name: (_) @namespace)
8
+ (file_scoped_namespace_declaration
9
+ name: (_) @namespace)
10
+
11
+ ; --- definitions ---
12
+ (class_declaration
13
+ name: (identifier) @name) @def.class
14
+
15
+ ; --- inheritance (INHERITS): `class B : A, IFoo`. The base_list mixes the base
16
+ ; class with interfaces (C# doesn't distinguish syntactically); only an entry
17
+ ; that resolves to an in-repo class becomes an INHERITS edge (interfaces, which
18
+ ; aren't Class nodes, drop out in the resolver). ---
19
+ (class_declaration
20
+ (base_list (identifier) @base.name)) @base.def
21
+
22
+ (interface_declaration
23
+ name: (identifier) @name) @def.interface
24
+
25
+ ; struct + enum + record -> Class (named nominal types).
26
+ (struct_declaration
27
+ name: (identifier) @name) @def.class
28
+
29
+ (enum_declaration
30
+ name: (identifier) @name) @def.class
31
+
32
+ (record_declaration
33
+ name: (identifier) @name) @def.class
34
+
35
+ ; methods + constructors live in a type body -> promoted to Method.
36
+ (method_declaration
37
+ name: (identifier) @name) @def.function
38
+
39
+ (constructor_declaration
40
+ name: (identifier) @name) @def.function
41
+
42
+ ; --- imports ---
43
+ ; `using System;` / `using App.Shapes;` -> a namespace (resolved to its files).
44
+ (using_directive
45
+ [(identifier) (qualified_name)] @import.module) @import
@@ -0,0 +1,38 @@
1
+ """The Go language pack (Tier A — structure + directory-package import resolution).
2
+
3
+ Go differs from the file-level packs: a **package is a directory**, so every
4
+ ``.go`` file in a dir shares one module key (``module_style="go"``). Import paths
5
+ are full module paths (``example.com/m/internal/bar``); the resolver suffix-matches
6
+ them to an in-repo package dir (it can't know the go.mod module prefix). Methods
7
+ are package-scoped (attached to a receiver type), captured here as ``Method`` but
8
+ file-owned — receiver→method ``CONTAINS`` linkage is a follow-up.
9
+ """
10
+
11
+ from __future__ import annotations
12
+
13
+ from pathlib import Path
14
+
15
+ from agentforge_graph.core import NodeKind
16
+ from agentforge_graph.ingest.pack import DescriptorRules, LanguagePack
17
+
18
+ _HERE = Path(__file__).parent
19
+
20
+ GO_PACK = LanguagePack(
21
+ language="go",
22
+ lang_slug="go",
23
+ grammar="go",
24
+ extensions=(".go",),
25
+ structure_queries=(_HERE / "structure.scm").read_text(encoding="utf-8"),
26
+ reference_queries=(_HERE / "references.scm").read_text(encoding="utf-8"),
27
+ descriptor_rules=DescriptorRules(
28
+ kinds={
29
+ "def.function": NodeKind.FUNCTION,
30
+ "def.method": NodeKind.METHOD,
31
+ "def.class": NodeKind.CLASS, # struct
32
+ "def.interface": NodeKind.INTERFACE,
33
+ "def.type": NodeKind.TYPE_ALIAS, # defined types / aliases
34
+ "def.variable": NodeKind.VARIABLE, # package-level const/var
35
+ }
36
+ ),
37
+ module_style="go",
38
+ )
@@ -0,0 +1,12 @@
1
+ ; Go reference queries (feat-002, pack-go).
2
+ ; Plain call `f(...)` and selector call `x.f(...)`. @call.recv is the operand, so
3
+ ; a call on the method's receiver (`s.f()`) resolves to a method of the receiver's
4
+ ; type (BUG-006); `pkg.Func` / other receivers stay unresolved (ADR-0004).
5
+
6
+ (call_expression
7
+ function: (identifier) @call.callee) @call
8
+
9
+ (call_expression
10
+ function: (selector_expression
11
+ operand: (identifier) @call.recv
12
+ field: (field_identifier) @call.callee)) @call
@@ -0,0 +1,64 @@
1
+ ; Go structure queries (feat-002, pack-go).
2
+ ; Shares the capture vocabulary so edge kinds mean the same as other packs.
3
+ ; A Go package is a *directory*: every `.go` file in a dir is one package, and
4
+ ; same-package files reference each other with no import (handled in the resolver).
5
+
6
+ ; --- definitions ---
7
+ (function_declaration
8
+ name: (identifier) @name) @def.function
9
+
10
+ ; methods are declared at package scope, attached to a receiver type. They're not
11
+ ; AST-nested in the type, so they're file-owned here (receiver→method CONTAINS
12
+ ; linkage is a follow-up); captured directly as Method.
13
+ (method_declaration
14
+ name: (field_identifier) @name) @def.method
15
+
16
+ ; the method's receiver `(s *T)` / `(s T)` -> bind the var name + type, so a call
17
+ ; on `s` inside the method resolves to a method of type T (BUG-006).
18
+ (method_declaration
19
+ receiver: (parameter_list (parameter_declaration
20
+ name: (identifier) @recv.var
21
+ type: [(type_identifier) @recv.type
22
+ (pointer_type (type_identifier) @recv.type)]))) @recv.method
23
+
24
+ ; `type T struct {…}` -> Class, `type T interface {…}` -> Interface.
25
+ (type_spec
26
+ name: (type_identifier) @name
27
+ (struct_type)) @def.class
28
+
29
+ (type_spec
30
+ name: (type_identifier) @name
31
+ (interface_type)) @def.interface
32
+
33
+ ; defined types / aliases: `type Celsius float64`, `type ID = string`, `type
34
+ ; Handler func(...)`. Listed underlying kinds exclude struct/interface so there's
35
+ ; no double-match with the two patterns above.
36
+ (type_spec
37
+ name: (type_identifier) @name
38
+ [(type_identifier)
39
+ (qualified_type)
40
+ (pointer_type)
41
+ (slice_type)
42
+ (array_type)
43
+ (map_type)
44
+ (channel_type)
45
+ (function_type)
46
+ (generic_type)]) @def.type
47
+
48
+ (type_alias
49
+ name: (type_identifier) @name) @def.type
50
+
51
+ ; package-level const / var (anchored to source_file so locals don't inflate).
52
+ (source_file
53
+ (const_declaration
54
+ (const_spec name: (identifier) @name) @def.variable))
55
+ (source_file
56
+ (var_declaration
57
+ (var_spec name: (identifier) @name) @def.variable))
58
+
59
+ ; --- imports ---
60
+ ; `import "example.com/m/pkg"` (and grouped `import ( … )`) -> the path string.
61
+ ; Go imports bind a *package*, not names; the resolver maps the path to a repo dir.
62
+ (import_spec
63
+ (interpreted_string_literal
64
+ (interpreted_string_literal_content) @import.module)) @import
@@ -0,0 +1,35 @@
1
+ """The Java language pack (Tier A — structure + namespace/FQN import resolution).
2
+
3
+ Java reuses the namespace/FQN mechanism (separator "."): a file declares a
4
+ `package`, and `import com.foo.Bar` resolves to the file declaring class `Bar` in
5
+ that package. Extracts class/enum/record (→Class), interface (→Interface),
6
+ methods + constructors. Method calls (`obj.m()`) stay unresolved (member access,
7
+ ADR-0004); since Java has no top-level functions, intra-class calls are method
8
+ dispatch too — the symbol graph + FQN dependency graph are the value.
9
+ """
10
+
11
+ from __future__ import annotations
12
+
13
+ from pathlib import Path
14
+
15
+ from agentforge_graph.core import NodeKind
16
+ from agentforge_graph.ingest.pack import DescriptorRules, LanguagePack
17
+
18
+ _HERE = Path(__file__).parent
19
+
20
+ JAVA_PACK = LanguagePack(
21
+ language="java",
22
+ lang_slug="java",
23
+ grammar="java",
24
+ extensions=(".java",),
25
+ structure_queries=(_HERE / "structure.scm").read_text(encoding="utf-8"),
26
+ reference_queries=(_HERE / "references.scm").read_text(encoding="utf-8"),
27
+ descriptor_rules=DescriptorRules(
28
+ kinds={
29
+ "def.class": NodeKind.CLASS, # class + enum + record
30
+ "def.interface": NodeKind.INTERFACE,
31
+ "def.function": NodeKind.FUNCTION, # method + constructor (promoted)
32
+ }
33
+ ),
34
+ namespace_sep=".", # `import com.foo.Bar` -> FQN resolution
35
+ )
@@ -0,0 +1,12 @@
1
+ ; Java reference queries (feat-002, pack-java).
2
+ ; A method invocation's `name` is the called method, with or without a receiver
3
+ ; (`f(...)`, `this.f(...)`, `obj.f(...)`). The second pattern captures the
4
+ ; receiver (@call.recv) so `this.f()` binds to the enclosing class's method
5
+ ; (BUG-006); other receivers stay unresolved (member access, ADR-0004).
6
+
7
+ (method_invocation
8
+ name: (identifier) @call.callee) @call
9
+
10
+ (method_invocation
11
+ object: (_) @call.recv
12
+ name: (identifier) @call.callee) @call
@@ -0,0 +1,38 @@
1
+ ; Java structure queries (feat-002, pack-java).
2
+ ; Namespace/FQN import model (reuses the PHP mechanism, separator "."): a file
3
+ ; declares a `package`; `import com.foo.Bar` resolves to the file declaring Bar.
4
+
5
+ ; --- package (drives FQN import resolution) ---
6
+ (package_declaration
7
+ (scoped_identifier) @namespace)
8
+
9
+ ; --- definitions ---
10
+ (class_declaration
11
+ name: (identifier) @name) @def.class
12
+
13
+ ; --- inheritance (INHERITS): `class B extends A` (implemented interfaces are a
14
+ ; separate relation, not captured here). ---
15
+ (class_declaration
16
+ superclass: (superclass (type_identifier) @base.name)) @base.def
17
+
18
+ (interface_declaration
19
+ name: (identifier) @name) @def.interface
20
+
21
+ ; enum + record -> Class (named nominal types).
22
+ (enum_declaration
23
+ name: (identifier) @name) @def.class
24
+
25
+ (record_declaration
26
+ name: (identifier) @name) @def.class
27
+
28
+ ; methods + constructors live in a class/interface body -> promoted to Method.
29
+ (method_declaration
30
+ name: (identifier) @name) @def.function
31
+
32
+ (constructor_declaration
33
+ name: (identifier) @name) @def.function
34
+
35
+ ; --- imports ---
36
+ ; `import com.foo.shapes.Shape;` -> the fully-qualified class name (FQN index).
37
+ (import_declaration
38
+ (scoped_identifier) @import.module) @import
@@ -0,0 +1,34 @@
1
+ """The JavaScript language pack (Tier A — structure + import resolution).
2
+
3
+ Shares the TS grammar family. The only structural delta is that JS
4
+ ``class_declaration`` names are ``(identifier)``, not ``(type_identifier)``
5
+ (see ``structure.scm``). Like TS, JS module specifiers are path-based
6
+ (``./util``), so the pack uses ``module_style="relative"``.
7
+ """
8
+
9
+ from __future__ import annotations
10
+
11
+ from pathlib import Path
12
+
13
+ from agentforge_graph.core import NodeKind
14
+ from agentforge_graph.ingest.pack import DescriptorRules, LanguagePack
15
+
16
+ _HERE = Path(__file__).parent
17
+
18
+ JAVASCRIPT_PACK = LanguagePack(
19
+ language="javascript",
20
+ lang_slug="js",
21
+ grammar="javascript",
22
+ extensions=(".js", ".jsx", ".mjs", ".cjs"),
23
+ structure_queries=(_HERE / "structure.scm").read_text(encoding="utf-8"),
24
+ reference_queries=(_HERE / "references.scm").read_text(encoding="utf-8"),
25
+ descriptor_rules=DescriptorRules(
26
+ kinds={
27
+ "def.class": NodeKind.CLASS,
28
+ "def.function": NodeKind.FUNCTION, # promoted to METHOD inside a class
29
+ # ENH-008: arrow/function-bound consts + module-level const tables.
30
+ "def.variable": NodeKind.VARIABLE,
31
+ }
32
+ ),
33
+ module_style="relative", # JS imports are path specifiers (./util), not dotted
34
+ )
@@ -0,0 +1,11 @@
1
+ ; JavaScript reference queries (feat-002, pack-js).
2
+ ; Plain call `f(...)` and method/attribute call `recv.f(...)`. @call.recv is the
3
+ ; receiver (BUG-006), so `this.f()` binds to the enclosing class's method.
4
+
5
+ (call_expression
6
+ function: (identifier) @call.callee) @call
7
+
8
+ (call_expression
9
+ function: (member_expression
10
+ object: (_) @call.recv
11
+ property: (property_identifier) @call.callee)) @call
@@ -0,0 +1,166 @@
1
+ ; JavaScript structure queries (feat-002, pack-js).
2
+ ; Mirrors the TS pack; the only grammar delta is the class name node:
3
+ ; JS `class_declaration` names are (identifier), not (type_identifier).
4
+ ; Definitions may be wrapped in `export_statement`; queries match nested.
5
+
6
+ ; --- definitions ---
7
+ (class_declaration
8
+ name: (identifier) @name) @def.class
9
+
10
+ ; --- inheritance (INHERITS): `class B extends A` (JS heritage holds the
11
+ ; superclass expression directly, no extends_clause wrapper). ---
12
+ (class_declaration
13
+ (class_heritage (identifier) @base.name)) @base.def
14
+
15
+ ; qualified base `class B extends mod.Base` -> base `mod.Base`; the resolver splits
16
+ ; the receiver and binds it via the importing module alias (default require).
17
+ (class_declaration
18
+ (class_heritage (member_expression) @base.name)) @base.def
19
+
20
+ (function_declaration
21
+ name: (identifier) @name) @def.function
22
+
23
+ ; methods live in a class_body -> promoted to METHOD by the extractor
24
+ (method_definition
25
+ name: (property_identifier) @name) @def.function
26
+
27
+ ; --- JSDoc docstrings (DESCRIBES) ---
28
+ ; a `/** … */` block comment immediately before a function/class/method becomes a
29
+ ; DocChunk that DESCRIBES the symbol (feat-010). `#match?` keeps only JSDoc (`/**`).
30
+ ((comment) @docstring . (function_declaration) @doc.owner
31
+ (#match? @docstring "^/[*][*]"))
32
+ ((comment) @docstring . (class_declaration) @doc.owner
33
+ (#match? @docstring "^/[*][*]"))
34
+ (class_body
35
+ (comment) @docstring . (method_definition) @doc.owner
36
+ (#match? @docstring "^/[*][*]"))
37
+
38
+ ; --- value bindings (ENH-008, shared with TS) ---
39
+ ; `const f = (…) => …` / `const f = function () {}` -> Function (named from the
40
+ ; binding). Captured at any depth — these are genuine functions. (JS has no
41
+ ; interface/enum/type-alias, so those TS captures are absent here.)
42
+ (lexical_declaration
43
+ (variable_declarator
44
+ name: (identifier) @name
45
+ value: [(arrow_function) (function_expression)])) @def.function
46
+
47
+ ; module-level const data tables -> Variable. Scoped to the top level (program /
48
+ ; export) so locals don't inflate it. Only object/array initializers — NOT call
49
+ ; results: `const x = require(...)` is an import binding (BUG-006), not a symbol.
50
+ (program
51
+ (lexical_declaration
52
+ (variable_declarator
53
+ name: (identifier) @name
54
+ value: [(object) (array)])) @def.variable)
55
+ (program
56
+ (export_statement
57
+ (lexical_declaration
58
+ (variable_declarator
59
+ name: (identifier) @name
60
+ value: [(object) (array)])) @def.variable))
61
+
62
+ ; --- imports (ESM) ---
63
+ ; `import { a, b } from "./mod"` -> module (relative path) + bound names
64
+ (import_statement
65
+ (import_clause (named_imports (import_specifier name: (identifier) @import.name)))
66
+ source: (string (string_fragment) @import.module)) @import
67
+
68
+ ; `import * as ns from "./mod"` -> the namespace alias binds the whole module, so
69
+ ; `ns.foo()` and a qualified base `extends ns.Base` resolve to its exports (BUG-006).
70
+ (import_statement
71
+ (import_clause (namespace_import (identifier) @import.default))
72
+ source: (string (string_fragment) @import.module)) @import
73
+
74
+ ; --- imports (CommonJS require, BUG-006) ---
75
+ ; `const x = require("./mod")` -> module + the default-bound local name
76
+ (variable_declarator
77
+ name: (identifier) @import.default
78
+ value: (call_expression
79
+ function: (identifier) @_require
80
+ arguments: (arguments (string (string_fragment) @import.module)))
81
+ (#eq? @_require "require")) @import
82
+
83
+ ; `const { a, b } = require("./mod")` -> module + named bindings
84
+ (variable_declarator
85
+ name: (object_pattern (shorthand_property_identifier_pattern) @import.name)
86
+ value: (call_expression
87
+ function: (identifier) @_require
88
+ arguments: (arguments (string (string_fragment) @import.module)))
89
+ (#eq? @_require "require")) @import
90
+
91
+ ; --- exports (CommonJS, BUG-006) ---
92
+ ; `module.exports = name` (incl. chained `exports = module.exports = name`) ->
93
+ ; the module's default export, so a default require binds to this symbol.
94
+ (assignment_expression
95
+ left: (member_expression
96
+ object: (identifier) @_mod
97
+ property: (property_identifier) @_exp)
98
+ right: (identifier) @export.default
99
+ (#eq? @_mod "module")
100
+ (#eq? @_exp "exports")) @export
101
+
102
+ ; `module.exports = function name() {}` (named function-expression default export —
103
+ ; the express-style router-factory pattern, incl. chained `var p = module.exports =
104
+ ; function name(){}`; BUG-006 residual). Two patterns on the same assignment: the
105
+ ; first makes the function a Function symbol, the second marks it the module default
106
+ ; export — so `const r = require("./m"); r()` resolves to it. (Anonymous
107
+ ; `module.exports = function(){}` / `= () => {}` have no name → no symbol; the
108
+ ; IMPORTS edge still exists.)
109
+ (assignment_expression
110
+ left: (member_expression
111
+ object: (identifier) @_mod
112
+ property: (property_identifier) @_exp)
113
+ right: (function_expression
114
+ name: (identifier) @name) @def.function
115
+ (#eq? @_mod "module")
116
+ (#eq? @_exp "exports"))
117
+
118
+ (assignment_expression
119
+ left: (member_expression
120
+ object: (identifier) @_mod
121
+ property: (property_identifier) @_exp)
122
+ right: (function_expression
123
+ name: (identifier) @export.default)
124
+ (#eq? @_mod "module")
125
+ (#eq? @_exp "exports")) @export
126
+
127
+ ; --- export-member modeling (BUG-006 residual) ---
128
+ ; Assigned-property exports whose value is an *anonymous* function — these never
129
+ ; become symbols any other way, so `m.foo()` / `const { foo } = require(...)` /
130
+ ; direct calls have nothing to bind to. The property name is the export name (an
131
+ ; anonymous function has no name of its own). Named function-expression values are
132
+ ; covered by the `const f = function name(){}` value-binding pattern's sibling
133
+ ; forms; here we deliberately name from the property, which is the export name.
134
+
135
+ ; `exports.foo = function () {}` / `exports.foo = () => {}` -> Function `foo`
136
+ (assignment_expression
137
+ left: (member_expression
138
+ object: (identifier) @_obj
139
+ property: (property_identifier) @name)
140
+ right: [(function_expression) (arrow_function)] @def.function
141
+ (#eq? @_obj "exports"))
142
+
143
+ ; `module.exports.foo = function () {}` / `= () => {}` -> Function `foo`
144
+ (assignment_expression
145
+ left: (member_expression
146
+ object: (member_expression
147
+ object: (identifier) @_mod
148
+ property: (property_identifier) @_exp)
149
+ property: (property_identifier) @name)
150
+ right: [(function_expression) (arrow_function)] @def.function
151
+ (#eq? @_mod "module")
152
+ (#eq? @_exp "exports"))
153
+
154
+ ; `module.exports = { foo: function(){}, bar: () => {} }` -> Function per inline
155
+ ; function-valued pair. Shorthand props (`{ a, b }`) that name top-level defs
156
+ ; already resolve via the export map, so only inline functions need extracting.
157
+ (assignment_expression
158
+ left: (member_expression
159
+ object: (identifier) @_mod
160
+ property: (property_identifier) @_exp)
161
+ right: (object
162
+ (pair
163
+ key: (property_identifier) @name
164
+ value: [(function_expression) (arrow_function)] @def.function))
165
+ (#eq? @_mod "module")
166
+ (#eq? @_exp "exports"))
@@ -0,0 +1,35 @@
1
+ """The PHP language pack (Tier A — structure + namespace/FQN import resolution).
2
+
3
+ PHP is the first namespace/FQN-based pack: a file declares one `namespace`, and
4
+ `use App\\Foo\\Bar` resolves to the file declaring class `Bar` in namespace
5
+ `App\\Foo` (PSR-4 maps namespaces to dirs). Extracts class/interface/trait/enum
6
+ (→Class/Interface), functions, methods, and constants. Method/static calls
7
+ (`$x->m()`, `C::m()`) stay unresolved (member access, ADR-0004).
8
+ """
9
+
10
+ from __future__ import annotations
11
+
12
+ from pathlib import Path
13
+
14
+ from agentforge_graph.core import NodeKind
15
+ from agentforge_graph.ingest.pack import DescriptorRules, LanguagePack
16
+
17
+ _HERE = Path(__file__).parent
18
+
19
+ PHP_PACK = LanguagePack(
20
+ language="php",
21
+ lang_slug="php",
22
+ grammar="php",
23
+ extensions=(".php",),
24
+ structure_queries=(_HERE / "structure.scm").read_text(encoding="utf-8"),
25
+ reference_queries=(_HERE / "references.scm").read_text(encoding="utf-8"),
26
+ descriptor_rules=DescriptorRules(
27
+ kinds={
28
+ "def.class": NodeKind.CLASS, # class + trait + enum
29
+ "def.interface": NodeKind.INTERFACE,
30
+ "def.function": NodeKind.FUNCTION, # function + method (promoted)
31
+ "def.variable": NodeKind.VARIABLE, # const
32
+ }
33
+ ),
34
+ namespace_sep="\\", # `use App\Foo\Bar` -> FQN resolution
35
+ )
@@ -0,0 +1,15 @@
1
+ ; PHP reference queries (feat-002, pack-php).
2
+ ; Plain call `f(...)`, method call `$x->f(...)`, static call `C::f(...)`. The
3
+ ; receiver is captured (@call.recv) so `$this->f()` / `self::f()` bind to the
4
+ ; enclosing class's method (BUG-006); other receivers stay unresolved (ADR-0004).
5
+
6
+ (function_call_expression
7
+ function: (name) @call.callee) @call
8
+
9
+ (member_call_expression
10
+ object: (_) @call.recv
11
+ name: (name) @call.callee) @call
12
+
13
+ (scoped_call_expression
14
+ scope: (_) @call.recv
15
+ name: (name) @call.callee) @call
@@ -0,0 +1,44 @@
1
+ ; PHP structure queries (feat-002, pack-php).
2
+ ; Namespace/FQN import model: a file declares one namespace; `use App\Foo\Bar`
3
+ ; resolves to the file declaring class Bar in namespace App\Foo.
4
+
5
+ ; --- namespace (drives FQN import resolution) ---
6
+ (namespace_definition
7
+ name: (namespace_name) @namespace)
8
+
9
+ ; --- definitions ---
10
+ (class_declaration
11
+ name: (name) @name) @def.class
12
+
13
+ ; --- inheritance (INHERITS): `class B extends A` (implemented interfaces are a
14
+ ; separate relation, not captured here). ---
15
+ (class_declaration
16
+ (base_clause (name) @base.name)) @base.def
17
+
18
+ (interface_declaration
19
+ name: (name) @name) @def.interface
20
+
21
+ ; a trait is a reusable unit of methods — model as Class (named method container).
22
+ (trait_declaration
23
+ name: (name) @name) @def.class
24
+
25
+ ; enum -> Class (a named nominal type; no dedicated Enum kind).
26
+ (enum_declaration
27
+ name: (name) @name) @def.class
28
+
29
+ (function_definition
30
+ name: (name) @name) @def.function
31
+
32
+ ; methods live in a class/interface/trait body -> promoted to Method by nesting.
33
+ (method_declaration
34
+ name: (name) @name) @def.function
35
+
36
+ ; top-level + class constants -> Variable.
37
+ (const_element
38
+ (name) @name) @def.variable
39
+
40
+ ; --- imports ---
41
+ ; `use App\Shapes\Shape;` -> the fully-qualified class name (resolved via FQN index).
42
+ (namespace_use_declaration
43
+ (namespace_use_clause
44
+ (qualified_name) @import.module)) @import
@@ -0,0 +1,25 @@
1
+ """The Python language pack (Tier A — structure + import resolution)."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from pathlib import Path
6
+
7
+ from agentforge_graph.core import NodeKind
8
+ from agentforge_graph.ingest.pack import DescriptorRules, LanguagePack
9
+
10
+ _HERE = Path(__file__).parent
11
+
12
+ PYTHON_PACK = LanguagePack(
13
+ language="python",
14
+ lang_slug="py",
15
+ grammar="python",
16
+ extensions=(".py",),
17
+ structure_queries=(_HERE / "structure.scm").read_text(encoding="utf-8"),
18
+ reference_queries=(_HERE / "references.scm").read_text(encoding="utf-8"),
19
+ descriptor_rules=DescriptorRules(
20
+ kinds={
21
+ "def.class": NodeKind.CLASS,
22
+ "def.function": NodeKind.FUNCTION, # promoted to METHOD when nested in a class
23
+ }
24
+ ),
25
+ )
@@ -0,0 +1,14 @@
1
+ ; Python reference queries (feat-002).
2
+ ; Calls only at v0.1: a plain call `f(...)` and an attribute call `recv.f(...)`.
3
+ ; @call.callee is the called name; @call.recv is the receiver (BUG-006), so the
4
+ ; resolver can bind `self.f()` to the enclosing class's method without guessing
5
+ ; for other receivers. The extractor attributes the call to its enclosing
6
+ ; definition and records it for pass-2 resolution.
7
+
8
+ (call
9
+ function: (identifier) @call.callee) @call
10
+
11
+ (call
12
+ function: (attribute
13
+ object: (_) @call.recv
14
+ attribute: (identifier) @call.callee)) @call
@@ -0,0 +1,57 @@
1
+ ; Python structure queries (feat-002).
2
+ ; Each definition pattern captures the definition node (@def.<kind>) and its
3
+ ; identifier (@name) in one pattern, so the extractor pairs them via matches().
4
+ ; Imports capture the module and (for `from` imports) the bound names.
5
+
6
+ ; --- definitions ---
7
+ (class_definition
8
+ name: (identifier) @name) @def.class
9
+
10
+ (function_definition
11
+ name: (identifier) @name) @def.function
12
+
13
+ ; --- docstrings (DESCRIBES) ---
14
+ ; the first string in a def/class body is its docstring; the extractor turns it
15
+ ; into a DocChunk that DESCRIBES the symbol (feat-010). The `.` anchor restricts
16
+ ; the match to the *first* body statement, so a non-leading string is not one.
17
+ (function_definition
18
+ body: (block . (string) @docstring)) @doc.owner
19
+ (class_definition
20
+ body: (block . (string) @docstring)) @doc.owner
21
+
22
+ ; --- inheritance (INHERITS) ---
23
+ ; a base class named by a bare identifier: `class B(A)` -> base `A`.
24
+ (class_definition
25
+ superclasses: (argument_list (identifier) @base.name)) @base.def
26
+
27
+ ; a qualified base `class B(mod.Base)` -> base `mod.Base`; the resolver splits the
28
+ ; receiver and binds it via the importing module alias (`import mod`).
29
+ (class_definition
30
+ superclasses: (argument_list (attribute) @base.name)) @base.def
31
+
32
+ ; --- imports ---
33
+ ; `import a.b.c` -> module only (the receiver in code is the dotted path itself).
34
+ (import_statement
35
+ name: (dotted_name) @import.module) @import
36
+
37
+ ; `import a.b.c as x` -> module + the alias `x` as the local binding name, so a
38
+ ; whole-module import bound to a short alias (`import numpy as np`) makes `np.f()`
39
+ ; / `extends np.Base` resolve to module `a.b.c`'s exports (BUG-006).
40
+ (import_statement
41
+ name: (aliased_import
42
+ (dotted_name) @import.module
43
+ alias: (identifier) @import.default)) @import
44
+
45
+ ; `from a.b import c, d` -> module + one or more bound names
46
+ (import_from_statement
47
+ module_name: (dotted_name) @import.module
48
+ name: [(dotted_name) @import.name
49
+ (aliased_import (dotted_name) @import.name)]) @import
50
+
51
+ ; `from .mod import x` / `from . import x` (relative) -> the relative module
52
+ ; text (leading dots + optional name, e.g. `.utils`, `..pkg.mod`, `.`) + names.
53
+ ; resolve_import() resolves the dots against the importer's package (BUG-004).
54
+ (import_from_statement
55
+ module_name: (relative_import) @import.module
56
+ name: [(dotted_name) @import.name
57
+ (aliased_import (dotted_name) @import.name)]) @import