40 lines
1.2 KiB
TypeScript
40 lines
1.2 KiB
TypeScript
import { Router } from 'express';
|
|
import { and, eq, gte, inArray, sql, SQL } from 'drizzle-orm';
|
|
import { db } from '../db/client';
|
|
import { rabbits } from '../db/schema';
|
|
|
|
const router = Router();
|
|
|
|
const KIT_AGE_WINDOW_DAYS = 56;
|
|
|
|
function count(...conditions: SQL[]) {
|
|
return db
|
|
.select({ value: sql<number>`count(*)` })
|
|
.from(rabbits)
|
|
.where(conditions.length ? and(...conditions) : undefined)
|
|
.get()!.value;
|
|
}
|
|
|
|
router.get('/', (req, res) => {
|
|
const kitCutoff = new Date(Date.now() - KIT_AGE_WINDOW_DAYS * 24 * 60 * 60 * 1000)
|
|
.toISOString()
|
|
.slice(0, 10);
|
|
|
|
res.json({
|
|
herd: count(eq(rabbits.status, 'active')),
|
|
bucks: count(eq(rabbits.status, 'active'), eq(rabbits.sex, 'buck')),
|
|
does: count(eq(rabbits.status, 'active'), eq(rabbits.sex, 'doe')),
|
|
kits: count(eq(rabbits.status, 'active'), gte(rabbits.dob, kitCutoff)),
|
|
for_sale: count(eq(rabbits.status, 'for_sale')),
|
|
on_hold: count(eq(rabbits.status, 'on_hold')),
|
|
sold: count(eq(rabbits.status, 'sold')),
|
|
archived: db
|
|
.select({ value: sql<number>`count(*)` })
|
|
.from(rabbits)
|
|
.where(inArray(rabbits.status, ['other', 'deceased']))
|
|
.get()!.value,
|
|
});
|
|
});
|
|
|
|
export default router;
|