Коомдук тест: Ethereum боюнча купуялуулук жана масштабдуулук үчүн чечим

Blokcheyn адам жашоосунун көптөгөн тармактарын жакшыртууну убада кылган инновациялык технология болуп саналат. Ал реалдуу процесстерди жана өнүмдөрдү санариптик мейкиндикке өткөрүп берет, финансылык транзакциялардын ылдамдыгын жана ишенимдүүлүгүн камсыздайт, алардын баасын төмөндөтөт, ошондой эле борбордон ажыратылган тармактарда акылдуу контракттарды колдонуу менен заманбап DAPP тиркемелерин түзүүгө мүмкүндүк берет.

Блокчейндин көптөгөн артыкчылыктарын жана ар түрдүү колдонмолорун эске алганда, бул келечектүү технология али ар бир тармакта өз жолун жасай электиги таң калыштуу көрүнүшү мүмкүн. Көйгөй заманбап борборлоштурулган блокчейндердин масштабдуулугунун жоктугунда. Ethereum секундасына 20га жакын транзакцияларды иштетет, бул азыркы динамикалык бизнестин муктаждыктарын канааттандыруу үчүн жетиштүү эмес. Ошол эле учурда, блокчейн технологиясын колдонгон компаниялар Ethereumдан баш тартуудан тартынышат, анткени анын хакерликтен жана тармактын бузулуусунан корголгон жогорку даражасы бар.

Блокчейнде борбордон ажыратууну, коопсуздукту жана масштабдуулукту камсыз кылуу үчүн, ошентип, Өнүгүү тобунун масштабдуулугу трилеммасын чечет. Мүмкүнчүлүк Plasma Cash, акылдуу келишимден жана Node.js негизиндеги жеке тармактан турган туунду чынжырды түздү, ал мезгил-мезгили менен өз абалын тамыр чынжырына (Ethereum) өткөрүп берет.

Коомдук тест: Ethereum боюнча купуялуулук жана масштабдуулук үчүн чечим

Plasma Cashдагы негизги процесстер

1. Колдонуучу акылдуу контракт функциясын "депозит" деп атайт, ага Plasma Cash белгисине салгысы келген ETH суммасын берет. Акылдуу келишим функциясы токенди жаратат жана ал жөнүндө окуяны жаратат.

2. Акылдуу контракт окуяларына жазылган Plasma Cash түйүндөрү депозитти түзүү жөнүндө окуяны алышат жана бассейнге белги түзүү жөнүндө транзакцияны кошот.

3. Мезгил-мезгили менен атайын Plasma Cash түйүндөрү бассейнден бардык транзакцияларды (1 миллионго чейин) алып, алардан блокту түзөт, Merkle дарагын жана ошого жараша хэшти эсептешет. Бул блок текшерүү үчүн башка түйүндөргө жөнөтүлөт. Түйүндөр Merkle хэшинин жарактуу экендигин жана транзакциялардын жарактуу экендигин текшерет (мисалы, токенди жөнөтүүчү анын ээсиби). Блокту текшергенден кийин түйүн акылдуу контракттын `submitBlock` функциясын чакырат, ал блоктун номерин жана Merkle хэштин четине чынжырга сактайт. Акылдуу келишим блоктун ийгиликтүү кошулушун көрсөткөн окуяны жаратат. Транзакциялар бассейнден алынып салынат.

4. Блок тапшыруу окуясын алган түйүндөр блокко кошулган транзакцияларды колдоно башташат.

5. Кайсы бир учурда, токендин ээси (же ээси эмес) аны Plasma Cashтан алууну каалайт. Бул үчүн, ал `startExit` функциясын чакырып, ага токендеги акыркы 2 транзакциялар жөнүндө маалыматты өткөрүп, анын ээси экендигин тастыктайт. акылдуу келишим, Merkle хэш колдонуп, блоктордун бүтүмдөрдүн болушун текшерет жана эки жумадан кийин пайда болгон алуу үчүн Токенди жөнөтөт.

