Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[TRA-625] Add upgrade handler for migrating vault params. #2304

Merged
merged 10 commits into from
Sep 20, 2024
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { setPaginationParams } from "../../helpers";
import { LCDClient } from "@osmonauts/lcd";
import { QueryParamsRequest, QueryParamsResponseSDKType, QueryVaultRequest, QueryVaultResponseSDKType, QueryAllVaultsRequest, QueryAllVaultsResponseSDKType, QueryMegavaultTotalSharesRequest, QueryMegavaultTotalSharesResponseSDKType, QueryMegavaultOwnerSharesRequest, QueryMegavaultOwnerSharesResponseSDKType } from "./query";
import { QueryParamsRequest, QueryParamsResponseSDKType, QueryVaultRequest, QueryVaultResponseSDKType, QueryAllVaultsRequest, QueryAllVaultsResponseSDKType, QueryMegavaultTotalSharesRequest, QueryMegavaultTotalSharesResponseSDKType, QueryMegavaultOwnerSharesRequest, QueryMegavaultOwnerSharesResponseSDKType, QueryVaultParamsRequest, QueryVaultParamsResponseSDKType } from "./query";
export class LCDQueryClient {
req: LCDClient;

Expand All @@ -15,6 +15,7 @@ export class LCDQueryClient {
this.allVaults = this.allVaults.bind(this);
this.megavaultTotalShares = this.megavaultTotalShares.bind(this);
this.megavaultOwnerShares = this.megavaultOwnerShares.bind(this);
this.vaultParams = this.vaultParams.bind(this);
}
/* Queries the Params. */

Expand Down Expand Up @@ -71,5 +72,12 @@ export class LCDQueryClient {
const endpoint = `dydxprotocol/vault/megavault/owner_shares`;
return await this.req.get<QueryMegavaultOwnerSharesResponseSDKType>(endpoint, options);
}
/* Queries vault params of a vault. */


async vaultParams(params: QueryVaultParamsRequest): Promise<QueryVaultParamsResponseSDKType> {
const endpoint = `dydxprotocol/vault/params/${params.type}/${params.number}`;
return await this.req.get<QueryVaultParamsResponseSDKType>(endpoint);
}

}
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { Rpc } from "../../helpers";
import * as _m0 from "protobufjs/minimal";
import { QueryClient, createProtobufRpcClient } from "@cosmjs/stargate";
import { QueryParamsRequest, QueryParamsResponse, QueryVaultRequest, QueryVaultResponse, QueryAllVaultsRequest, QueryAllVaultsResponse, QueryMegavaultTotalSharesRequest, QueryMegavaultTotalSharesResponse, QueryMegavaultOwnerSharesRequest, QueryMegavaultOwnerSharesResponse } from "./query";
import { QueryParamsRequest, QueryParamsResponse, QueryVaultRequest, QueryVaultResponse, QueryAllVaultsRequest, QueryAllVaultsResponse, QueryMegavaultTotalSharesRequest, QueryMegavaultTotalSharesResponse, QueryMegavaultOwnerSharesRequest, QueryMegavaultOwnerSharesResponse, QueryVaultParamsRequest, QueryVaultParamsResponse } from "./query";
/** Query defines the gRPC querier service. */

