عميل اختبار TON (شبكة Telegram Open Network) ولغة Fift الجديدة للعقود الذكية

منذ أكثر من عام ، أصبح معروفًا عن خطط برنامج Telegram messenger لإطلاق شبكة Telegram Open Network الخاصة بها . ثم أصبحت وثيقة تقنية ضخمة متوفرة ، والتي من المفترض أن كتبها نيكولاي دوروف ووصفت هيكل الشبكة المستقبلية. بالنسبة لأولئك الذين فاتتهم ، أوصي بقراءة إعادة سرد هذه الوثيقة ( الجزء 1 ، الجزء 2 ؛ الجزء الثالث ، للأسف ، ما زال يجمع الغبار في نسخ مسودة).


منذ ذلك الحين ، لم تكن هناك أخبار مهمة حول حالة تطوير TON ، حتى قبل يومين (في إحدى القنوات غير الرسمية ) رابط للصفحة https://test.ton.org/download.html ظهر ، حيث:


ton-test-liteclient-full.tar.xz - مصادر العميل الخفيف لشبكة اختبار TON ؛
ton-lite-client-test1.config.json - ملف التكوين للاتصال بشبكة اختبار ؛
AD README - معلومات حول بناء العميل وبدء تشغيله ؛
OW HOWTO - إرشادات خطوة بخطوة حول إنشاء عقد ذكي باستخدام عميل ؛
ton.pdf - وثيقة محدثة (بتاريخ 2 مارس 2019) مع نظرة عامة تقنية على شبكة TON ؛
tvm.pdf - الوصف التقني لـ TVM (TON Virtual Machine ، TON Virtual machine) ؛
bl tblkch.pdf - الوصف الفني لسلسلة TON blockchain ؛
ift fiftbase.pdf - وصف للغة Fift الجديدة ، المصممة لإنشاء عقود ذكية في TON.


أكرر ، لم يكن هناك تأكيد رسمي للصفحة وجميع هذه الوثائق من قبل Telegram ، ولكن حجم هذه المواد يجعلها معقولة للغاية. قم بتشغيل عميل منشور على مسؤوليتك الخاصة .


اختبار بناء العميل


أولاً ، دعونا نحاول إنشاء عميل اختبار وتشغيله - لحسن الحظ ، تصف README هذه العملية البسيطة بالتفصيل. سأفعل ذلك باستخدام المثال macOS 10.14.5 ، لا يمكنني أن أضمن نجاح التجميع على الأنظمة الأخرى.


  1. قم بتنزيل وفك ضغط الأرشيف باستخدام أكواد المصدر . من المهم تنزيل أحدث إصدار ، نظرًا لأن التوافق مع الإصدارات السابقة غير مضمون في هذه المرحلة.


  2. نتأكد من تثبيت أحدث إصدارات make ، cmake (الإصدار 3.0.2 أو أعلى) ، OpenSSL (بما في ذلك ملفات رأس C) ، g ++ أو clang على النظام. لم أكن مضطرًا إلى إعادة تثبيت أي شيء ، فكل شيء تجمع على الفور.


  3. افترض أن المصادر تم فك ضغطها في مجلد ~/lite-client . بشكل منفصل ، نقوم بإنشاء مجلد فارغ للمشروع المجمع (على سبيل المثال ، ~/liteclient-build ) ، ومنه ( cd ~/liteclient-build ) cd ~/liteclient-build الأوامر:


     cmake ~/lite-client cmake --build . --target test-lite-client 

    بناء العملاء الناجحين

    لإنشاء مترجم لغة Fift للعقود الذكية (انظر أدناه) ، ندعو أيضًا


     cmake --build . --target fift 

  4. قم بتنزيل ملف التكوين الحالي للاتصال بشبكة الاختبار ووضعه في المجلد مع العميل المجمَّع.


  5. تم ، يمكنك بدء العميل:


     ./test-lite-client -C ton-lite-client-test1.config.json 


إذا تم كل شيء بشكل صحيح ، فعندئذ يجب أن ترى شيئًا مثل هذا:


إطلاق العميل


كما ترون ، هناك بعض الأوامر المتاحة:


