fhEVM
WebsiteLibrariesProduct & ServicesDevelopersSupport
0.6
0.6
  • Welcome to fhEVM
  • White paper
  • Getting Started
    • Overview
    • Quick Start
      • Remix
        • 1. Setting up Remix
        • 2. Connect your wallet to Remix
        • 3. Deploying ConfidentialERC20
        • 4. Interacting with the contract
      • Hardhat
        • Prerequisites
        • 1. Setting up Hardhat
        • 2. Writing contracts
        • 3. Testing in mocked mode
        • 4. Deploying the contract
        • 5. Interacting with the contract
  • Tutorials
    • See all tutorials
  • Smart contract
    • Key features
    • Configuration
    • FhEVM contracts
    • Supported types
    • Operations on encrypted types
    • Access Control List
      • ACL examples
    • Encrypted Inputs
    • Decryption
      • Decryption
      • Decryption in depth
      • Re-encryption
    • If sentences
    • Branching in FHE
    • AsEbool, asEuintXX, asEaddress and asEbytesXX operations
    • Generate random numbers
    • Error handling
    • Gas estimation
    • Debug decrypt
    • Using Foundry
  • Frontend
    • Setup
    • Build a web application
    • Using React.js
    • Using Next.js
    • Using Vue.js
    • Using Node or Typescript
    • Using the CLI
    • Common webpack errors
  • Explanations
    • Architectural overview
    • FHE on blockchain
    • fhEVM components
    • Encryption, decryption, re-encryption, and computation
  • References
    • Table of all addresses
    • Smart contracts - fhEVM API
    • Frontend - fhevmjs lib
    • Repositories
  • Developer
    • Contributing
    • Development roadmap
    • Release note
    • Feature request
    • Bug report
    • Status
Powered by GitBook

Libraries

  • TFHE-rs
  • Concrete
  • Concrete ML
  • fhEVM

Developers

  • Blog
  • Documentation
  • Github
  • FHE resources

Company

  • About
  • Introduction to FHE
  • Media
  • Careers
On this page
  • Init (browser)
  • Create instance
  • Input
  • input.addBool, input.add8, ...
  • input.encrypt and input.send
  • Re-encryption
  • Keypair
  • Re-encryption

Was this helpful?

Export as PDF
  1. References

Frontend - fhevmjs lib

PreviousSmart contracts - fhEVM APINextRepositories

Last updated 4 months ago

Was this helpful?

This document provides an overview of the fhevmjs library, detailing its initialization, instance creation, input handling, encryption, and re-encryption processes.

is designed to assist in creating encrypted inputs and retrieving re-encryption data off-chain through a gateway. The library works with any fhEVM and fhEVM Coprocessors.

Init (browser)

If you are using fhevmjs in a web application, you need to initialize it before creating an instance. To do this, you should call initFhevm and wait for the promise to resolve.

import { FhevmInstance, createInstance } from "fhevmjs/node";

initFhevm().then(() => {
  const instance = await createInstance({
    network: window.ethereum,
    gatewayUrl: "https://gateway.sepolia.zama.ai",
    kmsContractAddress: "0x9D6891A6240D6130c54ae243d8005063D05fE14b",
    aclContractAddress: "0xFee8407e2f5e3Ee68ad77cAE98c434e637f516e5",
  });
});

Create instance

This function returns an instance of fhevmjs, which accepts an object containing:

  • kmsContractAddress: the address of the KMSVerifier contract;

  • aclContractAddress: the address of the ACL contract;

  • networkUrl or network: the URL or Eip1193 object provided by window.ethereum - used to fetch chainId and KMS nodes' public key

  • gatewayUrl: the URL of the gateway - used to retrieve the public key, ZKPoK public parameters and send inputs and get reencryption

  • chainId (optional): the chainId of the network

  • publicKey (optional): if the public key has been fetched separately or stored in cache, you can provide it

  • publicParams (optional): if the public params has been fetched separately or stored in cache, you can provide it

