npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

ethers-upgrade-v6

v0.1.0

Published

An automated codemod to migrate ethers.js v5 to v6

Readme

ethers-upgrade-v6

Codemod pipeline for migrating ethers.js v5 codebases to v6-compatible APIs.

Table of Contents

Overview

This repository contains a composed jscodeshift transform that runs multiple migration steps in a deterministic order.
Its goal is to automate common v5-to-v6 changes while staying conservative for ambiguous patterns.

The codemod entrypoint is src/index.ts, and the workflow integration points at that file via workflow.yaml.

How It Works

The main transform in src/index.ts:

  • Executes each transform step sequentially on the latest source.
  • Tracks whether each step changed the file.
  • Produces per-step and final summary reports (configurable).
  • Fails fast with enriched error context (step name + file path) if a step throws.

If no step changes a file, the original source is returned unchanged.

Pipeline Order

Transforms run in this exact order:

  1. normalizeImports
  2. bignumber-to-bigint
  3. providers
  4. contracts
  5. normalizeUtils
  6. constants

Ordering matters because earlier transforms normalize imports and namespaces that later transforms depend on.

Transform Coverage

1) normalizeImports

Normalizes and consolidates legacy imports:

  • Rewrites subpath imports to root ethers:
    • ethers/lib/*, ethers/lib.esm/*, ethers/utils*, ethers/providers*
    • @ethersproject/*
  • Removes deprecated root namespace imports from ethers:
    • providers, utils, BigNumber, constants, errors, logger, wordlists
  • Merges duplicate root ethers named imports, preserving type vs value import separation.
  • Keeps side-effect/default/namespace import declarations intact.

2) bignumber-to-bigint

Migrates safe constructor patterns:

  • ethers.BigNumber.from(x) -> BigInt(x)
  • BigNumber.from(x) -> BigInt(x) (when bound to the ethers import)

For chained BigNumber flows (for example .pow(), .add() chains), it does not auto-rewrite logic and instead adds:

  • TODO: v6-bigint manual BigNumber chain migration

3) providers

Applies provider-related migrations:

  • Flattens ethers.providers.* -> ethers.*
  • Renames:
    • Web3Provider -> BrowserProvider
    • StaticJsonRpcProvider -> JsonRpcProvider
  • Rewrites new StaticJsonRpcProvider(url, network?, options?) to v6 constructor shape and injects staticNetwork safely.
  • Rewrites likely provider calls:
    • sendTransaction(...) -> broadcastTransaction(...)
    • await provider.getGasPrice() -> (await provider.getFeeData()).gasPrice
  • Rewrites fee-data patterns:
    • lastBaseFeePerGas -> maxFeePerGas
    • maxPriorityFeePerGas + lastBaseFeePerGas (and .add(...) variant) -> maxFeePerGas
  • Adds TODO when getSigner() appears un-awaited on likely provider objects:
    • TODO: v6-provider getSigner() is now async; add await

4) contracts

Migrates removed contract method-bucket calls:

  • contract.functions.foo(args) -> contract.foo(args)
  • contract.callStatic.foo(args) -> contract.foo.staticCall(args)
  • contract.estimateGas.foo(args) -> contract.foo.estimateGas(args)
  • contract.populateTransaction.foo(args) -> contract.foo.populateTransaction(args)

Uses conservative receiver heuristics (contract, *Contract, this.contract) and skips computed access forms.

5) normalizeUtils

Normalizes ethers.utils usage:

  • Flattens ethers.utils.<name> -> ethers.<name> where supported.
  • Applies known utility renames:
    • hexDataSlice -> dataSlice
    • hexZeroPad -> zeroPadValue
    • hexValue -> toQuantity
    • arrayify -> getBytes
    • formatBytes32String -> encodeBytes32String
    • parseBytes32String -> decodeBytes32String
    • solidityPack -> solidityPacked
    • solidityKeccak256 -> solidityPackedKeccak256
    • soliditySha256 -> solidityPackedSha256
  • Signature helper migration:
    • splitSignature(x) / ethers.utils.splitSignature(x) -> ethers.Signature.from(x)
    • joinSignature(x) / ethers.utils.joinSignature(x) -> ethers.Signature.from(x).serialized
  • Transaction helper migration:
    • parseTransaction(tx) -> ethers.Transaction.from(tx)
    • serializeTransaction(tx, sig?) -> ethers.Transaction.from({...}).serialized
  • AbiCoder migration:
    • ethers.utils.defaultAbiCoder -> ethers.AbiCoder.defaultAbiCoder()
    • Also ensures AbiCoder.defaultAbiCoder usage becomes a call.
  • Numeric hexlify migration:
    • ethers.utils.hexlify(<number-like>) -> ethers.toBeHex(...)
  • defineReadOnly migration:
    • ethers.utils.defineReadOnly(obj, key, value) -> ethers.defineProperties(obj, { [key]: value })
  • Adds TODOs for removed utils that require manual migration:
    • TODO: v6-utils '<name>' removed in v6; migrate manually

6) constants

Flattens ethers.constants.* and handles numeric constants:

  • Renamed constants:
    • AddressZero -> ethers.ZeroAddress
    • HashZero -> ethers.ZeroHash
    • MaxUint256 -> ethers.MaxUint256
    • MaxInt256 -> ethers.MaxInt256
    • MinInt256 -> ethers.MinInt256
    • WeiPerEther -> ethers.WeiPerEther
    • EtherSymbol -> ethers.EtherSymbol
  • Numeric namespace constants:
    • NegativeOne -> BigInt("-1")
    • Zero -> BigInt("0")
    • One -> BigInt("1")
    • Two -> BigInt("2")

Also handles constants.* references when constants is bound to ethers.constants.

Manual Follow-Up TODOs

This codemod intentionally inserts TODO comments when migration requires semantic review:

  • TODO: v6-bigint manual BigNumber chain migration
  • TODO: v6-provider getSigner() is now async; add await
  • TODO: v6-utils '<name>' removed in v6; migrate manually

Search for TODO: v6- after running the codemod and resolve each case manually.

Usage

In codemod workflow

workflow.yaml is configured to run src/index.ts as the transform entrypoint.

Local fixture run

Run the full pipeline on test fixtures:

yarn test:fixture

This reads src/tests/fixtures/input.ts and writes src/tests/fixtures/output.ts.

Pipeline Options

The top-level transform in src/index.ts accepts:

  • log (default: true) - enable/disable reporting.
  • reportUnchangedSteps (default: false) - include per-step "no changes" logs.
  • summaryOnly (default: false) - emit only final per-file summary.
  • maxReportHunks (default: 3) - maximum changed hunks reported per step.

Project Structure

  • src/index.ts - orchestrates pipeline execution and reporting.
  • src/transforms/*.ts - individual migration transforms.
  • src/transforms/*.test.ts - transform-specific tests.
  • src/tests/fixtures/* - end-to-end fixture input/output.
  • scripts/run-fixture.ts - fixture runner for quick verification.
  • workflow.yaml - codemod workflow configuration.

Development

yarn install
yarn test
yarn test:coverage
yarn typecheck
yarn build

Safety and Limitations

  • The codemod is designed to be idempotent for covered patterns.
  • It uses heuristics for provider/contract detection to reduce false positives.
  • Ambiguous or behavior-sensitive patterns are intentionally left for manual migration via TODO markers.
  • Always run on a dedicated branch and review diffs before merging.