feat(policies): full CRUD + child editors + insurance lookups (plan phase 3)
Policy header, all five child collections, and the insurance reference catalogs become create/edit/delete-able on the RBAC foundation. API: - Policy gains archivedAt (soft-delete); list/browser default to archivedAt=null with ?includeArchived opt-in. - PoliciesService: header create/update/archive/restore (customer FK validated for a clean 404); add/update/remove for installments, vehicles, drivers, beneficiaries, claims — each scoped to its policy so one policy's id can't touch another's rows; lookups CRUD for providers, policy types, adjusters. - PoliciesController write routes: header create/update need STAFF+ (policy:create/update), archive/restore need MANAGER+ (policy:delete), every child route needs policy:update. New LookupsController at /lookups (read open; mutate needs lookup:manage / MANAGER+). Mutations audited. - DTOs (policy header, children, lookups); dates coerced; shared coerce.ts. Web: - Generic ChildCollection editor (config-driven add/edit/remove table), reused by both the policy detail child editors and the catalogs screen. - PolicyForm (header) with type/provider selects and a debounced CustomerPicker; /polizas/nuevo (accepts ?customerId prefill) and /polizas/[id]/editar. Policy detail: gated action bar (Editar/Archivar) + "Administrar detalles" child editors for all five collections. - /catalogos admin screen (aseguradoras/tipos/ajustadores), nav-gated on lookup:manage. "Nueva póliza" buttons on the list and on the customer detail (prefilled). api.ts + types for all of the above. Verified against dev: policy create (dates coerced, archivedAt null), installment/vehicle add, VIEWER child-add 403, cross-policy child guard 404, lookups CRUD with VIEWER 403 / MANAGER 201, archive drops from the default list and includeArchived surfaces it. Both apps compile clean. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,86 @@
|
||||
import {
|
||||
Body,
|
||||
Controller,
|
||||
Delete,
|
||||
Get,
|
||||
Param,
|
||||
Patch,
|
||||
Post,
|
||||
UseGuards,
|
||||
} from "@nestjs/common";
|
||||
import { AuthenticatedGuard } from "../auth/authenticated.guard";
|
||||
import { AbilityGuard } from "../auth/ability.guard";
|
||||
import { RequireAbility } from "../auth/require-ability.decorator";
|
||||
import { PoliciesService } from "./policies.service";
|
||||
import {
|
||||
AdjusterDto,
|
||||
PolicyTypeDto,
|
||||
ProviderDto,
|
||||
UpdateAdjusterDto,
|
||||
UpdatePolicyTypeDto,
|
||||
UpdateProviderDto,
|
||||
} from "./lookup.dto";
|
||||
|
||||
/**
|
||||
* Insurance reference data: providers, policy types, adjusters. Reading is open
|
||||
* to any authenticated user (the policy form needs the options); mutating needs
|
||||
* "lookup:manage" (MANAGER+).
|
||||
*/
|
||||
@UseGuards(AuthenticatedGuard, AbilityGuard)
|
||||
@Controller("lookups")
|
||||
export class LookupsController {
|
||||
constructor(private readonly policies: PoliciesService) {}
|
||||
|
||||
@Get()
|
||||
list() {
|
||||
return this.policies.listLookups();
|
||||
}
|
||||
|
||||
@Post("providers")
|
||||
@RequireAbility("lookup:manage")
|
||||
createProvider(@Body() dto: ProviderDto) {
|
||||
return this.policies.createProvider(dto);
|
||||
}
|
||||
@Patch("providers/:id")
|
||||
@RequireAbility("lookup:manage")
|
||||
updateProvider(@Param("id") id: string, @Body() dto: UpdateProviderDto) {
|
||||
return this.policies.updateProvider(id, dto);
|
||||
}
|
||||
@Delete("providers/:id")
|
||||
@RequireAbility("lookup:manage")
|
||||
removeProvider(@Param("id") id: string) {
|
||||
return this.policies.removeProvider(id);
|
||||
}
|
||||
|
||||
@Post("policy-types")
|
||||
@RequireAbility("lookup:manage")
|
||||
createType(@Body() dto: PolicyTypeDto) {
|
||||
return this.policies.createPolicyType(dto);
|
||||
}
|
||||
@Patch("policy-types/:id")
|
||||
@RequireAbility("lookup:manage")
|
||||
updateType(@Param("id") id: string, @Body() dto: UpdatePolicyTypeDto) {
|
||||
return this.policies.updatePolicyType(id, dto);
|
||||
}
|
||||
@Delete("policy-types/:id")
|
||||
@RequireAbility("lookup:manage")
|
||||
removeType(@Param("id") id: string) {
|
||||
return this.policies.removePolicyType(id);
|
||||
}
|
||||
|
||||
@Post("adjusters")
|
||||
@RequireAbility("lookup:manage")
|
||||
createAdjuster(@Body() dto: AdjusterDto) {
|
||||
return this.policies.createAdjuster(dto);
|
||||
}
|
||||
@Patch("adjusters/:id")
|
||||
@RequireAbility("lookup:manage")
|
||||
updateAdjuster(@Param("id") id: string, @Body() dto: UpdateAdjusterDto) {
|
||||
return this.policies.updateAdjuster(id, dto);
|
||||
}
|
||||
@Delete("adjusters/:id")
|
||||
@RequireAbility("lookup:manage")
|
||||
removeAdjuster(@Param("id") id: string) {
|
||||
return this.policies.removeAdjuster(id);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user