Refund i partial refund: kako modelovati povraćaj sredstava
Blog • Web razvoj • • 8 min čitanja

Refund i partial refund: kako modelovati povraćaj sredstava

Autor Autorski tim · DA. Diџital agencija
Ažurirano 29.09.2026
Vreme čitanja 8 min
Sadržaj Pregledajte teme u tekstu

Refund i partial refund treba modelovati kao zaseban poslovni tok, a ne kao jednostavnu izmenu statusa porudžbine. Sistem najpre beleži zahtev za povraćaj, proverava koliko je moguće vratiti, šalje instrukciju payment provajderu, čeka potvrdu obrade i tek onda ažurira porudžbinu, korisnički prikaz i finansijsku evidenciju.

To je suština pouzdane payment refund integracije: iznos, status i razlog povraćaja moraju biti sledljivi kroz ceo proces. Kod partial refund-a dodatno je potrebno voditi računa o preostalom refundabilnom iznosu, više uzastopnih povraćaja i neusaglašenosti između internog sistema i payment provajdera. Za širi kontekst povezivanja platnog sistema sa sajtom i poslovnim pravilima pogledajte integraciju platnih kartica.

Refund, void i chargeback nisu isti događaj

Pre nego što se definiše model, treba razdvojiti tri situacije koje se u praksi često mešaju:

  • Refund je povraćaj novca nakon što je transakcija naplaćena ili je plaćanje ušlo u fazu u kojoj se sredstva mogu vratiti.
  • Void ili cancellation poništava autorizaciju pre konačnog terećenja, kada payment provajder i kartična šema to dozvoljavaju.
  • Chargeback pokreće izdavalac kartice ili korisnik kroz bankarski proces, van standardnog refund dugmeta trgovca.

Ova razlika utiče na API poziv, status, rok obrade, finansijsko knjiženje i komunikaciju sa kupcem. Aplikacija zato ne bi trebalo da svako poništavanje porudžbine automatski naziva refundom. Otkazana porudžbina može značiti da novac nikada nije naplaćen, da je autorizacija oslobođena ili da je već izvršen refund.

Šta treba da sadrži model povraćaja

Minimalni model nije samo polje refunded_at. On treba da poveže internu porudžbinu, originalnu payment transakciju i svaki pojedinačni zahtev za refund.

1. Originalna transakcija

Sačuvajte interni identifikator porudžbine, identifikator payment pokušaja, identifikator transakcije kod provajdera, valutu i originalno naplaćeni iznos. Ako provajder podržava više payment pokušaja za jednu porudžbinu, refund mora biti vezan za konkretno uspešno plaćanje, a ne samo za broj porudžbine.

2. Refund zahtev

Svaki zahtev treba da ima sopstveni interni ID, iznos, valutu, razlog, korisnika ili servis koji ga je pokrenuo, vreme kreiranja i eventualnu vezu sa stavkama porudžbine. Razlog može biti, na primer, otkazivanje, povrat robe, nedostupnost dela porudžbine ili korekcija naplate. Razlog nije zamena za status, ali je važan za podršku, izveštaje i reviziju.

3. Status obrade

Interni status treba da opisuje šta se zaista dogodilo, a ne samo šta je aplikacija pokušala. Praktičan skup može izgledati ovako:

  • requested — zahtev je kreiran, ali još nije poslat;
  • submitted — zahtev je poslat payment provajderu;
  • pending — obrada nije konačna i čeka se dalja potvrda;
  • succeeded — refund je potvrđen kao uspešan;
  • failed — zahtev nije prihvaćen ili nije uspešno obrađen;
  • cancelled — zahtev je otkazan pre konačnog izvršenja, ako takav scenario postoji kod provajdera.

Nazivi mogu biti drugačiji, ali je važno da se statusi ne svode na dve vrednosti: „refundovan“ i „nije refundovan“. Posebno ne treba prikazati konačnu poruku kupcu dok je zahtev samo poslat, a ne potvrđen.

Kako modelovati partial refund

Partial refund znači da se vraća samo deo prvobitno naplaćenog iznosa. To može biti povraćaj jedne stavke, dela količine, razlike u ceni ili kompenzacija bez otkazivanja cele porudžbine.

Najvažnije pravilo je:

Ukupan uspešno refundiran iznos plus aktivni iznosi u obradi ne sme preći iznos koji je moguće vratiti po originalnoj transakciji.

U praksi se često koristi sledeća logika:

  • original_amount — ukupno naplaćen iznos;
  • succeeded_refunded_amount — zbir uspešnih refundova;
  • pending_refund_amount — zbir refund zahteva koji još nisu konačni;
  • available_refund_amount — iznos koji preostaje za novi zahtev.

Formula može biti: available_refund_amount = original_amount - succeeded_refunded_amount - pending_refund_amount. Konačna implementacija mora uzeti u obzir pravila konkretnog payment provajdera, zaokruživanje i valutu sa najmanjom novčanom jedinicom.

Refund po iznosu ili po stavkama

