Skip to content

Commit ab50471

Browse files
committed
Merge branch 'beta' into v6/v3-transactions
2 parents 8dc9b8a + da2db6f commit ab50471

File tree

13 files changed

+170
-43
lines changed

13 files changed

+170
-43
lines changed

CHANGELOG.md

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,29 @@
1+
# [6.0.0-beta.5](https://github.com/starknet-io/starknet.js/compare/v6.0.0-beta.4...v6.0.0-beta.5) (2023-12-10)
2+
3+
### Bug Fixes
4+
5+
- apply bound for contract address from hash calculation ([6d8c291](https://github.com/starknet-io/starknet.js/commit/6d8c291bce130d7b00ae6d81aff071c4986f04af))
6+
- **Calldata.compile:** do not split long `entrypoint` names before calling `getSelectorFromName` ([89715da](https://github.com/starknet-io/starknet.js/commit/89715da3fdb4b497cc5771eb83a88460007740b6))
7+
- prioritize error states in waitForTransaction evaluation ([ac54404](https://github.com/starknet-io/starknet.js/commit/ac544045e2079b68042d850a09b203fc5536c0d0))
8+
9+
## [5.24.5](https://github.com/starknet-io/starknet.js/compare/v5.24.4...v5.24.5) (2023-12-10)
10+
11+
### Bug Fixes
12+
13+
- apply bound for contract address from hash calculation ([6d8c291](https://github.com/starknet-io/starknet.js/commit/6d8c291bce130d7b00ae6d81aff071c4986f04af))
14+
- **Calldata.compile:** do not split long `entrypoint` names before calling `getSelectorFromName` ([89715da](https://github.com/starknet-io/starknet.js/commit/89715da3fdb4b497cc5771eb83a88460007740b6))
15+
- prioritize error states in waitForTransaction evaluation ([ac54404](https://github.com/starknet-io/starknet.js/commit/ac544045e2079b68042d850a09b203fc5536c0d0))
16+
17+
# [6.0.0-beta.4](https://github.com/starknet-io/starknet.js/compare/v6.0.0-beta.3...v6.0.0-beta.4) (2023-12-08)
18+
19+
### Bug Fixes
20+
21+
- remove account_deployment_data from deploy Account ([ede83bf](https://github.com/starknet-io/starknet.js/commit/ede83bfda3c6fcfa9dd397c92bd709293c8dda9b))
22+
23+
### Features
24+
25+
- simulate skip validate by default, spec deploy acc fix ([1b3e7ae](https://github.com/starknet-io/starknet.js/commit/1b3e7aeadaba5b7d59377e249b535f6a8cb8862e))
26+
127
# [6.0.0-beta.3](https://github.com/starknet-io/starknet.js/compare/v6.0.0-beta.2...v6.0.0-beta.3) (2023-12-07)
228

329
### Bug Fixes

__tests__/config/fixtures.ts

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -57,11 +57,8 @@ export function getTestProvider(isProvider: boolean = true): ProviderInterface |
5757
if (process.env.IS_LOCALHOST_DEVNET === 'true') {
5858
// accelerate the tests when running locally
5959
const originalWaitForTransaction = provider.waitForTransaction.bind(provider);
60-
provider.waitForTransaction = (
61-
txHash: string,
62-
{ retryInterval }: waitForTransactionOptions = {}
63-
) => {
64-
return originalWaitForTransaction(txHash, { retryInterval: retryInterval || 1000 });
60+
provider.waitForTransaction = (txHash: string, options: waitForTransactionOptions = {}) => {
61+
return originalWaitForTransaction(txHash, { retryInterval: 1000, ...options });
6562
};
6663
}
6764

__tests__/rpcProvider.test.ts

Lines changed: 70 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,16 @@
11
import { getStarkKey, utils } from '@scure/starknet';
22

3-
import { Account, Contract, GetBlockResponse, stark } from '../src';
3+
import {
4+
Account,
5+
CallData,
6+
Contract,
7+
GetBlockResponse,
8+
RPC,
9+
TransactionExecutionStatus,
10+
stark,
11+
waitForTransactionOptions,
12+
} from '../src';
413
import { StarknetChainId } from '../src/constants';
5-
import { CallData } from '../src/utils/calldata';
614
import { felt, uint256 } from '../src/utils/calldata/cairo';
715
import { toHexString } from '../src/utils/num';
816
import {
@@ -103,6 +111,66 @@ describeIfRpc('RPCProvider', () => {
103111
});
104112
});
105113

114+
describe('waitForTransaction', () => {
115+
const receipt = {};
116+
const transactionStatusSpy = jest.spyOn(rpcProvider as any, 'getTransactionStatus');
117+
const transactionReceiptSpy = jest.spyOn(rpcProvider as any, 'getTransactionReceipt');
118+
119+
const generateOptions = (o: waitForTransactionOptions) => ({ retryInterval: 10, ...o });
120+
const generateTransactionStatus = (
121+
finality_status: RPC.SPEC.TXN_STATUS,
122+
execution_status?: RPC.SPEC.TXN_EXECUTION_STATUS
123+
): RPC.TransactionStatus => ({
124+
finality_status,
125+
execution_status,
126+
});
127+
const response = {
128+
successful: generateTransactionStatus('ACCEPTED_ON_L1', 'SUCCEEDED'),
129+
reverted: generateTransactionStatus('ACCEPTED_ON_L2', 'REVERTED'),
130+
rejected: generateTransactionStatus('REJECTED'),
131+
};
132+
133+
beforeAll(() => {
134+
transactionStatusSpy.mockResolvedValue(null);
135+
transactionReceiptSpy.mockResolvedValue(receipt);
136+
});
137+
138+
afterAll(() => {
139+
transactionStatusSpy.mockRestore();
140+
transactionReceiptSpy.mockRestore();
141+
});
142+
143+
test('successful - default', async () => {
144+
transactionStatusSpy.mockResolvedValueOnce(response.successful);
145+
await expect(rpcProvider.waitForTransaction(0)).resolves.toBe(receipt);
146+
});
147+
148+
test('reverted - default', async () => {
149+
transactionStatusSpy.mockResolvedValueOnce(response.reverted);
150+
await expect(rpcProvider.waitForTransaction(0)).resolves.toBe(receipt);
151+
});
152+
153+
test('rejected - default', async () => {
154+
transactionStatusSpy.mockResolvedValueOnce(response.rejected);
155+
await expect(rpcProvider.waitForTransaction(0)).rejects.toThrow(
156+
`${undefined}: ${RPC.ETransactionStatus.REJECTED}`
157+
);
158+
});
159+
160+
test('reverted - as error state', async () => {
161+
transactionStatusSpy.mockResolvedValueOnce(response.reverted);
162+
const options = generateOptions({ errorStates: [TransactionExecutionStatus.REVERTED] });
163+
await expect(rpcProvider.waitForTransaction(0, options)).rejects.toThrow(
164+
`${RPC.ETransactionExecutionStatus.REVERTED}: ${RPC.ETransactionStatus.ACCEPTED_ON_L2}`
165+
);
166+
});
167+
168+
test('no error state; timed-out', async () => {
169+
const options = generateOptions({ errorStates: [] });
170+
await expect(rpcProvider.waitForTransaction(0, options)).rejects.toThrow(/timed-out/);
171+
});
172+
});
173+
106174
describe('RPC methods', () => {
107175
let latestBlock: GetBlockResponse;
108176

__tests__/utils/address.test.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { constants, num } from '../../src';
12
import {
23
addAddressPadding,
34
getChecksumAddress,
@@ -17,6 +18,11 @@ describe('validateAndParseAddress', () => {
1718

1819
return expect(validateAndParseAddress(addr)).toEqual(`${addAddressPadding(addr)}`);
1920
});
21+
22+
test('should fail for out of bound address', () => {
23+
const addr = num.toHex(constants.ADDR_BOUND + 1n);
24+
expect(() => validateAndParseAddress(addr)).toThrow(/^Message not signable/);
25+
});
2026
});
2127

2228
describe('address checksums', () => {

__tests__/utils/utils.test.ts

Lines changed: 24 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
import * as starkCurve from '@scure/starknet';
2+
13
import { constants, ec, hash, num, stark } from '../../src';
24
import { Block } from '../../src/utils/provider';
35

@@ -78,18 +80,15 @@ describe('estimatedFeeToMaxFee()', () => {
7880
});
7981

8082
describe('calculateContractAddressFromHash()', () => {
81-
// This test just show how to use calculateContractAddressFromHash for new devs
82-
83+
const ethAddress = '0x049d36570d4e46f48e99674bd3fcc84644ddd6b96f7c741b1562b82f9e004dc7';
84+
const daiAddress = '0x03e85bfbb8e2a42b7bead9e88e9a1b19dbccf661471061807292120462396ec9';
85+
const factoryAddress = '0x249827618A01858A72B7D04339C47195A324D20D6037033DFE2829F98AFF4FC';
86+
const classHash = '0x55187E68C60664A947048E0C9E5322F9BF55F7D435ECDCF17ED75724E77368F';
87+
// Any type of salt can be used. It depends on the dApp what kind of salt it wants to use.
88+
const salt = ec.starkCurve.pedersen(ethAddress, daiAddress);
89+
90+
// This test just shows how to use calculateContractAddressFromHash for new devs
8391
test('calculated contract address should match the snapshot', () => {
84-
const ethAddress = '0x049d36570d4e46f48e99674bd3fcc84644ddd6b96f7c741b1562b82f9e004dc7';
85-
86-
const daiAddress = '0x03e85bfbb8e2a42b7bead9e88e9a1b19dbccf661471061807292120462396ec9';
87-
const factoryAddress = '0x249827618A01858A72B7D04339C47195A324D20D6037033DFE2829F98AFF4FC';
88-
const classHash = '0x55187E68C60664A947048E0C9E5322F9BF55F7D435ECDCF17ED75724E77368F';
89-
90-
// Any type of salt can be used. It depends on the dApp what kind of salt it wants to use.
91-
const salt = ec.starkCurve.pedersen(ethAddress, daiAddress);
92-
9392
const res = hash.calculateContractAddressFromHash(
9493
salt,
9594
classHash,
@@ -101,6 +100,20 @@ describe('calculateContractAddressFromHash()', () => {
101100
`"0x36dc8dcb3440596472ddde11facacc45d0cd250df764ae7c3d1a360c853c324"`
102101
);
103102
});
103+
104+
test('output should be bound', () => {
105+
const starkCurveSpy = jest.spyOn(starkCurve, 'pedersen');
106+
starkCurveSpy.mockReturnValue(num.toHex(constants.ADDR_BOUND + 1n));
107+
const res = hash.calculateContractAddressFromHash(
108+
salt,
109+
classHash,
110+
[ethAddress, daiAddress, factoryAddress],
111+
factoryAddress
112+
);
113+
expect(starkCurveSpy).toHaveBeenCalled();
114+
expect(BigInt(res)).toBeLessThan(constants.ADDR_BOUND);
115+
starkCurveSpy.mockRestore();
116+
});
104117
});
105118

106119
describe('new Block()', () => {

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "starknet",
3-
"version": "6.0.0-beta.3",
3+
"version": "6.0.0-beta.5",
44
"description": "JavaScript library for Starknet",
55
"main": "dist/index.js",
66
"module": "dist/index.mjs",

src/channel/rpc_0_6.ts

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -240,7 +240,9 @@ export class RpcChannel {
240240
const retryInterval = options?.retryInterval ?? 5000;
241241
const errorStates: any = options?.errorStates ?? [
242242
RPC.ETransactionStatus.REJECTED,
243-
RPC.ETransactionExecutionStatus.REVERTED,
243+
// TODO: commented out to preserve the long-standing behavior of "reverted" not being treated as an error by default
244+
// should decide which behavior to keep in the future
245+
// RPC.ETransactionExecutionStatus.REVERTED,
244246
];
245247
const successStates: any = options?.successStates ?? [
246248
RPC.ETransactionExecutionStatus.SUCCEEDED,
@@ -266,14 +268,17 @@ export class RpcChannel {
266268
throw error;
267269
}
268270

269-
if (successStates.includes(executionStatus) || successStates.includes(finalityStatus)) {
270-
onchain = true;
271-
} else if (errorStates.includes(executionStatus) || errorStates.includes(finalityStatus)) {
271+
if (errorStates.includes(executionStatus) || errorStates.includes(finalityStatus)) {
272272
const message = `${executionStatus}: ${finalityStatus}`;
273273
const error = new Error(message) as Error & { response: RPC.TransactionStatus };
274274
error.response = txStatus;
275275
isErrorState = true;
276276
throw error;
277+
} else if (
278+
successStates.includes(executionStatus) ||
279+
successStates.includes(finalityStatus)
280+
) {
281+
onchain = true;
277282
}
278283
} catch (error) {
279284
if (error instanceof Error && isErrorState) {

src/constants.ts

Lines changed: 22 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -16,22 +16,28 @@ export { ETransactionVersion as TRANSACTION_VERSION };
1616

1717
export const ZERO = 0n;
1818
export const MASK_250 = 2n ** 250n - 1n; // 2 ** 250 - 1
19-
export const MASK_251 = 2n ** 251n;
2019
export const API_VERSION = ZERO;
2120

21+
// based on: https://github.com/starkware-libs/cairo-lang/blob/v0.12.3/src/starkware/starknet/common/storage.cairo#L3
22+
export const MAX_STORAGE_ITEM_SIZE = 256n;
23+
export const ADDR_BOUND = 2n ** 251n - MAX_STORAGE_ITEM_SIZE;
24+
2225
export enum BaseUrl {
2326
SN_MAIN = 'https://alpha-mainnet.starknet.io',
2427
SN_GOERLI = 'https://alpha4.starknet.io',
28+
SN_SEPOLIA = 'https://alpha-sepolia.starknet.io',
2529
}
2630

2731
export enum NetworkName {
2832
SN_MAIN = 'SN_MAIN',
2933
SN_GOERLI = 'SN_GOERLI',
34+
SN_SEPOLIA = 'SN_SEPOLIA',
3035
}
3136

3237
export enum StarknetChainId {
3338
SN_MAIN = '0x534e5f4d41494e', // encodeShortString('SN_MAIN'),
3439
SN_GOERLI = '0x534e5f474f45524c49', // encodeShortString('SN_GOERLI')
40+
SN_SEPOLIA = '0x534e5f5345504f4c4941', // encodeShortString('SN_SEPOLIA')
3541
}
3642

3743
export enum TransactionHashPrefix {
@@ -47,14 +53,19 @@ export const UDC = {
4753
ENTRYPOINT: 'deployContract',
4854
};
4955

50-
export const RPC_DEFAULT_VERSION = 'v0_5';
51-
52-
export const RPC_GOERLI_NODES = [
53-
`https://starknet-testnet.public.blastapi.io/rpc/${RPC_DEFAULT_VERSION}`,
54-
`https://free-rpc.nethermind.io/goerli-juno/${RPC_DEFAULT_VERSION}`,
55-
];
56+
export const RPC_DEFAULT_VERSION = 'v0_6';
5657

57-
export const RPC_MAINNET_NODES = [
58-
`https://starknet-mainnet.public.blastapi.io/rpc/${RPC_DEFAULT_VERSION}`,
59-
`https://free-rpc.nethermind.io/mainnet-juno/${RPC_DEFAULT_VERSION}`,
60-
];
58+
export const RPC_NODES = {
59+
SN_GOERLI: [
60+
`https://starknet-testnet.public.blastapi.io/rpc/${RPC_DEFAULT_VERSION}`,
61+
`https://free-rpc.nethermind.io/goerli-juno/${RPC_DEFAULT_VERSION}`,
62+
],
63+
SN_MAIN: [
64+
`https://starknet-mainnet.public.blastapi.io/rpc/${RPC_DEFAULT_VERSION}`,
65+
`https://free-rpc.nethermind.io/mainnet-juno/${RPC_DEFAULT_VERSION}`,
66+
],
67+
SN_SEPOLIA: [
68+
`https://starknet-sepolia.public.blastapi.io/rpc/${RPC_DEFAULT_VERSION}`,
69+
`https://free-rpc.nethermind.io/sepolia-juno/${RPC_DEFAULT_VERSION}`,
70+
],
71+
};

src/utils/address.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
/* eslint-disable no-bitwise */
22
import { hexToBytes } from '@noble/curves/abstract/utils';
33

4-
import { MASK_251, ZERO } from '../constants';
4+
import { ADDR_BOUND, ZERO } from '../constants';
55
import { BigNumberish } from '../types';
66
import { addHexPrefix, removeHexPrefix } from './encode';
77
import { keccakBn } from './hash';
@@ -12,7 +12,7 @@ export function addAddressPadding(address: BigNumberish): string {
1212
}
1313

1414
export function validateAndParseAddress(address: BigNumberish): string {
15-
assertInRange(address, ZERO, MASK_251, 'Starknet Address');
15+
assertInRange(address, ZERO, ADDR_BOUND - 1n, 'Starknet Address');
1616

1717
const result = addAddressPadding(address);
1818

0 commit comments

Comments
 (0)