Architecture Overview
Relevant source files
The following files were used as context for generating this wiki page:
Seaography is a GraphQL framework for Rust designed to bridge SeaORM and async-graphql. It automates the creation of a fully-typed GraphQL API by reflecting on database schemas defined as SeaORM entities. Unlike static code generation approaches, Seaography utilizes a dynamic schema engine to reduce compilation times while maintaining type safety and extensibility.
Sources: src/lib.rs:1-40, README.md:16-30
Core System Components
The Seaography ecosystem is divided into three primary functional areas: the CLI for project bootstrapping, the Generator for source code emission, and the Runtime Library for schema building and execution.
Architecture Flow
The following diagram illustrates the workflow from a database schema to a running GraphQL server.
Sources: README.md:58-95, generator/src/lib.rs:17-49
Component Descriptions
| Component | Responsibility | Relevant Files |
|---|---|---|
| CLI | Parses user arguments and database URLs to initiate project generation. | cli/src/main.rs |
| Generator | Generates Cargo.toml, main.rs, and query_root.rs based on web framework choice. | generator/src/writer.rs, generator/src/lib.rs |
| Builder | Orchestrates the dynamic assembly of SeaORM entities into GraphQL objects. | src/lib.rs, examples/sea-draw/src/schema.rs |
| Framework Templates | Provides boilerplate for Actix, Axum, and Poem integrations. | generator/src/templates/ |
Sources: cli/src/main.rs:7-39, generator/src/lib.rs:1-15, generator/src/writer.rs:10-20
Project Generation Pipeline
The generation process is triggered by the seaography-cli. It takes an existing directory of SeaORM entities and a target web framework (Actix, Axum, or Poem) to produce a standalone Rust project.
- URL Parsing: The CLI validates the database connection string to determine the appropriate SQL library (e.g.,
sqlx-mysql,sqlx-postgres). - File Writing: The
write_projectfunction manages the creation of the project structure, including environment variables and theCargo.toml. - Query Root Generation:
writer.rsscans the entity directory, excluding specific files likemod.rsorprelude.rs, and generates aquery_root.rsthat dynamically registers all entities.
Sources: cli/src/main.rs:45-125, generator/src/lib.rs:17-49, generator/src/writer.rs:12-40
Dynamic Schema Construction
The heart of the runtime is the Builder and BuilderContext. These components translate SeaORM metadata into async-graphql dynamic types at runtime.
The Builder Pattern
The Builder uses a BuilderContext to configure how entities are exposed. This includes naming conventions (camelCase vs snake_case), depth limits, and complexity limits for queries.
Entity Registration
Entities are registered using the register_entity method, which automatically handles:
- Filters: Generating input objects for column-based filtering (e.g.,
eq,gt,contains). - Relations: Mapping SeaORM relations (1-to-1, 1-to-N, M-to-N) to nested GraphQL fields.
- Pagination: Supporting both offset-based and cursor-based pagination.
Sources: examples/sea-draw/src/schema.rs:320-345, src/lib.rs:65-80
Extensibility and Security
Seaography provides several hooks for developers to inject custom logic into the dynamically generated schema.
Lifecycle Hooks
Developers can implement the LifecycleHooksInterface to control access at a granular level:
- Entity Guards: Block or allow entire operations (Create, Read, Update, Delete) on an entity.
- Field Guards: Restrict access to specific columns based on context (e.g., user permissions).
- Entity Filters: Automatically inject
WHEREclauses into queries based on the authenticated user.
Sources: examples/sea-draw/src/schema.rs:114-145, CHANGELOG.md:40-90
Custom Fields and Mutations
Using the #[CustomFields] macro, developers can extend the generated models with additional resolvers that are not directly mapped to database columns. This is often used for computed fields or complex business logic.
#[CustomFields]
impl Model {
async fn svg(&self, ctx: &Context<'_>) -> async_graphql::Result<String> {
// Custom logic to generate SVG from entity data
}
}
Sources: examples/sea-draw/src/entities/drawings.rs:72-96, CHANGELOG.md:25-50
Web Framework Integration
Seaography generates framework-specific boilerplate to host the GraphQL endpoint and the GraphQL Playground. The generated main.rs typically handles database connection initialization and schema mounting.
Request Handling Sequence
This sequence shows how a request is processed in an Axum-based generated project.
Summary
The Seaography architecture prioritizes developer velocity by automating the repetitive tasks of GraphQL API creation while maintaining high levels of customization. By leveraging SeaORM's metadata and async-graphql's dynamic schema capabilities, it creates a robust, type-safe bridge that scales from simple CRUD applications to complex, permissioned enterprise systems.
Sources: src/lib.rs:1-30, README.md:15-35