A Rails 8.1 application for tracking supervised driving hours toward a driver's license. The app tracks 50 total hours (including 10 night hours) and provides real-time updates via Turbo Streams and Action Cable.
- Track driving sessions with start/end times
- Automatic night hours, split at real sunset and sunrise for the driver's location
- Real-time progress tracking with live updates
- Timezone-aware time handling
- Export driving log to CSV (date, times, and duration split into day and night hours)
- Mobile-responsive design with PWA support
- Ruby 3.4.7 (see
.ruby-version) - Bundler (for managing Ruby gems)
- SQLite3 (database)
- Foreman (for running multiple processes in development -
gem install foreman) - Node.js is not required (uses ImportMaps, no build step)
git clone <repository-url>
cd drive50bundle installbin/rails db:prepareOr to reset and seed with sample data:
bin/rails db:reset
bin/rails db:seedbin/devThis will start:
- Rails server on http://localhost:3000
- Solid Queue jobs processor (for background jobs)
Alternative setup:
bin/setup # Full setup (installs deps, prepares DB, starts server)
bin/setup --reset # Reset database before starting
bin/setup --skip-server # Setup without starting server# Run all tests
bin/rails test
# Run only system tests
bin/rails test:system
# Run specific test file
bin/rails test test/models/user_test.rb
# Run specific test at a line number
bin/rails test test/models/user_test.rb:12# Run RuboCop linter (Omakase Ruby styling)
bin/rubocop
# Auto-correct RuboCop offenses
bin/rubocop -a
# Security vulnerability scanner
bin/brakeman
# Check for vulnerable gem versions
bin/bundler-audit# Create and setup database
bin/rails db:prepare
# Run pending migrations
bin/rails db:migrate
# Reset database (drop, create, migrate, seed)
bin/rails db:reset
# Load schema without running migrations
bin/rails db:schema:load# Start Rails console
bin/rails console
# Console that rolls back all changes on exit
bin/rails console --sandboxThe app uses Solid Queue for background jobs (e.g., sending emails with deliver_later). The jobs processor is automatically started with bin/dev via Procfile.dev.
Important: Solid Queue requires its database tables to be set up. If you see errors about missing solid_queue_* tables, run:
bin/rails runner "load 'db/queue_schema.rb'"To run jobs manually:
bin/jobsThe app automatically detects and stores each user's timezone:
- Detection: Browser timezone is detected via JavaScript (Stimulus
timezone_controller) and sent with forms - Storage: User timezone is stored in the
users.timezonecolumn (defaults to "UTC") - Display: Times are displayed in user's timezone using the
local_timegem - Forms: Datetime inputs are interpreted in the user's timezone (via
Time.zonein ApplicationController) and converted to UTC for storage - Night Drive: Sunset and sunrise are computed for the drive's date at the user's coordinates (falling back to representative coordinates for their timezone). A drive that crosses either boundary is split, so it contributes to both the day and night totals rather than counting wholly as one
Note: The timezone is automatically saved to the user's profile when detected, so it persists across sessions.
In development, emails use the :test delivery method (stored in ActionMailer::Base.deliveries).
For production, configure Resend SMTP credentials:
bin/rails credentials:editAdd:
resend:
api_key: your-resend-api-key
mail:
from: noreply@yourdomain.com
host: yourdomain.comSee docs/credentials-setup.md for more details.
User- User accounts with timezone supportDriveSession- Individual driving sessionsSession- Authentication sessions
DriveSessionsController- Main feature (CRUD for drive sessions)SessionsController- AuthenticationRegistrationsController- User signupPasswordsController- Password reset
The app uses Turbo Streams and Action Cable for real-time updates:
- Drive sessions broadcast updates when created/updated/destroyed
- Updates are scoped per-user
- Multiple DOM targets update independently (in-progress drive, recent drives, all drives table, progress summary)
- Hotwire: Turbo Rails + Stimulus
- No build step: Uses ImportMaps for JavaScript
- LocalTime gem: Converts UTC times to user's local timezone in the browser
The app is configured for deployment with Kamal (Docker-based). See config/deploy.yml for deployment configuration.
[Add your license here]
- Create a feature branch
- Make your changes
- Run tests:
bin/rails test - Run linters:
bin/rubocop - Submit a pull request