Быстрый старт с Oracle

Введение

Смарт-контракты, которые требуют внешних данных или событий в режиме реального времени, требуют доверенного oracle, то есть доверенного смарт-контракта, который предоставляет данные в цепочке.
Для чего это полезно?
    Оракул, который предоставляет цены XTZ / USD, может позволить пользователям вносить средства, которые немедленно конвертируются в какой-либо актив в цепочке и представляются как указание к действию.
    Оракул, который предоставляет данные о погоде, может позволить заключить договор страхования от цунами: пользователи покупают покрытие по контракту, которое выплачивается, когда в их районе появится достаточно сильное цунами
    Комбинация различных оракулов может использоваться для достижения консенсуса, например, где только результаты, опубликованные большинством оракулов, считаются действительными.

Установка

CLI

1
❯❯❯ lorentz-contract-oracle Oracle --help
2
Usage: lorentz-contract-oracle Oracle COMMAND
3
Oracle contract CLI interface
4
5
Available options:
6
-h,--help Show this help text
7
8
Available commands:
9
print Dump the Oracle contract in form of Michelson code
10
print-timestamped Dump the Timestamped Oracle contract in form of
11
Michelson code
12
init Initial storage for the Oracle contract
13
get-value get value
14
update-value update value
15
update-admin update admin
Copied!

Создание контракта

Печать контракта

Команда печати принимает единственный аргумент: valueType, тип значения, предоставленного оракулом.
Примечание. Пока проблема №6 в репозитории не будет исправлена, инструмент CLI будет выдавать ошибку, если valueType не является nat при печати контракта или в timestamped версии.
Например, если nat значения переданы:
1
❯❯❯ lorentz-contract-oracle Oracle print --valueType "nat"
2
3
parameter (or (pair %getValue unit
4
(contract nat))
5
(or (nat %updateValue)
6
(address %updateAdmin)));
7
storage (pair nat
8
address);
9
code { CAST (pair (or (pair unit (contract nat)) (or nat address)) (pair nat address));
10
DUP;
11
CAR;
12
DIP { CDR };
13
IF_LEFT { DUP;
14
CAR;
15
DIP { CDR };
16
DIP { DIP { DUP };
17
SWAP };
18
PAIR;
19
CDR;
20
CAR;
21
DIP { AMOUNT };
22
TRANSFER_TOKENS;
23
NIL operation;
24
SWAP;
25
CONS;
26
PAIR }
27
{ IF_LEFT { DIP { DUP;
28
CAR;
29
DIP { CDR } };
30
DIP { DROP;
31
DUP;
32
DIP { SENDER;
33
COMPARE;
34
EQ;
35
IF { }
36
{ PUSH string "only admin may update";
37
FAILWITH } } };
38
PAIR;
39
NIL operation;
40
PAIR }
41
{ DIP { DUP;
42
CAR;
43
DIP { CDR };
44
DIP { SENDER;
45
COMPARE;
46
EQ;
47
IF { }
48
{ PUSH string "only admin may update";
49
FAILWITH } } };
50
SWAP;
51
PAIR;
52
NIL operation;
53
PAIR } } };
Copied!

Начальное хранение

1
❯❯❯ lorentz-contract-oracle Oracle init --help
2
Usage: lorentz-contract-oracle Oracle init --initialValueType Michelson Type
3
--initialValue Michelson Value
4
--admin ADDRESS
5
Initial storage for the Oracle contract
6
7
Available options:
8
-h,--help Show this help text
9
--initialValueType Michelson Type
10
The Michelson Type of initialValue
11
--initialValue Michelson Value
12
The Michelson Value: initialValue
13
--admin ADDRESS Address of the admin.
14
-h,--help Show this help text
Copied!
Поскольку мы используем nat, initialValueType имеет значение nat, а initialValue может быть 0:
1
❯❯❯ lorentz-contract-oracle Oracle init \
2
--initialValueType "nat" \
3
--initialValue 3 \
4
--admin $ALICE_ADDRESS
5
Pair 3 "tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr"
Copied!

Запуск старта контракта

