Skip to content
Konjure / spatial intelligence

Develop the Rust SDK

Read a contract, run its Rust example, inspect the result, and improve one component at a time.

The website is Konjure’s primary project surface. Its book, guides, tutorials, examples, reference and devlog form one static site. Executable SDK contracts, API documentation and programmatic examples originate in Rust; the site builds and presents them alongside its authored learning material.

For registry releases and versioned API documentation, see Publishing Rust crates.

Start with an executable Rust example

From the repository root:

Sourcesh
cargo run -p konjure-sdk --example inspect
cargo test -p konjure-sdk --example inspect

The example constructs a scene using Rust types, samples motion under a parent transform, changes a declared behavior, and records an external effect proposal. It has independently asserted expected outcomes. Edit crates/konjure-sdk/examples/inspect.rs, run it again, and inspect what changed.

The Rust inspection example includes that exact source, a live view of its exported scene, and its native trace. The Rust API reference is generated from source comments.

Language and ECS iteration

The SDK’s data module is the foundation for numeric and media work. Start with cargo test -p konjure-sdk data and its Rust reference. Run cargo run -p konjure-sdk --example data for a small image/audio/precision example; its source and generated output appear in the SDK guide. The language examples in Numbers, text and bytes and Tensors and media exercise that same implementation. Check both native execution and WASM after changing a scalar, shape or buffer contract.

The reusable programming language lives in crates/konjure-lang. Its parser, linker, static type checker, interpreter, state snapshots and physics bridge are shared with WASM.

Sourcesh
bash scripts/check-language.sh
cargo run -p konjure-lang --example inspect
cargo run -p konjure-tools --bin kj-lang -- run crates/konjure-lang/examples/activity.kj --ticks 60

The language guide embeds those crate-owned programs in the same workbench as the Demo. The build also exports the Rust builtin catalog and tokenizes documentation snippets for source-linked highlighting. After changing the compiler or runtime, run npm run sdk:wasm and npm run test:web to check native/WASM agreement.

Keep each compiler phase explicit:

PhaseInput and guarantee
ParseUTF-8 sources become syntax nodes with original byte spans
LinkDeclarations resolve to nominal module identities and checked trait signatures
Type checkEvery body, default and initializer has valid calls, fields, operators and returns
InitializeChecked code creates bounded candidate state; failure creates no machine
RunTyped lifecycle callbacks and actions update state transactionally
AdaptRust validates geometry and physics before a host presents the accepted world

For a method such as Spinner.advance, test invalid unused bodies at compile time as well as accepted state changes at runtime. For systems, test query membership, init/frame/done order, component writeback and rollback. The guide/systems.kj fixture is exercised through Rust and WASM and embedded directly in the systems guide.

Teaching examples live under crates/konjure-lang/examples/guide/. The website imports those .kj files directly, including named modules and intentional compile errors. tests/guide_examples.rs checks their output, component state, lifecycle and rollback; the web tests compare the same programs against native Rust. Run cargo nextest run -p konjure-lang --test guide_examples while editing a lesson, then npm run test:web and npm run verify before review.

Write lessons around small examples: show the code, its output, and one edit to try. Use LanguageWorkbench with presentation="snippet" for basics and the full console or scene view for lifecycle and simulation work. Add a diagram when it clarifies control flow or ownership; keep its labels aligned with the tested source. See Language basics for this pattern.

packages/workbench/ owns the extracted common frame and its LanguageWorkbench component. It composes the toolbar, file explorer, source/preview and result panes for both website embeds and Kreate. The chrome controller owns file selection, resource inspection, expansion and Output/Debug/Trace tabs; the language adapter owns Rust/WASM execution and source metadata. Kreate keeps its application shell, project library and browser persistence under apps/kreate/, outside the reusable package. Run initializes the edited files; Reset restores the original example. Test two widgets on one page so edits, tabs and simulation controls stay isolated.

The short automatic check

Sourcesh
bash scripts/check-sdk.sh

This checks SDK formatting, Rust tests including the example, doctests, Clippy, API documentation and the executable example. It uses nextest when installed and explicitly falls back to Cargo’s test runner otherwise. It requires the pinned Rust toolchain and no browser, device, model credentials or Node runtime.

Use a focused test while editing a component, then run the complete SDK check before review:

Sourcesh
cargo test -p konjure-sdk validation
cargo test -p konjure-sdk --example inspect
cargo doc -p konjure-sdk --no-deps --open

To inspect the native scene and trace as files:

Sourcesh
cargo run -p konjure-sdk --example inspect -- /tmp/konjure-inspect

The output directory contains scene.konjure and trace.json. The trace records the example’s decisions and sampled states; it does not execute physical effects.

Review one component

