forked from tornado-packages/tornado-core
Compare commits
4 Commits
9f4044d110
...
69066e4fd1
Author | SHA1 | Date | |
---|---|---|---|
69066e4fd1 | |||
34d687c319 | |||
55d62f7973 | |||
e3dc748020 |
12
dist/deposits.d.ts
vendored
12
dist/deposits.d.ts
vendored
@ -22,7 +22,14 @@ export interface createNoteParams extends DepositType {
|
|||||||
}
|
}
|
||||||
export interface parsedNoteExec extends DepositType {
|
export interface parsedNoteExec extends DepositType {
|
||||||
note: string;
|
note: string;
|
||||||
|
noteHex: string;
|
||||||
}
|
}
|
||||||
|
export interface parsedInvoiceExec extends DepositType {
|
||||||
|
invoice: string;
|
||||||
|
commitmentHex: string;
|
||||||
|
}
|
||||||
|
export declare function parseNote(noteString: string): parsedNoteExec | undefined;
|
||||||
|
export declare function parseInvoice(invoiceString: string): parsedInvoiceExec | undefined;
|
||||||
export declare function createDeposit({ nullifier, secret }: createDepositParams): Promise<createDepositObject>;
|
export declare function createDeposit({ nullifier, secret }: createDepositParams): Promise<createDepositObject>;
|
||||||
export interface DepositConstructor {
|
export interface DepositConstructor {
|
||||||
currency: string;
|
currency: string;
|
||||||
@ -52,14 +59,11 @@ export declare class Deposit {
|
|||||||
static createNote({ currency, amount, netId, nullifier, secret }: createNoteParams): Promise<Deposit>;
|
static createNote({ currency, amount, netId, nullifier, secret }: createNoteParams): Promise<Deposit>;
|
||||||
static parseNote(noteString: string): Promise<Deposit>;
|
static parseNote(noteString: string): Promise<Deposit>;
|
||||||
}
|
}
|
||||||
export interface parsedInvoiceExec extends DepositType {
|
|
||||||
commitment: string;
|
|
||||||
}
|
|
||||||
export declare class Invoice {
|
export declare class Invoice {
|
||||||
currency: string;
|
currency: string;
|
||||||
amount: string;
|
amount: string;
|
||||||
netId: NetIdType;
|
netId: NetIdType;
|
||||||
commitment: string;
|
commitmentHex: string;
|
||||||
invoice: string;
|
invoice: string;
|
||||||
constructor(invoiceString: string);
|
constructor(invoiceString: string);
|
||||||
toString(): string;
|
toString(): string;
|
||||||
|
1
dist/index.d.ts
vendored
1
dist/index.d.ts
vendored
@ -14,6 +14,7 @@ export * from './mimc';
|
|||||||
export * from './multicall';
|
export * from './multicall';
|
||||||
export * from './networkConfig';
|
export * from './networkConfig';
|
||||||
export * from './pedersen';
|
export * from './pedersen';
|
||||||
|
export * from './permit';
|
||||||
export * from './prices';
|
export * from './prices';
|
||||||
export * from './providers';
|
export * from './providers';
|
||||||
export * from './relayerClient';
|
export * from './relayerClient';
|
||||||
|
245
dist/index.js
vendored
245
dist/index.js
vendored
@ -9238,6 +9238,36 @@ async function buffPedersenHash(buffer) {
|
|||||||
return pedersen.toStringBuffer(hash);
|
return pedersen.toStringBuffer(hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function parseNote(noteString) {
|
||||||
|
const noteRegex = /tornado-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<noteHex>[0-9a-fA-F]{124})/g;
|
||||||
|
const match = noteRegex.exec(noteString);
|
||||||
|
if (!match) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const { currency, amount, netId, noteHex } = match.groups;
|
||||||
|
return {
|
||||||
|
currency: currency.toLowerCase(),
|
||||||
|
amount,
|
||||||
|
netId: Number(netId),
|
||||||
|
noteHex: "0x" + noteHex,
|
||||||
|
note: noteString
|
||||||
|
};
|
||||||
|
}
|
||||||
|
function parseInvoice(invoiceString) {
|
||||||
|
const invoiceRegex = /tornadoInvoice-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<commitmentHex>[0-9a-fA-F]{64})/g;
|
||||||
|
const match = invoiceRegex.exec(invoiceString);
|
||||||
|
if (!match) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const { currency, amount, netId, commitmentHex } = match.groups;
|
||||||
|
return {
|
||||||
|
currency: currency.toLowerCase(),
|
||||||
|
amount,
|
||||||
|
netId: Number(netId),
|
||||||
|
commitmentHex: "0x" + commitmentHex,
|
||||||
|
invoice: invoiceString
|
||||||
|
};
|
||||||
|
}
|
||||||
async function createDeposit({ nullifier, secret }) {
|
async function createDeposit({ nullifier, secret }) {
|
||||||
const preimage = new Uint8Array([...leInt2Buff(nullifier), ...leInt2Buff(secret)]);
|
const preimage = new Uint8Array([...leInt2Buff(nullifier), ...leInt2Buff(secret)]);
|
||||||
const noteHex = toFixedHex(bytesToBN(preimage), 62);
|
const noteHex = toFixedHex(bytesToBN(preimage), 62);
|
||||||
@ -9332,31 +9362,27 @@ class Deposit {
|
|||||||
return newDeposit;
|
return newDeposit;
|
||||||
}
|
}
|
||||||
static async parseNote(noteString) {
|
static async parseNote(noteString) {
|
||||||
const noteRegex = /tornado-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<note>[0-9a-fA-F]{124})/g;
|
const parsedNote = parseNote(noteString);
|
||||||
const match = noteRegex.exec(noteString);
|
if (!parsedNote) {
|
||||||
if (!match) {
|
|
||||||
throw new Error("The note has invalid format");
|
throw new Error("The note has invalid format");
|
||||||
}
|
}
|
||||||
const matchGroup = match?.groups;
|
const { currency, amount, netId, note, noteHex: parsedNoteHex } = parsedNote;
|
||||||
const currency = matchGroup.currency.toLowerCase();
|
const bytes = bnToBytes(parsedNoteHex);
|
||||||
const amount = matchGroup.amount;
|
|
||||||
const netId = Number(matchGroup.netId);
|
|
||||||
const bytes = bnToBytes("0x" + matchGroup.note);
|
|
||||||
const nullifier = BigInt(leBuff2Int(bytes.slice(0, 31)).toString());
|
const nullifier = BigInt(leBuff2Int(bytes.slice(0, 31)).toString());
|
||||||
const secret = BigInt(leBuff2Int(bytes.slice(31, 62)).toString());
|
const secret = BigInt(leBuff2Int(bytes.slice(31, 62)).toString());
|
||||||
const depositObject = await createDeposit({ nullifier, secret });
|
const { noteHex, commitmentHex, nullifierHex } = await createDeposit({ nullifier, secret });
|
||||||
const invoice = `tornadoInvoice-${currency}-${amount}-${netId}-${depositObject.commitmentHex}`;
|
const invoice = `tornadoInvoice-${currency}-${amount}-${netId}-${commitmentHex}`;
|
||||||
const newDeposit = new Deposit({
|
const newDeposit = new Deposit({
|
||||||
currency,
|
currency,
|
||||||
amount,
|
amount,
|
||||||
netId,
|
netId,
|
||||||
note: noteString,
|
note,
|
||||||
noteHex: depositObject.noteHex,
|
noteHex,
|
||||||
invoice,
|
invoice,
|
||||||
nullifier,
|
nullifier,
|
||||||
secret,
|
secret,
|
||||||
commitmentHex: depositObject.commitmentHex,
|
commitmentHex,
|
||||||
nullifierHex: depositObject.nullifierHex
|
nullifierHex
|
||||||
});
|
});
|
||||||
return newDeposit;
|
return newDeposit;
|
||||||
}
|
}
|
||||||
@ -9365,23 +9391,19 @@ class Invoice {
|
|||||||
currency;
|
currency;
|
||||||
amount;
|
amount;
|
||||||
netId;
|
netId;
|
||||||
commitment;
|
commitmentHex;
|
||||||
invoice;
|
invoice;
|
||||||
constructor(invoiceString) {
|
constructor(invoiceString) {
|
||||||
const invoiceRegex = /tornadoInvoice-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<commitment>[0-9a-fA-F]{64})/g;
|
const parsedInvoice = parseInvoice(invoiceString);
|
||||||
const match = invoiceRegex.exec(invoiceString);
|
if (!parsedInvoice) {
|
||||||
if (!match) {
|
throw new Error("The invoice has invalid format");
|
||||||
throw new Error("The note has invalid format");
|
|
||||||
}
|
}
|
||||||
const matchGroup = match?.groups;
|
const { currency, amount, netId, invoice, commitmentHex } = parsedInvoice;
|
||||||
const currency = matchGroup.currency.toLowerCase();
|
|
||||||
const amount = matchGroup.amount;
|
|
||||||
const netId = Number(matchGroup.netId);
|
|
||||||
this.currency = currency;
|
this.currency = currency;
|
||||||
this.amount = amount;
|
this.amount = amount;
|
||||||
this.netId = netId;
|
this.netId = netId;
|
||||||
this.commitment = "0x" + matchGroup.commitment;
|
this.commitmentHex = commitmentHex;
|
||||||
this.invoice = invoiceString;
|
this.invoice = invoice;
|
||||||
}
|
}
|
||||||
toString() {
|
toString() {
|
||||||
return JSON.stringify(
|
return JSON.stringify(
|
||||||
@ -9389,7 +9411,7 @@ class Invoice {
|
|||||||
currency: this.currency,
|
currency: this.currency,
|
||||||
amount: this.amount,
|
amount: this.amount,
|
||||||
netId: this.netId,
|
netId: this.netId,
|
||||||
commitment: this.commitment,
|
commitmentHex: this.commitmentHex,
|
||||||
invoice: this.invoice
|
invoice: this.invoice
|
||||||
},
|
},
|
||||||
null,
|
null,
|
||||||
@ -10037,9 +10059,9 @@ async function getIndexedDB(netId) {
|
|||||||
}
|
}
|
||||||
];
|
];
|
||||||
const config = getConfig(netId);
|
const config = getConfig(netId);
|
||||||
const { tokens, nativeCurrency } = config;
|
const { tokens, nativeCurrency, registryContract, governanceContract } = config;
|
||||||
const stores = [...defaultState];
|
const stores = [...defaultState];
|
||||||
if (netId === NetId.MAINNET) {
|
if (registryContract) {
|
||||||
stores.push({
|
stores.push({
|
||||||
name: `registered_${netId}`,
|
name: `registered_${netId}`,
|
||||||
keyPath: "ensName",
|
keyPath: "ensName",
|
||||||
@ -10051,6 +10073,8 @@ async function getIndexedDB(netId) {
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
if (governanceContract) {
|
||||||
stores.push({
|
stores.push({
|
||||||
name: `governance_${netId}`,
|
name: `governance_${netId}`,
|
||||||
keyPath: "eid",
|
keyPath: "eid",
|
||||||
@ -10311,6 +10335,164 @@ async function multicall(Multicall2, calls) {
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const permit2Address = "0x000000000022D473030F116dDEE9F6B43aC78BA3";
|
||||||
|
async function getPermitSignature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline
|
||||||
|
}) {
|
||||||
|
const sigSigner = signer || Token.runner;
|
||||||
|
const provider = sigSigner.provider;
|
||||||
|
const [name, lastNonce, { chainId }] = await Promise.all([
|
||||||
|
Token.name(),
|
||||||
|
Token.nonces(sigSigner.address),
|
||||||
|
provider.getNetwork()
|
||||||
|
]);
|
||||||
|
const DOMAIN_SEPARATOR = {
|
||||||
|
name,
|
||||||
|
version: "1",
|
||||||
|
chainId,
|
||||||
|
verifyingContract: Token.target
|
||||||
|
};
|
||||||
|
const PERMIT_TYPE = {
|
||||||
|
Permit: [
|
||||||
|
{ name: "owner", type: "address" },
|
||||||
|
{ name: "spender", type: "address" },
|
||||||
|
{ name: "value", type: "uint256" },
|
||||||
|
{ name: "nonce", type: "uint256" },
|
||||||
|
{ name: "deadline", type: "uint256" }
|
||||||
|
]
|
||||||
|
};
|
||||||
|
return ethers.Signature.from(
|
||||||
|
await sigSigner.signTypedData(DOMAIN_SEPARATOR, PERMIT_TYPE, {
|
||||||
|
owner: sigSigner.address,
|
||||||
|
spender,
|
||||||
|
value,
|
||||||
|
nonce: nonce || lastNonce,
|
||||||
|
deadline: deadline || ethers.MaxUint256
|
||||||
|
})
|
||||||
|
);
|
||||||
|
}
|
||||||
|
async function getPermitCommitmentsSignature({
|
||||||
|
PermitTornado: PermitTornado2,
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
denomination,
|
||||||
|
commitments,
|
||||||
|
nonce
|
||||||
|
}) {
|
||||||
|
const value = BigInt(commitments.length) * denomination;
|
||||||
|
const commitmentsHash = ethers.solidityPackedKeccak256(["bytes32[]"], [commitments]);
|
||||||
|
return await getPermitSignature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender: PermitTornado2.target,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline: BigInt(commitmentsHash)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
async function getPermit2Signature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender,
|
||||||
|
value: amount,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
witness
|
||||||
|
}) {
|
||||||
|
const sigSigner = signer || Token.runner;
|
||||||
|
const provider = sigSigner.provider;
|
||||||
|
const domain = {
|
||||||
|
name: "Permit2",
|
||||||
|
chainId: (await provider.getNetwork()).chainId,
|
||||||
|
verifyingContract: permit2Address
|
||||||
|
};
|
||||||
|
const types = !witness ? {
|
||||||
|
PermitTransferFrom: [
|
||||||
|
{ name: "permitted", type: "TokenPermissions" },
|
||||||
|
{ name: "spender", type: "address" },
|
||||||
|
{ name: "nonce", type: "uint256" },
|
||||||
|
{ name: "deadline", type: "uint256" }
|
||||||
|
],
|
||||||
|
TokenPermissions: [
|
||||||
|
{ name: "token", type: "address" },
|
||||||
|
{ name: "amount", type: "uint256" }
|
||||||
|
]
|
||||||
|
} : {
|
||||||
|
PermitWitnessTransferFrom: [
|
||||||
|
{ name: "permitted", type: "TokenPermissions" },
|
||||||
|
{ name: "spender", type: "address" },
|
||||||
|
{ name: "nonce", type: "uint256" },
|
||||||
|
{ name: "deadline", type: "uint256" },
|
||||||
|
{ name: "witness", type: witness.witnessTypeName }
|
||||||
|
],
|
||||||
|
TokenPermissions: [
|
||||||
|
{ name: "token", type: "address" },
|
||||||
|
{ name: "amount", type: "uint256" }
|
||||||
|
],
|
||||||
|
...witness.witnessType
|
||||||
|
};
|
||||||
|
const values = {
|
||||||
|
permitted: {
|
||||||
|
token: Token.target,
|
||||||
|
amount
|
||||||
|
},
|
||||||
|
spender,
|
||||||
|
// Sorted nonce are not required for Permit2
|
||||||
|
nonce: nonce || rBigInt(16),
|
||||||
|
deadline: deadline || ethers.MaxUint256
|
||||||
|
};
|
||||||
|
if (witness) {
|
||||||
|
values.witness = witness.witness;
|
||||||
|
}
|
||||||
|
const hash = new ethers.TypedDataEncoder(types).hash(values);
|
||||||
|
const signature = ethers.Signature.from(await sigSigner.signTypedData(domain, types, values));
|
||||||
|
return {
|
||||||
|
domain,
|
||||||
|
types,
|
||||||
|
values,
|
||||||
|
hash,
|
||||||
|
signature
|
||||||
|
};
|
||||||
|
}
|
||||||
|
async function getPermit2CommitmentsSignature({
|
||||||
|
PermitTornado: PermitTornado2,
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
denomination,
|
||||||
|
commitments,
|
||||||
|
nonce,
|
||||||
|
deadline
|
||||||
|
}) {
|
||||||
|
const value = BigInt(commitments.length) * denomination;
|
||||||
|
const commitmentsHash = ethers.solidityPackedKeccak256(["bytes32[]"], [commitments]);
|
||||||
|
return await getPermit2Signature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender: PermitTornado2.target,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
witness: {
|
||||||
|
witnessTypeName: "PermitCommitments",
|
||||||
|
witnessType: {
|
||||||
|
PermitCommitments: [
|
||||||
|
{ name: "instance", type: "address" },
|
||||||
|
{ name: "commitmentsHash", type: "bytes32" }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
witness: {
|
||||||
|
instance: PermitTornado2.target,
|
||||||
|
commitmentsHash
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
class TokenPriceOracle {
|
class TokenPriceOracle {
|
||||||
oracle;
|
oracle;
|
||||||
multicall;
|
multicall;
|
||||||
@ -10837,6 +11019,10 @@ exports.getInstanceByAddress = getInstanceByAddress;
|
|||||||
exports.getMeta = getMeta;
|
exports.getMeta = getMeta;
|
||||||
exports.getNetworkConfig = getNetworkConfig;
|
exports.getNetworkConfig = getNetworkConfig;
|
||||||
exports.getNoteAccounts = getNoteAccounts;
|
exports.getNoteAccounts = getNoteAccounts;
|
||||||
|
exports.getPermit2CommitmentsSignature = getPermit2CommitmentsSignature;
|
||||||
|
exports.getPermit2Signature = getPermit2Signature;
|
||||||
|
exports.getPermitCommitmentsSignature = getPermitCommitmentsSignature;
|
||||||
|
exports.getPermitSignature = getPermitSignature;
|
||||||
exports.getProvider = getProvider;
|
exports.getProvider = getProvider;
|
||||||
exports.getProviderWithNetId = getProviderWithNetId;
|
exports.getProviderWithNetId = getProviderWithNetId;
|
||||||
exports.getRegisters = getRegisters;
|
exports.getRegisters = getRegisters;
|
||||||
@ -10865,7 +11051,10 @@ exports.mimc = mimc;
|
|||||||
exports.multicall = multicall;
|
exports.multicall = multicall;
|
||||||
exports.numberFormatter = numberFormatter;
|
exports.numberFormatter = numberFormatter;
|
||||||
exports.packEncryptedMessage = packEncryptedMessage;
|
exports.packEncryptedMessage = packEncryptedMessage;
|
||||||
|
exports.parseInvoice = parseInvoice;
|
||||||
|
exports.parseNote = parseNote;
|
||||||
exports.pedersen = pedersen;
|
exports.pedersen = pedersen;
|
||||||
|
exports.permit2Address = permit2Address;
|
||||||
exports.pickWeightedRandomRelayer = pickWeightedRandomRelayer;
|
exports.pickWeightedRandomRelayer = pickWeightedRandomRelayer;
|
||||||
exports.populateTransaction = populateTransaction;
|
exports.populateTransaction = populateTransaction;
|
||||||
exports.proofSchemaType = proofSchemaType;
|
exports.proofSchemaType = proofSchemaType;
|
||||||
|
242
dist/index.mjs
vendored
242
dist/index.mjs
vendored
@ -1,4 +1,4 @@
|
|||||||
import { FetchRequest, JsonRpcProvider, Network, EnsPlugin, GasCostPlugin, Wallet, HDNodeWallet, VoidSigner, JsonRpcSigner, BrowserProvider, getAddress, isAddress, parseEther, AbiCoder, namehash, formatEther, dataSlice, dataLength, Interface, Contract, computeAddress, keccak256, EnsResolver, parseUnits, Transaction, ZeroAddress } from 'ethers';
|
import { FetchRequest, JsonRpcProvider, Network, EnsPlugin, GasCostPlugin, Wallet, HDNodeWallet, VoidSigner, JsonRpcSigner, BrowserProvider, getAddress, isAddress, parseEther, AbiCoder, namehash, formatEther, dataSlice, dataLength, Interface, Contract, computeAddress, keccak256, EnsResolver, parseUnits, Transaction, Signature, MaxUint256, solidityPackedKeccak256, TypedDataEncoder, ZeroAddress } from 'ethers';
|
||||||
import crossFetch from 'cross-fetch';
|
import crossFetch from 'cross-fetch';
|
||||||
import { webcrypto } from 'crypto';
|
import { webcrypto } from 'crypto';
|
||||||
import BN from 'bn.js';
|
import BN from 'bn.js';
|
||||||
@ -9217,6 +9217,36 @@ async function buffPedersenHash(buffer) {
|
|||||||
return pedersen.toStringBuffer(hash);
|
return pedersen.toStringBuffer(hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function parseNote(noteString) {
|
||||||
|
const noteRegex = /tornado-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<noteHex>[0-9a-fA-F]{124})/g;
|
||||||
|
const match = noteRegex.exec(noteString);
|
||||||
|
if (!match) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const { currency, amount, netId, noteHex } = match.groups;
|
||||||
|
return {
|
||||||
|
currency: currency.toLowerCase(),
|
||||||
|
amount,
|
||||||
|
netId: Number(netId),
|
||||||
|
noteHex: "0x" + noteHex,
|
||||||
|
note: noteString
|
||||||
|
};
|
||||||
|
}
|
||||||
|
function parseInvoice(invoiceString) {
|
||||||
|
const invoiceRegex = /tornadoInvoice-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<commitmentHex>[0-9a-fA-F]{64})/g;
|
||||||
|
const match = invoiceRegex.exec(invoiceString);
|
||||||
|
if (!match) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const { currency, amount, netId, commitmentHex } = match.groups;
|
||||||
|
return {
|
||||||
|
currency: currency.toLowerCase(),
|
||||||
|
amount,
|
||||||
|
netId: Number(netId),
|
||||||
|
commitmentHex: "0x" + commitmentHex,
|
||||||
|
invoice: invoiceString
|
||||||
|
};
|
||||||
|
}
|
||||||
async function createDeposit({ nullifier, secret }) {
|
async function createDeposit({ nullifier, secret }) {
|
||||||
const preimage = new Uint8Array([...leInt2Buff(nullifier), ...leInt2Buff(secret)]);
|
const preimage = new Uint8Array([...leInt2Buff(nullifier), ...leInt2Buff(secret)]);
|
||||||
const noteHex = toFixedHex(bytesToBN(preimage), 62);
|
const noteHex = toFixedHex(bytesToBN(preimage), 62);
|
||||||
@ -9311,31 +9341,27 @@ class Deposit {
|
|||||||
return newDeposit;
|
return newDeposit;
|
||||||
}
|
}
|
||||||
static async parseNote(noteString) {
|
static async parseNote(noteString) {
|
||||||
const noteRegex = /tornado-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<note>[0-9a-fA-F]{124})/g;
|
const parsedNote = parseNote(noteString);
|
||||||
const match = noteRegex.exec(noteString);
|
if (!parsedNote) {
|
||||||
if (!match) {
|
|
||||||
throw new Error("The note has invalid format");
|
throw new Error("The note has invalid format");
|
||||||
}
|
}
|
||||||
const matchGroup = match?.groups;
|
const { currency, amount, netId, note, noteHex: parsedNoteHex } = parsedNote;
|
||||||
const currency = matchGroup.currency.toLowerCase();
|
const bytes = bnToBytes(parsedNoteHex);
|
||||||
const amount = matchGroup.amount;
|
|
||||||
const netId = Number(matchGroup.netId);
|
|
||||||
const bytes = bnToBytes("0x" + matchGroup.note);
|
|
||||||
const nullifier = BigInt(leBuff2Int(bytes.slice(0, 31)).toString());
|
const nullifier = BigInt(leBuff2Int(bytes.slice(0, 31)).toString());
|
||||||
const secret = BigInt(leBuff2Int(bytes.slice(31, 62)).toString());
|
const secret = BigInt(leBuff2Int(bytes.slice(31, 62)).toString());
|
||||||
const depositObject = await createDeposit({ nullifier, secret });
|
const { noteHex, commitmentHex, nullifierHex } = await createDeposit({ nullifier, secret });
|
||||||
const invoice = `tornadoInvoice-${currency}-${amount}-${netId}-${depositObject.commitmentHex}`;
|
const invoice = `tornadoInvoice-${currency}-${amount}-${netId}-${commitmentHex}`;
|
||||||
const newDeposit = new Deposit({
|
const newDeposit = new Deposit({
|
||||||
currency,
|
currency,
|
||||||
amount,
|
amount,
|
||||||
netId,
|
netId,
|
||||||
note: noteString,
|
note,
|
||||||
noteHex: depositObject.noteHex,
|
noteHex,
|
||||||
invoice,
|
invoice,
|
||||||
nullifier,
|
nullifier,
|
||||||
secret,
|
secret,
|
||||||
commitmentHex: depositObject.commitmentHex,
|
commitmentHex,
|
||||||
nullifierHex: depositObject.nullifierHex
|
nullifierHex
|
||||||
});
|
});
|
||||||
return newDeposit;
|
return newDeposit;
|
||||||
}
|
}
|
||||||
@ -9344,23 +9370,19 @@ class Invoice {
|
|||||||
currency;
|
currency;
|
||||||
amount;
|
amount;
|
||||||
netId;
|
netId;
|
||||||
commitment;
|
commitmentHex;
|
||||||
invoice;
|
invoice;
|
||||||
constructor(invoiceString) {
|
constructor(invoiceString) {
|
||||||
const invoiceRegex = /tornadoInvoice-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<commitment>[0-9a-fA-F]{64})/g;
|
const parsedInvoice = parseInvoice(invoiceString);
|
||||||
const match = invoiceRegex.exec(invoiceString);
|
if (!parsedInvoice) {
|
||||||
if (!match) {
|
throw new Error("The invoice has invalid format");
|
||||||
throw new Error("The note has invalid format");
|
|
||||||
}
|
}
|
||||||
const matchGroup = match?.groups;
|
const { currency, amount, netId, invoice, commitmentHex } = parsedInvoice;
|
||||||
const currency = matchGroup.currency.toLowerCase();
|
|
||||||
const amount = matchGroup.amount;
|
|
||||||
const netId = Number(matchGroup.netId);
|
|
||||||
this.currency = currency;
|
this.currency = currency;
|
||||||
this.amount = amount;
|
this.amount = amount;
|
||||||
this.netId = netId;
|
this.netId = netId;
|
||||||
this.commitment = "0x" + matchGroup.commitment;
|
this.commitmentHex = commitmentHex;
|
||||||
this.invoice = invoiceString;
|
this.invoice = invoice;
|
||||||
}
|
}
|
||||||
toString() {
|
toString() {
|
||||||
return JSON.stringify(
|
return JSON.stringify(
|
||||||
@ -9368,7 +9390,7 @@ class Invoice {
|
|||||||
currency: this.currency,
|
currency: this.currency,
|
||||||
amount: this.amount,
|
amount: this.amount,
|
||||||
netId: this.netId,
|
netId: this.netId,
|
||||||
commitment: this.commitment,
|
commitmentHex: this.commitmentHex,
|
||||||
invoice: this.invoice
|
invoice: this.invoice
|
||||||
},
|
},
|
||||||
null,
|
null,
|
||||||
@ -10016,9 +10038,9 @@ async function getIndexedDB(netId) {
|
|||||||
}
|
}
|
||||||
];
|
];
|
||||||
const config = getConfig(netId);
|
const config = getConfig(netId);
|
||||||
const { tokens, nativeCurrency } = config;
|
const { tokens, nativeCurrency, registryContract, governanceContract } = config;
|
||||||
const stores = [...defaultState];
|
const stores = [...defaultState];
|
||||||
if (netId === NetId.MAINNET) {
|
if (registryContract) {
|
||||||
stores.push({
|
stores.push({
|
||||||
name: `registered_${netId}`,
|
name: `registered_${netId}`,
|
||||||
keyPath: "ensName",
|
keyPath: "ensName",
|
||||||
@ -10030,6 +10052,8 @@ async function getIndexedDB(netId) {
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
if (governanceContract) {
|
||||||
stores.push({
|
stores.push({
|
||||||
name: `governance_${netId}`,
|
name: `governance_${netId}`,
|
||||||
keyPath: "eid",
|
keyPath: "eid",
|
||||||
@ -10290,6 +10314,164 @@ async function multicall(Multicall2, calls) {
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const permit2Address = "0x000000000022D473030F116dDEE9F6B43aC78BA3";
|
||||||
|
async function getPermitSignature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline
|
||||||
|
}) {
|
||||||
|
const sigSigner = signer || Token.runner;
|
||||||
|
const provider = sigSigner.provider;
|
||||||
|
const [name, lastNonce, { chainId }] = await Promise.all([
|
||||||
|
Token.name(),
|
||||||
|
Token.nonces(sigSigner.address),
|
||||||
|
provider.getNetwork()
|
||||||
|
]);
|
||||||
|
const DOMAIN_SEPARATOR = {
|
||||||
|
name,
|
||||||
|
version: "1",
|
||||||
|
chainId,
|
||||||
|
verifyingContract: Token.target
|
||||||
|
};
|
||||||
|
const PERMIT_TYPE = {
|
||||||
|
Permit: [
|
||||||
|
{ name: "owner", type: "address" },
|
||||||
|
{ name: "spender", type: "address" },
|
||||||
|
{ name: "value", type: "uint256" },
|
||||||
|
{ name: "nonce", type: "uint256" },
|
||||||
|
{ name: "deadline", type: "uint256" }
|
||||||
|
]
|
||||||
|
};
|
||||||
|
return Signature.from(
|
||||||
|
await sigSigner.signTypedData(DOMAIN_SEPARATOR, PERMIT_TYPE, {
|
||||||
|
owner: sigSigner.address,
|
||||||
|
spender,
|
||||||
|
value,
|
||||||
|
nonce: nonce || lastNonce,
|
||||||
|
deadline: deadline || MaxUint256
|
||||||
|
})
|
||||||
|
);
|
||||||
|
}
|
||||||
|
async function getPermitCommitmentsSignature({
|
||||||
|
PermitTornado: PermitTornado2,
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
denomination,
|
||||||
|
commitments,
|
||||||
|
nonce
|
||||||
|
}) {
|
||||||
|
const value = BigInt(commitments.length) * denomination;
|
||||||
|
const commitmentsHash = solidityPackedKeccak256(["bytes32[]"], [commitments]);
|
||||||
|
return await getPermitSignature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender: PermitTornado2.target,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline: BigInt(commitmentsHash)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
async function getPermit2Signature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender,
|
||||||
|
value: amount,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
witness
|
||||||
|
}) {
|
||||||
|
const sigSigner = signer || Token.runner;
|
||||||
|
const provider = sigSigner.provider;
|
||||||
|
const domain = {
|
||||||
|
name: "Permit2",
|
||||||
|
chainId: (await provider.getNetwork()).chainId,
|
||||||
|
verifyingContract: permit2Address
|
||||||
|
};
|
||||||
|
const types = !witness ? {
|
||||||
|
PermitTransferFrom: [
|
||||||
|
{ name: "permitted", type: "TokenPermissions" },
|
||||||
|
{ name: "spender", type: "address" },
|
||||||
|
{ name: "nonce", type: "uint256" },
|
||||||
|
{ name: "deadline", type: "uint256" }
|
||||||
|
],
|
||||||
|
TokenPermissions: [
|
||||||
|
{ name: "token", type: "address" },
|
||||||
|
{ name: "amount", type: "uint256" }
|
||||||
|
]
|
||||||
|
} : {
|
||||||
|
PermitWitnessTransferFrom: [
|
||||||
|
{ name: "permitted", type: "TokenPermissions" },
|
||||||
|
{ name: "spender", type: "address" },
|
||||||
|
{ name: "nonce", type: "uint256" },
|
||||||
|
{ name: "deadline", type: "uint256" },
|
||||||
|
{ name: "witness", type: witness.witnessTypeName }
|
||||||
|
],
|
||||||
|
TokenPermissions: [
|
||||||
|
{ name: "token", type: "address" },
|
||||||
|
{ name: "amount", type: "uint256" }
|
||||||
|
],
|
||||||
|
...witness.witnessType
|
||||||
|
};
|
||||||
|
const values = {
|
||||||
|
permitted: {
|
||||||
|
token: Token.target,
|
||||||
|
amount
|
||||||
|
},
|
||||||
|
spender,
|
||||||
|
// Sorted nonce are not required for Permit2
|
||||||
|
nonce: nonce || rBigInt(16),
|
||||||
|
deadline: deadline || MaxUint256
|
||||||
|
};
|
||||||
|
if (witness) {
|
||||||
|
values.witness = witness.witness;
|
||||||
|
}
|
||||||
|
const hash = new TypedDataEncoder(types).hash(values);
|
||||||
|
const signature = Signature.from(await sigSigner.signTypedData(domain, types, values));
|
||||||
|
return {
|
||||||
|
domain,
|
||||||
|
types,
|
||||||
|
values,
|
||||||
|
hash,
|
||||||
|
signature
|
||||||
|
};
|
||||||
|
}
|
||||||
|
async function getPermit2CommitmentsSignature({
|
||||||
|
PermitTornado: PermitTornado2,
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
denomination,
|
||||||
|
commitments,
|
||||||
|
nonce,
|
||||||
|
deadline
|
||||||
|
}) {
|
||||||
|
const value = BigInt(commitments.length) * denomination;
|
||||||
|
const commitmentsHash = solidityPackedKeccak256(["bytes32[]"], [commitments]);
|
||||||
|
return await getPermit2Signature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender: PermitTornado2.target,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
witness: {
|
||||||
|
witnessTypeName: "PermitCommitments",
|
||||||
|
witnessType: {
|
||||||
|
PermitCommitments: [
|
||||||
|
{ name: "instance", type: "address" },
|
||||||
|
{ name: "commitmentsHash", type: "bytes32" }
|
||||||
|
]
|
||||||
|
},
|
||||||
|
witness: {
|
||||||
|
instance: PermitTornado2.target,
|
||||||
|
commitmentsHash
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
class TokenPriceOracle {
|
class TokenPriceOracle {
|
||||||
oracle;
|
oracle;
|
||||||
multicall;
|
multicall;
|
||||||
@ -10700,4 +10882,4 @@ async function calculateSnarkProof(input, circuit, provingKey) {
|
|||||||
return { proof, args };
|
return { proof, args };
|
||||||
}
|
}
|
||||||
|
|
||||||
export { BaseEchoService, BaseEncryptedNotesService, BaseEventsService, BaseGovernanceService, BaseRegistryService, BaseTornadoService, BatchBlockService, BatchEventsService, BatchTransactionService, DBEchoService, DBEncryptedNotesService, DBGovernanceService, DBRegistryService, DBTornadoService, DEPOSIT, Deposit, ENSNameWrapper__factory, ENSRegistry__factory, ENSResolver__factory, ENSUtils, ENS__factory, ERC20__factory, EnsContracts, GET_DEPOSITS, GET_ECHO_EVENTS, GET_ENCRYPTED_NOTES, GET_GOVERNANCE_APY, GET_GOVERNANCE_EVENTS, GET_NOTE_ACCOUNTS, GET_REGISTERED, GET_STATISTIC, GET_WITHDRAWALS, INDEX_DB_ERROR, IndexedDB, Invoice, MAX_FEE, MAX_TOVARISH_EVENTS, MIN_FEE, MIN_STAKE_BALANCE, MerkleTreeService, Mimc, Multicall__factory, NetId, NoteAccount, OffchainOracle__factory, OvmGasPriceOracle__factory, Pedersen, RelayerClient, ReverseRecords__factory, TokenPriceOracle, TornadoBrowserProvider, TornadoFeeOracle, TornadoRpcSigner, TornadoVoidSigner, TornadoWallet, TovarishClient, WITHDRAWAL, _META, addNetwork, addressSchemaType, ajv, base64ToBytes, bigIntReplacer, bnSchemaType, bnToBytes, buffPedersenHash, bufferToBytes, bytes32BNSchemaType, bytes32SchemaType, bytesToBN, bytesToBase64, bytesToHex, calculateScore, calculateSnarkProof, chunk, concatBytes, convertETHToTokenAmount, createDeposit, crypto, customConfig, defaultConfig, defaultUserAgent, depositsEventsSchema, digest, downloadZip, echoEventsSchema, enabledChains, encodedLabelToLabelhash, encryptedNotesSchema, index as factories, fetch, fetchData, fetchGetUrlFunc, gasZipID, gasZipInbounds, gasZipInput, gasZipMinMax, getActiveTokenInstances, getActiveTokens, getAllDeposits, getAllEncryptedNotes, getAllGovernanceEvents, getAllGraphEchoEvents, getAllRegisters, getAllWithdrawals, getConfig, getDeposits, getEncryptedNotes, getEventsSchemaValidator, getGovernanceEvents, getGraphEchoEvents, getHttpAgent, getIndexedDB, getInstanceByAddress, getMeta, getNetworkConfig, getNoteAccounts, getProvider, getProviderWithNetId, getRegisters, getRelayerEnsSubdomains, getStatistic, getStatusSchema, getSupportedInstances, getTokenBalances, getTovarishNetworks, getWeightRandom, getWithdrawals, governanceEventsSchema, hexToBytes, initGroth16, isHex, isNode, jobRequestSchema, jobsSchema, labelhash, leBuff2Int, leInt2Buff, loadDBEvents, loadRemoteEvents, makeLabelNodeAndParent, mimc, multicall, numberFormatter, packEncryptedMessage, pedersen, pickWeightedRandomRelayer, populateTransaction, proofSchemaType, proposalState, queryGraph, rBigInt, registeredEventsSchema, saveDBEvents, sleep, substring, toFixedHex, toFixedLength, unpackEncryptedMessage, unzipAsync, validateUrl, withdrawalsEventsSchema, zipAsync };
|
export { BaseEchoService, BaseEncryptedNotesService, BaseEventsService, BaseGovernanceService, BaseRegistryService, BaseTornadoService, BatchBlockService, BatchEventsService, BatchTransactionService, DBEchoService, DBEncryptedNotesService, DBGovernanceService, DBRegistryService, DBTornadoService, DEPOSIT, Deposit, ENSNameWrapper__factory, ENSRegistry__factory, ENSResolver__factory, ENSUtils, ENS__factory, ERC20__factory, EnsContracts, GET_DEPOSITS, GET_ECHO_EVENTS, GET_ENCRYPTED_NOTES, GET_GOVERNANCE_APY, GET_GOVERNANCE_EVENTS, GET_NOTE_ACCOUNTS, GET_REGISTERED, GET_STATISTIC, GET_WITHDRAWALS, INDEX_DB_ERROR, IndexedDB, Invoice, MAX_FEE, MAX_TOVARISH_EVENTS, MIN_FEE, MIN_STAKE_BALANCE, MerkleTreeService, Mimc, Multicall__factory, NetId, NoteAccount, OffchainOracle__factory, OvmGasPriceOracle__factory, Pedersen, RelayerClient, ReverseRecords__factory, TokenPriceOracle, TornadoBrowserProvider, TornadoFeeOracle, TornadoRpcSigner, TornadoVoidSigner, TornadoWallet, TovarishClient, WITHDRAWAL, _META, addNetwork, addressSchemaType, ajv, base64ToBytes, bigIntReplacer, bnSchemaType, bnToBytes, buffPedersenHash, bufferToBytes, bytes32BNSchemaType, bytes32SchemaType, bytesToBN, bytesToBase64, bytesToHex, calculateScore, calculateSnarkProof, chunk, concatBytes, convertETHToTokenAmount, createDeposit, crypto, customConfig, defaultConfig, defaultUserAgent, depositsEventsSchema, digest, downloadZip, echoEventsSchema, enabledChains, encodedLabelToLabelhash, encryptedNotesSchema, index as factories, fetch, fetchData, fetchGetUrlFunc, gasZipID, gasZipInbounds, gasZipInput, gasZipMinMax, getActiveTokenInstances, getActiveTokens, getAllDeposits, getAllEncryptedNotes, getAllGovernanceEvents, getAllGraphEchoEvents, getAllRegisters, getAllWithdrawals, getConfig, getDeposits, getEncryptedNotes, getEventsSchemaValidator, getGovernanceEvents, getGraphEchoEvents, getHttpAgent, getIndexedDB, getInstanceByAddress, getMeta, getNetworkConfig, getNoteAccounts, getPermit2CommitmentsSignature, getPermit2Signature, getPermitCommitmentsSignature, getPermitSignature, getProvider, getProviderWithNetId, getRegisters, getRelayerEnsSubdomains, getStatistic, getStatusSchema, getSupportedInstances, getTokenBalances, getTovarishNetworks, getWeightRandom, getWithdrawals, governanceEventsSchema, hexToBytes, initGroth16, isHex, isNode, jobRequestSchema, jobsSchema, labelhash, leBuff2Int, leInt2Buff, loadDBEvents, loadRemoteEvents, makeLabelNodeAndParent, mimc, multicall, numberFormatter, packEncryptedMessage, parseInvoice, parseNote, pedersen, permit2Address, pickWeightedRandomRelayer, populateTransaction, proofSchemaType, proposalState, queryGraph, rBigInt, registeredEventsSchema, saveDBEvents, sleep, substring, toFixedHex, toFixedLength, unpackEncryptedMessage, unzipAsync, validateUrl, withdrawalsEventsSchema, zipAsync };
|
||||||
|
86
dist/permit.d.ts
vendored
Normal file
86
dist/permit.d.ts
vendored
Normal file
@ -0,0 +1,86 @@
|
|||||||
|
import { ERC20Permit, ERC20Mock, TORN, PermitTornado } from '@tornado/contracts';
|
||||||
|
import { BaseContract, Signature, Signer, TypedDataField } from 'ethers';
|
||||||
|
export interface PermitValue {
|
||||||
|
spender: string;
|
||||||
|
value: bigint;
|
||||||
|
nonce?: bigint;
|
||||||
|
deadline?: bigint;
|
||||||
|
}
|
||||||
|
export interface PermitCommitments {
|
||||||
|
denomination: bigint;
|
||||||
|
commitments: string[];
|
||||||
|
nonce?: bigint;
|
||||||
|
deadline?: bigint;
|
||||||
|
}
|
||||||
|
export declare const permit2Address = "0x000000000022D473030F116dDEE9F6B43aC78BA3";
|
||||||
|
/**
|
||||||
|
* From @uniswap/permit2-sdk ported for ethers.js v6
|
||||||
|
*/
|
||||||
|
export interface Witness {
|
||||||
|
witnessTypeName: string;
|
||||||
|
witnessType: {
|
||||||
|
[key: string]: TypedDataField[];
|
||||||
|
};
|
||||||
|
witness: any;
|
||||||
|
}
|
||||||
|
export declare function getPermitSignature({ Token, signer, spender, value, nonce, deadline, }: PermitValue & {
|
||||||
|
Token: ERC20Permit | ERC20Mock | TORN;
|
||||||
|
signer?: Signer;
|
||||||
|
}): Promise<Signature>;
|
||||||
|
export declare function getPermitCommitmentsSignature({ PermitTornado, Token, signer, denomination, commitments, nonce, }: PermitCommitments & {
|
||||||
|
PermitTornado: PermitTornado;
|
||||||
|
Token: ERC20Permit | ERC20Mock | TORN;
|
||||||
|
signer?: Signer;
|
||||||
|
}): Promise<Signature>;
|
||||||
|
export declare function getPermit2Signature({ Token, signer, spender, value: amount, nonce, deadline, witness, }: PermitValue & {
|
||||||
|
Token: BaseContract;
|
||||||
|
signer?: Signer;
|
||||||
|
witness?: Witness;
|
||||||
|
}): Promise<{
|
||||||
|
domain: {
|
||||||
|
name: string;
|
||||||
|
chainId: bigint;
|
||||||
|
verifyingContract: string;
|
||||||
|
};
|
||||||
|
types: {
|
||||||
|
[key: string]: TypedDataField[];
|
||||||
|
};
|
||||||
|
values: {
|
||||||
|
permitted: {
|
||||||
|
token: string;
|
||||||
|
amount: bigint;
|
||||||
|
};
|
||||||
|
spender: string;
|
||||||
|
nonce: bigint;
|
||||||
|
deadline: bigint;
|
||||||
|
witness?: any;
|
||||||
|
};
|
||||||
|
hash: string;
|
||||||
|
signature: Signature;
|
||||||
|
}>;
|
||||||
|
export declare function getPermit2CommitmentsSignature({ PermitTornado, Token, signer, denomination, commitments, nonce, deadline, }: PermitCommitments & {
|
||||||
|
PermitTornado: PermitTornado;
|
||||||
|
Token: BaseContract;
|
||||||
|
signer?: Signer;
|
||||||
|
}): Promise<{
|
||||||
|
domain: {
|
||||||
|
name: string;
|
||||||
|
chainId: bigint;
|
||||||
|
verifyingContract: string;
|
||||||
|
};
|
||||||
|
types: {
|
||||||
|
[key: string]: TypedDataField[];
|
||||||
|
};
|
||||||
|
values: {
|
||||||
|
permitted: {
|
||||||
|
token: string;
|
||||||
|
amount: bigint;
|
||||||
|
};
|
||||||
|
spender: string;
|
||||||
|
nonce: bigint;
|
||||||
|
deadline: bigint;
|
||||||
|
witness?: any;
|
||||||
|
};
|
||||||
|
hash: string;
|
||||||
|
signature: Signature;
|
||||||
|
}>;
|
1662
dist/tornado.umd.js
vendored
1662
dist/tornado.umd.js
vendored
File diff suppressed because it is too large
Load Diff
4
dist/tornado.umd.min.js
vendored
4
dist/tornado.umd.min.js
vendored
File diff suppressed because one or more lines are too long
3376
dist/tornadoContracts.umd.js
vendored
3376
dist/tornadoContracts.umd.js
vendored
File diff suppressed because one or more lines are too long
2
dist/tornadoContracts.umd.min.js
vendored
2
dist/tornadoContracts.umd.min.js
vendored
File diff suppressed because one or more lines are too long
10
package.json
10
package.json
@ -31,8 +31,8 @@
|
|||||||
"yarn.lock"
|
"yarn.lock"
|
||||||
],
|
],
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@metamask/eth-sig-util": "^7.0.3",
|
"@metamask/eth-sig-util": "^8.0.0",
|
||||||
"@tornado/contracts": "git+https://git.tornado.ws/tornadocontrib/tornado-contracts.git#ece511f424dc811c3aec149a4bf0e3731c0598a4",
|
"@tornado/contracts": "git+https://git.tornado.ws/tornadocontrib/tornado-contracts.git#1b1d707878c16a3dc60d295299d4f0e7ce6ba831",
|
||||||
"@tornado/fixed-merkle-tree": "^0.7.3",
|
"@tornado/fixed-merkle-tree": "^0.7.3",
|
||||||
"@tornado/snarkjs": "^0.1.20",
|
"@tornado/snarkjs": "^0.1.20",
|
||||||
"@tornado/websnark": "^0.0.4",
|
"@tornado/websnark": "^0.0.4",
|
||||||
@ -52,10 +52,10 @@
|
|||||||
"@typechain/ethers-v6": "^0.5.1",
|
"@typechain/ethers-v6": "^0.5.1",
|
||||||
"@types/bn.js": "^5.1.6",
|
"@types/bn.js": "^5.1.6",
|
||||||
"@types/circomlibjs": "^0.1.6",
|
"@types/circomlibjs": "^0.1.6",
|
||||||
"@types/node": "^22.7.5",
|
"@types/node": "^22.7.9",
|
||||||
"@types/node-fetch": "^2.6.11",
|
"@types/node-fetch": "^2.6.11",
|
||||||
"@typescript-eslint/eslint-plugin": "^8.9.0",
|
"@typescript-eslint/eslint-plugin": "^8.11.0",
|
||||||
"@typescript-eslint/parser": "^8.9.0",
|
"@typescript-eslint/parser": "^8.11.0",
|
||||||
"esbuild-loader": "^4.2.2",
|
"esbuild-loader": "^4.2.2",
|
||||||
"eslint": "8.57.0",
|
"eslint": "8.57.0",
|
||||||
"eslint-config-prettier": "^9.1.0",
|
"eslint-config-prettier": "^9.1.0",
|
||||||
|
@ -29,6 +29,49 @@ export interface createNoteParams extends DepositType {
|
|||||||
|
|
||||||
export interface parsedNoteExec extends DepositType {
|
export interface parsedNoteExec extends DepositType {
|
||||||
note: string;
|
note: string;
|
||||||
|
noteHex: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface parsedInvoiceExec extends DepositType {
|
||||||
|
invoice: string;
|
||||||
|
commitmentHex: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function parseNote(noteString: string): parsedNoteExec | undefined {
|
||||||
|
const noteRegex = /tornado-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<noteHex>[0-9a-fA-F]{124})/g;
|
||||||
|
const match = noteRegex.exec(noteString);
|
||||||
|
if (!match) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const { currency, amount, netId, noteHex } = match.groups as unknown as parsedNoteExec;
|
||||||
|
|
||||||
|
return {
|
||||||
|
currency: currency.toLowerCase(),
|
||||||
|
amount,
|
||||||
|
netId: Number(netId),
|
||||||
|
noteHex: '0x' + noteHex,
|
||||||
|
note: noteString,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export function parseInvoice(invoiceString: string): parsedInvoiceExec | undefined {
|
||||||
|
const invoiceRegex =
|
||||||
|
/tornadoInvoice-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<commitmentHex>[0-9a-fA-F]{64})/g;
|
||||||
|
const match = invoiceRegex.exec(invoiceString);
|
||||||
|
if (!match) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const { currency, amount, netId, commitmentHex } = match.groups as unknown as parsedInvoiceExec;
|
||||||
|
|
||||||
|
return {
|
||||||
|
currency: currency.toLowerCase(),
|
||||||
|
amount,
|
||||||
|
netId: Number(netId),
|
||||||
|
commitmentHex: '0x' + commitmentHex,
|
||||||
|
invoice: invoiceString,
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export async function createDeposit({ nullifier, secret }: createDepositParams): Promise<createDepositObject> {
|
export async function createDeposit({ nullifier, secret }: createDepositParams): Promise<createDepositObject> {
|
||||||
@ -153,72 +196,61 @@ export class Deposit {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static async parseNote(noteString: string): Promise<Deposit> {
|
static async parseNote(noteString: string): Promise<Deposit> {
|
||||||
const noteRegex = /tornado-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<note>[0-9a-fA-F]{124})/g;
|
const parsedNote = parseNote(noteString);
|
||||||
const match = noteRegex.exec(noteString);
|
|
||||||
if (!match) {
|
if (!parsedNote) {
|
||||||
throw new Error('The note has invalid format');
|
throw new Error('The note has invalid format');
|
||||||
}
|
}
|
||||||
const matchGroup = match?.groups as unknown as parsedNoteExec;
|
|
||||||
|
|
||||||
const currency = matchGroup.currency.toLowerCase();
|
const { currency, amount, netId, note, noteHex: parsedNoteHex } = parsedNote;
|
||||||
const amount = matchGroup.amount;
|
|
||||||
const netId = Number(matchGroup.netId);
|
|
||||||
|
|
||||||
const bytes = bnToBytes('0x' + matchGroup.note);
|
const bytes = bnToBytes(parsedNoteHex);
|
||||||
const nullifier = BigInt(leBuff2Int(bytes.slice(0, 31)).toString());
|
const nullifier = BigInt(leBuff2Int(bytes.slice(0, 31)).toString());
|
||||||
const secret = BigInt(leBuff2Int(bytes.slice(31, 62)).toString());
|
const secret = BigInt(leBuff2Int(bytes.slice(31, 62)).toString());
|
||||||
|
|
||||||
const depositObject = await createDeposit({ nullifier, secret });
|
const { noteHex, commitmentHex, nullifierHex } = await createDeposit({ nullifier, secret });
|
||||||
|
|
||||||
const invoice = `tornadoInvoice-${currency}-${amount}-${netId}-${depositObject.commitmentHex}`;
|
const invoice = `tornadoInvoice-${currency}-${amount}-${netId}-${commitmentHex}`;
|
||||||
|
|
||||||
const newDeposit = new Deposit({
|
const newDeposit = new Deposit({
|
||||||
currency,
|
currency,
|
||||||
amount,
|
amount,
|
||||||
netId,
|
netId,
|
||||||
note: noteString,
|
note,
|
||||||
noteHex: depositObject.noteHex,
|
noteHex,
|
||||||
invoice,
|
invoice,
|
||||||
nullifier,
|
nullifier,
|
||||||
secret,
|
secret,
|
||||||
commitmentHex: depositObject.commitmentHex,
|
commitmentHex,
|
||||||
nullifierHex: depositObject.nullifierHex,
|
nullifierHex,
|
||||||
});
|
});
|
||||||
|
|
||||||
return newDeposit;
|
return newDeposit;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface parsedInvoiceExec extends DepositType {
|
|
||||||
commitment: string;
|
|
||||||
}
|
|
||||||
|
|
||||||
export class Invoice {
|
export class Invoice {
|
||||||
currency: string;
|
currency: string;
|
||||||
amount: string;
|
amount: string;
|
||||||
netId: NetIdType;
|
netId: NetIdType;
|
||||||
commitment: string;
|
commitmentHex: string;
|
||||||
invoice: string;
|
invoice: string;
|
||||||
|
|
||||||
constructor(invoiceString: string) {
|
constructor(invoiceString: string) {
|
||||||
const invoiceRegex =
|
const parsedInvoice = parseInvoice(invoiceString);
|
||||||
/tornadoInvoice-(?<currency>\w+)-(?<amount>[\d.]+)-(?<netId>\d+)-0x(?<commitment>[0-9a-fA-F]{64})/g;
|
|
||||||
const match = invoiceRegex.exec(invoiceString);
|
|
||||||
if (!match) {
|
|
||||||
throw new Error('The note has invalid format');
|
|
||||||
}
|
|
||||||
const matchGroup = match?.groups as unknown as parsedInvoiceExec;
|
|
||||||
|
|
||||||
const currency = matchGroup.currency.toLowerCase();
|
if (!parsedInvoice) {
|
||||||
const amount = matchGroup.amount;
|
throw new Error('The invoice has invalid format');
|
||||||
const netId = Number(matchGroup.netId);
|
}
|
||||||
|
|
||||||
|
const { currency, amount, netId, invoice, commitmentHex } = parsedInvoice;
|
||||||
|
|
||||||
this.currency = currency;
|
this.currency = currency;
|
||||||
this.amount = amount;
|
this.amount = amount;
|
||||||
this.netId = netId;
|
this.netId = netId;
|
||||||
|
|
||||||
this.commitment = '0x' + matchGroup.commitment;
|
this.commitmentHex = commitmentHex;
|
||||||
this.invoice = invoiceString;
|
this.invoice = invoice;
|
||||||
}
|
}
|
||||||
|
|
||||||
toString() {
|
toString() {
|
||||||
@ -227,7 +259,7 @@ export class Invoice {
|
|||||||
currency: this.currency,
|
currency: this.currency,
|
||||||
amount: this.amount,
|
amount: this.amount,
|
||||||
netId: this.netId,
|
netId: this.netId,
|
||||||
commitment: this.commitment,
|
commitmentHex: this.commitmentHex,
|
||||||
invoice: this.invoice,
|
invoice: this.invoice,
|
||||||
},
|
},
|
||||||
null,
|
null,
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
/* eslint-disable @typescript-eslint/no-explicit-any */
|
/* eslint-disable @typescript-eslint/no-explicit-any */
|
||||||
import { openDB, deleteDB, OpenDBCallbacks, IDBPDatabase } from 'idb';
|
import { openDB, deleteDB, OpenDBCallbacks, IDBPDatabase } from 'idb';
|
||||||
import { getConfig, NetId, NetIdType } from './networkConfig';
|
import { getConfig, NetIdType } from './networkConfig';
|
||||||
|
|
||||||
export const INDEX_DB_ERROR = 'A mutation operation was attempted on a database that did not allow mutations.';
|
export const INDEX_DB_ERROR = 'A mutation operation was attempted on a database that did not allow mutations.';
|
||||||
|
|
||||||
@ -364,11 +364,11 @@ export async function getIndexedDB(netId?: NetIdType) {
|
|||||||
|
|
||||||
const config = getConfig(netId);
|
const config = getConfig(netId);
|
||||||
|
|
||||||
const { tokens, nativeCurrency } = config;
|
const { tokens, nativeCurrency, registryContract, governanceContract } = config;
|
||||||
|
|
||||||
const stores = [...defaultState];
|
const stores = [...defaultState];
|
||||||
|
|
||||||
if (netId === NetId.MAINNET) {
|
if (registryContract) {
|
||||||
stores.push({
|
stores.push({
|
||||||
name: `registered_${netId}`,
|
name: `registered_${netId}`,
|
||||||
keyPath: 'ensName',
|
keyPath: 'ensName',
|
||||||
@ -380,7 +380,9 @@ export async function getIndexedDB(netId?: NetIdType) {
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (governanceContract) {
|
||||||
stores.push({
|
stores.push({
|
||||||
name: `governance_${netId}`,
|
name: `governance_${netId}`,
|
||||||
keyPath: 'eid',
|
keyPath: 'eid',
|
||||||
|
@ -14,6 +14,7 @@ export * from './mimc';
|
|||||||
export * from './multicall';
|
export * from './multicall';
|
||||||
export * from './networkConfig';
|
export * from './networkConfig';
|
||||||
export * from './pedersen';
|
export * from './pedersen';
|
||||||
|
export * from './permit';
|
||||||
export * from './prices';
|
export * from './prices';
|
||||||
export * from './providers';
|
export * from './providers';
|
||||||
export * from './relayerClient';
|
export * from './relayerClient';
|
||||||
|
242
src/permit.ts
Normal file
242
src/permit.ts
Normal file
@ -0,0 +1,242 @@
|
|||||||
|
import { ERC20Permit, ERC20Mock, TORN, PermitTornado } from '@tornado/contracts';
|
||||||
|
import {
|
||||||
|
BaseContract,
|
||||||
|
MaxUint256,
|
||||||
|
Provider,
|
||||||
|
Signature,
|
||||||
|
Signer,
|
||||||
|
solidityPackedKeccak256,
|
||||||
|
TypedDataEncoder,
|
||||||
|
TypedDataField,
|
||||||
|
} from 'ethers';
|
||||||
|
import { rBigInt } from './utils';
|
||||||
|
|
||||||
|
export interface PermitValue {
|
||||||
|
spender: string;
|
||||||
|
value: bigint;
|
||||||
|
nonce?: bigint;
|
||||||
|
deadline?: bigint;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface PermitCommitments {
|
||||||
|
denomination: bigint;
|
||||||
|
commitments: string[];
|
||||||
|
nonce?: bigint;
|
||||||
|
deadline?: bigint;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const permit2Address = '0x000000000022D473030F116dDEE9F6B43aC78BA3';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* From @uniswap/permit2-sdk ported for ethers.js v6
|
||||||
|
*/
|
||||||
|
export interface Witness {
|
||||||
|
witnessTypeName: string;
|
||||||
|
witnessType: {
|
||||||
|
[key: string]: TypedDataField[];
|
||||||
|
};
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||||
|
witness: any;
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function getPermitSignature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
}: PermitValue & {
|
||||||
|
Token: ERC20Permit | ERC20Mock | TORN;
|
||||||
|
signer?: Signer;
|
||||||
|
}) {
|
||||||
|
const sigSigner = (signer || Token.runner) as Signer & { address: string };
|
||||||
|
const provider = sigSigner.provider as Provider;
|
||||||
|
|
||||||
|
const [name, lastNonce, { chainId }] = await Promise.all([
|
||||||
|
Token.name(),
|
||||||
|
Token.nonces(sigSigner.address),
|
||||||
|
provider.getNetwork(),
|
||||||
|
]);
|
||||||
|
|
||||||
|
const DOMAIN_SEPARATOR = {
|
||||||
|
name,
|
||||||
|
version: '1',
|
||||||
|
chainId,
|
||||||
|
verifyingContract: Token.target as string,
|
||||||
|
};
|
||||||
|
|
||||||
|
const PERMIT_TYPE = {
|
||||||
|
Permit: [
|
||||||
|
{ name: 'owner', type: 'address' },
|
||||||
|
{ name: 'spender', type: 'address' },
|
||||||
|
{ name: 'value', type: 'uint256' },
|
||||||
|
{ name: 'nonce', type: 'uint256' },
|
||||||
|
{ name: 'deadline', type: 'uint256' },
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
|
return Signature.from(
|
||||||
|
await sigSigner.signTypedData(DOMAIN_SEPARATOR, PERMIT_TYPE, {
|
||||||
|
owner: sigSigner.address,
|
||||||
|
spender,
|
||||||
|
value,
|
||||||
|
nonce: nonce || lastNonce,
|
||||||
|
deadline: deadline || MaxUint256,
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function getPermitCommitmentsSignature({
|
||||||
|
PermitTornado,
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
denomination,
|
||||||
|
commitments,
|
||||||
|
nonce,
|
||||||
|
}: PermitCommitments & {
|
||||||
|
PermitTornado: PermitTornado;
|
||||||
|
Token: ERC20Permit | ERC20Mock | TORN;
|
||||||
|
signer?: Signer;
|
||||||
|
}) {
|
||||||
|
const value = BigInt(commitments.length) * denomination;
|
||||||
|
const commitmentsHash = solidityPackedKeccak256(['bytes32[]'], [commitments]);
|
||||||
|
|
||||||
|
return await getPermitSignature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender: PermitTornado.target as string,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline: BigInt(commitmentsHash),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function getPermit2Signature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender,
|
||||||
|
value: amount,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
witness,
|
||||||
|
}: PermitValue & {
|
||||||
|
Token: BaseContract;
|
||||||
|
signer?: Signer;
|
||||||
|
witness?: Witness;
|
||||||
|
}) {
|
||||||
|
const sigSigner = (signer || Token.runner) as Signer & { address: string };
|
||||||
|
const provider = sigSigner.provider as Provider;
|
||||||
|
|
||||||
|
const domain = {
|
||||||
|
name: 'Permit2',
|
||||||
|
chainId: (await provider.getNetwork()).chainId,
|
||||||
|
verifyingContract: permit2Address,
|
||||||
|
};
|
||||||
|
|
||||||
|
const types: {
|
||||||
|
[key: string]: TypedDataField[];
|
||||||
|
} = !witness
|
||||||
|
? {
|
||||||
|
PermitTransferFrom: [
|
||||||
|
{ name: 'permitted', type: 'TokenPermissions' },
|
||||||
|
{ name: 'spender', type: 'address' },
|
||||||
|
{ name: 'nonce', type: 'uint256' },
|
||||||
|
{ name: 'deadline', type: 'uint256' },
|
||||||
|
],
|
||||||
|
TokenPermissions: [
|
||||||
|
{ name: 'token', type: 'address' },
|
||||||
|
{ name: 'amount', type: 'uint256' },
|
||||||
|
],
|
||||||
|
}
|
||||||
|
: {
|
||||||
|
PermitWitnessTransferFrom: [
|
||||||
|
{ name: 'permitted', type: 'TokenPermissions' },
|
||||||
|
{ name: 'spender', type: 'address' },
|
||||||
|
{ name: 'nonce', type: 'uint256' },
|
||||||
|
{ name: 'deadline', type: 'uint256' },
|
||||||
|
{ name: 'witness', type: witness.witnessTypeName },
|
||||||
|
],
|
||||||
|
TokenPermissions: [
|
||||||
|
{ name: 'token', type: 'address' },
|
||||||
|
{ name: 'amount', type: 'uint256' },
|
||||||
|
],
|
||||||
|
...witness.witnessType,
|
||||||
|
};
|
||||||
|
|
||||||
|
const values: {
|
||||||
|
permitted: {
|
||||||
|
token: string;
|
||||||
|
amount: bigint;
|
||||||
|
};
|
||||||
|
spender: string;
|
||||||
|
nonce: bigint;
|
||||||
|
deadline: bigint;
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||||
|
witness?: any;
|
||||||
|
} = {
|
||||||
|
permitted: {
|
||||||
|
token: Token.target as string,
|
||||||
|
amount,
|
||||||
|
},
|
||||||
|
spender,
|
||||||
|
// Sorted nonce are not required for Permit2
|
||||||
|
nonce: nonce || rBigInt(16),
|
||||||
|
deadline: deadline || MaxUint256,
|
||||||
|
};
|
||||||
|
|
||||||
|
if (witness) {
|
||||||
|
values.witness = witness.witness;
|
||||||
|
}
|
||||||
|
|
||||||
|
const hash = new TypedDataEncoder(types).hash(values);
|
||||||
|
|
||||||
|
const signature = Signature.from(await sigSigner.signTypedData(domain, types, values));
|
||||||
|
|
||||||
|
return {
|
||||||
|
domain,
|
||||||
|
types,
|
||||||
|
values,
|
||||||
|
hash,
|
||||||
|
signature,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function getPermit2CommitmentsSignature({
|
||||||
|
PermitTornado,
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
denomination,
|
||||||
|
commitments,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
}: PermitCommitments & {
|
||||||
|
PermitTornado: PermitTornado;
|
||||||
|
Token: BaseContract;
|
||||||
|
signer?: Signer;
|
||||||
|
}) {
|
||||||
|
const value = BigInt(commitments.length) * denomination;
|
||||||
|
const commitmentsHash = solidityPackedKeccak256(['bytes32[]'], [commitments]);
|
||||||
|
|
||||||
|
return await getPermit2Signature({
|
||||||
|
Token,
|
||||||
|
signer,
|
||||||
|
spender: PermitTornado.target as string,
|
||||||
|
value,
|
||||||
|
nonce,
|
||||||
|
deadline,
|
||||||
|
witness: {
|
||||||
|
witnessTypeName: 'PermitCommitments',
|
||||||
|
witnessType: {
|
||||||
|
PermitCommitments: [
|
||||||
|
{ name: 'instance', type: 'address' },
|
||||||
|
{ name: 'commitmentsHash', type: 'bytes32' },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
witness: {
|
||||||
|
instance: PermitTornado.target,
|
||||||
|
commitmentsHash,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
121
yarn.lock
121
yarn.lock
@ -623,10 +623,10 @@
|
|||||||
"@metamask/superstruct" "^3.1.0"
|
"@metamask/superstruct" "^3.1.0"
|
||||||
"@metamask/utils" "^9.0.0"
|
"@metamask/utils" "^9.0.0"
|
||||||
|
|
||||||
"@metamask/eth-sig-util@^7.0.3":
|
"@metamask/eth-sig-util@^8.0.0":
|
||||||
version "7.0.3"
|
version "8.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/@metamask/eth-sig-util/-/eth-sig-util-7.0.3.tgz#be9e444fe0b8474c04e2ff42fd983173767f6ac0"
|
resolved "https://registry.yarnpkg.com/@metamask/eth-sig-util/-/eth-sig-util-8.0.0.tgz#6310d93cd1101cab3cc6bc2a1ff526290ed2695b"
|
||||||
integrity sha512-PAtGnOkYvh90k2lEZldq/FK7GTLF6WxE+2bV85PoA3pqlJnmJCAY62tuvxHSwnVngSKlc4mcNvjnUg2eYO6JGg==
|
integrity sha512-IwE6aoxUL39IhmsAgE4nk+OZbNo+ThFZRNsUjE1pjdEa4MFpWzm1Rue4zJ5DMy1oUyZBi/aiCLMhdMnjl2bh2Q==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@ethereumjs/util" "^8.1.0"
|
"@ethereumjs/util" "^8.1.0"
|
||||||
"@metamask/abi-utils" "^2.0.4"
|
"@metamask/abi-utils" "^2.0.4"
|
||||||
@ -872,9 +872,9 @@
|
|||||||
"@noble/hashes" "~1.4.0"
|
"@noble/hashes" "~1.4.0"
|
||||||
"@scure/base" "~1.1.6"
|
"@scure/base" "~1.1.6"
|
||||||
|
|
||||||
"@tornado/contracts@git+https://git.tornado.ws/tornadocontrib/tornado-contracts.git#ece511f424dc811c3aec149a4bf0e3731c0598a4":
|
"@tornado/contracts@git+https://git.tornado.ws/tornadocontrib/tornado-contracts.git#1b1d707878c16a3dc60d295299d4f0e7ce6ba831":
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
resolved "git+https://git.tornado.ws/tornadocontrib/tornado-contracts.git#ece511f424dc811c3aec149a4bf0e3731c0598a4"
|
resolved "git+https://git.tornado.ws/tornadocontrib/tornado-contracts.git#1b1d707878c16a3dc60d295299d4f0e7ce6ba831"
|
||||||
dependencies:
|
dependencies:
|
||||||
"@openzeppelin/contracts" "5.0.2"
|
"@openzeppelin/contracts" "5.0.2"
|
||||||
"@openzeppelin/contracts-v3" "npm:@openzeppelin/contracts@3.2.0-rc.0"
|
"@openzeppelin/contracts-v3" "npm:@openzeppelin/contracts@3.2.0-rc.0"
|
||||||
@ -967,13 +967,20 @@
|
|||||||
dependencies:
|
dependencies:
|
||||||
undici-types "~6.19.2"
|
undici-types "~6.19.2"
|
||||||
|
|
||||||
"@types/node@22.7.5", "@types/node@^22.7.5":
|
"@types/node@22.7.5":
|
||||||
version "22.7.5"
|
version "22.7.5"
|
||||||
resolved "https://registry.yarnpkg.com/@types/node/-/node-22.7.5.tgz#cfde981727a7ab3611a481510b473ae54442b92b"
|
resolved "https://registry.yarnpkg.com/@types/node/-/node-22.7.5.tgz#cfde981727a7ab3611a481510b473ae54442b92b"
|
||||||
integrity sha512-jML7s2NAzMWc//QSJ1a3prpk78cOPchGvXJsC3C6R6PSMoooztvRVQEz89gmBTBY1SPMaqo5teB4uNHPdetShQ==
|
integrity sha512-jML7s2NAzMWc//QSJ1a3prpk78cOPchGvXJsC3C6R6PSMoooztvRVQEz89gmBTBY1SPMaqo5teB4uNHPdetShQ==
|
||||||
dependencies:
|
dependencies:
|
||||||
undici-types "~6.19.2"
|
undici-types "~6.19.2"
|
||||||
|
|
||||||
|
"@types/node@^22.7.9":
|
||||||
|
version "22.7.9"
|
||||||
|
resolved "https://registry.yarnpkg.com/@types/node/-/node-22.7.9.tgz#2bf2797b5e84702d8262ea2cf843c3c3c880d0e9"
|
||||||
|
integrity sha512-jrTfRC7FM6nChvU7X2KqcrgquofrWLFDeYC1hKfwNWomVvrn7JIksqf344WN2X/y8xrgqBd2dJATZV4GbatBfg==
|
||||||
|
dependencies:
|
||||||
|
undici-types "~6.19.2"
|
||||||
|
|
||||||
"@types/prettier@^2.1.1":
|
"@types/prettier@^2.1.1":
|
||||||
version "2.7.3"
|
version "2.7.3"
|
||||||
resolved "https://registry.yarnpkg.com/@types/prettier/-/prettier-2.7.3.tgz#3e51a17e291d01d17d3fc61422015a933af7a08f"
|
resolved "https://registry.yarnpkg.com/@types/prettier/-/prettier-2.7.3.tgz#3e51a17e291d01d17d3fc61422015a933af7a08f"
|
||||||
@ -984,62 +991,62 @@
|
|||||||
resolved "https://registry.yarnpkg.com/@types/resolve/-/resolve-1.20.2.tgz#97d26e00cd4a0423b4af620abecf3e6f442b7975"
|
resolved "https://registry.yarnpkg.com/@types/resolve/-/resolve-1.20.2.tgz#97d26e00cd4a0423b4af620abecf3e6f442b7975"
|
||||||
integrity sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==
|
integrity sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==
|
||||||
|
|
||||||
"@typescript-eslint/eslint-plugin@^8.9.0":
|
"@typescript-eslint/eslint-plugin@^8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.9.0.tgz#bf0b25305b0bf014b4b194a6919103d7ac2a7907"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.11.0.tgz#c3f087d20715fa94310b30666c08b3349e0ab084"
|
||||||
integrity sha512-Y1n621OCy4m7/vTXNlCbMVp87zSd7NH0L9cXD8aIpOaNlzeWxIK4+Q19A68gSmTNRZn92UjocVUWDthGxtqHFg==
|
integrity sha512-KhGn2LjW1PJT2A/GfDpiyOfS4a8xHQv2myUagTM5+zsormOmBlYsnQ6pobJ8XxJmh6hnHwa2Mbe3fPrDJoDhbA==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@eslint-community/regexpp" "^4.10.0"
|
"@eslint-community/regexpp" "^4.10.0"
|
||||||
"@typescript-eslint/scope-manager" "8.9.0"
|
"@typescript-eslint/scope-manager" "8.11.0"
|
||||||
"@typescript-eslint/type-utils" "8.9.0"
|
"@typescript-eslint/type-utils" "8.11.0"
|
||||||
"@typescript-eslint/utils" "8.9.0"
|
"@typescript-eslint/utils" "8.11.0"
|
||||||
"@typescript-eslint/visitor-keys" "8.9.0"
|
"@typescript-eslint/visitor-keys" "8.11.0"
|
||||||
graphemer "^1.4.0"
|
graphemer "^1.4.0"
|
||||||
ignore "^5.3.1"
|
ignore "^5.3.1"
|
||||||
natural-compare "^1.4.0"
|
natural-compare "^1.4.0"
|
||||||
ts-api-utils "^1.3.0"
|
ts-api-utils "^1.3.0"
|
||||||
|
|
||||||
"@typescript-eslint/parser@^8.9.0":
|
"@typescript-eslint/parser@^8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-8.9.0.tgz#0cecda6def8aef95d7c7098359c0fda5a362d6ad"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-8.11.0.tgz#2ad1481388dc1c937f50b2d138c9ca57cc6c5cce"
|
||||||
integrity sha512-U+BLn2rqTTHnc4FL3FJjxaXptTxmf9sNftJK62XLz4+GxG3hLHm/SUNaaXP5Y4uTiuYoL5YLy4JBCJe3+t8awQ==
|
integrity sha512-lmt73NeHdy1Q/2ul295Qy3uninSqi6wQI18XwSpm8w0ZbQXUpjCAWP1Vlv/obudoBiIjJVjlztjQ+d/Md98Yxg==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@typescript-eslint/scope-manager" "8.9.0"
|
"@typescript-eslint/scope-manager" "8.11.0"
|
||||||
"@typescript-eslint/types" "8.9.0"
|
"@typescript-eslint/types" "8.11.0"
|
||||||
"@typescript-eslint/typescript-estree" "8.9.0"
|
"@typescript-eslint/typescript-estree" "8.11.0"
|
||||||
"@typescript-eslint/visitor-keys" "8.9.0"
|
"@typescript-eslint/visitor-keys" "8.11.0"
|
||||||
debug "^4.3.4"
|
debug "^4.3.4"
|
||||||
|
|
||||||
"@typescript-eslint/scope-manager@8.9.0":
|
"@typescript-eslint/scope-manager@8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-8.9.0.tgz#c98fef0c4a82a484e6a1eb610a55b154d14d46f3"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-8.11.0.tgz#9d399ce624118966732824878bc9a83593a30405"
|
||||||
integrity sha512-bZu9bUud9ym1cabmOYH9S6TnbWRzpklVmwqICeOulTCZ9ue2/pczWzQvt/cGj2r2o1RdKoZbuEMalJJSYw3pHQ==
|
integrity sha512-Uholz7tWhXmA4r6epo+vaeV7yjdKy5QFCERMjs1kMVsLRKIrSdM6o21W2He9ftp5PP6aWOVpD5zvrvuHZC0bMQ==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@typescript-eslint/types" "8.9.0"
|
"@typescript-eslint/types" "8.11.0"
|
||||||
"@typescript-eslint/visitor-keys" "8.9.0"
|
"@typescript-eslint/visitor-keys" "8.11.0"
|
||||||
|
|
||||||
"@typescript-eslint/type-utils@8.9.0":
|
"@typescript-eslint/type-utils@8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-8.9.0.tgz#aa86da3e4555fe7c8b42ab75e13561c4b5a8dfeb"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-8.11.0.tgz#b7f9e6120c1ddee8a1a07615646642ad85fc91b5"
|
||||||
integrity sha512-JD+/pCqlKqAk5961vxCluK+clkppHY07IbV3vett97KOV+8C6l+CPEPwpUuiMwgbOz/qrN3Ke4zzjqbT+ls+1Q==
|
integrity sha512-ItiMfJS6pQU0NIKAaybBKkuVzo6IdnAhPFZA/2Mba/uBjuPQPet/8+zh5GtLHwmuFRShZx+8lhIs7/QeDHflOg==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@typescript-eslint/typescript-estree" "8.9.0"
|
"@typescript-eslint/typescript-estree" "8.11.0"
|
||||||
"@typescript-eslint/utils" "8.9.0"
|
"@typescript-eslint/utils" "8.11.0"
|
||||||
debug "^4.3.4"
|
debug "^4.3.4"
|
||||||
ts-api-utils "^1.3.0"
|
ts-api-utils "^1.3.0"
|
||||||
|
|
||||||
"@typescript-eslint/types@8.9.0":
|
"@typescript-eslint/types@8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-8.9.0.tgz#b733af07fb340b32e962c6c63b1062aec2dc0fe6"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-8.11.0.tgz#7c766250502097f49bbc2e651132e6bf489e20b8"
|
||||||
integrity sha512-SjgkvdYyt1FAPhU9c6FiYCXrldwYYlIQLkuc+LfAhCna6ggp96ACncdtlbn8FmnG72tUkXclrDExOpEYf1nfJQ==
|
integrity sha512-tn6sNMHf6EBAYMvmPUaKaVeYvhUsrE6x+bXQTxjQRp360h1giATU0WvgeEys1spbvb5R+VpNOZ+XJmjD8wOUHw==
|
||||||
|
|
||||||
"@typescript-eslint/typescript-estree@8.9.0":
|
"@typescript-eslint/typescript-estree@8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-8.9.0.tgz#1714f167e9063062dc0df49c1d25afcbc7a96199"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-8.11.0.tgz#35fe5d3636fc5727c52429393415412e552e222b"
|
||||||
integrity sha512-9iJYTgKLDG6+iqegehc5+EqE6sqaee7kb8vWpmHZ86EqwDjmlqNNHeqDVqb9duh+BY6WCNHfIGvuVU3Tf9Db0g==
|
integrity sha512-yHC3s1z1RCHoCz5t06gf7jH24rr3vns08XXhfEqzYpd6Hll3z/3g23JRi0jM8A47UFKNc3u/y5KIMx8Ynbjohg==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@typescript-eslint/types" "8.9.0"
|
"@typescript-eslint/types" "8.11.0"
|
||||||
"@typescript-eslint/visitor-keys" "8.9.0"
|
"@typescript-eslint/visitor-keys" "8.11.0"
|
||||||
debug "^4.3.4"
|
debug "^4.3.4"
|
||||||
fast-glob "^3.3.2"
|
fast-glob "^3.3.2"
|
||||||
is-glob "^4.0.3"
|
is-glob "^4.0.3"
|
||||||
@ -1047,22 +1054,22 @@
|
|||||||
semver "^7.6.0"
|
semver "^7.6.0"
|
||||||
ts-api-utils "^1.3.0"
|
ts-api-utils "^1.3.0"
|
||||||
|
|
||||||
"@typescript-eslint/utils@8.9.0":
|
"@typescript-eslint/utils@8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-8.9.0.tgz#748bbe3ea5bee526d9786d9405cf1b0df081c299"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-8.11.0.tgz#4480d1e9f2bb18ea3510c79f870a1aefc118103d"
|
||||||
integrity sha512-PKgMmaSo/Yg/F7kIZvrgrWa1+Vwn036CdNUvYFEkYbPwOH4i8xvkaRlu148W3vtheWK9ckKRIz7PBP5oUlkrvQ==
|
integrity sha512-CYiX6WZcbXNJV7UNB4PLDIBtSdRmRI/nb0FMyqHPTQD1rMjA0foPLaPUV39C/MxkTd/QKSeX+Gb34PPsDVC35g==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@eslint-community/eslint-utils" "^4.4.0"
|
"@eslint-community/eslint-utils" "^4.4.0"
|
||||||
"@typescript-eslint/scope-manager" "8.9.0"
|
"@typescript-eslint/scope-manager" "8.11.0"
|
||||||
"@typescript-eslint/types" "8.9.0"
|
"@typescript-eslint/types" "8.11.0"
|
||||||
"@typescript-eslint/typescript-estree" "8.9.0"
|
"@typescript-eslint/typescript-estree" "8.11.0"
|
||||||
|
|
||||||
"@typescript-eslint/visitor-keys@8.9.0":
|
"@typescript-eslint/visitor-keys@8.11.0":
|
||||||
version "8.9.0"
|
version "8.11.0"
|
||||||
resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-8.9.0.tgz#5f11f4d9db913f37da42776893ffe0dd1ae78f78"
|
resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-8.11.0.tgz#273de1cbffe63d9f9cd7dfc20b5a5af66310cb92"
|
||||||
integrity sha512-Ht4y38ubk4L5/U8xKUBfKNYGmvKvA1CANoxiTRMM+tOLk3lbF3DvzZCxJCRSE+2GdCMSh6zq9VZJc3asc1XuAA==
|
integrity sha512-EaewX6lxSjRJnc+99+dqzTeoDZUfyrA52d2/HRrkI830kgovWsmIiTfmr0NZorzqic7ga+1bS60lRBUgR3n/Bw==
|
||||||
dependencies:
|
dependencies:
|
||||||
"@typescript-eslint/types" "8.9.0"
|
"@typescript-eslint/types" "8.11.0"
|
||||||
eslint-visitor-keys "^3.4.3"
|
eslint-visitor-keys "^3.4.3"
|
||||||
|
|
||||||
"@ungap/structured-clone@^1.2.0":
|
"@ungap/structured-clone@^1.2.0":
|
||||||
|
Loading…
x
Reference in New Issue
Block a user