feat(admin): add approve_loan endpoint for admin loan approval#29
Conversation
- Add POST /admin/approve-loan endpoint with JWT auth and admin RBAC - Add approveLoan controller function in indexerController.ts - Add approveLoanBodySchema with zod validation for loanId - Add Swagger documentation for the new endpoint - Add 5 tests covering: successful build, non-admin rejection, missing loanId, invalid loanId, and missing auth - All 220 tests pass
ogazboiz
left a comment
There was a problem hiding this comment.
this is exactly what the issue asked for. the route is gated correctly (requireJwtAuth + requireRoles("admin") + the strict rate limiter + audit log + zod body validation), the loanId schema is a positive int, and it builds the right approve_loan soroban call via sorobanService. esm mocks are ordered before the dynamic app import and the connection mock is complete. 5/5 tests pass, full suite green, tsc clean.
one small non-blocking heads up: the handler lives in indexerController.ts rather than loanController.ts so it reads slightly off-theme, and there's a redundant 401 check on adminPublicKey that requireJwtAuth already guarantees. neither is worth holding the merge, just something to tidy if you touch it again. merging.
if you want to keep contributing, join us on Telegram: https://t.me/+DOylgFv1jyJlNzM0
Closes #11
Type of Change
Summary
The
sorobanService.buildApproveLoanTxfunction was implemented but never exposed through an API endpoint, meaning there was no way for an admin to approve a requested loan. This PR adds a new admin-authenticated endpoint that builds the unsignedapprove_loantransaction for the admin to sign with their wallet.Motivation / Context
Fixes #11
Every other contract wrapper (request/repay/deposit/withdraw) is exposed via an API endpoint, but approve_loan was missing. Without this endpoint, admins cannot approve loans through the API, creating a gap in the loan lifecycle.
Detailed Changes
POST /admin/approve-loanendpoint with JWT authentication and admin RBAC enforcementapproveLoancontroller function inindexerController.tsthat callssorobanService.buildApproveLoanTxapproveLoanBodySchemawith zod validation forloanId(positive integer required)/api/loans/submitendpointauditLogmiddlewarestrictRateLimiterCurrent Behavior vs. New Behavior
Before: No API path exists for an admin to approve a requested loan.
After: Admin can call
POST /admin/approve-loanwith{ loanId: number }to get an unsigned transaction XDR, sign it with their wallet, and submit via the generic submit endpoint.Testing
Breaking Changes
No.
Checklist
Self-Review
Testing
Documentation
Reviewer Notes
requireRoles("admin")middlewarebuildApproveLoanTxservice method already existed — this PR only exposes it via an API endpoint