ComponentQuestions to settle in Rust
Domain and validationAre identifiers, units, frames, limits and invalid states explicit?
GeometryAre topology, dimensions, normals and bounds independently checked?
RuntimeWho owns time and state? Are ordering, errors and effects explicit?
CompilerDoes each language construct produce the same validated domain model?
RecordingWhat is recorded, replayed, rejected or deliberately never re-executed?
BindingsDo generated declarations preserve semantics, ownership and diagnostics?

Read the public contract, change one small Rust example, test expected and rejected behavior, and inspect the result together. Introduce another module or package only when a concrete consumer or dependency boundary requires it.

Documentation and generation rules

Numeric reference text comes from the DType Rust definition macro in crates/konjure-sdk/src/data/scalar.rs. Its range and precision descriptions feed rustdoc and the builtin catalog; edit them there. Fundamental value descriptions come from Value variant docs, and every catalog example executes in tests.

Browser-specific Rust code belongs in crates/konjure-web. Its lifecycle example runs with cargo run -p konjure-web --example lifecycle. Keep DOM and capability dependencies out of the portable SDK. wasm-bindgen generates the bridge used by the TypeScript host package.

Public Rust APIs document units, ownership, time, failure conditions and relevant allocation or effect behavior in rustdoc. Compiling code examples belong there or in the crate’s examples. Tests assert independent expected behavior; generated output alone is not an independent oracle.

Builtin reference pages are generated from Rust registrations:

  • crates/konjure-lang/src/value.rs captures doc comments on the actual Value variants for primitive descriptions. catalog/values.rs supplies their checked examples and explains the Rust representation.
  • catalog/prelude.rs declares type and trait schemas once. Its macro emits compiler prelude source, rustdoc and reference metadata from the same declaration and doc comments. Field types and defaults are read by the ordinary parser.
  • catalog/functions.rs registers interpreter functions, overload signatures, parameter docs and examples. Concrete function-value signatures are parsed once from those same declarations and cached for the checker and runtime.
  • methods.rs owns receiver methods and their checked signatures. Keep data operations on their types; document recoverable errors with Res or Opt. SDK DataError variant doc comments generate the language error cases.

To add a builtin, document its units, behavior and failure conditions beside its Rust registration; include a standalone ExampleSpec with exact expected log lines. Use snippet for small value examples, console for callbacks and host controls, and scene for geometry or physics. Declare the number of simulation ticks required to observe its result. catalog_docs runs every example and checks its output and render conversion; the web tests run the same examples in WASM. A host resource schema must explain what the host still needs to implement.

Sourcesh
bash scripts/check-language.sh
npm run sdk:wasm
npm run test:web
npm run verify

The website’s signatures, member descriptions, examples and Rust links all come from the exported catalog. Edit the registrations rather than generated JSON or per-builtin website pages. Prelude types currently use interpreter records; they are not automatically aliases for similarly named Rust SDK structs.

Generated declarations, schemas and binding glue are disposable build outputs. Change their Rust source or generator, then regenerate. TypeScript/Astro, Python, C# and platform code own host-specific presentation and lifecycle, not another implementation of scene behavior. Existing handwritten Python/C# native declarations still need migration; their ergonomic host adapters remain useful.

Sourcesh
bash scripts/generate-sdk-contracts.sh
bash scripts/generate-sdk-contracts.sh --check

The web build generates WASM declarations, schemas, Rust reference pages and the native example outputs. The native build generates its C ABI header. Cross-language tests exercise those generated boundaries after Rust tests pass.

Explore through the project website

With Node 24 and wasm-pack 0.15.0 installed:

Sourcesh
npm ci
npm run dev -- --host 127.0.0.1

Root dev, build and verify commands regenerate WASM, Rust API documentation, contracts and native example outputs before Astro runs. npm run docs:rust rebuilds only the Rust API reference and native example outputs.

Open the Rust example to inspect the exported scene. After changing its Rust source, rerun npm run sdk:wasm to regenerate the native example, API reference and browser runtime. Rust compilation happens during development/build; the static website does not run a Rust compiler in the visitor’s browser.

Project organization

web/ is the canonical project home. Keep authored guides, book chapters and tutorials in web/src/content/docs/, grouped through their frontmatter and navigation. Blog and devlog entries live in web/src/content/blog/. Interactive examples live with the website routes and include tested Rust source rather than copies of its behavior. Everything ships together in web/dist/.

Rust libraries live in crates/, runnable applications in apps/, host adapters in packages/, and prototypes in proto/. Root docs/ retains historical design and hardware engineering records. New public learning material belongs in web/; review engineering records for currency before publishing them.

Chrome/web, Unity and Blender are integration targets. Konjure Kreate is the default workshop application, with an independent browser build under apps/kreate/ and reusable workbench code under packages/workbench/. The native RayNeo Konjure client remains under proto/wgpu-probe; it has not been relocated into a Kreate Android shell. See Applications and Konjure Kreate for ownership, local project-file semantics and the standalone/pairing workflow. Kode remains a candidate identity. SDK bindings are generated from Rust, while host-specific rendering, lifecycle and platform APIs stay in their adapters.