import { CIRCOM_P as e } from "../../constants/protocol.constants.mjs";
import { poseidonHash as t } from "../../crypto/poseidon.mjs";
import { babyJubInstance as n } from "../../crypto/babyJub.mjs";
import { AttachableMemoryCacheDevice as r } from "../cacheDevices/AttachableMemoryCacheDevice.mjs";
import { getCircomSign as i } from "./keyUtils.mjs";
import { ethers as a } from "ethers";
import { Keypair as o, PublicKey as s } from "@solana/web3.js";
import c from "bs58";
import l from "libsodium-wrappers";
import u from "tweetnacl";
//#region libs/shared/common/src/data-structures/crypto-keys/keys.ts
var d = new r(), f = new r(), p = class {
	signature;
	shieldedPrivateKey;
	constructor(e, t) {
		this.signature = e, this.shieldedPrivateKey = t;
	}
	getSignature() {
		return this.requireSignature(), this.signature;
	}
	setSignature(e) {
		this.signature = e;
	}
	requireSignature() {
		if (!this.signature) throw Error("No signature provided");
	}
	requireKeyMaterial() {
		if (!this.signature && !this.shieldedPrivateKey) throw Error("No signature or shielded private key provided");
	}
	verifyMessage(e) {
		return this.requireSignature(), a.verifyMessage(e, this.signature);
	}
	verifySolanaMessage(e, t) {
		this.requireSignature();
		let n = new TextEncoder().encode(e), r = a.getBytes(this.signature), i = new s(t).toBytes();
		return u.sign.detached.verify(n, r, i);
	}
	getShieldedPrivateKey = () => (this.requireKeyMaterial(), this.shieldedPrivateKey ||= a.keccak256(this.signature), this.shieldedPrivateKey);
	getShieldedPublicKey = () => (this.requireKeyMaterial(), t(this.getShieldedPrivateKey()));
	getShieldedPrivateKeyFromNonce = (e) => {
		this.requireKeyMaterial();
		let n = t(e, this.getShieldedPrivateKey(), this.getShieldedPublicKey());
		return a.keccak256(a.toUtf8Bytes(`hinkal-offchain-shielded-key:${n}`));
	};
	getDerivedEthereumAddress = () => (this.requireKeyMaterial(), new a.Wallet(this.getShieldedPrivateKey()).address);
	getDerivedSolanaPublicKey = () => (this.requireKeyMaterial(), o.fromSeed(a.getBytes(this.getShieldedPrivateKey())).publicKey.toBase58());
	getAccessKey = () => (this.requireKeyMaterial(), t(this.getShieldedPrivateKey(), this.getShieldedPublicKey()));
	getSignerPrivateKeyFromNonce = (e) => {
		this.requireKeyMaterial();
		let n = t(e, this.getShieldedPrivateKey(), this.getShieldedPublicKey());
		return a.keccak256(a.toUtf8Bytes(n));
	};
	getSignerSolanaPrivateKeyFromNonce = (e) => {
		let t = this.getSignerPrivateKeyFromNonce(e), n = a.getBytes(t), r = o.fromSeed(n);
		return c.encode(r.secretKey);
	};
	getWalletSalt = (e) => (this.requireKeyMaterial(), t(this.getShieldedPublicKey(), this.getShieldedPrivateKey(), e));
	getInHinkalAddress = (e) => {
		this.requireKeyMaterial();
		let n = t(this.getShieldedPrivateKey(), e);
		return BigInt(n);
	};
	getBackendToken = () => (this.requireKeyMaterial(), t(this.getAccessKey(), this.getShieldedPublicKey()));
	static getRandomizedStealthPair = d.attach((t, r) => {
		let i = n(), a = t * (BigInt(r) % e) % e, o = i.mulPointEscalar(i.Base8, t), s = i.mulPointEscalar(i.Base8, a);
		return {
			H0: [BigInt(i.F.toString(o[0])), BigInt(i.F.toString(o[1]))],
			H1: [BigInt(i.F.toString(s[0])), BigInt(i.F.toString(s[1]))]
		};
	});
	static getStealthAddressCompressedPoints = (e, t) => {
		let { H0: n, H1: r } = this.getRandomizedStealthPair(e, t), [a, o] = [n, r].map((e) => BigInt(e[1]) + 2n ** 255n * i(e[0]));
		return {
			h0: a,
			h1: o
		};
	};
	static getStealthAddress = f.attach((e, n) => {
		let { H0: r, H1: a } = this.getRandomizedStealthPair(e, n);
		return t(2n * i(r[0]) + i(a[0]), r[1], a[1]);
	});
	static getStealthAddressWithEKey = (e, t) => ({
		stealthAddress: this.getStealthAddress(e, t),
		encryptionKey: this.getEncryptionKeyPair(t).publicKey
	});
	static checkSignature = (e, t, n, r) => {
		let { h0: i, h1: a } = this.getStealthAddressCompressedPoints(e, r);
		return t === i && n === a;
	};
	static getEncryptionKeyPair = (e) => {
		let t = l.crypto_box_seed_keypair(a.getBytes(e));
		return {
			privateKey: a.hexlify(t.privateKey),
			publicKey: a.hexlify(t.publicKey)
		};
	};
};
//#endregion
export { p as UserKeys, f as stealthAddressCacheDevice, d as stealthPairCacheDevice };