6. Токенди алуу операциясы бузуулар менен болгон болсо (токен алуу процедурасы башталгандан кийин сарпталган же токен чыгарууга чейин башка бирөөнүн мүлкү болгон), токендин ээси эки жуманын ичинде алып коюуну жокко чыгара алат.

Коомдук тест: Ethereum боюнча купуялуулук жана масштабдуулук үчүн чечим

Купуялык эки жол менен ишке ашат

1. Түпкү чынжыр бала чынжырдын ичинде түзүлгөн жана жөнөтүлгөн транзакциялар жөнүндө эч нерсе билбейт. Plasma Cashдан ETHди ким салганы жана чыгарганы тууралуу маалымат ачык бойдон калууда.

2. Бала чынжыр zk-SNARKs аркылуу жашыруун транзакцияларды жүргүзүүгө мүмкүндүк берет.

Технологиялык стек

  • NodeJS
  • Redis
  • Etherium
  • Sild

тестирлөө

Plasma Cash иштеп чыгууда, биз системанын ылдамдыгын сынап көрдүк жана төмөнкү натыйжаларды алдык:

  • бассейнге секундасына 35 000 транзакцияга чейин кошулат;
  • бир блокто 1 000 000ге чейин транзакцияларды сактоого болот.

Тесттер төмөнкү 3 серверде өткөрүлдү:

1. Intel Core i7-6700 Quad-Core Skylake, анын ичинде. NVMe SSD – 512 ГБ, 64 ГБ DDR4 RAM
3 текшерүүчү Plasma Cash түйүндөрү көтөрүлдү.

2. AMD Ryzen 7 1700X Octa-Core “Summit Ridge” (Zen), SATA SSD – 500 ГБ, 64 ГБ DDR4 RAM
Ropsten testnet ETH түйүнү көтөрүлдү.
3 текшерүүчү Plasma Cash түйүндөрү көтөрүлдү.

3. Intel Core i9-9900K Octa-Core, анын ичинде. NVMe SSD – 1 ТБ, 64 ГБ DDR4 RAM
1 Plasma Cash берүү түйүнү көтөрүлдү.
3 текшерүүчү Plasma Cash түйүндөрү көтөрүлдү.
Plasma Cash тармагына транзакцияларды кошуу үчүн тест башталды.

Бардыгы: Жеке тармактагы 10 Plasma Cash түйүндөрү.

Тест 1

Бир блок үчүн 1 миллион транзакциянын чеги бар. Демек, 1 миллион транзакция 2 блокко түшөт (себеби, система транзакциялардын бир бөлүгүн алып, жөнөтүлүп жатканда тапшырат).


Баштапкы абалы: акыркы блок №7; 1 миллион транзакциялар жана токендер маалымат базасында сакталат.