export interface Query {
Expand All @@ -19,6 +19,9 @@ export interface Query {
/** Queries owner shares of megavault. */

megavaultOwnerShares(request?: QueryMegavaultOwnerSharesRequest): Promise<QueryMegavaultOwnerSharesResponse>;
/** Queries vault params of a vault. */

vaultParams(request: QueryVaultParamsRequest): Promise<QueryVaultParamsResponse>;
}
export class QueryClientImpl implements Query {
private readonly rpc: Rpc;
Expand All @@ -30,6 +33,7 @@ export class QueryClientImpl implements Query {
this.allVaults = this.allVaults.bind(this);
this.megavaultTotalShares = this.megavaultTotalShares.bind(this);
this.megavaultOwnerShares = this.megavaultOwnerShares.bind(this);
this.vaultParams = this.vaultParams.bind(this);
}

params(request: QueryParamsRequest = {}): Promise<QueryParamsResponse> {
Expand Down Expand Up @@ -66,6 +70,12 @@ export class QueryClientImpl implements Query {
return promise.then(data => QueryMegavaultOwnerSharesResponse.decode(new _m0.Reader(data)));
}

vaultParams(request: QueryVaultParamsRequest): Promise<QueryVaultParamsResponse> {
const data = QueryVaultParamsRequest.encode(request).finish();
const promise = this.rpc.request("dydxprotocol.vault.Query", "VaultParams", data);
return promise.then(data => QueryVaultParamsResponse.decode(new _m0.Reader(data)));
}

}
export const createRpcQueryExtension = (base: QueryClient) => {
const rpc = createProtobufRpcClient(base);
Expand All @@ -89,6 +99,10 @@ export const createRpcQueryExtension = (base: QueryClient) => {

megavaultOwnerShares(request?: QueryMegavaultOwnerSharesRequest): Promise<QueryMegavaultOwnerSharesResponse> {
return queryService.megavaultOwnerShares(request);
},

vaultParams(request: QueryVaultParamsRequest): Promise<QueryVaultParamsResponse> {
return queryService.vaultParams(request);
}

};
Expand Down
134 changes: 134 additions & 0 deletions indexer/packages/v4-protos/src/codegen/dydxprotocol/vault/query.ts
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,30 @@ export interface QueryMegavaultOwnerSharesResponseSDKType {
owner_shares: OwnerShareSDKType[];
pagination?: PageResponseSDKType;
}
/** QueryVaultParamsRequest is a request for the VaultParams RPC method. */

export interface QueryVaultParamsRequest {
type: VaultType;
number: number;
}
/** QueryVaultParamsRequest is a request for the VaultParams RPC method. */

export interface QueryVaultParamsRequestSDKType {
type: VaultTypeSDKType;
number: number;
}
/** QueryVaultParamsResponse is a response for the VaultParams RPC method. */

export interface QueryVaultParamsResponse {
vaultId?: VaultId;
vaultParams?: VaultParams;
}
/** QueryVaultParamsResponse is a response for the VaultParams RPC method. */

export interface QueryVaultParamsResponseSDKType {
vault_id?: VaultIdSDKType;
vault_params?: VaultParamsSDKType;
}

function createBaseQueryParamsRequest(): QueryParamsRequest {
return {};
Expand Down Expand Up @@ -670,4 +694,114 @@ export const QueryMegavaultOwnerSharesResponse = {
return message;
}

};

function createBaseQueryVaultParamsRequest(): QueryVaultParamsRequest {
return {
type: 0,
number: 0
};
}

export const QueryVaultParamsRequest = {
encode(message: QueryVaultParamsRequest, writer: _m0.Writer = _m0.Writer.create()): _m0.Writer {
if (message.type !== 0) {
writer.uint32(8).int32(message.type);
}

if (message.number !== 0) {
writer.uint32(16).uint32(message.number);
}

return writer;
},

decode(input: _m0.Reader | Uint8Array, length?: number): QueryVaultParamsRequest {
const reader = input instanceof _m0.Reader ? input : new _m0.Reader(input);
let end = length === undefined ? reader.len : reader.pos + length;
const message = createBaseQueryVaultParamsRequest();

while (reader.pos < end) {
const tag = reader.uint32();

switch (tag >>> 3) {
case 1:
message.type = (reader.int32() as any);
break;

case 2:
message.number = reader.uint32();
break;

default:
reader.skipType(tag & 7);
break;
}
}

return message;
},

fromPartial(object: DeepPartial<QueryVaultParamsRequest>): QueryVaultParamsRequest {
const message = createBaseQueryVaultParamsRequest();
message.type = object.type ?? 0;
message.number = object.number ?? 0;
return message;
}

};

function createBaseQueryVaultParamsResponse(): QueryVaultParamsResponse {
return {
vaultId: undefined,
vaultParams: undefined
};
}

export const QueryVaultParamsResponse = {
encode(message: QueryVaultParamsResponse, writer: _m0.Writer = _m0.Writer.create()): _m0.Writer {
if (message.vaultId !== undefined) {
VaultId.encode(message.vaultId, writer.uint32(10).fork()).ldelim();
}

if (message.vaultParams !== undefined) {
VaultParams.encode(message.vaultParams, writer.uint32(18).fork()).ldelim();
}

return writer;
},

decode(input: _m0.Reader | Uint8Array, length?: number): QueryVaultParamsResponse {
const reader = input instanceof _m0.Reader ? input : new _m0.Reader(input);
let end = length === undefined ? reader.len : reader.pos + length;
const message = createBaseQueryVaultParamsResponse();

while (reader.pos < end) {
const tag = reader.uint32();

switch (tag >>> 3) {
case 1:
message.vaultId = VaultId.decode(reader, reader.uint32());
break;

case 2:
message.vaultParams = VaultParams.decode(reader, reader.uint32());
break;

default:
reader.skipType(tag & 7);
break;
}
}

return message;
},

fromPartial(object: DeepPartial<QueryVaultParamsResponse>): QueryVaultParamsResponse {
const message = createBaseQueryVaultParamsResponse();
message.vaultId = object.vaultId !== undefined && object.vaultId !== null ? VaultId.fromPartial(object.vaultId) : undefined;
message.vaultParams = object.vaultParams !== undefined && object.vaultParams !== null ? VaultParams.fromPartial(object.vaultParams) : undefined;
return message;
}

};
16 changes: 16 additions & 0 deletions proto/dydxprotocol/vault/query.proto
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,10 @@ service Query {
returns (QueryMegavaultOwnerSharesResponse) {
option (google.api.http).get = "/dydxprotocol/vault/megavault/owner_shares";
}
// Queries vault params of a vault.
rpc VaultParams(QueryVaultParamsRequest) returns (QueryVaultParamsResponse) {
option (google.api.http).get = "/dydxprotocol/vault/params/{type}/{number}";
}
}

// QueryParamsRequest is a request type for the Params RPC method.
Expand Down Expand Up @@ -103,3 +107,15 @@ message QueryMegavaultOwnerSharesResponse {
repeated OwnerShare owner_shares = 1;
cosmos.base.query.v1beta1.PageResponse pagination = 2;
}

// QueryVaultParamsRequest is a request for the VaultParams RPC method.
message QueryVaultParamsRequest {
VaultType type = 1;
uint32 number = 2;
}

// QueryVaultParamsResponse is a response for the VaultParams RPC method.
message QueryVaultParamsResponse {
VaultId vault_id = 1 [ (gogoproto.nullable) = false ];
VaultParams vault_params = 2 [ (gogoproto.nullable) = false ];
}
1 change: 1 addition & 0 deletions protocol/app/upgrades.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ func (app *App) setupUpgradeHandlers() {
app.ModuleManager,
app.configurator,
app.PricesKeeper,
app.VaultKeeper,
),
)
}
Expand Down
36 changes: 36 additions & 0 deletions protocol/app/upgrades/v7.0.0/upgrade.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ import (
"github.com/dydxprotocol/v4-chain/protocol/lib"
"github.com/dydxprotocol/v4-chain/protocol/lib/slinky"
pricestypes "github.com/dydxprotocol/v4-chain/protocol/x/prices/types"
vaultkeeper "github.com/dydxprotocol/v4-chain/protocol/x/vault/keeper"
vaulttypes "github.com/dydxprotocol/v4-chain/protocol/x/vault/types"
)

func initCurrencyPairIDCache(ctx sdk.Context, k pricestypes.PricesKeeper) {
Expand All @@ -23,10 +25,41 @@ func initCurrencyPairIDCache(ctx sdk.Context, k pricestypes.PricesKeeper) {
}
}

func migrateVaultQuotingParamsToVaultParams(ctx sdk.Context, k vaultkeeper.Keeper) {
vaultIds := k.UnsafeGetAllVaultIds(ctx)
ctx.Logger().Info(fmt.Sprintf("Migrating quoting parameters of %d vaults", len(vaultIds)))
for _, vaultId := range vaultIds {
quotingParams, exists := k.UnsafeGetQuotingParams(ctx, vaultId)
vaultParams := vaulttypes.VaultParams{
Status: vaulttypes.VaultStatus_VAULT_STATUS_QUOTING,
}
if exists {
vaultParams.QuotingParams = &quotingParams
}
err := k.SetVaultParams(ctx, vaultId, vaultParams)
if err != nil {
panic(
fmt.Sprintf(
"failed to set vault params for vault %+v with params %+v: %s",
vaultId,
vaultParams,
err,
),
)
}
k.UnsafeDeleteQuotingParams(ctx, vaultId)
ctx.Logger().Info(fmt.Sprintf(
"Successfully migrated vault %+v",
vaultId,
))
}
}

func CreateUpgradeHandler(
mm *module.Manager,
configurator module.Configurator,
pricesKeeper pricestypes.PricesKeeper,
vaultKeeper vaultkeeper.Keeper,
) upgradetypes.UpgradeHandler {
return func(ctx context.Context, plan upgradetypes.Plan, vm module.VersionMap) (module.VersionMap, error) {
sdkCtx := lib.UnwrapSDKContext(ctx, "app/upgrades")
Expand All @@ -35,6 +68,9 @@ func CreateUpgradeHandler(
// Initialize the currency pair ID cache for all existing market params.
initCurrencyPairIDCache(sdkCtx, pricesKeeper)

// Migrate vault quoting params to vault params.
migrateVaultQuotingParamsToVaultParams(sdkCtx, vaultKeeper)

return mm.RunMigrations(ctx, configurator, vm)
}
}
51 changes: 47 additions & 4 deletions protocol/app/upgrades/v7.0.0/upgrade_container_test.go
Original file line number Diff line number Diff line change
@@ -1,13 +1,15 @@
//go:build all || container_test

package v_7_0_0_test

import (
"testing"

"github.com/cosmos/gogoproto/proto"

v_7_0_0 "github.com/dydxprotocol/v4-chain/protocol/app/upgrades/v7.0.0"
"github.com/dydxprotocol/v4-chain/protocol/dtypes"
"github.com/dydxprotocol/v4-chain/protocol/testing/containertest"
"github.com/dydxprotocol/v4-chain/protocol/testutil/constants"
vaulttypes "github.com/dydxprotocol/v4-chain/protocol/x/vault/types"
"github.com/stretchr/testify/require"
)

Expand Down Expand Up @@ -35,13 +37,54 @@ func TestStateUpgrade(t *testing.T) {
postUpgradeChecks(node, t)
}

func preUpgradeSetups(node *containertest.Node, t *testing.T) {
}
func preUpgradeSetups(node *containertest.Node, t *testing.T) {}

func preUpgradeChecks(node *containertest.Node, t *testing.T) {
// Add test for your upgrade handler logic below
}

func postUpgradeChecks(node *containertest.Node, t *testing.T) {
// Add test for your upgrade handler logic below
postUpgradeVaultParamsCheck(node, t)
}

func postUpgradeVaultParamsCheck(node *containertest.Node, t *testing.T) {
// Check that a vault with quoting params is successfully migrated and the quoting params are
// successfully migrated to the vault params.
expectedQuotingParams := &vaulttypes.QuotingParams{
Layers: 3,
SpreadMinPpm: 1500,
SpreadBufferPpm: 500,
SkewFactorPpm: 1000000,
OrderSizePctPpm: 50000,
OrderExpirationSeconds: 30,
ActivationThresholdQuoteQuantums: dtypes.NewIntFromUint64(500_000_000),
}

checkVaultParams(node, t, 0, vaulttypes.VaultStatus_VAULT_STATUS_QUOTING, expectedQuotingParams)

// Check that a vault without quoting params is successfully migrated and the quoting params are
// not set in the migrated vault params.
checkVaultParams(node, t, 1, vaulttypes.VaultStatus_VAULT_STATUS_QUOTING, nil)
}

func checkVaultParams(node *containertest.Node, t *testing.T, vaultNumber uint64, expectedStatus vaulttypes.VaultStatus, expectedQuotingParams *vaulttypes.QuotingParams) {
resp, err := containertest.Query(
node,
vaulttypes.NewQueryClient,
vaulttypes.QueryClient.VaultParams,
&vaulttypes.QueryVaultParamsRequest{
Type: vaulttypes.VaultType_VAULT_TYPE_CLOB,
Number: vaultNumber,
},
)
require.NoError(t, err)
require.NotNil(t, resp)

vaultParamsResp := vaulttypes.QueryVaultParamsResponse{}
err = proto.UnmarshalText(resp.String(), &vaultParamsResp)
require.NoError(t, err)

require.Equal(t, expectedStatus, vaultParamsResp.VaultParams.Status)
require.Equal(t, expectedQuotingParams, vaultParamsResp.VaultParams.QuotingParams)
}
Loading
Loading