feat(11-02): add findByNumber and getNextNumber to PhaseRepository
- Add findByNumber method to lookup phase by initiative and number - Add getNextNumber method to get next available phase number - Implement both methods in DrizzlePhaseRepository adapter - Use drizzle-orm max() and and() for query construction
This commit is contained in:
@@ -4,7 +4,7 @@
|
||||
* Implements PhaseRepository interface using Drizzle ORM.
|
||||
*/
|
||||
|
||||
import { eq, asc } from 'drizzle-orm';
|
||||
import { eq, asc, and, max } from 'drizzle-orm';
|
||||
import { nanoid } from 'nanoid';
|
||||
import type { DrizzleDatabase } from '../../index.js';
|
||||
import { phases, type Phase } from '../../schema.js';
|
||||
@@ -58,6 +58,26 @@ export class DrizzlePhaseRepository implements PhaseRepository {
|
||||
.orderBy(asc(phases.number));
|
||||
}
|
||||
|
||||
async findByNumber(initiativeId: string, number: number): Promise<Phase | null> {
|
||||
const result = await this.db
|
||||
.select()
|
||||
.from(phases)
|
||||
.where(and(eq(phases.initiativeId, initiativeId), eq(phases.number, number)))
|
||||
.limit(1);
|
||||
|
||||
return result[0] ?? null;
|
||||
}
|
||||
|
||||
async getNextNumber(initiativeId: string): Promise<number> {
|
||||
const result = await this.db
|
||||
.select({ maxNumber: max(phases.number) })
|
||||
.from(phases)
|
||||
.where(eq(phases.initiativeId, initiativeId));
|
||||
|
||||
const maxNumber = result[0]?.maxNumber ?? 0;
|
||||
return maxNumber + 1;
|
||||
}
|
||||
|
||||
async update(id: string, data: UpdatePhaseData): Promise<Phase> {
|
||||
const existing = await this.findById(id);
|
||||
if (!existing) {
|
||||
|
||||
@@ -46,6 +46,18 @@ export interface PhaseRepository {
|
||||
*/
|
||||
findByInitiativeId(initiativeId: string): Promise<Phase[]>;
|
||||
|
||||
/**
|
||||
* Find a phase by initiative and number.
|
||||
* Returns null if not found.
|
||||
*/
|
||||
findByNumber(initiativeId: string, number: number): Promise<Phase | null>;
|
||||
|
||||
/**
|
||||
* Get the next available phase number for an initiative.
|
||||
* Returns MAX(number) + 1, or 1 if no phases exist.
|
||||
*/
|
||||
getNextNumber(initiativeId: string): Promise<number>;
|
||||
|
||||
/**
|
||||
* Update a phase.
|
||||
* Throws if phase not found.
|
||||
|
||||
Reference in New Issue
Block a user