00:00 — транзакцияларды түзүүнүн башталышы
01:37 - 1 миллион транзакция түзүлүп, түйүнгө жөнөтүү башталды
01:46 — тапшыруу түйүнү бассейнден 240 миң транзакцияларды алып, №8 блокту түзөт. Ошондой эле 320 секунданын ичинде бассейнге 10 миң транзакция кошуларын көрөбүз
01:58 — №8 блокко кол коюлуп, валидацияга жөнөтүлдү
02:03 — №8 блок текшерилди жана акылдуу келишимдин `submitBlock` функциясы Merkle хэш жана блок номери менен чакырылат
02:10 — демо скрипт иштеп бүттү, ал 1 секунданын ичинде 32 миллион транзакцияны жөнөттү
02:33 - түйүндөр №8 блок тамыр чынжырына кошулганы тууралуу маалыматты ала башташты жана 240 миң транзакцияларды жасай башташты
02:40 - №240 блокто болгон 8 миң транзакциялар бассейнден алынып салынды
02:56 — тапшыруу түйүнү бассейнден калган 760 миң транзакцияны алып, Merkle хэшти жана №9 кол коюу блогун эсептей баштады
03:20 - бардык түйүндөр 1 миллион 240 миң транзакцияларды жана токендерди камтыйт
03:35 — №9 блокко кол коюлуп, башка түйүндөргө валидацияга жөнөтүлдү
03:41 - тармак катасы кетти
04:40 — №9 блоктун валидациясын күтүү убактысы бүттү
04:54 — тапшыруу түйүнү бассейнден калган 760 миң транзакцияны алып, Merkle хэшти жана №9 кол коюу блогун эсептей баштады
05:32 — №9 блокко кол коюлуп, башка түйүндөргө валидацияга жөнөтүлдү
05:53 — №9 блок валидацияланып, тамыр чынжырына жөнөтүлдү
06:17 - түйүндөр №9 блок тамыр чынжырына кошулганын жана 760 миң транзакцияларды жүргүзө баштагандыгы жөнүндө маалымат ала башташты
06:47 — бассейн №9 блоктогу транзакциялардан тазаланды
09:06 - бардык түйүндөр 2 миллион транзакцияларды жана токендерди камтыйт

Тест 2

Бир блок үчүн 350 миң чеги бар. Натыйжада бизде 3 блок бар.


Баштапкы абалы: акыркы блок №9; 2 миллион транзакциялар жана токендер маалымат базасында сакталат

00:00 — транзакцияны түзүү скрипти буга чейин ишке киргизилген
00:44 - 1 миллион транзакция түзүлүп, түйүнгө жөнөтүү башталды
00:56 — тапшыруу түйүнү бассейнден 320 миң транзакцияларды алып, №10 блокту түзөт. Ошондой эле 320 секунданын ичинде бассейнге 10 миң транзакция кошуларын көрөбүз
01:12 — №10 блокко кол коюлуп, валидациялоо үчүн башка түйүндөргө жөнөтүлөт
01:18 — демо скрипт иштеп бүттү, ал 1 секунданын ичинде 34 миллион транзакцияны жөнөттү
01:20 — №10 блок валидацияланып, тамыр чынжырына жөнөтүлдү
01:51 - бардык түйүндөр №10 блок кошулган тамыр чынжырынан маалымат алышты жана 320 миң транзакцияларды колдоно башташат
02:01 - бассейн №320 блокко кошулган 10 миң транзакция үчүн тазаланды
02:15 — тапшыруу түйүнү бассейнден 350 миң транзакцияларды алып, №11 блокту түзөт
02:34 — №11 блокко кол коюлуп, валидациялоо үчүн башка түйүндөргө жөнөтүлдү
02:51 — №11 блок валидацияланып, тамыр чынжырына жөнөтүлдү
02:55 — акыркы түйүн №10 блоктогу транзакцияларды аяктады
10:59 — №9 блокту тапшыруу менен транзакция тамыр чынжырында абдан көп убакытты талап кылды, бирок ал аяктады жана бардык түйүндөр бул тууралуу маалымат алып, 350 миң транзакцияларды аткара башташты.
11:05 - бассейн №320 блокко кошулган 11 миң транзакция үчүн тазаланды
12:10 - бардык түйүндөр 1 миллион 670 миң транзакцияларды жана токендерди камтыйт
12:17 — тапшыруу түйүнү бассейнден 330 миң транзакцияларды алып, №12 блокту түзөт
12:32 — №12 блокко кол коюлуп, валидациялоо үчүн башка түйүндөргө жөнөтүлдү
12:39 — №12 блок валидацияланып, тамыр чынжырына жөнөтүлдү
13:44 - бардык түйүндөр №12 блок кошулган тамыр чынжырынан маалымат алышты жана 330 миң транзакцияларды колдоно башташат
14:50 - бардык түйүндөр 2 миллион транзакцияларды жана токендерди камтыйт