ПРИМЕЧАНИЕ: чтобы использовать аннотированную (timestamped) версию, например для nat:
1
❯❯❯ tezos-client --wait none originate contract NatOracle \
2
transferring 0 from $ALICE_ADDRESS running \
3
"$(lorentz-contract-oracle Oracle print-timestamped --valueType "nat")" \
4
--init "$(lorentz-contract-oracle Oracle init \
5
--initialValueType "pair timestamp nat" --initialValue 'Pair "2019-12-10T17:43:53Z" 26871' \
6
--admin $ALICE_ADDRESS)" --burn-cap 0.859 --force
Copied!
ПРИМЕЧАНИЕ: контракт nat_oracle.tz можно найти здесь
Иначе:
1
❯❯❯ tezos-client --wait none originate contract NatOracle \
2
transferring 0 from $ALICE_ADDRESS running \
3
"$(lorentz-contract-oracle Oracle print --valueType "nat")" \
4
--init "$(lorentz-contract-oracle Oracle init \
5
--initialValueType "nat" --initialValue 3 \
6
--admin $ALICE_ADDRESS)" --burn-cap 0.612
7
8
Waiting for the node to be bootstrapped before injection...
9
Current head: BLE8kx6VhXbk (timestamp: 2020-04-03T15:28:43-00:00, validation: 2020-04-03T15:29:02-00:00)
10
Node is bootstrapped, ready for injecting operations.
11
Estimated gas: 20483 units (will add 100 for safety)
12
Estimated storage: 683 bytes added (will add 20 for safety)
13
Operation successfully injected in the node.
14
Operation hash is 'onsEwbbm71wpzgnk6baBGacDzsnKceypEL841STJ6B5V9cA4swr'
15
NOT waiting for the operation to be included.
16
Use command
17
tezos-client wait for onsEwbbm71wpzgnk6baBGacDzsnKceypEL841STJ6B5V9cA4swr to be included --confirmations 30 --branch BLE8kx6VhXbka6FGjXmKxnH56iypJLYZ9pM5mM3HLKvoVDBiMeS
18
and/or an external block explorer to make sure that it has been included.
19
This sequence of operations was run:
20
Manager signed operations:
21
From: tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm
22
Fee to the baker: ꜩ0.002729
23
Expected counter: 623928
24
Gas limit: 20583
25
Storage limit: 703 bytes
26
Balance updates:
27
tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm ............. -ꜩ0.002729
28
fees(tz1Ke2h7sDdakHJQh8WX4Z372du1KChsksyU,154) ... +ꜩ0.002729
29
Origination:
30
From: tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm
31
Credit: ꜩ0
32
Script:
33
{...}
34
Initial storage: (Pair 3 "tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr")
35
No delegate for this contract
36
This origination was successfully applied
37
Originated contracts:
38
KT1LVLUsC1WCo4yHzeoDEE8FxxoC7EW6bSyp
39
Storage size: 426 bytes
40
Paid storage size diff: 426 bytes
41
Consumed gas: 20483
42
Balance updates:
43
tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm ... -ꜩ0.426
44
tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm ... -ꜩ0.257
45
46
New contract KT1LVLUsC1WCo4yHzeoDEE8FxxoC7EW6bSyp originated.
47
Contract memorized as NatOracle.
Copied!
Создайте псевдоним для полученного адреса:
1
❯❯❯ ORACLE_ADDRESS="KT1LVLUsC1WCo4yHzeoDEE8FxxoC7EW6bSyp"
Copied!

Получение значения

Подготовка к просмотру контракта

Старт контракта:
1
❯❯❯ tezos-client --wait none originate contract nat_storage transferring 0 \
2
from $ALICE_ADDRESS running "$(lorentz-contract print --name NatStorageContract)" \
3
--init 0 --burn-cap 0.295
Copied!
Создайте псевдоним для полученного адреса:
1
❯❯❯ NAT_STORAGE_ADDRESS="KT1ShW17HERZgjUTxSxSc4W3tuWrfLCqBmEi"
Copied!
См. FA1.2 для получения дополнительной информации.

Создание параметра

1
❯❯❯ lorentz-contract-oracle Oracle get-value --help
2
Usage: lorentz-contract-oracle Oracle get-value --callbackContract ADDRESS
3
get value
4
5
Available options:
6
-h,--help Show this help text
7
--callbackContract ADDRESS
8
Address of the callbackContract.
9
-h,--help Show this help text
Copied!
1
❯❯❯ lorentz-contract-oracle Oracle get-value --callbackContract $NAT_STORAGE_ADDRESS
2
Left (Pair Unit "KT1ShW17HERZgjUTxSxSc4W3tuWrfLCqBmEi")
Copied!

Получение значения

