🚀 COMPLETE BACKEND AGENT PROMPT FOR AUCTION AND PREBID SYSTEM¶
You are a senior backend engineer responsible for building a production-grade auction system with prebid functionality for a fintech SaaS platform called “Dichit” (chit fund domain).
Your goal is to design and implement the system step-by-step with correctness, scalability, and data integrity as top priorities.
Tech stack:¶
- Node.js (TypeScript)
- PostgreSQL
- Redis (for locks / realtime support)
- Fastify framework
- Prisma ORM
SYSTEM CONTEXT¶
We are building a chit fund auction system where:
- Each chit group has multiple installments (monthly cycles)
- Each installment has one auction
- Subscribers place bids (discount amount)
- Lowest bid wins
- Prebid allows users to submit bids before auction starts
⸻
IMPORTANT RULES¶
- Lowest bid wins (reverse auction)
- Prebids are confidential and only applied when auction starts
- Only one active prebid per user per auction
- All financial data must be consistent and auditable
- Race conditions MUST be handled
- Never trust frontend validation
- Auction and prebid should be optionally allowed for the first cycle as well
- Prebid is available only after the subscriber has completed payment for that specific cycle
- If a valid prebid or bid reaches the program minimum bid amount, there is no need for further auction bidding
- If multiple subscribers reach the minimum bid amount, the winner must be selected by lot
- An enrolled subscriber can win only once in a program; past winners must be blocked from future prebids and bids in the same program
⸻
UPDATED BUSINESS RULES¶
- First cycle support:
- Do not hard-block auction/prebid for cycle 1
-
Make this configurable / optional so first-cycle auction flow can run when required
-
Payment-gated prebid:
- A subscriber becomes eligible for prebid only after completing the payment for that exact cycle
-
Eligibility must be validated from backend payment / transaction records, not from frontend state
-
Minimum bid short-circuit:
- If a prebid reaches the minimum bid amount, live auction is not needed
- If exactly one eligible subscriber reaches the minimum bid amount, that subscriber should be treated as the winning candidate directly
-
If more than one eligible subscriber reaches the minimum bid amount, the flow must move to a lot-based winner selection
-
Minimum bid tie rule:
- Multiple subscribers are allowed to place the minimum bid amount
- This applies to both prebid and live bid flows
-
Minimum-bid ties must not be broken by timestamp; they must go to lot
-
One win per program:
- Once an enrolled subscriber has already won in a program, that subscriber must be ineligible for any future prebid or auction participation in that same program
- This validation must happen before allowing prebid creation, prebid update, or live bid placement
⸻
IMPLEMENTATION PLAN (FOLLOW STRICTLY IN ORDER)¶
⸻
STEP 1: DATABASE SCHEMA¶
Design Prisma models for:
- User
- Program
- SubscriberProgram
- ProgramCycle
- Auction
- Bid
- Prebid
- AuctionResult
- Transaction (ledger)
Requirements:
- Use Unique IDs
- Add proper relations
- Add indexes for performance
- Enforce constraints:
- One prebid per user per auction (partial unique index)
- Use Decimal for monetary values
After schema:
- Generate migrations
- Provide SQL for critical indexes
⸻
STEP 2: PREBID MODULE¶
Implement:
APIs:¶
- Create prebid
- Update prebid
- Cancel prebid
- Get user’s prebid
Rules:¶
- Only before auction start
- Only after subscriber payment completion for that specific cycle
- Validate bid range
- Enforce single active prebid
- Block subscribers who have already won once in the same program
- Allow prebid for cycle 1 when first-cycle auction is enabled
- Log history (optional but recommended)
Edge cases:¶
- Auction already started → reject
- Cycle payment not completed → reject
- Subscriber already won in this program → reject
- Duplicate prebid → update instead
- Minimum bid amount reached:
- one subscriber at minimum → no live auction required
- multiple subscribers at minimum → move to lot selection flow instead of live auction
⸻
STEP 3: AUCTION START LOGIC (CRITICAL)¶
Implement a service:
startAuction(auctionId)
Flow:¶
- Begin DB transaction
- Lock auction row (SELECT FOR UPDATE)
- Fetch all ACTIVE prebids
- Find lowest prebid
- Check whether the lowest prebid is equal to the minimum bid amount
- If minimum bid amount is reached:
- if only one subscriber is at minimum → skip live auction and mark direct winning flow
- if multiple subscribers are at minimum → skip live auction and move to lot-based selection
- If minimum bid amount is not reached:
- insert winning prebid into bids table
- update auction.currentLowestBid
- mark prebids as APPLIED / SUPERSEDED as needed
- set auction status = LIVE
- Commit transaction
If no prebids:
- auction starts without initial bid
⸻
STEP 4: LIVE BIDDING SYSTEM¶
Implement:
API:
- Place bid
Rules:
- Bid must be < currentLowestBid
- Reject invalid bids
- Must handle concurrency
- Block subscribers who have already won once in the same program
- If a bid reaches the minimum bid amount:
- stop further auction bidding
- if only one subscriber is at minimum → direct winning flow
- if multiple subscribers are at minimum → lot-based winner selection
Concurrency handling:
- Use transaction + row locking OR Redis lock
- Prevent two users from winning same position
Flow:
- Lock auction row
- Validate bid
- Check winner eligibility (no previous win in same program)
- Insert bid
- Update currentLowestBid
- If minimum bid amount is reached, close bidding and move to direct winner or lot flow
- Commit
⸻
STEP 5: AUCTION END¶
Implement:
endAuction(auctionId)
Flow:
- Lock auction
- Fetch lowest bid / minimum-bid candidates
- If minimum bid tie exists, resolve by lot
- Assign winner
- Store in auction_results
- Update auction status = COMPLETED
- Trigger transaction entry (payout)
⸻
STEP 6: LEDGER / TRANSACTIONS¶
Implement transaction table logic:
- installment payments
- payout to winner
- penalties (optional)
Ensure:
- consistency
- no duplicate payouts
⸻
STEP 7: REAL-TIME EVENTS (BASIC)¶
Design event system (no need full infra yet):
Events:
- AUCTION_STARTED
- NEW_BID
- OUTBID_NOTIFICATION
- AUCTION_ENDED
⸻
STEP 8: VALIDATION & SECURITY¶
- Input validation (Zod or similar)
- Auth middleware
- Role-based access:
- Admin vs Subscriber
⸻
STEP 9: TESTING¶
Write tests for:
- Prebid creation
- Auction start with prebids
- Concurrent bid placement
- Winner selection
- Edge cases:
- same bid values
- no prebids
- rapid bidding
- first cycle auction enabled vs disabled
- prebid blocked before cycle payment completion
- minimum bid reached by one subscriber
- minimum bid reached by multiple subscribers → lot required
- previous program winner blocked from prebid
- previous program winner blocked from live bid
⸻
STEP 10: PERFORMANCE & INDEXING¶
Ensure:
- indexes on bids (auction_id, bid_amount)
- indexes on prebids
- query optimization
⸻
OUTPUT FORMAT
For each step: 1. Explain approach briefly 2. Provide code (TypeScript + Prisma) 3. Provide SQL where needed 4. Mention edge cases handled
⸻
DO NOT:
- Skip concurrency handling
- Assume single user environment
- Use floating point for money
- Over-engineer with microservices initially
⸻
SUCCESS CRITERIA
The system should:
- Handle multiple concurrent bidders safely
- Correctly apply prebids
- Always select correct winner
- Maintain financial integrity
- Be extensible for real-time updates later
Proceed step-by-step. Do NOT jump steps.
STEP X: ADMIN CONTROL & MODERATION¶
Implement full admin control over auctions.
Requirements:
- Auction lifecycle control:
- Admin can start, pause, resume, end auctions
-
Enforce valid state transitions
-
Winner approval:
- After auction ends, winner must be approved
- Allow override with reason
-
Store audit logs
-
Prebid moderation:
- Admin can view all prebids
-
Reject invalid/suspicious prebids
-
Bid moderation:
-
Admin can reject bids (fraud/manual correction)
-
Audit logging:
- Every admin action must be logged
-
Store metadata in JSONB
-
Authorization:
-
Only ADMIN role can access these APIs
-
Safety:
- Prevent illegal actions (e.g., ending already completed auction)
Output:
- APIs
- service layer
- schema updates
- validations