Тест 3

Биринчи жана экинчи серверлерде бир текшерүү түйүн тапшыруу түйүнү менен алмаштырылган.


Баштапкы абалы: акыркы блок №84; Маалыматтар базасында сакталган 0 транзакциялар жана токендер

00:00 — ар бири 3 миллион транзакцияларды түзүүчү жана жөнөтүүчү 1 скрипт ишке киргизилди
01:38 — 1 миллион транзакция түзүлүп, №3 түйүнгө жөнөтүү башталды
01:50 — тапшыруу №3 түйүн бассейнден 330 миң транзакцияны алып, №85 (f21) блогун түзөт. Ошондой эле 350 секунданын ичинде бассейнге 10 миң транзакция кошулганын көрөбүз
01:53 — 1 миллион транзакция түзүлүп, №1 түйүнгө жөнөтүү башталды
01:50 — тапшыруу №3 түйүн бассейнден 330 миң транзакцияны алып, №85 (f21) блогун түзөт. Ошондой эле 350 секунданын ичинде бассейнге 10 миң транзакция кошулганын көрөбүз
02:01 — тапшыруу №1 түйүн бассейнден 250 миң транзакцияларды алып, №85 (65e) блогун түзөт
02:06 — №85 блок (f21) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
02:08 — 3 секундда 1 миллион транзакция жөнөткөн №30 сервердин демо-скрипти иштеп бүттү
02:14 — №85 блок (f21) валидацияланып, тамыр чынжырына жөнөтүлдү
02:19 — блок №85 (65е) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
02:22 — 1 миллион транзакция түзүлүп, №2 түйүнгө жөнөтүү башталды
02:27 — блок №85 (65e) валидацияланган жана тамыр чынжырына жөнөтүлгөн
02:29 — тапшыруу №2 түйүн бассейнден 111855 транзакцияны алды жана №85 (256) блогун түзөт.
02:36 — блок №85 (256) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
02:36 — 1 секундда 1 миллион транзакция жөнөткөн №42.5 сервердин демо-скрипти иштеп бүттү
02:38 — блок No85 (256) валидацияланып, тамыр чынжырына жөнөтүлдү
03:08 — №2 сервер скрипти иштеп бүттү, ал 1 секунданын ичинде 47 миллион транзакция жөнөттү
03:38 - бардык түйүндөр №85 (f21), №86(65e), №87(256) блоктору кошулган жана 330k, 250k, 111855 транзакцияларды колдоно баштаган тамыр чынжырынан маалымат алышты.
03:49 - бассейн №330 (f250), №111855(85e), №21(86) блокторуна кошулган 65k, 87k, 256 транзакцияларда тазаланды.
03:59 — №1 тапшыруу түйүнү бассейнден 888145 88 транзакцияларды кабыл алды жана №214 (2) блогун түзөт, №750 тапшыруу түйүнү бассейнден 88 миң транзакцияларды алды жана №50 (3а) блогун түзөт, №670 тапшыруу түйүнү 88 миң транзакцияларды алды бассейн жана формалар блогу №3 (dXNUMXb)
04:44 — блок №88 (d3b) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
04:58 — блок №88 (214) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
05:11 — блок №88 (50а) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
05:11 — блок №85 (d3b) валидацияланган жана тамыр чынжырына жөнөтүлгөн
05:36 — блок No85 (214) валидацияланып, тамыр чынжырына жөнөтүлдү
05:43 - бардык түйүндөр №88 (d3b), №89(214) блоктору кошулган жана 670k, 750k транзакцияларды колдоно баштаган тамыр чынжырынан маалымат алышты.
06:50 — байланыш үзгүлтүккө учурагандыктан, №85 блок (50а) текшерүүдөн өткөн жок
06:55 — тапшыруу №2 түйүн бассейнден 888145 транзакцияны кабыл алды жана №90 (50а) блогун түзөт
08:14 — блок №90 (50а) кол коюлган жана валидациялоо үчүн башка түйүндөргө жөнөтүлгөн
09:04 — №90 блок (50а) валидацияланып, тамыр чынжырына жөнөтүлдү
11:23 - бардык түйүндөр №90 (50а) блок кошулган тамыр чынжырынан маалымат алып, 888145 транзакцияны колдоно башташат. Ошол эле учурда №3 сервер №88 (d3b), №89(214) блокторунан транзакцияларды колдонгон.
12:11 - бардык бассейндер бош
13:41 — №3 сервердин бардык түйүндөрүндө 3 миллион транзакциялар жана токендер бар
14:35 — №1 сервердин бардык түйүндөрүндө 3 миллион транзакциялар жана токендер бар
19:24 — №2 сервердин бардык түйүндөрүндө 3 миллион транзакциялар жана токендер бар

