Merge origin/dev into fix/gro-1749-uat-seed-sync
Resolve conflict in apps/api/src/routes/admin/seed.ts: - Keep UAT_CLIENT with address (not stripped by GRO-1743) - Keep weightKg in UAT_PETS (from both branches) - Use origin/dev coatType as const (typed properly) - Use existingPet naming (from origin/dev) Co-Authored-By: Paperclip <noreply@paperclip.ing>
This commit is contained in:
@@ -96,6 +96,7 @@ jobs:
|
||||
file: Dockerfile
|
||||
target: runner
|
||||
push: true
|
||||
provenance: false
|
||||
tags: |
|
||||
git.farh.net/groombook/api:${{ steps.version.outputs.tag }}
|
||||
${{ github.ref == 'refs/heads/main' && 'git.farh.net/groombook/api:latest' || '' }}
|
||||
@@ -110,6 +111,7 @@ jobs:
|
||||
file: Dockerfile
|
||||
target: migrate
|
||||
push: true
|
||||
provenance: false
|
||||
tags: |
|
||||
git.farh.net/groombook/migrate:${{ steps.version.outputs.tag }}
|
||||
${{ github.ref == 'refs/heads/main' && 'git.farh.net/groombook/migrate:latest' || '' }}
|
||||
@@ -124,6 +126,7 @@ jobs:
|
||||
file: Dockerfile
|
||||
target: seed
|
||||
push: true
|
||||
provenance: false
|
||||
tags: |
|
||||
git.farh.net/groombook/seed:${{ steps.version.outputs.tag }}
|
||||
${{ github.ref == 'refs/heads/main' && 'git.farh.net/groombook/seed:latest' || '' }}
|
||||
@@ -138,6 +141,7 @@ jobs:
|
||||
file: Dockerfile
|
||||
target: reset
|
||||
push: true
|
||||
provenance: false
|
||||
tags: |
|
||||
git.farh.net/groombook/reset:${{ steps.version.outputs.tag }}
|
||||
${{ github.ref == 'refs/heads/main' && 'git.farh.net/groombook/reset:latest' || '' }}
|
||||
|
||||
@@ -45,8 +45,8 @@ const UAT_CLIENT = {
|
||||
};
|
||||
|
||||
const UAT_PETS = [
|
||||
{ name: "Bella", species: "Dog", breed: "Poodle", coatType: "curly", weightKg: "20.00" },
|
||||
{ name: "Max", species: "Dog", breed: "Labrador Retriever", coatType: "short", weightKg: "30.00" },
|
||||
{ name: "Bella", species: "Dog", breed: "Poodle", coatType: "curly" as const, weightKg: "20.00" },
|
||||
{ name: "Max", species: "Dog", breed: "Labrador Retriever", coatType: "short" as const, weightKg: "30.00" },
|
||||
];
|
||||
|
||||
const DEMO_SERVICES = [
|
||||
@@ -164,11 +164,11 @@ adminSeedRouter.post("/", async (c) => {
|
||||
.where(eq(pets.clientId, uatClientId));
|
||||
|
||||
for (const uatPet of UAT_PETS) {
|
||||
const existing = existingUatPets.find(
|
||||
const existingPet = existingUatPets.find(
|
||||
(p) => p.name === uatPet.name && p.species === uatPet.species
|
||||
);
|
||||
if (existing) {
|
||||
results.push(`Pet '${uatPet.name}' already exists for UAT Customer (id: ${existing.id})`);
|
||||
if (existingPet) {
|
||||
results.push(`Pet '${uatPet.name}' already exists for UAT Customer (id: ${existingPet.id})`);
|
||||
} else {
|
||||
const [created] = await db
|
||||
.insert(pets)
|
||||
@@ -177,7 +177,7 @@ adminSeedRouter.post("/", async (c) => {
|
||||
name: uatPet.name,
|
||||
species: uatPet.species,
|
||||
breed: uatPet.breed,
|
||||
coatType: uatPet.coatType as any,
|
||||
coatType: uatPet.coatType,
|
||||
weightKg: uatPet.weightKg,
|
||||
dateOfBirth: new Date("2019-01-01T00:00:00Z"),
|
||||
})
|
||||
@@ -194,4 +194,4 @@ adminSeedRouter.post("/", async (c) => {
|
||||
staffOidcSub: KNOWN_STAFF.oidcSub,
|
||||
},
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -12,7 +12,7 @@ export function getDb() {
|
||||
if (_db) return _db;
|
||||
const url = process.env.DATABASE_URL;
|
||||
if (!url) throw new Error("DATABASE_URL is not set");
|
||||
const client = postgres(url, { max: 10 });
|
||||
const client = postgres(url, { max: 10, connect_timeout: 5 });
|
||||
_db = drizzle(client, { schema });
|
||||
return _db;
|
||||
}
|
||||
|
||||
+9
-4
@@ -59,6 +59,9 @@ app.use(
|
||||
);
|
||||
|
||||
// Health check — no auth required, registered on app at full path before auth middleware
|
||||
// /health: used by Dockerfile HEALTHCHECK and K8s readinessProbe/livenessProbe (port 3000 direct)
|
||||
app.get("/health", (c) => c.json({ status: "ok" }));
|
||||
// /api/health: used by Gateway HTTPRoute (/api/* → API pod)
|
||||
app.get("/api/health", (c) => c.json({ status: "ok" }));
|
||||
|
||||
// Public booking routes — no auth required, must be registered before auth middleware
|
||||
@@ -282,14 +285,16 @@ startReminderScheduler();
|
||||
|
||||
function shutdown() {
|
||||
console.log("Shutting down gracefully...");
|
||||
// SIGTERM/SIGINT → server.close() → callback → process.exit(0)
|
||||
// If graceful close takes >8s, force-exit to avoid being killed undrained
|
||||
setTimeout(() => {
|
||||
console.error("Graceful close timeout — forcing exit");
|
||||
process.exit(1);
|
||||
}, 8_000);
|
||||
server.close(() => {
|
||||
console.log("HTTP server closed");
|
||||
process.exit(0);
|
||||
});
|
||||
setTimeout(() => {
|
||||
console.error("Forced shutdown after timeout");
|
||||
process.exit(1);
|
||||
}, 10_000);
|
||||
}
|
||||
|
||||
process.on("SIGTERM", shutdown);
|
||||
|
||||
+3
-1
@@ -186,7 +186,9 @@ export async function initAuth(): Promise<void> {
|
||||
const discoveryUrlStr = `${providerConfig.issuerUrl}/.well-known/openid-configuration`;
|
||||
let oidcConfig: Record<string, string> = {};
|
||||
try {
|
||||
const discoveryRes = await fetch(discoveryUrlStr);
|
||||
const discoveryRes = await fetch(discoveryUrlStr, {
|
||||
signal: AbortSignal.timeout(5000),
|
||||
});
|
||||
if (discoveryRes.ok) {
|
||||
const discovery = await discoveryRes.json() as {
|
||||
authorization_endpoint?: string;
|
||||
|
||||
Reference in New Issue
Block a user