Rails Integration Guide
This guide shows how to integrate FakeDataDSL into your Rails application for frontend mocks, backend testing, and DevOps pipelines.
Installation
Add to your Gemfile:
# Gemfile
group :development, :test do
gem 'fake_data_dsl'
end
Directory Structure
Create the standard schema directory:
your_rails_app/
├── app/
├── config/
│ └── fake_data_dsl.yml # Configuration
├── schemas/ # DSL schemas
│ ├── user.dsl
│ ├── product.dsl
│ ├── order.dsl
│ └── api_response.dsl
├── generated/ # Generated outputs
│ ├── types/ # TypeScript types for frontend
│ ├── mocks/ # JSON mock data
│ └── docs/ # HTML documentation
└── spec/
└── schemas/ # Schema-specific tests
Configuration
# config/fake_data_dsl.yml
default_mode: random
max_unique_retries: 1000
limits:
max_array_size: 100
max_recursion: 5
test:
default_mode: edge # Use edge cases in tests
seed: 42 # Deterministic in CI
development:
default_mode: random
production:
# Production shouldn't use this gem
Schema Examples
User Schema
# schemas/user.dsl
User:
id: uuid(unique: true)
email: email(unique: true)
name: name
role: enum(admin, user, guest)
created_at: timestamp
updated_at: timestamp
API Response Schema
# schemas/api_response.dsl
APIResponse:
@latency 50..200ms # Simulate network latency
@failure 2% # 2% chance of failure
success: boolean(true:95%)
data: object
meta:
page: number(1..100)
per_page: const(20)
total: number(0..10000)
timestamp: now
E-Commerce Schemas
# schemas/product.dsl
Product:
id: uuid(unique: true)
name: text(10..100)
description: text(50..500)
price: money(range: 9.99..999.99)
currency: enum(USD, EUR, GBP)
category: enum(electronics, clothing, home, sports)
in_stock: boolean(true:85%)
images: array(url, 1..5)
# schemas/order.dsl
Order:
id: uuid(unique: true)
user_id: Ref(User.id)
items: array(OrderItem, 1..10)
subtotal: money(range: 10..5000)
tax: custom(:calculate_tax)
total: custom(:calculate_total)
status: enum(pending, processing, shipped, delivered, cancelled)
created_at: timestamp
OrderItem:
product_id: Ref(Product.id)
quantity: number(1..10)
unit_price: money(range: 9.99..999.99)
Frontend Integration
Generate TypeScript Types
# Generate all types
fake_data_dsl export --all -d schemas -f typescript -o frontend/src/types/api.ts
Output:
// frontend/src/types/api.ts
export interface User {
id: string;
email: string;
name: string;
role: 'admin' | 'user' | 'guest';
created_at: string;
updated_at: string;
}
export interface Product {
id: string;
name: string;
description: string;
price: number;
currency: 'USD' | 'EUR' | 'GBP';
category: 'electronics' | 'clothing' | 'home' | 'sports';
in_stock: boolean;
images: string[];
}
Generate Mock Data
# Generate mock users
fake_data_dsl generate User -d schemas -c 50 --pretty > frontend/mocks/users.json
# Generate with seed for deterministic mocks
fake_data_dsl generate User -d schemas -c 50 --seed 42 --pretty > frontend/mocks/users.json
Live Mock Server (Development)
# Start live preview with hot reload
fake_data_dsl live schemas/ --port 4567
Access http://localhost:4567 for interactive mock generation.
Backend Integration
RSpec Setup
# spec/support/fake_data_dsl.rb
require 'fake_data_dsl'
require 'fake_data_dsl/rails_test_helper'
RSpec.configure do |config|
config.include FakeDataDSL::RailsTestHelper
# Load schemas once
config.before(:suite) do
FakeDataDSL.configure_test_helper!
end
end
Using in Tests
# spec/models/user_spec.rb
RSpec.describe User do
describe 'validations' do
it 'validates with generated data' do
user_data = generate_for_test(User)
user = User.new(user_data)
expect(user).to be_valid
end
it 'tests edge cases' do
user_data = generate_for_test(User, :edge)
# Edge cases like empty strings, boundary values, etc.
end
it 'handles invalid data gracefully' do
user_data = generate_for_test(User, :invalid)
user = User.new(user_data)
expect(user).not_to be_valid
end
end
end
Snapshot Testing
# spec/schemas/user_schema_spec.rb
RSpec.describe 'User Schema' do
include FakeDataDSL::SnapshotTesting
it 'generates stable output' do
schema = FakeDataDSL.load('schemas/user.dsl')
expect_snapshot(schema, seed: 42)
end
end
Database Seeding
# db/seeds.rb
require 'fake_data_dsl'
FakeDataDSL.seed_database do
create User, count: 100
create Product, count: 500
create Order, count: 1000
end
Or with Rake task:
# lib/tasks/seed_fake_data.rake
namespace :db do
desc 'Seed database with fake data'
task seed_fake: :environment do
FakeDataDSL.seed_database(truncate: Rails.env.development?) do
create User, count: ENV.fetch('USER_COUNT', 100).to_i
create Product, count: ENV.fetch('PRODUCT_COUNT', 500).to_i
create Order, count: ENV.fetch('ORDER_COUNT', 1000).to_i
end
end
end
DevOps Integration
GitHub Actions CI
# .github/workflows/schema-ci.yml
name: Schema CI
on: [push, pull_request]
jobs:
validate:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Set up Ruby
uses: ruby/setup-ruby@v1
with:
ruby-version: '3.2'
bundler-cache: true
- name: Validate schemas
run: bundle exec fake_data_dsl lint schemas/ --strict
- name: Check for breaking changes
if: github.event_name == 'pull_request'
run: |
git fetch origin ${{ github.base_ref }}
bundle exec fake_data_dsl diff \
schemas/ \
origin/${{ github.base_ref }}:schemas/ \
--breaking-only
- name: Generate documentation
run: bundle exec fake_data_dsl docs schemas/ --output docs/schemas/
- name: Upload docs artifact
uses: actions/upload-artifact@v3
with:
name: schema-docs
path: docs/schemas/
Pre-commit Hook
#!/bin/bash
# .git/hooks/pre-commit
# Validate schemas before commit
if ! bundle exec fake_data_dsl lint schemas/ --strict; then
echo "❌ Schema validation failed"
exit 1
fi
echo "✅ Schemas valid"
Docker Integration
# Dockerfile.dev
FROM ruby:3.2
# Install fake_data_dsl globally for CLI access
RUN gem install fake_data_dsl
# Your app setup...
WORKDIR /app
COPY . .
# Generate mocks at build time
RUN fake_data_dsl generate User -d schemas -c 100 > mocks/users.json
API Mock Server
For a full mock API server, use the Live Preview or create a simple Sinatra app:
# mock_server.rb
require 'sinatra'
require 'fake_data_dsl'
registry = FakeDataDSL::Registry.new
registry.load_dir('schemas')
get '/api/users' do
content_type :json
schema = registry.schema('User')
count = params[:count]&.to_i || 10
schema.generate_many(count).to_json
end
get '/api/users/:id' do
content_type :json
schema = registry.schema('User')
schema.generate(overrides: { 'id' => params[:id] }).to_json
end
get '/api/products' do
content_type :json
schema = registry.schema('Product')
schema.generate_many(params[:count]&.to_i || 20).to_json
end
# Run: ruby mock_server.rb
Common Patterns
Pattern 1: Environment-specific Data
# Generate different data per environment
mode = case Rails.env
when 'test' then :edge
when 'development' then :random
else :random
end
schema.generate(mode: mode)
Pattern 2: Factory Bot Bridge
# spec/factories.rb
FakeDataDSL.define_factory(:user, schema: 'User') do
trait(:admin) { role { 'admin' } }
trait(:guest) { role { 'guest' } }
end
# Usage
create(:user, :admin)
Pattern 3: GraphQL Mocks
# Generate GraphQL schema
fake_data_dsl export --all -d schemas -f graphql -o graphql/mocks.graphql
Pattern 4: Import from OpenAPI
# Convert existing OpenAPI spec to DSL
fake_data_dsl import swagger.yaml --output schemas/
Troubleshooting
Schema not found
# Check available schemas
fake_data_dsl info schemas/
Breaking change detected in CI
# See detailed diff
fake_data_dsl diff schemas/old/ schemas/new/
Slow generation
# Use native Rust engine for millions of records
schema.generate_many(1_000_000, engine: :native, threads: 4)
Next Steps
- Create schemas for your domain models
- Set up CI with schema validation
- Generate TypeScript types for frontend
- Configure test helpers for RSpec/Minitest
- Set up mock server for frontend development
For more examples, see the tech_example/ directory.