diff --git a/frontend/app/[locale]/layout.tsx b/frontend/app/[locale]/layout.tsx index e7a496fd..ddf43e1f 100644 --- a/frontend/app/[locale]/layout.tsx +++ b/frontend/app/[locale]/layout.tsx @@ -37,6 +37,7 @@ export default async function LocaleLayout({ title: string; }> = []; + const enableAdmin = ( process.env.ENABLE_ADMIN_API ?? diff --git a/frontend/db/index.ts b/frontend/db/index.ts index 8648dd00..cb9b681e 100644 --- a/frontend/db/index.ts +++ b/frontend/db/index.ts @@ -12,14 +12,29 @@ dotenv.config(); type AppDatabase = PgDatabase; const APP_ENV = process.env.APP_ENV?.trim().toLowerCase(); + +if (!APP_ENV) { + throw new Error( + '[db] APP_ENV is required. Set APP_ENV=local in .env for development, or APP_ENV=develop/production for deployment' + ); +} + const IS_LOCAL_ENV = APP_ENV === 'local'; + +if (process.env.NODE_ENV !== 'test') { + console.log('[db] runtime env check', { + has_DATABASE_URL: Boolean(process.env.DATABASE_URL?.trim()), + has_DATABASE_URL_LOCAL: Boolean(process.env.DATABASE_URL_LOCAL?.trim()), + }); +} + const STRICT_LOCAL_DB_GUARD = process.env.SHOP_STRICT_LOCAL_DB === '1'; const REQUIRED_LOCAL_DB_URL = process.env.SHOP_REQUIRED_DATABASE_URL_LOCAL; if (STRICT_LOCAL_DB_GUARD) { if (!IS_LOCAL_ENV) { throw new Error( - `[db] SHOP_STRICT_LOCAL_DB=1 requires APP_ENV=local (got "${APP_ENV ?? 'undefined'}")` + `[db] SHOP_STRICT_LOCAL_DB=1 requires APP_ENV=local (got "${APP_ENV}")` ); } @@ -68,7 +83,7 @@ if (IS_LOCAL_ENV) { if (!url) { throw new Error( - `[db] APP_ENV=${APP_ENV ?? 'undefined'} requires DATABASE_URL to be set` + `[db] APP_ENV=${APP_ENV} requires DATABASE_URL to be set` ); } diff --git a/frontend/db/queries/categories/admin-categories.ts b/frontend/db/queries/categories/admin-categories.ts index 97a59934..2e92e358 100644 --- a/frontend/db/queries/categories/admin-categories.ts +++ b/frontend/db/queries/categories/admin-categories.ts @@ -20,13 +20,17 @@ export async function getAdminCategoryList(): Promise { title: categoryTranslations.title, }) .from(categories) - .innerJoin( + .leftJoin( categoryTranslations, sql`${categoryTranslations.categoryId} = ${categories.id} AND ${categoryTranslations.locale} = ${ADMIN_LOCALE}` ) .orderBy(categories.displayOrder); - return rows; + return rows.map(row => ({ + id: row.id, + slug: row.slug, + title: row.title ?? row.slug, + })); } export async function getMaxQuizDisplayOrder(