Refund po ukupnom iznosu je jednostavniji, ali slabije objašnjava šta se dogodilo sa porudžbinom. Refund po stavkama zahteva dodatni model: koja stavka je vraćena, u kojoj količini, po kojoj ceni, sa kojim proporcionalnim delom dostave, poreza ili popusta.

Za prodavnicu sa fizičkom robom, stavke su često korisnije jer povezuju payment događaj sa magacinom i procesom povrata. Za uslugu ili pretplatu, iznos i razlog mogu biti dovoljni, ali treba jasno zabeležiti period, paket ili račun na koji se refund odnosi.

Ne treba automatski pretpostaviti da payment API razume katalog proizvoda. Payment provajder obično zna transakciju i iznos, dok je mapiranje refund-a na artikle odgovornost vaše aplikacije ili commerce sistema.

Idempotency: zaštita od duplog refund-a

Refund je operacija kod koje ponovljeni zahtev može proizvesti finansijsku posledicu. Zato retry logika mora biti projektovana pre produkcije, a ne dodata tek kada se pojavi timeout.

Primer problema: administrator klikne „Vrati novac“, zahtev stigne do provajdera, ali odgovor ne stigne nazad zbog mrežnog prekida. Ako aplikacija slepo pošalje novi zahtev, može pokušati da vrati isti iznos drugi put.

Rešenje je idempotency ključ koji je stabilno vezan za jedan poslovni zahtev. Pre slanja treba sačuvati lokalni zapis, generisati jedinstveni ključ i pri ponavljanju koristiti isti ključ, u skladu sa pravilima provajdera. Pored toga, aplikacija treba da proveri da li za istu porudžbinu već postoji refund sa istim iznosom, razlogom i poslovnim identitetom.

Idempotency ne znači da je svaki retry bezbedan u svim okolnostima. Potrebno je proveriti kako konkretan provajder čuva ključeve, koliko dugo ih prihvata i kako razlikuje isti zahtev od novog refund-a.

Webhook i polling: kako saznati konačan ishod

API odgovor potvrđuje da je zahtev primljen ili kreiran, ali ne mora uvek da znači da je novac konačno vraćen. Kod asinkrone obrade konačni ishod može stići kroz webhook događaj ili se proverava naknadnim upitom ka payment sistemu.

Webhook handler zato treba da bude:

  • idempotentan — isti događaj može stići više puta;
  • otporan na promenu redosleda — događaji ne moraju uvek stići idealnim redom;
  • verifikovan — potpis ili drugi mehanizam autentičnosti mora biti obrađen prema dokumentaciji provajdera;
  • auditabilan — sačuvajte originalni događaj ili dovoljno podataka za kasniju proveru.

Interni status ne treba unapred prepisati na osnovu korisničkog interfejsa. Na primer, prikaz „zahtev je poslat“ može biti tačan dok god je refund pending, ali poruka „sredstva su vraćena“ zahteva potvrđen uspešan ishod.

Za integracije koje već imaju problem sa neuspešnim naplatama, retry pravilima i obradom događaja, koristan je i tekst o failed payments i dunning procesu. Refund nije isti tok kao ponovna naplata, ali oba zahtevaju pouzdanu obradu asinkronih payment događaja.

Kako refund izgleda u korisničkom i administratorskom interfejsu

Administratorski ekran treba da spreči slučajne i nejasne operacije. Pre potvrde prikažite originalni iznos, već refundirani iznos, iznos koji je u obradi i maksimalni raspoloživi iznos. Ako se refund radi po stavkama, prikažite količinu i vrednost svake stavke.

Dobro je zahtevati razlog i jasno označiti da li se vraća ceo iznos ili samo deo. Dugme ne bi trebalo da bude aktivno kada je iznos nula, veći od dostupnog iznosa ili u pogrešnoj valuti. Kod paralelnih refund zahteva korisno je privremeno zaključati obradu ili ponovo izračunati raspoloživi iznos neposredno pre slanja.

Korisnik ne mora videti sve tehničke statuse, ali poruka treba da bude precizna:

  • „Zahtev za povraćaj je primljen“ kada obrada još nije konačna;
  • „Povraćaj je potvrđen“ kada postoji potvrda uspeha;
  • „Povraćaj nije uspeo; proverite detalje ili kontaktirajte podršku“ kada je zahtev odbijen.

Nemojte obećavati tačan trenutak kada će sredstva biti vidljiva na računu ako to zavisi od banke, izdavaoca kartice ili payment provajdera. U obaveštenju navedite ono što vaša aplikacija zaista zna: iznos, valutu, datum zahteva i referencu.

Refund i evidencija novca

Payment status i status porudžbine nisu isto što i računovodstvena evidencija. Uspešan refund treba povezati sa originalnom transakcijom, iznosom, valutom, naknadama i internim dokumentom koji koristi finansijski tim. Da li se naknada vraća, delimično zadržava ili se knjiži na drugi način zavisi od ugovora sa payment provajderom i računovodstvenih pravila.

Za svaku promenu sačuvajte ko je pokrenuo refund, kada, iz kog interfejsa ili servisa, koji je bio prethodni status i koji identifikator je vratio provajder. Takav trag olakšava rešavanje reklamacija i usklađivanje izveštaja.