help - عرض قائمة الأوامر هذه ؛
quit - الخروج ؛
time - عرض الوقت الحالي على الخادم ؛
status - إظهار حالة الاتصال وقاعدة البيانات المحلية ؛
last - تحديث حالة blockchain (تحميل الكتلة الأخيرة). من المهم تنفيذ هذا الأمر قبل أي طلبات للتأكد من أنك ترى تمامًا الحالة الحالية للشبكة.
sendfile <filename> - تحميل ملف محلي إلى شبكة TON. هذا هو التفاعل مع الشبكة - بما في ذلك ، على سبيل المثال ، إنشاء عقود ذكية جديدة وطلبات تحويل الأموال بين الحسابات ؛
getaccount <address> - عرض حالة الحساب الحالية (في وقت تنفيذ last أمر) مع العنوان المحدد ؛
privkey <filename> - قم بتحميل المفتاح الخاص من الملف المحلي.


إذا قمت عند تشغيل العميل بتمرير المجلد إليه باستخدام الخيار -D ، فسوف يقوم بإضافة الكتلة الأخيرة من السلسلة الرئيسية إليه:


 ./test-lite-client -C ton-lite-client-test1.config.json -D ~/ton-db-dir 

الآن يمكننا الانتقال إلى أشياء أكثر إثارة للاهتمام - تعلم لغة Fift ، ومحاولة ترجمة عقد ذكي (على سبيل المثال ، إنشاء محفظة اختبار) ، وتحميلها على الشبكة ومحاولة تحويل الأموال بين الحسابات.


اللغة الخمس


من المستند fiftbase.pdf ، يمكنك معرفة أنه لإنشاء عقود ذكية ، ابتكر فريق Telegram لغة مكدس جديدة Fift (على ما يبدو ، من الرقم الخامس ، عن طريق القياس مع Forth - لغة تشترك Fift فيها كثيرًا).


المستند ضخم جدًا ، حيث يحتوي على 87 صفحة ، ولن أعيد بيع محتوياته بالتفصيل في إطار هذه المقالة (على الأقل لأنني أنا لم أكمل قراءتها :). سأتطرق إلى النقاط الرئيسية وسأقدم بضعة أمثلة على الكود في هذه اللغة.


في المستوى الأساسي ، يكون بناء جملة Fift بسيطًا للغاية: يتكون الكود من كلمات ، وعادةً ما تكون مفصولة بمسافات أو فواصل أسطر (حالة خاصة: بعض الكلمات لا تتطلب محددًا بعدها). أي كلمة هي سلسلة أحرف حساسة لحالة الأحرف تتوافق مع بعض التعريفات (بشكل تقريبي ، ما يجب على المترجم القيام به عندما يواجه هذه الكلمة). إذا لم يكن هناك تعريف للكلمة ، يحاول المترجم تحليلها كرقم ووضعها في المجموعة. بالمناسبة ، فإن الأرقام هنا - فجأة - أعداد صحيحة 257 بت ، ولكن لا توجد أرقام كسرية على الإطلاق - وبشكل أكثر دقة ، فإنها تتحول على الفور إلى زوج من الأعداد الصحيحة ، وتشكل البسط والمقام لكسر عقلاني.


