vdb Docs Security

Security

vdb renders your full database schema. That is sensitive information. This page covers the recommended practices for keeping it safe.

Never expose vdb in production without authentication. The schema reveals table names, column names, data types, indexes, and relationships — everything an attacker needs to craft targeted SQL injection or enumerate PII fields.

Development-only mounting

The simplest and most robust guard is to only mount the engine in development:

# config/routes.rb

Rails.application.routes.draw do
  if Rails.env.development?
    mount Vdb::Engine, at: '/dev/erd'
  end

  # …
end

This means the route does not exist at all in staging or production — no auth bypass possible.


HTTP Basic Auth

If you need the ERD accessible on a non-local environment (e.g. a shared staging server), enable Basic Auth via the config:

# config/initializers/vdb.rb

return unless Rails.env.development? || Rails.env.staging?

Vdb.configure do |c|
  c.username = ENV.fetch('VDB_USER')
  c.password = ENV.fetch('VDB_PASS')
end

Both values must be non-nil for auth to activate. The comparison uses ActiveSupport::SecurityUtils.secure_compare — a constant-time string comparison that prevents timing attacks.

Note HTTP Basic Auth credentials are sent on every request in a Base64-encoded header. Always serve the ERD over HTTPS when enabling auth on a shared server.

Environment variable setup

Set the credentials as environment variables — never commit them to source control:

# .env (never commit this file)
VDB_USER=admin
VDB_PASS=a-long-random-secret-string
# Or export directly in your shell
export VDB_USER=admin
export VDB_PASS=a-long-random-secret-string

Content Security Policy

vdb loads D3.js and Stimulus from jsDelivr CDN. If your app enforces a strict CSP, you need to permit these sources for script-src:

# config/initializers/content_security_policy.rb

Rails.application.configure do
  config.content_security_policy do |policy|
    policy.script_src :self,
                      'https://cdnjs.cloudflare.com'  # highlight.js (docs only)

    # vdb loads from jsDelivr:
    policy.script_src_attr :none
    policy.script_src_elem :self,
                            'https://cdn.jsdelivr.net'
  end
end
Tip Apply CDN exceptions only in Rails.env.development? blocks so production CSP stays strict.

What data is exposed

vdb reads only db/schema.rb (or the configured schema files). It never:

  • Queries the database
  • Reads table contents or row counts
  • Accesses Rails credentials, secrets, or environment variables
  • Makes outbound HTTP requests (schema is read from disk)

The schema file itself reveals:

  • Table and column names
  • Column types and null constraints
  • Index definitions (including unique indexes)
  • Foreign-key declarations

This is enough to understand your entire data model. Treat it accordingly.


Security checklist

EnvironmentRecommended setup
Local development No auth needed. Default config is sufficient.
Shared / remote development Enable Basic Auth via env vars. Use HTTPS.
Staging Use Basic Auth + environment guard. Or skip mounting entirely.
Production Do not mount. Wrap mount in if Rails.env.development?.
vdb v0.1.0 — MIT License — GitHub