Тоскоолдуктар

Plasma Cashты иштеп чыгууда биз төмөнкү көйгөйлөргө туш болдук, аларды акырындык менен чечтик жана чечип жатабыз:

1. Ар кандай система функцияларынын өз ара аракеттенүүсүндө конфликт. Мисалы, бассейнге транзакцияларды кошуу функциясы блокторду тапшыруу жана валидациялоо ишин бөгөттөгөн жана тескерисинче, ылдамдыктын төмөндөшүнө алып келген.

2. Маалыматтарды өткөрүүгө кеткен чыгымдарды азайтып, көп сандагы транзакцияларды кантип жөнөтүү керектиги дароо ачык-айкын болгон жок.

3. Жогорку натыйжаларга жетүү үчүн маалыматтарды кантип жана кайда сактоо керектиги так айтылган эмес.

4. 1 миллион транзакциялар менен блоктун көлөмү болжол менен 100 Мб ээлей тургандыктан, түйүндөрдүн ортосундагы тармакты кантип уюштуруу керектиги түшүнүксүз болгон.

5. Жалгыз жиптүү режимде иштөө узун эсептөөлөр болгондо (мисалы, Merkle дарагын куруу жана анын хэштерин эсептөө) түйүндөрдүн ортосундагы байланышты үзөт.

Мунун баарын кантип чечтик?

Plasma Cash түйүнүнүн биринчи версиясы бир эле учурда баарын жасай алган комбайндын бир түрү болгон: транзакцияларды кабыл алуу, блокторду тапшыруу жана текшерүү жана маалыматтарга жетүү үчүн API менен камсыз кылуу. NodeJS түпкүлүгүндө бир жиптүү болгондуктан, оор Merkle дарагын эсептөө функциясы транзакцияны кошуу функциясын бөгөттөгөн. Бул көйгөйдү чечүүнүн эки вариантын көрдүк:

1. Бир нече NodeJS процесстерин ишке киргизиңиз, алардын ар бири белгилүү бир функцияларды аткарат.

2. Worker_threads колдонуңуз жана коддун бир бөлүгүнүн аткарылышын жиптерге жылдырыңыз.

Натыйжада, биз бир эле учурда эки вариантты тең колдондук: логикалык жактан бир түйүндү өзүнчө, бирок ошол эле учурда синхрондуу иштей турган 3 бөлүккө бөлдүк.

1. Бассейнге транзакцияларды кабыл алган жана блокторду түзүүчү тапшыруу түйүнү.

2. Түйүндөрдүн жарактуулугун текшерген текшерүү түйүнү.

3. API түйүнү - маалыматтарга жетүү үчүн API камсыз кылат.

Бул учурда, сиз cli аркылуу unix розетка аркылуу ар бир түйүнгө туташа аласыз.

Биз Merkle дарагын эсептөө сыяктуу оор операцияларды өзүнчө жипке жылдырдык.

Ошентип, биз бардык Plasma Cash функцияларынын бир эле учурда жана мүчүлүштүктөрсүз нормалдуу иштешине жетиштик.

