From fbb18778095638768bcc5e5829e07a530d5a8479 Mon Sep 17 00:00:00 2001 From: HuangYi Date: Thu, 15 Sep 2022 16:17:12 +0800 Subject: [PATCH 1/3] keep the balance query endpoint compatible with legacy blocks Closes: #13296 A temporary solution before the proxy tool developed, since the balance endpoint is too important. --- CHANGELOG.md | 1 + x/bank/keeper/grpc_query.go | 7 +++--- x/bank/keeper/view.go | 44 ++++++++++++++++++++++++++----------- 3 files changed, 36 insertions(+), 16 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 94b7073e8820..3a1d3ea8a5b4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -85,6 +85,7 @@ Ref: https://keepachangelog.com/en/1.0.0/ * [#13178](https://github.com/cosmos/cosmos-sdk/pull/13178) Add `cosmos.msg.v1.service` protobuf annotation to allow tooling to distinguish between Msg and Query services via reflection. * [#13233](https://github.com/cosmos/cosmos-sdk/pull/13233) Add `--append` to `add-genesis-account` sub-command to append new tokens after an account is already created. * [#13236](https://github.com/cosmos/cosmos-sdk/pull/13236) Integrate Filter Logging +* [#]() Keep the balance query endpoint compatible with legacy blocks ### State Machine Breaking diff --git a/x/bank/keeper/grpc_query.go b/x/bank/keeper/grpc_query.go index 3ea34a445212..60d0be75c630 100644 --- a/x/bank/keeper/grpc_query.go +++ b/x/bank/keeper/grpc_query.go @@ -62,11 +62,12 @@ func (k BaseKeeper) AllBalances(ctx context.Context, req *types.QueryAllBalances accountStore := k.getAccountStore(sdkCtx, addr) pageRes, err := query.Paginate(accountStore, req.Pagination, func(key, value []byte) error { - var amount math.Int - if err := amount.Unmarshal(value); err != nil { + denom := string(key) + balance, err := UnmarshalBalanceCompat(k.cdc, value, denom) + if err != nil { return err } - balances = append(balances, sdk.NewCoin(string(key), amount)) + balances = append(balances, balance) return nil }) if err != nil { diff --git a/x/bank/keeper/view.go b/x/bank/keeper/view.go index 32e146ecdd15..d438ee09ec40 100644 --- a/x/bank/keeper/view.go +++ b/x/bank/keeper/view.go @@ -4,6 +4,7 @@ import ( "fmt" "cosmossdk.io/math" + "github.com/tendermint/tendermint/libs/log" "github.com/cosmos/cosmos-sdk/codec" @@ -100,17 +101,13 @@ func (k BaseViewKeeper) GetAccountsBalances(ctx sdk.Context) []types.Balance { // by address. func (k BaseViewKeeper) GetBalance(ctx sdk.Context, addr sdk.AccAddress, denom string) sdk.Coin { accountStore := k.getAccountStore(ctx, addr) - amount := math.ZeroInt() bz := accountStore.Get([]byte(denom)) - if bz == nil { - return sdk.NewCoin(denom, amount) - } - - if err := amount.Unmarshal(bz); err != nil { + balance, err := UnmarshalBalanceCompat(k.cdc, bz, denom) + if err != nil { panic(err) } - return sdk.NewCoin(denom, amount) + return balance } // IterateAccountBalances iterates over the balances of a single account and @@ -123,12 +120,13 @@ func (k BaseViewKeeper) IterateAccountBalances(ctx sdk.Context, addr sdk.AccAddr defer iterator.Close() for ; iterator.Valid(); iterator.Next() { - var amount math.Int - if err := amount.Unmarshal(iterator.Value()); err != nil { + denom := string(iterator.Key()) + balance, err := UnmarshalBalanceCompat(k.cdc, iterator.Value(), denom) + if err != nil { panic(err) } - if cb(sdk.NewCoin(string(iterator.Key()), amount)) { + if cb(balance) { break } } @@ -153,12 +151,12 @@ func (k BaseViewKeeper) IterateAllBalances(ctx sdk.Context, cb func(sdk.AccAddre panic(err) } - var amount math.Int - if err := amount.Unmarshal(iterator.Value()); err != nil { + balance, err := UnmarshalBalanceCompat(k.cdc, iterator.Value(), denom) + if err != nil { panic(err) } - if cb(address, sdk.NewCoin(denom, amount)) { + if cb(address, balance) { break } } @@ -252,3 +250,23 @@ func (k BaseViewKeeper) getAccountStore(ctx sdk.Context, addr sdk.AccAddress) pr func (k BaseViewKeeper) getDenomAddressPrefixStore(ctx sdk.Context, denom string) prefix.Store { return prefix.NewStore(ctx.KVStore(k.storeKey), types.CreateDenomAddressPrefix(denom)) } + +// UnmarshalBalanceCompat unmarshal sdk.Coin from storage, it's backward-compatible with the legacy format. +func UnmarshalBalanceCompat(cdc codec.BinaryCodec, bz []byte, denom string) (sdk.Coin, error) { + amount := math.ZeroInt() + if bz == nil { + return sdk.NewCoin(denom, amount), nil + } + + if err := amount.Unmarshal(bz); err != nil { + // try to unmarshal with the legacy format. + var balance sdk.Coin + if cdc.Unmarshal(bz, &balance) != nil { + // return with the original error + return sdk.Coin{}, err + } + return balance, nil + } + + return sdk.NewCoin(denom, amount), nil +} From 0f50ac5424c9bf400c0b87fec2332738eea14eae Mon Sep 17 00:00:00 2001 From: yihuang Date: Thu, 15 Sep 2022 16:24:12 +0800 Subject: [PATCH 2/3] Update CHANGELOG.md --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 3a1d3ea8a5b4..bfe4cfa357fb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -85,7 +85,7 @@ Ref: https://keepachangelog.com/en/1.0.0/ * [#13178](https://github.com/cosmos/cosmos-sdk/pull/13178) Add `cosmos.msg.v1.service` protobuf annotation to allow tooling to distinguish between Msg and Query services via reflection. * [#13233](https://github.com/cosmos/cosmos-sdk/pull/13233) Add `--append` to `add-genesis-account` sub-command to append new tokens after an account is already created. * [#13236](https://github.com/cosmos/cosmos-sdk/pull/13236) Integrate Filter Logging -* [#]() Keep the balance query endpoint compatible with legacy blocks +* [#13301](https://github.com/cosmos/cosmos-sdk/pull/13301) Keep the balance query endpoint compatible with legacy blocks ### State Machine Breaking From 0a5ba80ec562b0ba48addca4436fa9d377f19fa3 Mon Sep 17 00:00:00 2001 From: yihuang Date: Thu, 15 Sep 2022 18:05:36 +0800 Subject: [PATCH 3/3] Apply suggestions from code review --- x/bank/keeper/view.go | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/x/bank/keeper/view.go b/x/bank/keeper/view.go index d438ee09ec40..865b6e1eda4e 100644 --- a/x/bank/keeper/view.go +++ b/x/bank/keeper/view.go @@ -4,7 +4,6 @@ import ( "fmt" "cosmossdk.io/math" - "github.com/tendermint/tendermint/libs/log" "github.com/cosmos/cosmos-sdk/codec" @@ -251,7 +250,7 @@ func (k BaseViewKeeper) getDenomAddressPrefixStore(ctx sdk.Context, denom string return prefix.NewStore(ctx.KVStore(k.storeKey), types.CreateDenomAddressPrefix(denom)) } -// UnmarshalBalanceCompat unmarshal sdk.Coin from storage, it's backward-compatible with the legacy format. +// UnmarshalBalanceCompat unmarshal balance amount from storage, it's backward-compatible with the legacy format. func UnmarshalBalanceCompat(cdc codec.BinaryCodec, bz []byte, denom string) (sdk.Coin, error) { amount := math.ZeroInt() if bz == nil {