mirror of
https://github.com/cosmos/cosmjs.git
synced 2025-03-10 13:47:12 +00:00
Merge pull request #1376 from cosmos/tendermint-0.37
Add a Tendermint 0.37 client
This commit is contained in:
commit
2c1f779dbd
15
CHANGELOG.md
15
CHANGELOG.md
@ -21,6 +21,8 @@ and this project adheres to
|
||||
- @cosmjs/proto-signing: Remove `fromJSON`/`toJSON` from `TsProtoGeneratedType`
|
||||
such that generated types are not required to generate those anymore. The
|
||||
methods were provided by ts-proto but we never needed them. ([#1329])
|
||||
- @cosmjs/stargate: Rename `fromTendermint34Event` to `fromTendermintEvent` and
|
||||
let it support both Tendermint 0.34 and 0.37 events as input.
|
||||
|
||||
[#1002]: https://github.com/cosmos/cosmjs/issues/1002
|
||||
[#1240]: https://github.com/cosmos/cosmjs/pull/1240
|
||||
@ -29,10 +31,23 @@ and this project adheres to
|
||||
[#1329]: https://github.com/cosmos/cosmjs/pull/1329
|
||||
|
||||
### Added
|
||||
|
||||
- @cosmjs/stargate: Add `granteeGrants` and `granterGrants` queries to
|
||||
`AuthzExtension` ([#1308]).
|
||||
- @cosmjs/tendermint-rpc: Add new `Tendermint37Client` and remove unused
|
||||
`Tendermint35Client`; Add `TendermintClient` as a union type for
|
||||
`Tendermint34Client` or `Tendermint37Client` and
|
||||
`isTendermint34Client`/`isTendermint37Client` to get the specific type
|
||||
([#1376]).
|
||||
- @cosmjs/stargate: Add constructors `StargateClient.create` and
|
||||
`SigningStargateClient.createWithSigner` to construct with a given Tendermint
|
||||
client ([#1376]).
|
||||
- @cosmjs/cosmwasm-stargate: Add constructors `CosmWasmClient.create` and
|
||||
`SigningCosmWasmClient.createWithSigner` to construct with a given Tendermint
|
||||
client ([#1376]).
|
||||
|
||||
[#1308]: https://github.com/cosmos/cosmjs/pull/1308
|
||||
[#1376]: https://github.com/cosmos/cosmjs/pull/1376
|
||||
|
||||
## [0.29.5] - 2022-12-07
|
||||
|
||||
|
40
packages/cli/examples/tendermint0.37.ts
Normal file
40
packages/cli/examples/tendermint0.37.ts
Normal file
@ -0,0 +1,40 @@
|
||||
import { coins, makeCosmoshubPath } from "@cosmjs/amino";
|
||||
import { DirectSecp256k1HdWallet } from "@cosmjs/proto-signing";
|
||||
import { assertIsDeliverTxSuccess, calculateFee, GasPrice, SigningStargateClient } from "@cosmjs/stargate";
|
||||
import { Tendermint37Client } from "@cosmjs/tendermint-rpc";
|
||||
|
||||
// Network config
|
||||
const prefix = "wasm";
|
||||
const rpcEndpoint = "http://146.190.50.102:26657"; // or 137.184.83.82:26657
|
||||
const gasPrice = GasPrice.fromString("0.001stake");
|
||||
|
||||
// Wallet wasm16jd84xm6yerfaafvtp7s6tpetdqkpu6wxumszp
|
||||
const mnemonic = "royal next favorite duck plastic august rent knee strong weather father opinion";
|
||||
const wallet = await DirectSecp256k1HdWallet.fromMnemonic(mnemonic, { prefix: prefix });
|
||||
const [account] = await wallet.getAccounts();
|
||||
console.log("Signer address:", account.address);
|
||||
|
||||
// Setup client. In contrast to most other examples out there, we create the Tendermint client
|
||||
// explicitly. Otherwise the 0.34 client will be used.
|
||||
const tmClient = await Tendermint37Client.connect(rpcEndpoint);
|
||||
const version = (await tmClient.status()).nodeInfo.version;
|
||||
console.log("Tendermint version:", version);
|
||||
const client = await SigningStargateClient.createWithSigner(tmClient, wallet, { gasPrice: gasPrice });
|
||||
|
||||
// Get my balance
|
||||
const balance = await client.getAllBalances(account.address);
|
||||
console.log("Balance:", balance);
|
||||
|
||||
// Send a transaction
|
||||
const recipient = "wasm142u9fgcjdlycfcez3lw8x6x5h7rfjlnfaallkd";
|
||||
const result = await client.sendTokens(
|
||||
account.address,
|
||||
recipient,
|
||||
coins(1, "stake"),
|
||||
1.5, // In the current testnet the default multiplier of 1.3 is not sufficient 🤷♂️
|
||||
"Have fun with this gift",
|
||||
);
|
||||
assertIsDeliverTxSuccess(result);
|
||||
console.log("Successfully broadcasted:", result);
|
||||
|
||||
client.disconnect();
|
@ -10,7 +10,7 @@ import {
|
||||
BroadcastTxError,
|
||||
Coin,
|
||||
DeliverTxResponse,
|
||||
fromTendermint34Event,
|
||||
fromTendermintEvent,
|
||||
IndexedTx,
|
||||
isSearchByHeightQuery,
|
||||
isSearchBySentFromOrToQuery,
|
||||
@ -25,7 +25,12 @@ import {
|
||||
TimeoutError,
|
||||
TxExtension,
|
||||
} from "@cosmjs/stargate";
|
||||
import { HttpEndpoint, Tendermint34Client, toRfc3339WithNanoseconds } from "@cosmjs/tendermint-rpc";
|
||||
import {
|
||||
HttpEndpoint,
|
||||
Tendermint34Client,
|
||||
TendermintClient,
|
||||
toRfc3339WithNanoseconds,
|
||||
} from "@cosmjs/tendermint-rpc";
|
||||
import { assert, sleep } from "@cosmjs/utils";
|
||||
import {
|
||||
CodeInfoResponse,
|
||||
@ -77,26 +82,40 @@ export interface ContractCodeHistoryEntry {
|
||||
|
||||
/** Use for testing only */
|
||||
export interface PrivateCosmWasmClient {
|
||||
readonly tmClient: Tendermint34Client | undefined;
|
||||
readonly tmClient: TendermintClient | undefined;
|
||||
readonly queryClient:
|
||||
| (QueryClient & AuthExtension & BankExtension & TxExtension & WasmExtension)
|
||||
| undefined;
|
||||
}
|
||||
|
||||
export class CosmWasmClient {
|
||||
private readonly tmClient: Tendermint34Client | undefined;
|
||||
private readonly tmClient: TendermintClient | undefined;
|
||||
private readonly queryClient:
|
||||
| (QueryClient & AuthExtension & BankExtension & TxExtension & WasmExtension)
|
||||
| undefined;
|
||||
private readonly codesCache = new Map<number, CodeDetails>();
|
||||
private chainId: string | undefined;
|
||||
|
||||
/**
|
||||
* Creates an instance by connecting to the given Tendermint RPC endpoint.
|
||||
*
|
||||
* For now this uses the Tendermint 0.34 client. If you need Tendermint 0.37
|
||||
* support, see `create`.
|
||||
*/
|
||||
public static async connect(endpoint: string | HttpEndpoint): Promise<CosmWasmClient> {
|
||||
const tmClient = await Tendermint34Client.connect(endpoint);
|
||||
return CosmWasmClient.create(tmClient);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an instance from a manually created Tendermint client.
|
||||
* Use this to use `Tendermint37Client` instead of `Tendermint34Client`.
|
||||
*/
|
||||
public static async create(tmClient: TendermintClient): Promise<CosmWasmClient> {
|
||||
return new CosmWasmClient(tmClient);
|
||||
}
|
||||
|
||||
protected constructor(tmClient: Tendermint34Client | undefined) {
|
||||
protected constructor(tmClient: TendermintClient | undefined) {
|
||||
if (tmClient) {
|
||||
this.tmClient = tmClient;
|
||||
this.queryClient = QueryClient.withExtensions(
|
||||
@ -109,11 +128,11 @@ export class CosmWasmClient {
|
||||
}
|
||||
}
|
||||
|
||||
protected getTmClient(): Tendermint34Client | undefined {
|
||||
protected getTmClient(): TendermintClient | undefined {
|
||||
return this.tmClient;
|
||||
}
|
||||
|
||||
protected forceGetTmClient(): Tendermint34Client {
|
||||
protected forceGetTmClient(): TendermintClient {
|
||||
if (!this.tmClient) {
|
||||
throw new Error(
|
||||
"Tendermint client not available. You cannot use online functionality in offline mode.",
|
||||
@ -464,7 +483,7 @@ export class CosmWasmClient {
|
||||
height: tx.height,
|
||||
hash: toHex(tx.hash).toUpperCase(),
|
||||
code: tx.result.code,
|
||||
events: tx.result.events.map(fromTendermint34Event),
|
||||
events: tx.result.events.map(fromTendermintEvent),
|
||||
rawLog: tx.result.log || "",
|
||||
tx: tx.tx,
|
||||
gasUsed: tx.result.gasUsed,
|
||||
|
@ -31,7 +31,7 @@ import {
|
||||
SignerData,
|
||||
StdFee,
|
||||
} from "@cosmjs/stargate";
|
||||
import { HttpEndpoint, Tendermint34Client } from "@cosmjs/tendermint-rpc";
|
||||
import { HttpEndpoint, Tendermint34Client, TendermintClient } from "@cosmjs/tendermint-rpc";
|
||||
import { assert, assertDefined } from "@cosmjs/utils";
|
||||
import { MsgWithdrawDelegatorReward } from "cosmjs-types/cosmos/distribution/v1beta1/tx";
|
||||
import { MsgDelegate, MsgUndelegate } from "cosmjs-types/cosmos/staking/v1beta1/tx";
|
||||
@ -183,12 +183,30 @@ export class SigningCosmWasmClient extends CosmWasmClient {
|
||||
private readonly aminoTypes: AminoTypes;
|
||||
private readonly gasPrice: GasPrice | undefined;
|
||||
|
||||
/**
|
||||
* Creates an instance by connecting to the given Tendermint RPC endpoint.
|
||||
*
|
||||
* For now this uses the Tendermint 0.34 client. If you need Tendermint 0.37
|
||||
* support, see `createWithSigner`.
|
||||
*/
|
||||
public static async connectWithSigner(
|
||||
endpoint: string | HttpEndpoint,
|
||||
signer: OfflineSigner,
|
||||
options: SigningCosmWasmClientOptions = {},
|
||||
): Promise<SigningCosmWasmClient> {
|
||||
const tmClient = await Tendermint34Client.connect(endpoint);
|
||||
return SigningCosmWasmClient.createWithSigner(tmClient, signer, options);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an instance from a manually created Tendermint client.
|
||||
* Use this to use `Tendermint37Client` instead of `Tendermint34Client`.
|
||||
*/
|
||||
public static async createWithSigner(
|
||||
tmClient: TendermintClient,
|
||||
signer: OfflineSigner,
|
||||
options: SigningCosmWasmClientOptions = {},
|
||||
): Promise<SigningCosmWasmClient> {
|
||||
return new SigningCosmWasmClient(tmClient, signer, options);
|
||||
}
|
||||
|
||||
@ -209,7 +227,7 @@ export class SigningCosmWasmClient extends CosmWasmClient {
|
||||
}
|
||||
|
||||
protected constructor(
|
||||
tmClient: Tendermint34Client | undefined,
|
||||
tmClient: TendermintClient | undefined,
|
||||
signer: OfflineSigner,
|
||||
options: SigningCosmWasmClientOptions,
|
||||
) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { fromUtf8 } from "@cosmjs/encoding";
|
||||
import { tendermint34 } from "@cosmjs/tendermint-rpc";
|
||||
import { tendermint34, tendermint37 } from "@cosmjs/tendermint-rpc";
|
||||
|
||||
/**
|
||||
* An event attribute.
|
||||
@ -30,16 +30,16 @@ export interface Event {
|
||||
}
|
||||
|
||||
/**
|
||||
* Takes a Tendemrint 0.34 event with binary encoded key and value
|
||||
* Takes a Tendermint 0.34 or 0.37 event with binary encoded key and value
|
||||
* and converts it into an `Event` with string attributes.
|
||||
*/
|
||||
export function fromTendermint34Event(event: tendermint34.Event): Event {
|
||||
export function fromTendermintEvent(event: tendermint34.Event | tendermint37.Event): Event {
|
||||
return {
|
||||
type: event.type,
|
||||
attributes: event.attributes.map(
|
||||
(attr): Attribute => ({
|
||||
key: fromUtf8(attr.key, true),
|
||||
value: fromUtf8(attr.value, true),
|
||||
key: typeof attr.key == "string" ? attr.key : fromUtf8(attr.key, true),
|
||||
value: typeof attr.value == "string" ? attr.value : fromUtf8(attr.value, true),
|
||||
}),
|
||||
),
|
||||
};
|
||||
|
@ -1,6 +1,6 @@
|
||||
export { Account, accountFromAny, AccountParser } from "./accounts";
|
||||
export { AminoConverter, AminoConverters, AminoTypes } from "./aminotypes";
|
||||
export { Attribute, Event, fromTendermint34Event } from "./events";
|
||||
export { Attribute, Event, fromTendermintEvent } from "./events";
|
||||
export { calculateFee, GasPrice } from "./fee";
|
||||
export * as logs from "./logs";
|
||||
export {
|
||||
|
@ -2,7 +2,7 @@
|
||||
import { iavlSpec, ics23, tendermintSpec, verifyExistence, verifyNonExistence } from "@confio/ics23";
|
||||
import { toAscii, toHex } from "@cosmjs/encoding";
|
||||
import { firstEvent } from "@cosmjs/stream";
|
||||
import { tendermint34, Tendermint34Client } from "@cosmjs/tendermint-rpc";
|
||||
import { tendermint34, TendermintClient } from "@cosmjs/tendermint-rpc";
|
||||
import { arrayContentEquals, assert, assertDefined, isNonNullObject, sleep } from "@cosmjs/utils";
|
||||
import { ProofOps } from "cosmjs-types/tendermint/crypto/proof";
|
||||
import { Stream } from "xstream";
|
||||
@ -45,24 +45,24 @@ export interface QueryAbciResponse {
|
||||
|
||||
export class QueryClient {
|
||||
/** Constructs a QueryClient with 0 extensions */
|
||||
public static withExtensions(tmClient: Tendermint34Client): QueryClient;
|
||||
public static withExtensions(tmClient: TendermintClient): QueryClient;
|
||||
|
||||
/** Constructs a QueryClient with 1 extension */
|
||||
public static withExtensions<A extends object>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
): QueryClient & A;
|
||||
|
||||
/** Constructs a QueryClient with 2 extensions */
|
||||
public static withExtensions<A extends object, B extends object>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
): QueryClient & A & B;
|
||||
|
||||
/** Constructs a QueryClient with 3 extensions */
|
||||
public static withExtensions<A extends object, B extends object, C extends object>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -70,7 +70,7 @@ export class QueryClient {
|
||||
|
||||
/** Constructs a QueryClient with 4 extensions */
|
||||
public static withExtensions<A extends object, B extends object, C extends object, D extends object>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -85,7 +85,7 @@ export class QueryClient {
|
||||
D extends object,
|
||||
E extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -102,7 +102,7 @@ export class QueryClient {
|
||||
E extends object,
|
||||
F extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -121,7 +121,7 @@ export class QueryClient {
|
||||
F extends object,
|
||||
G extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -142,7 +142,7 @@ export class QueryClient {
|
||||
G extends object,
|
||||
H extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -165,7 +165,7 @@ export class QueryClient {
|
||||
H extends object,
|
||||
I extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -190,7 +190,7 @@ export class QueryClient {
|
||||
I extends object,
|
||||
J extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -217,7 +217,7 @@ export class QueryClient {
|
||||
J extends object,
|
||||
K extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -246,7 +246,7 @@ export class QueryClient {
|
||||
K extends object,
|
||||
L extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -277,7 +277,7 @@ export class QueryClient {
|
||||
L extends object,
|
||||
M extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -310,7 +310,7 @@ export class QueryClient {
|
||||
M extends object,
|
||||
N extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -345,7 +345,7 @@ export class QueryClient {
|
||||
N extends object,
|
||||
O extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -382,7 +382,7 @@ export class QueryClient {
|
||||
O extends object,
|
||||
P extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -421,7 +421,7 @@ export class QueryClient {
|
||||
P extends object,
|
||||
Q extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -462,7 +462,7 @@ export class QueryClient {
|
||||
Q extends object,
|
||||
R extends object,
|
||||
>(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
setupExtensionA: QueryExtensionSetup<A>,
|
||||
setupExtensionB: QueryExtensionSetup<B>,
|
||||
setupExtensionC: QueryExtensionSetup<C>,
|
||||
@ -484,7 +484,7 @@ export class QueryClient {
|
||||
): QueryClient & A & B & C & D & E & F & G & H & I & J & K & L & M & N & O & P & Q & R;
|
||||
|
||||
public static withExtensions(
|
||||
tmClient: Tendermint34Client,
|
||||
tmClient: TendermintClient,
|
||||
...extensionSetups: Array<QueryExtensionSetup<object>>
|
||||
): any {
|
||||
const client = new QueryClient(tmClient);
|
||||
@ -506,9 +506,9 @@ export class QueryClient {
|
||||
return client;
|
||||
}
|
||||
|
||||
private readonly tmClient: Tendermint34Client;
|
||||
private readonly tmClient: TendermintClient;
|
||||
|
||||
public constructor(tmClient: Tendermint34Client) {
|
||||
public constructor(tmClient: TendermintClient) {
|
||||
this.tmClient = tmClient;
|
||||
}
|
||||
|
||||
|
@ -12,7 +12,7 @@ import {
|
||||
Registry,
|
||||
TxBodyEncodeObject,
|
||||
} from "@cosmjs/proto-signing";
|
||||
import { HttpEndpoint, Tendermint34Client } from "@cosmjs/tendermint-rpc";
|
||||
import { HttpEndpoint, Tendermint34Client, TendermintClient } from "@cosmjs/tendermint-rpc";
|
||||
import { assert, assertDefined } from "@cosmjs/utils";
|
||||
import { Coin } from "cosmjs-types/cosmos/base/v1beta1/coin";
|
||||
import { MsgWithdrawDelegatorReward } from "cosmjs-types/cosmos/distribution/v1beta1/tx";
|
||||
@ -114,12 +114,30 @@ export class SigningStargateClient extends StargateClient {
|
||||
private readonly aminoTypes: AminoTypes;
|
||||
private readonly gasPrice: GasPrice | undefined;
|
||||
|
||||
/**
|
||||
* Creates an instance by connecting to the given Tendermint RPC endpoint.
|
||||
*
|
||||
* For now this uses the Tendermint 0.34 client. If you need Tendermint 0.37
|
||||
* support, see `createWithSigner`.
|
||||
*/
|
||||
public static async connectWithSigner(
|
||||
endpoint: string | HttpEndpoint,
|
||||
signer: OfflineSigner,
|
||||
options: SigningStargateClientOptions = {},
|
||||
): Promise<SigningStargateClient> {
|
||||
const tmClient = await Tendermint34Client.connect(endpoint);
|
||||
return SigningStargateClient.createWithSigner(tmClient, signer, options);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an instance from a manually created Tendermint client.
|
||||
* Use this to use `Tendermint37Client` instead of `Tendermint34Client`.
|
||||
*/
|
||||
public static async createWithSigner(
|
||||
tmClient: TendermintClient,
|
||||
signer: OfflineSigner,
|
||||
options: SigningStargateClientOptions = {},
|
||||
): Promise<SigningStargateClient> {
|
||||
return new SigningStargateClient(tmClient, signer, options);
|
||||
}
|
||||
|
||||
@ -140,7 +158,7 @@ export class SigningStargateClient extends StargateClient {
|
||||
}
|
||||
|
||||
protected constructor(
|
||||
tmClient: Tendermint34Client | undefined,
|
||||
tmClient: TendermintClient | undefined,
|
||||
signer: OfflineSigner,
|
||||
options: SigningStargateClientOptions,
|
||||
) {
|
||||
|
@ -2,7 +2,12 @@
|
||||
import { addCoins } from "@cosmjs/amino";
|
||||
import { toHex } from "@cosmjs/encoding";
|
||||
import { Uint53 } from "@cosmjs/math";
|
||||
import { HttpEndpoint, Tendermint34Client, toRfc3339WithNanoseconds } from "@cosmjs/tendermint-rpc";
|
||||
import {
|
||||
HttpEndpoint,
|
||||
Tendermint34Client,
|
||||
TendermintClient,
|
||||
toRfc3339WithNanoseconds,
|
||||
} from "@cosmjs/tendermint-rpc";
|
||||
import { assert, sleep } from "@cosmjs/utils";
|
||||
import { MsgData } from "cosmjs-types/cosmos/base/abci/v1beta1/abci";
|
||||
import { Coin } from "cosmjs-types/cosmos/base/v1beta1/coin";
|
||||
@ -10,7 +15,7 @@ import { QueryDelegatorDelegationsResponse } from "cosmjs-types/cosmos/staking/v
|
||||
import { DelegationResponse } from "cosmjs-types/cosmos/staking/v1beta1/staking";
|
||||
|
||||
import { Account, accountFromAny, AccountParser } from "./accounts";
|
||||
import { Event, fromTendermint34Event } from "./events";
|
||||
import { Event, fromTendermintEvent } from "./events";
|
||||
import {
|
||||
AuthExtension,
|
||||
BankExtension,
|
||||
@ -171,7 +176,7 @@ export class BroadcastTxError extends Error {
|
||||
|
||||
/** Use for testing only */
|
||||
export interface PrivateStargateClient {
|
||||
readonly tmClient: Tendermint34Client | undefined;
|
||||
readonly tmClient: TendermintClient | undefined;
|
||||
}
|
||||
|
||||
export interface StargateClientOptions {
|
||||
@ -179,22 +184,39 @@ export interface StargateClientOptions {
|
||||
}
|
||||
|
||||
export class StargateClient {
|
||||
private readonly tmClient: Tendermint34Client | undefined;
|
||||
private readonly tmClient: TendermintClient | undefined;
|
||||
private readonly queryClient:
|
||||
| (QueryClient & AuthExtension & BankExtension & StakingExtension & TxExtension)
|
||||
| undefined;
|
||||
private chainId: string | undefined;
|
||||
private readonly accountParser: AccountParser;
|
||||
|
||||
/**
|
||||
* Creates an instance by connecting to the given Tendermint RPC endpoint.
|
||||
*
|
||||
* For now this uses the Tendermint 0.34 client. If you need Tendermint 0.37
|
||||
* support, see `create`.
|
||||
*/
|
||||
public static async connect(
|
||||
endpoint: string | HttpEndpoint,
|
||||
options: StargateClientOptions = {},
|
||||
): Promise<StargateClient> {
|
||||
const tmClient = await Tendermint34Client.connect(endpoint);
|
||||
return StargateClient.create(tmClient, options);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates an instance from a manually created Tendermint client.
|
||||
* Use this to use `Tendermint37Client` instead of `Tendermint34Client`.
|
||||
*/
|
||||
public static async create(
|
||||
tmClient: TendermintClient,
|
||||
options: StargateClientOptions = {},
|
||||
): Promise<StargateClient> {
|
||||
return new StargateClient(tmClient, options);
|
||||
}
|
||||
|
||||
protected constructor(tmClient: Tendermint34Client | undefined, options: StargateClientOptions) {
|
||||
protected constructor(tmClient: TendermintClient | undefined, options: StargateClientOptions) {
|
||||
if (tmClient) {
|
||||
this.tmClient = tmClient;
|
||||
this.queryClient = QueryClient.withExtensions(
|
||||
@ -209,11 +231,11 @@ export class StargateClient {
|
||||
this.accountParser = accountParser;
|
||||
}
|
||||
|
||||
protected getTmClient(): Tendermint34Client | undefined {
|
||||
protected getTmClient(): TendermintClient | undefined {
|
||||
return this.tmClient;
|
||||
}
|
||||
|
||||
protected forceGetTmClient(): Tendermint34Client {
|
||||
protected forceGetTmClient(): TendermintClient {
|
||||
if (!this.tmClient) {
|
||||
throw new Error(
|
||||
"Tendermint client not available. You cannot use online functionality in offline mode.",
|
||||
@ -471,7 +493,7 @@ export class StargateClient {
|
||||
height: tx.height,
|
||||
hash: toHex(tx.hash).toUpperCase(),
|
||||
code: tx.result.code,
|
||||
events: tx.result.events.map(fromTendermint34Event),
|
||||
events: tx.result.events.map(fromTendermintEvent),
|
||||
rawLog: tx.result.log || "",
|
||||
tx: tx.tx,
|
||||
gasUsed: tx.result.gasUsed,
|
||||
|
@ -95,10 +95,9 @@ export {
|
||||
} from "./tendermint34";
|
||||
export * as tendermint34 from "./tendermint34";
|
||||
export { Tendermint34Client } from "./tendermint34";
|
||||
// Tendermint 0.35 support is not public. The implementation may break or be removed at any point in time.
|
||||
// See https://github.com/cosmos/cosmjs/issues/1225 for more context.
|
||||
// export * as tendermint35 from "./tendermint35";
|
||||
// export { Tendermint35Client } from "./tendermint35";
|
||||
export * as tendermint37 from "./tendermint37";
|
||||
export { Tendermint37Client } from "./tendermint37";
|
||||
export { isTendermint34Client, isTendermint37Client, TendermintClient } from "./tendermintclient";
|
||||
export {
|
||||
BlockIdFlag,
|
||||
CommitSignature,
|
||||
|
@ -1,7 +1,7 @@
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
import { toAscii } from "@cosmjs/encoding";
|
||||
import { toAscii, toHex } from "@cosmjs/encoding";
|
||||
import { firstEvent, toListPromise } from "@cosmjs/stream";
|
||||
import { sleep } from "@cosmjs/utils";
|
||||
import { assert, sleep } from "@cosmjs/utils";
|
||||
import { ReadonlyDate } from "readonly-date";
|
||||
import { Stream } from "xstream";
|
||||
|
||||
@ -344,7 +344,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
const height = (await client.status()).syncInfo.latestBlockHeight;
|
||||
const blockchain = await client.blockchain(undefined, height - 1);
|
||||
expect(blockchain.lastHeight).toEqual(height);
|
||||
expect(blockchain.lastHeight).toBeGreaterThanOrEqual(height);
|
||||
expect(blockchain.blockMetas.length).toBeGreaterThanOrEqual(2);
|
||||
expect(blockchain.blockMetas[0].header.height).toEqual(height - 1); // upper limit included
|
||||
expect(blockchain.blockMetas[1].header.height).toEqual(height - 2);
|
||||
@ -435,25 +435,6 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
expect(r.height).toEqual(height);
|
||||
expect(r.proof).toBeTruthy();
|
||||
|
||||
// txSearch - you must enable the indexer when running
|
||||
// tendermint, else you get empty results
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: find }] });
|
||||
|
||||
const s = await client.txSearch({ query: query, page: 1, per_page: 30 });
|
||||
// should find the tx
|
||||
expect(s.totalCount).toEqual(1);
|
||||
// should return same info as querying directly,
|
||||
// except without the proof
|
||||
expect(s.txs[0]).toEqual({ ...r, proof: undefined });
|
||||
|
||||
// ensure txSearchAll works as well
|
||||
const sall = await client.txSearchAll({ query: query });
|
||||
// should find the tx
|
||||
expect(sall.totalCount).toEqual(1);
|
||||
// should return same info as querying directly,
|
||||
// except without the proof
|
||||
expect(sall.txs[0]).toEqual({ ...r, proof: undefined });
|
||||
|
||||
// and let's query the block itself to see this transaction
|
||||
const block = await client.block(height);
|
||||
expect(block.block.txs.length).toEqual(1);
|
||||
@ -464,25 +445,28 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
});
|
||||
|
||||
describe("txSearch", () => {
|
||||
const key = randomString();
|
||||
const txKey = randomString(); // a key used for multiple transactions
|
||||
let tx1: Uint8Array | undefined;
|
||||
let broadcast1: responses.BroadcastTxCommitResponse | undefined;
|
||||
|
||||
beforeAll(async () => {
|
||||
if (tendermintEnabled()) {
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
// eslint-disable-next-line no-inner-declarations
|
||||
async function sendTx(): Promise<void> {
|
||||
async function sendTx(): Promise<[Uint8Array, responses.BroadcastTxCommitResponse]> {
|
||||
const me = randomString();
|
||||
const tx = buildKvTx(key, me);
|
||||
const tx = buildKvTx(txKey, me);
|
||||
|
||||
const txRes = await client.broadcastTxCommit({ tx: tx });
|
||||
expect(responses.broadcastTxCommitSuccess(txRes)).toEqual(true);
|
||||
expect(txRes.height).toBeTruthy();
|
||||
expect(txRes.hash.length).not.toEqual(0);
|
||||
expect(txRes.hash.length).toEqual(32);
|
||||
return [tx, txRes];
|
||||
}
|
||||
|
||||
// send 3 txs
|
||||
await sendTx();
|
||||
[tx1, broadcast1] = await sendTx();
|
||||
await sendTx();
|
||||
await sendTx();
|
||||
|
||||
@ -492,6 +476,68 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
}
|
||||
});
|
||||
|
||||
it("finds a single tx by hash", async () => {
|
||||
pendingWithoutTendermint();
|
||||
assert(tx1 && broadcast1);
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
const result = await client.txSearch({ query: `tx.hash='${toHex(broadcast1.hash)}'` });
|
||||
expect(result.totalCount).toEqual(1);
|
||||
expect(result.txs[0]).toEqual({
|
||||
hash: broadcast1.hash,
|
||||
height: broadcast1.height,
|
||||
index: 0,
|
||||
tx: tx1,
|
||||
result: broadcast1.deliverTx!,
|
||||
proof: undefined,
|
||||
});
|
||||
|
||||
client.disconnect();
|
||||
});
|
||||
|
||||
it("finds a single tx by tags", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
const txKey2 = randomString();
|
||||
const txValue2 = randomString();
|
||||
const tx = buildKvTx(txKey2, txValue2);
|
||||
|
||||
const txRes = await client.broadcastTxCommit({ tx: tx });
|
||||
expect(responses.broadcastTxCommitSuccess(txRes)).toEqual(true);
|
||||
await tendermintSearchIndexUpdated();
|
||||
|
||||
// txSearch - you must enable the indexer when running
|
||||
// tendermint, else you get empty results
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey2 }] });
|
||||
|
||||
const search = await client.txSearch({ query: query, page: 1, per_page: 30 });
|
||||
// should find the tx
|
||||
expect(search.totalCount).toEqual(1);
|
||||
// should return same info as querying directly,
|
||||
// except without the proof
|
||||
expect(search.txs[0]).toEqual({
|
||||
hash: txRes.hash,
|
||||
height: txRes.height,
|
||||
index: 0,
|
||||
tx: tx,
|
||||
result: txRes.deliverTx!,
|
||||
proof: undefined,
|
||||
});
|
||||
|
||||
// Ensure txSearchAll works as well. This should be moved in a dedicated "txSearchAll" test block.
|
||||
const searchAll = await client.txSearchAll({ query: query });
|
||||
expect(searchAll.totalCount).toEqual(1);
|
||||
expect(searchAll.txs[0]).toEqual({
|
||||
hash: txRes.hash,
|
||||
height: txRes.height,
|
||||
index: 0,
|
||||
tx: tx,
|
||||
result: txRes.deliverTx!,
|
||||
proof: undefined,
|
||||
});
|
||||
});
|
||||
|
||||
it("returns transactions in ascending order by default", async () => {
|
||||
// NOTE: The Tendermint docs claim the default ordering is "desc" but it is actually "asc"
|
||||
// Docs: https://docs.tendermint.com/master/rpc/#/Info/tx_search
|
||||
@ -499,15 +545,15 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
const s = await client.txSearch({ query: query });
|
||||
const result = await client.txSearch({ query: query });
|
||||
|
||||
expect(s.totalCount).toEqual(3);
|
||||
s.txs.slice(1).reduce((lastHeight, { height }) => {
|
||||
expect(result.totalCount).toEqual(3);
|
||||
result.txs.slice(1).reduce((lastHeight, { height }) => {
|
||||
expect(height).toBeGreaterThanOrEqual(lastHeight);
|
||||
return height;
|
||||
}, s.txs[0].height);
|
||||
}, result.txs[0].height);
|
||||
|
||||
client.disconnect();
|
||||
});
|
||||
@ -516,7 +562,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
const s1 = await client.txSearch({ query: query, order_by: "desc" });
|
||||
const s2 = await client.txSearch({ query: query, order_by: "asc" });
|
||||
@ -531,7 +577,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
// expect one page of results
|
||||
const s1 = await client.txSearch({ query: query, page: 1, per_page: 2 });
|
||||
@ -550,15 +596,14 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint34Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
const sall = await client.txSearchAll({ query: query, per_page: 2 });
|
||||
expect(sall.totalCount).toEqual(3);
|
||||
expect(sall.txs.length).toEqual(3);
|
||||
// make sure there are in order from lowest to highest height
|
||||
const [tx1, tx2, tx3] = sall.txs;
|
||||
expect(tx2.height).toEqual(tx1.height + 1);
|
||||
expect(tx3.height).toEqual(tx2.height + 1);
|
||||
expect(sall.txs[1].height).toEqual(sall.txs[0].height + 1);
|
||||
expect(sall.txs[2].height).toEqual(sall.txs[1].height + 1);
|
||||
|
||||
client.disconnect();
|
||||
});
|
||||
|
@ -5,7 +5,7 @@ import { Adaptor } from "./types";
|
||||
|
||||
export { Decoder, Encoder, Params, Responses } from "./types";
|
||||
|
||||
export const adaptor35: Adaptor = {
|
||||
export const adaptor37: Adaptor = {
|
||||
params: Params,
|
||||
responses: Responses,
|
||||
hashTx: hashTx,
|
@ -74,13 +74,13 @@ function encodeBroadcastTxParams(params: requests.BroadcastTxParams): RpcBroadca
|
||||
}
|
||||
|
||||
interface RpcTxParams {
|
||||
/** hex encoded */
|
||||
/** base64 encoded */
|
||||
readonly hash: string;
|
||||
readonly prove?: boolean;
|
||||
}
|
||||
function encodeTxParams(params: requests.TxParams): RpcTxParams {
|
||||
return {
|
||||
hash: toHex(assertNotEmpty(params.hash)),
|
||||
hash: toBase64(assertNotEmpty(params.hash)),
|
||||
prove: params.prove,
|
||||
};
|
||||
}
|
@ -1,5 +1,5 @@
|
||||
// Note: all exports in this module are publicly available via
|
||||
// `import { tendermint35 } from "@cosmjs/tendermint-rpc"`
|
||||
// `import { tendermint37 } from "@cosmjs/tendermint-rpc"`
|
||||
|
||||
export {
|
||||
AbciInfoRequest,
|
||||
@ -76,4 +76,4 @@ export {
|
||||
Vote,
|
||||
VoteType,
|
||||
} from "./responses";
|
||||
export { Tendermint35Client } from "./tendermint35client";
|
||||
export { Tendermint37Client } from "./tendermint37client";
|
@ -1,7 +1,7 @@
|
||||
/* eslint-disable @typescript-eslint/naming-convention */
|
||||
import { toAscii } from "@cosmjs/encoding";
|
||||
import { toAscii, toHex } from "@cosmjs/encoding";
|
||||
import { firstEvent, toListPromise } from "@cosmjs/stream";
|
||||
import { sleep } from "@cosmjs/utils";
|
||||
import { assert, sleep } from "@cosmjs/utils";
|
||||
import { ReadonlyDate } from "readonly-date";
|
||||
import { Stream } from "xstream";
|
||||
|
||||
@ -16,16 +16,16 @@ import {
|
||||
tendermintInstances,
|
||||
tendermintSearchIndexUpdated,
|
||||
} from "../testutil.spec";
|
||||
import { adaptor35 } from "./adaptor";
|
||||
import { adaptor37 } from "./adaptor";
|
||||
import { buildQuery } from "./requests";
|
||||
import * as responses from "./responses";
|
||||
import { Tendermint35Client } from "./tendermint35client";
|
||||
import { Tendermint37Client } from "./tendermint37client";
|
||||
|
||||
function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues): void {
|
||||
describe("create", () => {
|
||||
it("can auto-discover Tendermint version and communicate", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const info = await client.abciInfo();
|
||||
expect(info).toBeTruthy();
|
||||
client.disconnect();
|
||||
@ -33,7 +33,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can connect to Tendermint with known version", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
expect(await client.abciInfo()).toBeTruthy();
|
||||
client.disconnect();
|
||||
});
|
||||
@ -41,7 +41,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can get genesis", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const genesis = await client.genesis();
|
||||
expect(genesis).toBeTruthy();
|
||||
client.disconnect();
|
||||
@ -50,7 +50,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("broadcastTxCommit", () => {
|
||||
it("can broadcast a transaction", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const tx = buildKvTx(randomString(), randomString());
|
||||
|
||||
const response = await client.broadcastTxCommit({ tx: tx });
|
||||
@ -70,7 +70,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("broadcastTxSync", () => {
|
||||
it("can broadcast a transaction", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const tx = buildKvTx(randomString(), randomString());
|
||||
|
||||
const response = await client.broadcastTxSync({ tx: tx });
|
||||
@ -86,7 +86,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("broadcastTxAsync", () => {
|
||||
it("can broadcast a transaction", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const tx = buildKvTx(randomString(), randomString());
|
||||
|
||||
const response = await client.broadcastTxAsync({ tx: tx });
|
||||
@ -98,9 +98,9 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("gets the same tx hash from backend as calculated locally", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const tx = buildKvTx(randomString(), randomString());
|
||||
const calculatedTxHash = adaptor35.hashTx(tx);
|
||||
const calculatedTxHash = adaptor37.hashTx(tx);
|
||||
|
||||
const response = await client.broadcastTxCommit({ tx: tx });
|
||||
expect(response.hash).toEqual(calculatedTxHash);
|
||||
@ -111,7 +111,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("abciQuery", () => {
|
||||
it("can query the state", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const key = randomString();
|
||||
const value = randomString();
|
||||
@ -137,7 +137,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can get a commit", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const response = await client.commit(4);
|
||||
|
||||
expect(response).toBeTruthy();
|
||||
@ -152,7 +152,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can get validators", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const response = await client.validators({});
|
||||
|
||||
expect(response).toBeTruthy();
|
||||
@ -170,7 +170,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can get all validators", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const response = await client.validatorsAll();
|
||||
|
||||
expect(response).toBeTruthy();
|
||||
@ -188,7 +188,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can call a bunch of methods", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
expect(await client.block()).toBeTruthy();
|
||||
expect(await client.genesis()).toBeTruthy();
|
||||
@ -200,7 +200,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("status", () => {
|
||||
it("works", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const status = await client.status();
|
||||
|
||||
@ -230,7 +230,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("numUnconfirmedTxs", () => {
|
||||
it("works", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const response = await client.numUnconfirmedTxs();
|
||||
|
||||
@ -244,7 +244,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("blockResults", () => {
|
||||
it("works", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const height = 3;
|
||||
const results = await client.blockResults(height);
|
||||
@ -260,7 +260,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("blockSearch", () => {
|
||||
beforeAll(async () => {
|
||||
if (tendermintEnabled()) {
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
// eslint-disable-next-line no-inner-declarations
|
||||
async function sendTx(): Promise<void> {
|
||||
@ -285,7 +285,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can paginate over blockSearch results", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ raw: "block.height >= 1 AND block.height <= 3" });
|
||||
|
||||
@ -304,7 +304,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can get all search results in one call", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ raw: "block.height >= 1 AND block.height <= 3" });
|
||||
|
||||
@ -323,7 +323,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("blockchain", () => {
|
||||
it("returns latest in descending order by default", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
// Run in parallel to increase chance there is no block between the calls
|
||||
const [status, blockchain] = await Promise.all([client.status(), client.blockchain()]);
|
||||
@ -340,7 +340,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can limit by maxHeight", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const height = (await client.status()).syncInfo.latestBlockHeight;
|
||||
const blockchain = await client.blockchain(undefined, height - 1);
|
||||
@ -354,7 +354,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("works with maxHeight in the future", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const height = (await client.status()).syncInfo.latestBlockHeight;
|
||||
const blockchain = await client.blockchain(undefined, height + 20);
|
||||
@ -369,7 +369,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can limit by minHeight and maxHeight", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const height = (await client.status()).syncInfo.latestBlockHeight;
|
||||
const blockchain = await client.blockchain(height - 2, height - 1);
|
||||
@ -383,7 +383,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("contains all the info", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const height = (await client.status()).syncInfo.latestBlockHeight;
|
||||
const blockchain = await client.blockchain(height - 1, height - 1);
|
||||
@ -412,7 +412,7 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
describe("tx", () => {
|
||||
it("can query a tx properly", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const find = randomString();
|
||||
const me = randomString();
|
||||
@ -436,25 +436,6 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
expect(r.height).toEqual(height);
|
||||
expect(r.proof).toBeTruthy();
|
||||
|
||||
// txSearch - you must enable the indexer when running
|
||||
// tendermint, else you get empty results
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: find }] });
|
||||
|
||||
const s = await client.txSearch({ query: query, page: 1, per_page: 30 });
|
||||
// should find the tx
|
||||
expect(s.totalCount).toEqual(1);
|
||||
// should return same info as querying directly,
|
||||
// except without the proof
|
||||
expect(s.txs[0]).toEqual({ ...r, proof: undefined });
|
||||
|
||||
// ensure txSearchAll works as well
|
||||
const sall = await client.txSearchAll({ query: query });
|
||||
// should find the tx
|
||||
expect(sall.totalCount).toEqual(1);
|
||||
// should return same info as querying directly,
|
||||
// except without the proof
|
||||
expect(sall.txs[0]).toEqual({ ...r, proof: undefined });
|
||||
|
||||
// and let's query the block itself to see this transaction
|
||||
const block = await client.block(height);
|
||||
expect(block.block.txs.length).toEqual(1);
|
||||
@ -465,25 +446,28 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
});
|
||||
|
||||
describe("txSearch", () => {
|
||||
const key = randomString();
|
||||
const txKey = randomString(); // a key used for multiple transactions
|
||||
let tx1: Uint8Array | undefined;
|
||||
let broadcast1: responses.BroadcastTxCommitResponse | undefined;
|
||||
|
||||
beforeAll(async () => {
|
||||
if (tendermintEnabled()) {
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
// eslint-disable-next-line no-inner-declarations
|
||||
async function sendTx(): Promise<void> {
|
||||
async function sendTx(): Promise<[Uint8Array, responses.BroadcastTxCommitResponse]> {
|
||||
const me = randomString();
|
||||
const tx = buildKvTx(key, me);
|
||||
const tx = buildKvTx(txKey, me);
|
||||
|
||||
const txRes = await client.broadcastTxCommit({ tx: tx });
|
||||
expect(responses.broadcastTxCommitSuccess(txRes)).toEqual(true);
|
||||
expect(txRes.height).toBeTruthy();
|
||||
expect(txRes.hash.length).not.toEqual(0);
|
||||
expect(txRes.hash.length).toEqual(32);
|
||||
return [tx, txRes];
|
||||
}
|
||||
|
||||
// send 3 txs
|
||||
await sendTx();
|
||||
[tx1, broadcast1] = await sendTx();
|
||||
await sendTx();
|
||||
await sendTx();
|
||||
|
||||
@ -493,22 +477,86 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
}
|
||||
});
|
||||
|
||||
it("returns transactions in descending order by default", async () => {
|
||||
it("finds a single tx by hash", async () => {
|
||||
pendingWithoutTendermint();
|
||||
assert(tx1 && broadcast1);
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const result = await client.txSearch({ query: `tx.hash='${toHex(broadcast1.hash)}'` });
|
||||
expect(result.totalCount).toEqual(1);
|
||||
expect(result.txs[0]).toEqual({
|
||||
hash: broadcast1.hash,
|
||||
height: broadcast1.height,
|
||||
index: 0,
|
||||
tx: tx1,
|
||||
result: broadcast1.deliverTx!,
|
||||
proof: undefined,
|
||||
});
|
||||
|
||||
client.disconnect();
|
||||
});
|
||||
|
||||
it("finds a single tx by tags", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const txKey2 = randomString();
|
||||
const txValue2 = randomString();
|
||||
const tx = buildKvTx(txKey2, txValue2);
|
||||
|
||||
const txRes = await client.broadcastTxCommit({ tx: tx });
|
||||
expect(responses.broadcastTxCommitSuccess(txRes)).toEqual(true);
|
||||
await tendermintSearchIndexUpdated();
|
||||
|
||||
// txSearch - you must enable the indexer when running
|
||||
// tendermint, else you get empty results
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey2 }] });
|
||||
|
||||
const search = await client.txSearch({ query: query, page: 1, per_page: 30 });
|
||||
// should find the tx
|
||||
expect(search.totalCount).toEqual(1);
|
||||
// should return same info as querying directly,
|
||||
// except without the proof
|
||||
expect(search.txs[0]).toEqual({
|
||||
hash: txRes.hash,
|
||||
height: txRes.height,
|
||||
index: 0,
|
||||
tx: tx,
|
||||
result: txRes.deliverTx!,
|
||||
proof: undefined,
|
||||
});
|
||||
|
||||
// Ensure txSearchAll works as well. This should be moved in a dedicated "txSearchAll" test block.
|
||||
const searchAll = await client.txSearchAll({ query: query });
|
||||
expect(searchAll.totalCount).toEqual(1);
|
||||
expect(searchAll.txs[0]).toEqual({
|
||||
hash: txRes.hash,
|
||||
height: txRes.height,
|
||||
index: 0,
|
||||
tx: tx,
|
||||
result: txRes.deliverTx!,
|
||||
proof: undefined,
|
||||
});
|
||||
});
|
||||
|
||||
it("returns transactions in ascending order by default", async () => {
|
||||
// NOTE: The Tendermint docs states the default ordering is "desc". Until
|
||||
// 0.35 it was actually "asc" but from 0.35 on it is "desc".
|
||||
// Then it was changed back to "asc" in 0.37.
|
||||
// Docs: https://docs.tendermint.com/master/rpc/#/Info/tx_search
|
||||
// Code 0.34: https://github.com/tendermint/tendermint/blob/v0.34.10/rpc/core/tx.go#L89
|
||||
// Code 0.35: https://github.com/tendermint/tendermint/blob/v0.35.6/internal/rpc/core/tx.go#L93
|
||||
// Code 0.37: https://github.com/cometbft/cometbft/blob/v0.37.0-rc3/rpc/core/tx.go#L87
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
const result = await client.txSearch({ query: query });
|
||||
|
||||
expect(result.totalCount).toEqual(3);
|
||||
result.txs.slice(1).reduce((lastHeight, { height }) => {
|
||||
expect(height).toBeLessThanOrEqual(lastHeight);
|
||||
expect(height).toBeGreaterThanOrEqual(lastHeight);
|
||||
return height;
|
||||
}, result.txs[0].height);
|
||||
|
||||
@ -517,9 +565,9 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can set the order", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
const result1 = await client.txSearch({ query: query, order_by: "desc" });
|
||||
const result2 = await client.txSearch({ query: query, order_by: "asc" });
|
||||
@ -532,9 +580,9 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can paginate over txSearch results", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
// expect one page of results
|
||||
const s1 = await client.txSearch({ query: query, page: 1, per_page: 2 });
|
||||
@ -551,17 +599,16 @@ function defaultTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValues)
|
||||
|
||||
it("can get all search results in one call", async () => {
|
||||
pendingWithoutTendermint();
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: key }] });
|
||||
const query = buildQuery({ tags: [{ key: "app.key", value: txKey }] });
|
||||
|
||||
const sall = await client.txSearchAll({ query: query, per_page: 2 });
|
||||
expect(sall.totalCount).toEqual(3);
|
||||
expect(sall.txs.length).toEqual(3);
|
||||
// make sure there are in order from highest to lowest height
|
||||
const [tx1, tx2, tx3] = sall.txs;
|
||||
expect(tx2.height).toBeLessThan(tx1.height);
|
||||
expect(tx3.height).toBeLessThan(tx2.height);
|
||||
expect(sall.txs[1].height).toEqual(sall.txs[0].height + 1);
|
||||
expect(sall.txs[2].height).toEqual(sall.txs[1].height + 1);
|
||||
|
||||
client.disconnect();
|
||||
});
|
||||
@ -576,7 +623,7 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
|
||||
(async () => {
|
||||
const events: responses.NewBlockHeaderEvent[] = [];
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const stream = client.subscribeNewBlockHeader();
|
||||
expect(stream).toBeTruthy();
|
||||
const subscription = stream.subscribe({
|
||||
@ -635,7 +682,7 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
const transactionData2 = buildKvTx(randomString(), randomString());
|
||||
|
||||
const events: responses.NewBlockEvent[] = [];
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const stream = client.subscribeNewBlock();
|
||||
const subscription = stream.subscribe({
|
||||
next: (event) => {
|
||||
@ -694,7 +741,7 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
pendingWithoutTendermint();
|
||||
|
||||
const events: responses.TxEvent[] = [];
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const stream = client.subscribeTx();
|
||||
const subscription = stream.subscribe({
|
||||
next: (event) => {
|
||||
@ -738,7 +785,7 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
const transactionData2 = buildKvTx(randomString(), randomString());
|
||||
|
||||
const events: responses.TxEvent[] = [];
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const query = buildQuery({ tags: [{ key: "app.creator", value: expected.appCreator }] });
|
||||
const stream = client.subscribeTx(query);
|
||||
expect(stream).toBeTruthy();
|
||||
@ -776,7 +823,7 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
it("can unsubscribe and re-subscribe to the same stream", async () => {
|
||||
pendingWithoutTendermint();
|
||||
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const stream = client.subscribeNewBlockHeader();
|
||||
|
||||
const event1 = await firstEvent(stream);
|
||||
@ -809,7 +856,7 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
it("can subscribe twice", async () => {
|
||||
pendingWithoutTendermint();
|
||||
|
||||
const client = await Tendermint35Client.create(rpcFactory());
|
||||
const client = await Tendermint37Client.create(rpcFactory());
|
||||
const stream1 = client.subscribeNewBlockHeader();
|
||||
const stream2 = client.subscribeNewBlockHeader();
|
||||
|
||||
@ -821,15 +868,15 @@ function websocketTestSuite(rpcFactory: () => RpcClient, expected: ExpectedValue
|
||||
});
|
||||
}
|
||||
|
||||
describe("Tendermint35Client", () => {
|
||||
const { url, expected } = tendermintInstances[35];
|
||||
describe("Tendermint37Client", () => {
|
||||
const { url, expected } = tendermintInstances[37];
|
||||
|
||||
it("can connect to a given url", async () => {
|
||||
pendingWithoutTendermint();
|
||||
|
||||
// default connection
|
||||
{
|
||||
const client = await Tendermint35Client.connect(url);
|
||||
const client = await Tendermint37Client.connect(url);
|
||||
const info = await client.abciInfo();
|
||||
expect(info).toBeTruthy();
|
||||
client.disconnect();
|
||||
@ -837,7 +884,7 @@ describe("Tendermint35Client", () => {
|
||||
|
||||
// http connection
|
||||
{
|
||||
const client = await Tendermint35Client.connect("http://" + url);
|
||||
const client = await Tendermint37Client.connect("http://" + url);
|
||||
const info = await client.abciInfo();
|
||||
expect(info).toBeTruthy();
|
||||
client.disconnect();
|
||||
@ -845,7 +892,7 @@ describe("Tendermint35Client", () => {
|
||||
|
||||
// ws connection
|
||||
{
|
||||
const client = await Tendermint35Client.connect("ws://" + url);
|
||||
const client = await Tendermint37Client.connect("ws://" + url);
|
||||
const info = await client.abciInfo();
|
||||
expect(info).toBeTruthy();
|
||||
client.disconnect();
|
@ -10,41 +10,36 @@ import {
|
||||
SubscriptionEvent,
|
||||
WebsocketClient,
|
||||
} from "../rpcclients";
|
||||
import { adaptor35, Decoder, Encoder, Params, Responses } from "./adaptor";
|
||||
import { adaptor37, Decoder, Encoder, Params, Responses } from "./adaptor";
|
||||
import * as requests from "./requests";
|
||||
import * as responses from "./responses";
|
||||
|
||||
/**
|
||||
* Please note the Tendermint 0.35 client is currently not exported and may break or be removed at any point in time.
|
||||
*
|
||||
* @see https://github.com/cosmos/cosmjs/issues/1225
|
||||
*/
|
||||
export class Tendermint35Client {
|
||||
export class Tendermint37Client {
|
||||
/**
|
||||
* Creates a new Tendermint client for the given endpoint.
|
||||
*
|
||||
* Uses HTTP when the URL schema is http or https. Uses WebSockets otherwise.
|
||||
*/
|
||||
public static async connect(endpoint: string | HttpEndpoint): Promise<Tendermint35Client> {
|
||||
public static async connect(endpoint: string | HttpEndpoint): Promise<Tendermint37Client> {
|
||||
if (typeof endpoint === "object") {
|
||||
return Tendermint35Client.create(new HttpClient(endpoint));
|
||||
return Tendermint37Client.create(new HttpClient(endpoint));
|
||||
} else {
|
||||
const useHttp = endpoint.startsWith("http://") || endpoint.startsWith("https://");
|
||||
const rpcClient = useHttp ? new HttpClient(endpoint) : new WebsocketClient(endpoint);
|
||||
return Tendermint35Client.create(rpcClient);
|
||||
return Tendermint37Client.create(rpcClient);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new Tendermint client given an RPC client.
|
||||
*/
|
||||
public static async create(rpcClient: RpcClient): Promise<Tendermint35Client> {
|
||||
public static async create(rpcClient: RpcClient): Promise<Tendermint37Client> {
|
||||
// For some very strange reason I don't understand, tests start to fail on some systems
|
||||
// (our CI) when skipping the status call before doing other queries. Sleeping a little
|
||||
// while did not help. Thus we query the version as a way to say "hi" to the backend,
|
||||
// even in cases where we don't use the result.
|
||||
const _version = await this.detectVersion(rpcClient);
|
||||
return new Tendermint35Client(rpcClient);
|
||||
return new Tendermint37Client(rpcClient);
|
||||
}
|
||||
|
||||
private static async detectVersion(client: RpcClient): Promise<string> {
|
||||
@ -68,12 +63,12 @@ export class Tendermint35Client {
|
||||
private readonly r: Responses;
|
||||
|
||||
/**
|
||||
* Use `Tendermint34Client.connect` or `Tendermint34Client.create` to create an instance.
|
||||
* Use `Tendermint37Client.connect` or `Tendermint37Client.create` to create an instance.
|
||||
*/
|
||||
private constructor(client: RpcClient) {
|
||||
this.client = client;
|
||||
this.p = adaptor35.params;
|
||||
this.r = adaptor35.responses;
|
||||
this.p = adaptor37.params;
|
||||
this.r = adaptor37.responses;
|
||||
}
|
||||
|
||||
public disconnect(): void {
|
13
packages/tendermint-rpc/src/tendermintclient.ts
Normal file
13
packages/tendermint-rpc/src/tendermintclient.ts
Normal file
@ -0,0 +1,13 @@
|
||||
import { Tendermint34Client } from "./tendermint34";
|
||||
import { Tendermint37Client } from "./tendermint37";
|
||||
|
||||
/** A TendermintClient is either a Tendermint34Client or a Tendermint37Client */
|
||||
export type TendermintClient = Tendermint34Client | Tendermint37Client;
|
||||
|
||||
export function isTendermint34Client(client: TendermintClient): client is Tendermint34Client {
|
||||
return client instanceof Tendermint34Client;
|
||||
}
|
||||
|
||||
export function isTendermint37Client(client: TendermintClient): client is Tendermint37Client {
|
||||
return client instanceof Tendermint37Client;
|
||||
}
|
@ -49,13 +49,13 @@ export const tendermintInstances = {
|
||||
appVersion: 1,
|
||||
},
|
||||
},
|
||||
35: {
|
||||
url: "localhost:11135",
|
||||
version: "0.35.x",
|
||||
37: {
|
||||
url: "localhost:11137",
|
||||
version: "0.37.x",
|
||||
blockTime: 500,
|
||||
expected: {
|
||||
chainId: /^dockerchain$/,
|
||||
version: /^$/, // Unfortunately we don't get info here
|
||||
version: /^0\.37\.0-alpha\.3$/,
|
||||
appCreator: "Cosmoshi Netowoko",
|
||||
p2pVersion: 8,
|
||||
blockVersion: 11,
|
||||
|
@ -2,18 +2,25 @@
|
||||
set -o errexit -o nounset -o pipefail
|
||||
command -v shellcheck >/dev/null && shellcheck "$0"
|
||||
|
||||
# Find latest patch releases at https://hub.docker.com/r/tendermint/tendermint/tags/
|
||||
declare -a TM_VERSIONS
|
||||
TM_VERSIONS[34]=v0.34.19
|
||||
TM_VERSIONS[35]=v0.35.6
|
||||
# Find latest patch releases at
|
||||
# - https://hub.docker.com/r/tendermint/tendermint/tags/
|
||||
# - https://hub.docker.com/r/cometbft/cometbft/tags/
|
||||
declare -a TM_IMAGES
|
||||
TM_IMAGES[34]="tendermint/tendermint:v0.34.19"
|
||||
TM_IMAGES[37]="cometbft/cometbft:v0.37.0-rc3"
|
||||
|
||||
declare -a TM_ROOTS
|
||||
TM_ROOTS[34]="/tendermint"
|
||||
TM_ROOTS[37]="/cometbft"
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
|
||||
for KEY in "${!TM_VERSIONS[@]}"; do
|
||||
export TENDERMINT_VERSION="${TM_VERSIONS[$KEY]}"
|
||||
for KEY in "${!TM_IMAGES[@]}"; do
|
||||
export TENDERMINT_IMAGE="${TM_IMAGES[$KEY]}"
|
||||
export TENDERMINT_ROOT="${TM_ROOTS[$KEY]}"
|
||||
export TENDERMINT_PORT="111$KEY"
|
||||
export TENDERMINT_NAME="tendermint-$KEY"
|
||||
|
||||
echo "Starting $TENDERMINT_NAME ($TENDERMINT_VERSION) on port $TENDERMINT_PORT ..."
|
||||
echo "Starting $TENDERMINT_NAME ($TENDERMINT_IMAGE) on port $TENDERMINT_PORT ..."
|
||||
"$SCRIPT_DIR/start.sh"
|
||||
done
|
||||
|
@ -2,13 +2,9 @@
|
||||
set -o errexit -o nounset -o pipefail
|
||||
command -v shellcheck >/dev/null && shellcheck "$0"
|
||||
|
||||
declare -a TM_VERSIONS
|
||||
TM_VERSIONS[34]=v0.34.19
|
||||
TM_VERSIONS[35]=v0.35.6
|
||||
|
||||
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
|
||||
for KEY in "${!TM_VERSIONS[@]}"; do
|
||||
for KEY in 34 37; do
|
||||
export TENDERMINT_NAME="tendermint-$KEY"
|
||||
|
||||
echo "Stopping $TENDERMINT_NAME ..."
|
||||
|
@ -6,7 +6,7 @@ gnused="$(command -v gsed || echo sed)"
|
||||
|
||||
# Tendermint settings must be specified
|
||||
# Choose version from https://hub.docker.com/r/tendermint/tendermint/tags/
|
||||
for SETTING in "TENDERMINT_VERSION" "TENDERMINT_PORT" "TENDERMINT_NAME"; do
|
||||
for SETTING in "TENDERMINT_IMAGE" "TENDERMINT_PORT" "TENDERMINT_NAME"; do
|
||||
if test -z "$(eval echo "\$$SETTING")"; then
|
||||
echo "\$$SETTING must be set when running this script"
|
||||
exit 1
|
||||
@ -20,8 +20,8 @@ LOGFILE="$TMP_DIR/tendermint.log"
|
||||
|
||||
docker run --rm \
|
||||
--user="$UID" \
|
||||
-v "${TMP_DIR}:/tendermint" \
|
||||
"tendermint/tendermint:${TENDERMINT_VERSION}" \
|
||||
-v "${TMP_DIR}:${TENDERMINT_ROOT}" \
|
||||
"${TENDERMINT_IMAGE}" \
|
||||
init validator
|
||||
|
||||
# make sure we allow cors origins, only possible by modifying the config file
|
||||
@ -36,11 +36,11 @@ docker run --rm \
|
||||
docker run --rm \
|
||||
--user="$UID" \
|
||||
--name "$TENDERMINT_NAME" \
|
||||
-p "${TENDERMINT_PORT}:26657" -v "${TMP_DIR}:/tendermint" \
|
||||
-p "${TENDERMINT_PORT}:26657" -v "${TMP_DIR}:${TENDERMINT_ROOT}" \
|
||||
-e "TM_TX_INDEX_INDEX_ALL_KEYS=true" \
|
||||
-e "PROXY_APP=kvstore" \
|
||||
-e "LOG_LEVEL=state:info,rpc:info,*:error" \
|
||||
"tendermint/tendermint:${TENDERMINT_VERSION}" node \
|
||||
"${TENDERMINT_IMAGE}" node \
|
||||
--rpc.laddr=tcp://0.0.0.0:26657 \
|
||||
>"$LOGFILE" 2>&1 &
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user