Ako refund utiče na lager, fakturu, loyalty bodove ili pristup digitalnom sadržaju, te posledice ne treba skrivati unutar payment callback-a. Bolje je emitovati interni događaj, kao što je „refund confirmed“, pa zasebnim handlerima ažurirati povezane sisteme. Time se smanjuje rizik da pad jednog dodatnog servisa blokira prijem payment potvrde.

Najčešće greške u refund integraciji

  • Refund se vezuje samo za broj porudžbine. Ako postoji više payment pokušaja, može biti vraćen pogrešan payment zapis.
  • Status se postavlja na uspešan odmah posle API poziva. Prijem zahteva nije uvek konačna potvrda.
  • Ne postoji zbir prethodnih partial refund-ova. Sistem može dozvoliti povraćaj veći od originalno naplaćenog iznosa.
  • Retry generiše novi zahtev. Timeout se pogrešno tumači kao neuspeh bez provere idempotency ključa i statusa.
  • Webhook se obrađuje više puta. Ponovljena isporuka može duplirati email, knjiženje ili promenu zaliha.
  • Refund se meša sa otkazivanjem autorizacije. Posledica je pogrešan prikaz korisniku i netačno izveštavanje.
  • Valuta se ne proverava. Iznos bez eksplicitne valute nije dovoljno precizan za međunarodne ili multi-currency tokove.

Kada checkout ima više načina plaćanja ili wallet opcija, povraćaj treba testirati za svaki relevantan payment flow. Povezani tekst o hosted checkout i embedded payment formi pomaže pri razumevanju gde se prikupljaju podaci i koji deo toka kontroliše aplikacija. Za wallet scenarije pogledajte i Apple Pay i Google Pay integraciju u checkout-u.

Praktičan redosled za implementaciju

  1. Popišite poslovna pravila. Odredite ko sme da pokrene refund, da li su dozvoljeni višestruki partial refund-ovi i kako se refundiraju dostava, porez i popust.
  2. Definišite model podataka. Odvojite originalnu transakciju, refund zahtev i konačan payment događaj.
  3. Mapirajte statusni dijagram. Upišite dozvoljene prelaze i ponašanje pri grešci, timeout-u i ponovljenom webhook-u.
  4. Uvedite kontrolu iznosa i idempotency. Provera mora postojati i u korisničkom interfejsu i na serverskoj strani.
  5. Implementirajte webhook obradu. Verifikujte događaje, čuvajte trag obrade i sprečite duple efekte.
  6. Testirajte granične slučajeve. Pokrijte puni refund, više delimičnih refund-ova, neuspeh, kašnjenje, pogrešnu valutu, paralelne zahteve i ponovljenu isporuku događaja.
  7. Uskladite izveštaje. Uporedite interne refund zapise sa izveštajima payment provajdera i definišite proceduru za neslaganja.

Ako refund postaje deo šireg checkout-a, pretplate, kataloga ili administratorskog sistema, zahtevi treba da budu opisani zajedno sa ostatkom arhitekture. Kod projekata gde je potreban novi ili prilagođeni korisnički tok, relevantan kontekst je i izrada sajta, ali refund logika ne treba da ostane samo na nivou dizajna ekrana — ključna je serverska obrada i evidencija.

Šta proveriti pre puštanja u rad

Pre produkcije proverite dokumentaciju konkretnog payment provajdera za podržane tipove refund-a, ograničenja po transakciji, webhook događaje, rokove i ponašanje u slučaju greške. Pravila se razlikuju između provajdera, metoda plaćanja i tržišta, pa generički model treba potvrditi kroz stvarni sandbox i kontrolisani test.

Dobro projektovan refund tok omogućava da podrška vidi šta je zatraženo, finansije šta je potvrđeno, a korisnik dobije jasnu poruku bez lažnog obećanja. Sledeći korak je da se pre implementacije nacrtaju statusi, izvori istine i pravila za partial refund, a zatim ta odluka uklopi u kompletnu integraciju platnih kartica.

Podelite tekst
LinkedIn X Facebook
DA.
Autor i urednik sadržaja

DA. Editorial Team

SEO, PPC, web razvoj i dizajn tim DA. Tekstove zasnivamo na iskustvu iz aktivnih projekata, Search Console podacima, platformskim promenama i praktičnim testovima.

Google Preferred Sources

Pratite DA. kao izvor koji želite da viđate češće.

Dodajte da.org.rs u svoje Preferred Sources i olakšajte Google-u da vam češće prikaže DA. sadržaj kada je relevantan za vaše pretrage.

Dodaj DA. kao izvor
DA. Web razvoj

Treba vam sajt koji je brz, jasan i spreman za rast?

Od prezentacionih sajtova do custom CMS i web rešenja, gradimo tehničku osnovu za SEO, kampanje i konverzije.

DA. DIGITALNI SAVETNIK

Pitajte DA.

Recite mi cilj, problem ili sledeći potez. Usmeriću vas na relevantan DA vodič ili uslugu.