import { createInstance } from "fhevmjs";

const instance = await createInstance({
  networkUrl: "https://eth-sepolia.public.blastapi.io",
  gatewayUrl: "https://gateway.sepolia.zama.ai",
  kmsContractAddress: "0x9D6891A6240D6130c54ae243d8005063D05fE14b",
  aclContractAddress: "0xFee8407e2f5e3Ee68ad77cAE98c434e637f516e5",
});

Using window.ethereum object:

import { FhevmInstance, createInstance } from "fhevmjs/bundle";

const instance = await createInstance({
  network: window.ethereum,
  gatewayUrl: "https://gateway.sepolia.zama.ai",
  kmsContractAddress: "0x9D6891A6240D6130c54ae243d8005063D05fE14b",
  aclContractAddress: "0xFee8407e2f5e3Ee68ad77cAE98c434e637f516e5",
});

Input

This method creates an encrypted input and returns an input object. It requires both the user address and the contract address to ensure the encrypted input isn't reused inappropriately in a different context. An input can include multiple values of various types, resulting in a single ciphertext that packs these values.

const userAddress = "0xa5e1defb98EFe38EBb2D958CEe052410247F4c80";
const contractAddress = "0xfCefe53c7012a075b8a711df391100d9c431c468";

const input = instance.createEncryptedInput(contractAddress, userAddress);

input.addBool, input.add8, ...

Input object has different method to add values:

  • addBool

  • add4

  • add8

  • add16

  • add32

  • add64

  • add128

  • add256

  • addBytes64

  • addBytes128

  • addBytes256

  • addAddress

const input = instance.createEncryptedInput(contractAddress, userAddress);

input.addBool(true);
input.add16(239);
input.addAddress("0xa5e1defb98EFe38EBb2D958CEe052410247F4c80");
input.addBool(true);

input.encrypt and input.send

These methods process values and return the necessary data for use on the blockchain. The encrypt method encrypts these values and provides parameters for use. The send method encrypts, dispatches the ciphertext and proof to the coprocessor, and returns the required parameters.

input.addBool(true);
input.addBool(true);
input.add8(4);
const inputs = await input.encrypt(); // or input.send() if using a coprocessor

contract.myExample(
  "0xa5e1defb98EFe38EBb2D958CEe052410247F4c80",
  inputs.handles[0],
  32,
  inputs.handles[1],
  inputs.handles[2],
  true,
  inputs.inputProof,
);

Re-encryption

Keypair

A keypair consists of a private key and a public key, both generated by the dApp. These keys are used to reencrypt a blockchain ciphertext, allowing it to be securely transferred to user-specific keypairs.

// Generate the private and public key, used for the reencryption
const { publicKey, privateKey } = instance.generateKeypair();

Verifying that the public key used in the reencryption process belongs to the user requires the user to sign the public key linked to a specific contract address. This signature allows any ciphertext allowed for the user and the contract can be reencrypted using the signed public key. To streamline user interaction during the signature process, we utilize the EIP712 standard as the object to be signed.

// Create an EIP712 object for the user to sign.
const eip712 = instance.createEIP712(publicKey, CONTRACT_ADDRESS);

This eip712 can be signed using eth_signTypedData_v4 for example in a browser:

const params = [USER_ADDRESS, JSON.stringify(eip712)];
const signature = await window.ethereum.request({ method: "eth_signTypedData_v4", params });

Note: it is recommended to store the keypair and the signature in the user's browser to avoid re-requesting signature on every user connection.

Re-encryption

Reencrypt method will use the gatewayUrl to get the reencryption of a ciphertext and decrypt it.

const handle = await erc20.balanceOf(userAddress); // returns the handle of hte ciphertext as a uint256 (bigint)
const myBalance = await instance.reencrypt(handle, privateKey, publicKey, signature, contractAddress, userAddress);
fhevmjs