تتفاعل الكلمات عادة مع معاني في الجزء العلوي من المكدس. لا يستخدم نوع منفصل من الكلمات - بادئة - المكدس ، ولكن الأحرف اللاحقة من الملف المصدر. على سبيل المثال ، يتم تطبيق القيم الحرفية للسلسلة بهذه الطريقة - حرف "علامة اقتباس" ( " ) هو كلمة بادئة تبحث عن علامة اقتباس (الإغلاق) التالية وتضع السلسلة بينهما في الحزمة. تتصرف سطر واحد ( // ) وخط متعدد الأسطر ( /* ) بنفس الطريقة. التعليقات.


في هذا ، ينتهي الهيكل الداخلي للغة تقريبًا. يتم تعريف كل شيء آخر (بما في ذلك هياكل التحكم) ككلمات (إما داخلية ، مثل العمليات الحسابية وتعريف الكلمات الجديدة ؛ أو المعرفة في "المكتبة القياسية" Fift.fif ، والتي تقع في crypto/fift في المصدر).


مثال بسيط لبرنامج Fift:


 { dup =: x dup * =: y } : setxy 3 setxy x . y . xy + . 7 setxy x . y . xy + . 

يحدد السطر الأول كلمة setxy الجديدة (لاحظ البادئة { ، التي تنشئ الكتلة قبل الإغلاق } والبادئة : والتي تحدد الكلمة فعليًا). يأخذ setxy رقمًا من أعلى المكدس ، setxy (أو يعيد تعريفه) باعتباره ثابتًا عالميًا x ، ومربع هذا الرقم ثابتًا y (بالنظر إلى أن قيم الثوابت يمكن إعادة تعريفها ، فأنا أفضل أن أسميها متغيرات ، لكنني أتبع التسمية باللغة).


في السطرين التاليين ، يتم وضع رقم في الحزمة ، يتم setxy ، ثم يتم عرض قيم الثوابت x ، y (يتم استخدام الكلمة للإخراج . ) ، يتم وضع كلا الثوابت على المكدس ، ولخصهما ، كما يتم عرض النتيجة. نتيجة لذلك ، سوف نرى:


 3 9 12 ok 7 49 56 ok 

(يقوم المترجم بطباعة الخط "موافق" عندما ينتهي من معالجة الخط الحالي في وضع الإدخال التفاعلي)


حسنًا ، مثال رمز كامل:


 "Asm.fif" include -1 constant wc // create a wallet in workchain -1 (masterchain) // Create new simple wallet <{ SETCP0 DUP IFNOTRET INC 32 THROWIF // return if recv_internal, fail unless recv_external 512 INT LDSLICEX DUP 32 PLDU // sign cs cnt c4 PUSHCTR CTOS 32 LDU 256 LDU ENDS // sign cs cnt cnt' pubk s1 s2 XCPU // sign cs cnt pubk cnt' cnt EQUAL 33 THROWIFNOT // ( seqno mismatch? ) s2 PUSH HASHSU // sign cs cnt pubk hash s0 s4 s4 XC2PU // pubk cs cnt hash sign pubk CHKSIGNU // pubk cs cnt ? 34 THROWIFNOT // signature mismatch ACCEPT SWAP 32 LDU NIP DUP SREFS IF:<{ 8 LDU LDREF // pubk cnt mode msg cs s0 s2 XCHG SENDRAWMSG // pubk cnt cs ; ( message sent ) }> ENDS INC NEWC 32 STU 256 STU ENDC c4 POPCTR }>c // code <b 0 32 u, newkeypair swap dup constant wallet_pk "new-wallet.pk" B>file B, b> // data // no libraries <bb{00110} s, rot ref, swap ref, b> // create StateInit dup ."StateInit: " <s csr. cr dup hash dup constant wallet_addr ."new wallet address = " wc . .": " dup x. cr wc over 7 smca>$ type cr 256 u>B "new-wallet.addr" B>file <b 0 32 u, b> dup ."signing message: " <s csr. cr dup hash wallet_pk ed25519_sign_uint rot <bb{1000100} s, wc 8 i, wallet_addr 256 u, b{000010} s, swap <ss, b{0} s, swap B, swap <ss, b> dup ."External message for initialization is " <s csr. cr 2 boc+>B dup Bx. cr "new-wallet-query.boc" tuck B>file ."(Saved to file " type .")" cr 

تم تصميم ملف المظهر المخيف هذا لإنشاء عقد ذكي - سيتم وضعه في ملف new-wallet-query.boc بعد التنفيذ. يرجى ملاحظة أنه يتم استخدام لغة تجميع أخرى هنا لـ TON Virtual Machine (لن أتناولها بالتفصيل) ، وسيتم وضع التعليمات الخاصة بها على blockchain.


وبالتالي ، يتم تجميع المجمّع لـ TVM في Fift - مصادر هذا المجمّع موجودة في ملف crypto/fift/Asm.fif ويتم توصيلها في بداية قطعة الشفرة أعلاه.


ماذا يمكنني أن أقول ، على ما يبدو ، يحب Nikolai Durov فقط إنشاء لغات برمجة جديدة :)


