Skip to content

Instantly share code, notes, and snippets.

@geetfun
Created July 10, 2025 02:00
Show Gist options
  • Save geetfun/91ebab905e63df39d5f816259754214c to your computer and use it in GitHub Desktop.
Save geetfun/91ebab905e63df39d5f816259754214c to your computer and use it in GitHub Desktop.
Rails application template v07092025
# Rails Application Template for Stepsies-style Applications
# Usage: rails new myapp -m rails_template.rb
# Configuration
app_name = @app_name || ask("What is the name of your application?")
# Gem additions
gem_group :development, :test do
gem 'brakeman', require: false
gem 'rubocop-rails-omakase', require: false
gem 'debug', platforms: %i[mri windows], require: 'debug/prelude'
end
gem_group :development do
gem 'web-console'
gem 'claude-on-rails', '~> 0.2.0'
gem 'annotaterb'
end
gem_group :test do
gem 'capybara'
gem 'selenium-webdriver'
gem 'mocha'
end
# Main application gems
gem 'mission_control-jobs'
gem 'meta-tags'
gem 'sitemap_generator'
gem 'google_sign_in'
gem 'view_component', '4.0.0.rc2'
gem 'name_of_person'
# Enable bcrypt (uncomment existing line)
gsub_file 'Gemfile', /# gem "bcrypt"/, 'gem "bcrypt"'
# Database configuration
create_file 'config/database.yml', <<~YAML
# PostgreSQL. Versions 9.3 and up are supported.
#
# Install the pg driver:
# gem install pg
# On macOS with Homebrew:
# gem install pg -- --with-pg-config=/usr/local/bin/pg_config
# On Windows:
# gem install pg
# Choose the win32 build.
# Install PostgreSQL and put its /bin directory on your path.
#
# Configure Using Gemfile
# gem "pg"
#
default: &default
adapter: postgresql
encoding: unicode
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
# Remove timeout as it's not typically used with PostgreSQL
test:
primary:
<<: *default
database: #{app_name}_test
host: 127.0.0.1
username: postgres
password: postgres
cache:
<<: *default
database: #{app_name}_cache_test
migrations_paths: db/cache_migrate
host: 127.0.0.1
username: postgres
password: postgres
queue:
<<: *default
database: #{app_name}_queue_test
migrations_paths: db/queue_migrate
host: 127.0.0.1
username: postgres
password: postgres
cable:
<<: *default
database: #{app_name}_cable_test
migrations_paths: db/cable_migrate
host: 127.0.0.1
username: postgres
password: postgres
development:
primary:
<<: *default
database: #{app_name}_development
host: 127.0.0.1
username: postgres
password: postgres
cache:
<<: *default
database: #{app_name}_cache_development
migrations_paths: db/cache_migrate
host: 127.0.0.1
username: postgres
password: postgres
queue:
<<: *default
database: #{app_name}_queue_development
migrations_paths: db/queue_migrate
host: 127.0.0.1
username: postgres
password: postgres
cable:
<<: *default
database: #{app_name}_cable_development
migrations_paths: db/cable_migrate
host: 127.0.0.1
username: postgres
password: postgres
# As with config/credentials.yml, you never want to store sensitive information,
# like your database password, in your source code. If your source code is
# ever seen by anyone, they now have access to your database.
#
# Instead, provide the password or a full connection URL as an environment
# variable when you boot the app. For example:
#
# DATABASE_URL="postgres://myuser:mypass@localhost/somedatabase"
#
# If the connection URL is provided in the special DATABASE_URL environment
# variable, Rails will automatically merge its configuration values on top of
# the values provided in this file. Alternatively, you can specify a connection
# URL environment variable explicitly:
#
# production:
# url: <%= ENV["MY_APP_DATABASE_URL"] %>
#
# Read https://guides.rubyonrails.org/configuring.html#configuring-a-database
# for a full overview on how database connection configuration can be specified.
#
production:
primary:
<<: *default
database: #{app_name}_primary_production
username: <%= ENV['DATABASE_USERNAME'] %>
password: <%= ENV['DATABASE_PASSWORD'] %>
host: <%= ENV['DATABASE_HOST'] %>
cache:
<<: *default
database: #{app_name}_cache_production
username: <%= ENV['CACHE_DATABASE_USERNAME'] %>
password: <%= ENV['CACHE_DATABASE_PASSWORD'] %>
host: <%= ENV['CACHE_DATABASE_HOST'] %>
migrations_paths: db/cache_migrate
queue:
<<: *default
database: #{app_name}_queue_production
username: <%= ENV['QUEUE_DATABASE_USERNAME'] %>
password: <%= ENV['QUEUE_DATABASE_PASSWORD'] %>
host: <%= ENV['QUEUE_DATABASE_HOST'] %>
migrations_paths: db/queue_migrate
cable:
<<: *default
database: #{app_name}_cable_production
username: <%= ENV['CABLE_DATABASE_USERNAME'] %>
password: <%= ENV['CABLE_DATABASE_PASSWORD'] %>
host: <%= ENV['CABLE_DATABASE_HOST'] %>
migrations_paths: db/cable_migrate
YAML
# Docker Compose configuration
create_file 'docker-compose.yml', <<~YAML
services:
db:
image: postgres:17-alpine
ports:
- 127.0.0.1:5432:5432
environment:
POSTGRES_USER: postgres
POSTGRES_HOST_AUTH_METHOD: trust
redis:
image: redis:7-alpine
ports:
- 127.0.0.1:6379:6379
YAML
# Update bin/dev script
create_file 'bin/dev', <<~SCRIPT
#!/usr/bin/env sh
if ! gem list foreman -i --silent; then
echo "Installing foreman..."
gem install foreman
fi
# Stop all running Docker containers regardless of origin
echo "Stopping all Docker containers..."
docker stop $(docker ps -q) 2>/dev/null || true
# Start Docker containers in detached mode
echo "Starting Docker containers in detached mode..."
docker compose up -d
# Start Cursor in a separate process and disown it
echo "Starting Cursor..."
nohup cursor . >/dev/null 2>&1 & disown
# Default to port 3000 if not specified
export PORT="${PORT:-3000}"
# Let the debug gem allow remote connections,
# but avoid loading until `debugger` is called
export RUBY_DEBUG_OPEN="true"
export RUBY_DEBUG_LAZY="true"
# Create a cleanup function
cleanup() {
echo "Cleaning up processes..."
pkill -P $$
exit 0
}
# Trap both SIGTERM and SIGINT to the cleanup function
trap cleanup SIGTERM SIGINT
# Execute foreman without exec to keep the shell process
foreman start -f Procfile.dev "$@"
SCRIPT
# Update Rubocop configuration
append_to_file '.rubocop.yml', <<~YAML
# Prefer single quotes over double quotes
Style/StringLiterals:
EnforcedStyle: single_quotes
# Require newlines at end of files
Layout/EndOfLine:
Enabled: true
YAML
# Update routes for Mission Control Jobs
inject_into_file 'config/routes.rb', after: "get \"up\" => \"rails/health#show\", as: :rails_health_check\n" do
<<~RUBY
# Mission Control Jobs UI
mount MissionControl::Jobs::Engine, at: "/jobs"
RUBY
end
# Update test helper for Mocha
inject_into_file 'test/test_helper.rb', after: "require \"rails/test_help\"\n" do
<<~RUBY
require "mocha/minitest"
RUBY
end
# CLAUDE.md configuration file
create_file 'CLAUDE.md', <<~MARKDOWN
## ClaudeOnRails Configuration
You are working on #{app_name}, a Rails application. Review the ClaudeOnRails context file at @.claude-on-rails/context.md
## Rails 8 Project
This is a Rails 8 project. For reference, you should always consider the information at:
- https://guides.rubyonrails.org/v8.0/index.html
- https://api.rubyonrails.org/
## Test Driven Development
We follow test driven development best practices. This means:
- Tests should be written first
- Demonstrate that they fail
- Then write implementation and correct until tests pass
## Gem Management
You may suggest the use of gems, but do not automatically add them. Instead, you should present that information to me first, and let me decide.
## Frontend Development Pattern
We will use Stimulus JS with Turbo (and Turboframes) for more complex interactions. For simple interactions, we will leverage Alpine JS.
## Styling and UI Components
We will use TailwindCSS v4 for the styling of the web application. For UI components, please use Tailwind Plus (formerly known as Tailwind UI). Reference: https://tailwindcss.com/plus. The UI blocks are at https://tailwindcss.com/plus/ui-blocks/
MARKDOWN
# After bundle install, run generators and setup
after_bundle do
# Make bin/dev executable
run "chmod +x bin/dev"
# Generate meta_tags initializer
generate "meta_tags:install"
# Generate annotaterb setup
generate "annotate_rb:install"
# Setup Alpine.js
run "bin/importmap pin alpinejs"
run "bin/importmap pin alpine-turbo-drive-adapter"
# Update application.js for Alpine.js
inject_into_file 'app/javascript/application.js', after: "import \"controllers\"\n" do
<<~JAVASCRIPT
import "alpine-turbo-drive-adapter"
import Alpine from "alpinejs"
window.Alpine = Alpine
Alpine.start()
JAVASCRIPT
end
# Create ClaudeOnRails context directory and basic structure
directory = '.claude-on-rails'
empty_directory directory
create_file "#{directory}/context.md", <<~MARKDOWN
# ClaudeOnRails Context
This project uses ClaudeOnRails with a swarm of specialized agents for Rails development.
## Project Information
- **Rails Version**: 8.0.2
- **Ruby Version**: 3.4.2
- **Project Type**: Full-stack Rails
- **Test Framework**: Minitest
- **Turbo/Stimulus**: Enabled
- **Alpine.js**: Enabled
## Swarm Configuration
The claude-swarm.yml file defines specialized agents for different aspects of Rails development:
- Each agent has specific expertise and works in designated directories
- Agents collaborate to implement features across all layers
- The architect agent coordinates the team
## Development Guidelines
When working on this project:
- Follow Rails conventions and best practices
- Write tests for all new functionality
- Use strong parameters in controllers
- Keep models focused with single responsibilities
- Extract complex business logic to service objects
- Ensure proper database indexing for foreign keys and queries
MARKDOWN
# Initialize git repository if not already initialized
git :init unless File.exist?('.git')
# Add all files to git
git add: '.'
# Initial commit
git commit: "-m 'Initial commit with Rails 8 template'"
say "🎉 Rails application '#{app_name}' has been created successfully!"
say ""
say "Next steps:"
say "1. Run 'bin/dev' to start the development server"
say "2. The application includes:"
say " - PostgreSQL multi-database setup"
say " - Docker Compose for local development"
say " - Alpine.js for simple interactions"
say " - Stimulus.js for complex interactions"
say " - TailwindCSS v4 for styling"
say " - Mission Control Jobs at /jobs"
say " - Meta tags and SEO optimization"
say " - ViewComponent for reusable components"
say " - Mocha for testing"
say " - Annotaterb for model annotations"
say " - ClaudeOnRails integration"
say ""
say "3. Check CLAUDE.md for development guidelines"
say "4. Use 'docker compose up -d' to start PostgreSQL and Redis"
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment