Skip to content
This repository was archived by the owner on Jul 31, 2026. It is now read-only.

Commit ab88dfa

Browse files
committed
feat: implement declarative struct-based additive migrations and cascading soft deletes
1 parent 721dc6c commit ab88dfa

5 files changed

Lines changed: 28 additions & 4 deletions

File tree

CHANGELOG.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,11 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8-
## [6.2.0] - 2026-07-28
8+
## [6.2.0] - unreleased
99

1010
### Added
1111
- **Cascading Soft Deletes (Phase 6):** Added `cascade_soft_delete` option to `has_many` and `has_one` relations. When a parent model is soft-deleted, all dependent children are now automatically soft-deleted in a recursive, transactional manner, ensuring referential logic integrity without breaking changes.
12-
- **Declarative Struct-Based Migrations (MVP):** Introduced the foundational AST-parsing engine (`schema_diff.rs`) to power the new `artisan make:migration:auto` command. This engine leverages `syn` to read local `.rs` files and dynamically compare Rust structs against the live database, scaffolding missing tables and columns automatically. As an MVP, this engine prioritizes data safety by solely generating additive SQL (CREATE TABLE / ADD COLUMN) and intentionally bypassing destructive operations.
12+
- **Declarative Struct-Based Migrations (Safe Additive):** Introduced the foundational AST-parsing engine (`schema_diff.rs`) to power the new `artisan make:migration:auto` command. This engine leverages `syn` to read local `.rs` files and dynamically compare Rust structs against the live database, scaffolding missing tables and columns automatically. Currently, this engine prioritizes data safety by solely generating additive SQL (CREATE TABLE / ADD COLUMN) and intentionally bypassing destructive operations. (Note: Full destructive capabilities will be implemented in future versions protected by 'Safe by Default' mechanisms like `--allow-destructive` flags).
1313

1414
## [6.1.1] - 2026-07-26
1515

README.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,8 @@ In traditional Rust database handling, you have to write raw SQL queries, manage
5757
- **Data Governance & Privacy**: Compile-time GDPR/LGPD compliance with at-rest encryption and log masking.
5858
- **Scout Search**: Seamlessly sync models to full-text search engines.
5959
- **Database-First Introspection**: The official framework CLI (`cargo rullst generate:models`) connects to legacy databases and generates your `#[derive(Orm)]` Rust structs automatically.
60+
- **Declarative Struct-Based Migrations**: Safely auto-generate additive SQL migrations (`make:migration:auto`) directly from your Rust struct definitions.
61+
- **Cascading Soft Deletes**: Configure relationships to automatically soft-delete dependent children records in a single transaction.
6062
- **Type-Safe Partial Updates**: Virtual dirty checking with `.update_partial()` to intelligently modify only changed columns.
6163
- **Model Policies (Authorization)**: Laravel-style fine-grained access control securely tied to your structs via `#[orm(policy = "MyPolicy")]`.
6264
- **Strict Lazy Loading Prevention**: Enable a global toggle to instantly panic on N+1 queries during development.

ROADMAP.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,8 @@ We introduced the `strict-postgres`, `strict-mysql`, and `strict-sqlite` feature
7777
Our goal is to provide tools that normally cost thousands of dollars, completely free and open-source, ensuring `rullst-orm` stands unrivaled in the Rust ecosystem.
7878

