Rails + AI gives you speed-to-market. MechaRuby is the armor.
AI agents can ship a feature in thirty seconds—and open ten security holes along the way. The mecha_* gems are AI-first libraries built to give coding agents one central registry to read and fast, deterministic feedback when they drift. Build software at scale without creating security nightmares.
Ruby on Rails and AI coding agents give small teams superpowers. An agent can generate models, controllers, and migrations in minutes that used to take a team all week. We love that speed.
But Rails leaves your sharpest boundaries open by default. Add a new route, and any logged-in user can hit it unless the agent remembers the right before_action. Add a controller action, and one bare Message.find(params[:id]) leaks another customer's data. Add a database column, and sensitive tokens sit in plaintext until someone notices in a post-mortem.
Traditional teams rely on tribal conventions, manual PR checklists, or policy objects scattered across dozens of files. AI agents cannot read rules that live in a senior developer's head. When your security model is spread across a hundred files, an agent has to guess—and one bad guess ships a breach.
Give AI agents a single source of truth and a compiler-grade feedback loop: declare every boundary in one YAML file, enforce it at runtime, audit it statically in milliseconds, and attack it automatically in CI.
That is the MechaRuby approach. Each mecha_* library gives coding agents clear, consistent, line-numbered feedback so they fix violations before code ever ships. No magic DSLs. No guesswork. Just mechanical certainty.
One Architecture. Three Guarantees.
Every MechaRuby gem enforces the same three-step feedback loop for humans and AI coding agents.
Closed by Default
Declare every route, model, and database column in a single YAML registry. Humans and AI agents read and update one file instead of hunting across the codebase. If a resource is not in the file, the system rejects it immediately.
Deterministic Agent Feedback
Inspect your Rails routes, Prism controller ASTs, and database schemas in milliseconds. Unmapped resources and unscoped queries fail with exact file-and-line instructions that AI agents fix on the first pass.
Live Attack Matrices
Do not trust static config alone. Built-in probers fire real requests across every persona, run cross-tenant IDOR attacks, and verify database ciphertexts in CI.
Make cross-tenant data leaks a syntax error, not a production incident.
AI agents default to standard Rails idioms like Invoice.find(params[:id]). That single unscoped line leaks another customer's data, and human pull-request reviews will never catch every occurrence at scale.
mecha_tenant forces every model into the light. You classify each ApplicationRecord subclass in config/mecha_tenant.yml as either tenant (with an explicit ownership path and scope resolver) or global.
In controllers, code queries tenant data through tenant_scope(Model). If an action does not touch tenant data, it must call skip_tenant_enforcement! with a written reason.
- Prism AST feedback for agents: Parses every controller with Ruby's Prism parser and prints the exact file, line, and required
tenant_scope(Model)call whenever an agent writes a bare model query. - Strict model registry: Generating a new model without registering its tenancy classification in
mecha_tenant.ymlfails the audit immediately. - Automated IDOR prober: Seeds victim and attacker records, verifies scope isolation for every model, and fires cross-tenant requests at your parameterized routes.
class MessagesController < ApplicationController
# Bare `EmailMessage.find(params[:id])` fails the Prism AST audit.
# Every tenant lookup goes through `tenant_scope`:
def show
@message = tenant_scope(EmailMessage).find(params[:id])
end
end
Running MechaTenant static model & controller AST audit...
-> 24 models registered (21 tenant, 3 global)
-> 84 controller routes audited (76 enforced, 8 explicitly skipped)
ERROR: Found 1 unscoped model reference violation(s) in controllers:
- app/controllers/drafts_controller.rb:19 [DraftsController#destroy]
Direct query on tenant model 'EmailDraft' must use tenant_scope(EmailDraft)
EmailDraft.find(params[:id]).destroy!
Account for every column in your database. Encrypt secrets; justify the rest.
Rails 7+ ships with excellent ActiveRecord encryption. The hard part is not encrypting a column. The hard part is when an AI agent generates three new tables during a feature sprint and leaves OAuth tokens or PII sitting in plaintext.
mecha_encrypt brings closed-by-default discipline to your database schema. Every table and column must be registered in config/mecha_encrypt.yml.
If you set encrypted: false on a column, you must write a comment explaining why plaintext storage is safe. No silent defaults.
- 100% schema parity: When an agent runs a migration that adds a column, the audit fails with the exact missing table and column name until it is classified in
mecha_encrypt.yml. - Model vs. YAML verification: Catches columns marked encrypted in YAML that lack
encrypts :columnon the ActiveRecord model (and vice versa). - Index & ciphertext prober: Verifies raw database ciphertexts, tests round-trip decryption, and catches B-tree indexes placed on non-deterministic encrypted columns.
tables:
email_accounts:
id:
encrypted: false
comment: "Primary key UUID identifier"
email_address:
encrypted: true
deterministic: true
oauth_refresh_token:
encrypted: true
deterministic: false
Running MechaEncrypt static database & model encryption audit...
-> 24 tables audited (3 framework/engine tables ignored via pattern)
-> 198 columns audited (42 encrypted, 9 deterministic, 147 unencrypted)
✓ Static database encryption audit passed: 0 unregistered columns.
Running MechaEncrypt behavioral encryption & index safety test suite...
-> Verified raw ciphertext envelopes & IVs across 51 encrypted columns
-> Verified 0 non-deterministic columns covered by broken B-tree indexes
✓ All encryption & index safety checks passed.