# Blockchain Updates Extension
Blockchain Updates is a node extension that sends blockchain updates via gRPC (opens new window).
Blockchain Updates enables tracking changes made by each transaction and block:
- balance updates,
- leased or unleased WAVES,
- account data storage updates,
- token issues and token parameter updates (including reissue/burning, sponsorship setup, replacing script).
You can obtain updates over a specified range of height or in real time.
Examples of usage:
- Integration with the messenger to send notifications about events on your account.
- Tracking payments to dApp in Invoke Script transactions.
- Calculation of the average weekly account balance (used in the market maker program (opens new window)).
- Services for searching tokens by parameters, searching through account data storages, etc.
# Hardware Requirements
For a node with the Blockchain Updates extension, we recommended to increase the disk space by 50 GB (for instance, at height 2422450, 35 GB is used for extension data).
# Launch Node with Extension
⚠️ Important: Blockchain Updates requires the history of changes since the blockchain creation. Therefore, you should start the node with the extension from scratch and synchronize the blockchain during regular node operation, see the Synchronize Waves Blockchain article. This can take 1–3 days. Neither importing blockchain from a binary file, nor downloading the latest blockchain database are applicable.
There are two ways to install the node with Blockchain Updates extension: using a DEB package or a JAR file. The Blockchain Updates extension is in the same package and archive as gRPC Server. You can install these extensions both together and separately, only the settings in the node configuration file differ.
# Installation via DEB Package
Download the latest versions of DEB packages of node and extension from the Releases (opens new window) page (Assets section) on Github.
The extension package name is as follows:
• for Mainnet:
grpc-server_{version number}_all.deb
• for Testnet:
grpc-server-testnet_{version number}_all.deb
• for Stagenet:
grpc-server-stagenet_{version number}_all.deb
Install the packages.
Mainnet:
sudo dpkg -i waves_{version number}_all.deb sudo dpkg -i grpc-server_{version number}_all.deb
Testnet:
sudo dpkg -i waves-testnet_{version number}_all.deb sudo dpkg -i grpc-server-testnet_{version number}_all.deb
Stagenet:
sudo dpkg -i waves-stagenet_{version number}_all.deb sudo dpkg -i grpc-server-stagenet_{version number}_all.deb
Edit the node configuration file as described in the Node Configuration article. For Mainnet, the configuration file is located at
/etc/waves/waves.conf
, for Testnet at/etc/waves-testnet/waves.conf
, for Stagenet at/etc/waves-stagenet/waves.conf
.3.1. Add Blockchain Updates to the
waves.extensions
section:waves { ... extensions = [ com.wavesplatform.events.BlockchainUpdates ] }
3.2. If you want to change the port for client connection (default is 6881), add the following setting:
waves { ... blockchain-updates { grpc-port = 6888 # Specify port }
Start the node.
Mainnet:
sudo systemctl start waves
Testnet:
sudo systemctl start waves-testnet
Stagenet:
sudo systemctl start waves-stagenet
If the extension runs, it writes messages to the node log:
BlockchainUpdates extension starting with settings <...>
BlockchainUpdates startup check successful at height <...>
BlockchainUpdates extension started gRPC API on port <...>
# Installation via JAR File
Download the latest versions of node JAR file and extension TGZ archive from the Releases (opens new window) page (Assets section) on Github.
TGZ archive name is as follows:
• for Mainnet:
grpc-server-{version number}.tgz
• for Testnet:
grpc-server-testnet-{version number}.tgz
• for Stagenet:
grpc-server-stagenet-{version number}.tgz
Unpack the TGZ archive to the directory containing node's JAR file.
Create a new configuration file or open the existing one, see the Node Configuration article.
3.1. Add Blockchain Updates to the
waves.extensions
section:waves { ... extensions = [ com.wavesplatform.events.BlockchainUpdates ] }
3.2. If you want to change the port for client connection (default is 6881), add the following setting:
waves { ... blockchain-updates { grpc-port = 6888 # Specify port }
Run the command:
Mainnet
java -cp 'waves-all-{version number}.jar:grpc-server-{version number}/lib/*' com.wavesplatform.Application {configuration file name}.conf
Testnet:
java -cp 'waves-all-{version number}.jar:grpc-server-testnet-{version number}/lib/*' com.wavesplatform.Application {configuration file name}.conf
Stagenet:
java -cp 'waves-all-{version number}.jar:grpc-server-stagenet-{version number}/lib/*' com.wavesplatform.Application {configuration file name}.conf
On Windows, use
;
instead of:
, for example:java -cp 'waves-all-{version number}.jar;grpc-server-{version number}/lib/*' com.wavesplatform.Application {configuration file name}.conf
If the extension runs, it writes messages to the node log:
BlockchainUpdates extension starting with settings <...>
BlockchainUpdates startup check successful at height <...>
BlockchainUpdates extension started gRPC API on port <...>
# Client Generation
Clone the repository containing protobuf schemes:
git clone https://github.com/wavesplatform/protobuf-schemas/
Generate your client code from the blockchain_updates.proto (opens new window) scheme. Use the gRPC tools for your programming language, find the instructions on the Supported languages and platforms (opens new window) page of gRPC documentation.
# Best Practices
API Blockchain Updates provides the following functions:
GetBlockUpdate
returns updates performed by the block at the given height.GetBlockUpdatesRange
returns updates performed by the blocks at the given range of height.Subscribe
returns stream of messages, first historical data (i.e. updates up to the current blockchain height), then current events in real time. Optionally, you can specify the start and/or end height.
The Subscribe
function returns all the events in real time: block append, microblock append, block rollback, microblock rollback (see the Waves-NG protocol description). To handle rollbacks, we recommend that your client stores the previous states of the blockchain. 10 blocks back from the current block is enough in most cases. The maximum height that the node can rollback automatically is 100, the maximum height of manual rollback is 2000 blocks. For more details, see the Deal With Forks section.
If the connection was interrupted, roll back the last block on the client and restart receiving events from the previous block.
For some analytical tasks, real-time events are not needed, for example, it is enough to update the data once an hour or once a day. In such cases, we recommend to use the GetBlockUpdatesRange
function. It only returns historical data of blocks that are already applied, which is much easier to process. It is better to indicate the end height of the range a few blocks less than the current blockchain height to avoid issues with rollbacks.
# Events Format
See the format of requests and responses in the blockchain_updates.proto (opens new window) and events.proto (opens new window) files.
Events examples:
BlockAppend
update {
id: 6AmsQJEEmxu3wtTRFVzEWgVHf1WBh8nwTNJhDxRKts7U
height: 1199932
append {
block {
block {
header {
chain_id: 84
reference: 7ebn8KgNxaWVK1U4teSJVg24oiesDFPei9njdNMbVFL1
base_target: 1508
generation_signature: Wbtq75BMT4zw35MiWHBcycbG3157byfA8vWYgjaMRUW1V6w6yJZ1TgdUoHe4H7xSZnSXuKJvBotn1nZV8xF8WiQMbfdzjppUvMjcXzkxssy8LK6z7ZKcd9rq1BugZcqnK1R
timestamp: 1601462351767
version: 5
generator: GzkwrZ2tcc2Hu4X2yBHHHsM5cFQAPygFHuRCUSA9chnU
reward_vote: -1
transactions_root: E2SUKG7CVPQYF7ccZWD4zf2W3Ygdp59ZhLFU1R9cFafC
}
signature: 3jaZa2DhvSN16b65e369MBDbypgXEysMZGdNTXx4N8uU9Qn25xsg8xg3nsbySuQWPM9ftjypLEVNkMffHA3cSrxQ
transactions {
transaction {
chain_id: 84
sender_public_key: 57C4SttrQ3a2s6nHqTyPoKo6g7JFKhvojLkS3qgrVqyv
fee {
amount: 500000
}
timestamp: 1601462356424
version: 1
invoke_script {
d_app {
public_key_hash: 3D7mfXL6hAbaKGqCTWC6r2tjdM5Y
}
function_call: BkiQZbtVDKYHAvYcq6FfTfibZCkBt5UF9wF6Y5DwhBQfEoezXDzmvUwfUmuX4mcRiW66ReRuVbCo1M6946wJrUciG94jozz1umDzYYkvWzfQ4mcfEbQgVU5afhxHooyJJruaY9WpPUQQwwzauPg9hmZNyTxDFy7yN2nYyWJKpdF9KC7ucuAMAjw1uifVVufdVwfYi1yxMVtduWGEGuPCzd2UJXSs27EeQtS7AM8ZxtjeQbPbuMxUhCcnVKVhuQ9WLmwwgLecqJEgRPg3KjHMijjtUz2mHKsjupiELThYQCM1NiTCV1wZTwNThW3NZ8jt4rSi3wk38u5JfRH9t8umgoYAVbAmhvgYwDjEFKm9YExJufedEeLFQ1MGx83AqKjmawWLE8Z41JBdMb98mtmu3SbJ8xJpehSZhfJKV23dpBfNXouPsnScQDPHgfvTdr7oDoz71p2qQqLinZkVtEn8fiXgDtQyzHNRY1juMS3WGxKyzK8rKAPSbpoNCaF1fmznm6wyD25k9dJ91ZpKYfLDGg5Ag6ySgXKvFVVUREMrsgqKirwaz7wHmTRrc7f2Va
}
}
proofs: 4WhHHPj6T9xa2y9rLAJtdko3dgkMQ1gaKsuVpkKgEW8NH6QqANsJSHqe13pTwYEG3XzVWAjcefyyszgKZZvoZ4oo
}
}
updated_waves_amount: 10000000600000000
}
transaction_ids: DAunM3yCYmoPoAHD5z5ddX225Pa47BNBNsMoMLM2ApFC
state_update {
balances {
address: 3NAhtLNFJhfB6TgMia9HzdaSkKiJD5N2V3b
amount {
amount: 1480157680000
}
}
}
transaction_state_updates {
balances {
address: 3MuhGCajV9HXunkyuQpwXvHTjTLaMy93g9Y
amount {
amount: 5932500000
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "deficit_1199932"
int_value: -379468596950
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "deficit_percent_1199932"
int_value: -31
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "price"
int_value: 5500000
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "price_index"
int_value: 159817
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "neutrinoSupply_1199932"
int_value: 1230373751604
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "price_index_159817"
int_value: 1199932
}
}
data_entries {
address: 3N4NS7d4Jo9a6F14LiFUKKYVdUkkf2eP4Zx
data_entry {
key: "price_1199932"
int_value: 5500000
}
}
}
}
}
MicroBlockAppend
update {
id: 5DbKdfhsDaFRNfzmYwPLivksKE28VUtBZA8qt7eGwL4W
height: 1199936
append {
micro_block {
micro_block {
micro_block {
version: 5
reference: 2EvXRVtn7sEXxFKqmfqHtJQM9r2muQUjjbY3g1D8JJHb
updated_block_signature: 3jBu2vx5arqPtDgTahxdWYGByjwafXranfMm8sFtyr71wcQM5w4e2k8UPBa12gHAaWS31wA1JsBvJdwe19345tZA
sender_public_key: 3ikUmWkNpbkeVZaoA7fogfDjKw5hn4ZWVbP4gW7dMQNi
transactions {
transaction {
chain_id: 84
sender_public_key: 4yLsZuHMtyc4nQaF5MSGkKRQqGYfQBMim1qVLKCtacqx
fee {
amount: 900000
}
timestamp: 1601462611517
version: 2
transfer {
recipient {
public_key_hash: 4W5hFHdYbrx7fBFP7ofmZNLsjwPB
}
amount {
asset_id: LVf3qaCtb9tieS1bHD8gg5XjWvqpBm5TaDxeSVcqPwn
amount: 10000000
}
}
}
proofs: 4d1YtV7e9XaVGgmiZZcDNXUri6ycKmECf1R59Bz8CnvfrN31Bd3eiHzSJnFPrLTEjZ5oQLpDmcYsTaxZWdWbtsBB
}
}
signature: 571Xg1T5aYsChW3nzKxH7N9te7xgsZsJj3yKQWwwUr4fTQehzYn5tzdudDrwdVnDuKQC7AccNqhzTPDk9AM7oVZ8
total_block_id: 5DbKdfhsDaFRNfzmYwPLivksKE28VUtBZA8qt7eGwL4W
}
updated_transactions_root: Cv59LBRGPd1Qipk9zT8V6d2yawGVuxBLfR2JejKgCnUP
}
transaction_ids: GXTbnhwEtZLrsq7GhwSjmff12Luc1ABTjZsLq6Bun9AD
state_update {
balances {
address: 3MtQQX9NwYH5URGGcS2e6ptEgV7wTFesaRW
amount {
amount: 40776090986764
}
}
}
transaction_state_updates {
balances {
address: 3NCpyPuNzUaB7LFS4KBzwzWVnXmjur582oy
amount {
asset_id: LVf3qaCtb9tieS1bHD8gg5XjWvqpBm5TaDxeSVcqPwn
amount: 9786003244627670
}
}
balances {
address: 3MzykUc8kraFGbuYVWXtsYrnvkA8w6JeWuK
amount {
amount: 138800000
}
}
balances {
address: 3MzykUc8kraFGbuYVWXtsYrnvkA8w6JeWuK
amount {
asset_id: LVf3qaCtb9tieS1bHD8gg5XjWvqpBm5TaDxeSVcqPwn
amount: 99320000000
}
}
}
}
}
Rollback (for block)
update {
id: 7Z4md34VUp5Db2wwYW21tb9UdVVuMbFnDqQiTy1E99uZ
height: 1199939
rollback {
type: BLOCK
}
}
Rollback (for microblock)
update {
id: C6zsDGh2ahvTbDLA5ESGtaPMcGdUeg2g5FzB7XVCRTBP
height: 1199973
rollback {
type: MICROBLOCK
}
}
Some updates on the blockchain are not associated with any transaction, they are performed at the block level. For example, updates of the block generator balance: 40% of transaction fee that is received by the generator of the current block and is associated with the transaction, and the 60% that the generator of the next block receives is associated only with the block. The block reward is also associated with the block only.
If the transaction fee is indicated in the sponsored asset, then Blockchain Updates returns, in addition to the sender's balance and block generator's balance updates, the sponsor's balance update: the sponsor receives the fee in the sponsored asset and pays the fee equivalent in WAVES. More about sponsorship