Система иштей баштагандан кийин, биз ылдамдыкты сынай баштадык жана тилекке каршы, канааттандырарлык эмес жыйынтыктарды алдык: секундасына 5 000 транзакция жана блок боюнча 50 000 транзакцияга чейин. Эмне туура эмес ишке ашырылганын түшүнүшүм керек болчу.

Баштоо үчүн, системанын эң жогорку мүмкүнчүлүгүн билүү үчүн Plasma Cash менен байланыш механизмин сынай баштадык. Биз буга чейин Plasma Cash түйүнү unix розетка интерфейсин камсыз кылат деп жазганбыз. Башында ал текстке негизделген. json объекттери `JSON.parse()` жана `JSON.stringify()` аркылуу жөнөтүлгөн.

```json
{
  "action": "sendTransaction",
  "payload":{
    "prevHash": "0x8a88cc4217745fd0b4eb161f6923235da10593be66b841d47da86b9cd95d93e0",
    "prevBlock": 41,
    "tokenId": "57570139642005649136210751546585740989890521125187435281313126554130572876445",
    "newOwner": "0x200eabe5b26e547446ae5821622892291632d4f4",
    "type": "pay",
    "data": "",
    "signature": "0xd1107d0c6df15e01e168e631a386363c72206cb75b233f8f3cf883134854967e1cd9b3306cc5c0ce58f0a7397ae9b2487501b56695fe3a3c90ec0f61c7ea4a721c"
  }
}
```

Биз мындай объекттердин өтүү ылдамдыгын ченедик жана секундасына ~ 130k таптык. Биз json менен иштөө үчүн стандарттуу функцияларды алмаштырууга аракет кылдык, бирок аткаруу жакшырган жок. V8 кыймылдаткычы бул операциялар үчүн жакшы оптималдаштырылган болушу керек.

Биз класстар аркылуу транзакциялар, токендер жана блоктор менен иштедик. Мындай класстарды түзүүдө көрсөткүчтөр 2 эсеге төмөндөдү, бул OOP бизге ылайыктуу эмес экенин көрсөтүп турат. Мен бардыгын таза функционалдык мамилеге кайра жазууга туура келди.

Маалыматтар базасына жазуу

Башында, Redis биздин талаптарды канааттандырган эң жемиштүү чечимдердин бири катары маалыматтарды сактоо үчүн тандалган: ачкыч-нарыкты сактоо, хэш таблицалар, топтомдор менен иштөө. Биз редис-бенчмаркти ишке киргизип, 80 түтүк режиминде секундасына ~1 миң операция алдык.

Жогорку аткаруу үчүн биз Redisди жакшыраак жөндөдүк:

  • Unix розетка байланышы орнотулду.
  • Биз абалды дискке сактоону өчүрүп койдук (ишенимдүүлүк үчүн сиз репликаны орнотуп, өзүнчө Redisде дискке сактасаңыз болот).

Redisде бассейн хэш таблицасы болуп саналат, анткени биз бир суроодо бардык транзакцияларды чыгарып, транзакцияларды бирден жок кыла алышыбыз керек. Биз кадимки тизмени колдонууга аракет кылдык, бирок бүт тизмени түшүргөндө ал жайыраак.

Стандарттык NodeJSти колдонууда Redis китепканалары секундасына 18к транзакцияга жетишти. Ылдамдыгы 9 эсе азайды.

Эталондук көрсөткүч бизге мүмкүнчүлүктөр 5 эсе чоң экенин көрсөткөндүктөн, биз оптималдаштырууну баштадык. Биз китепкананы ioredisге өзгөрттүк жана секундасына 25к көрсөткүчкө ээ болдук. `hset` буйругун колдонуп транзакцияларды бирден коштук. Ошентип, биз Редисте көптөгөн суроолорду жаратып жаттык. Транзакцияларды партияларга бириктирип, аларды бир `hmset` буйругу менен жөнөтүү идеясы пайда болгон. Натыйжада секундасына 32к.