1
❯❯❯ tezos-client --wait none transfer 0 from $ALICE_ADDRESS to $ORACLE_ADDRESS \
2
--arg "$(lorentz-contract-oracle Oracle get-value \
3
--callbackContract $NAT_STORAGE_ADDRESS)" --burn-cap 0.000001
4
5
Waiting for the node to be bootstrapped before injection...
6
Current head: BL7fbZE3Gs2V (timestamp: 2020-04-03T15:33:25-00:00, validation: 2020-04-03T15:33:45-00:00)
7
Node is bootstrapped, ready for injecting operations.
8
Estimated gas: 31566 units (will add 100 for safety)
9
Estimated storage: no bytes added
10
Operation successfully injected in the node.
11
Operation hash is 'opWqWvkJczWzq5m99svSDzW7HmWY5nCUB1rerDn6utLLH5NJ1dS'
12
NOT waiting for the operation to be included.
13
Use command
14
tezos-client wait for opWqWvkJczWzq5m99svSDzW7HmWY5nCUB1rerDn6utLLH5NJ1dS to be included --confirmations 30 --branch BL7fbZE3Gs2VkmziY11S4biX9cfuLVnQmLr8r7ALbJukxD4tRSY
15
and/or an external block explorer to make sure that it has been included.
16
This sequence of operations was run:
17
Manager signed operations:
18
From: tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm
19
Fee to the baker: ꜩ0.00347
20
Expected counter: 623930
21
Gas limit: 31666
22
Storage limit: 0 bytes
23
Balance updates:
24
tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm ............. -ꜩ0.00347
25
fees(tz1Ke2h7sDdakHJQh8WX4Z372du1KChsksyU,154) ... +ꜩ0.00347
26
Transaction:
27
Amount: ꜩ0
28
From: tz1bDCu64RmcpWahdn9bWrDMi6cu7mXZynHm
29
To: KT1LVLUsC1WCo4yHzeoDEE8FxxoC7EW6bSyp
30
Parameter: (Left (Pair Unit "KT1ShW17HERZgjUTxSxSc4W3tuWrfLCqBmEi"))
31
This transaction was successfully applied
32
Updated storage:
33
(Pair 3 0x00003b5d4596c032347b72fb51f688c45200d0cb50db)
34
Storage size: 426 bytes
35
Consumed gas: 20242
36
Internal operations:
37
Transaction:
38
Amount: ꜩ0
39
From: KT1LVLUsC1WCo4yHzeoDEE8FxxoC7EW6bSyp
40
To: KT1ShW17HERZgjUTxSxSc4W3tuWrfLCqBmEi
41
Parameter: 3
42
This transaction was successfully applied
43
Updated storage: 3
44
Storage size: 38 bytes
45
Consumed gas: 11324
Copied!

Изменение значения

Создание параметра

1
❯❯❯ lorentz-contract-oracle Oracle update-value --help
2
Usage: lorentz-contract-oracle Oracle update-value --newValueType Michelson Type
3
--newValue Michelson Value
4
update value
5
6
Available options:
7
-h,--help Show this help text
8
--newValueType Michelson Type
9
The Michelson Type of newValue
10
--newValue Michelson Value
11
The Michelson Value: newValue
12
-h,--help Show this help text
Copied!

Изменение значения

Чтобы изменить значение на 4:
1
Waiting for the node to be bootstrapped before injection...
2
Current head: BMLjQ5pgcmxd (timestamp: 2020-04-03T15:35:39-00:00, validation: 2020-04-03T15:35:44-00:00)
3
Node is bootstrapped, ready for injecting operations.
4
Estimated gas: 19463 units (will add 100 for safety)
5
Estimated storage: no bytes added
6
Operation successfully injected in the node.
7
Operation hash is 'ooEf7sgpvhMcUBcn66iMLaWNzs4TEAxb4icjXKF27xM2QPMTGQP'
8
NOT waiting for the operation to be included.
9
Use command
10
tezos-client wait for ooEf7sgpvhMcUBcn66iMLaWNzs4TEAxb4icjXKF27xM2QPMTGQP to be included --confirmations 30 --branch BMLjQ5pgcmxdN11kfhA2NS4igfSdJeL5HbopDn8LyAckBroWZhi
11
and/or an external block explorer to make sure that it has been included.
12
This sequence of operations was run:
13
Manager signed operations:
14
From: tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr
15
Fee to the baker: ꜩ0.001259
16
Expected counter: 632294
17
Gas limit: 10000
18
Storage limit: 0 bytes
19
Balance updates:
20
tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr ............. -ꜩ0.001259
21
fees(tz1Ke2h7sDdakHJQh8WX4Z372du1KChsksyU,154) ... +ꜩ0.001259
22
Revelation of manager public key:
23
Contract: tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr
24
Key: edpkvCHgVArnZo9RTP4P6euLTyhE89u73CYjBgsP4wEJbj4quao9oR
25
This revelation was successfully applied
26
Consumed gas: 10000
27
Manager signed operations:
28
From: tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr
29
Fee to the baker: ꜩ0.002123
30
Expected counter: 632295
31
Gas limit: 19563
32
Storage limit: 0 bytes
33
Balance updates:
34
tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr ............. -ꜩ0.002123
35
fees(tz1Ke2h7sDdakHJQh8WX4Z372du1KChsksyU,154) ... +ꜩ0.002123
36
Transaction:
37
Amount: ꜩ0
38
From: tz1R3vJ5TV8Y5pVj8dicBR23Zv8JArusDkYr
39
To: KT1LVLUsC1WCo4yHzeoDEE8FxxoC7EW6bSyp
40
Parameter: (Right (Left 4))
41
This transaction was successfully applied
42
Updated storage:
43
(Pair 4 0x00003b5d4596c032347b72fb51f688c45200d0cb50db)
44
Storage size: 426 bytes
45
Consumed gas: 19463
Copied!