إنشاء عقد ذكي والتفاعل مع TON


لذلك ، لنفترض أننا قمنا بتكوين عميل TON ومترجم فوريت ، كما هو موضح أعلاه ، وأصبحنا على دراية باللغة. كيفية إنشاء عقد ذكي الآن؟ هذا موصوف في ملف HOWTO المرفق بالمصدر.


حسابات تون


كما وصفت في مراجعة TON ، تحتوي هذه الشبكة على أكثر من كتلة واحدة - هناك واحدة مشتركة ، ما يسمى "سلسلة رئيسية" ، بالإضافة إلى عدد عشوائي من "سلاسل العمل" الإضافية المحددة برقم 32 بت. تحتوي السلسلة الرئيسية على معرف -1 ، بالإضافة إلى ذلك ، يمكن أيضًا استخدام سلسلة عمل "أساسية" ذات المعرف 0. يمكن أن يكون لكل سلسلة عمل تكوينها الخاص. داخليًا ، يتم تقسيم كل مجموعة عمل إلى مجموعات أسهم ، ولكن هذا يمثل بالفعل تفصيلًا للتنفيذ ، والذي لا يجب وضعه في الاعتبار.


يتم تخزين الكثير من الحسابات داخل سلسلة عمل واحدة ، لها معرفات حسابية خاصة بها. بالنسبة للسلسلة الرئيسية وسلسلة العمل الصفرية ، يبلغ طولها 256 بت. وبالتالي ، يتم كتابة معرف الحساب ، على سبيل المثال ، مثل هذا:


 -1:8156775b79325e5d62e742d9b96c30b6515a5cd2f1f64c5da4b193c03f070e0d 

هذا تنسيق "خام": أولاً ، معرف سلسلة العمل ، ثم نقطتين ، ومعرف الحساب بترميز سداسي عشري.


بالإضافة إلى ذلك ، هناك تنسيق مختصر - يتم تشفير رقم سلسلة العمل وعنوان الحساب في شكل ثنائي ، ويتم إضافة المجموع الاختباري لهم ويتم ترميز كل ذلك في Base64:


 Ef+BVndbeTJeXWLnQtm5bDC2UVpc0vH2TF2ksZPAPwcODSkb 

مع العلم بتنسيق التسجيل هذا ، يمكننا طلب الحالة الحالية للحساب من خلال عميل اختبار باستخدام الأمر


 getaccount -1:8156775b79325e5d62e742d9b96c30b6515a5cd2f1f64c5da4b193c03f070e0d 

