API za autore modpakova: aktivacioni kodovi i ažuriranja
Kako autor plaćenog modpaka može da izdaje aktivacione kodove i objavljuje ažuriranja preko Millida Hosting API-ja: verzije modpaka, otpremanje arhive, objavljivanje, vraćanje na prethodnu verziju, status koda i webhook.
Ažurirano 6. septembar 2026.
Ne moraš da pišeš kod. Sve što je opisano ispod sada je dostupno i preko dugmadi: ako je tvoj modpak povezan sa tvojim Millida nalogom, u profilu se pojavljuje kartica „Moji modpakovi” — tamo otpremaš verzije, uređuješ karticu i praviš landing stranice. Ako nije povezan — piši nam i povezujemo ga. API je za one koji objavljuju iz svog CI-ja.
Ovaj članak je za autore plaćenih modpakova koji ih sami prodaju i instalaciju servera prepuštaju nama. Kupac ne mora ništa da preuzima: unese kod i dobije postavljen modpak. Da vidiš kako to izgleda sa njegove strane, pročitaj Plaćeni modpak preko aktivacionog koda.
Šta ti treba za početak
- Pošalji nam serverski arhiv svog modpaka —
.zipsamods/u korenu (bez omotača kao što jeServer Files/) ili.mrpack. Arhiv se čuva u našem privatnom skladištu, a link se nikada ne deli spolja. - Reci nam koji je core, verzija igre i minimalna memorija — čarobnjak ih koristi da izbaci planove na kojima modpak neće raditi.
- Dobij od nas ključ modpaka (
key, na primerarcania) i token za izdavanje — tvoj sajt ga koristi da generiše kodove.
Token se prikazuje samo jednom: čuvamo samo njegov otisak. Ako ga izgubiš, traži da ga ponovo izdamo — stari će prestati da radi.
Kako šema funkcioniše
- Plaćanje primaš sam, na svojoj strani.
- Posle plaćanja, tvoj sajt poziva naš API i dobija aktivacioni kod.
- Kod daješ kupcu — mejlom, preko bota ili na stranici „hvala”.
- Kupac unosi kod na našoj strani i dobija server sa modpakom na plaćenom planu.
- Fajlovi modpaka na serveru su zaključani:
modsne može da se preuzme iz panela ni preko SFTP-a.
Fizički, kupac nikada ne dobija serverski modpak u ruke — samo server koji radi.
Endpoint i autorizacija
Osnovni URL — https://millida.net/v2/hosting.
Token se prosleđuje u zaglavlju X-Pack-Token. To nije JWT ni Bearer token — to je posebna tajna za tvoj modpak.
X-Pack-Token: mpk_pack_XXXXXXXXXXXXXXXX
Content-Type: application/json
Token živi na tvom serveru — drži ga u promenljivama okruženja, ne u frontend kodu.
Izdavanje kodova
POST /v2/hosting/packs/{key}/keys
| Polje | Tip | Podrazumevano | Šta radi |
|---|---|---|---|
count | broj 1–200 | 1 | Koliko kodova se generiše po pozivu |
note | string do 120 | — | Tvoja napomena: broj porudžbine, nadimak kupca |
maxServers | broj 1–20 | 1 | Na koliko servera jedan kod može da se aktivira |
expiresAt | ISO datum | — | Datum isteka koda |
curl -X POST https://millida.net/v2/hosting/packs/arcania/keys \
-H "X-Pack-Token: $PACK_TOKEN" \
-H "Content-Type: application/json" \
-d '{"count": 1, "note": "order 4821"}'
{
"code": "A7K2-9MHD-4RTP-QW38",
"codes": ["A7K2-9MHD-4RTP-QW38"]
}
Polje code je prvi kod u seriji, zadržano zbog kompatibilnosti; kada je count > 1, koristi codes.
Kodovi se vraćaju samo ovde i nigde drugde. Čuvamo njihov heš — kao lozinku. Ako izgubiš kod, ne možemo da ga povratimo: izdaj novi i opozovi stari.
Ograničenje je 30 zahteva u minuti po modpaku. Serije do 200 kodova po pozivu postoje upravo zbog prodaje: generiši ih u paketima, a ne jedan kod po zahtevu.
Šta se dogodilo sa kodovima
GET /v2/hosting/packs/{key}/keys?limit=100
[
{
"codeHint": "A7K29MHD",
"note": "order 4821",
"maxServers": 1,
"usedCount": 1,
"state": "spent",
"expiresAt": null,
"revokedAt": null,
"createdAt": "2026-08-03T12:20:11.000Z"
}
]
Sami kodovi nisu u odgovoru i ne mogu biti. codeHint je početak koda — koristi ga da upariš red sa svojom porudžbinom.
Stanja: free — neiskorišćen, spent — iskorišćen, expired — istekao, revoked — opozvan od tvoje strane.
Provera jednog koda
POST /v2/hosting/packs/{key}/keys/status, telo {"code": "A7K2-9MHD-4RTP-QW38"}.
Odgovor je isti red kao u listi. Kod ide u telo, ne u URL: URL-ovi završavaju u logovima proksija i istoriji pregledača, a pre aktivacije kod je radni ključ.
Crtice i velika/mala slova nisu važni: a7k29mhd4rtpqw38 će biti nađen isto kao A7K2-9MHD-4RTP-QW38.
Opoziv koda
POST /v2/hosting/packs/{key}/keys/revoke, telo {"code": "..."}.
Koristi ga za povraćaje novca, greške pri izdavanju ili sporove. Opoziv blokira buduće aktivacije, ali ne uklanja već postavljen modpak — kupac koji ga je aktivirao zadržava server koji radi.
Webhook za aktivaciju
Ako nam daš URL webhook-a, pozvaćemo ga u trenutku kada se kod iskoristi:
POST <your-address>
X-Millida-Pack: arcania
Content-Type: application/json
{
"event": "pack.activated",
"packKey": "arcania",
"codeHint": "A7K29MHD",
"serverId": "cm4x...",
"activatedAt": "2026-08-04T09:14:02.000Z"
}
Poziv nije potpisan: možeš da ga proveriš istim tokenom preko keys/status — pomoću codeHint naći ćeš svoj red i videćeš state: "spent". Tako ne moraš da čuvaš drugu tajnu.
Webhook se šalje bez čekanja na odgovor i ne ponavlja se: ako je tvoj server bio nedostupan, aktivacija je ipak prošla, a to možeš da vidiš u listi kodova. URL mora biti javni — ne pozivamo interne ni lokalne adrese. Preusmeravanja se ne prate.
Kartica modpaka
GET /v2/hosting/packs/{key} je javno, token nije potreban. Vraća ono što kupac vidi: naziv, core, verziju, minimalnu memoriju, listu planova i zastavice zaštite. Link do arhiva nije u odgovoru.
Zgodno za stranicu „Kupi” na tvom sajtu: zahtevi planova dolaze iz jednog izvora i neće se razlikovati od onoga što kaže naš čarobnjak.
Polja izloga svoje kartice uređuješ sam: PATCH /v2/hosting/packs/{key} sa tokenom prihvata name, authorName, authorUrl, iconUrl, webhookUrl. Uslovi prodaje (paidOnly, requireKey, lockFiles, planCodes), uključivanje modpaka u izlog i JVM zastavice za pokretanje ne mogu da se menjaju tokenom — to je naš dogovor sa tobom i naši nodovi, pa nam se obrati u vezi s tim.
Ažuriranja modpaka
Ranije je ažuriranje značilo mejl nama i čekanje. Sada sam objavljuješ verziju, a vlasnici servera je biraju u svom panelu.
Ključna stvar: nikoga ne ažuriramo tiho. Prelazak između verzija modpaka može biti nekompatibilan sa svetom, a odluku donosi vlasnik servera. Objavljena verzija je ono što dobijaju novi serveri i što nudimo već postavljenima; prethodne verzije ostaju u listi, pa možeš da ostaneš na njima ili da se vratiš na njih.
Kako ciklus izgleda
# 1. Create a version
curl -X POST https://millida.net/v2/hosting/packs/arcania/versions \
-H "X-Pack-Token: $PACK_TOKEN" -H "Content-Type: application/json" \
-d '{"label":"1.5.0","changelog":"Updated Create to 0.5.1, fixes crash on portals","minRamMb":10240}'
# 2. Upload the archive in chunks (32 MB each), addressing by offset
curl -X POST "https://millida.net/v2/hosting/packs/arcania/versions/1.5.0/archive?offset=0" \
-H "X-Pack-Token: $PACK_TOKEN" -H "Content-Type: application/octet-stream" \
--data-binary @part0.bin
# 3. Say the archive is finished, and publish after parsing
curl -X POST https://millida.net/v2/hosting/packs/arcania/versions/1.5.0/finish \
-H "X-Pack-Token: $PACK_TOKEN" -H "Content-Type: application/json" \
-d '{"archiveSha256":"<sha256 of archive>","publish":true}'
# 4. Wait for parsing
curl https://millida.net/v2/hosting/packs/arcania/versions/1.5.0 -H "X-Pack-Token: $PACK_TOKEN"
Verzija
| Polje | Tip | Čemu služi |
|---|---|---|
label | string do 40 | Broj verzije: latinična slova, cifre, tačka, crtica, donja crta. Nepromenljivo: isti label sa različitim fajlovima pretvara istragu o žalbi u nagađanje |
changelog | string do 4000 | Šta se promenilo — vlasnik servera ovo čita pre ažuriranja |
core, gameVersion | stringovi | Ako je konfiguracija servera prešla na drugi core ili verziju igre |
loaderBuild, javaVersion | stringovi | Fiksiranje build-a loadera i Java-e, ako verzija to zahteva |
minRamMb | broj | Donja granica memorije za baš tu verziju. Svako kome ne bude dovoljno videće razlog i neće izgubiti svoj svet |
archiveSha256 | hex 64 | Proveravamo pre parsiranja: bolje je odbiti arhivu koja nije stigla cela nego je raspakovati na pola |
Otpremanje
POST /v2/hosting/packs/{key}/versions/{label}/archive?offset=N, telo — deo .zip fajla, Content-Type: application/octet-stream. Deo do 32 MB, cela arhiva do 4 GB.
Deo se adresira po offsetu, a ne „dodaj na kraj”: deo prekinut na pola je već delimično sleteo u fajl, a ponovni pokušaj bi dodao iste bajtove još jednom — arhiva bi stigla tiho oštećena. Odgovor vraća uploadedBytes, što se koristi za nastavak otpremanja posle prekida.
Parsiranje
POST .../finish odgovara odmah (status: "processing"), dok parsiranje radi u pozadini: raspakivanje konfiguracije servera veličine gigabajta traje minutima. Stanje čitaj iz GET .../versions/{label}: processing → ready ili failed sa tekstom razloga u error.
Šta arhiva mora da prođe:
- to je server pak: nakon uklanjanja jednog omotača (
Server Files/i slično),mods/iliplugins/je u korenu. Klijentski pak na serveru daje prazan svet, pa ga odbijamo umesto da ga instaliramo; - nema
.., apsolutnih putanja ni Windows separatora u imenima unutar arhive; - nema lozinke, nema egzotičnih metoda kompresije (samo store i deflate);
- ograničenja: 60.000 fajlova, 12 GB raspakovano, odnos kompresije do 200×.
Neuspeh ne utiče na objavljenu verziju: tvoji klijenti nastavljaju da vrte prethodnu, a ti otpremiš ponovo. Nedovršene skice: najviše tri po konfiguraciji servera, napuštene se automatski čiste posle jednog dana.
Objavljivanje, vraćanje i uklanjanje
| Zahtev | Šta radi |
|---|---|
POST .../versions/{label}/publish | Čini verziju objavljenom. Ovako se radi i vraćanje: objavi prethodnu — novi serveri je opet dobijaju |
POST .../versions/{label}/archive-version | Uklanja verziju iz izbora. Oni koji je već imaju zadržavaju je |
PATCH .../versions/{label} | Menja opis već kreirane verzije: changelog i minRamMb. Fajlovi verzije su nepromenljivi, pa se core, loader i Java ne menjaju |
DELETE .../versions/{label} | Briše verziju zajedno sa njenim fajlovima. Ne možeš da obrišeš objavljenu verziju ni onu koja je na bar jednom serveru |
GET .../versions | Verzije dostupne za izbor (javno, bez tokena) |
GET .../versions/all | Sve tvoje, uključujući skice i neuspehe |
GET .../versions/rollout | Koliko je servera na kojoj verziji — vidiš kako se ažuriranje širi |
Objavljivanje prenosi core, verziju igre, fiksiranje loadera, Java-u i donju granicu memorije verzije u karticu konfiguracije servera: novi serveri to dobijaju bez ikakve dodatne akcije s tvoje strane.
Šta vlasnik servera vidi
U panelu, u bloku premijum konfiguracije servera: koja je verzija instalirana, koja je objavljena, tvoj changelog i lista verzija sa dugmetom „Prebaci”. Ažuriranje ne utiče na svet — zamenjuju se samo fajlovi konfiguracije servera, a pre zamene pravimo kopiju. Prilagođeni modovi, ako si ih dozvolio, moraće ponovo da se dodaju posle prebacivanja: konfiguracija servera se seli kao jedna celina, a pola stare verzije u mods/ znači pad pri pokretanju.
Ako vlasnikov paket ne može da izdrži verziju, prikazujemo je sa razlogom umesto da je sakrijemo: čovek treba da vidi šta mu treba, a ne da nagađa zašto se konfiguracija servera ne ažurira.
Stranica tvoje konfiguracije servera
Landing stranicu za svoju konfiguraciju servera gradiš sam u svom nalogu (profil → „Moje konfiguracije servera” → „Stranice konfiguracija servera”): prvi ekran, funkcionalnosti, snimci ekrana, pitanja i odgovori, tvoje boje. Paketi i lista verzija se popunjavaju našim podacima da ne zastare.
Gotova stranica živi na millida.net/sborka/<tvoja-adresa> — obična veb stranica, indeksirana od strane pretraživača i uključena u našu sitemap-u. Skicu ne vidi niko osim tebe.
Slike se otpremaju na istom mestu, u tvom nalogu: stranica se servira sa našeg domena, a njeni fajlovi se čuvaju kod nas — ako ti hosting padne, stranica ostaje netaknuta.
Stranice ne mogu da se menjaju preko API-ja: to je ekran, a ne rollout.
Kodovi odgovora
| Kod | Kada | Šta da radiš |
|---|---|---|
403 | Nevažeći token za izdavanje | Proveri X-Pack-Token. Token je vezan za jednu konfiguraciju servera: ne radi sa tuđim ključem |
404 | Konfiguracija servera je onemogućena, nije povezana sa izdavanjem ili ne postoji takva verzija | Piši nam |
400 | Datum expiresAt ne može da se parsira, loš label verzije, prazan ili preveliki deo | Pogledaj tekst greške |
409 | Verzija je već kreirana, već parsirana, objavljena ili instalirana na serverima | Labeli su nepromenljivi: objavi sledeću |
429 | Više od 30 zahteva u minuti (otpremanje — 600) | Šalji u serijama i šalji veće delove |
Kako da sve testiraš pre prodaje
Zatraži od nas par test kodova: izdaj kod preko API-ja, aktiviraj ga na svom serveru na našem hostingu, vidi šta je stiglo u webhook i šta prikazuje keys/status. Tako ćeš videti ceo put kupca pre nego što kroz njega prođe prvi kupac koji plaća.