Настройка сервера

Хотя у нас есть все необходимое для создания и администрирования контракта оракула, мы хотели бы автоматически отправлять обновления в контракт.
Ниже приведены два простых примера того, как вы можете периодически получать некоторые данные и автоматически передавать их в контракт оракула.

Минимальный сервер на Bash

Минимальный сервер, написанный на Bash, может состоять из:
    Bash скрипта update_value.sh который получает NEW_VALUE и вызывает точку входа
    update-value:
1
##!/bin/bash
2
## update_value.sh
3
4
NEW_VALUE="$(my_get_new_value_script)
5
6
tezos-client --wait none transfer 0 from $ALICE_ADDRESS to $ORACLE_ADDRESS \
7
--arg "$(lorentz-contract-oracle Oracle update-value \
8
--newValueType "nat" --newValue $NEW_VALUE)" --burn-cap 0.000001
Copied!
    crontab настройку update_value.sh запускающуюся периодически
    (в примере: ежедневно в 5:03 pm):
1
03 05 * * * update_value.sh
Copied!

Сервер Docker Flask

Существует реализация указанного выше сервера Bash на Python, упакованная как образ Docker, которая:
    Получает последнюю информацию о ценах на акции от Alpha Vantage
    Запускает "задание cron", чтобы отправить обновление в контракт оракула с pytezos каждые 30 секунд
    Обслуживает веб-страницу для отладки
Он делает то же самое, что и скрипт Bash, где my_get_new_value_script извлекает последнюю цену из Alpha Vantage.
Вы можете найти проект на Github здесь или просмотреть однофайловый код Python здесь.
Чтобы получить изображение из репозитория DockerHub, запустите:
1
❯❯❯ docker pull tqtezos/oracle-stock-ticker:2.1
Copied!
Сервер настраивается с использованием переменных среды:
    Чтобы сгенерировать TEZOS_USER_KEY, выполните: echo "$(base64 MY_KEY_FILE.json | tr -d '\n')",
    где MY_KEY_FILE.json это ваш файл Tezos вилки (см. здесь, чтобы получить файл).
    Вы можете получить бесплатный ALPHA_VANTAGE_API_KEY от Alpha Vantage
    Search Endpoint от Alpha Vantage можно использовать, чтобы найти значения ALPHA_VANTAGE_TICKER_SYMBOL
1
TEZOS_USER_KEY=".."
2
ORACLE_ADDRESS="KT1CUTjTqf4UMf6c9A8ZA4e1ntWbLVTnvrKG"
3
ALPHA_VANTAGE_API_KEY=".."
4
ALPHA_VANTAGE_TICKER_SYMBOL="AAPL"
5
FLASK_APP="tq/oracles/ticker.py"
Copied!
Чтобы запустить контейнер Docker:
1
❯❯❯ docker run -d -p 5000:5000 \
2
--env TEZOS_USER_KEY=".."
3
--env ORACLE_ADDRESS="KT1.." \
4
--env ALPHA_VANTAGE_API_KEY=".." \
5
--env ALPHA_VANTAGE_TICKER_SYMBOL="AAPL" \
6
--env FLASK_APP="tq/oracles/ticker.py" \
7
oracle-stock-ticker
Copied!
Как только он будет запущен, он будет обслуживать страницу отладки и обновлять контракт оракула примерно каждые 30 секунд.
Теперь вы должны иметь возможность просматривать экран отладки по адресу localhost:5000, получать последние значения с помощью get-value и использовать проводник блоков для проверки контракта.
Вы можете найти действующий пример контракта на Carthage.
Материалы разработаны TQ Tezos переведены на русский язык Tezos Ukraine
Last modified 1yr ago