Jednog jutra naišao sam na članak o na blockchain platformi Waves.
Cjelokupna slika bila je jasna, ali način konkretne implementacije nije. Kakvi su to kodovi, potpisi, što, kamo, zašto?
Nakon nekoliko konzultacija s autorom orakula, uspjeli smo spojiti logiku izvlačenja (implementiranu u PHP-u) s algoritmom za generiranje slučajnog broja.
- Na početku turnira/kruga tražimo od orakula prvi dio koda (R-code).
U tom trenutku nema informacija ni o broju igrača, ni o broju nagradnih mjesta, ni o iznosu nagradnih isplata, pa čak ni o postojanju lutrije. Orakl putem transakcije izdaje osobni slučajni kod koji se može koristiti samo jednom i samo od strane onoga tko ga je zatražio. Usput, R-code se može 'nabaviti' (misli se na trošak transakcije zahtjeva + naknada orakulu za odgovor, to je otprilike $0.015 po trenutnom tečaju, a sam kod se izdaje besplatno) unaprijed nekoliko puta, kako ne bismo kasnije čekali odgovor transakcije. Napravio sam mali redovno dopunjeni buffer u bazi podataka.
- Turnir traje standardno 60 blokova blockchaina Waves platforme, što je trenutno otprilike 1 sat. Turnir se smatra održanim i zatvorenim ako nakon 60 blokova ima najmanje dva kupona, inače se vrijeme trajanja turnira produžava za sljedećih 60 blokova.
- Odmah nakon zatvaranja turnira formiramo i šaljemo datumsku transakciju (za koju također plaćamo proviziju od otprilike $0.005), po potrebi – nekoliko, koja bilježi sve uvjete izvlačenja i uređen popis igrača (kupona) iz kojeg trebamo odabrati pobjednike.
- U ovom trenutku već imamo prvi dio koda (R-code) plus ID datum transakcije (TXID). Šaljemo ih orakulu na potpis u obliku konkatenacije (R-code + TXID), ponovno plaćamo proviziju + naknadu. Orakl provjerava primljene podatke u vezi s jedinstvenošću i pripadnošću, a zatim nam šalje drugi dio koda (S-code) u formatu sha256, koji je polazna točka za generator slučajnih brojeva.
- Da bismo dobili slučajni broj koji će označavati redni broj dobitničkog kupona, pretvaramo S-kod iz binarnih podataka sha256 u heksadecimalnu (HEX) reprezentaciju. Zatim, iz dobijene HEX string, dobijamo broj. Dobijamo ostatak deljenja dobijenog broja s brojem kupona (all_tickets) i dodajemo 1 kao rezultat (da bismo dobili broj od 1 do all_tickets). Na kraju dobijamo redni broj pobednika.
- Ako prema pravilima žrebanja ima više dobitnika, ponavljamo prethodne operacije u broju koji odgovara broju nagradnih mesta. Pri tome svaki put uklanjamo iz liste kupon koji je već pobedio i smanjujemo all_tickets za 1, a umesto S-koda navodimo prethodno dobijeni broj.
Razmotrimo konkretan pravi primer, turnir broj 119:
Ukupno 7 kupona (all_tickets)
Cena kupona 50 novčića (Bet)
Igrački zbir 10% (Fee)
Prema pravilima lutrije, 30% ide u nagrade, tj. u ovom slučaju 2 kupona treba da dobiju nagradu, čija se veličina računa po formuli (Bet * all_tickets - Fee) / 2.
1. Dobijamo R-kod:
2. Nakon zatvaranja turnira imamo listu kupona u obliku parova: broj + adresu (adresu novčanika sa koje je izvršena uplata za učešće u turniru). Primećujemo da se adrese mogu ponavljati, to znači da je jedan učesnik kupio više kupona na jednom turniru, što nije zabranjeno pravilima.
Poslali smo datum transakcije:
3. Zatražili smo S-kod: sa komentarom (R-kod + TXID):
RdbAiAhKhveAtR4eyTKq75noMxdcEoxbE6BvojJjM13VE 82JTMzhHM5xEA2fQ9Qscd5QAJU3DAd8nShLjdVHTer5S
4. Dobijamo S-kod:
5. Odredili smo pobednike.
6.
Kao rezultat imamo u blokčejnu korak-po-korak beleženje procesa žrebanja nagrada s mogućnošću da ga proverimo u bilo kojem trenutku. Manipulacija rezultatima od strane organizatora gotovo je nemoguća, barem neće biti moguće to učiniti neprimetno.
odredite pobjednika br. 1
Sve_karte:
Indeks: 1 Karte:139
Indeks: 2 Karte:141
Indeks: 3 Karte:143
Indeks: 4 Karte:145
Indeks: 5 Karte:147
Indeks: 6 Karte:149
Indeks: 7 Karte:151
1. bin -> hex ( bin2hex(sha256(S-kod)) ): Ri89jHB4UXZDXY6gT1m4LBDXGMTaYzHozMk4nxiuqVXdC -> 0xdaf5802953dcb27f89972e38e8900b898733f6a613e6e1c6c5491362c1832596
2. hex -> gmp broj: 0xdaf5802953dcb27f89972e38e8900b898733f6a613e6e1c6c5491362c1832596 -> 99037963059744689166154019807924045947962565922868104113173478160267437352342
3. gmp -> modulo (mod=7): 99037963059744689166154019807924045947962565922868104113173478160267437352342 -> 4
4. modulo -> karta: 4 -> 145
odredite pobjednika br. 2
Sve_karte:
Indeks: 1 Karte:139
Indeks: 2 Karte:141
Indeks: 3 Karte:143
Indeks: 4 Karte:147
Indeks: 5 Karte:149
Indeks: 6 Karte:151
1. bin -> hex ( bin2hex(sha256(prethodni hex)) ): daf5802953dcb27f89972e38e8900b898733f6a613e6e1c6c5491362c1832596 -> 0x9560e77525e9ea2db92cdb8484dc52046ccafac7c719b8859ff55f0eb92834a0
2. hex -> gmp broj: 0x9560e77525e9ea2db92cdb8484dc52046ccafac7c719b8859ff55f0eb92834a0 -> 67565829218838067182838043983962684143266386786567427968312120473742580659360
3. gmp -> modulo (mod=6): 67565829218838067182838043983962684143266386786567427968312120473742580659360 -> 1
4. modulo -> karta: 1 -> 139
Kraj.Izvor: habr.com