نحصل على إجابة مثل هذا:


 [ 3][t 2][1558746708.815218925][test-lite-client.cpp:631][!testnode] requesting account state for -1:8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D [ 3][t 2][1558746708.858564138][test-lite-client.cpp:652][!testnode] got account state for -1:8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D with respect to blocks (-1,8000000000000000,72355):F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296:1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F and (-1,8000000000000000,72355):F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296:1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F account state is (account addr:(addr_std anycast:nothing workchain_id:-1 address:x8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D) storage_stat:(storage_info used:(storage_used cells:(var_uint len:1 value:3) bits:(var_uint len:2 value:539) public_cells:(var_uint len:0 value:0)) last_paid:0 due_payment:nothing) storage:(account_storage last_trans_lt:74208000003 balance:(currencies grams:(nanograms amount:(var_uint len:7 value:999928362430000)) other:(extra_currencies dict:hme_empty)) state:(account_active ( split_depth:nothing special:nothing code:(just value:(raw@^Cell x{} x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} )) data:(just value:(raw@^Cell x{} x{0000000D} )) library:hme_empty)))) x{CFF8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D2068086C000000000000000451C90E00DC0E35B7DB5FB8C134_} x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} x{0000000D} -client.cpp: [ 3][t 2][1558746708.815218925][test-lite-client.cpp:631][!testnode] requesting account state for -1:8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D [ 3][t 2][1558746708.858564138][test-lite-client.cpp:652][!testnode] got account state for -1:8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D with respect to blocks (-1,8000000000000000,72355):F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296:1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F and (-1,8000000000000000,72355):F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296:1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F account state is (account addr:(addr_std anycast:nothing workchain_id:-1 address:x8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D) storage_stat:(storage_info used:(storage_used cells:(var_uint len:1 value:3) bits:(var_uint len:2 value:539) public_cells:(var_uint len:0 value:0)) last_paid:0 due_payment:nothing) storage:(account_storage last_trans_lt:74208000003 balance:(currencies grams:(nanograms amount:(var_uint len:7 value:999928362430000)) other:(extra_currencies dict:hme_empty)) state:(account_active ( split_depth:nothing special:nothing code:(just value:(raw@^Cell x{} x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} )) data:(just value:(raw@^Cell x{} x{0000000D} )) library:hme_empty)))) x{CFF8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D2068086C000000000000000451C90E00DC0E35B7DB5FB8C134_} x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} x{0000000D} ل-1: 8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D فيما يتعلق كتل (-1،8000000000000000،72355): F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296: 1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F و [ 3][t 2][1558746708.815218925][test-lite-client.cpp:631][!testnode] requesting account state for -1:8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D [ 3][t 2][1558746708.858564138][test-lite-client.cpp:652][!testnode] got account state for -1:8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D with respect to blocks (-1,8000000000000000,72355):F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296:1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F and (-1,8000000000000000,72355):F566005749C1B97F18EDE013EBA7A054B9014961BC1AD91F475B9082919A2296:1BD5DE54333164025EE39D389ECE2E93DA2871DA616D488253953E52B50DC03F account state is (account addr:(addr_std anycast:nothing workchain_id:-1 address:x8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D) storage_stat:(storage_info used:(storage_used cells:(var_uint len:1 value:3) bits:(var_uint len:2 value:539) public_cells:(var_uint len:0 value:0)) last_paid:0 due_payment:nothing) storage:(account_storage last_trans_lt:74208000003 balance:(currencies grams:(nanograms amount:(var_uint len:7 value:999928362430000)) other:(extra_currencies dict:hme_empty)) state:(account_active ( split_depth:nothing special:nothing code:(just value:(raw@^Cell x{} x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} )) data:(just value:(raw@^Cell x{} x{0000000D} )) library:hme_empty)))) x{CFF8156775B79325E5D62E742D9B96C30B6515A5CD2F1F64C5DA4B193C03F070E0D2068086C000000000000000451C90E00DC0E35B7DB5FB8C134_} x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} x{0000000D} 

نرى الهيكل الذي يتم تخزينه في DHT من سلسلة العمل المحددة. على سبيل المثال ، في الحقل storage.balance هو رصيد الحساب الحالي ، وفي storage.state.code هو رمز العقد الذكي ، وفي storage.state.data هي بياناته الحالية. لاحظ أن مخزن بيانات TON - الخلية ، الخلايا - عبارة عن شجرة ، ويمكن أن تحتوي كل خلية على بياناتها الخاصة ، وكذلك الخلايا التابعة. يظهر هذا كالتقدم البادئة في الأسطر الأخيرة.


عقد العقد الذكية


الآن ، لنقم بإنشاء مثل هذه البنية بأنفسنا (يطلق عليها BOC - كيس من الخلايا ) باستخدام لغة Fift. لحسن الحظ ، لن تضطر إلى كتابة عقد ذكي بنفسك - في مجلد crypto/block من أرشيف المصدر ، يوجد ملف new-wallet.fif سيساعدنا في إنشاء محفظة جديدة. قم ~/liteclient-build إلى المجلد مع العميل المجمَّع ( ~/liteclient-build ، إذا ~/liteclient-build الإرشادات أعلاه). لقد ذكرت محتوياتها أعلاه كمثال على الكود على Fift.


نحن ننفذ هذا الملف على النحو التالي:


 ./crypto/fift -I"<source-directory>/crypto/fift" new-wallet.fif 

هنا يجب استبدال <source-directory> بالمسار إلى المصادر غير المحزومة (لا يمكن استخدام الرمز "~" هنا ، لسوء الحظ ، تحتاج إلى المسار الكامل). بدلاً من استخدام رمز -I يمكنك تحديد FIFTPATH البيئة FIFTPATH ووضع هذا المسار فيه.


