Skip to content

R: box::use() import declarations produce no IMPORTS edges #218

Closed

Description

@marcusyoung

Summary

When indexing R code that uses the box module system (common in Rhino-framework Shiny applications), box::use() declarations are not parsed into IMPORTS edges in the knowledge graph. The result is a silent gap: queries that rely on import relationships — trace_path caller chains, query_graph module dependency questions — return incomplete results with no indication that edges are missing.

Expected behaviour

A box::use() declaration should produce IMPORTS edges equivalent to those produced by library(), require(), or source() in base R. For example:

box::use(
  shiny[moduleServer, NS],
  app/logic/validation[validate_input]
)

should produce IMPORTS edges from the current module to shiny, and from the current module to app/logic/validation.

Actual behaviour

No IMPORTS edges are created. The module appears to have no import relationships in the graph.

Impact

box is the standard import mechanism for the Rhino framework (Appsilon), which is a production-grade structure for large R/Shiny applications. Projects using Rhino exclusively use box::use() — library() is explicitly discouraged. Without IMPORTS edge support, the call graph for any Rhino project is structurally incomplete.

The failure is silent: trace_path returns partial caller lists rather than an error. This produces false confidence in impact assessments made by agents using the tool.

Version

0.6.0 (Windows amd64)

Activity

  1. DeusData commented on Apr 7, 2026

    @DeusData
    Owner

    Hey, thx for reporting 🙏 Will tackle this asap after the 15th. Hope you can wait until then

  2. added
    bugSomething isn't working
    parsing/qualityGraph extraction bugs, false positives, missing edges
    on Apr 15, 2026
  3. DeusData commented on May 31, 2026

    @DeusData
    Owner

    Confirmed: box::use() is not yet parsed into IMPORTS edges. R imports are currently extracted generically from call nodes (covering library()/require()/source()), but there's no handler for the box module system's box::use(path/to/mod, pkg[fn1, fn2]) syntax — so those declarations produce no edges.

    Fix scope: add a box-aware import handler that recognizes the box::use(...) call shape and emits IMPORTS edges for each module path (and tracks the imported symbols for call resolution — see #219). This is a real R-extractor enhancement; reproduced and queued (kept open). 🙏

  4. DeusData commented on May 31, 2026

    @DeusData
    Owner

    Thanks. This is an accepted feature-gap. R is currently a tree-sitter-only language (like Rust/Java — not one of the hybrid-LSP languages), and its lang-spec doesn't yet handle the box module system: box::use(...) declarations aren't turned into IMPORTS edges. Implementing this means extending the R extraction query to recognize box::use() import forms and emit IMPORTS edges to the referenced modules. Tracking it as an R-extraction enhancement (paired with #219). A pointer to a representative public R/box project would help me build it against real code. Thanks!

  5. marcusyoung commented on May 31, 2026

    @marcusyoung
    Author
  6. DeusData commented on May 31, 2026

    @DeusData
    Owner

    Fixed in commit 1a636f1. Root cause was bigger than expected: R had no import extraction at all — it wasn't wired into the import dispatch, so library(), require(), source() and box::use() all produced zero IMPORTS edges.

    Added parse_r_imports which recursively scans the R AST and emits IMPORTS edges for:

    • base R: library(pkg), require(pkg), requireNamespace("pkg"), loadNamespace("pkg"), source("file.R")
    • box: each box::use(...) argument → one IMPORTS edge, with the module path taken as the spec text before the [symbols] list. So:
      box::use(
        shiny[moduleServer, NS],            # → import "shiny"
        app/logic/validation[validate_input] # → import "app/logic/validation"
      )

    I confirmed the exact tree-sitter-R node types (namespace_operator, subset, binary_operator) with a probe before writing the parser rather than guessing. Regression test extract_r_box_use_imports_issue218 covers box::use + library + source.

    (module$function() call resolution is the sibling fix in #219, same commit.) Ships next release — thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't workingparsing/qualityGraph extraction bugs, false positives, missing edges

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions