Hydrogen
당신과 코딩 에이전트를 위한 상거래 기본 요소. 기존 프레임워크에 장바구니·상품·결제·계정을 추가합니다
검증된 지역 장인에게 물건을 맡겨 수리 견적을 AI가 제공하고 배송 시 PayPal 보호 결제로 두 번째 삶을 부여합니다
Give your things a second life. Verified local karigars, doorstep pickup, AI repair quotes and PayPal-protected payments released only on delivery.
커머스TypeScript · JavaScriptGitHub @meenakshisatpathy20-del온라인운영자 미확인
써 보셨어요? 한 번만 눌러 주세요. 로그인은 필요 없어요.
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
개인 계정의 공개 저장소 소유자는 GitHub로 로그인해 운영자를 확인하고 소개를 직접 관리할 수 있습니다. 관리자 승인은 필요하지 않습니다.
로그인한 뒤 확인 파일을 만들어 이 저장소의 기본 브랜치에 30분 안에 커밋해 주세요. 다른 브랜치나 포크의 파일은 인정하지 않습니다. 파일을 올린 뒤 아래에서 확인하면 관리자 승인 없이 관리할 수 있습니다. 자격을 유지하려면 파일을 남겨 두세요.
로그인이 필요하면 로그인 화면으로 이동합니다. 로그인 후 이곳으로 돌아와 원하는 확인 버튼을 다시 눌러 주세요.
프로젝트 폴더에서 /nomorevibe verify를 실행하면 소유권을 확인하고 소개를 직접 관리할 수 있습니다.
1분 만에 확인하기doorstep repair marketplace for local karigars: AI repair quotes, PayPal-held payments released on delivery OTP, instant payouts. PayPal AI Hackathon 2026.
저장소 README에서 가져옴
README 전체를 불러오는 중입니다.
README 전문 보기 ↗A doorstep repair marketplace for local karigars (informal repairers), built on PayPal + AI. Snap a photo of something broken. AI estimates the repair cost against the price of buying new. A verified local karigar fixes it, a Repair Saathi does the pickup and delivery, and the customer's PayPal payment is held until the repaired item is back in their hands. On the delivery OTP, PayPal captures the money and instantly pays out the karigar and the Saathi.
Built by Meenakshi Satpathy (solo) for the PayPal AI Hackathon 2026. 🌐 Live demo: the Website link in this repository's About section · 🎥 Demo video: on the Devpost project page · 📸 Screenshots · 🧭 Demo guide: every page and feature (also in the app at
/guide)
This Diwali, my mother was sorting old things at home that only needed a small repair. Even though we live in a city, she struggled to find anyone to fix them. The karigars (cobblers, tailors, mixer and fan repairers) are right there in our neighbourhood, but nobody can find them online, nobody comes home to collect the items, and nobody knows what a fair price is. So people buy new and throw the old one away.
Sudhaar fixes each of those problems:
| Problem | How Sudhaar solves it |
|---|---|
| "I don't know a good repairer nearby" | Verified karigars compared side by side by price, rating, distance and ready time |
| "I have to carry it to a shop and go back" | Repair Saathi pickup and delivery (plumbers and electricians do home visits) |
| "Is it worth repairing?" | AI Snap & Quote: repair-cost range vs. new price, so you see the saving |
| "I'll get overcharged / I can't trust a stranger" | Price shown upfront, PayPal holds the money until delivery, OTP at every handover |
| "What if it breaks again?" | 15-day warranty (30 with Sudhaar Care) and Resolve Hub, a full claims desk built into the site: claim ids, priority with a decision deadline (SLA), photo evidence, a three-way conversation (customer, karigar, Sudhaar team), status workflow, activity log, notifications, and PayPal refunds approved by a person |
| Karigars get few customers and get paid late | Free listing, karigar keeps 90% of the repair charge, instant PayPal payout |
sequenceDiagram
actor C as Customer
participant S as Sudhaar
participant AI as Gemini (AI)
participant PP as PayPal sandbox
actor K as Karigar
actor R as Repair Saathi
C->>S: Photo + description
S->>AI: Vision quote (item, damage, repair range, new price)
S-->>C: Karigars ranked by price, distance, rating, ETA
C->>S: Book
S->>PP: Orders v2 create (intent AUTHORIZE)
C->>PP: Approve in PayPal popup (JS SDK v6)
S->>PP: Authorize, so funds are held, not taken
R->>S: Pickup OTP verified
K->>S: Repaired + after photo
S->>AI: Before/after completion check
R->>S: Delivery OTP verified
S->>PP: Capture authorization
S->>PP: Payouts v1: 90% repair to karigar, 75% pickup fee to Saathi
S->>PP: Invoicing v2: digital bill, marked paid
C->>S: Resolve Hub complaint (bill auto-attached)
S->>AI: Review complaint + bill + photos
S->>PP: Refund capture (partial/full)
/agent is a Gemini function-calling agent that acts for the customer: "My mixer jar blade is loose, get it fixed under $8 by Friday." It quotes the job (with vision if a photo is attached), picks the karigar against the budget and deadline, books it and creates the PayPal order, tracks status, files warranty claims and issues refunds up to a $5 policy limit that is enforced in code. It uses PayPal Agent Toolkit tools for PayPal lookups (orders, invoices, refunds, transactions, disputes). The customer approves every payment in the PayPal popup, so the agent can never spend money on its own.
Born from my mother's Diwali cleaning: walk around the house and snap every broken thing (a bag zip, a chappal, the mixer). Gemini quotes each item, the best karigar is picked for each, one Repair Saathi collects everything in one trip (cheaper than separate pickups), and the customer makes one PayPal payment. On delivery PayPal captures it once and Payouts splits it to every karigar for their own items plus the Saathi. Each karigar repairs only their items in the Karigar app, with an AI photo check per item.
Many parents live alone while their children work in other cities. A parent books the repair (even by voice), picks Someone else pays, and shares a WhatsApp link. The son or daughter opens /pay/<order> and approves the PayPal payment from their own account. The money is still only held until the item is back home.
Every booking gets a tracking number and a shareable tracking link (/track/<order>?t=…) that a son or daughter can open without logging in. It shows a step-by-step timeline with times, the karigar shop, the Saathi and the Saathi's live position with an ETA. The Saathi app shares the phone's GPS while riding (or a clearly labelled demo ride so judges can watch it from a desk), and the ETA uses the Saathi's vehicle (walk, bicycle, scooter, motorbike). The page never shows OTPs, prices or the exact home address. The Saathi app plans the day as a numbered route (nearest stop first) on the map, with directions for each stop, and the admin console shows the live fleet.
A monthly plan (₹169, billed $1.99/month by PayPal in the sandbox) for homes that repair often: free doorstep pickup on every repair and a 30-day warranty instead of 15 days. It uses the PayPal Catalog Products → Billing Plans → Subscriptions APIs: the customer approves on PayPal, comes back to Sudhaar, and the server asks PayPal for the subscription status before switching Care on (it never trusts the return link alone). Cancelling calls the Subscriptions cancel API, and webhooks (BILLING.SUBSCRIPTION.*, PAYMENT.SALE.COMPLETED) keep the membership in step. Members' bookings show the pickup fee as a PayPal discount line; Sudhaar still pays the Saathi their full share.
Codes such as FIRSTFIX (₹50 off a first repair), DIWALI25 (₹25 off above ₹200) and GHARSAFAI (15% off baskets). Every code is checked on the server (first order only, baskets only, minimum order, once per customer, usage limit, expiry) when it's applied and again when booking. The discount comes out of Sudhaar's own share and is capped by it, so the karigar and Saathi are always paid in full; it reaches PayPal as breakdown.discount on the order and invoice_discount on the invoice. The admin console creates codes, switches them off and shows how often each was used.
A Hindi voice agent on Bolna answers a phone number. It recognises returning callers by their number, quotes a repair with Gemini, books a pickup slot, tells callers where their repair is, cancels before pickup (voiding the PayPal hold) and files warranty claims into Resolve Hub. It does all of this through Sudhaar's own /api/voice/* functions, which are protected by a shared secret.
Bolna is used as a voice layer on the whole repair, in both directions. Inbound, the agent quotes, books, tracks, cancels, files claims, texts a forgotten OTP and hands callers to a person. Outbound, a background conductor has the same agent call the family payer when a phone booking isn't paid after 2 hours and call the phone customer before the pickup, alongside SMS reminders, expiry notices and job texts to the karigar and Saathi. The admin sees every call (transcripts), text and callback request per customer in Admin → Phone line → Customer timeline.
Payment never happens on the call. Each phone booking creates a PayPal order and a Family Pay link, which is texted to the payer's mobile (the caller's son or daughter, or the caller). Callers without a smartphone get their pickup and delivery OTPs by SMS, can answer a karigar's price change from the SMS link, hear the team's questions on their claim when they call, and can ask for a forgotten OTP to be texted again. A new caller also gets an account with a PIN, read out once, so they can use the website later. The agent never reads OTPs aloud. Customers can also press "Ask Sudhaar to call me" on the website, which uses Bolna's outbound call API. Bolna's post-call webhook logs each call (summary and transcript) in Admin → Phone line, where the team can send pay links. Setup: docs/BOLNA.md; agent prompt and functions: bolna/.
A karigar sometimes finds more damage after opening the item. They can't just charge more: they send a new price with a reason, the customer approves or declines it in the app, and an increase is paid as a second PayPal authorization for only the difference. The repair can't be marked done while a price change is waiting. On delivery both holds are captured, and a later refund is split across both captures.
All calls go to the PayPal sandbox. Every PayPal id appears on the order page and in the admin grid, so you can verify each one in the sandbox dashboard.
| PayPal capability | Where | What Sudhaar does with it |
|---|---|---|
JavaScript SDK v6 (paypal-payments, <paypal-button>) | components/PayPalCheckout.tsx | Checkout popup on the order page and inside the agent chat |
Orders v2, intent AUTHORIZE | lib/paypal.ts createAuthorizeOrder, authorizeOrder | Holds the customer's money at booking, works like escrow. Coupons and Sudhaar Care are sent as amount.breakdown.discount against itemised lines |
| Second authorization for a price increase | createTopUpOrder | If the customer approves a karigar's higher price, only the difference is authorized as its own PayPal order and captured with the first |
| Payments v2 capture / void | captureAuthorization, voidAuthorization | Captures only after the delivery OTP; voids if the customer cancels before pickup |
Orders v2, intent CAPTURE | createTipOrder, captureOrder | Thank-you tips are paid immediately (no hold), then paid out in full to the karigar in their own Payouts batch |
| Payouts v1 | sendPayouts, getPayoutBatch | Instant split to the karigar(s) and the Saathi the moment the job is confirmed. A Ghar Safai basket pays several karigars from one payment. Partners press Check payout status with PayPal to refresh each batch's status |
| Invoicing v2 | createPaidInvoice | Generates, sends and marks paid a PayPal invoice (with invoice_discount for coupons / Care): the "digital bill" used by Resolve Hub |
| Catalog Products + Billing Plans v1 | createCareProduct, createCarePlan |
Google Gemini (gemini-flash-latest by default, via Google's official @google/genai SDK) with JSON-schema structured outputs and function calling (lib/llm.ts, lib/ai.ts). A free API key from Google AI Studio is enough to run it:
Without a GEMINI_API_KEY, features 1–3 fall back to a deterministic estimator that is clearly labelled "Simulated" in the UI. The agent needs a key. If Gemini is busy or over its usage limit, quotes fall back to the price table, photo checks go to a person, and the agent asks the customer to try again in a minute.
I'm a solo participant, a 3rd-year Computer Science student.
My part: I came up with the idea from a real problem at home, researched it, and designed the product and its features: OTP handovers, Repair Saathi pickup by local volunteers and students, Shiprocket-style distance pricing and tracking, Resolve Hub complaints with bill proof, KYC-verified karigars, and a fair split so karigars keep 90%. I also did the testing in the PayPal sandbox and made the demo video.
AI as my coding assistant: I used Claude Code (Anthropic's AI coding assistant) to turn my design into code. The first commit, the initial app, was generated with Claude Code from my specification. Later changes, fixes and new features were also written with Claude Code, following my product decisions and feedback, and I reviewed and tested them.
| Decision | Why |
|---|---|
| Money is only held (PayPal AUTHORIZE) until the delivery OTP | The customer's item leaves their home. They shouldn't pay for something they haven't got back, and the karigar shouldn't work for money that isn't there. Holding solves both. |
| OTPs are never spoken on a call, only texted to the registered number | Caller ID can be faked. Anyone who calls "as Kamla" could otherwise collect her item. A text only reaches the real phone. |
| A person decides every refund; Gemini only suggests | AI is good at reading a bill and photos, but taking money back from a karigar is a judgement about a person's livelihood. |
| The family pays, the elder books (Family Pay link by SMS) | In India the person who needs the repair and the person with a PayPal account are often different people in different cities. |
| Voice first, app optional | The people who repair most (older people, small towns) are the least likely to install an app. A phone call works on any phone. |
| Street karigars, not our own staff | They already have the skill and the shop; what they lack is customers and safe digital payment. Karigars keep 90% of the repair price. |
| The karigar and Saathi get jobs by SMS | They often don't watch an app either, so the voice-and-SMS layer serves both sides of the market. |
| ₹ | |
|---|---|
| Customer pays: repair ₹383 + pickup ₹85 | 468 |
| Karigar (90% of the repair) | 345 |
| Repair Saathi (75% of the pickup fee) | 64 |
| Sudhaar keeps (10% of repair + 25% of pickup) | 59 |
| Phone-line cost for a phone booking: about 3 min of Bolna at $0.06/min (Bolna dashboard) | ≈ 15 |
| SMS: about 5 texts per order (pay link, OTPs, delivery). Twilio's India rate is per segment and must be checked in the Twilio console; an Indian DLT SMS provider is usually cheaper | a few ₹ to ≈ 30 |
| PayPal fees | per PayPal's rate for the market |
So a website booking keeps roughly ₹59, and a phone booking still covers its call and texts. Ghar Safai baskets (several items, one pickup) and Sudhaar Care (a monthly subscription) raise the margin per trip. These are prototype prices in the PayPal sandbox (USD shown as ₹ at 85).
/admin (partner side) (orders, payouts, karigars, PayPal webhooks) with sorting, filtering and pagination.render.yaml.postman/Sudhaar.postman_collection.json drives the whole flow through the API.Hosted demo: open the Website link in this repository's About section. It runs against the PayPal sandbox. Log in to PayPal with the sandbox buyer account shown right under the PayPal button (also in the testing instructions on the Devpost page). It's a PayPal sandbox account with test money only. On the free hosting plan, the first load can take about a minute while the server wakes up.
Fastest way in: open /guide in the app (the green bar at the top links to it). It has one-tap logins for the customer, Saathi, karigar and admin, the whole journey step by step, and a table of every page. The full written version is docs/DEMO-GUIDE.md.
Demo logins (each role sees only its own app and data; real users sign up with their own phone + PIN):
| Role | Where | Phone | PIN | One tap |
|---|---|---|---|---|
| Customer (Anita) | any "Log in" | 9999999999 | 1234 | Try the demo account |
| Karigar | /partner | 9000000003 (Mohan) | 1111 | Karigar demo button: opens the karigar of the latest booking |
| Other sample karigars | /partner | 9000000001 … 9000000008 | 1111 | |
| Saathi (Vikas / Pooja) | /partner | 9100000001 / 9100000002 | 2222 | Saathi demo button: opens the Saathi of the latest booking |
| Admin | /partner | 9000000000 | 2026 | Admin demo button |
The demo buttons open the karigar and Saathi of the most recent booking that's waiting on them, so you always land on your own test order.
/partner and log in as the Saathi → enter the pickup OTP the customer reads out from their order page (Saathis never receive OTPs) → Handed to karigar./partner, Karigar demo button) → Inspect & start repair → optionally Change price after inspection with a reason (Ask the customer); the customer approves it on their order page and pays the difference in a second PayPal popup → upload an after photo → Mark repaired (the AI completion check runs). If the AI rejects the photo or is unavailable, the money stays held and the repair appears in Admin console → Photo checks for a person to approve or send back./resolve/RH-…: status, stage stepper (Submitted → AI review → Investigation → Decision → Closed), SLA countdown, Gemini's suggestion, a conversation with the Sudhaar team and the karigar, photo evidence and the activity log. As admin, open the claim (bell icon or Admin console → Resolve Hub): assign it, change priority, ask the customer or karigar a question, then decide: PayPal refund, free re-repair or close with a reason. The customer gets a notification and sees the PayPal refund id.Requirements: Node 20+.
git clone https://github.com/meenakshisatpathy20-del/sudhaar-paypal.git
cd sudhaar-paypal
npm install
cp .env.example .env # fill in the values below
npm run smoke:paypal # optional: checks your PayPal sandbox credentials
npm run dev # http://localhost:3000
The app also runs with an empty .env: PayPal and AI calls are then simulated and the header shows yellow "Simulated" badges. Add sandbox keys so the real PayPal flow runs.
PAYPAL_CLIENT_ID / PAYPAL_CLIENT_SECRET.PAYPAL_KARIGAR_EMAIL / PAYPAL_SAATHI_EMAIL. Use the default sandbox Personal account as the buyer (PAYPAL_CUSTOMER_EMAIL).https://<your-host>/api/paypal/webhook and put its id in PAYPAL_WEBHOOK_ID.| Variable | Required | Purpose |
|---|---|---|
PAYPAL_CLIENT_ID, PAYPAL_CLIENT_SECRET | for real PayPal | Sandbox REST app credentials |
PAYPAL_KARIGAR_EMAIL, PAYPAL_SAATHI_EMAIL | for real payouts | Sandbox personal accounts that receive payouts |
PAYPAL_CUSTOMER_EMAIL | optional | Invoice recipient fallback |
PAYPAL_WEBHOOK_ID | optional | Enables webhook signature verification |
PAYPAL_DEMO_BUYER_EMAIL, PAYPAL_DEMO_BUYER_PASSWORD | optional | A sandbox buyer login (test money) shown under the PayPal button for judges |
GEMINI_API_KEY | for real AI + agent | Gemini API key from Google AI Studio (free tier available) |
AI_MODEL | optional | Defaults to gemini-flash-latest |
SESSION_SECRET | recommended in production | Signs login cookies. Render generates it (see render.yaml); locally a random one is saved in DATA_DIR |
DEMO_CENTER_LAT/LNG, DATA_DIR | optional | Demo location and data folder |
app/(customer)/ Customer app: home, fix flow, ghar-safai (basket), orders/[id] tracking, repairs, talk (agent), care (subscription), guide (demo guide), profile, karigars/[id], login, join (karigar and Saathi onboarding)
app/pay/[id] Family Pay page the family member opens to pay with PayPal
app/track/[id] Public, token-protected tracking page (timeline, live Saathi, ETA)
app/api/voice/ Bolna phone line functions (caller, quote, book, status, cancel, complaint, webhook, callback)
app/(partner)/ Partner side (phone + PIN login per role): karigar app, saathi app, admin console (AG Grid)
app/api/ auth, me, quote, baskets, orders (+approve/action/price/price-decision/complaint/resolve/review/rate/tip), partner (me/online/location/profile/payouts), track, care (+return), coupons, applications, agent, karigars, admin, uploads, paypal/webhook
components/ UI (shadcn/ui components, doodles, three.js hero, PayPal SDK v6 checkout, voice, map, Family Pay, Fix-or-Replace meter…)
lib/
paypal.ts PayPal REST client (Orders, Payments, Payouts, Invoicing, Catalog Products, Billing Plans, Subscriptions, Webhooks)
care.ts Sudhaar Care: plan setup, subscribe, confirm with PayPal, cancel, webhook updates
coupons.ts Coupon rules, capped at Sudhaar's share
tracking.ts Tracking timeline, the Saathi's live location and ETA
voice.ts Bolna phone line: caller lookup, quote, book, status, cancel, claim, call log
bolna.ts Bolna outbound call API ("Call me")
bolna/ Phone agent prompt and custom function definitions for Bolna
llm.ts Gemini client and structured outputs
ai.ts Gemini: quote, completion check, complaint review
agent.ts Repair Agent (Gemini function calling + PayPal Agent Toolkit)
orders.ts Order state machine, OTP checks, price changes, settlement, Resolve Hub, photo-check review
claims.ts Resolve Hub desk: conversation, evidence, status, assignment, notifications, reports
claims-shared.ts Claim statuses, priorities, SLA hours and stages (used by server and pages)
auth.ts / pin.ts Phone + PIN accounts, scrypt hashes, signed session cookies, lockout
access.ts Who may see and act on which order
onboarding.ts Karigar and Saathi applications and checks
privacy.ts What each role's APIs may show (no OTPs for partners, no payout emails, masked contacts)
geo.ts Customer location and placing the sample neighbourhood around it
pricing.ts Rate card (distance × size), split, haversine
i18n.ts, locales/ Strings in 8 languages (English and Hindi in i18n.ts, the rest in locales/)
db.ts / seed.ts JSON-file store with seeded demo karigars
postman/ Postman collection for the full flow
scripts/ PayPal sandbox smoke test
Sudhaar works end to end today as a demo on the PayPal sandbox. This is my plan to make it work for millions of households, and the facts it rests on.
Why now
How the money works (from the code, not a projection)
lib/pricing.ts).Payments at scale: an honest plan
Roadmap
| Stage | What gets built |
|---|---|
| 1. Pilot: one neighbourhood, about 20 karigars | SMS OTP to verify phone numbers, named staff accounts, Postgres and cloud photo storage instead of the JSON file, karigars' real shop locations and address search, a paid map-tile provider, WhatsApp and SMS updates at every step |
| 2. One city | "Repair Points" at kirana shops for drop-off, smarter Saathi routes that combine pickups, DigiLocker ID checks with consent, transit insurance for items, voice-first Karigar and Saathi apps, translations reviewed by native speakers |
| 3. More cities and countries | Bulk Ghar Safai for housing societies and offices, a booking line over WhatsApp or phone calls for people without smartphones, PayPal multiparty in PayPal-domestic markets |
Risks I've designed for
INR_PER_USD in lib/pricing.ts). The Admin console and PayPal records stay in USD so they match the sandbox dashboard.data/db.json) that is re-seeded automatically, so a fresh deploy always works./guide, linked from the bar at the top and the footer): one-tap logins for all four roles, the whole journey step by step, and every page with what to try and the APIs behind it.| Creates the Sudhaar Care product and monthly plan the first time anyone subscribes |
| Subscriptions v1 | createSubscription, getSubscription, cancelSubscription (lib/care.ts) | Customer approves on PayPal; Sudhaar confirms the status with PayPal before activating; cancel from the app |
| Refunds (Payments v2) | refundCapture | Partial or full refunds from Resolve Hub (support desk or agent within limit), split across both captures when there was a price increase |
| Webhooks | app/api/paypal/webhook/route.ts | Verifies signatures (verify-webhook-signature), logs events on the order, and (only when verified) updates Sudhaar Care from BILLING.SUBSCRIPTION.* and PAYMENT.SALE.COMPLETED |
| PayPal Agent Toolkit | lib/agent.ts | get_order, get_invoice, list_invoices, get_refund, list_transactions, list_disputes as agent tools |
/pay/… link to pay as the family member. In the Karigar app, switch between karigars to repair each one's items; after delivery the order shows one capture and one payout per karigar./join) → apply → in Admin console → Applications tick the three KYC checks → Approve and list karigar, which shows the new karigar's login PIN → the new karigar appears in quotes with a "New" badge instead of a made-up rating and can log in at /partner. Become a Repair Saathi (/join?as=saathi) works the same way, with ID, training and trial-trip checks.FIRSTFIX (or type a code). The bill and the PayPal order show the discount; try it again on a second booking to see it refused. In Admin → Coupons, create a new code or switch one off.