@dedot/contracts 0.12.1-next.f19f185a.2 → 0.13.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Contract.d.ts +4 -4
- package/Contract.js +41 -6
- package/ContractDeployer.d.ts +2 -2
- package/ContractDeployer.js +8 -6
- package/TypinkRegistry.d.ts +29 -6
- package/TypinkRegistry.js +144 -24
- package/cjs/Contract.js +44 -9
- package/cjs/ContractDeployer.js +10 -8
- package/cjs/TypinkRegistry.js +144 -24
- package/cjs/errors.js +3 -3
- package/cjs/executor/ConstructorQueryExecutor.js +49 -9
- package/cjs/executor/ConstructorTxExecutor.js +17 -6
- package/cjs/executor/QueryExecutor.js +30 -5
- package/cjs/executor/TxExecutor.js +10 -1
- package/cjs/executor/abstract/ContractExecutor.js +4 -5
- package/cjs/executor/abstract/DeployerExecutor.js +2 -2
- package/cjs/index.js +1 -1
- package/cjs/storage/BaseLazyObject.js +25 -0
- package/cjs/storage/LazyMapping.js +22 -0
- package/cjs/storage/LazyObject.js +18 -0
- package/cjs/storage/LazyStorageVec.js +54 -0
- package/cjs/storage/index.js +19 -0
- package/cjs/types/index.js +3 -0
- package/cjs/types/v6.js +2 -0
- package/cjs/utils/address.js +67 -0
- package/cjs/utils/ensure.js +68 -0
- package/cjs/utils/index.js +21 -0
- package/cjs/utils/proxy.js +11 -0
- package/cjs/utils/storage.js +44 -0
- package/cjs/{utils.js → utils/types.js} +31 -34
- package/errors.js +2 -2
- package/executor/ConstructorQueryExecutor.js +47 -7
- package/executor/ConstructorTxExecutor.js +18 -7
- package/executor/QueryExecutor.js +27 -2
- package/executor/TxExecutor.js +11 -2
- package/executor/abstract/ContractExecutor.d.ts +3 -4
- package/executor/abstract/ContractExecutor.js +2 -3
- package/executor/abstract/DeployerExecutor.js +1 -1
- package/index.d.ts +1 -1
- package/index.js +1 -1
- package/package.json +7 -6
- package/storage/BaseLazyObject.d.ts +10 -0
- package/storage/BaseLazyObject.js +21 -0
- package/storage/LazyMapping.d.ts +4 -0
- package/storage/LazyMapping.js +18 -0
- package/storage/LazyObject.d.ts +4 -0
- package/storage/LazyObject.js +14 -0
- package/storage/LazyStorageVec.d.ts +5 -0
- package/storage/LazyStorageVec.js +27 -0
- package/storage/index.d.ts +3 -0
- package/storage/index.js +3 -0
- package/types/index.d.ts +73 -11
- package/types/index.js +3 -0
- package/types/shared.d.ts +6 -18
- package/types/v4.d.ts +47 -3
- package/types/v5.d.ts +43 -4
- package/types/v6.d.ts +13 -0
- package/types/v6.js +1 -0
- package/utils/address.d.ts +30 -0
- package/utils/address.js +61 -0
- package/utils/ensure.d.ts +12 -0
- package/utils/ensure.js +59 -0
- package/utils/index.d.ts +5 -0
- package/utils/index.js +5 -0
- package/utils/proxy.d.ts +3 -0
- package/utils/proxy.js +7 -0
- package/utils/storage.d.ts +2 -0
- package/utils/storage.js +40 -0
- package/utils/types.d.ts +17 -0
- package/{utils.js → utils/types.js} +29 -30
- package/utils.d.ts +0 -13
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { concatU8a, toU8a } from '@dedot/utils';
|
|
2
|
+
import { BaseLazyObject } from './BaseLazyObject.js';
|
|
3
|
+
export class LazyMapping extends BaseLazyObject {
|
|
4
|
+
async get(key) {
|
|
5
|
+
const { id, type: { params }, } = this.typeDef;
|
|
6
|
+
const [keyType, valueType] = params;
|
|
7
|
+
const $Key = this.registry.findCodec(keyType.type);
|
|
8
|
+
const $Value = this.registry.findCodec(valueType.type);
|
|
9
|
+
const rootKey = this.findStorageRootLayout(id);
|
|
10
|
+
const encodedKey = $Key.tryEncode(key);
|
|
11
|
+
const storageKey = concatU8a(toU8a(rootKey), encodedKey);
|
|
12
|
+
const rawValue = await this.getContractStorage(storageKey);
|
|
13
|
+
if (rawValue) {
|
|
14
|
+
return $Value.tryDecode(rawValue);
|
|
15
|
+
}
|
|
16
|
+
return undefined;
|
|
17
|
+
}
|
|
18
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { BaseLazyObject } from './BaseLazyObject.js';
|
|
2
|
+
export class LazyObject extends BaseLazyObject {
|
|
3
|
+
async get() {
|
|
4
|
+
const { id, type: { params }, } = this.typeDef;
|
|
5
|
+
const [valueType] = params;
|
|
6
|
+
const $Value = this.registry.findCodec(valueType.type);
|
|
7
|
+
const rootKey = this.findStorageRootLayout(id);
|
|
8
|
+
const rawValue = await this.getContractStorage(rootKey);
|
|
9
|
+
if (rawValue) {
|
|
10
|
+
return $Value.tryDecode(rawValue);
|
|
11
|
+
}
|
|
12
|
+
return undefined;
|
|
13
|
+
}
|
|
14
|
+
}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import * as $ from '@dedot/shape';
|
|
2
|
+
import { concatU8a, toU8a } from '@dedot/utils';
|
|
3
|
+
import { BaseLazyObject } from './BaseLazyObject.js';
|
|
4
|
+
export class LazyStorageVec extends BaseLazyObject {
|
|
5
|
+
async len() {
|
|
6
|
+
const { id } = this.typeDef;
|
|
7
|
+
const rootKey = this.findStorageRootLayout(id);
|
|
8
|
+
const rawValue = await this.getContractStorage(rootKey);
|
|
9
|
+
if (rawValue) {
|
|
10
|
+
return $.u32.tryDecode(rawValue);
|
|
11
|
+
}
|
|
12
|
+
return 0;
|
|
13
|
+
}
|
|
14
|
+
async get(index) {
|
|
15
|
+
const { id, type: { params }, } = this.typeDef;
|
|
16
|
+
const [valueType] = params;
|
|
17
|
+
const $Value = this.registry.findCodec(valueType.type);
|
|
18
|
+
const rootKey = this.findStorageRootLayout(id);
|
|
19
|
+
const encodedKey = $.u32.tryEncode(index);
|
|
20
|
+
const storageKey = concatU8a(toU8a(rootKey), encodedKey);
|
|
21
|
+
const rawValue = await this.getContractStorage(storageKey);
|
|
22
|
+
if (rawValue) {
|
|
23
|
+
return $Value.tryDecode(rawValue);
|
|
24
|
+
}
|
|
25
|
+
return undefined;
|
|
26
|
+
}
|
|
27
|
+
}
|
package/storage/index.js
ADDED
package/types/index.d.ts
CHANGED
|
@@ -1,10 +1,14 @@
|
|
|
1
1
|
import { SubstrateApi } from '@dedot/api/chaintypes';
|
|
2
|
-
import {
|
|
3
|
-
import { AnyFunc, AsyncMethod, GenericSubstrateApi, IEventRecord, RpcVersion, Unsub, VersionedGenericSubstrateApi } from '@dedot/types';
|
|
4
|
-
import { ContractCallMessage, ContractConstructorMessage } from './shared.js';
|
|
2
|
+
import { AccountId32Like, type Bytes, BytesLike, type DispatchError, Extrinsic, type H256, type Result, Weight } from '@dedot/codecs';
|
|
3
|
+
import { AnyFunc, AsyncMethod, GenericSubstrateApi, IEventRecord, ISubmittableExtrinsic, RpcVersion, Unsub, VersionedGenericSubstrateApi } from '@dedot/types';
|
|
4
|
+
import { ContractAddress, ContractCallMessage, ContractConstructorMessage } from './shared.js';
|
|
5
5
|
import { ContractEventV4, ContractMetadataV4 } from './v4.js';
|
|
6
6
|
import { ContractEventV5, ContractMetadataV5 } from './v5.js';
|
|
7
|
+
import { ContractMetadataV6 } from './v6.js';
|
|
7
8
|
export * from './shared.js';
|
|
9
|
+
export * from './v4.js';
|
|
10
|
+
export * from './v5.js';
|
|
11
|
+
export * from './v6.js';
|
|
8
12
|
export type ContractEventMeta = ContractEventV4 | ContractEventV5;
|
|
9
13
|
/**
|
|
10
14
|
* Flags used by a contract to customize exit behaviour.
|
|
@@ -18,17 +22,61 @@ export interface GenericContractCallResult<DecodedData = any, ContractResult = a
|
|
|
18
22
|
data: DecodedData;
|
|
19
23
|
raw: ContractResult;
|
|
20
24
|
flags: ReturnFlags;
|
|
25
|
+
inputData: Bytes;
|
|
21
26
|
}
|
|
22
27
|
export interface GenericConstructorCallResult<DecodedData = any, ContractResult = any> extends GenericContractCallResult<DecodedData, ContractResult> {
|
|
23
|
-
address:
|
|
28
|
+
address: ContractAddress;
|
|
29
|
+
}
|
|
30
|
+
export type ContractCode = {
|
|
31
|
+
type: 'Upload';
|
|
32
|
+
value: Bytes;
|
|
33
|
+
} | {
|
|
34
|
+
type: 'Existing';
|
|
35
|
+
value: H256;
|
|
36
|
+
};
|
|
37
|
+
export type WeightV2 = {
|
|
38
|
+
refTime: bigint;
|
|
39
|
+
proofSize: bigint;
|
|
40
|
+
};
|
|
41
|
+
export type StorageDeposit = {
|
|
42
|
+
type: 'Refund';
|
|
43
|
+
value: bigint;
|
|
44
|
+
} | {
|
|
45
|
+
type: 'Charge';
|
|
46
|
+
value: bigint;
|
|
47
|
+
};
|
|
48
|
+
export type ExecReturnValue = {
|
|
49
|
+
flags: {
|
|
50
|
+
bits: number;
|
|
51
|
+
};
|
|
52
|
+
data: Bytes;
|
|
53
|
+
};
|
|
54
|
+
export type InstantiateReturnValue = {
|
|
55
|
+
result: ExecReturnValue;
|
|
56
|
+
address: ContractAddress;
|
|
57
|
+
};
|
|
58
|
+
export type ContractCallResult<_ extends GenericSubstrateApi> = {
|
|
59
|
+
gasConsumed: WeightV2;
|
|
60
|
+
gasRequired: WeightV2;
|
|
61
|
+
storageDeposit: StorageDeposit;
|
|
62
|
+
debugMessage?: Bytes;
|
|
63
|
+
result: Result<ExecReturnValue, DispatchError>;
|
|
64
|
+
};
|
|
65
|
+
export type ContractInstantiateResult<_ extends GenericSubstrateApi> = {
|
|
66
|
+
gasConsumed: WeightV2;
|
|
67
|
+
gasRequired: WeightV2;
|
|
68
|
+
storageDeposit: StorageDeposit;
|
|
69
|
+
debugMessage?: Bytes;
|
|
70
|
+
result: Result<InstantiateReturnValue, DispatchError>;
|
|
71
|
+
};
|
|
72
|
+
type SubmittableExtrinsic = ISubmittableExtrinsic & Extrinsic;
|
|
73
|
+
export type ContractSubmittableExtrinsic<_ extends GenericSubstrateApi> = SubmittableExtrinsic;
|
|
74
|
+
export type GenericInstantiateSubmittableExtrinsic<_ extends GenericSubstrateApi> = SubmittableExtrinsic;
|
|
75
|
+
export type ContractMetadata = ContractMetadataV4 | ContractMetadataV5 | ContractMetadataV6;
|
|
76
|
+
export interface LooseContractMetadata {
|
|
77
|
+
version: number | string;
|
|
78
|
+
[prop: string]: any;
|
|
24
79
|
}
|
|
25
|
-
export type ContractCallResult<ChainApi extends GenericSubstrateApi> = Awaited<ReturnType<ChainApi['call']['contractsApi']['call']>>;
|
|
26
|
-
export type ContractInstantiateResult<ChainApi extends GenericSubstrateApi> = Awaited<ReturnType<ChainApi['call']['contractsApi']['instantiate']>>;
|
|
27
|
-
export type ContractSubmittableExtrinsic<ChainApi extends GenericSubstrateApi> = ReturnType<ChainApi['tx']['contracts']['call']>;
|
|
28
|
-
export type InstantiateWithCodeSubmittableExtrinsic<ChainApi extends GenericSubstrateApi> = ReturnType<ChainApi['tx']['contracts']['instantiateWithCode']>;
|
|
29
|
-
export type InstantiateSubmittableExtrinsic<ChainApi extends GenericSubstrateApi> = ReturnType<ChainApi['tx']['contracts']['instantiate']>;
|
|
30
|
-
export type GenericInstantiateSubmittableExtrinsic<ChainApi extends GenericSubstrateApi> = InstantiateSubmittableExtrinsic<ChainApi> | InstantiateWithCodeSubmittableExtrinsic<ChainApi>;
|
|
31
|
-
export type ContractMetadata = ContractMetadataV4 | ContractMetadataV5;
|
|
32
80
|
export type CallOptions = {
|
|
33
81
|
value?: bigint;
|
|
34
82
|
gasLimit?: Weight | undefined;
|
|
@@ -89,13 +137,21 @@ export interface GenericContractEvents<_ extends GenericSubstrateApi> {
|
|
|
89
137
|
[event: string]: GenericContractEvent;
|
|
90
138
|
}
|
|
91
139
|
export type GenericInkLangError = 'CouldNotReadInput' | any;
|
|
140
|
+
export type GenericRootStorage = any;
|
|
141
|
+
export type GenericLazyStorage = any;
|
|
92
142
|
export interface GenericContractApi<Rv extends RpcVersion = RpcVersion, ChainApi extends VersionedGenericSubstrateApi = SubstrateApi> {
|
|
93
143
|
query: GenericContractQuery<ChainApi[Rv]>;
|
|
94
144
|
tx: GenericContractTx<ChainApi[Rv]>;
|
|
95
145
|
constructorQuery: GenericConstructorQuery<ChainApi[Rv]>;
|
|
96
146
|
constructorTx: GenericConstructorTx<ChainApi[Rv]>;
|
|
97
147
|
events: GenericContractEvents<ChainApi[Rv]>;
|
|
148
|
+
storage: {
|
|
149
|
+
root(): Promise<GenericRootStorage>;
|
|
150
|
+
lazy(): GenericLazyStorage;
|
|
151
|
+
};
|
|
98
152
|
types: {
|
|
153
|
+
RootStorage: GenericRootStorage;
|
|
154
|
+
LazyStorage: GenericLazyStorage;
|
|
99
155
|
LangError: GenericInkLangError;
|
|
100
156
|
ChainApi: ChainApi[Rv];
|
|
101
157
|
};
|
|
@@ -103,3 +159,9 @@ export interface GenericContractApi<Rv extends RpcVersion = RpcVersion, ChainApi
|
|
|
103
159
|
export interface ExecutionOptions {
|
|
104
160
|
defaultCaller?: AccountId32Like;
|
|
105
161
|
}
|
|
162
|
+
type HasGetter<T> = T extends {
|
|
163
|
+
get: (...args: any[]) => any;
|
|
164
|
+
} ? true : false;
|
|
165
|
+
export type WithLazyStorage<T> = {
|
|
166
|
+
[K in keyof T as HasGetter<T[K]> extends true ? K : T[K] extends object ? keyof WithLazyStorage<T[K]> extends never ? never : K : never]: T[K] extends object ? HasGetter<T[K]> extends true ? T[K] : WithLazyStorage<T[K]> : never;
|
|
167
|
+
};
|
package/types/index.js
CHANGED
package/types/shared.d.ts
CHANGED
|
@@ -1,20 +1,19 @@
|
|
|
1
|
+
export type ContractAddress = string;
|
|
2
|
+
export interface ContractInformation {
|
|
3
|
+
name: string;
|
|
4
|
+
version: string;
|
|
5
|
+
authors: string[];
|
|
6
|
+
}
|
|
1
7
|
export interface ContractSource {
|
|
2
8
|
hash: string;
|
|
3
|
-
wasm?: string;
|
|
4
9
|
language: string;
|
|
5
10
|
compiler: string;
|
|
6
11
|
build_info: BuildInfo;
|
|
7
12
|
}
|
|
8
|
-
export interface ContractInformation {
|
|
9
|
-
name: string;
|
|
10
|
-
version: string;
|
|
11
|
-
authors: string[];
|
|
12
|
-
}
|
|
13
13
|
export interface BuildInfo {
|
|
14
14
|
build_mode: string;
|
|
15
15
|
cargo_contract_version: string;
|
|
16
16
|
rust_toolchain: string;
|
|
17
|
-
wasm_opt_settings: WasmOptSettings;
|
|
18
17
|
}
|
|
19
18
|
export interface WasmOptSettings {
|
|
20
19
|
keep_debug_symbols: boolean;
|
|
@@ -96,17 +95,6 @@ export interface ParamInfo {
|
|
|
96
95
|
name: string;
|
|
97
96
|
type: number;
|
|
98
97
|
}
|
|
99
|
-
export interface ContractStorage {
|
|
100
|
-
root: {
|
|
101
|
-
layout: {
|
|
102
|
-
struct: {
|
|
103
|
-
fields: any[];
|
|
104
|
-
name: string;
|
|
105
|
-
};
|
|
106
|
-
};
|
|
107
|
-
root_key: string;
|
|
108
|
-
};
|
|
109
|
-
}
|
|
110
98
|
export interface ContractEventArg extends ContractMessageArg {
|
|
111
99
|
docs: string[];
|
|
112
100
|
indexed: boolean;
|
package/types/v4.d.ts
CHANGED
|
@@ -1,12 +1,18 @@
|
|
|
1
|
-
import { ContractConstructorMessage, ContractEventArg, ContractInformation,
|
|
1
|
+
import { BuildInfo, ContractCallMessage, ContractConstructorMessage, ContractEventArg, ContractInformation, ContractSource, ContractType, ContractTypeInfo, WasmOptSettings } from './shared.js';
|
|
2
2
|
export interface ContractMetadataV4 {
|
|
3
|
-
source:
|
|
3
|
+
source: ContractSourceV4;
|
|
4
4
|
contract: ContractInformation;
|
|
5
5
|
spec: ContractSpecV4;
|
|
6
|
-
storage:
|
|
6
|
+
storage: ContractStorageV4;
|
|
7
7
|
types: ContractType[];
|
|
8
8
|
version: '4';
|
|
9
9
|
}
|
|
10
|
+
export interface ContractSourceV4 extends ContractSource {
|
|
11
|
+
wasm?: string;
|
|
12
|
+
build_info: BuildInfo & {
|
|
13
|
+
wasm_opt_settings: WasmOptSettings;
|
|
14
|
+
};
|
|
15
|
+
}
|
|
10
16
|
export interface ContractSpecV4 {
|
|
11
17
|
constructors: ContractConstructorMessage[];
|
|
12
18
|
docs: string[];
|
|
@@ -29,3 +35,41 @@ export interface ContractEnvironmentV4 {
|
|
|
29
35
|
maxEventTopics: number;
|
|
30
36
|
timestamp: ContractTypeInfo;
|
|
31
37
|
}
|
|
38
|
+
export interface StructLayoutV4 {
|
|
39
|
+
name: string;
|
|
40
|
+
fields: {
|
|
41
|
+
name: string;
|
|
42
|
+
layout: AnyLayoutV4;
|
|
43
|
+
}[];
|
|
44
|
+
}
|
|
45
|
+
export interface LeafLayoutV4 {
|
|
46
|
+
key: string;
|
|
47
|
+
ty: number;
|
|
48
|
+
}
|
|
49
|
+
export interface HashLayoutV4 {
|
|
50
|
+
}
|
|
51
|
+
export interface ArrayLayoutV4 {
|
|
52
|
+
offset: string;
|
|
53
|
+
len: number;
|
|
54
|
+
layout: AnyLayoutV4;
|
|
55
|
+
}
|
|
56
|
+
export interface EnumLayoutV4 {
|
|
57
|
+
name: string;
|
|
58
|
+
dispatch_key: string;
|
|
59
|
+
variants: Record<number, StructLayoutV4>;
|
|
60
|
+
}
|
|
61
|
+
export interface RootLayoutV4 {
|
|
62
|
+
root_key: string;
|
|
63
|
+
layout: AnyLayoutV4;
|
|
64
|
+
}
|
|
65
|
+
export type AnyLayoutV4 = {
|
|
66
|
+
struct?: StructLayoutV4;
|
|
67
|
+
leaf?: LeafLayoutV4;
|
|
68
|
+
hash?: HashLayoutV4;
|
|
69
|
+
array?: ArrayLayoutV4;
|
|
70
|
+
enum?: EnumLayoutV4;
|
|
71
|
+
root?: RootLayoutV4;
|
|
72
|
+
};
|
|
73
|
+
export interface ContractStorageV4 {
|
|
74
|
+
root: RootLayoutV4;
|
|
75
|
+
}
|
package/types/v5.d.ts
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import { ContractInformation,
|
|
2
|
-
import { ContractEnvironmentV4, ContractEventV4, ContractSpecV4 } from './v4.js';
|
|
1
|
+
import { ContractInformation, ContractType } from './shared.js';
|
|
2
|
+
import { ContractEnvironmentV4, ContractEventV4, ContractSourceV4, ContractSpecV4 } from './v4.js';
|
|
3
3
|
export interface ContractMetadataV5 {
|
|
4
|
-
source:
|
|
4
|
+
source: ContractSourceV4;
|
|
5
5
|
contract: ContractInformation;
|
|
6
6
|
spec: ContractSpecV5;
|
|
7
|
-
storage:
|
|
7
|
+
storage: ContractStorageV5;
|
|
8
8
|
types: ContractType[];
|
|
9
9
|
version: 5;
|
|
10
10
|
}
|
|
@@ -19,3 +19,42 @@ export interface ContractEventV5 extends ContractEventV4 {
|
|
|
19
19
|
export interface ContractEnvironmentV5 extends ContractEnvironmentV4 {
|
|
20
20
|
staticBufferSize: number;
|
|
21
21
|
}
|
|
22
|
+
export interface StructLayoutV5 {
|
|
23
|
+
name: string;
|
|
24
|
+
fields: {
|
|
25
|
+
name: string;
|
|
26
|
+
layout: AnyLayoutV5;
|
|
27
|
+
}[];
|
|
28
|
+
}
|
|
29
|
+
export interface LeafLayoutV5 {
|
|
30
|
+
key: string;
|
|
31
|
+
ty: number;
|
|
32
|
+
}
|
|
33
|
+
export interface HashLayoutV5 {
|
|
34
|
+
}
|
|
35
|
+
export interface ArrayLayoutV5 {
|
|
36
|
+
offset: string;
|
|
37
|
+
len: number;
|
|
38
|
+
layout: AnyLayoutV5;
|
|
39
|
+
}
|
|
40
|
+
export interface EnumLayoutV5 {
|
|
41
|
+
name: string;
|
|
42
|
+
dispatch_key: string;
|
|
43
|
+
variants: Record<number, StructLayoutV5>;
|
|
44
|
+
}
|
|
45
|
+
export interface RootLayoutV5 {
|
|
46
|
+
root_key: string;
|
|
47
|
+
layout: AnyLayoutV5;
|
|
48
|
+
ty: number;
|
|
49
|
+
}
|
|
50
|
+
export type AnyLayoutV5 = {
|
|
51
|
+
struct?: StructLayoutV5;
|
|
52
|
+
leaf?: LeafLayoutV5;
|
|
53
|
+
hash?: HashLayoutV5;
|
|
54
|
+
array?: ArrayLayoutV5;
|
|
55
|
+
enum?: EnumLayoutV5;
|
|
56
|
+
root?: RootLayoutV5;
|
|
57
|
+
};
|
|
58
|
+
export interface ContractStorageV5 {
|
|
59
|
+
root: RootLayoutV5;
|
|
60
|
+
}
|
package/types/v6.d.ts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { ContractInformation, ContractSource, ContractType } from './shared';
|
|
2
|
+
import { ContractSpecV5, ContractStorageV5 } from './v5.js';
|
|
3
|
+
export interface ContractSourceV6 extends ContractSource {
|
|
4
|
+
contract_binary?: string;
|
|
5
|
+
}
|
|
6
|
+
export interface ContractMetadataV6 {
|
|
7
|
+
source: ContractSourceV6;
|
|
8
|
+
contract: ContractInformation;
|
|
9
|
+
spec: ContractSpecV5;
|
|
10
|
+
storage: ContractStorageV5;
|
|
11
|
+
types: ContractType[];
|
|
12
|
+
version: 6;
|
|
13
|
+
}
|
package/types/v6.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { AccountId20Like, AccountId32Like, BytesLike } from '@dedot/codecs';
|
|
2
|
+
import { HexString } from '@dedot/utils';
|
|
3
|
+
/**
|
|
4
|
+
* Calculate new contract's address is based on the deployer's address and a nonce
|
|
5
|
+
*
|
|
6
|
+
* Ref: https://github.com/paritytech/polkadot-sdk/blob/5405e473854b139f1d0735550d90687eaf1a13f9/substrate/frame/revive/src/address.rs#L197-L204
|
|
7
|
+
*
|
|
8
|
+
* @param deployer
|
|
9
|
+
* @param nonce
|
|
10
|
+
*/
|
|
11
|
+
export declare function CREATE1(deployer: AccountId20Like, nonce: number): HexString;
|
|
12
|
+
/**
|
|
13
|
+
* Calculate contract's address deterministically based on the salt, deployer's address, and the code & input data.
|
|
14
|
+
*
|
|
15
|
+
* Ref: https://github.com/paritytech/polkadot-sdk/blob/5405e473854b139f1d0735550d90687eaf1a13f9/substrate/frame/revive/src/address.rs#L206-L219
|
|
16
|
+
*
|
|
17
|
+
* @param deployer
|
|
18
|
+
* @param code
|
|
19
|
+
* @param inputData Input data for the constructor call
|
|
20
|
+
* @param salt Salt for the deployment
|
|
21
|
+
*/
|
|
22
|
+
export declare function CREATE2(deployer: AccountId20Like, code: BytesLike, inputData: BytesLike, salt: BytesLike): HexString;
|
|
23
|
+
/**
|
|
24
|
+
* Convert a substrate address (H256) to an evm address (H160)
|
|
25
|
+
*
|
|
26
|
+
* Ref: https://github.com/paritytech/polkadot-sdk/blob/5405e473854b139f1d0735550d90687eaf1a13f9/substrate/frame/revive/src/address.rs#L101-L113
|
|
27
|
+
*
|
|
28
|
+
* @param accountId
|
|
29
|
+
*/
|
|
30
|
+
export declare function toEvmAddress(accountId: AccountId32Like): HexString;
|
package/utils/address.js
ADDED
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
import { AccountId20, AccountId32 } from '@dedot/codecs';
|
|
2
|
+
import { concatU8a, hexToU8a, keccakAsU8a, toHex, toU8a, u8aToHex } from '@dedot/utils';
|
|
3
|
+
import { RLP } from '@ethereumjs/rlp';
|
|
4
|
+
/**
|
|
5
|
+
* Calculate new contract's address is based on the deployer's address and a nonce
|
|
6
|
+
*
|
|
7
|
+
* Ref: https://github.com/paritytech/polkadot-sdk/blob/5405e473854b139f1d0735550d90687eaf1a13f9/substrate/frame/revive/src/address.rs#L197-L204
|
|
8
|
+
*
|
|
9
|
+
* @param deployer
|
|
10
|
+
* @param nonce
|
|
11
|
+
*/
|
|
12
|
+
export function CREATE1(deployer, nonce) {
|
|
13
|
+
const encodedData = RLP.encode([new AccountId20(deployer).raw, toHex(nonce)]);
|
|
14
|
+
const hash = keccakAsU8a(encodedData);
|
|
15
|
+
return u8aToHex(hash.subarray(12));
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Calculate contract's address deterministically based on the salt, deployer's address, and the code & input data.
|
|
19
|
+
*
|
|
20
|
+
* Ref: https://github.com/paritytech/polkadot-sdk/blob/5405e473854b139f1d0735550d90687eaf1a13f9/substrate/frame/revive/src/address.rs#L206-L219
|
|
21
|
+
*
|
|
22
|
+
* @param deployer
|
|
23
|
+
* @param code
|
|
24
|
+
* @param inputData Input data for the constructor call
|
|
25
|
+
* @param salt Salt for the deployment
|
|
26
|
+
*/
|
|
27
|
+
export function CREATE2(deployer, code, inputData, salt) {
|
|
28
|
+
const initCodeHash = keccakAsU8a(concatU8a(toU8a(code), toU8a(inputData)));
|
|
29
|
+
const bytes = new Uint8Array(1 + (20 + 32 + 32)); // 0xff + deployer + salt + initCodeHash
|
|
30
|
+
bytes[0] = 0xff;
|
|
31
|
+
bytes.set(hexToU8a(new AccountId20(deployer).raw), 1);
|
|
32
|
+
bytes.set(toU8a(salt), 21);
|
|
33
|
+
bytes.set(initCodeHash, 53);
|
|
34
|
+
return u8aToHex(keccakAsU8a(bytes).subarray(12));
|
|
35
|
+
}
|
|
36
|
+
function isEthDerived(accountId) {
|
|
37
|
+
if (accountId.length >= 32) {
|
|
38
|
+
return accountId.slice(20, accountId.length).every((byte) => byte === 0xee);
|
|
39
|
+
}
|
|
40
|
+
return false;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Convert a substrate address (H256) to an evm address (H160)
|
|
44
|
+
*
|
|
45
|
+
* Ref: https://github.com/paritytech/polkadot-sdk/blob/5405e473854b139f1d0735550d90687eaf1a13f9/substrate/frame/revive/src/address.rs#L101-L113
|
|
46
|
+
*
|
|
47
|
+
* @param accountId
|
|
48
|
+
*/
|
|
49
|
+
export function toEvmAddress(accountId) {
|
|
50
|
+
const accountBytes = hexToU8a(new AccountId32(accountId).raw);
|
|
51
|
+
const accountBuffer = new Uint8Array(32);
|
|
52
|
+
accountBuffer.set(accountBytes.slice(0, 32));
|
|
53
|
+
if (isEthDerived(accountBytes)) {
|
|
54
|
+
// This was originally an eth address
|
|
55
|
+
// We just strip the 0xEE suffix to get the original address
|
|
56
|
+
return ('0x' + Buffer.from(accountBuffer.slice(0, 20)).toString('hex'));
|
|
57
|
+
}
|
|
58
|
+
else {
|
|
59
|
+
return u8aToHex(keccakAsU8a(accountBuffer).subarray(12));
|
|
60
|
+
}
|
|
61
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { ISubstrateClient } from '@dedot/api';
|
|
2
|
+
import { SubstrateApi } from '@dedot/api/chaintypes';
|
|
3
|
+
import { Hash } from '@dedot/codecs';
|
|
4
|
+
import { RpcVersion } from '@dedot/types';
|
|
5
|
+
import { TypinkRegistry } from 'src/TypinkRegistry';
|
|
6
|
+
import { ContractAddress, LooseContractMetadata } from 'src/types';
|
|
7
|
+
export declare const ensureStorageApiSupports: (version: string | number) => void;
|
|
8
|
+
export declare function ensurePalletPresence(client: ISubstrateClient<SubstrateApi[RpcVersion]>, registry: TypinkRegistry): void;
|
|
9
|
+
export declare function ensureContractPresence(client: ISubstrateClient<SubstrateApi[RpcVersion]>, registry: TypinkRegistry, address: ContractAddress): Promise<void>;
|
|
10
|
+
export declare function ensureValidContractAddress(address: ContractAddress, registry: TypinkRegistry): void;
|
|
11
|
+
export declare function ensureValidCodeHashOrCode(codeHashOrCode: Hash | Uint8Array | string, registry: TypinkRegistry): void;
|
|
12
|
+
export declare function ensureSupportedContractMetadataVersion(metadata: LooseContractMetadata): void;
|
package/utils/ensure.js
ADDED
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { accountId32ToHex } from '@dedot/codecs';
|
|
2
|
+
import { assert, DedotError, ensurePresence, hexToU8a, isEvmAddress, isPvm, isWasm, toU8a, } from '@dedot/utils';
|
|
3
|
+
export const ensureStorageApiSupports = (version) => {
|
|
4
|
+
const numberedVersion = typeof version === 'number' ? version : parseInt(version);
|
|
5
|
+
assert(numberedVersion >= 5, `Contract Storage Api Only Available for metadata version >= 5, current version: ${version}`);
|
|
6
|
+
};
|
|
7
|
+
export function ensurePalletPresence(client, registry) {
|
|
8
|
+
if (registry.isRevive()) {
|
|
9
|
+
try {
|
|
10
|
+
!!client.call.reviveApi.call.meta && !!client.tx.revive.call.meta;
|
|
11
|
+
}
|
|
12
|
+
catch {
|
|
13
|
+
throw new DedotError('Pallet Revive is not available');
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
else {
|
|
17
|
+
try {
|
|
18
|
+
!!client.call.contractsApi.call.meta && !!client.tx.contracts.call.meta;
|
|
19
|
+
}
|
|
20
|
+
catch {
|
|
21
|
+
throw new DedotError('Pallet Contracts is not available');
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
export async function ensureContractPresence(client, registry, address) {
|
|
26
|
+
const contractInfo = await (() => {
|
|
27
|
+
if (registry.isRevive()) {
|
|
28
|
+
return client.query.revive.contractInfoOf(address);
|
|
29
|
+
}
|
|
30
|
+
else {
|
|
31
|
+
return client.query.contracts.contractInfoOf(address);
|
|
32
|
+
}
|
|
33
|
+
})();
|
|
34
|
+
ensurePresence(contractInfo, `Contract with address ${address} does not exist on chain!`);
|
|
35
|
+
}
|
|
36
|
+
export function ensureValidContractAddress(address, registry) {
|
|
37
|
+
if (registry.isRevive()) {
|
|
38
|
+
assert(isEvmAddress(address), `Invalid contract address: ${address}. Expected an EVM 20-byte address as a hex string or a Uint8Array`);
|
|
39
|
+
}
|
|
40
|
+
else {
|
|
41
|
+
assert(hexToU8a(accountId32ToHex(address)).length === 32, `Invalid contract address: ${address}. Expected a Substrate 32-byte address as a hex string or a Uint8Array`);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
export function ensureValidCodeHashOrCode(codeHashOrCode, registry) {
|
|
45
|
+
assert(toU8a(codeHashOrCode).length === 32 || (registry.isRevive() ? isPvm(codeHashOrCode) : isWasm(codeHashOrCode)), 'Invalid code hash or code: expected a hash of 32-byte or a valid PVM/WASM code as a hex string or a Uint8Array');
|
|
46
|
+
}
|
|
47
|
+
const UNSUPPORTED_VERSIONS = ['V3', 'V2', 'V1'];
|
|
48
|
+
const SUPPORTED_VERSIONS = [6, 5, '4'];
|
|
49
|
+
export function ensureSupportedContractMetadataVersion(metadata) {
|
|
50
|
+
// This is for V1, V2, V3
|
|
51
|
+
const unsupportedVersion = UNSUPPORTED_VERSIONS.find((o) => metadata[o]);
|
|
52
|
+
if (unsupportedVersion) {
|
|
53
|
+
throw new DedotError(`Unsupported metadata version: ${unsupportedVersion}`);
|
|
54
|
+
}
|
|
55
|
+
// This is for V4, V5, V6
|
|
56
|
+
if (!SUPPORTED_VERSIONS.includes(metadata.version)) {
|
|
57
|
+
throw new DedotError(`Unsupported metadata version: ${metadata.version}`);
|
|
58
|
+
}
|
|
59
|
+
}
|
package/utils/index.d.ts
ADDED
package/utils/index.js
ADDED
package/utils/proxy.d.ts
ADDED
package/utils/proxy.js
ADDED
package/utils/storage.js
ADDED
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
export function findStorageRootKey(layout, targetId) {
|
|
2
|
+
if (layout.root) {
|
|
3
|
+
if (layout.root.ty === targetId) {
|
|
4
|
+
return layout.root.root_key;
|
|
5
|
+
}
|
|
6
|
+
else {
|
|
7
|
+
return findStorageRootKey(layout.root.layout, targetId);
|
|
8
|
+
}
|
|
9
|
+
}
|
|
10
|
+
else if (layout.array) {
|
|
11
|
+
return findStorageRootKey(layout.array.layout, targetId);
|
|
12
|
+
}
|
|
13
|
+
else if (layout.enum) {
|
|
14
|
+
for (const one of Object.values(layout.enum.variants)) {
|
|
15
|
+
for (const structField of one.fields) {
|
|
16
|
+
const potentialKey = findStorageRootKey(structField.layout, targetId);
|
|
17
|
+
if (potentialKey)
|
|
18
|
+
return potentialKey;
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
return undefined;
|
|
22
|
+
}
|
|
23
|
+
else if (layout.leaf) {
|
|
24
|
+
if (layout.leaf.ty === targetId) {
|
|
25
|
+
return layout.leaf.key;
|
|
26
|
+
}
|
|
27
|
+
else {
|
|
28
|
+
return undefined;
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
else if (layout.struct) {
|
|
32
|
+
for (const structField of layout.struct.fields) {
|
|
33
|
+
const potentialKey = findStorageRootKey(structField.layout, targetId);
|
|
34
|
+
if (potentialKey)
|
|
35
|
+
return potentialKey;
|
|
36
|
+
}
|
|
37
|
+
return undefined;
|
|
38
|
+
}
|
|
39
|
+
throw new Error(`Layout Not Supported: ${JSON.stringify(layout)}`);
|
|
40
|
+
}
|
package/utils/types.d.ts
ADDED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { PortableType, TypeDef } from '@dedot/codecs';
|
|
2
|
+
import { ContractMetadata, ContractTypeDef, ReturnFlags } from 'src/types';
|
|
3
|
+
export declare const extractContractTypes: (contractMetadata: ContractMetadata) => PortableType[];
|
|
4
|
+
export declare const normalizeContractTypeDef: (def: ContractTypeDef) => TypeDef;
|
|
5
|
+
export declare function normalizeLabel(label?: string): string;
|
|
6
|
+
export declare function toReturnFlags(bits: number): ReturnFlags;
|
|
7
|
+
export declare enum KnownLazyType {
|
|
8
|
+
LAZY = "LAZY",
|
|
9
|
+
MAPPING = "MAPPING",
|
|
10
|
+
STORAGE_VEC = "STORAGE_VEC"
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Check if a type is lazy/non-packed storage
|
|
14
|
+
*
|
|
15
|
+
* @param typePath
|
|
16
|
+
*/
|
|
17
|
+
export declare function isLazyType(typePath?: string | string[] | undefined): KnownLazyType | undefined;
|