Async-first .NET 8 client library for the Object Agent Mapper (ROAM). Install via NuGet:
dotnet add package RoamSdk
using Roam.Sdk;
var config = new RoamClientConfig
{
Host = "localhost",
Port = 50051,
ApiKey = "your-api-key"
};
await using var client = new RoamClient(config);
await client.ConnectAsync();
var sessionId = await client.RegisterAsync("my-agent", "1.0.0", SchemaMode.CodeFirst);
await client.RegisterModelAsync("users");
await client.CloseAsync();
| Property | Type | Default | Description |
|---|---|---|---|
Host | string | "localhost" | Backend hostname |
Port | int | 50051 | gRPC port |
ApiKey | string | required | Injected as x-roam-api-key interceptor |
UseTls | bool | false | Use HTTPS/TLS channel |
Main entry point. Implements IAsyncDisposable and IDisposable.
| Property | Type | Description |
|---|---|---|
IsConnected | bool | True when channel is open |
SchemaMode | SchemaMode | Current schema mode set by RegisterAsync |
RegisteredModels | IReadOnlyCollection<string> | Registered table names |
Query | QueryExecutor | SQL query executor (requires connection) |
Opens the gRPC channel and initialises Agent, Query, and Schema service clients.
await client.ConnectAsync();
Registers the agent and returns the session ID string.
var sessionId = await client.RegisterAsync("my-agent", "1.0.0", SchemaMode.CodeFirst);
Registers a table name for agent access. Only allowed in CodeFirst and Hybrid modes.
await client.RegisterModelAsync("orders");
Gracefully shuts down the channel and cleans up resources.
public enum SchemaMode
{
DataFirst = 0, // Read-only. Schema from DB introspection. Model registration not allowed.
CodeFirst = 1, // App extension. Only registered models. Read-write capable.
Hybrid = 2, // Registered models + read-only introspection fallback.
}
Decorate EF Core models with [RoamModel] and extend RoamDbContext:
using Roam.Sdk.ORM;
using Microsoft.EntityFrameworkCore;
[RoamModel("users")]
public class User
{
public int Id { get; set; }
public string Name { get; set; } = "";
public string Email { get; set; } = "";
}
public class MyDbContext : RoamDbContext
{
public DbSet<User> Users => Set<User>();
protected override void OnConfiguring(DbContextOptionsBuilder options)
=> options.UseSqlServer("connection-string");
}
| Exception | When thrown |
|---|---|
AuthenticationException | Invalid API key or connection failure |
SchemaModeMismatchException | RegisterModel called in DataFirst mode |
ValidationException | Client-side SQL validation failure |
RoamException | Base class for all ROAM-specific errors |
services.AddSingleton(new RoamClientConfig
{
Host = "localhost",
Port = 50051,
ApiKey = Environment.GetEnvironmentVariable("ROAM_API_KEY")!
});
services.AddSingleton<RoamClient>();
Roam.Sdk.Testing.TestClient is an in-memory stub that implements the same interface as RoamClient — no backend required.
using Roam.Sdk.Testing;
var client = new TestClient();
await client.RegisterModelAsync("users");
Assert.Contains("users", client.RegisteredModels);
# Build dotnet build # Unit tests (no backend needed) dotnet test tests/unit/RoamSdk.Tests.csproj # Integration tests (requires make grpc-start) dotnet test tests/integration/RoamSdk.IntegrationTests.csproj