Skip to content

feat(gdscript): add .gd extraction support (#697) - #1836

Open
TPAteeq wants to merge 1 commit into
Graphify-Labs:v8from
TPAteeq:feat/697-gdscript-support
Open

feat(gdscript): add .gd extraction support (#697)#1836
TPAteeq wants to merge 1 commit into
Graphify-Labs:v8from
TPAteeq:feat/697-gdscript-support

Conversation

@TPAteeq

@TPAteeq TPAteeq commented Jul 12, 2026

Copy link
Copy Markdown
Contributor

Closes #697

Summary

  • Add a dedicated tree-sitter GDScript extractor for .gd files.
  • Wire GDScript into detection, dispatch, extractor registry, language-family guards, and analysis.
  • Add the optional graphifyy[gdscript] dependency using a tree-sitter-compatible language-pack release.
  • Document GDScript support and installation.

Extraction coverage

  • Named and implicit script classes
  • Functions, members, constants, signals, enums, and inner classes
  • Identifier and res:// inheritance
  • Typed member references
  • Type.new() instantiations
  • Same-script calls
  • preload() and load() dependencies
  • Cross-file type resolution

Godot built-ins are filtered to avoid noisy graph hubs, ambiguous receiver calls are not guessed, and unresolved type stubs use a reserved namespace to prevent
collisions with file nodes.

Validation

  • uv run pytest -q — 3,119 passed, 30 skipped
  • Ruff passed
  • Pyright passed
  • Package build passed
  • graphify update . completed successfully

@luevano

luevano commented Jul 26, 2026

Copy link
Copy Markdown

Hey, could you also include godot resource parsing (.tscn and .tres)? it is already included in the tree-sitter-language-pack. #1929 already has a version that does both, but it's not using the language pack you included, I think a combination of both PRs could be really helpful.

ozdemirsarman added a commit to ozdemirsarman/graphify that referenced this pull request Jul 26, 2026
Address review (Graphify-Labs#1929): depend on tree-sitter-language-pack>=1.12.5,<1.13 (as Graphify-Labs#1836 does) instead of the unpublished tree-sitter-gdscript wheel. The .gd extractor loads the bundled gdscript grammar; the scene/resource extractor now uses the bundled godot_resource grammar, falling back to a dependency-free line parser when the extra is absent.
luevano added a commit to luevano/graphify that referenced this pull request Jul 27, 2026
luevano pushed a commit to luevano/graphify that referenced this pull request Jul 27, 2026
Address review (Graphify-Labs#1929): depend on tree-sitter-language-pack>=1.12.5,<1.13 (as Graphify-Labs#1836 does) instead of the unpublished tree-sitter-gdscript wheel. The .gd extractor loads the bundled gdscript grammar; the scene/resource extractor now uses the bundled godot_resource grammar, falling back to a dependency-free line parser when the extra is absent.
luevano added a commit to luevano/graphify that referenced this pull request Jul 27, 2026
luevano added a commit to luevano/graphify that referenced this pull request Jul 27, 2026
…namespace

Complete the godot_scene -> godot_resource rename across the module, its test and the registry (Graphify-Labs#1836 parity), and fix three id-correctness bugs in the Godot extractors.

res:// resolution ended in .resolve(), so cross-file targets - autoload calls, preload/extends, and every ext_resource in a .tscn - were built from the on-disk path while every other id derives from the scan-relative path the walker passes in. extract()'s Graphify-Labs#502 remap cannot repair those: it re-derives ids from the emitting file's source_file, which for a cross-file target is the wrong file, so the edge dangles for good. The resolved path is only ever used to build ids and labels, never for filesystem access, so it now stays relative.

Neither extractor filtered engine API, so Godot types, global functions and Object/Node methods became graph nodes accumulating edges from every call site. Bare calls need the method set too, since implicit-self calls like add_child(x) are idiomatic GDScript. extends edges to engine types are deliberately kept: one per script rather than one per call site, so they cannot accumulate into a god node, and which scripts are CharacterBody3D vs Control is real structure.

handle_attribute_call took the first identifier of an attribute chain as the receiver, so PlayerProfile.library.set_active_skin() resolved into player_profile.gd, which defines no such function. Only a direct Autoload.method() resolves now.

On a 77-file Godot project this takes AST dangling edge endpoints from 118 to 0, and the graph from 2026 nodes / 3611 edges to 1484 / 2460.

Both test modules built their expected ids with .resolve(), the same absolutizing step at fault, so they would have gone green over a broken extractor; they now derive expectations from the extractor's own output. Adds regression tests for absolute-path leaks, engine-method phantoms and chained attribute calls.
luevano pushed a commit to luevano/graphify that referenced this pull request Jul 27, 2026
Address review (Graphify-Labs#1929): depend on tree-sitter-language-pack>=1.12.5,<1.13 (as Graphify-Labs#1836 does) instead of the unpublished tree-sitter-gdscript wheel. The .gd extractor loads the bundled gdscript grammar; the scene/resource extractor now uses the bundled godot_resource grammar, falling back to a dependency-free line parser when the extra is absent.
luevano added a commit to luevano/graphify that referenced this pull request Jul 27, 2026
…namespace

Complete the godot_scene -> godot_resource rename across the module, its test and the registry (Graphify-Labs#1836 parity), and fix three id-correctness bugs in the Godot extractors.

res:// resolution ended in .resolve(), so cross-file targets - autoload calls, preload/extends, and every ext_resource in a .tscn - were built from the on-disk path while every other id derives from the scan-relative path the walker passes in. extract()'s Graphify-Labs#502 remap cannot repair those: it re-derives ids from the emitting file's source_file, which for a cross-file target is the wrong file, so the edge dangles for good. The resolved path is only ever used to build ids and labels, never for filesystem access, so it now stays relative.

Neither extractor filtered engine API, so Godot types, global functions and Object/Node methods became graph nodes accumulating edges from every call site. Bare calls need the method set too, since implicit-self calls like add_child(x) are idiomatic GDScript. extends edges to engine types are deliberately kept: one per script rather than one per call site, so they cannot accumulate into a god node, and which scripts are CharacterBody3D vs Control is real structure.

handle_attribute_call took the first identifier of an attribute chain as the receiver, so PlayerProfile.library.set_active_skin() resolved into player_profile.gd, which defines no such function. Only a direct Autoload.method() resolves now.

On a 77-file Godot project this takes AST dangling edge endpoints from 118 to 0, and the graph from 2026 nodes / 3611 edges to 1484 / 2460.

Both test modules built their expected ids with .resolve(), the same absolutizing step at fault, so they would have gone green over a broken extractor; they now derive expectations from the extractor's own output. Adds regression tests for absolute-path leaks, engine-method phantoms and chained attribute calls.
ozdemirsarman added a commit to ozdemirsarman/graphify that referenced this pull request Jul 27, 2026
…yze/build/MIGRATION, README + fixtures (Graphify-Labs#1929)

- Register .gd (gdscript) and .tscn/.tres/project.godot (godot_resource) in analyze.py, build.py and extractors/MIGRATION.md, matching Graphify-Labs#1836.
- Rename the scene extractor to godot_resource (module, extract_godot_resource, registry key, wiring) per review.
- Shrink the pyproject godot comment to one line.
- README: add a godot extras row and split the godot file types into their own GDScript / Godot resources rows.
- Move the inline gdscript/godot test bodies into tests/fixtures/godot/ and rename the test file to test_godot_resource.py.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add GDScript (.gd) support

2 participants