Skip to main content

Generating Client Bindings

Before you can interact with a SpacetimeDB database from a client application, you must generate client bindings for your module. These bindings create type-safe interfaces that allow your client to query tables, invoke reducers, call procedures, and subscribe to tables, and/or views.

What Are Module Bindings?

Module bindings are auto-generated code that mirrors your module's schema and functions. They provide:

  • Type definitions matching your module's tables and types
  • Callable functions for invoking reducers and procedures
  • Query interfaces for subscriptions and local cache access
  • Callback registration for observing database changes

The bindings ensure compile-time type safety between your client and server code, catching errors before runtime.

Generating Bindings

Use the spacetime generate command to create bindings from your module:

mkdir -p src/module_bindings
spacetime generate --lang rust --out-dir client/src/module_bindings --project-path PATH-TO-MODULE-DIRECTORY

This generates Rust files in client/src/module_bindings/. Import them in your client with:

mod module_bindings;

Replace PATH-TO-MODULE-DIRECTORY with the path to your module's directory, where the module's Cargo.toml is located.

What Gets Generated

The spacetime generate command creates client-side representations of your module's components:

Tables

For each table in your module, codegen generates:

  • Type/class definitions with properties for each column
  • Table accessor on the DbConnection for querying the client cache
  • Callback registration methods for observing insertions, updates, and deletions

For example, a user table becomes:

// Generated type
pub struct User {
    pub id: u64,
    pub name: String,
    pub email: String,
}

// Access via DbConnection
conn.db().user()

See the Tables documentation for details on defining tables in your module.

Reducers

For each reducer in your module, codegen generates:

  • Client-callable function that sends a reducer invocation request to the server
  • Callback registration method for observing when the reducer runs
  • Type-safe parameters matching the reducer's signature

For example, a create_user reducer becomes:

// Call the reducer
conn.reducers().create_user(name, email);

// Register a callback to observe reducer invocations
conn.reducers().on_create_user(|ctx, name, email| {
    println!("User created: {}", name);
});

See the Reducers documentation for details on defining reducers in your module.

Procedures

For each procedure in your module, codegen generates:

  • Client-callable function that invokes the procedure
  • Return value handling for procedures that return results
  • Type-safe parameters matching the procedure's signature

Procedures are currently in beta. For example, a fetch_external_data procedure becomes:

// Call the procedure without a callback
conn.procedures().fetch_external_data(url);

// Call the procedure with a callback for the result
conn.procedures().fetch_external_data_then(url, |ctx, result| {
    match result {
        Ok(data) => println!("Got result: {:?}", data),
        Err(error) => eprintln!("Error: {:?}", error),
    }
});

See the Procedures documentation for details on defining procedures in your module.

Views

For each view in your module, codegen generates:

  • Type definitions for the view's return type
  • Subscription interfaces for subscribing to view results
  • Query methods for accessing cached view results

Views provide subscribable, computed queries over your data.

See the Views documentation for details on defining views in your module.

Regenerating Bindings

Whenever you modify your module's schema or function signatures, regenerate the client bindings by running spacetime generate again. The tool will overwrite the existing generated files with updated code.

If you're actively developing and testing changes, consider adding spacetime generate to your build or development workflow.

Using the Generated Code

Once you've generated the bindings, you're ready to connect to your database and start interacting with it. See:

Troubleshooting

Missing module directory

If spacetime generate fails to find your module, ensure you're pointing to the directory containing your module's project file (Cargo.toml, .csproj, or package.json).

Outdated bindings

If your client doesn't see new tables or reducers, ensure you've regenerated the bindings after updating your module. Generated code is not automatically updated when the module changes.