Inspiration
When floods hit northern Bangladesh, people around me give money to relief efforts through friends, pages, and WhatsApp groups. Almost nobody sees what happened to that money afterwards. Not because people are dishonest, but because there is no easy way to show proof, and no easy way to ask for it.
I wanted to build the small missing piece: a fund where money moves only after someone shows a receipt and a photo that a donor can look at too. I called it Sakkhi (সাক্ষী), which means "witness" in Bangla.
What it does
Sakkhi is a proof-based relief fund.
- A coordinator creates a campaign (for example, flood relief in Kurigram) split into milestones, each with an amount and a checklist of required proof.
- Donors give to a campaign. The money is tracked in a per-campaign ledger, not sent straight to anyone.
- A local volunteer completes a milestone and uploads photos and a receipt through a simple phone-friendly page.
- An AI verifier reads the proof. It checks the receipt total against the milestone, whether the photos match the checklist, and whether an image is a duplicate, then writes a plain-language explanation. Code-level rules run before and after the model, so the model alone can never approve a payout. Low-confidence cases go to a human coordinator.
- Only approved milestones release money to the volunteer.
- Donors see a public timeline: what was bought, the receipt, why it was verified, and where the money went.
How we built it
- Next.js 14, TypeScript, Tailwind for the app, with Prisma + SQLite so anyone can run it with no database setup.
- PayPal REST APIs for the money flow: Orders (create and capture) for donations, Webhooks with signature verification, and Payouts for releasing funds to volunteers.
- AI verification behind a provider interface (Gemini, Anthropic, or a deterministic mock), with structured JSON output validated by Zod, and deterministic checks around it: receipt amount tolerance, duplicate image hashing, EXIF date checks, and a confidence threshold.
- A ledger with idempotency keys, so a retried request can never double-spend a milestone.
- A humanist design system: Literata for headings, Source Sans 3 for body text, Hind Siliguri for Bangla, on a warm paper-colored palette. I wanted a fund that feels like a person writing to you, not a banking dashboard.
- Vitest tests for the ledger, upload validation, verifier rules, payouts, and security edge cases.
I built it with an AI coding IDE, writing the architecture, data model, and security docs first, then building feature by feature and testing after each step.
Challenges we ran into
PayPal is not available in Bangladesh. I could not register a PayPal account, so I could not get my own sandbox credentials in time. I wrote the Orders, Webhooks, and Payouts integration against PayPal's official documentation and covered it with unit tests using mocked responses. Anyone with sandbox credentials can put them in .env.local and switch the app to real sandbox mode.
Other challenges:
- Making AI verification trustworthy. A vision model can misread a receipt or be fooled by text inside an image, so the final decision rests on code-level rules, with a human override.
- Keeping duplicate and reused proof out without storing anything sensitive.
- Designing something warm and readable on a low-end phone in 14 days, as a solo student.
Accomplishments that we're proud of
- A complete donate, prove, verify, release loop designed so that money cannot move without verified proof.
- A verifier that explains itself in plain words a donor can read, instead of returning a bare "approved".
- A design that does not look like a template.
- Honest documentation: the README states exactly what works, what is simulated, and why.
What we learned
- Trust is a product feature. Showing the evidence matters as much as collecting the money.
- Never let a model be the only gate on money. Rules in code, human override, and an audit log are what make AI usable here.
- Writing architecture and security docs before code saved me days of rework.
- Building around a platform you cannot access forces good boundaries: a clean PayPal client layer, a mock layer, and honest labels.
What's next for Sakkhi
- Test every PayPal flow against the live sandbox, then a real pilot with a small local relief group.
- bKash and Nagad payouts for volunteers in Bangladesh.
- Bangla-first interface and Bangla receipt reading.
- A volunteer mobile app that works offline in low-connectivity areas.
- Coordinator tools: multiple verifiers per milestone and dispute handling.
- A public API so other relief groups can embed proof timelines.
Log in or sign up for Devpost to join the conversation.