diff --git a/.gitignore b/.gitignore index 3fe092dd1..cad1eb0ab 100644 --- a/.gitignore +++ b/.gitignore @@ -35,4 +35,5 @@ core/service/testdata/snapshots/ _* *.db-shm -*.db-wal \ No newline at end of file +*.db-wal +.run \ No newline at end of file diff --git a/api/service/transactionApiService.go b/api/service/transactionApiService.go index 59b900e7c..599a64db4 100644 --- a/api/service/transactionApiService.go +++ b/api/service/transactionApiService.go @@ -246,7 +246,7 @@ func (ts *TransactionService) GetTransactions( &tx.Signature, &tx.Version, &tx.TransactionIndex, - &tx.MultisigChild, + &tx.ChildType, &tx.Message, ) if err != nil { diff --git a/api/service/transactionApiService_test.go b/api/service/transactionApiService_test.go index 805d0d59b..751829f4e 100644 --- a/api/service/transactionApiService_test.go +++ b/api/service/transactionApiService_test.go @@ -54,17 +54,17 @@ package service import ( "database/sql" "errors" - "github.com/zoobc/zoobc-core/common/crypto" - "github.com/zoobc/zoobc-core/common/feedbacksystem" - "github.com/zoobc/zoobc-core/common/storage" "reflect" "testing" "github.com/DATA-DOG/go-sqlmock" "github.com/sirupsen/logrus" "github.com/zoobc/zoobc-core/common/chaintype" + "github.com/zoobc/zoobc-core/common/crypto" + "github.com/zoobc/zoobc-core/common/feedbacksystem" "github.com/zoobc/zoobc-core/common/model" "github.com/zoobc/zoobc-core/common/query" + "github.com/zoobc/zoobc-core/common/storage" "github.com/zoobc/zoobc-core/common/transaction" "github.com/zoobc/zoobc-core/core/service" "github.com/zoobc/zoobc-core/observer" @@ -659,7 +659,7 @@ func (*mockQueryGetTransactionsSuccess) ExecuteSelect(qStr string, tx bool, args []byte{0, 0, 0, 0, 0, 0, 0}, 1, 1, - false, + model.TransactionChildType_MultiSignatureChild, []byte{1, 2, 3}, ), ) @@ -758,7 +758,7 @@ func TestTransactionService_GetTransactions(t *testing.T) { Signature: []byte{0, 0, 0, 0, 0, 0, 0}, Version: 1, TransactionIndex: 1, - MultisigChild: false, + ChildType: model.TransactionChildType_MultiSignatureChild, Message: []byte{1, 2, 3}, }, }, @@ -836,7 +836,7 @@ func (*mockQueryGetTransactionSuccess) ExecuteSelectRow(qstr string, tx bool, ar 8, []byte{1, 2, 3, 4, 5, 6, 7, 8}, []byte{0, 0, 0, 0, 0, 0, 0}, 1, 1, - false, + model.TransactionChildType_MultiSignatureChild, "", ), ) @@ -916,7 +916,7 @@ func TestTransactionService_GetTransaction(t *testing.T) { Signature: []byte{0, 0, 0, 0, 0, 0, 0}, Version: 1, TransactionIndex: 1, - MultisigChild: false, + ChildType: model.TransactionChildType_MultiSignatureChild, Message: []byte{}, }, }, diff --git a/cmd/account/account.go b/cmd/account/account.go index 562f4d9a9..ce51d3406 100644 --- a/cmd/account/account.go +++ b/cmd/account/account.go @@ -90,11 +90,11 @@ private key both in bytes and hex representation + the secret phrase Use: "ed25519", Short: "Generate account using ed25519 algorithm. This is the default zoobc account", } - bitcoinAccuntCmd = &cobra.Command{ + bitcoinAccountCmd = &cobra.Command{ Use: "bitcoin", Short: "Generate account based on Bitcoin signature that using Elliptic Curve Digital Signature Algorithm", } - convAccuntToHexCmd = &cobra.Command{ + convAccountToHexCmd = &cobra.Command{ Use: "hexconv", Short: "Convert a given (encoded/string) account address to hex format", } @@ -122,21 +122,21 @@ func init() { ed25519AccountCmd.Flags().StringVar(&seed, "seed", "", "Seed that is used to generate the account") ed25519AccountCmd.Flags().BoolVar(&ed25519UseSlip10, "use-slip10", false, "use slip10 to generate ed25519 private key") // bitcoin - bitcoinAccuntCmd.Flags().StringVar(&seed, "seed", "", "Seed that is used to generate the account") - bitcoinAccuntCmd.Flags().Int32Var( + bitcoinAccountCmd.Flags().StringVar(&seed, "seed", "", "Seed that is used to generate the account") + bitcoinAccountCmd.Flags().Int32Var( &bitcoinPrivateKeyLength, "private-key-length", int32(model.PrivateKeyBytesLength_PrivateKey256Bits), "The length of private key Bitcoin want to generate. supported format are 32, 48 & 64 length", ) - convAccuntToHexCmd.Flags().StringVar(&encodedAccountAddress, "encodedAccountAddress", "", + convAccountToHexCmd.Flags().StringVar(&encodedAccountAddress, "encodedAccountAddress", "", "formatted/encoded account address. eg. ZBC_F5YUYDXD_WFDJSAV5_K3Y72RCM_GLQP32XI_QDVXOGGD_J7CGSSSK_5VKR7YML") - convAccuntToHexCmd.Flags().Int32Var(&accountTypeInt, "accountType", 0, "Account type num: 0=default, 1=btc, etc..") + convAccountToHexCmd.Flags().Int32Var(&accountTypeInt, "accountType", 0, "Account type num: 0=default, 1=btc, etc..") convHexAccountToEncodedCmd.Flags().StringVar(&hexAccountAddress, "hexAccountAddress", "", - "full accound address in hex format: eg. 00000000e1e6ea65267121801089048c3a1dd863aea1fab123977677c612658a749a8a01") + "full account address in hex format: eg. 00000000e1e6ea65267121801089048c3a1dd863aea1fab123977677c612658a749a8a01") generateAccountAddressTableCmd.Flags().StringVar(&dbPath, "dbPath", "../resource", "folder path to zoobc.db, relative to cmd root path. if none provided, resource folder will be targeted") - bitcoinAccuntCmd.Flags().Int32Var( + bitcoinAccountCmd.Flags().Int32Var( &bitcoinPublicKeyFormat, "public-key-format", int32(model.BitcoinPublicKeyFormat_PublicKeyFormatCompressed), @@ -160,10 +160,10 @@ func Commands() *cobra.Command { } ed25519AccountCmd.Run = accountGeneratorInstance.GenerateEd25519Account() accountCmd.AddCommand(ed25519AccountCmd) - bitcoinAccuntCmd.Run = accountGeneratorInstance.GenerateBitcoinAccount() - accountCmd.AddCommand(bitcoinAccuntCmd) - convAccuntToHexCmd.Run = accountGeneratorInstance.ConvertEncodedAccountAddressToHex() - accountCmd.AddCommand(convAccuntToHexCmd) + bitcoinAccountCmd.Run = accountGeneratorInstance.GenerateBitcoinAccount() + accountCmd.AddCommand(bitcoinAccountCmd) + convAccountToHexCmd.Run = accountGeneratorInstance.ConvertEncodedAccountAddressToHex() + accountCmd.AddCommand(convAccountToHexCmd) convHexAccountToEncodedCmd.Run = accountGeneratorInstance.ConvertHexAccountToEncoded() accountCmd.AddCommand(convHexAccountToEncodedCmd) generateAccountAddressTableCmd.Run = accountGeneratorInstance.GenerateAccountAddressTable() @@ -174,7 +174,7 @@ func Commands() *cobra.Command { } -// GenerateMultiSignatureAccount to generate address for multi signature transaction +// ConvertEncodedAccountAddressToHex to generate address for multi signature transaction func (gc *GeneratorCommands) ConvertEncodedAccountAddressToHex() RunCommand { return func(cmd *cobra.Command, args []string) { var ( diff --git a/cmd/readme.md b/cmd/readme.md index 4e271a595..28e9760d8 100644 --- a/cmd/readme.md +++ b/cmd/readme.md @@ -19,52 +19,68 @@ Command line interface to as a utility tools to develop the zoobc system. ### See more help about commands - `go run main --help` to see available commands and flags -- `go run main {command} --help` to see to see available subcommands and flags -- `go run main {command} {subcommand} --help` to see to see available subcommands and flags of subcommand +- `go run main {command} --help` to see available subcommands and flags +- `go run main {command} {subcommand} --help` to see available subcommands and flags of subcommand ## Transaction Commands ### Transaction general flag +```bash +Flags: + -n, --db-name string --db-name "zoobc.db". Defines database name {name}.db (default "zoobc.db") + -p, --db-path string --db-path "resource". Defines database path location (default "resource") + --fee int --fee 1. Defines the fee of the transaction (default 1) + -h, --help help for transaction + --message string --message "test message". Include an arbitrary message in the transaction (max 256 bytes) + --output string --output hex. Defines the type of the output to be generated (default "bytes") + --post --post. Post generated bytes to [127.0.0.1:7000](default) + --post-host string --post-host "127.0.0.1:7000". Destination of post action (default "127.0.0.1:7000") + --recipient string --recipient 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073. Provide recipient transaction hex format + --sender-address string --sender-address 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073. Transaction's sender address, [no necessary if contain --sender-seed] + --sender-seed Sender Account Address --sender-seed mnemonic. Defines the sender seed that's used to sign transaction and whose public key will be used in theSender Account Address field of the transaction + -s, --sign --sign false. Defines transaction should be signed (default true) + --timestamp int --timestamp 23456789. defines timestamp of the transaction (default 1603324318) + --version uint32 --version 2. Defines version of the transaction (default 1) -- `--output` to provide generated ouput type. Example: `--ouput bytes` -- `--version` to provide version of transaction. Example: `--version 1` -- `--timestamp` to provide timestamp of trasaction. Example: `--timestamp 1234567` -- `--sender-seed` to provide the seed of sender transaction. Example: `--sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved"` -- `--sender-address` transaction's sender address -- `--recipient` provide recepient transaction. Example `--recipient VZvYd80p5S-rxSNQmMZwYXC7LyAzBmcfcj4MUUAdudWM` -- `--fee` to provide fee transaction, Example `--fee 1` -- `--post` to define automate post transaction or not. Example: `-post true` -- `--post-host` to provide where the transaction will post. Example: `--post-host "127.0.0.1:7000"` -- `--message` include an arbitrary message in the transaction (max 256 bytes). Example: `--message "test message"` - +``` ### Transaction Send Money - +```bash +Flags: + --amount int Amount of money we want to send + --approver-address string Escrow fields: Approver account address, require if escrow true + --commission int Escrow fields: Commission + --escrow Escrowable transaction ? need approver-address if yes (default true) + -h, --help help for send-money + --instruction string Escrow fields: Instruction + --timeout uint Escrow fields: Timeout transaction id +``` +Example: ``` -go run main.go transaction send-money --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --recipient ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU --amount 5000000000 +go run main.go transaction send-money --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --recipient 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073 --amount 5000000000 ``` ### Transaction send money escrow, set flag `--escrow true` and 3 more fields: `--approver-address`, `--timeout`, `--commission` and `--instruction` ```bash -go run main.go transaction send-money --escrow true --approver-address ZBC_EQAR73E3_JYON3222_KL5YYC54_Y54KMULE_KF4YSXUS_DR72QQNX_FOO2KA3L --timeout 200 --sender-seed "execute beach inflict session course dance vanish cover lawsuit earth casino fringe waste warfare also habit skull donate window cannon scene salute dawn good" --amount 1111 --commission 111 --instruction "Check amount should be 111" --recipient ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU +go run main.go transaction send-money --escrow true --approver-address 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073 --timeout 200 --sender-seed "execute beach inflict session course dance vanish cover lawsuit earth casino fringe waste warfare also habit skull donate window cannon scene salute dawn good" --amount 1111 --commission 111 --instruction "Check amount should be 111" --recipient ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU ``` ### Transaction Register Node ```bash -go run main.go transaction register-node --node-owner-account-address="ZBC_EQAR73E3_JYON3222_KL5YYC54_Y54KMULE_KF4YSXUS_DR72QQNX_FOO2KA3L" --sender-address="ZBC_EQAR73E3_JYON3222_KL5YYC54_Y54KMULE_KF4YSXUS_DR72QQNX_FOO2KA3L" --recipient="ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU" --sender-seed="pizza midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire miracle" --node-seed="armed midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire pizza" --locked-balance=100000000 +go run main.go transaction register-node --node-owner-account-address="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --sender-address="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --recipient="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --sender-seed="pizza midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire miracle" --node-seed="armed midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire pizza" --locked-balance=100000000 ``` ### Transaction Update Node Registration ```bash -go run main.go transaction update-node --timestamp 1257894000 --node-owner-account-address="ZBC_EQAR73E3_JYON3222_KL5YYC54_Y54KMULE_KF4YSXUS_DR72QQNX_FOO2KA3L" --sender-address="ZBC_EQAR73E3_JYON3222_KL5YYC54_Y54KMULE_KF4YSXUS_DR72QQNX_FOO2KA3L" --recipient="ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU" --sender-seed="pizza midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire miracle" --node-seed="armed midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire pizza" --locked-balance=100000000 +go run main.go transaction update-node --timestamp 1257894000 --node-owner-account-address="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --sender-address="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --recipient="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --sender-seed="pizza midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire miracle" --node-seed="armed midnight enforce morning panda entire fatal plastic piece roof edge subject soap taxi car swim cash future egg burden stone step fire pizza" --locked-balance=100000000 ``` ### Transaction Claim Node ```bash -go run main.go transaction claim-node --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --node-owner-account-address "ZBC_EQAR73E3_JYON3222_KL5YYC54_Y54KMULE_KF4YSXUS_DR72QQNX_FOO2KA3L" --node-seed "sprinkled sneak species pork outpost thrift unwind cheesy vexingly dizzy neurology neatness" --recipient "ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU" --poow-hex "7233537248687a792d35726c71475f644f473258626a504263574f68445552495070465267675254732d327458d880d3d1e6d68a8afeaa2c030ce50b7562fca7b7cb2ddac419c6e2ee33e0a7030000004d4e8d33954aa3deee656de56289e77d17ba29baff32da82147500e354ceaacf6cdafd6437a1037f243574dbeb2b81f52dd459ae8f0ee2ce4cbc272f832" +go run main.go transaction claim-node --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --node-owner-account-address "000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --node-seed "sprinkled sneak species pork outpost thrift unwind cheesy vexingly dizzy neurology neatness" --recipient "000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --poow-hex "7233537248687a792d35726c71475f644f473258626a504263574f68445552495070465267675254732d327458d880d3d1e6d68a8afeaa2c030ce50b7562fca7b7cb2ddac419c6e2ee33e0a7030000004d4e8d33954aa3deee656de56289e77d17ba29baff32da82147500e354ceaacf6cdafd6437a1037f243574dbeb2b81f52dd459ae8f0ee2ce4cbc272f832" ``` ### Transaction Remove Node @@ -76,13 +92,13 @@ go run main.go transaction remove-node --timestamp 1257894000 --sender-seed "con ### Transaction Set Account Dataset ```bash -go run main.go transaction set-account-dataset --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --recipient "ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU" --property "Member" --value "Welcome to the jungle" +go run main.go transaction set-account-dataset --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --recipient "000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --property "Member" --value "Welcome to the jungle" ``` ### Transaction Remove Account Dataset ```bash -go run main.go transaction remove-account-dataset --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --recipient "ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU" --property "Member" --value "Good Boy" +go run main.go transaction remove-account-dataset --timestamp 1257894000 --sender-seed "concur vocalist rotten busload gap quote stinging undiluted surfer goofiness deviation starved" --recipient "000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --property "Member" --value "Good Boy" ``` ### Transaction Escrow Approval @@ -115,6 +131,21 @@ So the completed comment it will be: go run main.go transaction multi-signature --sender-seed="execute beach inflict session course dance vanish cover lawsuit earth casino fringe waste warfare also habit skull donate window cannon scene salute dawn good" --unsigned-transaction="01000000012ba5ba5e000000002c000000486c5a4c683356636e4e6c764279576f417a584f51326a416c77464f69794f395f6e6a49336f7135596768612c000000486c38393154655446784767574f57664f4f464b59725f586468584e784f384a4b38576e4d4a56366738614c41420f0000000000080000000600000000000000000000000000000000000000000000000000000000000000" --transaction-hash="21ddbdada9903da81bf17dba6569ff7e2665fec38760c7f6636419ee30da65b0" --address-signatures="HlZLh3VcnNlvByWoAzXOQ2jAlwFOiyO9_njI3oq5Ygha=00000000b4efe21822c9d63818d8d19f6c608d917b2237426d1157b4e6689b22ce6c256ccf8ec8e2c1016ab09dd4ef2b01191fe2df70b7a123fec7115d7afd5a938f9b0a" ``` +### Transaction Atomic +Help: +```bash +Usage: + zoobc transaction atomic [flags] + +Flags: + -h, --help help for atomic + -i, --inners uint32 inners 2, indicate want to have 2 inner transaction (default 1) +``` +Example: +```bash + go run main.go transaction atomic --sender-seed "execute beach inflict session course dance vanish cover lawsuit earth casino fringe waste warfare also habit skull donate window cannon scene salute dawn good" --recipient 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073 +``` + ### Transaction Fee Vote Commitment Vote ```bash @@ -154,12 +185,12 @@ go run main.go account bitcoin --seed "concur vocalist rotten busload gap quote ### Account Generating multisig ```bash -go run main.go account multisig --addresses "BCZnSfqpP5tqFQlMTYkDeBVFWnbyVK7vLr5ORFpTjgtN" --addresses "BCZD_VxfO2S9aziIL3cn_cXW7uPDVPOrnXuP98GEAUC7" --addresses "BCZKLvgUYZ1KKx-jtF9KoJskjVPvB9jpIjfzzI6zDW0J" —-min-sigs=2 --nonce=3 +go run main.go account multisig --addresses "BCZnSfqpP5tqFQlMTYkDeBVFWnbyVK7vLr5ORFpTjgtN" --addresses "000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --addresses "BCZKLvgUYZ1KKx-jtF9KoJskjVPvB9jpIjfzzI6zDW0J" —-min-sigs=2 --nonce=3 ``` ### Account Converting from encoded to hex ```bash -go run main.go account hexconv --encodedAccountAddress="ZBC_3WWDF4S2_IZVG2HHD_VOPSCNGN_COLYZ2OZ_M4QJZ4OL_44YHTKVC_2TPZBZAU" --accountType=0 +go run main.go account hexconv --encodedAccountAddress="000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073" --accountType=0 ``` ### Account Decoding and hex-encoded full account address to its human readable encoded format diff --git a/cmd/snapshot/snapshot.go b/cmd/snapshot/snapshot.go index dc2bb5b4c..16456ca29 100644 --- a/cmd/snapshot/snapshot.go +++ b/cmd/snapshot/snapshot.go @@ -52,23 +52,22 @@ package snapshot import ( "crypto/sha256" "database/sql" - "github.com/zoobc/zoobc-core/common/crypto" "math/rand" "os" - "github.com/zoobc/zoobc-core/common/util" - "github.com/sirupsen/logrus" "github.com/spf13/cobra" "github.com/ugorji/go/codec" "github.com/zoobc/zoobc-core/common/auth" "github.com/zoobc/zoobc-core/common/chaintype" "github.com/zoobc/zoobc-core/common/constant" + "github.com/zoobc/zoobc-core/common/crypto" "github.com/zoobc/zoobc-core/common/database" "github.com/zoobc/zoobc-core/common/model" "github.com/zoobc/zoobc-core/common/query" "github.com/zoobc/zoobc-core/common/storage" "github.com/zoobc/zoobc-core/common/transaction" + "github.com/zoobc/zoobc-core/common/util" "github.com/zoobc/zoobc-core/core/service" "golang.org/x/crypto/sha3" ) @@ -152,6 +151,7 @@ func newSnapshotProcess() func(ccmd *cobra.Command, args []string) { query.NewFeeVoteRevealVoteQuery(), query.NewLiquidPaymentTransactionQuery(), query.NewNodeAdmissionTimestampQuery(), + query.NewAtomicTransactionQuery(), query.NewBlockQuery(mainChain), query.GetSnapshotQuery(mainChain), query.GetBlocksmithSafeQuery(mainChain), @@ -387,6 +387,7 @@ func storingPayloadProcess() func(ccmd *cobra.Command, args []string) { query.NewFeeVoteRevealVoteQuery(), query.NewLiquidPaymentTransactionQuery(), query.NewNodeAdmissionTimestampQuery(), + query.NewAtomicTransactionQuery(), query.NewBlockQuery(mainChain), query.GetSnapshotQuery(mainChain), query.GetBlocksmithSafeQuery(mainChain), diff --git a/cmd/transaction/cmd.go b/cmd/transaction/cmd.go index fff1bf519..a44a90093 100644 --- a/cmd/transaction/cmd.go +++ b/cmd/transaction/cmd.go @@ -51,8 +51,8 @@ package transaction import ( "database/sql" + "encoding/hex" "fmt" - "github.com/zoobc/zoobc-core/common/signaturetype" "os" "path" "time" @@ -65,6 +65,7 @@ import ( "github.com/zoobc/zoobc-core/common/database" "github.com/zoobc/zoobc-core/common/model" "github.com/zoobc/zoobc-core/common/query" + "github.com/zoobc/zoobc-core/common/signaturetype" "github.com/zoobc/zoobc-core/common/transaction" commonUtil "github.com/zoobc/zoobc-core/common/util" "golang.org/x/crypto/sha3" @@ -142,33 +143,54 @@ var ( Short: "transaction sub command used to generate 'liquid payment stop' transaction", Long: "transaction sub command used to generate 'liquid payment stop' transaction used to stop a particular liquid payment", } + atomicCmd = &cobra.Command{ + Use: "atomic", + Short: "transaction sub command used to generate `atomic` transaction", + Long: "transaction sub command used to generate `atomic` transaction", + } ) func init() { /* TXCommandRoot */ - txCmd.PersistentFlags().StringVar(&message, "message", "", "arbitrary message that can be added to any transaction") - txCmd.PersistentFlags().BoolVarP(&sign, "sign", "s", true, "defines transaction should be signed") - txCmd.PersistentFlags().StringVar(&outputType, "output", "bytes", "defines the type of the output to be generated [\"bytes\", \"hex\"]") - txCmd.PersistentFlags().Uint32Var(&version, "version", 1, "defines version of the transaction") - txCmd.PersistentFlags().Int64Var(×tamp, "timestamp", time.Now().Unix(), "defines timestamp of the transaction") + txCmd.PersistentFlags().StringVar( + &message, + "message", + "", + "--message \"test message\". Include an arbitrary message in the transaction (max 256 bytes)", + ) + txCmd.PersistentFlags().BoolVarP(&sign, "sign", "s", true, "--sign false. Defines transaction should be signed") + txCmd.PersistentFlags().StringVar(&outputType, "output", "bytes", "--output hex. Defines the type of the output to be generated") + txCmd.PersistentFlags().Uint32Var(&version, "version", 1, "--version 2. Defines version of the transaction") + txCmd.PersistentFlags().Int64Var(×tamp, "timestamp", time.Now().Unix(), "--timestamp 23456789. defines timestamp of the transaction") txCmd.PersistentFlags().StringVar(&senderSeed, "sender-seed", "", - "defines the sender seed that's used to sign transaction and whose public key will be used in the"+ + "--sender-seed mnemonic. Defines the sender seed that's used to sign transaction and whose public key will be used in the"+ "`Sender Account Address` field of the transaction") - txCmd.PersistentFlags().StringVar(&recipientAccountAddressHex, "recipient", "", "defines the recipient intended for the transaction") - txCmd.PersistentFlags().Int64Var(&fee, "fee", 1, "defines the fee of the transaction") - txCmd.PersistentFlags().BoolVar(&post, "post", false, "post generated bytes to [127.0.0.1:7000](default)") - txCmd.PersistentFlags().StringVar(&postHost, "post-host", "127.0.0.1:7000", "destination of post action") - txCmd.PersistentFlags().StringVar(&senderAddressHex, "sender-address", "", "transaction's sender address") - txCmd.PersistentFlags().StringVarP(&dbPath, "db-path", "p", "resource", "db-path is database path location") - txCmd.PersistentFlags().StringVarP(&dBName, "db-name", "n", "zoobc.db", "db-name is database name {name}.db") + txCmd.PersistentFlags().StringVar( + &recipientAccountAddressHex, + "recipient", + "", + "--recipient 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073. Provide recipient transaction hex format", + ) + txCmd.PersistentFlags().Int64Var(&fee, "fee", 1, "--fee 1. Defines the fee of the transaction") + txCmd.PersistentFlags().BoolVar(&post, "post", false, "--post. Post generated bytes to [127.0.0.1:7000](default)") + txCmd.PersistentFlags().StringVar(&postHost, "post-host", "127.0.0.1:7000", "--post-host \"127.0.0.1:7000\". Destination of post action") + txCmd.PersistentFlags().StringVar( + &senderAddressHex, + "sender-address", + "", + "--sender-address 000000006f5461d22d8b6ce3c9b76e2c1078bb1b475a9f5280d30b77353ff53514e5c073. "+ + "Transaction's sender address, [no necessary if contain --sender-seed]", + ) + txCmd.PersistentFlags().StringVarP(&dbPath, "db-path", "p", "resource", "--db-path \"resource\". Defines database path location") + txCmd.PersistentFlags().StringVarP(&dBName, "db-name", "n", "zoobc.db", "--db-name \"zoobc.db\". Defines database name {name}.db") /* SendMoney Command */ sendMoneyCmd.Flags().Int64Var(&sendAmount, "amount", 0, "Amount of money we want to send") sendMoneyCmd.Flags().BoolVar(&escrow, "escrow", true, "Escrowable transaction ? need approver-address if yes") - sendMoneyCmd.Flags().StringVar(&esApproverAddressHex, "approver-address", "", "Escrow fields: Approver account address") + sendMoneyCmd.Flags().StringVar(&esApproverAddressHex, "approver-address", "", "Escrow fields: Approver account address, require if escrow true") sendMoneyCmd.Flags().Uint64Var(&esTimeout, "timeout", 0, "Escrow fields: Timeout transaction id") sendMoneyCmd.Flags().Int64Var(&esCommission, "commission", 0, "Escrow fields: Commission") sendMoneyCmd.Flags().StringVar(&esInstruction, "instruction", "", "Escrow fields: Instruction") @@ -267,6 +289,10 @@ func init() { liquidPaymentStopCmd */ liquidPaymentStopCmd.Flags().Int64Var(&transactionID, "transaction-id", 0, "liquid payment stop transaction body field which is int64") + /* + atomicCmd + */ + atomicCmd.Flags().Uint32VarP(&inners, "inners", "i", 1, "inners 2, indicate want to have 2 inner transaction") } // Commands set TXGeneratorCommandsInstance that will used by whole commands @@ -301,6 +327,9 @@ func Commands() *cobra.Command { txCmd.AddCommand(liquidPaymentCmd) liquidPaymentStopCmd.Run = txGeneratorCommandsInstance.LiquidPaymentStopProcess() txCmd.AddCommand(liquidPaymentStopCmd) + atomicCmd.Run = txGeneratorCommandsInstance.AtomicProcess() + txCmd.AddCommand(atomicCmd) + return txCmd } @@ -320,7 +349,7 @@ func (*TXGeneratorCommands) SendMoneyProcess() RunCommand { if escrow { tx = GenerateEscrowedTransaction(tx) } - senderAccountType := getAccountTypeFromAccountHex(senderAddressHex).GetTypeInt() + senderAccountType := getAccountTypeFromAccountHex(hex.EncodeToString(tx.GetSenderAccountAddress())).GetTypeInt() PrintTx(GenerateSignedTxBytes(tx, senderSeed, senderAccountType, sign), outputType) } } @@ -742,3 +771,21 @@ func (*TXGeneratorCommands) LiquidPaymentStopProcess() RunCommand { PrintTx(GenerateSignedTxBytes(tx, senderSeed, senderAccountType, sign), outputType) } } + +func (*TXGeneratorCommands) AtomicProcess() RunCommand { + return func(ccmd *cobra.Command, args []string) { + tx := GenerateBasicTransaction( + senderAddressHex, + senderSeed, + version, + timestamp, + fee, + recipientAccountAddressHex, + message, + ) + + tx = GenerateAtomic(tx, inners) + senderAccountType := getAccountTypeFromAccountHex(hex.EncodeToString(tx.GetSenderAccountAddress())).GetTypeInt() + PrintTx(GenerateSignedTxBytes(tx, senderSeed, senderAccountType, sign), outputType) + } +} diff --git a/cmd/transaction/const.go b/cmd/transaction/const.go index 932a97c35..1c2549744 100644 --- a/cmd/transaction/const.go +++ b/cmd/transaction/const.go @@ -68,6 +68,7 @@ var ( "liquidPaymentStop": {6, 1, 0, 0}, "feeVoteCommit": {7, 0, 0, 0}, "feeVoteReveal": {7, 1, 0, 0}, + "atomic": {8, 0, 0, 0}, } signature = &crypto.Signature{} @@ -123,4 +124,7 @@ var ( dbPath, dBName string // liquidPayment completeMinutes uint64 + + // atomic transaction + inners uint32 ) diff --git a/cmd/transaction/generator.go b/cmd/transaction/generator.go index d22096d59..f1eb3caec 100644 --- a/cmd/transaction/generator.go +++ b/cmd/transaction/generator.go @@ -53,17 +53,17 @@ import ( "context" "encoding/hex" "fmt" - "github.com/zoobc/zoobc-core/common/accounttype" - "github.com/zoobc/zoobc-core/common/signaturetype" "log" "strings" "time" "github.com/zoobc/zoobc-core/cmd/admin" + "github.com/zoobc/zoobc-core/common/accounttype" "github.com/zoobc/zoobc-core/common/constant" "github.com/zoobc/zoobc-core/common/model" "github.com/zoobc/zoobc-core/common/query" rpcService "github.com/zoobc/zoobc-core/common/service" + "github.com/zoobc/zoobc-core/common/signaturetype" "github.com/zoobc/zoobc-core/common/transaction" "github.com/zoobc/zoobc-core/common/util" "golang.org/x/crypto/sha3" @@ -288,7 +288,7 @@ func GenerateBasicTransaction( message string, ) *model.Transaction { if senderAccountAddressHex == "" && senderSeed != "" { - accountType := getAccountTypeFromAccountHex(senderAccountAddressHex) + accountType := &accounttype.ZbcAccountType{} // TODO: move this into AccountType interface switch accountType.GetSignatureType() { case model.SignatureType_DefaultSignature: @@ -300,10 +300,17 @@ func GenerateBasicTransaction( if err != nil { panic(err.Error()) } - senderAccountAddressHex, err = signaturetype.NewEd25519Signature().GetAddressFromPublicKey(constant.PrefixZoobcDefaultAccount, bb) - if err != nil { - panic(err.Error()) + + accType, e := accounttype.NewAccountType(accountType.GetTypeInt(), bb) + if e != nil { + panic(e) } + senderBytes, e := accType.GetAccountAddress() + if e != nil { + panic(e) + } + senderAccountAddressHex = hex.EncodeToString(senderBytes) + case model.SignatureType_BitcoinSignature: var ( bitcoinSig = signaturetype.NewBitcoinSignature(signaturetype.DefaultBitcoinNetworkParams(), signaturetype.DefaultBitcoinCurve()) @@ -417,7 +424,9 @@ func GenerateSignedTxBytes( tx.Fee += minimumFee unsignedTxBytes, _ := transactionUtil.GetTransactionBytes(tx, false) - if senderSeed == "" { + wantToSign, _ := optionalSignParams[0].(bool) + + if senderSeed == "" || !wantToSign { return unsignedTxBytes } txBytesHash := sha3.Sum256(unsignedTxBytes) @@ -650,7 +659,7 @@ func GenerateTxLiquidPayment(tx *model.Transaction, sendAmount int64, completeMi return tx } -// GenerateTxLiquidPaymentStop return liquid payment stop transaction based on provided basic transaction & ammunt +// GenerateTxLiquidPaymentStop return liquid payment stop transaction based on provided basic transaction & amount func GenerateTxLiquidPaymentStop(tx *model.Transaction, transactionID int64) *model.Transaction { txBody := &model.LiquidPaymentStopTransactionBody{ TransactionID: transactionID, @@ -666,3 +675,79 @@ func GenerateTxLiquidPaymentStop(tx *model.Transaction, transactionID int64) *mo tx.TransactionBodyLength = uint32(len(txBodyBytes)) return tx } + +// GenerateAtomic return atomic transaction based on provided basic transaction +func GenerateAtomic(tx *model.Transaction, innerCount uint32) *model.Transaction { + var ( + unsignedTXBytes = make([][]byte, 0) + hashTransactions = make([]byte, 0) + unsignedTransactions = make([]*model.Transaction, 0) + err error + ) + + for i := 0; i < int(innerCount); i++ { + var ( + senderHex = hex.EncodeToString(tx.GetSenderAccountAddress()) + ) + + innerTX := GenerateBasicTransaction( + senderHex, + senderSeed, + version, + timestamp, + fee, + recipientAccountAddressHex, + message, + ) + innerTX = GenerateTxSendMoney(innerTX, 10) + unsignedTransactions = append(unsignedTransactions, innerTX) + + senderAccountType := getAccountTypeFromAccountHex(hex.EncodeToString(innerTX.GetSenderAccountAddress())).GetTypeInt() + unsignedBytes := GenerateSignedTxBytes(innerTX, senderSeed, senderAccountType, false) + unsignedTXBytes = append(unsignedTXBytes, unsignedBytes) + + txBytesHash := sha3.Sum256(unsignedBytes) + hashTransactions = append(hashTransactions, txBytesHash[:]...) + + innerTX.Signature, err = signature.Sign( + txBytesHash[:], + model.AccountType(senderAccountType), + senderSeed, + true, + ) + if err != nil { + panic(err) + } + } + + var ( + signatures = make(map[string][]byte) + signTX []byte + ) + for _, unsignedTX := range unsignedTransactions { + signTX, err = signature.Sign( + hashTransactions, + model.AccountType(getAccountTypeFromAccountHex(hex.EncodeToString(unsignedTX.GetSenderAccountAddress())).GetTypeInt()), + senderSeed, + true, + ) + if err != nil { + panic(err) + } + signatures[hex.EncodeToString(unsignedTX.GetSenderAccountAddress())] = signTX + } + + txBody := &model.AtomicTransactionBody{ + UnsignedTransactionBytes: unsignedTXBytes, + Signatures: signatures, + } + txBodyBytes, _ := (&transaction.AtomicTransaction{ + Body: txBody, + }).GetBodyBytes() + + tx.TransactionBodyBytes = txBodyBytes + tx.TransactionBodyLength = uint32(len(txBodyBytes)) + tx.TransactionType = util.ConvertBytesToUint32(txTypeMap["atomic"]) + + return tx +} diff --git a/common/database/migration.go b/common/database/migration.go index fe6e6aea6..7058569ac 100644 --- a/common/database/migration.go +++ b/common/database/migration.go @@ -355,7 +355,7 @@ func (m *Migration) Init() error { `, ` ALTER TABLE "transaction" - ADD COLUMN "multisig_child" INTEGER DEFAULT 0 + ADD COLUMN "child_type" INTEGER DEFAULT 0 -- indicate transaction is a child of transaction `, ` CREATE INDEX "node_registry_height_idx" ON "node_registry" ("height") @@ -537,6 +537,25 @@ func (m *Migration) Init() error { ALTER TABLE "transaction" ADD COLUMN "message" BLOB `, + `CREATE TABLE IF NOT EXISTS "atomic_transaction" ( + "id" INTEGER, -- relative to transaction.id + "transaction_id" INTEGER, -- relative to transaction.id which is the wrapper transaction + "sender_address" BLOB, -- account address + "block_height" INTEGER, -- reference block height + "unsigned_transaction" BLOB, -- one if unsigned transaction bytes has included + "signature" BLOB, -- combined unsigned transaction bytes collection hash signature + "atomic_index" INTEGER, -- position/index on wrapper unsigned transaction collection + PRIMARY KEY("id","sender_address") -- primary key + )`, + ` + CREATE INDEX "transaction_id_idx" ON "atomic_transaction" ("transaction_id") + `, + ` + CREATE INDEX "sender_address_idx" ON "atomic_transaction" ("sender_address") + `, + ` + CREATE INDEX "block_height_idx" ON "atomic_transaction" ("block_height") + `, } return nil } diff --git a/common/model/atomic.pb.go b/common/model/atomic.pb.go new file mode 100644 index 000000000..85535f1ef --- /dev/null +++ b/common/model/atomic.pb.go @@ -0,0 +1,134 @@ +// Code generated by protoc-gen-go. DO NOT EDIT. +// source: model/atomic.proto + +package model + +import ( + fmt "fmt" + proto "github.com/golang/protobuf/proto" + math "math" +) + +// Reference imports to suppress errors if they are not otherwise used. +var _ = proto.Marshal +var _ = fmt.Errorf +var _ = math.Inf + +// This is a compile-time assertion to ensure that this generated file +// is compatible with the proto package it is being compiled against. +// A compilation error at this line likely means your copy of the +// proto package needs to be updated. +const _ = proto.ProtoPackageIsVersion3 // please upgrade the proto package + +type Atomic struct { + ID int64 `protobuf:"varint,1,opt,name=ID,proto3" json:"ID,omitempty"` + // TransactionID is reference transaction.id which is the wrapper + TransactionID int64 `protobuf:"varint,2,opt,name=TransactionID,proto3" json:"TransactionID,omitempty"` + SenderAddress []byte `protobuf:"bytes,3,opt,name=SenderAddress,proto3" json:"SenderAddress,omitempty"` + BlockHeight uint32 `protobuf:"varint,4,opt,name=BlockHeight,proto3" json:"BlockHeight,omitempty"` + UnsignedTransaction []byte `protobuf:"bytes,5,opt,name=UnsignedTransaction,proto3" json:"UnsignedTransaction,omitempty"` + Signature []byte `protobuf:"bytes,6,opt,name=Signature,proto3" json:"Signature,omitempty"` + AtomicIndex uint32 `protobuf:"varint,7,opt,name=AtomicIndex,proto3" json:"AtomicIndex,omitempty"` + XXX_NoUnkeyedLiteral struct{} `json:"-"` + XXX_unrecognized []byte `json:"-"` + XXX_sizecache int32 `json:"-"` +} + +func (m *Atomic) Reset() { *m = Atomic{} } +func (m *Atomic) String() string { return proto.CompactTextString(m) } +func (*Atomic) ProtoMessage() {} +func (*Atomic) Descriptor() ([]byte, []int) { + return fileDescriptor_cae14e4104d09dca, []int{0} +} + +func (m *Atomic) XXX_Unmarshal(b []byte) error { + return xxx_messageInfo_Atomic.Unmarshal(m, b) +} +func (m *Atomic) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + return xxx_messageInfo_Atomic.Marshal(b, m, deterministic) +} +func (m *Atomic) XXX_Merge(src proto.Message) { + xxx_messageInfo_Atomic.Merge(m, src) +} +func (m *Atomic) XXX_Size() int { + return xxx_messageInfo_Atomic.Size(m) +} +func (m *Atomic) XXX_DiscardUnknown() { + xxx_messageInfo_Atomic.DiscardUnknown(m) +} + +var xxx_messageInfo_Atomic proto.InternalMessageInfo + +func (m *Atomic) GetID() int64 { + if m != nil { + return m.ID + } + return 0 +} + +func (m *Atomic) GetTransactionID() int64 { + if m != nil { + return m.TransactionID + } + return 0 +} + +func (m *Atomic) GetSenderAddress() []byte { + if m != nil { + return m.SenderAddress + } + return nil +} + +func (m *Atomic) GetBlockHeight() uint32 { + if m != nil { + return m.BlockHeight + } + return 0 +} + +func (m *Atomic) GetUnsignedTransaction() []byte { + if m != nil { + return m.UnsignedTransaction + } + return nil +} + +func (m *Atomic) GetSignature() []byte { + if m != nil { + return m.Signature + } + return nil +} + +func (m *Atomic) GetAtomicIndex() uint32 { + if m != nil { + return m.AtomicIndex + } + return 0 +} + +func init() { + proto.RegisterType((*Atomic)(nil), "model.Atomic") +} + +func init() { proto.RegisterFile("model/atomic.proto", fileDescriptor_cae14e4104d09dca) } + +var fileDescriptor_cae14e4104d09dca = []byte{ + // 235 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x6c, 0xd0, 0xb1, 0x4e, 0xc3, 0x30, + 0x10, 0x06, 0x60, 0x39, 0xa5, 0x41, 0x18, 0xca, 0x60, 0x16, 0x0f, 0x0c, 0x11, 0x62, 0x88, 0x90, + 0x68, 0x90, 0x78, 0x82, 0x56, 0x19, 0xc8, 0x9a, 0xc2, 0xc2, 0xe6, 0xd8, 0x27, 0xd7, 0xa2, 0xbe, + 0x43, 0xb6, 0x2b, 0x21, 0x9e, 0x9c, 0x11, 0xd5, 0x19, 0x48, 0x24, 0x16, 0x0f, 0xdf, 0x9d, 0xfc, + 0xeb, 0x7e, 0x2e, 0x3c, 0x19, 0x38, 0x34, 0x2a, 0x91, 0x77, 0x7a, 0xfd, 0x19, 0x28, 0x91, 0x58, + 0x66, 0xbb, 0xfb, 0x61, 0xbc, 0xdc, 0x64, 0x17, 0xd7, 0xbc, 0xe8, 0x5a, 0xc9, 0x2a, 0x56, 0x2f, + 0xfa, 0xa2, 0x6b, 0xc5, 0x3d, 0x5f, 0xbd, 0x06, 0x85, 0x51, 0xe9, 0xe4, 0x08, 0xbb, 0x56, 0x16, + 0x79, 0x34, 0xc7, 0xd3, 0xd6, 0x0e, 0xd0, 0x40, 0xd8, 0x18, 0x13, 0x20, 0x46, 0xb9, 0xa8, 0x58, + 0x7d, 0xd5, 0xcf, 0x51, 0x54, 0xfc, 0x72, 0x7b, 0x20, 0xfd, 0xf1, 0x02, 0xce, 0xee, 0x93, 0x3c, + 0xab, 0x58, 0xbd, 0xea, 0xa7, 0x24, 0x9e, 0xf8, 0xcd, 0x1b, 0x46, 0x67, 0x11, 0xcc, 0x24, 0x40, + 0x2e, 0xf3, 0x6f, 0xff, 0x8d, 0xc4, 0x2d, 0xbf, 0xd8, 0x39, 0x8b, 0x2a, 0x1d, 0x03, 0xc8, 0x32, + 0xef, 0xfd, 0xc1, 0x29, 0x71, 0xbc, 0xab, 0x43, 0x03, 0x5f, 0xf2, 0x7c, 0x4c, 0x9c, 0xd0, 0xf6, + 0xe1, 0xbd, 0xb6, 0x2e, 0xed, 0x8f, 0xc3, 0x5a, 0x93, 0x6f, 0xbe, 0x89, 0x06, 0x3d, 0xbe, 0x8f, + 0x9a, 0x02, 0x34, 0x9a, 0xbc, 0x27, 0x6c, 0x72, 0x4d, 0x43, 0x99, 0x4b, 0x7b, 0xfe, 0x0d, 0x00, + 0x00, 0xff, 0xff, 0xc2, 0x1a, 0xc5, 0xfa, 0x4a, 0x01, 0x00, 0x00, +} diff --git a/common/model/event.pb.go b/common/model/event.pb.go index 05b2fa606..ff43394a6 100644 --- a/common/model/event.pb.go +++ b/common/model/event.pb.go @@ -89,6 +89,7 @@ const ( EventType_EventLiquidPaymentPaidTransaction EventType = 14 EventType_EventLiquidPaymentStopTransaction EventType = 15 EventType_EventEscrowedTransaction EventType = 16 + EventType_EventAtomicTransaction EventType = 17 ) var EventType_name = map[int32]string{ @@ -109,6 +110,7 @@ var EventType_name = map[int32]string{ 14: "EventLiquidPaymentPaidTransaction", 15: "EventLiquidPaymentStopTransaction", 16: "EventEscrowedTransaction", + 17: "EventAtomicTransaction", } var EventType_value = map[string]int32{ @@ -129,6 +131,7 @@ var EventType_value = map[string]int32{ "EventLiquidPaymentPaidTransaction": 14, "EventLiquidPaymentStopTransaction": 15, "EventEscrowedTransaction": 16, + "EventAtomicTransaction": 17, } func (x EventType) String() string { @@ -143,32 +146,31 @@ func init() { proto.RegisterEnum("model.EventType", EventType_name, EventType_value) } -func init() { - proto.RegisterFile("model/event.proto", fileDescriptor_24dabb9f57ff37c9) -} +func init() { proto.RegisterFile("model/event.proto", fileDescriptor_24dabb9f57ff37c9) } var fileDescriptor_24dabb9f57ff37c9 = []byte{ - // 345 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x7c, 0xd2, 0xcf, 0x4e, 0x32, 0x31, - 0x10, 0x00, 0xf0, 0xef, 0x53, 0x40, 0x28, 0x28, 0x6b, 0x4f, 0x9a, 0x88, 0x11, 0x05, 0x45, 0x12, - 0xd9, 0x83, 0x4f, 0x80, 0x88, 0x27, 0x31, 0x04, 0xd0, 0x83, 0xb7, 0xd2, 0x9d, 0x60, 0x93, 0x6d, - 0x67, 0xed, 0x76, 0x97, 0xac, 0x8f, 0xeb, 0x93, 0x18, 0x0a, 0x21, 0xc5, 0x3f, 0x5c, 0x36, 0x99, - 0x99, 0xdf, 0x76, 0x32, 0xed, 0x90, 0x43, 0x89, 0x01, 0x84, 0x3e, 0xa4, 0xa0, 0x4c, 0x27, 0xd2, - 0x68, 0x90, 0xe6, 0x6d, 0xaa, 0xfd, 0x99, 0x23, 0xa5, 0xfe, 0x22, 0x3d, 0xc9, 0x22, 0xa0, 0x15, - 0x52, 0xb4, 0x41, 0x57, 0x65, 0xde, 0x3f, 0x5a, 0x23, 0xc7, 0x36, 0x1a, 0x83, 0x0a, 0x06, 0xa8, - 0x20, 0x9b, 0x68, 0xa6, 0x62, 0xc6, 0x8d, 0x40, 0xe5, 0xfd, 0xa7, 0x0d, 0x72, 0x66, 0xcb, 0x4f, - 0x18, 0xc0, 0x08, 0x66, 0x22, 0x36, 0x9a, 0x2d, 0x4a, 0xae, 0xda, 0xa1, 0x6d, 0x72, 0x69, 0xd5, - 0x73, 0x14, 0x30, 0x03, 0xdb, 0xec, 0xee, 0xda, 0x8e, 0x40, 0x62, 0xba, 0xd5, 0xe6, 0xe8, 0x35, - 0x69, 0x5a, 0xdb, 0x0b, 0x99, 0x90, 0xdb, 0x68, 0x9e, 0x5e, 0x91, 0x8b, 0xd5, 0x1c, 0x26, 0x89, - 0xba, 0x9c, 0x63, 0xa2, 0xcc, 0x3d, 0x33, 0x2c, 0x06, 0xe3, 0xc2, 0x02, 0x6d, 0x91, 0x86, 0xd3, - 0xff, 0x6f, 0xb9, 0x47, 0xab, 0xa4, 0xbc, 0x92, 0x73, 0xa6, 0x03, 0xaf, 0x48, 0xcf, 0xc9, 0xe9, - 0xf2, 0xe6, 0xa2, 0x48, 0x63, 0xca, 0xc2, 0x7e, 0xcc, 0x35, 0xce, 0xdd, 0x9f, 0x4a, 0x6b, 0x33, - 0x48, 0x42, 0x23, 0xc6, 0x62, 0xa6, 0x98, 0x49, 0x34, 0xb8, 0x86, 0xd0, 0x3a, 0xa9, 0x59, 0xf3, - 0x00, 0xf0, 0x82, 0x06, 0x7a, 0x28, 0xa5, 0xd8, 0xe8, 0x5d, 0xfe, 0x4e, 0x46, 0x90, 0x02, 0x0b, - 0x5d, 0x52, 0x59, 0x93, 0x47, 0xf1, 0x9e, 0x88, 0x60, 0xc8, 0x32, 0xb9, 0x78, 0x61, 0x87, 0xec, - 0xd3, 0x26, 0xa9, 0xff, 0x24, 0x43, 0x26, 0x02, 0x97, 0x1d, 0xfc, 0xce, 0xc6, 0x06, 0x23, 0x97, - 0x55, 0xe9, 0x09, 0x39, 0xb2, 0x6c, 0x39, 0x36, 0x6c, 0x1c, 0xe2, 0xdd, 0xb5, 0x5f, 0x5b, 0x33, - 0x61, 0xde, 0x92, 0x69, 0x87, 0xa3, 0xf4, 0x3f, 0x10, 0xa7, 0x7c, 0xf9, 0xbd, 0xe1, 0xa8, 0xc1, - 0xe7, 0x28, 0x25, 0x2a, 0xdf, 0x2e, 0xe4, 0xb4, 0x60, 0xd7, 0xf3, 0xf6, 0x2b, 0x00, 0x00, 0xff, - 0xff, 0x57, 0x47, 0x7f, 0x63, 0xb3, 0x02, 0x00, 0x00, + // 359 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x7c, 0xd2, 0x5f, 0x8f, 0xd2, 0x40, + 0x10, 0x00, 0x70, 0xff, 0x00, 0xc2, 0x80, 0x52, 0xf6, 0xc1, 0xa8, 0x11, 0x23, 0x0a, 0x8a, 0x24, + 0xd2, 0x07, 0x3f, 0x01, 0x22, 0x3e, 0x89, 0x21, 0x80, 0x3e, 0xdc, 0xdb, 0xb2, 0x9d, 0x70, 0x9b, + 0x74, 0x77, 0x7a, 0xdb, 0x6d, 0x49, 0xef, 0xc3, 0x5f, 0x2e, 0x6c, 0x09, 0x59, 0xee, 0x0f, 0x2f, + 0x4d, 0x66, 0xe6, 0xd7, 0x4e, 0x66, 0x3a, 0xd0, 0x51, 0x14, 0x61, 0x1c, 0x62, 0x8e, 0xda, 0x8e, + 0x13, 0x43, 0x96, 0x58, 0xd5, 0xa5, 0x46, 0x37, 0x15, 0x68, 0xcc, 0xf6, 0xe9, 0x75, 0x91, 0x20, + 0x6b, 0x41, 0xdd, 0x05, 0x13, 0x5d, 0x04, 0x4f, 0x58, 0x17, 0xde, 0xba, 0x68, 0x85, 0x3a, 0x9a, + 0x93, 0xc6, 0x62, 0x6d, 0xb8, 0x4e, 0xb9, 0xb0, 0x92, 0x74, 0xf0, 0x94, 0xf5, 0xe1, 0xa3, 0x2b, + 0xff, 0xa5, 0x08, 0x97, 0xb8, 0x95, 0xa9, 0x35, 0x7c, 0x5f, 0xf2, 0xd5, 0x33, 0x36, 0x82, 0x2f, + 0x4e, 0xfd, 0x4b, 0x22, 0x6e, 0xf1, 0x9c, 0x7d, 0x7e, 0xb4, 0x4b, 0x54, 0x94, 0x9f, 0xb5, 0x15, + 0xf6, 0x0d, 0x06, 0xce, 0x4e, 0x63, 0x2e, 0xd5, 0x39, 0x5a, 0x65, 0x5f, 0xe1, 0xf3, 0x61, 0x0e, + 0x9b, 0x25, 0x13, 0x21, 0x28, 0xd3, 0xf6, 0x17, 0xb7, 0x3c, 0x45, 0xeb, 0xc3, 0x1a, 0x1b, 0x42, + 0xdf, 0xeb, 0xff, 0xb8, 0x7c, 0xc1, 0xda, 0xd0, 0x3c, 0xc8, 0x1d, 0x37, 0x51, 0x50, 0x67, 0x9f, + 0xe0, 0x43, 0xb9, 0xb9, 0x24, 0x31, 0x94, 0xf3, 0x78, 0x96, 0x0a, 0x43, 0x3b, 0xff, 0xa5, 0xc6, + 0xd1, 0xcc, 0xb3, 0xd8, 0xca, 0x95, 0xdc, 0x6a, 0x6e, 0x33, 0x83, 0xbe, 0x01, 0xd6, 0x83, 0xae, + 0x33, 0xbf, 0x11, 0xff, 0x93, 0xc5, 0x29, 0x29, 0x25, 0x4f, 0x7a, 0x37, 0xef, 0x92, 0x25, 0xe6, + 0xc8, 0x63, 0x9f, 0xb4, 0x8e, 0xe4, 0x8f, 0xbc, 0xca, 0x64, 0xb4, 0xe0, 0x85, 0xda, 0xff, 0x61, + 0x8f, 0xbc, 0x64, 0x03, 0xe8, 0xdd, 0x27, 0x0b, 0x2e, 0x23, 0x9f, 0xbd, 0x7a, 0x98, 0xad, 0x2c, + 0x25, 0x3e, 0x6b, 0xb3, 0xf7, 0xf0, 0xc6, 0xb1, 0x72, 0x6c, 0x3c, 0xf9, 0x48, 0xc0, 0xde, 0xc1, + 0xeb, 0x72, 0x39, 0x96, 0x94, 0x14, 0x7e, 0xad, 0xf3, 0x73, 0x74, 0x31, 0xdc, 0x4a, 0x7b, 0x99, + 0x6d, 0xc6, 0x82, 0x54, 0x78, 0x4d, 0xb4, 0x11, 0xe5, 0xf3, 0xbb, 0x20, 0x83, 0xa1, 0x20, 0xa5, + 0x48, 0x87, 0xee, 0x58, 0x37, 0x35, 0x77, 0xba, 0x3f, 0x6e, 0x03, 0x00, 0x00, 0xff, 0xff, 0x16, + 0x5d, 0xdb, 0x17, 0xcf, 0x02, 0x00, 0x00, } diff --git a/common/model/snapshot.pb.go b/common/model/snapshot.pb.go index b06823460..7febd1ceb 100644 --- a/common/model/snapshot.pb.go +++ b/common/model/snapshot.pb.go @@ -168,6 +168,7 @@ type SnapshotPayload struct { LiquidPayment []*LiquidPayment `protobuf:"bytes,15,rep,name=LiquidPayment,proto3" json:"LiquidPayment,omitempty"` NodeAdmissionTimestamp []*NodeAdmissionTimestamp `protobuf:"bytes,16,rep,name=NodeAdmissionTimestamp,proto3" json:"NodeAdmissionTimestamp,omitempty"` MultiSignatureParticipants []*MultiSignatureParticipant `protobuf:"bytes,17,rep,name=MultiSignatureParticipants,proto3" json:"MultiSignatureParticipants,omitempty"` + AtomicTransaction []*Atomic `protobuf:"bytes,18,rep,name=AtomicTransaction,proto3" json:"AtomicTransaction,omitempty"` XXX_NoUnkeyedLiteral struct{} `json:"-"` XXX_unrecognized []byte `json:"-"` XXX_sizecache int32 `json:"-"` @@ -317,61 +318,68 @@ func (m *SnapshotPayload) GetMultiSignatureParticipants() []*MultiSignatureParti return nil } +func (m *SnapshotPayload) GetAtomicTransaction() []*Atomic { + if m != nil { + return m.AtomicTransaction + } + return nil +} + func init() { proto.RegisterType((*SnapshotFileInfo)(nil), "model.SnapshotFileInfo") proto.RegisterType((*SnapshotPayload)(nil), "model.SnapshotPayload") } -func init() { - proto.RegisterFile("model/snapshot.proto", fileDescriptor_5d9d8140a8c06fc6) -} +func init() { proto.RegisterFile("model/snapshot.proto", fileDescriptor_5d9d8140a8c06fc6) } var fileDescriptor_5d9d8140a8c06fc6 = []byte{ - // 731 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x7c, 0x55, 0x5f, 0x4f, 0xdb, 0x3a, - 0x14, 0x57, 0x29, 0xed, 0x05, 0x43, 0x29, 0x35, 0x7f, 0xae, 0xa9, 0xe0, 0x2a, 0x42, 0xf7, 0xa1, - 0x62, 0x5a, 0x2b, 0xb1, 0xb7, 0x49, 0xdb, 0x04, 0x8c, 0x8a, 0x69, 0x63, 0xaa, 0x5c, 0xb6, 0x87, - 0x3d, 0xcd, 0x75, 0x4c, 0x63, 0x91, 0xd8, 0x59, 0xec, 0x6c, 0x63, 0x5f, 0x6c, 0x2f, 0xfb, 0x70, - 0x53, 0x1c, 0xa7, 0xd4, 0x49, 0xe0, 0xa5, 0x52, 0xce, 0xef, 0x4f, 0xfc, 0x3b, 0xf1, 0x39, 0x05, - 0xbb, 0x91, 0xf4, 0x59, 0x38, 0x52, 0x82, 0xc4, 0x2a, 0x90, 0x7a, 0x18, 0x27, 0x52, 0x4b, 0xd8, - 0x32, 0xd5, 0xfe, 0x7f, 0x16, 0x8c, 0xb9, 0x60, 0xe7, 0xa1, 0xa4, 0x77, 0xd7, 0x44, 0xf0, 0x5b, - 0xa6, 0x2c, 0xad, 0xdf, 0xcf, 0x71, 0x42, 0xa9, 0x4c, 0x85, 0x3e, 0x27, 0x21, 0x11, 0x94, 0x59, - 0xec, 0x30, 0xc7, 0x84, 0xf4, 0x19, 0x66, 0x73, 0xae, 0x74, 0x42, 0x34, 0x97, 0xa2, 0x56, 0xf9, - 0x96, 0x68, 0xa2, 0x58, 0xe1, 0x6a, 0xdf, 0x1a, 0x93, 0x44, 0x73, 0xca, 0x63, 0x23, 0x9b, 0x52, - 0x99, 0x94, 0x9c, 0xe3, 0x74, 0x16, 0x72, 0x15, 0x30, 0x1f, 0x33, 0xca, 0x78, 0x5c, 0xa8, 0x61, - 0x8e, 0x32, 0x45, 0x13, 0xf9, 0xc3, 0x7d, 0x5b, 0x94, 0x86, 0x9a, 0x4f, 0xf9, 0x5c, 0x10, 0x9d, - 0x2e, 0xdc, 0x7a, 0x39, 0x36, 0xcb, 0xe2, 0xd9, 0xd2, 0x91, 0x8d, 0x7d, 0xc7, 0xe3, 0x98, 0xf9, - 0x26, 0xb8, 0x8a, 0xb8, 0x0e, 0x2c, 0x6c, 0x5b, 0x76, 0xcb, 0xd8, 0x94, 0x92, 0xb0, 0xf0, 0xd9, - 0x59, 0x54, 0x3f, 0x4b, 0x5d, 0x14, 0x0f, 0xf2, 0x62, 0xc8, 0xbf, 0xa5, 0xdc, 0x9f, 0x90, 0xfb, - 0x88, 0x09, 0x7b, 0xce, 0xe3, 0xdf, 0x2b, 0x60, 0x7b, 0x6a, 0xbb, 0x3e, 0xe6, 0x21, 0x7b, 0x27, - 0x6e, 0x25, 0x3c, 0x71, 0x6b, 0x57, 0x44, 0x05, 0xa8, 0xe1, 0x35, 0x06, 0x9b, 0xb8, 0x52, 0x87, - 0xfb, 0xa0, 0x7d, 0xc5, 0xf8, 0x3c, 0xd0, 0x68, 0xc5, 0x6b, 0x0c, 0x3a, 0xd8, 0x3e, 0xc1, 0xd7, - 0xa0, 0x3f, 0x49, 0x24, 0x65, 0x4a, 0x5d, 0xfe, 0x8c, 0x79, 0xde, 0xf5, 0x1b, 0x1e, 0x31, 0xa5, - 0x49, 0x14, 0xa3, 0xa6, 0xd7, 0x18, 0x34, 0xf1, 0x13, 0x0c, 0x78, 0x08, 0xd6, 0x2f, 0x02, 0xc2, - 0xc5, 0xcd, 0x7d, 0xcc, 0xd0, 0xaa, 0xd7, 0x18, 0xb4, 0xf0, 0x43, 0x01, 0x7e, 0x02, 0xfb, 0xd3, - 0xca, 0x75, 0x30, 0xd4, 0x96, 0xd7, 0x18, 0x6c, 0x9d, 0x1e, 0x0d, 0x4d, 0xe4, 0x61, 0x3d, 0x09, - 0x3f, 0x22, 0xce, 0x82, 0x67, 0xc1, 0x2e, 0x82, 0x54, 0xdc, 0xa9, 0x2c, 0x1e, 0x53, 0xa8, 0xed, - 0x35, 0xb3, 0xe0, 0xe5, 0xfa, 0xf1, 0x9f, 0x75, 0xd0, 0x2d, 0xba, 0x31, 0x21, 0xf7, 0xa1, 0x24, - 0x3e, 0xfc, 0x1f, 0xb4, 0xf3, 0xef, 0x84, 0x1a, 0x5e, 0x73, 0xb0, 0x71, 0xba, 0x69, 0x8f, 0x61, - 0x8a, 0xd8, 0x62, 0xf0, 0x0d, 0xe8, 0x9e, 0x39, 0x77, 0x55, 0xa1, 0x15, 0x43, 0xdf, 0xb3, 0x74, - 0x17, 0xc5, 0x65, 0x36, 0xbc, 0x04, 0xbd, 0x8f, 0xa5, 0x0b, 0xad, 0x50, 0xd3, 0x58, 0xfc, 0x6b, - 0x2d, 0xca, 0x38, 0xae, 0x2a, 0x96, 0xce, 0x61, 0x6f, 0xbe, 0x42, 0xab, 0x75, 0xe7, 0xb0, 0x28, - 0x2e, 0xb3, 0xe1, 0x7b, 0xb0, 0x33, 0xa9, 0x8c, 0x87, 0x42, 0x2d, 0x63, 0x72, 0x60, 0x4d, 0xaa, - 0x0c, 0x5c, 0xa7, 0xca, 0x42, 0x4d, 0x4a, 0xb3, 0x94, 0x37, 0xff, 0x21, 0x54, 0x19, 0xc7, 0x55, - 0x05, 0x7c, 0x05, 0xe0, 0xa5, 0x19, 0xba, 0x9b, 0x84, 0x08, 0x45, 0x68, 0xde, 0x9c, 0x7f, 0x8c, - 0x4f, 0xc7, 0xfa, 0xe4, 0x04, 0x5c, 0x43, 0x34, 0x91, 0x98, 0xf0, 0xb9, 0x98, 0x3b, 0xfa, 0x35, - 0x37, 0x52, 0x85, 0x81, 0xeb, 0x54, 0x26, 0x52, 0x5e, 0x5e, 0x8c, 0xbb, 0x42, 0xeb, 0x6e, 0xa4, - 0x12, 0x8e, 0xab, 0x8a, 0xec, 0x4c, 0xd7, 0xce, 0xce, 0xc8, 0x86, 0x54, 0x21, 0xe0, 0x9c, 0xa9, - 0xca, 0xc0, 0x75, 0x2a, 0x78, 0x05, 0xe0, 0xb4, 0xbc, 0x51, 0x14, 0xda, 0x30, 0x5e, 0xa8, 0x98, - 0x9a, 0x32, 0x01, 0xd7, 0x68, 0xe0, 0x33, 0xb0, 0x36, 0xb6, 0xcb, 0x07, 0x6d, 0x1a, 0x7d, 0xd7, - 0xea, 0x8b, 0x32, 0x5e, 0x10, 0x20, 0x06, 0x7b, 0xe3, 0x7c, 0x27, 0x5d, 0xc8, 0x28, 0xe2, 0x3a, - 0x5b, 0x41, 0xd9, 0x13, 0xea, 0x18, 0xe5, 0xe1, 0x83, 0xb2, 0xca, 0xc1, 0xf5, 0x52, 0x38, 0x06, - 0x3d, 0x0b, 0x60, 0xf6, 0x9d, 0x91, 0xd0, 0xf8, 0x6d, 0x39, 0x49, 0x2a, 0x38, 0xae, 0x4a, 0xe0, - 0x4b, 0xd0, 0xf9, 0xb0, 0xbc, 0x1a, 0x51, 0xd7, 0x78, 0xec, 0x5a, 0x0f, 0x07, 0xc3, 0x2e, 0x35, - 0x5b, 0x44, 0xd9, 0x60, 0x9d, 0xf9, 0x11, 0x57, 0xca, 0x59, 0x71, 0xdb, 0xc6, 0xe4, 0x68, 0x69, - 0x1e, 0xab, 0x24, 0xfc, 0x88, 0x18, 0x7e, 0x05, 0x7d, 0xf7, 0xe3, 0x2d, 0x26, 0x46, 0x68, 0x85, - 0x7a, 0xc6, 0xda, 0xab, 0xfd, 0xf2, 0x4b, 0x44, 0xfc, 0x84, 0xc7, 0xf9, 0xc9, 0x97, 0xc1, 0x9c, - 0xeb, 0x20, 0x9d, 0x0d, 0xa9, 0x8c, 0x46, 0xbf, 0xa4, 0x9c, 0xd1, 0xfc, 0xf7, 0x79, 0x36, 0x8e, - 0x23, 0x2a, 0xa3, 0x48, 0x8a, 0x91, 0x79, 0xc3, 0xac, 0x6d, 0xfe, 0x2b, 0x5e, 0xfc, 0x0d, 0x00, - 0x00, 0xff, 0xff, 0x85, 0x99, 0x5e, 0x0f, 0xa6, 0x07, 0x00, 0x00, + // 754 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x7c, 0x55, 0x5d, 0x4f, 0xdb, 0x3a, + 0x18, 0x56, 0x29, 0xed, 0x01, 0x43, 0x29, 0x35, 0x1f, 0xc7, 0x54, 0x70, 0x14, 0xa1, 0x73, 0x51, + 0x71, 0x74, 0x5a, 0x89, 0xdd, 0x6d, 0xda, 0x26, 0x60, 0x54, 0x4c, 0x1b, 0x53, 0xe5, 0xb2, 0x5d, + 0xec, 0x6a, 0xae, 0x63, 0x1a, 0x8b, 0xc4, 0xce, 0x6a, 0x77, 0x1b, 0xfb, 0x63, 0xfb, 0x6d, 0xbb, + 0x9b, 0x62, 0x3b, 0xa5, 0x4e, 0x02, 0x37, 0x91, 0xf2, 0x3e, 0x1f, 0xf1, 0x63, 0xfb, 0x7d, 0x03, + 0x76, 0x13, 0x19, 0xb2, 0x78, 0xa0, 0x04, 0x49, 0x55, 0x24, 0x75, 0x3f, 0x9d, 0x49, 0x2d, 0x61, + 0xc3, 0x54, 0xbb, 0xff, 0x38, 0x30, 0xe5, 0x82, 0x9d, 0xc7, 0x92, 0xde, 0x5d, 0x13, 0xc1, 0x6f, + 0x99, 0x72, 0xb4, 0x6e, 0xd7, 0xe2, 0x84, 0x52, 0x39, 0x17, 0xfa, 0x9c, 0xc4, 0x44, 0x50, 0xe6, + 0xb0, 0x43, 0x8b, 0x09, 0x19, 0x32, 0xcc, 0xa6, 0x5c, 0xe9, 0x19, 0xd1, 0x5c, 0x8a, 0x4a, 0xe5, + 0x1b, 0xa2, 0x89, 0x62, 0xb9, 0xab, 0xfb, 0x6a, 0x4a, 0x66, 0x9a, 0x53, 0x9e, 0x1a, 0xd9, 0x98, + 0xca, 0x59, 0xc1, 0x39, 0x9d, 0x4f, 0x62, 0xae, 0x22, 0x16, 0x62, 0x46, 0x19, 0x4f, 0x73, 0x35, + 0xb4, 0x28, 0x53, 0x74, 0x26, 0xbf, 0xfb, 0x5f, 0x4b, 0xe6, 0xb1, 0xe6, 0x63, 0x3e, 0x15, 0x44, + 0xcf, 0x17, 0x6e, 0x1d, 0x8b, 0x4d, 0xb2, 0x78, 0xae, 0x74, 0xe4, 0x62, 0xdf, 0xf1, 0x34, 0x65, + 0xa1, 0x09, 0xae, 0x12, 0xae, 0x23, 0x07, 0xbb, 0x2d, 0xbb, 0x65, 0x6c, 0x4c, 0x49, 0x9c, 0xfb, + 0xec, 0x2c, 0xaa, 0x9f, 0xa4, 0xce, 0x8b, 0x07, 0xb6, 0x18, 0xf3, 0xaf, 0x73, 0x1e, 0x8e, 0xc8, + 0x7d, 0xc2, 0x44, 0x61, 0x9d, 0x44, 0xcb, 0x84, 0x53, 0x5b, 0x3b, 0xfe, 0xb5, 0x02, 0xb6, 0xc7, + 0xee, 0x24, 0x86, 0x3c, 0x66, 0x6f, 0xc5, 0xad, 0x84, 0x27, 0x7e, 0xed, 0x8a, 0xa8, 0x08, 0xd5, + 0x82, 0x5a, 0x6f, 0x13, 0x97, 0xea, 0x70, 0x1f, 0x34, 0xaf, 0x18, 0x9f, 0x46, 0x1a, 0xad, 0x04, + 0xb5, 0x5e, 0x0b, 0xbb, 0x37, 0xf8, 0x0a, 0x74, 0x47, 0x33, 0x49, 0x99, 0x52, 0x97, 0x3f, 0x52, + 0x6e, 0x4f, 0xe2, 0x86, 0x27, 0x4c, 0x69, 0x92, 0xa4, 0xa8, 0x1e, 0xd4, 0x7a, 0x75, 0xfc, 0x04, + 0x03, 0x1e, 0x82, 0xf5, 0x8b, 0x88, 0x70, 0x71, 0x73, 0x9f, 0x32, 0xb4, 0x1a, 0xd4, 0x7a, 0x0d, + 0xfc, 0x50, 0x80, 0x1f, 0xc1, 0xfe, 0xb8, 0x74, 0x45, 0x0c, 0xb5, 0x11, 0xd4, 0x7a, 0x5b, 0xa7, + 0x47, 0x7d, 0x93, 0xb5, 0x5f, 0x4d, 0xc2, 0x8f, 0x88, 0xb3, 0xe0, 0x59, 0xb0, 0x8b, 0x68, 0x2e, + 0xee, 0x54, 0x16, 0x8f, 0x29, 0xd4, 0x0c, 0xea, 0x59, 0xf0, 0x62, 0xfd, 0xf8, 0xf7, 0x3a, 0x68, + 0xe7, 0xbb, 0x31, 0x22, 0xf7, 0xb1, 0x24, 0x21, 0xfc, 0x17, 0x34, 0xed, 0xd9, 0xa1, 0x5a, 0x50, + 0xef, 0x6d, 0x9c, 0x6e, 0xba, 0x65, 0x98, 0x22, 0x76, 0x18, 0x7c, 0x0d, 0xda, 0x67, 0xde, 0xfd, + 0x55, 0x68, 0xc5, 0xd0, 0xf7, 0x1c, 0xdd, 0x47, 0x71, 0x91, 0x0d, 0x2f, 0x41, 0xe7, 0x43, 0xe1, + 0x92, 0x2b, 0x54, 0x37, 0x16, 0x7f, 0x3b, 0x8b, 0x22, 0x8e, 0xcb, 0x8a, 0xa5, 0x75, 0xb8, 0x6e, + 0x50, 0x68, 0xb5, 0x6a, 0x1d, 0x0e, 0xc5, 0x45, 0x36, 0x7c, 0x07, 0x76, 0x46, 0xa5, 0x96, 0x51, + 0xa8, 0x61, 0x4c, 0x0e, 0x9c, 0x49, 0x99, 0x81, 0xab, 0x54, 0x59, 0xa8, 0x51, 0xa1, 0xbf, 0xec, + 0xe6, 0x3f, 0x84, 0x2a, 0xe2, 0xb8, 0xac, 0x80, 0x2f, 0x01, 0xbc, 0x34, 0x8d, 0x78, 0x33, 0x23, + 0x42, 0x11, 0x6a, 0x37, 0xe7, 0x2f, 0xe3, 0xd3, 0x72, 0x3e, 0x96, 0x80, 0x2b, 0x88, 0x26, 0x12, + 0x13, 0x21, 0x17, 0x53, 0x4f, 0xbf, 0xe6, 0x47, 0x2a, 0x31, 0x70, 0x95, 0xca, 0x44, 0xb2, 0xe5, + 0xc5, 0x08, 0x50, 0x68, 0xdd, 0x8f, 0x54, 0xc0, 0x71, 0x59, 0x91, 0xad, 0xe9, 0xda, 0x9b, 0x23, + 0x59, 0x93, 0x2a, 0x04, 0xbc, 0x35, 0x95, 0x19, 0xb8, 0x4a, 0x05, 0xaf, 0x00, 0x1c, 0x17, 0xa7, + 0x8c, 0x42, 0x1b, 0xc6, 0x0b, 0xe5, 0x5d, 0x53, 0x24, 0xe0, 0x0a, 0x0d, 0xfc, 0x0f, 0xac, 0x0d, + 0xdd, 0x40, 0x42, 0x9b, 0x46, 0xdf, 0x76, 0xfa, 0xbc, 0x8c, 0x17, 0x04, 0x88, 0xc1, 0xde, 0xd0, + 0xce, 0xa9, 0x0b, 0x99, 0x24, 0x5c, 0x67, 0x63, 0x29, 0x7b, 0x43, 0x2d, 0xa3, 0x3c, 0x7c, 0x50, + 0x96, 0x39, 0xb8, 0x5a, 0x0a, 0x87, 0xa0, 0xe3, 0x00, 0xcc, 0xbe, 0x31, 0x12, 0x1b, 0xbf, 0x2d, + 0x2f, 0x49, 0x09, 0xc7, 0x65, 0x09, 0x7c, 0x0e, 0x5a, 0xef, 0x97, 0xc7, 0x25, 0x6a, 0x1b, 0x8f, + 0x5d, 0xe7, 0xe1, 0x61, 0xd8, 0xa7, 0x66, 0x83, 0x28, 0x6b, 0xac, 0xb3, 0x30, 0xe1, 0x4a, 0x79, + 0x23, 0x6e, 0xdb, 0x98, 0x1c, 0x2d, 0xf5, 0x63, 0x99, 0x84, 0x1f, 0x11, 0xc3, 0x2f, 0xa0, 0xeb, + 0x1f, 0xde, 0xa2, 0x63, 0x84, 0x56, 0xa8, 0x63, 0xac, 0x83, 0xca, 0x93, 0x5f, 0x22, 0xe2, 0x27, + 0x3c, 0xe0, 0x0b, 0xd0, 0x39, 0x33, 0x3f, 0x82, 0xa5, 0x1b, 0x8b, 0xa0, 0xd7, 0x26, 0x16, 0xc7, + 0x65, 0xde, 0xf9, 0xc9, 0xe7, 0xde, 0x94, 0xeb, 0x68, 0x3e, 0xe9, 0x53, 0x99, 0x0c, 0x7e, 0x4a, + 0x39, 0xa1, 0xf6, 0xf9, 0x7f, 0xd6, 0xcb, 0x03, 0x2a, 0x93, 0x44, 0x8a, 0x81, 0x71, 0x99, 0x34, + 0xcd, 0x8f, 0xe6, 0xd9, 0x9f, 0x00, 0x00, 0x00, 0xff, 0xff, 0x4c, 0xb1, 0xb3, 0xc3, 0xf7, 0x07, + 0x00, 0x00, } diff --git a/common/model/transaction.pb.go b/common/model/transaction.pb.go index e77198e9a..00dcce23a 100644 --- a/common/model/transaction.pb.go +++ b/common/model/transaction.pb.go @@ -100,6 +100,8 @@ const ( TransactionType_FeeVoteCommitmentVoteTransaction TransactionType = 7 // in bytes: []byte{7,1,0,0} TransactionType_FeeVoteRevealVoteTransaction TransactionType = 263 + // in bytes: []byte{8,0,0,0} + TransactionType_AtomicTransaction TransactionType = 8 ) var TransactionType_name = map[int32]string{ @@ -117,6 +119,7 @@ var TransactionType_name = map[int32]string{ 262: "LiquidPaymentStopTransaction", 7: "FeeVoteCommitmentVoteTransaction", 263: "FeeVoteRevealVoteTransaction", + 8: "AtomicTransaction", } var TransactionType_value = map[string]int32{ @@ -134,6 +137,7 @@ var TransactionType_value = map[string]int32{ "LiquidPaymentStopTransaction": 262, "FeeVoteCommitmentVoteTransaction": 7, "FeeVoteRevealVoteTransaction": 263, + "AtomicTransaction": 8, } func (x TransactionType) String() string { @@ -144,22 +148,51 @@ func (TransactionType) EnumDescriptor() ([]byte, []int) { return fileDescriptor_8333001f09b34082, []int{0} } +// TransactionChildType transaction child type it will reference to transaction.child_type +type TransactionChildType int32 + +const ( + TransactionChildType_NoneChild TransactionChildType = 0 + TransactionChildType_MultiSignatureChild TransactionChildType = 1 + TransactionChildType_AtomicChild TransactionChildType = 2 +) + +var TransactionChildType_name = map[int32]string{ + 0: "NoneChild", + 1: "MultiSignatureChild", + 2: "AtomicChild", +} + +var TransactionChildType_value = map[string]int32{ + "NoneChild": 0, + "MultiSignatureChild": 1, + "AtomicChild": 2, +} + +func (x TransactionChildType) String() string { + return proto.EnumName(TransactionChildType_name, int32(x)) +} + +func (TransactionChildType) EnumDescriptor() ([]byte, []int) { + return fileDescriptor_8333001f09b34082, []int{1} +} + // Transaction represent the transaction data structure stored in the database type Transaction struct { - Version uint32 `protobuf:"varint,1,opt,name=Version,proto3" json:"Version,omitempty"` - ID int64 `protobuf:"varint,2,opt,name=ID,proto3" json:"ID,omitempty"` - BlockID int64 `protobuf:"varint,3,opt,name=BlockID,proto3" json:"BlockID,omitempty"` - Height uint32 `protobuf:"varint,4,opt,name=Height,proto3" json:"Height,omitempty"` - SenderAccountAddress []byte `protobuf:"bytes,5,opt,name=SenderAccountAddress,proto3" json:"SenderAccountAddress,omitempty"` - RecipientAccountAddress []byte `protobuf:"bytes,6,opt,name=RecipientAccountAddress,proto3" json:"RecipientAccountAddress,omitempty"` - TransactionType uint32 `protobuf:"varint,7,opt,name=TransactionType,proto3" json:"TransactionType,omitempty"` - Fee int64 `protobuf:"varint,8,opt,name=Fee,proto3" json:"Fee,omitempty"` - Timestamp int64 `protobuf:"varint,9,opt,name=Timestamp,proto3" json:"Timestamp,omitempty"` - TransactionHash []byte `protobuf:"bytes,10,opt,name=TransactionHash,proto3" json:"TransactionHash,omitempty"` - TransactionBodyLength uint32 `protobuf:"varint,11,opt,name=TransactionBodyLength,proto3" json:"TransactionBodyLength,omitempty"` - TransactionBodyBytes []byte `protobuf:"bytes,12,opt,name=TransactionBodyBytes,proto3" json:"TransactionBodyBytes,omitempty"` - TransactionIndex uint32 `protobuf:"varint,13,opt,name=TransactionIndex,proto3" json:"TransactionIndex,omitempty"` - MultisigChild bool `protobuf:"varint,14,opt,name=MultisigChild,proto3" json:"MultisigChild,omitempty"` + Version uint32 `protobuf:"varint,1,opt,name=Version,proto3" json:"Version,omitempty"` + ID int64 `protobuf:"varint,2,opt,name=ID,proto3" json:"ID,omitempty"` + BlockID int64 `protobuf:"varint,3,opt,name=BlockID,proto3" json:"BlockID,omitempty"` + Height uint32 `protobuf:"varint,4,opt,name=Height,proto3" json:"Height,omitempty"` + SenderAccountAddress []byte `protobuf:"bytes,5,opt,name=SenderAccountAddress,proto3" json:"SenderAccountAddress,omitempty"` + RecipientAccountAddress []byte `protobuf:"bytes,6,opt,name=RecipientAccountAddress,proto3" json:"RecipientAccountAddress,omitempty"` + TransactionType uint32 `protobuf:"varint,7,opt,name=TransactionType,proto3" json:"TransactionType,omitempty"` + Fee int64 `protobuf:"varint,8,opt,name=Fee,proto3" json:"Fee,omitempty"` + Timestamp int64 `protobuf:"varint,9,opt,name=Timestamp,proto3" json:"Timestamp,omitempty"` + TransactionHash []byte `protobuf:"bytes,10,opt,name=TransactionHash,proto3" json:"TransactionHash,omitempty"` + TransactionBodyLength uint32 `protobuf:"varint,11,opt,name=TransactionBodyLength,proto3" json:"TransactionBodyLength,omitempty"` + TransactionBodyBytes []byte `protobuf:"bytes,12,opt,name=TransactionBodyBytes,proto3" json:"TransactionBodyBytes,omitempty"` + TransactionIndex uint32 `protobuf:"varint,13,opt,name=TransactionIndex,proto3" json:"TransactionIndex,omitempty"` + ChildType TransactionChildType `protobuf:"varint,14,opt,name=ChildType,proto3,enum=model.TransactionChildType" json:"ChildType,omitempty"` // transactionbody // // Types that are valid to be assigned to TransactionBody: @@ -177,14 +210,14 @@ type Transaction struct { // *Transaction_FeeVoteRevealTransactionBody // *Transaction_LiquidPaymentTransactionBody // *Transaction_LiquidPaymentStopTransactionBody - TransactionBody isTransaction_TransactionBody `protobuf_oneof:"TransactionBody"` - Signature []byte `protobuf:"bytes,31,opt,name=Signature,proto3" json:"Signature,omitempty"` - // nullable - Escrow *Escrow `protobuf:"bytes,32,opt,name=Escrow,proto3" json:"Escrow,omitempty"` - Message []byte `protobuf:"bytes,33,opt,name=Message,proto3" json:"Message,omitempty"` - XXX_NoUnkeyedLiteral struct{} `json:"-"` - XXX_unrecognized []byte `json:"-"` - XXX_sizecache int32 `json:"-"` + // *Transaction_AtomicTransactionBody + TransactionBody isTransaction_TransactionBody `protobuf_oneof:"TransactionBody"` + Signature []byte `protobuf:"bytes,32,opt,name=Signature,proto3" json:"Signature,omitempty"` + Escrow *Escrow `protobuf:"bytes,33,opt,name=Escrow,proto3" json:"Escrow,omitempty"` + Message []byte `protobuf:"bytes,34,opt,name=Message,proto3" json:"Message,omitempty"` + XXX_NoUnkeyedLiteral struct{} `json:"-"` + XXX_unrecognized []byte `json:"-"` + XXX_sizecache int32 `json:"-"` } func (m *Transaction) Reset() { *m = Transaction{} } @@ -303,11 +336,11 @@ func (m *Transaction) GetTransactionIndex() uint32 { return 0 } -func (m *Transaction) GetMultisigChild() bool { +func (m *Transaction) GetChildType() TransactionChildType { if m != nil { - return m.MultisigChild + return m.ChildType } - return false + return TransactionChildType_NoneChild } type isTransaction_TransactionBody interface { @@ -370,6 +403,10 @@ type Transaction_LiquidPaymentStopTransactionBody struct { LiquidPaymentStopTransactionBody *LiquidPaymentStopTransactionBody `protobuf:"bytes,30,opt,name=liquidPaymentStopTransactionBody,proto3,oneof"` } +type Transaction_AtomicTransactionBody struct { + AtomicTransactionBody *AtomicTransactionBody `protobuf:"bytes,31,opt,name=atomicTransactionBody,proto3,oneof"` +} + func (*Transaction_EmptyTransactionBody) isTransaction_TransactionBody() {} func (*Transaction_SendMoneyTransactionBody) isTransaction_TransactionBody() {} @@ -398,6 +435,8 @@ func (*Transaction_LiquidPaymentTransactionBody) isTransaction_TransactionBody() func (*Transaction_LiquidPaymentStopTransactionBody) isTransaction_TransactionBody() {} +func (*Transaction_AtomicTransactionBody) isTransaction_TransactionBody() {} + func (m *Transaction) GetTransactionBody() isTransaction_TransactionBody { if m != nil { return m.TransactionBody @@ -503,6 +542,13 @@ func (m *Transaction) GetLiquidPaymentStopTransactionBody() *LiquidPaymentStopTr return nil } +func (m *Transaction) GetAtomicTransactionBody() *AtomicTransactionBody { + if x, ok := m.GetTransactionBody().(*Transaction_AtomicTransactionBody); ok { + return x.AtomicTransactionBody + } + return nil +} + func (m *Transaction) GetSignature() []byte { if m != nil { return m.Signature @@ -541,6 +587,7 @@ func (*Transaction) XXX_OneofWrappers() []interface{} { (*Transaction_FeeVoteRevealTransactionBody)(nil), (*Transaction_LiquidPaymentTransactionBody)(nil), (*Transaction_LiquidPaymentStopTransactionBody)(nil), + (*Transaction_AtomicTransactionBody)(nil), } } @@ -1200,6 +1247,55 @@ func (m *LiquidPaymentStopTransactionBody) GetTransactionID() int64 { return 0 } +type AtomicTransactionBody struct { + // UnsignedTransactionBytes is collection of unsigned transaction bytes + UnsignedTransactionBytes [][]byte `protobuf:"bytes,1,rep,name=UnsignedTransactionBytes,proto3" json:"UnsignedTransactionBytes,omitempty"` + // Signatures is + Signatures map[string][]byte `protobuf:"bytes,2,rep,name=Signatures,proto3" json:"Signatures,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"` + XXX_NoUnkeyedLiteral struct{} `json:"-"` + XXX_unrecognized []byte `json:"-"` + XXX_sizecache int32 `json:"-"` +} + +func (m *AtomicTransactionBody) Reset() { *m = AtomicTransactionBody{} } +func (m *AtomicTransactionBody) String() string { return proto.CompactTextString(m) } +func (*AtomicTransactionBody) ProtoMessage() {} +func (*AtomicTransactionBody) Descriptor() ([]byte, []int) { + return fileDescriptor_8333001f09b34082, []int{15} +} + +func (m *AtomicTransactionBody) XXX_Unmarshal(b []byte) error { + return xxx_messageInfo_AtomicTransactionBody.Unmarshal(m, b) +} +func (m *AtomicTransactionBody) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + return xxx_messageInfo_AtomicTransactionBody.Marshal(b, m, deterministic) +} +func (m *AtomicTransactionBody) XXX_Merge(src proto.Message) { + xxx_messageInfo_AtomicTransactionBody.Merge(m, src) +} +func (m *AtomicTransactionBody) XXX_Size() int { + return xxx_messageInfo_AtomicTransactionBody.Size(m) +} +func (m *AtomicTransactionBody) XXX_DiscardUnknown() { + xxx_messageInfo_AtomicTransactionBody.DiscardUnknown(m) +} + +var xxx_messageInfo_AtomicTransactionBody proto.InternalMessageInfo + +func (m *AtomicTransactionBody) GetUnsignedTransactionBytes() [][]byte { + if m != nil { + return m.UnsignedTransactionBytes + } + return nil +} + +func (m *AtomicTransactionBody) GetSignatures() map[string][]byte { + if m != nil { + return m.Signatures + } + return nil +} + // GetTransactionRequest return model.Transaction type GetTransactionRequest struct { // Fetch Transaction by its ID @@ -1213,7 +1309,7 @@ func (m *GetTransactionRequest) Reset() { *m = GetTransactionRequest{} } func (m *GetTransactionRequest) String() string { return proto.CompactTextString(m) } func (*GetTransactionRequest) ProtoMessage() {} func (*GetTransactionRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{15} + return fileDescriptor_8333001f09b34082, []int{16} } func (m *GetTransactionRequest) XXX_Unmarshal(b []byte) error { @@ -1258,7 +1354,7 @@ func (m *GetTransactionsRequest) Reset() { *m = GetTransactionsRequest{} func (m *GetTransactionsRequest) String() string { return proto.CompactTextString(m) } func (*GetTransactionsRequest) ProtoMessage() {} func (*GetTransactionsRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{16} + return fileDescriptor_8333001f09b34082, []int{17} } func (m *GetTransactionsRequest) XXX_Unmarshal(b []byte) error { @@ -1335,7 +1431,7 @@ func (m *GetTransactionsResponse) Reset() { *m = GetTransactionsResponse func (m *GetTransactionsResponse) String() string { return proto.CompactTextString(m) } func (*GetTransactionsResponse) ProtoMessage() {} func (*GetTransactionsResponse) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{17} + return fileDescriptor_8333001f09b34082, []int{18} } func (m *GetTransactionsResponse) XXX_Unmarshal(b []byte) error { @@ -1383,7 +1479,7 @@ func (m *PostTransactionRequest) Reset() { *m = PostTransactionRequest{} func (m *PostTransactionRequest) String() string { return proto.CompactTextString(m) } func (*PostTransactionRequest) ProtoMessage() {} func (*PostTransactionRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{18} + return fileDescriptor_8333001f09b34082, []int{19} } func (m *PostTransactionRequest) XXX_Unmarshal(b []byte) error { @@ -1422,7 +1518,7 @@ func (m *PostTransactionResponse) Reset() { *m = PostTransactionResponse func (m *PostTransactionResponse) String() string { return proto.CompactTextString(m) } func (*PostTransactionResponse) ProtoMessage() {} func (*PostTransactionResponse) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{19} + return fileDescriptor_8333001f09b34082, []int{20} } func (m *PostTransactionResponse) XXX_Unmarshal(b []byte) error { @@ -1464,7 +1560,7 @@ func (m *SendTransactionRequest) Reset() { *m = SendTransactionRequest{} func (m *SendTransactionRequest) String() string { return proto.CompactTextString(m) } func (*SendTransactionRequest) ProtoMessage() {} func (*SendTransactionRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{20} + return fileDescriptor_8333001f09b34082, []int{21} } func (m *SendTransactionRequest) XXX_Unmarshal(b []byte) error { @@ -1518,7 +1614,7 @@ func (m *SendTransactionResponse) Reset() { *m = SendTransactionResponse func (m *SendTransactionResponse) String() string { return proto.CompactTextString(m) } func (*SendTransactionResponse) ProtoMessage() {} func (*SendTransactionResponse) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{21} + return fileDescriptor_8333001f09b34082, []int{22} } func (m *SendTransactionResponse) XXX_Unmarshal(b []byte) error { @@ -1560,7 +1656,7 @@ func (m *RequestBlockTransactionsRequest) Reset() { *m = RequestBlockTra func (m *RequestBlockTransactionsRequest) String() string { return proto.CompactTextString(m) } func (*RequestBlockTransactionsRequest) ProtoMessage() {} func (*RequestBlockTransactionsRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{22} + return fileDescriptor_8333001f09b34082, []int{23} } func (m *RequestBlockTransactionsRequest) XXX_Unmarshal(b []byte) error { @@ -1616,7 +1712,7 @@ func (m *SendBlockTransactionsRequest) Reset() { *m = SendBlockTransacti func (m *SendBlockTransactionsRequest) String() string { return proto.CompactTextString(m) } func (*SendBlockTransactionsRequest) ProtoMessage() {} func (*SendBlockTransactionsRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{23} + return fileDescriptor_8333001f09b34082, []int{24} } func (m *SendBlockTransactionsRequest) XXX_Unmarshal(b []byte) error { @@ -1670,7 +1766,7 @@ func (m *SendBlockTransactionsResponse) Reset() { *m = SendBlockTransact func (m *SendBlockTransactionsResponse) String() string { return proto.CompactTextString(m) } func (*SendBlockTransactionsResponse) ProtoMessage() {} func (*SendBlockTransactionsResponse) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{24} + return fileDescriptor_8333001f09b34082, []int{25} } func (m *SendBlockTransactionsResponse) XXX_Unmarshal(b []byte) error { @@ -1710,7 +1806,7 @@ func (m *GetTransactionMinimumFeeRequest) Reset() { *m = GetTransactionM func (m *GetTransactionMinimumFeeRequest) String() string { return proto.CompactTextString(m) } func (*GetTransactionMinimumFeeRequest) ProtoMessage() {} func (*GetTransactionMinimumFeeRequest) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{25} + return fileDescriptor_8333001f09b34082, []int{26} } func (m *GetTransactionMinimumFeeRequest) XXX_Unmarshal(b []byte) error { @@ -1750,7 +1846,7 @@ func (m *GetTransactionMinimumFeeResponse) Reset() { *m = GetTransaction func (m *GetTransactionMinimumFeeResponse) String() string { return proto.CompactTextString(m) } func (*GetTransactionMinimumFeeResponse) ProtoMessage() {} func (*GetTransactionMinimumFeeResponse) Descriptor() ([]byte, []int) { - return fileDescriptor_8333001f09b34082, []int{26} + return fileDescriptor_8333001f09b34082, []int{27} } func (m *GetTransactionMinimumFeeResponse) XXX_Unmarshal(b []byte) error { @@ -1780,6 +1876,7 @@ func (m *GetTransactionMinimumFeeResponse) GetFee() int64 { func init() { proto.RegisterEnum("model.TransactionType", TransactionType_name, TransactionType_value) + proto.RegisterEnum("model.TransactionChildType", TransactionChildType_name, TransactionChildType_value) proto.RegisterType((*Transaction)(nil), "model.Transaction") proto.RegisterType((*EmptyTransactionBody)(nil), "model.EmptyTransactionBody") proto.RegisterType((*SendMoneyTransactionBody)(nil), "model.SendMoneyTransactionBody") @@ -1795,6 +1892,8 @@ func init() { proto.RegisterType((*FeeVoteRevealTransactionBody)(nil), "model.FeeVoteRevealTransactionBody") proto.RegisterType((*LiquidPaymentTransactionBody)(nil), "model.LiquidPaymentTransactionBody") proto.RegisterType((*LiquidPaymentStopTransactionBody)(nil), "model.LiquidPaymentStopTransactionBody") + proto.RegisterType((*AtomicTransactionBody)(nil), "model.AtomicTransactionBody") + proto.RegisterMapType((map[string][]byte)(nil), "model.AtomicTransactionBody.SignaturesEntry") proto.RegisterType((*GetTransactionRequest)(nil), "model.GetTransactionRequest") proto.RegisterType((*GetTransactionsRequest)(nil), "model.GetTransactionsRequest") proto.RegisterType((*GetTransactionsResponse)(nil), "model.GetTransactionsResponse") @@ -1812,108 +1911,115 @@ func init() { func init() { proto.RegisterFile("model/transaction.proto", fileDescriptor_8333001f09b34082) } var fileDescriptor_8333001f09b34082 = []byte{ - // 1635 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xa4, 0x58, 0xdb, 0x6e, 0xdb, 0x46, - 0x13, 0x16, 0x25, 0xcb, 0x87, 0xf1, 0x21, 0xf2, 0xc6, 0x07, 0xc6, 0x91, 0x63, 0x85, 0xb1, 0xfd, - 0xeb, 0x77, 0x12, 0xfb, 0x8f, 0xff, 0x20, 0x08, 0x72, 0xe7, 0x43, 0x52, 0x19, 0xb1, 0x1a, 0x77, - 0xed, 0xb8, 0x40, 0x81, 0x5e, 0xd0, 0xd4, 0x5a, 0x22, 0x22, 0x72, 0x19, 0x92, 0x4a, 0xea, 0x26, - 0x28, 0xd0, 0xf4, 0x84, 0x02, 0xbd, 0xec, 0x33, 0xf4, 0x59, 0xfa, 0x1c, 0xb9, 0xed, 0x4b, 0x14, - 0xbb, 0x5c, 0x51, 0x5c, 0x8a, 0x22, 0xd9, 0xf4, 0x46, 0x10, 0x67, 0xbe, 0x9d, 0x6f, 0x76, 0x76, - 0x76, 0x67, 0x76, 0x61, 0xd9, 0xa2, 0x2d, 0xd2, 0xdd, 0xf1, 0x5d, 0xdd, 0xf6, 0x74, 0xc3, 0x37, - 0xa9, 0xbd, 0xed, 0xb8, 0xd4, 0xa7, 0xa8, 0xcc, 0x15, 0x2b, 0xd5, 0x40, 0xef, 0xb8, 0x94, 0x5e, - 0xbe, 0xb8, 0x7c, 0xf1, 0xd6, 0x26, 0xae, 0xd7, 0x31, 0x9d, 0x00, 0xb4, 0xb2, 0x24, 0xb4, 0x7a, - 0xdb, 0xb4, 0xf5, 0xc1, 0xe0, 0x95, 0xeb, 0x81, 0xdc, 0x25, 0x06, 0x31, 0x1d, 0x5f, 0x08, 0x85, - 0x29, 0x9b, 0xb6, 0x08, 0x26, 0x6d, 0xd3, 0xf3, 0xdd, 0xe8, 0x10, 0x14, 0x68, 0x89, 0x67, 0xb8, - 0xf4, 0xad, 0x90, 0xad, 0x04, 0x32, 0xab, 0xd7, 0xf5, 0xcd, 0x53, 0xb3, 0x6d, 0xeb, 0x7e, 0xcf, - 0x25, 0x32, 0xc5, 0x25, 0x21, 0xe7, 0xd4, 0x17, 0x42, 0xed, 0xe3, 0x3c, 0x4c, 0x9f, 0x0d, 0xa6, - 0x82, 0x54, 0x98, 0x38, 0x27, 0xae, 0x67, 0x52, 0x5b, 0x55, 0x6a, 0x4a, 0x7d, 0x16, 0xf7, 0x3f, - 0x11, 0x82, 0xe2, 0xd1, 0xa1, 0x5a, 0xac, 0x29, 0xf5, 0xd2, 0x7e, 0xf1, 0x7f, 0x0a, 0x2e, 0x1e, - 0x1d, 0xa2, 0x2a, 0x4c, 0xec, 0x77, 0xa9, 0xf1, 0xea, 0xe8, 0x50, 0x2d, 0x85, 0x8a, 0xbe, 0x08, - 0x2d, 0xc1, 0x78, 0x83, 0x98, 0xed, 0x8e, 0xaf, 0x8e, 0x71, 0x53, 0xe2, 0x0b, 0xed, 0xc2, 0xc2, - 0x29, 0xb1, 0x5b, 0xc4, 0xdd, 0x33, 0x0c, 0xda, 0xb3, 0xfd, 0xbd, 0x56, 0xcb, 0x25, 0x9e, 0xa7, - 0x96, 0x6b, 0x4a, 0x7d, 0x06, 0x27, 0xea, 0xd0, 0x63, 0x58, 0xc6, 0xc4, 0x30, 0x1d, 0x93, 0xd8, - 0x7e, 0x6c, 0xd8, 0x38, 0x1f, 0x36, 0x4a, 0x8d, 0xea, 0x70, 0x2d, 0x32, 0xc1, 0xb3, 0x2b, 0x87, - 0xa8, 0x13, 0xdc, 0x9d, 0xb8, 0x18, 0x2d, 0x40, 0xe9, 0x19, 0x21, 0xea, 0x64, 0x38, 0x13, 0xf6, - 0x89, 0x6a, 0x30, 0x75, 0x66, 0x5a, 0xc4, 0xf3, 0x75, 0xcb, 0x51, 0xa7, 0x42, 0xdd, 0x40, 0x18, - 0x63, 0x68, 0xe8, 0x5e, 0x47, 0x05, 0xee, 0x53, 0x5c, 0x8c, 0x1e, 0xc2, 0x62, 0x44, 0xb4, 0x4f, - 0x5b, 0x57, 0xc7, 0xc4, 0x6e, 0xfb, 0x1d, 0x75, 0x9a, 0x7b, 0x94, 0xac, 0x64, 0xf1, 0x8a, 0x29, - 0xf6, 0xaf, 0x7c, 0xe2, 0xa9, 0x33, 0x41, 0xbc, 0x92, 0x74, 0x68, 0x0b, 0x2a, 0x11, 0xf9, 0x91, - 0xdd, 0x22, 0xdf, 0xa8, 0xb3, 0x9c, 0x64, 0x48, 0x8e, 0xd6, 0x61, 0xb6, 0xc9, 0x12, 0xc6, 0x33, - 0xdb, 0x07, 0x1d, 0xb3, 0xdb, 0x52, 0xe7, 0x6a, 0x4a, 0x7d, 0x12, 0xcb, 0x42, 0xf4, 0x05, 0x2c, - 0x10, 0xcb, 0xf1, 0xaf, 0x62, 0x74, 0xea, 0x7c, 0x4d, 0xa9, 0x4f, 0xef, 0xde, 0xdc, 0xe6, 0xd9, - 0xb5, 0xfd, 0x34, 0x01, 0xd2, 0x28, 0xe0, 0xc4, 0xa1, 0xe8, 0x6b, 0x50, 0x3d, 0x62, 0xb7, 0x9a, - 0xd4, 0x26, 0x43, 0x66, 0x11, 0x37, 0xbb, 0x26, 0xcc, 0x9e, 0x8e, 0x80, 0x35, 0x0a, 0x78, 0xa4, - 0x09, 0xe4, 0xc2, 0x5a, 0x7c, 0xeb, 0xc4, 0x59, 0xae, 0x73, 0x96, 0x4d, 0xc1, 0xf2, 0x79, 0x3a, - 0xba, 0x51, 0xc0, 0x59, 0x06, 0xd1, 0x8f, 0x0a, 0x6c, 0xf4, 0x9c, 0x96, 0xee, 0x93, 0x0c, 0x63, - 0xea, 0x02, 0xa7, 0xbe, 0x27, 0xa8, 0x5f, 0xe6, 0x19, 0xd3, 0x28, 0xe0, 0x7c, 0xc6, 0xb9, 0x1b, - 0x2e, 0xb1, 0xe8, 0x9b, 0x4c, 0x37, 0x16, 0x25, 0x37, 0x70, 0x9e, 0x31, 0xcc, 0x8d, 0x5c, 0xc6, - 0xd1, 0xf7, 0x0a, 0xac, 0x1b, 0x5d, 0xdd, 0xb4, 0xb2, 0xbc, 0x58, 0xe2, 0x5e, 0xdc, 0x15, 0x5e, - 0x1c, 0xe4, 0x18, 0xd2, 0x28, 0xe0, 0x5c, 0xa6, 0xd1, 0x3b, 0xd0, 0x3c, 0xe2, 0xf7, 0x1c, 0x71, - 0x2c, 0x1c, 0xea, 0xbe, 0xee, 0x11, 0x3f, 0xee, 0xc0, 0x32, 0x77, 0xe0, 0xbf, 0x61, 0xba, 0x65, - 0x0d, 0x68, 0x14, 0x70, 0x0e, 0xb3, 0xe8, 0x3b, 0xb8, 0x13, 0x44, 0x2a, 0x9d, 0x5d, 0xe5, 0xec, - 0x5b, 0xd2, 0x22, 0x64, 0xd1, 0xe7, 0x31, 0x8c, 0xba, 0xb0, 0xaa, 0x3b, 0x8e, 0x4b, 0xdf, 0xe8, - 0xdd, 0xa7, 0xbc, 0x4e, 0xc4, 0x99, 0x6f, 0x70, 0xe6, 0x75, 0xc1, 0xbc, 0x97, 0x86, 0x6d, 0x14, - 0x70, 0xba, 0x31, 0xc6, 0x26, 0x57, 0x9e, 0x38, 0xdb, 0x8a, 0xc4, 0xd6, 0x4c, 0xc3, 0x32, 0xb6, - 0x54, 0x63, 0xc8, 0x84, 0xaa, 0xa8, 0x65, 0x07, 0xd4, 0xb2, 0xcc, 0xa1, 0xa0, 0xde, 0xe4, 0x64, - 0x77, 0x04, 0xd9, 0xb3, 0x14, 0x68, 0xa3, 0x80, 0x53, 0x4d, 0x45, 0xa8, 0x30, 0x79, 0x43, 0xf4, - 0x6e, 0x9c, 0xaa, 0x9a, 0x44, 0x95, 0x08, 0x8d, 0x50, 0x25, 0xea, 0x19, 0x55, 0xd7, 0x7c, 0xdd, - 0x33, 0x5b, 0x27, 0xfa, 0x95, 0x45, 0xec, 0xa1, 0x59, 0xad, 0x4a, 0x54, 0xc7, 0x29, 0x50, 0x46, - 0x95, 0x66, 0x0a, 0xf5, 0xa0, 0x26, 0xe9, 0x4f, 0x7d, 0xea, 0xc4, 0xe9, 0x6e, 0x71, 0xba, 0xff, - 0x24, 0xd1, 0x25, 0xc0, 0x1b, 0x05, 0x9c, 0x69, 0x12, 0x55, 0x61, 0x2a, 0x5c, 0x53, 0x75, 0x8d, - 0xd7, 0xb0, 0x81, 0x00, 0x6d, 0xc0, 0x78, 0x90, 0x5c, 0x6a, 0x8d, 0x53, 0xcf, 0xf6, 0x0b, 0x0b, - 0x17, 0x62, 0xa1, 0x64, 0x7d, 0x4a, 0x93, 0x78, 0x9e, 0xde, 0x26, 0xea, 0x6d, 0x6e, 0xa2, 0xff, - 0xb9, 0x3f, 0x2f, 0x55, 0x63, 0xc6, 0xa8, 0x2d, 0xc1, 0x42, 0x52, 0x5d, 0xd2, 0x1e, 0x81, 0x3a, - 0xaa, 0xb0, 0xa0, 0x15, 0x18, 0xdf, 0xb3, 0xd8, 0xce, 0xe2, 0x7d, 0x50, 0x50, 0xf3, 0x85, 0x44, - 0xfb, 0x53, 0x81, 0xb5, 0xac, 0x63, 0x67, 0x1d, 0x66, 0x19, 0xe4, 0xa4, 0x77, 0xd1, 0x35, 0x8d, - 0xe7, 0xe4, 0x8a, 0x9b, 0x99, 0xc1, 0xb2, 0x10, 0x6d, 0xc2, 0x5c, 0xac, 0x9b, 0x29, 0x72, 0xd8, - 0xdc, 0x50, 0x13, 0x33, 0x7b, 0x4c, 0x8d, 0x57, 0xa4, 0xb5, 0xaf, 0x77, 0x75, 0xdb, 0x20, 0x91, - 0x76, 0x4b, 0x56, 0xa0, 0xfb, 0x50, 0x3e, 0xa1, 0xf4, 0xad, 0xcd, 0x7b, 0xae, 0xe9, 0xdd, 0x65, - 0x11, 0xbe, 0x93, 0x58, 0x3b, 0x8a, 0x03, 0x94, 0xf6, 0x87, 0x02, 0x1b, 0xb9, 0x6a, 0x4f, 0xce, - 0x09, 0x0d, 0x39, 0x5a, 0xcc, 0x74, 0xb4, 0x94, 0xcb, 0xd1, 0x26, 0x6c, 0xe4, 0x2a, 0x4e, 0xf9, - 0xfc, 0xd4, 0xde, 0xc1, 0x7a, 0x9e, 0x2a, 0x93, 0x73, 0xd6, 0xe1, 0x5c, 0x8a, 0xb9, 0xe6, 0x72, - 0x0e, 0x5a, 0x76, 0x85, 0x41, 0x2b, 0x30, 0x79, 0xe2, 0x52, 0x87, 0xb8, 0x7e, 0xc0, 0x3a, 0x85, - 0xc3, 0x6f, 0xb4, 0x00, 0xe5, 0x73, 0xbd, 0xdb, 0x0b, 0xc2, 0x3b, 0x85, 0x83, 0x0f, 0xed, 0x4b, - 0xb8, 0x93, 0xa3, 0x76, 0x7c, 0x82, 0xe1, 0xf7, 0xb0, 0x9a, 0x5a, 0x1a, 0xd0, 0x03, 0x98, 0xec, - 0x03, 0xb8, 0xc9, 0xb9, 0xdd, 0x45, 0x69, 0xdf, 0xf6, 0x95, 0x38, 0x84, 0xb1, 0x4c, 0x89, 0x76, - 0xa2, 0xd1, 0xab, 0x85, 0xac, 0xd0, 0x3e, 0x2a, 0xb0, 0x9a, 0x5a, 0x2b, 0xd0, 0x11, 0x20, 0x19, - 0x70, 0x64, 0x5f, 0x52, 0xee, 0xc8, 0xf4, 0xee, 0x8d, 0xc4, 0x6a, 0xc3, 0x00, 0x38, 0x61, 0x10, - 0x7a, 0x02, 0xea, 0x4b, 0xdb, 0x33, 0xdb, 0x36, 0x69, 0x45, 0x59, 0x78, 0xc3, 0x1d, 0xec, 0xcd, - 0x91, 0x7a, 0xf4, 0x04, 0x66, 0x65, 0x0f, 0x82, 0xd4, 0x5e, 0xe8, 0x77, 0x15, 0x12, 0xb9, 0x0c, - 0xd5, 0x9e, 0x40, 0x35, 0xad, 0x44, 0xb1, 0x45, 0x63, 0x4a, 0x7e, 0xbb, 0x08, 0x72, 0x30, 0xfc, - 0xd6, 0xde, 0x87, 0x63, 0x93, 0x6b, 0xca, 0x43, 0x98, 0x16, 0xfa, 0x48, 0x5c, 0x90, 0x5c, 0xad, - 0xb8, 0x4f, 0x51, 0x18, 0x3b, 0x9b, 0xd8, 0x7f, 0x77, 0x70, 0x58, 0x8b, 0xb3, 0x49, 0x96, 0x6a, - 0x1d, 0xa8, 0xa6, 0x95, 0xa1, 0xb4, 0x93, 0x14, 0xdd, 0x83, 0x6b, 0x07, 0xd4, 0x72, 0xba, 0xc4, - 0x27, 0x4d, 0xd3, 0xee, 0xf5, 0x83, 0x3c, 0xc6, 0x41, 0x71, 0x95, 0x76, 0x0c, 0xb5, 0xac, 0x0a, - 0x34, 0x9c, 0x56, 0xca, 0xa8, 0xb4, 0xba, 0x0b, 0x8b, 0x9f, 0x49, 0x9b, 0x03, 0x93, 0xd7, 0x3d, - 0xe2, 0xf9, 0xe2, 0xa6, 0xab, 0x44, 0x6f, 0xba, 0xda, 0xaf, 0x45, 0x58, 0x92, 0xd1, 0x5e, 0x1f, - 0x3e, 0x7c, 0x86, 0x2b, 0x89, 0x67, 0xf8, 0xe0, 0x3a, 0x5c, 0x94, 0xae, 0xc3, 0x5b, 0x30, 0x17, - 0xde, 0x25, 0x4f, 0x7d, 0xdd, 0xf5, 0x23, 0x87, 0x7b, 0x4c, 0x83, 0x36, 0x61, 0x26, 0x94, 0x3c, - 0xb5, 0x5b, 0xfc, 0x90, 0x0f, 0x90, 0x92, 0x3c, 0xe9, 0xd2, 0x5b, 0x4e, 0xbe, 0xf4, 0x3e, 0x00, - 0x38, 0x09, 0x1f, 0x23, 0xf8, 0x5d, 0x7a, 0x7a, 0x77, 0xbe, 0x7f, 0x7e, 0x85, 0x0a, 0x1c, 0x01, - 0x69, 0xaf, 0x60, 0x79, 0x28, 0x14, 0x9e, 0x43, 0x6d, 0x8f, 0x20, 0x15, 0xca, 0x67, 0xd4, 0x17, - 0x87, 0x40, 0xb0, 0x8a, 0x81, 0x00, 0x3d, 0x82, 0x99, 0xe8, 0x08, 0xb5, 0x58, 0x2b, 0x45, 0x92, - 0x30, 0xba, 0x0a, 0x12, 0x4e, 0x3b, 0x84, 0xa5, 0x13, 0xea, 0x25, 0x2d, 0x93, 0x7c, 0xc5, 0x0d, - 0x76, 0x68, 0x10, 0xf9, 0x21, 0xb9, 0xf6, 0x02, 0x96, 0x87, 0xac, 0x08, 0x97, 0x1f, 0x4a, 0x0f, - 0x20, 0xb1, 0xcd, 0x11, 0x1d, 0x10, 0x85, 0x69, 0xbf, 0x29, 0xb0, 0xc4, 0x7a, 0x87, 0x7f, 0xe7, - 0x17, 0xeb, 0x85, 0x0e, 0x3a, 0xba, 0x19, 0xac, 0x10, 0x4b, 0x8b, 0x32, 0x1e, 0x08, 0xd8, 0x2a, - 0x06, 0x8f, 0x21, 0x83, 0xf2, 0x53, 0x0a, 0x1e, 0x16, 0x62, 0x62, 0xed, 0x00, 0x96, 0x87, 0xbc, - 0x11, 0xf3, 0xab, 0xc3, 0x04, 0x0e, 0x5e, 0x95, 0xc4, 0xdc, 0xe6, 0xc2, 0x6b, 0x06, 0x97, 0xe2, - 0xbe, 0x5a, 0xfb, 0x49, 0x81, 0x35, 0x31, 0x09, 0xfe, 0x84, 0x33, 0x22, 0xd9, 0xa5, 0x5d, 0xc4, - 0xa6, 0x56, 0xaa, 0x97, 0x70, 0x4c, 0x9a, 0x31, 0xb1, 0xd4, 0x77, 0x23, 0xed, 0x77, 0x05, 0xaa, - 0x6c, 0x36, 0x23, 0x9d, 0x90, 0x8c, 0x2b, 0x71, 0xe3, 0xf7, 0x60, 0x3e, 0x3a, 0xa8, 0x7f, 0x74, - 0x97, 0xea, 0x33, 0x78, 0x58, 0xf1, 0x0f, 0x62, 0xfc, 0x1c, 0x56, 0x47, 0x78, 0x25, 0x22, 0xbd, - 0x05, 0x93, 0x22, 0x94, 0x41, 0x54, 0x86, 0x43, 0x1d, 0xea, 0xb5, 0x26, 0xac, 0xc9, 0x7b, 0xa8, - 0x69, 0xda, 0xa6, 0xd5, 0xb3, 0x9e, 0x11, 0xf2, 0x29, 0xf9, 0xfd, 0x18, 0x6a, 0xa3, 0xcd, 0x09, - 0xf7, 0xc4, 0xf3, 0x96, 0x22, 0x3d, 0x6f, 0x6d, 0xfd, 0x55, 0x82, 0x84, 0x87, 0xb0, 0x4a, 0xbc, - 0x5f, 0xae, 0x14, 0x90, 0x1a, 0x3c, 0xdb, 0xc5, 0xbb, 0xe5, 0x8a, 0x82, 0xd6, 0xe0, 0x66, 0x4a, - 0x1f, 0x55, 0x29, 0xa2, 0x4d, 0xb8, 0x9d, 0xd9, 0x64, 0x56, 0x3e, 0x70, 0x5c, 0x66, 0x93, 0x57, - 0xf9, 0x30, 0x86, 0x36, 0xa0, 0x96, 0xd5, 0xbd, 0x55, 0x3e, 0x8c, 0x23, 0x0d, 0x6e, 0xa5, 0xf7, - 0x59, 0x95, 0x12, 0x5a, 0x67, 0x39, 0x9f, 0xda, 0x33, 0x55, 0x7e, 0x28, 0xa2, 0x55, 0xb8, 0x31, - 0xb2, 0x01, 0xaa, 0x8c, 0x31, 0xf5, 0xc8, 0x06, 0xa5, 0x52, 0x46, 0x55, 0x50, 0x47, 0x55, 0xc8, - 0xca, 0x38, 0xba, 0x1d, 0xab, 0x9f, 0xb1, 0xaa, 0x56, 0xf9, 0xb9, 0x88, 0xd6, 0xa1, 0x26, 0x35, - 0x07, 0x0c, 0xc6, 0xbe, 0xa2, 0xb0, 0x09, 0x66, 0x48, 0x6a, 0x03, 0xe2, 0x88, 0x5f, 0x8a, 0xfb, - 0x5b, 0x5f, 0xd5, 0xdb, 0xa6, 0xdf, 0xe9, 0x5d, 0x6c, 0x1b, 0xd4, 0xda, 0xf9, 0x96, 0xd2, 0x0b, - 0x23, 0xf8, 0xbd, 0x6f, 0x50, 0x97, 0xec, 0x18, 0xd4, 0xb2, 0xa8, 0xbd, 0xc3, 0x93, 0xf6, 0x62, - 0x9c, 0xbf, 0x10, 0xff, 0xff, 0xef, 0x00, 0x00, 0x00, 0xff, 0xff, 0x5b, 0xad, 0x2f, 0xa6, 0xf1, - 0x16, 0x00, 0x00, + // 1758 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xa4, 0x58, 0xdd, 0x6e, 0xdb, 0xca, + 0x11, 0x16, 0x25, 0xcb, 0x3f, 0x23, 0xff, 0xd0, 0x1b, 0xdb, 0x62, 0x14, 0xf9, 0x58, 0x61, 0x6c, + 0x57, 0xf5, 0xc9, 0xb1, 0x7b, 0xdc, 0x20, 0x48, 0x0d, 0xf4, 0xc2, 0x7f, 0xa9, 0x8c, 0xd8, 0xb1, + 0xbb, 0x76, 0x5c, 0xa0, 0x40, 0x2f, 0x68, 0x6a, 0x2d, 0x11, 0x16, 0xb9, 0x0c, 0x49, 0x39, 0x75, + 0x13, 0x14, 0xa8, 0xfb, 0x87, 0x02, 0xbd, 0xec, 0x33, 0xf4, 0x59, 0x7a, 0xd3, 0x77, 0x28, 0xfa, + 0x24, 0xc5, 0x2e, 0x29, 0x8a, 0x4b, 0x52, 0x14, 0x9b, 0x73, 0x63, 0x78, 0x67, 0xbe, 0x9d, 0x6f, + 0x76, 0x34, 0xbb, 0x33, 0x1c, 0xa8, 0x9a, 0xb4, 0x4d, 0x7a, 0x3b, 0x9e, 0xa3, 0x59, 0xae, 0xa6, + 0x7b, 0x06, 0xb5, 0xb6, 0x6d, 0x87, 0x7a, 0x14, 0x95, 0xb9, 0xa2, 0x56, 0xf7, 0xf5, 0xb6, 0x43, + 0xe9, 0xed, 0xf9, 0xed, 0xf9, 0x27, 0x8b, 0x38, 0x6e, 0xd7, 0xb0, 0x7d, 0x50, 0x6d, 0x25, 0xd0, + 0x6a, 0x1d, 0xc3, 0xd2, 0x86, 0x9b, 0x6b, 0x4f, 0x7c, 0xb9, 0x43, 0x74, 0x62, 0xd8, 0x5e, 0x20, + 0x0c, 0x4c, 0x59, 0xb4, 0x4d, 0x30, 0xe9, 0x18, 0xae, 0xe7, 0x44, 0xb7, 0x20, 0x5f, 0x4b, 0x5c, + 0xdd, 0xa1, 0x9f, 0x02, 0x59, 0xcd, 0x97, 0x99, 0xfd, 0x9e, 0x67, 0x5c, 0x1a, 0x1d, 0x4b, 0xf3, + 0xfa, 0x0e, 0x11, 0x29, 0x6e, 0x09, 0xb9, 0xa6, 0x5e, 0x20, 0x54, 0xff, 0x8d, 0xa0, 0x72, 0x35, + 0x3c, 0x0a, 0x52, 0x60, 0xea, 0x9a, 0x38, 0xae, 0x41, 0x2d, 0x45, 0x6a, 0x48, 0xcd, 0x39, 0x3c, + 0x58, 0x22, 0x04, 0xc5, 0x93, 0x23, 0xa5, 0xd8, 0x90, 0x9a, 0xa5, 0x83, 0xe2, 0x4f, 0x24, 0x5c, + 0x3c, 0x39, 0x42, 0x75, 0x98, 0x3a, 0xe8, 0x51, 0xfd, 0xee, 0xe4, 0x48, 0x29, 0x85, 0x8a, 0x81, + 0x08, 0xad, 0xc0, 0x64, 0x8b, 0x18, 0x9d, 0xae, 0xa7, 0x4c, 0x70, 0x53, 0xc1, 0x0a, 0xed, 0xc2, + 0xd2, 0x25, 0xb1, 0xda, 0xc4, 0xd9, 0xd7, 0x75, 0xda, 0xb7, 0xbc, 0xfd, 0x76, 0xdb, 0x21, 0xae, + 0xab, 0x94, 0x1b, 0x52, 0x73, 0x16, 0xa7, 0xea, 0xd0, 0x1b, 0xa8, 0x62, 0xa2, 0x1b, 0xb6, 0x41, + 0x2c, 0x2f, 0xb6, 0x6d, 0x92, 0x6f, 0x1b, 0xa5, 0x46, 0x4d, 0x58, 0x88, 0x1c, 0xf0, 0xea, 0xc1, + 0x26, 0xca, 0x14, 0x77, 0x27, 0x2e, 0x46, 0x4b, 0x50, 0x7a, 0x4b, 0x88, 0x32, 0x1d, 0x9e, 0x84, + 0x2d, 0x51, 0x03, 0x66, 0xae, 0x0c, 0x93, 0xb8, 0x9e, 0x66, 0xda, 0xca, 0x4c, 0xa8, 0x1b, 0x0a, + 0x63, 0x0c, 0x2d, 0xcd, 0xed, 0x2a, 0xc0, 0x7d, 0x8a, 0x8b, 0xd1, 0x2b, 0x58, 0x8e, 0x88, 0x0e, + 0x68, 0xfb, 0xe1, 0x94, 0x58, 0x1d, 0xaf, 0xab, 0x54, 0xb8, 0x47, 0xe9, 0x4a, 0x16, 0xaf, 0x98, + 0xe2, 0xe0, 0xc1, 0x23, 0xae, 0x32, 0xeb, 0xc7, 0x2b, 0x4d, 0x87, 0xb6, 0x40, 0x8e, 0xc8, 0x4f, + 0xac, 0x36, 0xf9, 0xad, 0x32, 0xc7, 0x49, 0x12, 0x72, 0xf4, 0x33, 0x98, 0x39, 0xec, 0x1a, 0xbd, + 0x36, 0x8f, 0xcd, 0x7c, 0x43, 0x6a, 0xce, 0xef, 0x3e, 0xdb, 0xe6, 0xc9, 0xb2, 0x1d, 0xc1, 0x86, + 0x10, 0x3c, 0x44, 0xa3, 0x5f, 0xc2, 0x12, 0x31, 0x6d, 0xef, 0x21, 0xe6, 0x83, 0xb2, 0xd8, 0x90, + 0x9a, 0x95, 0xd0, 0xca, 0x71, 0x0a, 0xa4, 0x55, 0xc0, 0xa9, 0x5b, 0xd1, 0x6f, 0x40, 0x71, 0x89, + 0xd5, 0x3e, 0xa3, 0x16, 0x49, 0x98, 0x45, 0xdc, 0xec, 0x5a, 0x60, 0xf6, 0x72, 0x04, 0xac, 0x55, + 0xc0, 0x23, 0x4d, 0x20, 0x07, 0xd6, 0xe2, 0xf7, 0x29, 0xce, 0xf2, 0x84, 0xb3, 0x6c, 0x06, 0x2c, + 0xef, 0xb3, 0xd1, 0xad, 0x02, 0x1e, 0x67, 0x10, 0xfd, 0x49, 0x82, 0x8d, 0xbe, 0xdd, 0xd6, 0x3c, + 0x32, 0xc6, 0x98, 0xb2, 0xc4, 0xa9, 0x5f, 0x06, 0xd4, 0x1f, 0xf2, 0xec, 0x69, 0x15, 0x70, 0x3e, + 0xe3, 0xdc, 0x0d, 0x87, 0x98, 0xf4, 0x7e, 0xac, 0x1b, 0xcb, 0x82, 0x1b, 0x38, 0xcf, 0x1e, 0xe6, + 0x46, 0x2e, 0xe3, 0xe8, 0x0f, 0x12, 0xac, 0xeb, 0x3d, 0xcd, 0x30, 0xc7, 0x79, 0xb1, 0xc2, 0xbd, + 0xf8, 0x36, 0xf0, 0xe2, 0x30, 0xc7, 0x96, 0x56, 0x01, 0xe7, 0x32, 0x8d, 0x3e, 0x83, 0xea, 0x12, + 0xaf, 0x6f, 0x07, 0x6f, 0xc5, 0x91, 0xe6, 0x69, 0x2e, 0xf1, 0xe2, 0x0e, 0x54, 0xb9, 0x03, 0x3f, + 0x0e, 0xd3, 0x6d, 0xdc, 0x86, 0x56, 0x01, 0xe7, 0x30, 0x8b, 0x7e, 0x0f, 0x2f, 0xfc, 0x48, 0x65, + 0xb3, 0x2b, 0x9c, 0x7d, 0x4b, 0xf8, 0x11, 0xc6, 0xd1, 0xe7, 0x31, 0x8c, 0x7a, 0xb0, 0xaa, 0xd9, + 0xb6, 0x43, 0xef, 0xb5, 0xde, 0x31, 0x2f, 0x1e, 0x71, 0xe6, 0xa7, 0x9c, 0x79, 0x3d, 0x60, 0xde, + 0xcf, 0xc2, 0xb6, 0x0a, 0x38, 0xdb, 0x18, 0x63, 0x13, 0xcb, 0x51, 0x9c, 0xad, 0x26, 0xb0, 0x9d, + 0x65, 0x61, 0x19, 0x5b, 0xa6, 0x31, 0x64, 0x40, 0x3d, 0x28, 0x70, 0x87, 0xd4, 0x34, 0x8d, 0x44, + 0x50, 0x9f, 0x71, 0xb2, 0x17, 0x01, 0xd9, 0xdb, 0x0c, 0x68, 0xab, 0x80, 0x33, 0x4d, 0x45, 0xa8, + 0x30, 0xb9, 0x27, 0x5a, 0x2f, 0x4e, 0x55, 0x4f, 0xa3, 0x4a, 0x85, 0x46, 0xa8, 0x52, 0xf5, 0x8c, + 0xaa, 0x67, 0x7c, 0xec, 0x1b, 0xed, 0x0b, 0xed, 0xc1, 0x24, 0x56, 0xe2, 0x54, 0xab, 0x02, 0xd5, + 0x69, 0x06, 0x94, 0x51, 0x65, 0x99, 0x42, 0x7d, 0x68, 0x08, 0xfa, 0x4b, 0x8f, 0xda, 0x71, 0xba, + 0x6f, 0x38, 0xdd, 0x8f, 0xd2, 0xe8, 0x52, 0xe0, 0xad, 0x02, 0x1e, 0x6b, 0x12, 0x5d, 0xc1, 0xb2, + 0xe6, 0x51, 0xd3, 0xd0, 0xe3, 0x5c, 0x6b, 0x9c, 0xab, 0x3e, 0xc8, 0xc5, 0x34, 0x4c, 0xab, 0x80, + 0xd3, 0x37, 0xa3, 0x3a, 0xcc, 0x84, 0x99, 0xa2, 0x34, 0x78, 0xb9, 0x1c, 0x0a, 0xd0, 0x06, 0x4c, + 0xfa, 0x29, 0xab, 0x3c, 0xe7, 0x24, 0x73, 0x83, 0x72, 0xc5, 0x85, 0x38, 0x50, 0xb2, 0x96, 0xe8, + 0x8c, 0xb8, 0xae, 0xd6, 0x21, 0x8a, 0xca, 0x4d, 0x0c, 0x96, 0x07, 0x8b, 0x42, 0xe1, 0x67, 0x8c, + 0xea, 0x0a, 0x2c, 0xa5, 0x55, 0x3b, 0xf5, 0x35, 0x28, 0xa3, 0xca, 0x15, 0xaa, 0xc1, 0xe4, 0xbe, + 0xc9, 0xee, 0x2b, 0x6f, 0xb9, 0xfc, 0xf6, 0x22, 0x90, 0xa8, 0xff, 0x92, 0x60, 0x6d, 0xdc, 0x63, + 0xb6, 0x0e, 0x73, 0x0c, 0x72, 0xd1, 0xbf, 0xe9, 0x19, 0xfa, 0x3b, 0xf2, 0xc0, 0xcd, 0xcc, 0x62, + 0x51, 0x88, 0x36, 0x61, 0x3e, 0xd6, 0x38, 0x15, 0x39, 0x6c, 0x3e, 0xd1, 0x2f, 0xcd, 0x9d, 0x52, + 0xfd, 0x8e, 0xb4, 0x0f, 0xb4, 0x9e, 0x66, 0xe9, 0x24, 0xd2, 0xd9, 0x89, 0x0a, 0xf4, 0x1d, 0x94, + 0x2f, 0x28, 0xfd, 0x64, 0xf1, 0xf6, 0xae, 0xb2, 0x5b, 0x0d, 0xc2, 0x77, 0x11, 0xeb, 0x7c, 0xb1, + 0x8f, 0x52, 0xff, 0x29, 0xc1, 0x46, 0xae, 0x8a, 0x96, 0xf3, 0x40, 0x09, 0x47, 0x8b, 0x63, 0x1d, + 0x2d, 0xe5, 0x72, 0xf4, 0x0c, 0x36, 0x72, 0x95, 0xbc, 0x7c, 0x7e, 0xaa, 0x9f, 0x61, 0x3d, 0x4f, + 0xed, 0xca, 0x79, 0xea, 0xf0, 0x2c, 0xc5, 0x5c, 0x67, 0xb9, 0x06, 0x75, 0x7c, 0xdd, 0x42, 0x35, + 0x98, 0xbe, 0x70, 0xa8, 0x4d, 0x1c, 0xcf, 0x67, 0x9d, 0xc1, 0xe1, 0x1a, 0x2d, 0x41, 0xf9, 0x5a, + 0xeb, 0xf5, 0xfd, 0xf0, 0xce, 0x60, 0x7f, 0xa1, 0xfe, 0x0a, 0x5e, 0xe4, 0xa8, 0x48, 0x5f, 0x61, + 0xf8, 0x0b, 0xac, 0x66, 0x16, 0x1c, 0xf4, 0x3d, 0x4c, 0x0f, 0x00, 0xdc, 0xe4, 0xfc, 0xee, 0xb2, + 0x70, 0x6f, 0x07, 0x4a, 0x1c, 0xc2, 0x58, 0xa6, 0x44, 0x9b, 0xde, 0xe8, 0x57, 0x8c, 0xa8, 0x50, + 0xff, 0x2b, 0xc1, 0x6a, 0x66, 0x05, 0x42, 0x27, 0x80, 0x44, 0xc0, 0x89, 0x75, 0x4b, 0xb9, 0x23, + 0x95, 0xdd, 0xa7, 0xa9, 0x35, 0x8c, 0x01, 0x70, 0xca, 0x26, 0xb4, 0x07, 0xca, 0x07, 0xcb, 0x35, + 0x3a, 0x16, 0x69, 0x47, 0x59, 0x78, 0x6f, 0xef, 0xdf, 0xcd, 0x91, 0x7a, 0xb4, 0x07, 0x73, 0xa2, + 0x07, 0x7e, 0x6a, 0x2f, 0x0d, 0x7a, 0x15, 0x81, 0x5c, 0x84, 0xaa, 0x7b, 0x50, 0xcf, 0x2a, 0x7c, + 0xec, 0x47, 0x63, 0x4a, 0xfe, 0x21, 0xe3, 0xe7, 0x60, 0xb8, 0x56, 0xbf, 0x84, 0x7b, 0xd3, 0x2b, + 0xd5, 0x2b, 0xa8, 0x04, 0xfa, 0x48, 0x5c, 0x90, 0x58, 0x03, 0xb9, 0x4f, 0x51, 0x18, 0x7b, 0x9b, + 0xd8, 0xff, 0xce, 0xf0, 0xb1, 0x0e, 0xde, 0x26, 0x51, 0xaa, 0x76, 0xa1, 0x9e, 0x55, 0xdc, 0xb2, + 0x5e, 0x52, 0xf4, 0x12, 0x16, 0x0e, 0xa9, 0x69, 0xf7, 0x88, 0x47, 0xce, 0x0c, 0xab, 0x3f, 0x08, + 0xf2, 0x04, 0x07, 0xc5, 0x55, 0xea, 0x29, 0x34, 0xc6, 0xd5, 0xb5, 0x64, 0x5a, 0x49, 0xa3, 0xd2, + 0xea, 0x3f, 0x12, 0x2c, 0xa7, 0x96, 0xae, 0xcc, 0x1c, 0x90, 0x1a, 0xa5, 0xcc, 0x1c, 0x38, 0x05, + 0x08, 0x43, 0xc3, 0x0e, 0x53, 0x8a, 0xf4, 0xec, 0xa9, 0x6c, 0xc3, 0xb4, 0x70, 0x8f, 0x2d, 0xcf, + 0x79, 0xc0, 0x91, 0xfd, 0xb5, 0x9f, 0xc3, 0x42, 0x4c, 0x8d, 0x64, 0x28, 0xdd, 0x91, 0xc1, 0xc5, + 0x65, 0xff, 0xb2, 0x3b, 0x7b, 0x1f, 0xde, 0xd9, 0x59, 0xec, 0x2f, 0xf6, 0x8a, 0x6f, 0x24, 0xf5, + 0x5b, 0x58, 0xfe, 0x85, 0x70, 0xff, 0x31, 0xf9, 0xd8, 0x27, 0xae, 0x17, 0xcc, 0x0d, 0xa4, 0xe8, + 0xdc, 0x40, 0xfd, 0x5b, 0x11, 0x56, 0x44, 0xb4, 0x3b, 0x80, 0x27, 0xcb, 0x94, 0x94, 0x5a, 0xa6, + 0x86, 0xc3, 0x85, 0xa2, 0x30, 0x5c, 0xd8, 0x82, 0xf9, 0xf0, 0xcb, 0xfc, 0xd2, 0xd3, 0x1c, 0x2f, + 0x52, 0xbf, 0x62, 0x1a, 0xb4, 0x09, 0xb3, 0xa1, 0xe4, 0xd8, 0x6a, 0xf3, 0x3a, 0xe6, 0x23, 0x05, + 0x79, 0xda, 0x08, 0xa1, 0x9c, 0x3e, 0x42, 0xf8, 0x1e, 0xe0, 0x22, 0x1c, 0xed, 0xf0, 0xc9, 0x44, + 0x65, 0x77, 0x71, 0xf0, 0x44, 0x87, 0x0a, 0x1c, 0x01, 0xa9, 0x77, 0x50, 0x4d, 0x84, 0xc2, 0xb5, + 0xa9, 0xe5, 0x12, 0xa4, 0x40, 0xf9, 0x8a, 0x7a, 0xc1, 0x3b, 0xe7, 0x27, 0xaa, 0x2f, 0x40, 0xaf, + 0x61, 0x36, 0xba, 0x23, 0xf8, 0xf1, 0x51, 0xf2, 0xab, 0x1d, 0x0b, 0x38, 0xf5, 0x08, 0x56, 0x2e, + 0xa8, 0x9b, 0xf6, 0x33, 0x89, 0x03, 0x83, 0x41, 0x02, 0xb2, 0xc8, 0x27, 0xe4, 0xea, 0x39, 0x54, + 0x13, 0x56, 0x02, 0x97, 0x5f, 0x09, 0xe3, 0xa4, 0xd8, 0xfd, 0x8f, 0x6e, 0x88, 0xc2, 0xd4, 0xbf, + 0x4b, 0xb0, 0xc2, 0xda, 0xa3, 0x1f, 0xe6, 0x17, 0x6b, 0xf7, 0x0e, 0xbb, 0x9a, 0xe1, 0xff, 0x42, + 0x2c, 0x2d, 0xca, 0x78, 0x28, 0x60, 0xbf, 0xa2, 0x3f, 0x5a, 0x1a, 0x56, 0xd8, 0x92, 0x3f, 0xa6, + 0x89, 0x89, 0xd5, 0x43, 0xa8, 0x26, 0xbc, 0x09, 0xce, 0xd7, 0x84, 0x29, 0xec, 0xcf, 0xe8, 0x82, + 0xb3, 0xcd, 0x87, 0xdf, 0x67, 0x5c, 0x8a, 0x07, 0x6a, 0xf5, 0xcf, 0x12, 0xac, 0x05, 0x87, 0xe0, + 0x03, 0xb1, 0x11, 0xc9, 0x2e, 0x3c, 0x14, 0xfe, 0x9d, 0x2f, 0xe1, 0x98, 0x74, 0xcc, 0xc1, 0x32, + 0xa7, 0x70, 0xea, 0x3f, 0x24, 0xa8, 0xb3, 0xd3, 0x8c, 0x74, 0x42, 0x30, 0x2e, 0xc5, 0x8d, 0xbf, + 0x84, 0xc5, 0xe8, 0xa6, 0x41, 0x75, 0x62, 0x2f, 0x53, 0x52, 0xf1, 0x7f, 0xc4, 0xf8, 0x1d, 0xac, + 0x8e, 0xf0, 0x2a, 0x88, 0xf4, 0x16, 0x4c, 0x07, 0xa1, 0xf4, 0xa3, 0x92, 0x0c, 0x75, 0xa8, 0x57, + 0xcf, 0x60, 0x4d, 0xbc, 0x43, 0x67, 0x86, 0x65, 0x98, 0x7d, 0xf3, 0x2d, 0x21, 0x5f, 0x93, 0xdf, + 0x6f, 0xa0, 0x31, 0xda, 0x5c, 0xe0, 0x5e, 0x30, 0x2c, 0x94, 0x84, 0x61, 0xe1, 0xd6, 0xe3, 0x04, + 0xa4, 0x8c, 0x15, 0xe5, 0xf8, 0x27, 0x81, 0x5c, 0x40, 0x8a, 0x3f, 0x04, 0x8d, 0x7f, 0x10, 0xc8, + 0x12, 0x5a, 0x83, 0x67, 0x19, 0xad, 0xa2, 0x5c, 0x44, 0x9b, 0xf0, 0x7c, 0x6c, 0x1f, 0x2d, 0x3f, + 0x72, 0xdc, 0xd8, 0x3e, 0x56, 0x7e, 0x9c, 0x40, 0x1b, 0xd0, 0x18, 0xd7, 0xa0, 0xca, 0x8f, 0x93, + 0x48, 0x85, 0x6f, 0xb2, 0x5b, 0x49, 0xb9, 0x84, 0xd6, 0x59, 0xce, 0x67, 0xb6, 0x85, 0xf2, 0x1f, + 0x8b, 0x68, 0x15, 0x9e, 0x8e, 0xec, 0xf1, 0xe4, 0x09, 0xa6, 0x1e, 0xd9, 0x83, 0xc9, 0x65, 0x54, + 0x07, 0x65, 0x54, 0x13, 0x20, 0x4f, 0xa2, 0xe7, 0xb1, 0x16, 0x21, 0x56, 0xb8, 0xe5, 0xbf, 0x14, + 0xd1, 0x3a, 0x34, 0x84, 0xfe, 0x87, 0xc1, 0xd8, 0x2a, 0x0a, 0x9b, 0x62, 0x86, 0x84, 0x4e, 0x27, + 0x8e, 0xf8, 0x6b, 0x11, 0x2d, 0xc3, 0x62, 0xa2, 0xce, 0xca, 0xd3, 0x5b, 0xe7, 0xc2, 0xbc, 0x76, + 0x38, 0x2c, 0x9d, 0x83, 0x99, 0xf7, 0xd4, 0x22, 0x5c, 0x20, 0x17, 0x50, 0x15, 0x9e, 0x88, 0xc7, + 0xf4, 0x15, 0x12, 0x5a, 0x80, 0x8a, 0x6f, 0xd6, 0x17, 0x14, 0x0f, 0xb6, 0x7e, 0xdd, 0xec, 0x18, + 0x5e, 0xb7, 0x7f, 0xb3, 0xad, 0x53, 0x73, 0xe7, 0x77, 0x94, 0xde, 0xe8, 0xfe, 0xdf, 0xef, 0x74, + 0xea, 0x90, 0x1d, 0x9d, 0x9a, 0x26, 0xb5, 0x76, 0xf8, 0xe5, 0xb8, 0x99, 0xe4, 0x73, 0xfd, 0x9f, + 0xfe, 0x2f, 0x00, 0x00, 0xff, 0xff, 0x8d, 0x86, 0x32, 0x40, 0xa7, 0x18, 0x00, 0x00, } diff --git a/common/model/transactionBody.go b/common/model/transactionBody.go index 472082fa2..f607af3aa 100644 --- a/common/model/transactionBody.go +++ b/common/model/transactionBody.go @@ -66,3 +66,4 @@ func (*FeeVoteCommitTransactionBody) isTransaction_TransactionBody() {} func (*FeeVoteRevealTransactionBody) isTransaction_TransactionBody() {} func (*LiquidPaymentTransactionBody) isTransaction_TransactionBody() {} func (*LiquidPaymentStopTransactionBody) isTransaction_TransactionBody() {} +func (*AtomicTransactionBody) isTransaction_TransactionBody() {} diff --git a/common/query/atomicTransaction.go b/common/query/atomicTransaction.go new file mode 100644 index 000000000..9954be41a --- /dev/null +++ b/common/query/atomicTransaction.go @@ -0,0 +1,175 @@ +package query + +import ( + "database/sql" + "fmt" + "strings" + + "github.com/zoobc/zoobc-core/common/blocker" + "github.com/zoobc/zoobc-core/common/model" +) + +type ( + AtomicTransactionQuery struct { + Fields []string + TableName string + } + AtomicTransactionQueryInterface interface { + InsertAtomicTransactions(atomics []*model.Atomic) (str string, args []interface{}) + ExtractModel(atomic *model.Atomic) []interface{} + BuildModel(atomics []*model.Atomic, rows *sql.Rows) ([]*model.Atomic, error) + Scan(atomic *model.Atomic, row *sql.Row) error + } +) + +func NewAtomicTransactionQuery() *AtomicTransactionQuery { + return &AtomicTransactionQuery{ + Fields: []string{ + "id", + "transaction_id", + "sender_address", + "block_height", + "unsigned_transaction", + "signature", + "atomic_index", + }, + TableName: "atomic_transaction", + } +} + +func (a *AtomicTransactionQuery) InsertAtomicTransactions(atomics []*model.Atomic) (str string, args []interface{}) { + if len(atomics) > 0 { + str = fmt.Sprintf( + "INSERT INTO %s (%s) VALUES ", + a.getTableName(), + strings.Join(a.Fields, ", "), + ) + for k, atomic := range atomics { + str += fmt.Sprintf( + "(?%s)", + strings.Repeat(", ?", len(a.Fields)-1), + ) + if k < len(atomics)-1 { + str += "," + } + + args = append(args, a.ExtractModel(atomic)...) + } + } + return str, args +} + +func (a *AtomicTransactionQuery) ExtractModel(atomic *model.Atomic) []interface{} { + return []interface{}{ + atomic.GetID(), + atomic.GetTransactionID(), + atomic.GetSenderAddress(), + atomic.GetBlockHeight(), + atomic.GetUnsignedTransaction(), + atomic.GetSignature(), + atomic.GetAtomicIndex(), + } +} + +func (a *AtomicTransactionQuery) BuildModel(atomics []*model.Atomic, rows *sql.Rows) ([]*model.Atomic, error) { + for rows.Next() { + var ( + atomic model.Atomic + err error + ) + err = rows.Scan( + &atomic.ID, + &atomic.TransactionID, + &atomic.SenderAddress, + &atomic.BlockHeight, + &atomic.UnsignedTransaction, + &atomic.Signature, + &atomic.AtomicIndex, + ) + if err != nil { + return atomics, err + } + atomics = append(atomics, &atomic) + } + return atomics, nil +} + +func (a *AtomicTransactionQuery) Scan(atomic *model.Atomic, row *sql.Row) error { + return row.Scan( + &atomic.ID, + &atomic.TransactionID, + &atomic.SenderAddress, + &atomic.BlockHeight, + &atomic.UnsignedTransaction, + &atomic.Signature, + &atomic.AtomicIndex, + ) +} + +func (a *AtomicTransactionQuery) getTableName() string { + return a.TableName +} + +func (a *AtomicTransactionQuery) Rollback(height uint32) (queries [][]interface{}) { + return [][]interface{}{ + { + fmt.Sprintf("DELETE FROM %s WHERE height > ?", a.getTableName()), + height, + }, + } +} + +func (a *AtomicTransactionQuery) SelectDataForSnapshot(fromHeight, toHeight uint32) string { + return fmt.Sprintf( + "SELECT %s FROM %s WHERE (transaction_id, block_height) IN "+ + "(SELECT tx.transaction_id, MAX(tx.block_height) FROM %s tx "+ + "WHERE tx.block_height >= %d AND tx.block_height <= %d AND tx.block_height != 0 GROUP BY tx.transaction_id) "+ + "ORDER BY block_height", + strings.Join(a.Fields, ", "), + a.getTableName(), + a.getTableName(), + fromHeight, + toHeight, + ) +} + +func (a *AtomicTransactionQuery) TrimDataBeforeSnapshot(fromHeight, toHeight uint32) string { + return fmt.Sprintf( + "DELETE FROM %s WHERE block_height >= %d AND block_height <= %d AND block_height != 0", + a.getTableName(), + fromHeight, + toHeight, + ) + +} + +func (a *AtomicTransactionQuery) ImportSnapshot(payload interface{}) ([][]interface{}, error) { + var ( + queries [][]interface{} + ) + + atomicTXs, ok := payload.([]*model.Atomic) + if !ok { + return nil, blocker.NewBlocker(blocker.DBErr, "ImportSnapshotCannotCastTo"+a.TableName) + } + if len(atomicTXs) > 0 { + var ( + qry string + args []interface{} + ) + recordsPerPeriod, rounds, remaining := CalculateBulkSize(len(a.Fields), len(atomicTXs)) + for i := 0; i < rounds; i++ { + qry, args = a.InsertAtomicTransactions(atomicTXs[i*recordsPerPeriod : (i*recordsPerPeriod)+recordsPerPeriod]) + queries = append(queries, append([]interface{}{qry}, args...)) + } + if remaining > 0 { + qry, args = a.InsertAtomicTransactions(atomicTXs[len(atomicTXs)-remaining:]) + queries = append(queries, append([]interface{}{qry}, args...)) + } + } + return queries, nil +} + +func (a *AtomicTransactionQuery) RecalibrateVersionedTable() []string { + return []string{} +} diff --git a/common/query/atomicTransaction_test.go b/common/query/atomicTransaction_test.go new file mode 100644 index 000000000..bea5c7a2e --- /dev/null +++ b/common/query/atomicTransaction_test.go @@ -0,0 +1,122 @@ +package query + +import ( + "reflect" + "testing" + + "github.com/zoobc/zoobc-core/common/model" +) + +func TestAtomicTransactionQuery_InsertAtomicTransactions(t *testing.T) { + type fields struct { + Fields []string + TableName string + } + type args struct { + atomics []*model.Atomic + } + tests := []struct { + name string + fields fields + args args + wantStr string + wantArgs []interface{} + }{ + { + name: "WantSuccess", + fields: fields(*NewAtomicTransactionQuery()), + args: args{ + atomics: []*model.Atomic{ + { + ID: 123456789, + TransactionID: 1234567890, + SenderAddress: []byte{}, + BlockHeight: 1, + UnsignedTransaction: []byte{}, + Signature: []byte{}, + AtomicIndex: 0, + }, + }, + }, + wantStr: "INSERT INTO atomic_transaction (id, transaction_id, sender_address, block_height, unsigned_transaction, signature, atomic_index) " + + "VALUES (?, ?, ?, ?, ?, ?, ?)", + wantArgs: []interface{}{ + int64(123456789), + int64(1234567890), + []byte{}, + uint32(1), + []byte{}, + []byte{}, + uint32(0), + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + a := &AtomicTransactionQuery{ + Fields: tt.fields.Fields, + TableName: tt.fields.TableName, + } + gotStr, gotArgs := a.InsertAtomicTransactions(tt.args.atomics) + if gotStr != tt.wantStr { + t.Errorf("InsertAtomicTransactions() gotStr = \n%v, want \n%v", gotStr, tt.wantStr) + return + } + if !reflect.DeepEqual(gotArgs, tt.wantArgs) { + t.Errorf("InsertAtomicTransactions() gotArgs = \n%v, want \n%v", gotArgs, tt.wantArgs) + } + }) + } +} + +func TestAtomicTransactionQuery_ExtractModel(t *testing.T) { + type fields struct { + Fields []string + TableName string + } + type args struct { + atomic *model.Atomic + } + tests := []struct { + name string + fields fields + args args + want []interface{} + }{ + { + name: "WantSuccess", + fields: fields(*NewAtomicTransactionQuery()), + args: args{ + atomic: &model.Atomic{ + ID: 123456789, + TransactionID: 1234567890, + SenderAddress: []byte{}, + BlockHeight: 1, + UnsignedTransaction: []byte{}, + Signature: []byte{}, + AtomicIndex: 0, + }, + }, + want: []interface{}{ + int64(123456789), + int64(1234567890), + []byte{}, + uint32(1), + []byte{}, + []byte{}, + uint32(0), + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + a := &AtomicTransactionQuery{ + Fields: tt.fields.Fields, + TableName: tt.fields.TableName, + } + if got := a.ExtractModel(tt.args.atomic); !reflect.DeepEqual(got, tt.want) { + t.Errorf("ExtractModel() = %v, want %v", got, tt.want) + } + }) + } +} diff --git a/common/query/query.go b/common/query/query.go index 9a8d75772..1c490df8c 100644 --- a/common/query/query.go +++ b/common/query/query.go @@ -101,6 +101,7 @@ func GetDerivedQuery(ct chaintype.ChainType) (derivedQuery []DerivedQuery) { NewNodeAdmissionTimestampQuery(), NewMultiSignatureParticipantQuery(), NewBatchReceiptQuery(), + NewAtomicTransactionQuery(), NewMerkleTreeQuery(), } derivedQuery = append(derivedQuery, mainchainDerivedQuery...) @@ -135,6 +136,7 @@ func GetSnapshotQuery(ct chaintype.ChainType) (snapshotQuery map[string]Snapshot "feeVoteReveal": NewFeeVoteRevealVoteQuery(), "liquidPaymentTransaction": NewLiquidPaymentTransactionQuery(), "nodeAdmissionTimestamp": NewNodeAdmissionTimestampQuery(), + "atomicTransaction": NewAtomicTransactionQuery(), } default: snapshotQuery = map[string]SnapshotQuery{} diff --git a/common/query/query_test.go b/common/query/query_test.go index 0d04e503b..76f49eddb 100644 --- a/common/query/query_test.go +++ b/common/query/query_test.go @@ -91,6 +91,7 @@ func TestGetDerivedQuery(t *testing.T) { NewNodeAdmissionTimestampQuery(), NewMultiSignatureParticipantQuery(), NewBatchReceiptQuery(), + NewAtomicTransactionQuery(), NewMerkleTreeQuery(), }, }, diff --git a/common/query/transactionQuery.go b/common/query/transactionQuery.go index 411d8a519..94fb67782 100644 --- a/common/query/transactionQuery.go +++ b/common/query/transactionQuery.go @@ -61,6 +61,7 @@ import ( type ( TransactionQueryInterface interface { InsertTransaction(tx *model.Transaction) (str string, args []interface{}) + InsertTransactions(txs []*model.Transaction) (str string, args []interface{}) GetTransaction(id int64) string GetTransactionsByIds(txIds []int64) (str string, args []interface{}) GetTransactionsByBlockID(blockID int64) (str string, args []interface{}) @@ -94,7 +95,7 @@ func NewTransactionQuery(chaintype chaintype.ChainType) *TransactionQuery { "signature", "version", "transaction_index", - "multisig_child", + "child_type", "message", }, TableName: "\"transaction\"", @@ -125,19 +126,42 @@ func (tq *TransactionQuery) InsertTransaction(tx *model.Transaction) (str string return query, tq.ExtractModel(tx) } +func (tq *TransactionQuery) InsertTransactions(txs []*model.Transaction) (str string, args []interface{}) { + if len(txs) > 0 { + str = fmt.Sprintf( + "INSERT INTO %s (%s) VALUES ", + tq.getTableName(), + strings.Join(tq.Fields, ", "), + ) + for k, atomic := range txs { + str += fmt.Sprintf( + "(?%s)", + strings.Repeat(", ?", len(tq.Fields)-1), + ) + if k < len(txs)-1 { + str += "," + } + + args = append(args, tq.ExtractModel(atomic)...) + } + } + return str, args + +} func (tq *TransactionQuery) GetTransactionsByBlockID(blockID int64) (str string, args []interface{}) { - query := fmt.Sprintf("SELECT %s FROM %s WHERE block_id = ? AND multisig_child = false "+ + query := fmt.Sprintf("SELECT %s FROM %s WHERE block_id = ? AND child_type = ? "+ "ORDER BY transaction_index ASC", strings.Join(tq.Fields, ", "), tq.getTableName()) - return query, []interface{}{blockID} + return query, []interface{}{blockID, uint32(model.TransactionChildType_NoneChild)} } func (tq *TransactionQuery) GetTransactionsByIds(txIds []int64) (str string, args []interface{}) { + args = append(args, uint32(model.TransactionChildType_NoneChild)) for _, id := range txIds { args = append(args, id) } return fmt.Sprintf( - "SELECT %s FROM %s WHERE multisig_child = false AND id IN(?%s)", + "SELECT %s FROM %s WHERE child_type = ? AND id IN(?%s)", strings.Join(tq.Fields, ", "), tq.getTableName(), strings.Repeat(", ?", len(txIds)-1), @@ -162,7 +186,7 @@ func (*TransactionQuery) ExtractModel(tx *model.Transaction) []interface{} { &tx.Signature, &tx.Version, &tx.TransactionIndex, - &tx.MultisigChild, + &tx.ChildType, &tx.Message, } } @@ -188,7 +212,7 @@ func (*TransactionQuery) BuildModel(txs []*model.Transaction, rows *sql.Rows) ([ &tx.Signature, &tx.Version, &tx.TransactionIndex, - &tx.MultisigChild, + &tx.ChildType, &tx.Message, ) if err != nil { @@ -215,7 +239,7 @@ func (*TransactionQuery) Scan(tx *model.Transaction, row *sql.Row) error { &tx.Signature, &tx.Version, &tx.TransactionIndex, - &tx.MultisigChild, + &tx.ChildType, &tx.Message, ) return err diff --git a/common/query/transactionQuery_test.go b/common/query/transactionQuery_test.go index ef0a17b41..cc7259c3a 100644 --- a/common/query/transactionQuery_test.go +++ b/common/query/transactionQuery_test.go @@ -126,7 +126,7 @@ func TestGetTransaction(t *testing.T) { want: "SELECT id, block_id, block_height, sender_account_address, " + "recipient_account_address, transaction_type, fee, timestamp, " + "transaction_hash, transaction_body_length, transaction_body_bytes, signature, version, " + - "transaction_index, multisig_child, message from \"transaction\"" + + "transaction_index, child_type, message from \"transaction\"" + " WHERE id = 1", }, } @@ -250,11 +250,11 @@ func TestTransactionQuery_GetTransactionsByBlockID(t *testing.T) { name: "wantSuccess", fields: fields(*mockTransactionQuery), args: args{blockID: int64(1)}, - wantStr: fmt.Sprintf("SELECT %s FROM \"transaction\" WHERE block_id = ? AND multisig_child = false"+ + wantStr: fmt.Sprintf("SELECT %s FROM \"transaction\" WHERE block_id = ? AND child_type = ?"+ " ORDER BY transaction_index ASC", strings.Join(mockTransactionQuery.Fields, ", "), ), - wantArgs: []interface{}{int64(1)}, + wantArgs: []interface{}{int64(1), uint32(model.TransactionChildType_NoneChild)}, }, } for _, tt := range tests { @@ -298,8 +298,9 @@ func TestTransactionQuery_GetTransactionsByIds(t *testing.T) { args: args{txIds: []int64{1, 2, 3, 4}}, wantStr: "SELECT id, block_id, block_height, sender_account_address, recipient_account_address, transaction_type, fee, timestamp, " + "transaction_hash, transaction_body_length, transaction_body_bytes, signature, version, transaction_index, " + - "multisig_child, message FROM \"transaction\" WHERE multisig_child = false AND id IN(?, ?, ?, ?)", + "child_type, message FROM \"transaction\" WHERE child_type = ? AND id IN(?, ?, ?, ?)", wantArgs: []interface{}{ + uint32(model.TransactionChildType_NoneChild), int64(1), int64(2), int64(3), @@ -349,7 +350,7 @@ func (*mockQueryExecutorBuildModel) ExecuteSelect(query string, tx bool, args .. make([]byte, 68), 1, 1, - false, + model.TransactionChildType_NoneChild, []byte{1, 2, 3}, ), ) @@ -422,8 +423,8 @@ func (*mockRowTransactionQueryScan) ExecuteSelectRow(qStr string, args ...interf make([]byte, 68), 1, 1, - false, - "", + model.TransactionChildType_MultiSignatureChild, + []byte{}, ), ) return db.QueryRow("") diff --git a/common/transaction/atomicTransaction.go b/common/transaction/atomicTransaction.go new file mode 100644 index 000000000..3bbfa2b13 --- /dev/null +++ b/common/transaction/atomicTransaction.go @@ -0,0 +1,484 @@ +package transaction + +import ( + "bytes" + "database/sql" + "encoding/hex" + "errors" + + "github.com/zoobc/zoobc-core/common/accounttype" + "github.com/zoobc/zoobc-core/common/blocker" + "github.com/zoobc/zoobc-core/common/constant" + "github.com/zoobc/zoobc-core/common/crypto" + "github.com/zoobc/zoobc-core/common/fee" + "github.com/zoobc/zoobc-core/common/model" + "github.com/zoobc/zoobc-core/common/query" + "github.com/zoobc/zoobc-core/common/util" + "golang.org/x/crypto/sha3" +) + +type ( + // AtomicTransaction field for AtomicTransactionInterface + AtomicTransaction struct { + ID int64 + Fee int64 + SenderAddress []byte + Height uint32 + Body *model.AtomicTransactionBody + AtomicTransactionQuery query.AtomicTransactionQueryInterface + Escrow *model.Escrow + EscrowQuery query.EscrowTransactionQueryInterface + QueryExecutor query.ExecutorInterface + TransactionQuery query.TransactionQueryInterface + TypeActionSwitcher TypeActionSwitcher + AccountBalanceHelper AccountBalanceHelperInterface + EscrowFee fee.FeeModelInterface + NormalFee fee.FeeModelInterface + TransactionUtil UtilInterface + Signature crypto.SignatureInterface + } +) + +func (tx *AtomicTransaction) ApplyConfirmed(blockTimestamp int64) (err error) { + + var ( + atomics []*model.Atomic + txs []*model.Transaction + queries [][]interface{} + ) + + err = tx.AccountBalanceHelper.AddAccountBalance( + tx.SenderAddress, + -tx.Fee, + model.EventType_EventAtomicTransaction, + tx.Height, + tx.ID, + uint64(blockTimestamp), + ) + if err != nil { + return err + } + + for k, unsignedTX := range tx.Body.GetUnsignedTransactionBytes() { + var ( + innerTX *model.Transaction + typeAction TypeAction + ) + + innerTX, err = tx.TransactionUtil.ParseTransactionBytes(unsignedTX, false) + if err != nil { + return err + } + typeAction, err = tx.TypeActionSwitcher.GetTransactionType(innerTX) + if err != nil { + return err + } + err = typeAction.ApplyConfirmed(blockTimestamp) + if err != nil { + return err + } + + atomics = append(atomics, &model.Atomic{ + ID: innerTX.GetID(), + TransactionID: tx.ID, + SenderAddress: innerTX.GetSenderAccountAddress(), + BlockHeight: tx.Height, + UnsignedTransaction: unsignedTX, + Signature: tx.Body.GetSignatures()[hex.EncodeToString(innerTX.GetSenderAccountAddress())], + AtomicIndex: uint32(k), + }) + + innerTX.ChildType = model.TransactionChildType_AtomicChild + txs = append(txs, innerTX) + } + txQ, txArgs := tx.TransactionQuery.InsertTransactions(txs) + queries = append(queries, append([]interface{}{txQ}, txArgs...)) + atomicQ, atomicArgs := tx.AtomicTransactionQuery.InsertAtomicTransactions(atomics) + queries = append(queries, append([]interface{}{atomicQ}, atomicArgs...)) + err = tx.QueryExecutor.ExecuteTransactions(queries) + if err != nil { + return err + } + return nil +} + +func (tx *AtomicTransaction) ApplyUnconfirmed() error { + + for _, unsignedTX := range tx.Body.GetUnsignedTransactionBytes() { + var ( + innerTX *model.Transaction + typeAction TypeAction + ) + innerTX, err := tx.TransactionUtil.ParseTransactionBytes(unsignedTX, false) + if err != nil { + return err + } + typeAction, err = tx.TypeActionSwitcher.GetTransactionType(innerTX) + if err != nil { + return err + } + err = typeAction.ApplyUnconfirmed() + if err != nil { + return err + } + } + return tx.AccountBalanceHelper.AddAccountSpendableBalance(tx.SenderAddress, -tx.Fee) +} + +func (tx *AtomicTransaction) UndoApplyUnconfirmed() (err error) { + + for _, unsignedTX := range tx.Body.GetUnsignedTransactionBytes() { + var ( + innerTX *model.Transaction + typeAction TypeAction + ) + + innerTX, err = tx.TransactionUtil.ParseTransactionBytes(unsignedTX, false) + if err != nil { + return err + } + typeAction, err = tx.TypeActionSwitcher.GetTransactionType(innerTX) + if err != nil { + return err + } + err = typeAction.UndoApplyUnconfirmed() + if err != nil { + return err + } + } + return tx.AccountBalanceHelper.AddAccountSpendableBalance(tx.SenderAddress, tx.Fee) +} + +func (tx *AtomicTransaction) Validate(dbTx bool) (err error) { + + if len(tx.Body.GetUnsignedTransactionBytes()) == 0 { + return blocker.NewBlocker(blocker.ValidationErr, "EmptyAtomicInnerTransaction") + } + if len(tx.Body.GetSignatures()) == 0 { + return blocker.NewBlocker(blocker.ValidationErr, "EmptySignatures") + } + + enough, e := tx.AccountBalanceHelper.HasEnoughSpendableBalance(dbTx, tx.SenderAddress, tx.Fee) + if e != nil { + if e != sql.ErrNoRows { + return err + } + return blocker.NewBlocker(blocker.ValidationErr, "AccountBalanceNotFound") + } + + if !enough { + return blocker.NewBlocker( + blocker.ValidationErr, + "UserBalanceNotEnough", + ) + } + + var unsignedHash []byte + for _, unsignedTX := range tx.Body.GetUnsignedTransactionBytes() { + var ( + innerTX *model.Transaction + typeAction TypeAction + ) + innerTX, err = tx.TransactionUtil.ParseTransactionBytes(unsignedTX, false) + if err != nil { + return err + } + typeAction, err = tx.TypeActionSwitcher.GetTransactionType(innerTX) + if err != nil { + return err + } + err = typeAction.Validate(dbTx) + if err != nil { + return err + } + hashed := sha3.Sum256(unsignedTX) + unsignedHash = append(unsignedHash, hashed[:]...) + } + for accountAddressHex, signature := range tx.Body.GetSignatures() { + var accountAddress []byte + accountAddress, err = hex.DecodeString(accountAddressHex) + if err != nil { + return err + } + err = tx.Signature.VerifySignature(unsignedHash, signature, accountAddress) + if err != nil { + return err + } + } + + return nil +} + +func (tx *AtomicTransaction) GetMinimumFee() (int64, error) { + if tx.Escrow != nil && tx.Escrow.GetApproverAddress() != nil && !bytes.Equal(tx.Escrow.GetApproverAddress(), []byte{}) { + return tx.EscrowFee.CalculateTxMinimumFee(tx.Body, tx.Escrow) + } + return tx.NormalFee.CalculateTxMinimumFee(tx.Body, tx.Escrow) +} + +func (tx *AtomicTransaction) GetAmount() int64 { + return 0 +} + +func (tx *AtomicTransaction) GetSize() (uint32, error) { + var size int + + size += len(tx.Body.GetUnsignedTransactionBytes()) + for _, unsignedTX := range tx.Body.GetUnsignedTransactionBytes() { + size += 4 // unsignedTX length + size += len(unsignedTX) + } + + for addressHex, signature := range tx.Body.GetSignatures() { + size += len(addressHex) + size += len(signature) + } + + return uint32(size), nil +} + +func (tx *AtomicTransaction) ParseBodyBytes(txBodyBytes []byte) (body model.TransactionBodyInterface, err error) { + var ( + buff = bytes.NewBuffer(txBodyBytes) + unsignedTXs = make([][]byte, 0) + signatures = make(map[string][]byte) + ) + + innerTXCount := util.ConvertBytesToUint32(buff.Next(4)) + if innerTXCount == 0 { + return body, errors.New("empty inner tx") + } + + for i := 0; i < int(innerTXCount); i++ { + var ( + unsignedTX []byte + ) + + unsignedTXLength := util.ConvertBytesToUint32(buff.Next(4)) + unsignedTX, err = util.ReadTransactionBytes(buff, int(unsignedTXLength)) + if err != nil { + return body, err + } + unsignedTXs = append(unsignedTXs, unsignedTX) + } + + signatureCount := util.ConvertBytesToUint32(buff.Next(4)) + if signatureCount == 0 { + return body, errors.New("empty signature") + } + for i := 0; i < int(signatureCount); i++ { + var ( + signature []byte + accType accounttype.AccountTypeInterface + accountAddress []byte + ) + accType, err = accounttype.ParseBytesToAccountType(buff) + if err != nil { + return body, err + } + signature, err = util.ReadTransactionBytes(buff, int(accType.GetSignatureLength())) + if err != nil { + return body, err + } + accountAddress, err = accType.GetAccountAddress() + if err != nil { + return body, err + } + signatures[hex.EncodeToString(accountAddress)] = signature + } + + body = &model.AtomicTransactionBody{ + UnsignedTransactionBytes: unsignedTXs, + Signatures: signatures, + } + return body, nil +} + +func (tx *AtomicTransaction) GetBodyBytes() (bodyBytes []byte, err error) { + var ( + buff = bytes.NewBuffer([]byte{}) + ) + + buff.Write(util.ConvertUint32ToBytes(uint32(len(tx.Body.GetUnsignedTransactionBytes())))) // total unsigned inner transactions + for _, unsignedTX := range tx.Body.GetUnsignedTransactionBytes() { + buff.Write(util.ConvertUint32ToBytes(uint32(len(unsignedTX)))) + buff.Write(unsignedTX) + } + buff.Write(util.ConvertUint32ToBytes(uint32(len(tx.Body.GetSignatures())))) // total signatures + for addressHex, signature := range tx.Body.GetSignatures() { + var addressBytes []byte + addressBytes, err = hex.DecodeString(addressHex) + if err != nil { + return bodyBytes, err + } + buff.Write(addressBytes) + buff.Write(signature) + } + + return buff.Bytes(), nil +} + +func (tx *AtomicTransaction) GetTransactionBody(transaction *model.Transaction) { + transaction.TransactionBody = &model.Transaction_AtomicTransactionBody{ + AtomicTransactionBody: tx.Body, + } +} + +func (tx *AtomicTransaction) SkipMempoolTransaction( + selectedTransactions []*model.Transaction, + blockTimestamp int64, + blockHeight uint32, +) (bool, error) { + return false, nil +} + +func (tx *AtomicTransaction) Escrowable() (EscrowTypeAction, bool) { + if tx.Escrow.GetApproverAddress() != nil && !bytes.Equal(tx.Escrow.GetApproverAddress(), []byte{}) { + tx.Escrow = &model.Escrow{ + ID: tx.ID, + SenderAddress: tx.SenderAddress, + ApproverAddress: tx.Escrow.GetApproverAddress(), + Commission: tx.Escrow.GetCommission(), + Timeout: tx.Escrow.GetTimeout(), + Status: tx.Escrow.GetStatus(), + BlockHeight: tx.Height, + Latest: true, + Instruction: tx.Escrow.GetInstruction(), + } + return EscrowTypeAction(tx), true + } + return nil, false +} + +func (tx *AtomicTransaction) EscrowApplyConfirmed(blockTimestamp int64) error { + var ( + err error + ) + + err = tx.AccountBalanceHelper.AddAccountBalance( + tx.SenderAddress, + -(tx.Fee + tx.Escrow.GetCommission()), + model.EventType_EventEscrowedTransaction, + tx.Height, + tx.ID, + uint64(blockTimestamp), + ) + if err != nil { + return err + } + addEscrowQ := tx.EscrowQuery.InsertEscrowTransaction(tx.Escrow) + err = tx.QueryExecutor.ExecuteTransactions(addEscrowQ) + if err != nil { + return err + } + return nil +} + +func (tx *AtomicTransaction) EscrowApplyUnconfirmed() error { + return tx.AccountBalanceHelper.AddAccountSpendableBalance(tx.SenderAddress, -(tx.Fee + tx.Escrow.GetCommission())) +} + +func (tx *AtomicTransaction) EscrowUndoApplyUnconfirmed() error { + return tx.AccountBalanceHelper.AddAccountSpendableBalance(tx.SenderAddress, tx.Fee+tx.Escrow.GetCommission()) +} + +func (tx *AtomicTransaction) EscrowValidate(dbTx bool) error { + var ( + err error + enough bool + ) + if tx.Escrow.GetCommission() <= 0 { + return blocker.NewBlocker(blocker.ValidationErr, "CommissionNotEnough") + } + if tx.Escrow.GetApproverAddress() == nil || bytes.Equal(tx.Escrow.GetApproverAddress(), []byte{}) { + return blocker.NewBlocker(blocker.ValidationErr, "ApproverAddressRequired") + } + if tx.Escrow.GetRecipientAddress() == nil || bytes.Equal(tx.Escrow.GetRecipientAddress(), []byte{}) { + return blocker.NewBlocker(blocker.ValidationErr, "RecipientAddressRequired") + } + if tx.Escrow.GetTimeout() > uint64(constant.MinRollbackBlocks) { + return blocker.NewBlocker(blocker.ValidationErr, "TimeoutLimitExceeded") + } + + err = tx.Validate(dbTx) + if err != nil { + return err + } + enough, err = tx.AccountBalanceHelper.HasEnoughSpendableBalance(dbTx, tx.SenderAddress, tx.Fee+tx.Escrow.GetCommission()) + if err != nil { + if err != sql.ErrNoRows { + return err + } + return blocker.NewBlocker(blocker.ValidationErr, "AccountBalanceNotFound") + } + if !enough { + return blocker.NewBlocker(blocker.ValidationErr, "AccountBalanceNotEnough") + } + return nil +} + +func (tx *AtomicTransaction) EscrowApproval(blockTimestamp int64, txBody *model.ApprovalEscrowTransactionBody) (err error) { + + switch txBody.GetApproval() { + case model.EscrowApproval_Approve: + tx.Escrow.Status = model.EscrowStatus_Approved + err = tx.AccountBalanceHelper.AddAccountBalance( + tx.SenderAddress, + tx.Fee, + model.EventType_EventEscrowedTransaction, + tx.Height, + tx.ID, + uint64(blockTimestamp), + ) + if err != nil { + return err + } + err = tx.ApplyConfirmed(blockTimestamp) + if err != nil { + return err + } + err = tx.AccountBalanceHelper.AddAccountBalance( + tx.Escrow.GetApproverAddress(), + tx.Escrow.GetCommission(), + model.EventType_EventApprovalEscrowTransaction, + tx.Height, + tx.ID, + uint64(blockTimestamp), + ) + if err != nil { + return err + } + case model.EscrowApproval_Reject: + tx.Escrow.Status = model.EscrowStatus_Rejected + err = tx.AccountBalanceHelper.AddAccountBalance( + tx.Escrow.GetApproverAddress(), + tx.Escrow.GetCommission(), + model.EventType_EventApprovalEscrowTransaction, + tx.Height, + tx.ID, + uint64(blockTimestamp), + ) + if err != nil { + return err + } + default: + tx.Escrow.Status = model.EscrowStatus_Expired + err = tx.AccountBalanceHelper.AddAccountBalance( + tx.SenderAddress, + tx.Escrow.GetCommission(), + model.EventType_EventApprovalEscrowTransaction, + tx.Height, + tx.ID, + uint64(blockTimestamp), + ) + if err != nil { + return err + } + } + addEscrowQ := tx.EscrowQuery.InsertEscrowTransaction(tx.Escrow) + err = tx.QueryExecutor.ExecuteTransactions(addEscrowQ) + if err != nil { + return err + } + return nil +} diff --git a/common/transaction/atomicTransaction_test.go b/common/transaction/atomicTransaction_test.go new file mode 100644 index 000000000..b10970469 --- /dev/null +++ b/common/transaction/atomicTransaction_test.go @@ -0,0 +1,259 @@ +package transaction + +import ( + "database/sql" + "errors" + "testing" + + "github.com/zoobc/zoobc-core/common/chaintype" + "github.com/zoobc/zoobc-core/common/crypto" + "github.com/zoobc/zoobc-core/common/fee" + "github.com/zoobc/zoobc-core/common/model" + "github.com/zoobc/zoobc-core/common/query" +) + +// Atomic TX +var _, innerTX = GetFixtureForSpecificTransaction( + 0, 123456789, + senderAddress1, nil, + 8, model.TransactionType_SendMoneyTransaction, + &model.SendMoneyTransactionBody{ + Amount: 10, + }, + false, false, +) +var atomicBody, _ = GetFixtureForAtomicTransaction( + map[string][][]byte{ + senderAddress1PassPhrase: { + innerTX, + }, + }, +) + +type ( + mockTypeActionAtomicTransaction struct { + TypeAction + WantErr bool + } +) + +func (m *mockTypeActionAtomicTransaction) ApplyConfirmed(int64) error { + if m.WantErr { + return errors.New("just want to") + } + return nil +} +func (m *mockTypeActionAtomicTransaction) Validate(bool) error { + if m.WantErr { + return errors.New("just want to") + } + return nil +} + +type ( + mockTypeActionSwitcherAtomicTransaction struct { + WantErr bool + TypeActionSwitcher + } +) + +func (m *mockTypeActionSwitcherAtomicTransaction) GetTransactionType(*model.Transaction) (TypeAction, error) { + return &mockTypeActionAtomicTransaction{ + WantErr: m.WantErr, + }, nil +} + +type ( + mockQueryExecutorAtomicTransactionApplyConfirmed struct { + query.Executor + WantErr bool + } +) + +func (m *mockQueryExecutorAtomicTransactionApplyConfirmed) ExecuteTransactions([][]interface{}) error { + if m.WantErr { + return sql.ErrConnDone + } + return nil +} +func TestAtomicTransaction_ApplyConfirmed(t *testing.T) { + type fields struct { + ID int64 + Fee int64 + SenderAddress []byte + Height uint32 + Body *model.AtomicTransactionBody + AtomicTransactionQuery query.AtomicTransactionQueryInterface + Escrow *model.Escrow + EscrowQuery query.EscrowTransactionQueryInterface + QueryExecutor query.ExecutorInterface + TransactionQuery query.TransactionQueryInterface + TypeActionSwitcher TypeActionSwitcher + AccountBalanceHelper AccountBalanceHelperInterface + EscrowFee fee.FeeModelInterface + NormalFee fee.FeeModelInterface + TransactionUtil UtilInterface + Signature crypto.SignatureInterface + } + type args struct { + blockTimestamp int64 + } + tests := []struct { + name string + fields fields + args args + wantErr bool + }{ + { + name: "WantErr:AddAccountBalance", + fields: fields{ + AccountBalanceHelper: &mockAccountBalanceHelperFail{}, + }, + wantErr: true, + }, + { + name: "WantErr:ApplyingInnerFail", + fields: fields{ + AccountBalanceHelper: &mockAccountBalanceHelperSuccess{}, + Body: atomicBody, + TransactionUtil: &Util{}, + TypeActionSwitcher: &mockTypeActionSwitcherAtomicTransaction{WantErr: true}, + }, + wantErr: true, + }, + { + name: "WantErr:ExecuteTransactionFail", + fields: fields{ + AccountBalanceHelper: &mockAccountBalanceHelperSuccess{}, + Body: atomicBody, + TransactionUtil: &Util{}, + TypeActionSwitcher: &mockTypeActionSwitcherAtomicTransaction{}, + QueryExecutor: &mockQueryExecutorAtomicTransactionApplyConfirmed{WantErr: true}, + TransactionQuery: query.NewTransactionQuery(&chaintype.MainChain{}), + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), + }, + wantErr: true, + }, + { + name: "WantSuccess", + fields: fields{ + AccountBalanceHelper: &mockAccountBalanceHelperSuccess{}, + Body: atomicBody, + TransactionUtil: &Util{}, + TypeActionSwitcher: &mockTypeActionSwitcherAtomicTransaction{}, + QueryExecutor: &mockQueryExecutorAtomicTransactionApplyConfirmed{}, + TransactionQuery: query.NewTransactionQuery(&chaintype.MainChain{}), + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), + }, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + tx := &AtomicTransaction{ + ID: tt.fields.ID, + Fee: tt.fields.Fee, + SenderAddress: tt.fields.SenderAddress, + Height: tt.fields.Height, + Body: tt.fields.Body, + AtomicTransactionQuery: tt.fields.AtomicTransactionQuery, + Escrow: tt.fields.Escrow, + EscrowQuery: tt.fields.EscrowQuery, + QueryExecutor: tt.fields.QueryExecutor, + TransactionQuery: tt.fields.TransactionQuery, + TypeActionSwitcher: tt.fields.TypeActionSwitcher, + AccountBalanceHelper: tt.fields.AccountBalanceHelper, + EscrowFee: tt.fields.EscrowFee, + NormalFee: tt.fields.NormalFee, + TransactionUtil: tt.fields.TransactionUtil, + Signature: tt.fields.Signature, + } + if err := tx.ApplyConfirmed(tt.args.blockTimestamp); (err != nil) != tt.wantErr { + t.Errorf("ApplyConfirmed() error = %v, wantErr %v", err, tt.wantErr) + } + }) + } +} + +func TestAtomicTransaction_Validate(t *testing.T) { + type fields struct { + ID int64 + Fee int64 + SenderAddress []byte + Height uint32 + Body *model.AtomicTransactionBody + AtomicTransactionQuery query.AtomicTransactionQueryInterface + Escrow *model.Escrow + EscrowQuery query.EscrowTransactionQueryInterface + QueryExecutor query.ExecutorInterface + TransactionQuery query.TransactionQueryInterface + TypeActionSwitcher TypeActionSwitcher + AccountBalanceHelper AccountBalanceHelperInterface + EscrowFee fee.FeeModelInterface + NormalFee fee.FeeModelInterface + TransactionUtil UtilInterface + Signature crypto.SignatureInterface + } + type args struct { + dbTx bool + } + tests := []struct { + name string + fields fields + args args + wantErr bool + }{ + { + name: "WantErr:EmptyAtomicInnerTransaction", + fields: fields{ + Body: &model.AtomicTransactionBody{}, + }, + wantErr: true, + }, + { + name: "WantErr:InnerValidateFail", + fields: fields{ + Body: atomicBody, + AccountBalanceHelper: &mockAccountBalanceHelperSuccess{}, + TypeActionSwitcher: &mockTypeActionSwitcherAtomicTransaction{WantErr: true}, + TransactionUtil: &Util{}, + }, + wantErr: true, + }, + { + name: "WantSuccess", + fields: fields{ + Body: atomicBody, + AccountBalanceHelper: &mockAccountBalanceHelperSuccess{}, + TypeActionSwitcher: &mockTypeActionSwitcherAtomicTransaction{}, + TransactionUtil: &Util{}, + Signature: crypto.NewSignature(), + }, + wantErr: true, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + tx := &AtomicTransaction{ + ID: tt.fields.ID, + Fee: tt.fields.Fee, + SenderAddress: tt.fields.SenderAddress, + Height: tt.fields.Height, + Body: tt.fields.Body, + AtomicTransactionQuery: tt.fields.AtomicTransactionQuery, + Escrow: tt.fields.Escrow, + EscrowQuery: tt.fields.EscrowQuery, + QueryExecutor: tt.fields.QueryExecutor, + TransactionQuery: tt.fields.TransactionQuery, + TypeActionSwitcher: tt.fields.TypeActionSwitcher, + AccountBalanceHelper: tt.fields.AccountBalanceHelper, + EscrowFee: tt.fields.EscrowFee, + NormalFee: tt.fields.NormalFee, + TransactionUtil: tt.fields.TransactionUtil, + Signature: tt.fields.Signature, + } + if err := tx.Validate(tt.args.dbTx); (err != nil) != tt.wantErr { + t.Errorf("Validate() error = %v, wantErr %v", err, tt.wantErr) + } + }) + } +} diff --git a/common/transaction/fixtureGenerator.go b/common/transaction/fixtureGenerator.go index c39e1215b..a5a99a0a5 100644 --- a/common/transaction/fixtureGenerator.go +++ b/common/transaction/fixtureGenerator.go @@ -50,10 +50,15 @@ package transaction import ( + "encoding/hex" + + "github.com/zoobc/zoobc-core/common/accounttype" + "github.com/zoobc/zoobc-core/common/chaintype" "github.com/zoobc/zoobc-core/common/crypto" "github.com/zoobc/zoobc-core/common/model" "github.com/zoobc/zoobc-core/common/query" + "github.com/zoobc/zoobc-core/common/signaturetype" "github.com/zoobc/zoobc-core/common/util" "golang.org/x/crypto/sha3" ) @@ -100,33 +105,6 @@ var ( TotalCoinBase: 1, Version: 0, } - TransactionWithEscrow = &model.Transaction{ - ID: 670925173877174625, - Version: 1, - TransactionType: 2, - BlockID: 0, - Height: 0, - Timestamp: 1562806389280, - SenderAccountAddress: senderAddress1, - RecipientAccountAddress: recipientAddress1, - Fee: 1, - TransactionHash: []byte{ - 59, 106, 191, 6, 145, 54, 181, 186, 75, 93, 234, 139, 131, 96, 153, 252, 40, 245, 235, 132, - 187, 45, 245, 113, 210, 87, 23, 67, 157, 117, 41, 143, - }, - TransactionBodyLength: 8, - TransactionBodyBytes: []byte{1, 2, 3, 4, 5, 6, 7, 8}, - Signature: []byte{ - 0, 0, 0, 0, 4, 38, 103, 73, 250, 169, 63, 155, 106, 21, 9, 76, 77, 137, 3, 120, 21, 69, 90, 118, 242, 84, 174, - 239, 46, 190, 78, 68, 90, 83, 142, 11, 4, 38, 68, 24, 230, 247, 88, 220, 119, 124, 51, 149, 127, 214, 82, 224, 72, 239, 56, - 139, 255, 81, 229, 184, 77, 80, 80, 39, 254, 173, 28, 169, - }, - Escrow: &model.Escrow{ - ApproverAddress: make([]byte, 36), // STEF TODO: update it with a real address (in bytes), - Commission: 1, - Timeout: 100, - }, - } ) func GetFixturesForNoderegistration(nodeRegistrationQuery query.NodeRegistrationQueryInterface) ( @@ -433,7 +411,11 @@ func GetFixtureForSpecificTransaction( hashed := sha3.Sum256(transactionBytes) tx.TransactionHash = hashed[:] + } else { + hashed := sha3.Sum256(transactionBytes) + tx.TransactionHash = hashed[:] } + tx.TransactionBody = nil return tx, transactionBytes } @@ -499,3 +481,49 @@ func GetFixtureForFeeVoteRevealTransaction( return tx.Body } + +func GetFixtureForAtomicTransaction( + unsignedBytes map[string][][]byte, +) (body *model.AtomicTransactionBody, txBodyBytes []byte) { + + var ( + uBytes = make([][]byte, 0) + signatures = make(map[string][]byte) + ) + for seed, txsBytes := range unsignedBytes { + for _, txBytes := range txsBytes { + var ( + accType accounttype.AccountTypeInterface + address []byte + err error + ) + + uBytes = append(uBytes, txBytes) + signature, _ := (&crypto.Signature{}).Sign( + txBytes, + model.AccountType_ZbcAccountType, + seed, + ) + privateKey, _ := signaturetype.NewEd25519Signature().GetPrivateKeyFromSeedUseSlip10(seed) + pubKey, _ := signaturetype.NewEd25519Signature().GetPublicKeyFromPrivateKeyUseSlip10(privateKey) + accType, err = accounttype.NewAccountType((&accounttype.ZbcAccountType{}).GetTypeInt(), pubKey) + if err != nil { + panic(err) + } + address, err = accType.GetAccountAddress() + if err != nil { + panic(err) + } + signatures[hex.EncodeToString(address)] = signature + } + } + + tx := &AtomicTransaction{ + Body: &model.AtomicTransactionBody{ + UnsignedTransactionBytes: uBytes, + Signatures: signatures, + }, + } + txBodyBytes, _ = tx.GetBodyBytes() + return tx.Body, txBodyBytes +} diff --git a/common/transaction/multiSignature.go b/common/transaction/multiSignature.go index d4b0bd1da..958896667 100644 --- a/common/transaction/multiSignature.go +++ b/common/transaction/multiSignature.go @@ -502,7 +502,7 @@ func (tx *MultiSignatureTransaction) ApplyConfirmed(blockTimestamp int64) error } // save multisig_child transaction - utx.MultisigChild = true + utx.ChildType = model.TransactionChildType_MultiSignatureChild utx.BlockID = tx.BlockID err = tx.TransactionHelper.InsertTransaction(utx) if err != nil { diff --git a/common/transaction/transaction.go b/common/transaction/transaction.go index f52a65085..ce2abc625 100644 --- a/common/transaction/transaction.go +++ b/common/transaction/transaction.go @@ -510,6 +510,33 @@ func (ts *TypeSwitcher) GetTransactionType(tx *model.Transaction) (TypeAction, e default: return nil, nil } + case 8: + transactionBody, err = (&AtomicTransaction{ + TransactionUtil: transactionUtil, + }).ParseBodyBytes(tx.GetTransactionBodyBytes()) + if err != nil { + return nil, err + } + return &AtomicTransaction{ + ID: tx.GetID(), + Fee: tx.GetFee(), + SenderAddress: tx.GetSenderAccountAddress(), + Height: tx.GetHeight(), + Body: transactionBody.(*model.AtomicTransactionBody), + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), + Escrow: tx.GetEscrow(), + EscrowQuery: query.NewEscrowTransactionQuery(), + QueryExecutor: ts.Executor, + TransactionQuery: query.NewTransactionQuery(&chaintype.MainChain{}), + TypeActionSwitcher: ts, + AccountBalanceHelper: accountBalanceHelper, + EscrowFee: fee.NewBlockLifeTimeFeeModel( + 10, fee.SendMoneyFeeConstant, + ), + NormalFee: fee.NewConstantFeeModel(fee.SendMoneyFeeConstant), + TransactionUtil: transactionUtil, + Signature: crypto.NewSignature(), + }, nil default: return nil, blocker.NewBlocker(blocker.ValidationErr, fmt.Sprintf("transaction type is not valid: %v", buf[0])) } diff --git a/common/transaction/transactionGeneral.go b/common/transaction/transactionGeneral.go index 02b6d5c2f..782f41c02 100644 --- a/common/transaction/transactionGeneral.go +++ b/common/transaction/transactionGeneral.go @@ -205,12 +205,19 @@ func (u *Util) ParseTransactionBytes(transactionBytes []byte, sign bool) (*model if err != nil { return &transaction, err } - err = u.MempoolCacheStorage.GetItem(txID, &mempoolObject) - if err != nil { - return nil, err - } - if mempoolObject.Tx.TransactionHash != nil { - return &mempoolObject.Tx, nil + + /* + Need to check the MempoolCacheStorage is nil, it would nil when call from cmd. + That because no necessary to check from mempool cache + */ + if u.MempoolCacheStorage != nil { + err = u.MempoolCacheStorage.GetItem(txID, &mempoolObject) + if err != nil { + return nil, err + } + if mempoolObject.Tx.TransactionHash != nil { + return &mempoolObject.Tx, nil + } } buffer = bytes.NewBuffer(transactionBytes) diff --git a/common/transaction/transaction_test.go b/common/transaction/transaction_test.go index 9bd078a43..fa1cd1e87 100644 --- a/common/transaction/transaction_test.go +++ b/common/transaction/transaction_test.go @@ -52,13 +52,13 @@ package transaction import ( "crypto/sha256" "encoding/binary" - "github.com/zoobc/zoobc-core/common/crypto" "reflect" "testing" "github.com/zoobc/zoobc-core/common/auth" "github.com/zoobc/zoobc-core/common/chaintype" "github.com/zoobc/zoobc-core/common/constant" + "github.com/zoobc/zoobc-core/common/crypto" "github.com/zoobc/zoobc-core/common/fee" "github.com/zoobc/zoobc-core/common/model" "github.com/zoobc/zoobc-core/common/query" @@ -101,6 +101,28 @@ func TestTypeSwitcher_GetTransactionType(t *testing.T) { } txActiveNodeRegistryCache := fixtureTransactionalCache(&mockNodeRegistryCacheSuccess{}) txPendingNodeRegistryCache := fixtureTransactionalCache(&mockNodeRegistryCacheSuccess{}) + + txBodyBytes1, _ := (&FeeVoteRevealTransaction{ + Body: feeVoteRevealBody, + }).GetBodyBytes() + + // Atomic TX + _, innerTX := GetFixtureForSpecificTransaction( + 0, 123456789, + senderAddress1, nil, + 8, model.TransactionType_SendMoneyTransaction, + &model.SendMoneyTransactionBody{ + Amount: 10, + }, + false, false, + ) + atomicBody, atomicBodyBytes := GetFixtureForAtomicTransaction( + map[string][][]byte{ + senderAddress1PassPhrase: { + innerTX, + }, + }, + ) type fields struct { Executor query.ExecutorInterface NodeAuthValidation auth.NodeAuthValidationInterface @@ -114,10 +136,6 @@ func TestTypeSwitcher_GetTransactionType(t *testing.T) { tx *model.Transaction } - txBodyBytes1, _ := (&FeeVoteRevealTransaction{ - Body: feeVoteRevealBody, - }).GetBodyBytes() - tests := []struct { name string fields fields @@ -603,6 +621,41 @@ func TestTypeSwitcher_GetTransactionType(t *testing.T) { EscrowQuery: query.NewEscrowTransactionQuery(), }, }, + { + name: "Want:AtomicTransaction", + fields: fields{ + Executor: &query.Executor{}, + }, + args: args{ + tx: &model.Transaction{ + Height: 5, + SenderAccountAddress: senderAddress1, + TransactionBody: atomicBody, + TransactionType: binary.LittleEndian.Uint32([]byte{8, 0, 0, 0}), + TransactionBodyBytes: atomicBodyBytes, + }, + }, + want: &AtomicTransaction{ + ID: 0, + SenderAddress: senderAddress1, + Body: atomicBody, + Height: 5, + QueryExecutor: &query.Executor{}, + AccountBalanceHelper: accountBalanceHelper, + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), + TransactionQuery: query.NewTransactionQuery(&chaintype.MainChain{}), + TypeActionSwitcher: &TypeSwitcher{ + Executor: &query.Executor{}, + }, + EscrowFee: fee.NewBlockLifeTimeFeeModel( + 10, fee.SendMoneyFeeConstant, + ), + NormalFee: fee.NewConstantFeeModel(fee.SendMoneyFeeConstant), + EscrowQuery: query.NewEscrowTransactionQuery(), + Signature: crypto.NewSignature(), + TransactionUtil: &Util{}, + }, + }, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { diff --git a/core/service/snapshotMainBlockService.go b/core/service/snapshotMainBlockService.go index 7b0c75aa1..4b45c3bb1 100644 --- a/core/service/snapshotMainBlockService.go +++ b/core/service/snapshotMainBlockService.go @@ -89,6 +89,7 @@ type ( FeeVoteRevealVoteQuery query.FeeVoteRevealVoteQueryInterface LiquidPaymentTransactionQuery query.LiquidPaymentTransactionQueryInterface NodeAdmissionTimestampQuery query.NodeAdmissionTimestampQueryInterface + AtomicTransactionQuery query.AtomicTransactionQueryInterface SnapshotQueries map[string]query.SnapshotQuery BlocksmithSafeQuery map[string]bool DerivedQueries []query.DerivedQuery @@ -119,6 +120,7 @@ func NewSnapshotMainBlockService( feeVoteRevealVoteQuery query.FeeVoteRevealVoteQueryInterface, liquidPaymentTransactionQuery query.LiquidPaymentTransactionQueryInterface, nodeAdmissionTimestampQuery query.NodeAdmissionTimestampQueryInterface, + atomicTransaction query.AtomicTransactionQueryInterface, blockQuery query.BlockQueryInterface, snapshotQueries map[string]query.SnapshotQuery, blocksmithSafeQueries map[string]bool, @@ -160,6 +162,7 @@ func NewSnapshotMainBlockService( BlockMainService: blockMainService, NodeRegistrationService: nodeRegistrationService, ScrambleNodeService: scrambleNodeService, + AtomicTransactionQuery: atomicTransaction, } } @@ -258,6 +261,8 @@ func (ss *SnapshotMainBlockService) NewSnapshotFile(block *model.Block) (snapsho snapshotPayload.LiquidPayment, err = ss.LiquidPaymentTransactionQuery.BuildModels(rows) case "nodeAdmissionTimestamp": snapshotPayload.NodeAdmissionTimestamp, err = ss.NodeAdmissionTimestampQuery.BuildModel([]*model.NodeAdmissionTimestamp{}, rows) + case "atomicTransaction": + snapshotPayload.AtomicTransaction, err = ss.AtomicTransactionQuery.BuildModel([]*model.Atomic{}, rows) default: err = blocker.NewBlocker(blocker.ParserErr, fmt.Sprintf("Invalid Snapshot Query Repository: %s", qryRepoName)) } @@ -509,6 +514,14 @@ func (ss *SnapshotMainBlockService) InsertSnapshotPayloadToDB(payload *model.Sna } queries = append(queries, q...) } + case "atomicTransaction": + if len(payload.GetAtomicTransaction()) > 0 { + q, err := snapshotQuery.ImportSnapshot(payload.GetAtomicTransaction()) + if err != nil { + return err + } + queries = append(queries, q...) + } default: return blocker.NewBlocker(blocker.ParserErr, fmt.Sprintf("Invalid Snapshot Query Repository: %s", qryRepoName)) } diff --git a/core/service/snapshotMainBlockService_test.go b/core/service/snapshotMainBlockService_test.go index 7eabc54e2..510221c45 100644 --- a/core/service/snapshotMainBlockService_test.go +++ b/core/service/snapshotMainBlockService_test.go @@ -629,6 +629,7 @@ func TestSnapshotMainBlockService_NewSnapshotFile(t *testing.T) { FeeVoteRevealVoteQuery query.FeeVoteRevealVoteQueryInterface LiquidPaymentTransactionQuery query.LiquidPaymentTransactionQueryInterface NodeAdmissionTimestampQuery query.NodeAdmissionTimestampQueryInterface + AtomicTransaction query.AtomicTransactionQueryInterface BlockQuery query.BlockQueryInterface SnapshotQueries map[string]query.SnapshotQuery BlocksmithSafeQuery map[string]bool @@ -677,6 +678,7 @@ func TestSnapshotMainBlockService_NewSnapshotFile(t *testing.T) { SnapshotQueries: query.GetSnapshotQuery(chaintype.GetChainType(0)), BlocksmithSafeQuery: query.GetBlocksmithSafeQuery(chaintype.GetChainType(0)), DerivedQueries: query.GetDerivedQuery(chaintype.GetChainType(0)), + AtomicTransaction: query.NewAtomicTransactionQuery(), }, args: args{ block: blockForSnapshot1, @@ -722,6 +724,7 @@ func TestSnapshotMainBlockService_NewSnapshotFile(t *testing.T) { LiquidPaymentTransactionQuery: tt.fields.LiquidPaymentTransactionQuery, NodeAdmissionTimestampQuery: tt.fields.NodeAdmissionTimestampQuery, DerivedQueries: tt.fields.DerivedQueries, + AtomicTransactionQuery: tt.fields.AtomicTransaction, } got, err := ss.NewSnapshotFile(tt.args.block) if err != nil { @@ -768,6 +771,7 @@ func TestSnapshotMainBlockService_Integration_NewSnapshotFile(t *testing.T) { LiquidPaymentTransactionQuery query.LiquidPaymentTransactionQueryInterface BlockQuery query.BlockQueryInterface NodeAdmissionTimestampQuery query.NodeAdmissionTimestampQueryInterface + AtomicTransactionQuery query.AtomicTransactionQueryInterface SnapshotQueries map[string]query.SnapshotQuery BlocksmithSafeQuery map[string]bool DerivedQueries []query.DerivedQuery @@ -817,6 +821,7 @@ func TestSnapshotMainBlockService_Integration_NewSnapshotFile(t *testing.T) { SnapshotQueries: query.GetSnapshotQuery(chaintype.GetChainType(0)), DerivedQueries: query.GetDerivedQuery(chaintype.GetChainType(0)), BlocksmithSafeQuery: query.GetBlocksmithSafeQuery(chaintype.GetChainType(0)), + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), }, args: args{ block: blockForSnapshot1, @@ -859,6 +864,7 @@ func TestSnapshotMainBlockService_Integration_NewSnapshotFile(t *testing.T) { SnapshotQueries: query.GetSnapshotQuery(chaintype.GetChainType(0)), DerivedQueries: query.GetDerivedQuery(chaintype.GetChainType(0)), BlocksmithSafeQuery: query.GetBlocksmithSafeQuery(chaintype.GetChainType(0)), + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), }, args: args{ block: blockForSnapshot1, @@ -893,6 +899,7 @@ func TestSnapshotMainBlockService_Integration_NewSnapshotFile(t *testing.T) { FeeVoteRevealVoteQuery: tt.fields.FeeVoteRevealVoteQuery, LiquidPaymentTransactionQuery: tt.fields.LiquidPaymentTransactionQuery, NodeAdmissionTimestampQuery: tt.fields.NodeAdmissionTimestampQuery, + AtomicTransactionQuery: tt.fields.AtomicTransactionQuery, } got, err := ss.NewSnapshotFile(tt.args.block) if err != nil { @@ -975,6 +982,7 @@ func TestSnapshotMainBlockService_ImportSnapshotFile(t *testing.T) { FeeVoteRevealVoteQuery query.FeeVoteRevealVoteQueryInterface LiquidPaymentTransactionQuery query.LiquidPaymentTransactionQueryInterface NodeAdmissionTimestampQuery query.NodeAdmissionTimestampQueryInterface + AtomicTransactionQuery query.AtomicTransactionQueryInterface BlockQuery query.BlockQueryInterface SnapshotQueries map[string]query.SnapshotQuery BlocksmithSafeQuery map[string]bool @@ -1030,6 +1038,7 @@ func TestSnapshotMainBlockService_ImportSnapshotFile(t *testing.T) { BlockMainService: &mockBlockMainServiceSuccess{}, NodeRegistrationService: &mockImportSnapshotFileNodeRegistrationServiceSuccess{}, ScrambleNodeService: &mockScrambleNodeServiceInitSuccess{}, + AtomicTransactionQuery: query.NewAtomicTransactionQuery(), }, }, } @@ -1066,6 +1075,7 @@ func TestSnapshotMainBlockService_ImportSnapshotFile(t *testing.T) { BlockMainService: tt.fields.BlockMainService, NodeRegistrationService: tt.fields.NodeRegistrationService, ScrambleNodeService: tt.fields.ScrambleNodeService, + AtomicTransactionQuery: tt.fields.AtomicTransactionQuery, } snapshotFileInfo, err := ss.NewSnapshotFile(blockForSnapshot1) if err != nil { diff --git a/core/service/transactionCoreService_test.go b/core/service/transactionCoreService_test.go index a51f17069..ee4c47d6e 100644 --- a/core/service/transactionCoreService_test.go +++ b/core/service/transactionCoreService_test.go @@ -192,7 +192,7 @@ func (*mockGetTransactionsByIdsExecutorSelectWithEscrowSuccess) ExecuteSelect(q mockedTX.GetSignature(), mockedTX.GetVersion(), mockedTX.GetTransactionIndex(), - mockedTX.GetMultisigChild(), + mockedTX.GetChildType(), mockedTX.GetMessage(), )) default: @@ -492,7 +492,7 @@ func (*mockQueryExecutorExpiringEscrowSuccess) ExecuteSelectRow(qStr string, _ b tx.GetSignature(), tx.GetVersion(), tx.GetTransactionIndex(), - tx.GetMultisigChild(), + tx.GetChildType(), tx.GetMessage(), ) mock.ExpectQuery(qStr).WillReturnRows(mockedRows) diff --git a/main.go b/main.go index 0806cd9ae..15a90e73c 100644 --- a/main.go +++ b/main.go @@ -640,6 +640,7 @@ func initiateMainInstance() { query.NewFeeVoteRevealVoteQuery(), query.NewLiquidPaymentTransactionQuery(), query.NewNodeAdmissionTimestampQuery(), + query.NewAtomicTransactionQuery(), query.NewBlockQuery(mainchain), query.GetSnapshotQuery(mainchain), query.GetBlocksmithSafeQuery(mainchain),