نظرًا لأننا أطلقنا Fift باسم الملف new-wallet.fif ، فسيتم تنفيذه new-wallet.fif . إذا حذفت اسم الملف ، فيمكنك اللعب مع المترجم الفوري في الوضع التفاعلي.


بعد التنفيذ ، يجب عرض شيء مثل هذا في وحدة التحكم:


 StateInit: x{34_} x{FF0020DDA4F260810200D71820D70B1FED44D0D31FD3FFD15112BAF2A122F901541044F910F2A2F80001D31F3120D74A96D307D402FB00DED1A4C8CB1FCBFFC9ED54} x{0000000055375F730EDC2292E8CB15C42E8036EE9C25AA958EE002D2DE48A205E3A3426B} new wallet address = -1 : 4fcd520b8fcca096b567d734be3528edc6bed005f6930a9ec9ac1aa714f211f2 0f9PzVILj8yglrVn1zS-NSjtxr7QBfaTCp7JrBqnFPIR8nhZ signing message: x{00000000} External message for initialization is x{89FEE120E20C7E953E31546F64C23CD654002C1AA919ADD24DB12DDF85C6F3B58AE41198A28AD8DAF3B9588E7A629252BA3DB88F030D00BC1016110B2073359EAC3C13823C53245B65D056F2C070B940CDA09789585935C7ABA4D2AD4BED139281CFA1200000001_} x{FF0020DDA4F260810200D71820D70B1FED44D0D31FD3FFD15112BAF2A122F901541044F910F2A2F80001D31F3120D74A96D307D402FB00DED1A4C8CB1FCBFFC9ED54} x{0000000055375F730EDC2292E8CB15C42E8036EE9C25AA958EE002D2DE48A205E3A3426B} B5EE9C724104030100000000D60002CF89FEE120E20C7E953E31546F64C23CD654002C1AA919ADD24DB12DDF85C6F3B58AE41198A28AD8DAF3B9588E7A629252BA3DB88F030D00BC1016110B2073359EAC3C13823C53245B65D056F2C070B940CDA09789585935C7ABA4D2AD4BED139281CFA1200000001001020084FF0020DDA4F260810200D71820D70B1FED44D0D31FD3FFD15112BAF2A122F901541044F910F2A2F80001D31F3120D74A96D307D402FB00DED1A4C8CB1FCBFFC9ED5400480000000055375F730EDC2292E8CB15C42E8036EE9C25AA958EE002D2DE48A205E3A3426B6290698B (Saved to file new-wallet-query.boc) } StateInit: x{34_} x{FF0020DDA4F260810200D71820D70B1FED44D0D31FD3FFD15112BAF2A122F901541044F910F2A2F80001D31F3120D74A96D307D402FB00DED1A4C8CB1FCBFFC9ED54} x{0000000055375F730EDC2292E8CB15C42E8036EE9C25AA958EE002D2DE48A205E3A3426B} new wallet address = -1 : 4fcd520b8fcca096b567d734be3528edc6bed005f6930a9ec9ac1aa714f211f2 0f9PzVILj8yglrVn1zS-NSjtxr7QBfaTCp7JrBqnFPIR8nhZ signing message: x{00000000} External message for initialization is x{89FEE120E20C7E953E31546F64C23CD654002C1AA919ADD24DB12DDF85C6F3B58AE41198A28AD8DAF3B9588E7A629252BA3DB88F030D00BC1016110B2073359EAC3C13823C53245B65D056F2C070B940CDA09789585935C7ABA4D2AD4BED139281CFA1200000001_} x{FF0020DDA4F260810200D71820D70B1FED44D0D31FD3FFD15112BAF2A122F901541044F910F2A2F80001D31F3120D74A96D307D402FB00DED1A4C8CB1FCBFFC9ED54} x{0000000055375F730EDC2292E8CB15C42E8036EE9C25AA958EE002D2DE48A205E3A3426B} B5EE9C724104030100000000D60002CF89FEE120E20C7E953E31546F64C23CD654002C1AA919ADD24DB12DDF85C6F3B58AE41198A28AD8DAF3B9588E7A629252BA3DB88F030D00BC1016110B2073359EAC3C13823C53245B65D056F2C070B940CDA09789585935C7ABA4D2AD4BED139281CFA1200000001001020084FF0020DDA4F260810200D71820D70B1FED44D0D31FD3FFD15112BAF2A122F901541044F910F2A2F80001D31F3120D74A96D307D402FB00DED1A4C8CB1FCBFFC9ED5400480000000055375F730EDC2292E8CB15C42E8036EE9C25AA958EE002D2DE48A205E3A3426B6290698B (Saved to file new-wallet-query.boc) 

