Configuration
This guide explains how environment variables and app/Config files work together in JCC Express MVC, and where to change behavior safely.
How configuration fits together
.env(project root) holds secrets and environment-specific values. It is not committed to Git in real projects;.env.exampledocuments every key for new setups.
- The framework loads
.envwith dotenv when theconfighelper fromjcc-express-mvcis first used (jcc-express-mvc/lib/Config/Config.ts). Values end up onprocess.env.
app/Config/index.tsbuilds aconfigobject (engine, CORS, queue, rate limiting, database, OAuth services, etc.) and passes it into the app inbootstrap/app.tsvia.withConfig(config).
- At runtime you can read env keys with:
- config.get("KEY", "default") after import { config } from "jcc-express-mvc", or - the global env("KEY", "default") once the app has bootstrapped (same underlying store).
Change .env when a value varies by machine (database password, API keys). Change app/Config/*.ts when you want code-level defaults or structured objects (CORS rules, session cookie options, queue connections) that are shared across environments.
Important environment variables
Your .env.example is the authoritative list of keys for your repo. Below are the groups you will touch most often.
Application and HTTP
APP_NAME,APP_URL,APP_ENV,APP_DEBUG— App identity and debug behavior.PORT— HTTP port the server listens on (used when the application starts; default comes from env if set).
Use a full URL for APP_URL in production (for example https://example.com). OAuth redirect URLs and similar features build on this.
Database and ORM
DB_ORM—jcc(Knex / JCC Eloquent),sequelize, ormongoose.DB_CONNECTION— Driver for Knex (for examplemysql2,postgres,sqlite,better-sqlite3).DB_HOST,DB_PORT,DB_DATABASE,DB_USERNAME,DB_PASSWORD— Connection details.
For SQLite / better-sqlite3, the framework typically uses a database file under the project root (see framework database setup).
FILE_EXT—tsorjsfor generated files (make:model,make:controller, etc.).
Security
JWT_SECRET— Signing key for JWTs. Generate a strong value withbun artisanNode key:generate(see Installation.md). Do not ship placeholder secrets to production.- Session-related secrets in
.env(if your app uses them) should be long random strings; session cookie behavior is also configured inapp/Config/session.ts.
Keys such as MAIL_DRIVER, MAIL_HOST, MAIL_PORT, MAIL_USERNAME, MAIL_PASSWORD, MAIL_FROM_ADDRESS, and provider-specific values (for example MAIL_API_KEY for Resend) are read by the mail layer when you send email. See .env.example for the exact set.
OAuth (Socialite-style)
OAuth clients are wired through app/Config/service.ts, which reads env vars such as:
GOOGLE_CLIENT_ID/GOOGLE_CLIENT_SECRET(optionalGOOGLE_REDIRECT_URI)- Same pattern for GitHub, Facebook, GitLab (plus
GITLAB_URLfor self-hosted), Twitter, Slack
If *_REDIRECT_URI is omitted, defaults follow {APP_URL}/auth/{provider}/callback.
Queues and Redis
app/Config/queue.ts uses:
QUEUE_CONNECTION— For examplememory,database, orredis(defaults tomemoryif unset).REDIS_HOST,REDIS_PORT,REDIS_USERNAME,REDIS_PASSWORD,REDIS_DB— When using the Redis queue connection.
Files under app/Config/
index.ts— Exports the mergedconfigobject passed toApplication.configuration().withConfig(config)inbootstrap/app.ts.database.ts— MapsDB_ORMand related env vars into Sequelize- and Mongoose-shaped options (Knex / JCC Eloquent also readsDB_*viaconfig.getinside the framework).service.ts— Laravelconfig/services.php–style OAuth map for Socialite providers (see above).queue.ts— Queue driver, memory/database/redis connection shapes; usesprocess.envforQUEUE_CONNECTIONand Redis.session.ts— Session driver (file), lifetime, cookie name and flags, storage understorage/sessions.cors.ts— CORS origin, methods, and status codes.rate-limit.ts— Rate limit window and max requests.engine.ts— View engine (for example JCC Blade), views path (resources/views), file extension.auth.ts— Optional or app-specific auth config (may be commented out until you enable it).
app/Config/app.ts exports a providers array. Some framework helpers (for example getProviders() in jcc-express-mvc) read this file. The running application registers providers from bootstrap/providers.ts via bootstrap/app.ts—keep both lists aligned if your project uses both, or treat bootstrap/providers.ts as the source of truth for what actually boots.
After you change configuration
.envonly — Restartbun run dev(ornpm run dev) so the process reloads environment variables.- TypeScript under
app/Config/— Restart the dev server; if you use a watch build, saving the file may be enough.
What to read next
- Installation.md —
.env,key:generate, migrations,watch+dev. - Introduction.md — What the framework is and requirements.
- Directory-structure.md —
app/,route/,bootstrap/,storage/,jcc-express-mvc/. - Frontend.md — Vite
input, Blade root view, and Inertia. - Deployment.md — Production
.envand release steps.
For mail, queues, Socialite, and Eloquent in depth, see docs/docs-for-dev.md (or docs-for-dev.md at the repository root).