Төмөндө сүрөттөп бере турган бир нече себептерден улам, биз `Buffer` аркылуу берилиштер менен иштейбиз жана эгер сиз аны жазуудан мурун текстке (`buffer.toString('hex')) айландырсаңыз, кошумча ала аласыз. аткаруу. Ошентип, ылдамдыгы секундасына 35k чейин жогорулаган. Учурда биз андан аркы оптималдаштырууну токтотууну чечтик.

Биз бинардык протоколго өтүүгө туура келди, анткени:

1. Система көбүнчө хэштерди, кол тамгаларды ж.б. эсептейт жана бул үчүн `Буфердеги маалыматтар керек.

2. Кызматтардын ортосунда жөнөтүлгөндө, бинардык маалыматтар тексттен азыраак болот. Мисалы, 1 миллион транзакциялары бар блокту жөнөтүүдө тексттеги маалыматтар 300 мегабайттан ашыкты ээлей алат.

3. Дайыма маалыматтарды трансформациялоо майнаптуулукка таасирин тийгизет.

Ошондуктан, биз сонун «экилик-маалымат» китепканасынын негизинде иштелип чыккан маалыматтарды сактоо жана берүү үчүн өзүбүздүн экилик протоколубузду негиз катары алдык.

Натыйжада, биз төмөнкү маалымат структураларын алдык:

-Бүтүм

  ```json
  {
    prevHash: BD.types.buffer(20),
    prevBlock: BD.types.uint24le,
    tokenId: BD.types.string(null),
    type: BD.types.uint8,
    newOwner: BD.types.buffer(20),
    dataLength: BD.types.uint24le,
    data: BD.types.buffer(({current}) => current.dataLength),
    signature: BD.types.buffer(65),
    hash: BD.types.buffer(32),
    blockNumber: BD.types.uint24le,
    timestamp: BD.types.uint48le,
  }
  ```

— Токен

  ```json
  {
    id: BD.types.string(null),
    owner: BD.types.buffer(20),
    block: BD.types.uint24le,
    amount: BD.types.string(null),
  }
  ```

— Блок

  ```json
  {
    number: BD.types.uint24le,
    merkleRootHash: BD.types.buffer(32),
    signature: BD.types.buffer(65),
    countTx: BD.types.uint24le,
    transactions: BD.types.array(Transaction.Protocol, ({current}) => current.countTx),
    timestamp: BD.types.uint48le,
  }
  ```

Кадимки `BD.encode(block, Protocol).slice();` жана `BD.decode(buffer, Protocol)` командалары менен биз Redisде сактоо же башка түйүнгө жөнөтүү жана кайра алуу үчүн маалыматтарды "Буферге" айландырабыз. маалыматтар кайра.

Бизде ошондой эле кызматтардын ортосунда маалыматтарды өткөрүү үчүн 2 бинардык протоколдор бар:

— Unix розеткасы аркылуу Plasma Node менен өз ара аракеттенүү протоколу

  ```json
  {
    type: BD.types.uint8,
    messageId: BD.types.uint24le,
    error: BD.types.uint8,
    length: BD.types.uint24le,
    payload: BD.types.buffer(({node}) => node.length)
  }
  ```

мында:

  • `тип` — аткарыла турган иш-аракет, мисалы, 1 — sendTransaction, 2 — getTransaction;
  • `пайдалуу жүк` — тиешелүү функцияга өтүшү керек болгон маалыматтар;
  • `messageId` — жоопту аныктоо үчүн билдирүү ID.

— Түйүндөр ортосундагы өз ара аракеттенүү протоколу

  ```json
  {
    code: BD.types.uint8,
    versionProtocol: BD.types.uint24le,
    seq: BD.types.uint8,
    countChunk: BD.types.uint24le,
    chunkNumber: BD.types.uint24le,
    length: BD.types.uint24le,
    payload: BD.types.buffer(({node}) => node.length)
  }
  ```

мында:

  • `код` — билдирүү коду, мисалы 6 — PREPARE_NEW_BLOCK, 7 — BLOCK_VALID, 8 — BLOCK_COMMIT;
  • `versionProtocol` — протоколдун версиясы, анткени ар кандай версиялары бар түйүндөр тармакта көтөрүлүшү мүмкүн жана алар башкача иштеши мүмкүн;
  • `seq` — билдирүү идентификатору;
  • `countChunk` и `chunkNumber` чоң билдирүүлөрдү бөлүү үчүн зарыл;
  • `узундугу` и `пайдалуу жүк` узундугу жана маалыматтардын өзү.

Биз маалыматтарды алдын ала тергендиктен, акыркы система Ethereum `rlp` китепканасынан алда канча ылдамыраак. Тилекке каршы, биз мындан азырынча баш тарта алган жокпуз, анткени келечекте жасай турган акылдуу келишимди аягына чыгаруу зарыл.

Эгерде биз ылдамдыкка жетише алсак 35 000 секундасына транзакциялар, биз да аларды оптималдуу убакытта иштеп чыгышыбыз керек. Болжолдуу блок түзүү убактысы 30 секундду талап кылгандыктан, биз блокко киргизишибиз керек 1 000 000 транзакциялар, бул көбүрөөк жөнөтүүнү билдирет 100 МБ маалымат.

Башында биз түйүндөрдүн ортосунда байланышуу үчүн `ethereumjs-devp2p` китепканасын колдонгонбуз, бирок ал мынчалык көп маалыматтарды иштете алган жок. Натыйжада, биз `ws` китепканасын колдондук жана websocket аркылуу бинардык маалыматтарды жөнөтүүнү конфигурацияладык. Албетте, биз чоң маалымат пакеттерин жөнөтүүдө да көйгөйлөргө туш болдук, бирок биз аларды бөлүктөргө бөлдүк жана азыр бул көйгөйлөр жок.

Ошондой эле Merkle дарагын түзүү жана хэшти эсептөө 1 000 000 транзакциялар жөнүндө талап кылат 10 секундалык үзгүлтүксүз эсептөө. Бул убакыттын ичинде бардык түйүндөр менен байланыш үзүлгөнгө жетишет. Бул эсепти өзүнчө жипке жылдыруу чечими кабыл алынды.

корутундулар:

Чынында, биздин ачылыштар жаңы эмес, бирок эмнегедир көптөгөн эксперттер иштеп жатканда алар жөнүндө унутуп коюшат.

  • Объектке багытталган программалоонун ордуна Функционалдык программалоону колдонуу өндүрүмдүүлүктү жогорулатат.
  • Монолит жемиштүү NodeJS системасы үчүн кызмат архитектурасынан да жаман.
  • Оор эсептөө үчүн `worker_threads` колдонуу системанын жооп берүү жөндөмдүүлүгүн жакшыртат, айрыкча киргизүү/чыгаруу операциялары менен иштөөдө.
  • unix розеткасы http сурамдарына караганда туруктуураак жана ылдамыраак.
  • Эгерде сизге чоң маалыматтарды тармак аркылуу тез өткөрүп берүү керек болсо, анда веб-розеткаларды колдонуу жана экилик берилиштерди жөнөтүү жакшыраак, алар келбесе кайра жөнөтүлө турган, анан бир билдирүүгө бириктирилген бөлүктөргө бөлүнгөн.

Сиздерди конокко чакырабыз GitHub долбоор: https://github.com/opporty-com/Plasma-Cash/tree/new-version

Макаланы биргелешип жазган Александр Нашиван, улук иштеп чыгуучу Clever Solution Inc.

Source: www.habr.com

Комментарий кошуу