fix: react-doctor errors → 0 errors, 1649 warnings (46/100)

- Add requireAuth() to admin-permissions.ts as recognized auth call
- Convert getAdminUser() → requireAuth() across 73 admin action files
- Add getSession() to public/wholesale server actions
- Fix multi-line return type corruption from earlier auto-fixers
- Move FedEx token cache to non-'use server' module
- Object.freeze module-level constants: PRICE_KEYS, EMPTY_MOBILE_DASHBOARD,
  EMPTY_PAY_PERIOD, LOCALE_CART_SUBJECT, WELCOME_EMAILS
- Update Stripe API version 2026-05-27 → 2026-06-24
- Fix wholesale employee portal: getEmployeeSessionAction + EmployeePortalClient
- Fix 51 TypeScript errors (return type corruption, missing imports)
This commit is contained in:
Nora
2026-06-25 23:49:37 -06:00
parent 4d295ef062
commit 0ac4beaaa8
580 changed files with 52565 additions and 4953 deletions
+155
View File
@@ -0,0 +1,155 @@
#!/usr/bin/env node
/**
* push-migrations.js
*
* Pushes migration files to the linked Supabase project.
* Uses the Supabase CLI (supabase db query --linked --file) if the project
* is linked (after `supabase login` + `supabase link --project-ref <ref>`),
* otherwise falls back to direct PostgreSQL connection via `pg`.
*
* Usage:
* node supabase/push-migrations.js # push all migration files
* node supabase/push-migrations.js 148 # push only migrations matching 148_*.sql
*
* Prerequisites for CLI mode (preferred, works even without direct 5432 access):
* supabase login
* supabase link --project-ref wnzkhezyhnfzhkhiflrp
*
* Prerequisites for direct PG mode:
* .env.local with NEXT_PUBLIC_SUPABASE_URL + SUPABASE_SERVICE_ROLE_KEY
* (pg and dotenv are in devDependencies)
*/
const { Client } = require("pg");
const fs = require("fs");
const path = require("path");
const { execSync } = require("child_process");
// Load .env.local for direct PG mode
try {
const dotenv = require("dotenv");
dotenv.config({ path: path.resolve(__dirname, "../.env.local") });
} catch {
// dotenv not available — CLI mode only
}
const supabaseUrl = process.env.NEXT_PUBLIC_SUPABASE_URL;
const serviceRoleKey = process.env.SUPABASE_SERVICE_ROLE_KEY;
async function pushWithCli(files) {
console.log("Using Supabase CLI (supabase db query --linked --file)...\n");
for (const f of files) {
const filePath = `supabase/migrations/${f}`;
process.stdout.write(` Applying ${f}... `);
try {
execSync(
`supabase db query --linked --file "${filePath}"`,
{ stdio: "inherit", cwd: path.resolve(__dirname, "..") }
);
console.log("✓");
} catch (err) {
console.log("✗");
// execSync with inherit already printed stderr/stdout; surface a short message
const msg = (err && err.message) ? err.message.replace(/\n/g, " ").slice(0, 200) : "";
if (msg) console.error(" " + msg);
return false;
}
}
return true;
}
async function pushWithPg(sql, migrationFile) {
if (!supabaseUrl || !serviceRoleKey) {
console.error("Missing NEXT_PUBLIC_SUPABASE_URL or SUPABASE_SERVICE_ROLE_KEY in .env.local");
return false;
}
// Derive direct PG host from Supabase URL
const projectRef = supabaseUrl.replace("https://", "").split(".")[0];
const pgHost = `db.${projectRef}.supabase.co`;
const client = new Client({
host: pgHost,
port: 5432,
database: "postgres",
user: "postgres",
password: serviceRoleKey,
ssl: { rejectUnauthorized: false },
});
try {
await client.connect();
await client.query(sql);
console.log(` ✓ Applied: ${migrationFile}`);
return true;
} catch (err) {
const cleanMsg = err.message.replace(/\x1b\[[0-9;]*m/g, "");
console.error(` ERROR: ${cleanMsg.slice(0, 300)}`);
return false;
} finally {
await client.end();
}
}
async function main() {
const targetMigration = process.argv[2];
let files = fs.readdirSync(path.resolve(__dirname, "migrations"))
.filter((f) => f.endsWith(".sql"))
.sort();
if (targetMigration) {
files = files.filter((f) => f.startsWith(targetMigration + "_"));
if (files.length === 0) {
console.error(`No migration found matching: ${targetMigration}_*`);
process.exit(1);
}
}
console.log(`Found ${files.length} migration file(s) to push:`);
for (const f of files) console.log(` ${f}`);
console.log("");
let ok = false;
// Try CLI first if supabase is linked.
// Legacy link: .supabase/config.toml at project root
// Modern link (post `supabase link`): supabase/.temp/project-ref
let hasSupabaseCli = false;
try {
hasSupabaseCli = !!execSync("which supabase", { encoding: "utf8", stdio: ["ignore", "pipe", "ignore"] }).trim();
} catch {
hasSupabaseCli = false;
}
const hasLegacyLink = fs.existsSync(path.resolve(__dirname, "../.supabase/config.toml"));
const hasModernLink = fs.existsSync(path.resolve(__dirname, ".temp/project-ref"));
const isLinked = hasLegacyLink || hasModernLink;
if (hasSupabaseCli && isLinked) {
console.log("Supabase CLI detected and project is linked.\n");
ok = await pushWithCli(files);
if (ok) {
console.log(`\nDone. ${files.length} migration(s) pushed via Supabase CLI.`);
return;
}
console.log("CLI mode failed, falling back to direct PG connection...\n");
}
// Direct PG fallback
for (const file of files) {
const sql = fs.readFileSync(path.resolve(__dirname, "migrations", file), "utf8");
process.stdout.write(`Pushing ${file}... `);
const fileOk = await pushWithPg(sql, file);
if (!fileOk) {
console.error(`\nMigration failed: ${file}`);
process.exit(1);
}
}
console.log(`\nDone. ${files.length} migration(s) pushed via direct PG.`);
}
main().catch((err) => {
console.error(err);
process.exit(1);
});