هذا يعني أن المحفظة ذات المعرف -1:4fcd520b8fcca096b567d734be3528edc6bed005f6930a9ec9ac1aa714f211f2 (أو ، وهو نفس الشيء ، 0f9PzVILj8yglrVn1zS-NSjtxr7QBfaTCp7JrBqnFPIR8nhZ new-wallet-query.boc الرمز المقابل لها في ملف new-wallet-query.boc ، وعنوانه في new-wallet.addr ، والمفتاح الخاص في new-wallet.pk (كن حذرًا - ستؤدي إعادة تشغيل البرنامج النصي إلى الكتابة فوق هذه الملفات).


بالطبع ، شبكة TON لا تعرف عن هذه المحفظة بعد ، يتم تخزينها فقط في شكل هذه الملفات. أنت الآن بحاجة إلى تحميله على الشبكة. صحيح أن المشكلة تكمن في إنشاء عقد ذكي تحتاج إلى دفع عمولة ، ولا يزال رصيد حسابك صفراً.


في وضع العمل ، سيتم حل هذه المشكلة عن طريق شراء غرام في البورصة (أو عن طريق التحويل من محفظة أخرى). حسنًا ، في وضع الاختبار الحالي ، تم إنشاء عقد ذكي خاص ، يمكنك من خلاله طلب ما يصل إلى 20 جرامًا من هذا القبيل تمامًا.


تشكيل طلب لعقد شخص آخر ذكي


طلب عقد ذكي ، وتوزيع غرام اليسار واليمين ، القيام بذلك. في نفس المجلد crypto/block نجد ملف testgiver.fif :


 // "testgiver.addr" file>B 256 B>u@ 0x8156775b79325e5d62e742d9b96c30b6515a5cd2f1f64c5da4b193c03f070e0d dup constant wallet_addr ."Test giver address = " x. cr 0x4fcd520b8fcca096b567d734be3528edc6bed005f6930a9ec9ac1aa714f211f2 constant dest_addr -1 constant wc 0x00000011 constant seqno 1000000000 constant Gram { Gram swap */ } : Gram*/ 6.666 Gram*/ constant amount // bx --> b' ( serializes a Gram amount ) { -1 { 1+ 2dup 8 * ufits } until rot over 4 u, -rot 8 * u, } : Gram, // create a message (NB: 01b00.., b = bounce) <bb{010000100} s, wc 8 i, dest_addr 256 u, amount Gram, 0 9 64 32 + + 1+ 1+ u, "GIFT" $, b> <b seqno 32 u, 1 8 u, swap ref, b> dup ."enveloping message: " <s csr. cr <bb{1000100} s, wc 8 i, wallet_addr 256 u, 0 Gram, b{00} s, swap <ss, b> dup ."resulting external message: " <s csr. cr 2 boc+>B dup Bx. cr "wallet-query.boc" B>file 

نحن أيضا حفظه في المجلد مع العميل المجمعة ، ولكن إصلاح السطر الخامس - قبل السطر " constant dest_addr ". استبدلها بعنوان المحفظة التي قمت بإنشائها من قبل (ممتلئة ، غير مختصرة). "-1:" لا تحتاج إلى الكتابة في البداية ، بدلاً من ذلك ضع "0x" في البداية.


يمكنك أيضًا تغيير السطر 6.666 Gram*/ constant amount - هذا هو المبلغ بالجرامات التي تطلبها (لا يزيد عن 20). حتى لو قمت بتحديد عدد صحيح ، اترك العلامة العشرية.


أخيرًا ، تحتاج إلى تصحيح السطر 0x00000011 constant seqno . الرقم الأول هنا هو رقم التسلسل الحالي ، والذي يتم تخزينه في الحساب الذي يصدر الجرامات. من أين تحصل عليه؟ كما ذكر أعلاه ، قم ببدء تشغيل العميل وتشغيله:


 last getaccount -1:8156775b79325e5d62e742d9b96c30b6515a5cd2f1f64c5da4b193c03f070e0d 

في النهاية سوف تكون بيانات العقد الذكي


 ... x{FF0020DDA4F260D31F01ED44D0D31FD166BAF2A1F80001D307D4D1821804A817C80073FB0201FB00A4C8CB1FC9ED54} x{0000000D} 

الرقم 0000000D (سيكون لديك المزيد) هو رقم التسلسل ، الذي يجب استبداله في testgiver.fif .


هذا كل شيء ، احفظ الملف وقم بتشغيله ( ./crypto/fift testgiver.fif ). سيكون الإخراج wallet-query.boc . هذه هي الرسالة المشكلة لعقد شخص آخر - الطلب هو "نقل الكثير من الغرامات إلى حساب كهذا وكذا".


باستخدام العميل ، نقوم بتحميله على الشبكة:


 > sendfile wallet-query.boc [ 1][t 1][1558747399.456575155][test-lite-client.cpp:577][!testnode] sending query from file wallet-query.boc [ 3][t 2][1558747399.500236034][test-lite-client.cpp:587][!query] external message status is 1 

إذا اتصلنا الآن بالآخر ، ثم طلبنا مرة أخرى حالة الحساب الذي طلبنا منه غرامات ، فمن المفترض أن نرى أن رقم التسلسل الخاص به قد زاد بمقدار واحد - وهذا يعني أنه أرسل الأموال إلى حسابنا.


تبقى الخطوة الأخيرة - نقوم بتحميل رمز محفظتنا (تم تجديد رصيدها بالفعل ، لكن بدون رمز العقد الذكي لن نتمكن من إدارته). sendfile new-wallet-query.boc - وهذا هو ، لديك محفظتك الخاصة في شبكة TON (وإن كان ذلك الآن اختبار واحد فقط).


إنشاء المعاملات الصادرة


لتحويل الأموال من رصيد الحساب الذي تم إنشاؤه ، يوجد ملف crypto/block/wallet.fif ، والذي يجب أيضًا وضعه في المجلد مع العميل الذي تم جمعه.


على غرار الخطوات السابقة ، تحتاج إلى ضبط المبلغ الذي تنقله ، وعنوان المستلم (dest_addr) ، و seqno محفظتك (هو 1 بعد تهيئة المحفظة ويزيد بمقدار 1 بعد كل معاملة صادرة - يمكنك الاطلاع عليها عن طريق طلب حالة حسابك) . للاختبارات ، يمكنك استخدام ، على سبيل المثال ، محفظتي - 0x4fcd520b8fcca096b567d734be3528edc6bed005f6930a9ec9ac1aa714f211f2 .


عندما تقوم بتشغيل ( ./crypto/fift wallet.fif ) ، سينتقل البرنامج النصي إلى عنوان محفظتك (من أين تنقلها من) والمفتاح الخاص بها من الملفات new-wallet.addr و new-wallet.pk ، وكتابة الرسالة المستلمة إلى new-wallet-query.boc .


كما كان من قبل ، لتنفيذ المعاملة مباشرةً ، ندعو sendfile new-wallet-query.boc في العميل. بعد ذلك ، لا تنسَ تحديث حالة blockchain ( last ) وتحقق من أن رصيد و seqno من محفظتنا قد تغيرت ( getaccount <account_id> ).


وصف الحساب


هذا كل شيء ، الآن يمكننا إنشاء عقود ذكية في TON وإرسال الطلبات إليها. كما ترون ، الوظيفة الحالية كافية بالفعل ، على سبيل المثال ، لإنشاء محفظة أكثر ودية مع واجهة رسومية (ومع ذلك ، فمن المتوقع أن تصبح متاحة كجزء من برنامج المراسلة).

Source: https://habr.com/ru/post/ar453714/


All Articles