feat: add pagination support to admin categories endpoint
- Add page/limit query parameters with Zod validation (max 50) - Update listCategories service to return paginated results - Response format includes pagination metadata (total, page, limit) - Matches existing pattern from questions/feedback endpoints Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
2dd5f18822
commit
6e65993f89
7
.claude/settings.json
Normal file
7
.claude/settings.json
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
{
|
||||||
|
"enabledPlugins": {
|
||||||
|
"typescript-lsp@claude-plugins-official": true,
|
||||||
|
"claude-md-management@claude-plugins-official": true,
|
||||||
|
"glm-plan-usage@zai-coding-plugins": false
|
||||||
|
}
|
||||||
|
}
|
||||||
15
.claude/settings.local.json
Normal file
15
.claude/settings.local.json
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
{
|
||||||
|
"permissions": {
|
||||||
|
"allow": [
|
||||||
|
"mcp__plugin_ecc_context7__resolve-library-id",
|
||||||
|
"mcp__plugin_ecc_context7__query-docs",
|
||||||
|
"Bash(bun install:*)",
|
||||||
|
"Bash(bun add:*)",
|
||||||
|
"Bash(bunx tsc:*)",
|
||||||
|
"Bash(git status:*)",
|
||||||
|
"Bash(git add:*)",
|
||||||
|
"Bash(git commit:*)",
|
||||||
|
"Bash(bun run:*)"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -18,10 +18,32 @@ const updateCategorySchema = z.object({
|
|||||||
status: z.enum(['active', 'inactive']).optional(),
|
status: z.enum(['active', 'inactive']).optional(),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const listCategoriesQuerySchema = z.object({
|
||||||
|
page: z.coerce.number().int().positive().optional().default(1),
|
||||||
|
limit: z.coerce.number().int().positive().max(50).optional().default(20),
|
||||||
|
});
|
||||||
|
|
||||||
export async function adminCategoriesRoutes(app: FastifyInstance): Promise<void> {
|
export async function adminCategoriesRoutes(app: FastifyInstance): Promise<void> {
|
||||||
app.get('/', async () => {
|
app.get('/', async (request) => {
|
||||||
const data = await categoryService.listCategories();
|
const parsed = listCategoriesQuerySchema.safeParse(request.query);
|
||||||
return { success: true, data, error: null };
|
if (!parsed.success) {
|
||||||
|
return {
|
||||||
|
success: false,
|
||||||
|
data: null,
|
||||||
|
error: {
|
||||||
|
code: 'VALIDATION_ERROR',
|
||||||
|
message: parsed.error.issues[0]?.message ?? 'Invalid query parameters'
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
const result = await categoryService.listCategories(parsed.data);
|
||||||
|
return {
|
||||||
|
success: true,
|
||||||
|
data: result.items,
|
||||||
|
pagination: result.pagination,
|
||||||
|
error: null
|
||||||
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
app.post('/', async (request) => {
|
app.post('/', async (request) => {
|
||||||
|
|||||||
@ -2,8 +2,33 @@ import { db } from '../../db/client.js';
|
|||||||
import { categories, questions } from '../../db/schema.js';
|
import { categories, questions } from '../../db/schema.js';
|
||||||
import { eq, and, sql } from 'drizzle-orm';
|
import { eq, and, sql } from 'drizzle-orm';
|
||||||
|
|
||||||
export async function listCategories() {
|
interface ListOptions {
|
||||||
return db.select().from(categories).orderBy(categories.sortOrder);
|
page?: number;
|
||||||
|
limit?: number;
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function listCategories({ page = 1, limit = 20 }: ListOptions = {}) {
|
||||||
|
const offset = (page - 1) * limit;
|
||||||
|
|
||||||
|
// Get total count
|
||||||
|
const [countResult] = await db
|
||||||
|
.select({ total: sql<number>`COUNT(*)` })
|
||||||
|
.from(categories);
|
||||||
|
|
||||||
|
const total = Number(countResult?.total ?? 0);
|
||||||
|
|
||||||
|
// Get paginated items
|
||||||
|
const items = await db
|
||||||
|
.select()
|
||||||
|
.from(categories)
|
||||||
|
.orderBy(categories.sortOrder)
|
||||||
|
.limit(limit)
|
||||||
|
.offset(offset);
|
||||||
|
|
||||||
|
return {
|
||||||
|
items,
|
||||||
|
pagination: { total, page, limit }
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function createCategory(data: { id: string; name: string; slug: string; parentId?: string; sortOrder?: number }) {
|
export async function createCategory(data: { id: string; name: string; slug: string; parentId?: string; sortOrder?: number }) {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user