7979
- [x] **Native Core Multi-tenancy (Global Scopes)**: Automatic Global Scopes isolate tenant data in SaaS. With `#[orm(global_scope = "tenant")]`, the ORM injects `WHERE tenant_id = X` and prevents leaks; requiring global access demands explicit and noisy calls like `.unscoped()`.
80-
- [ ] **Declarative Struct-Based Migrations (AST-Driven)**: Automatic bidirectional synchronization reading Rust structs to generate corresponding SQL migrations, supporting codemods to apply perfectly formatted `ALTER TABLE` via the `cargo rullst upgrade` command.
80+
- [x] **Declarative Struct-Based Migrations (Safe Additive)**: Automatic synchronization reading Rust structs to generate corresponding SQL migrations (tables and columns) via the `make:migration:auto` command, guaranteeing data safety.
81+
- [ ] **Declarative Migrations (Destructive Operations)**: Implement full resource synchronization (dropping columns and tables) protected by "Safe by Default" patterns (e.g., `--allow-destructive` flag or commented-out SQL generation) to prevent accidental data loss.
8182
- [x] **Strict Lazy Loading Prevention**: A Laravel-inspired feature (`Orm::prevent_lazy_loading(true)`) that throws a loud runtime error during development/testing if a relationship is accessed without being eager-loaded, completely preventing N+1 issues without polluting the codebase with strict typestates.
8283
- [x] **Type-Safe Partial Updates (Virtual Dirty Checking)**: A macro-driven mechanism that tracks changed properties in memory, generating an `UPDATE` only for modified columns without overhead, using typing to honor database constraints (e.g., not null).
8384
- [x] **Automated Compliance & Data Governance (GDPR/LGPD)**: `#[derive(PersonalData)]` macro for out-of-the-box privacy reports, and `SecretString` for transparent AES-256-GCM encryption at rest, preventing accidental data leakage.
@@ -88,7 +89,7 @@ Our goal is to provide tools that normally cost thousands of dollars, completely
8889
- [x] **Rullst ORM Admin Panel**: A drop-in function that generates a beautiful web dashboard to manage your data without writing frontend code.
8990
- [x] **API Resources & Transformers**: A declarative way to transform Rullst Models and eager-loaded relationships into clean JSON API responses, handling hidden fields, date formatting, and nested relations effortlessly.
9091
- [x] **Schema Visualizer (Mermaid ER Diagrams)**: A CLI command (`cargo rullst generate:diagram`) that reads models and outputs a Mermaid markdown file showing database architecture and relationships.
91-
- [ ] **Cascading Soft Deletes**: Automatic recursive soft deletion. If a parent is soft-deleted, automatically apply soft deletes to dependent children (`ON DELETE CASCADE` equivalent for logical deletes).
92+
- [x] **Cascading Soft Deletes**: Automatic recursive soft deletion. If a parent is soft-deleted, automatically apply soft deletes to dependent children (`ON DELETE CASCADE` equivalent for logical deletes).
9293
- [x] **Native Enum Mapping**: Clean, type-safe mapping of Rust `enum` to database `ENUM` types (PostgreSQL/MySQL) or secure string constraints (SQLite).
9394

9495
## 🧠 Phase 7: The Future (AI, Quantum & Infrastructure)

website/docs/2-relationships.md

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,21 @@ pub struct Post {
5656
}
5757
```
5858

59+
### Cascading Soft Deletes
60+
61+
When using Soft Deletes (`deleted_at`), you can configure relationships to automatically soft-delete dependent children when the parent is soft-deleted.
62+
63+
```rust
64+
#[derive(Debug, Clone, FromRow, Orm)]
65+
pub struct User {
66+
pub id: i32,
67+
68+
// If the User is soft-deleted, all their posts will be soft-deleted automatically!
69+
#[orm(has_many(model = "Post", foreign_key = "user_id", local_key = "id", cascade_soft_delete = true))]
70+
pub posts: Vec<Post>,
71+
}
72+
```
73+
5974
---
6075

6176
## Eager Loading (With)

website/docs/4-migrations-schema.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,3 +88,9 @@ Reverts the last batch of executed migrations by triggering their `down()` or `d
8888
cargo run -- make:audit
8989
```
9090
Automatically seeds the `rullst_audits` tracking table into your schema to support the `#[orm(auditable)]` feature.
91+
92+
#### 5. Declarative Migrations (Auto MVP)
93+
```bash
94+
cargo run -- make:migration:auto
95+
```
96+
An experimental MVP feature that compares your Rust structs (`#[derive(Orm)]`) directly against the live database and automatically generates additive SQL (creating missing tables and columns) without manual intervention. It prioritizes data safety by ignoring destructive operations (like drops).

0 commit comments

Comments
 (0)