SchemaSaurus is a .NET library for capturing a complete, immutable snapshot of a relational database's structural metadata — tables, views, indexes, foreign keys, stored procedures, functions, sequences, and user-defined types — into a single, JSON-serializable object graph.
It is designed for tools that need a stable, provider-agnostic view of a database schema: code generators, ORM tooling, migration diffing, documentation generation, and schema visualization.
| Package | Version |
|---|---|
| SchemaSaurus.Metadata | |
| SchemaSaurus.SqlServer | |
| SchemaSaurus.PostgreSql | |
| SchemaSaurus.MySql | |
| SchemaSaurus.Oracle | |
| SchemaSaurus.Sqlite |
- Immutable, JSON round-trippable model rooted at
DatabaseModelwith structural equality. - Provider-agnostic abstraction via
IDatabaseSchemaReader— a single API across every supported engine. - Rich metadata coverage — tables, columns, primary keys, unique constraints, check constraints, indexes, foreign keys, views, stored procedures, scalar and table-valued functions, sequences, user-defined types, and triggers.
- Filtering by schema, table, and object kind through
SchemaReaderOptions. - Visitor pattern (
DatabaseVisitor) for walking the model in code generators and analyzers. - Annotations on every metadata element for engine-specific extensions (collation, identity, extended properties, etc.).
- Multi-target —
netstandard2.0,net462,net8.0,net9.0, andnet10.0.
| Package | Minimum Supported Server |
|---|---|
SchemaSaurus.SqlServer |
SQL Server 2016 (13.x) or later, Azure SQL Database, Azure SQL Managed Instance |
SchemaSaurus.PostgreSql |
PostgreSQL 12 or later |
SchemaSaurus.MySql |
MySQL 5.7 or later, MariaDB 10.2 or later |
SchemaSaurus.Oracle |
Oracle Database 12c (12.1) or later |
SchemaSaurus.Sqlite |
SQLite 3.31.0 or later |
All providers depend on the shared SchemaSaurus.Metadata package, which defines the model and abstractions.
Install the metadata package plus the provider for your target engine:
dotnet add package SchemaSaurus.Metadata
dotnet add package SchemaSaurus.SqlServerusing SchemaSaurus.Metadata;
using SchemaSaurus.Metadata.Provider;
using SchemaSaurus.SqlServer;
IDatabaseSchemaReader reader = new SqlServerSchemaReader();
DatabaseModel model = await reader.ReadAsync("Server=.;Database=AdventureWorks;Integrated Security=true;TrustServerCertificate=true");
Console.WriteLine($"{model.DatabaseName} ({model.Provider} {model.ServerVersion})");
Console.WriteLine($"Tables: {model.Tables.Count}, Views: {model.Views.Count}");var options = new SchemaReaderOptions
{
Schemas = ["dbo", "Sales"],
IncludeStoredProcedures = false,
IncludeScalarFunctions = false,
};
var model = await reader.ReadAsync(connectionString, options);The model uses source-generated System.Text.Json serialization via MetadataJsonContext for AOT-friendly, allocation-light round-tripping.
using System.Text.Json;
using SchemaSaurus.Metadata;
string json = JsonSerializer.Serialize(model, MetadataJsonContext.Default.DatabaseModel);
DatabaseModel restored = JsonSerializer.Deserialize(json, MetadataJsonContext.Default.DatabaseModel)!;Walk the model to drive code generation or analysis:
public sealed class TableLogger : DatabaseVisitor
{
protected override void VisitTable(Table table)
{
Console.WriteLine($"{table.Name} ({table.Columns.Count} columns)");
base.VisitTable(table);
}
}
new TableLogger().VisitDatabase(model);DatabaseModel is a flat container — every object carries its own SchemaQualifiedName, so consumers can group or filter by schema without traversing a hierarchy.
Tables→Columns,PrimaryKey,UniqueConstraints,CheckConstraints,Indexes,ForeignKeys,TriggersViews→Columns,DefinitionStoredProcedures/ScalarFunctions/TableValuedFunctions→Parameters,ReturnColumns,DefinitionSequences,UserDefinedTypes
Every metadata element implements IAnnotatable for engine-specific extension data.
MIT © LoreSoft