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 🙏

© 2024 – Pkg Stats / Ryan Hefner

evm-watcher

v1.0.2

Published

Fault tolerant event watcher for topics on the ethereum virtual machine.

Downloads

5

Readme

EVM Watcher

This NPM Module is a thin wrapper around ethersjs module.

This is only used to talk to ethereum nodes, and follow along in the blockchain watching for specific events.

Then install it into your project

npm install evm-watcher

Then import it with it's types and everything.

import { EvmWatcher } from "evm-watcher";

Examples

See the src/example.ts file for a working example. Try it out by cloning this repo locally, and running:

npm install

ts-node ./src/example.ts

How It Works

IMPORTANT: This module requires that you bring your own state. If you run a stateless application, it will not be able to persist important data between subsequent invocations (page-refresh, restarts, etc.) You will need a place for this module to keep track of the "last block processed", but should not need to worry about the minutia of using/refreshing this state.

Create some initial params to bound our ethereum "worker".

const initialParams = {
  // startBlock (required) must be an integer > -1. No decimals, or abstract numerical values (e.g.: Infinity).
  startBlock: 12508210,
  // endBlock (optional) default = undefined, meaning: run forever.
  endBlock: undefined,
  // network (optional) default = ETHERUM_MAINNET
  network: SupportedNetwork.ETHERUM_MAINNET,
  // maxLogBatchSize (optional) default = 10
  maxLogBatchSize: 100,
};

Create a Data Access Object matching the expected interface, capable of reading/writing to state.

const dao = {
  getWorkerState: async ({
    startBlock,
    endBlock,
  }: {
    startBlock: number;
    endBlock: number;
  }) => {
    // ... Do anything! :D
    // ... e.g.: query postgres, or read form S3, call your grandmother...
    // This just needs to return an object matching the interface of the WorkerState.
    return testState; // < -- replace with your data
  },
  setLastBlockProcessed: async (lastBlock: number) => {
    // Again, do whatever you need to do here, but this must write lastBlock to state, such that it is retrieved when `getWorkerState` is called.
    testState.lastBlockProcessed = lastBlock;
    return undefined;
  },
};

Choose an event filter.

// This is an example of an event filter that the Aggregator uses.
const TOPIC_TRANSFER_721_OR_20 =
  "0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef";
const TOPIC_TRANSFER_1155 =
  "0xc3d58168c5ae7397731d063d5bbf3d657854427343f4c083240f7aacaa2d0f62";
const TOPIC_TRANSFER_BATCH_1155 =
  "0x4a39dc06d4c0dbc64b70af90fd698a233a518aa5d07e595d983b8c0526c8f7fb";

const eventFilter = {
  topics: [
    [TOPIC_TRANSFER_BATCH_1155, TOPIC_TRANSFER_1155, TOPIC_TRANSFER_721_OR_20],
    null,
    null,
    null,
  ],
};
// This is an example of an event filter looking for events around a single address.
const eventFilter = { address: "0xD5525D397898e5502075Ea5E830d8914f6F0affe" };

"Subscribe" to a stateful event stream, which will ensure you fully process a block. This is not truly pub/sub, as it's operating on promises, not Nodejs Events... but it does give you that pubby-subby feel you love so much.

const watcher = new EvmWatcher({ dao, initialParams });

watcher.onLogEvent(eventFilter, async (log, isNewBlock) => {
  if (isNewBlock)
    console.log(
      "I should now delete transactional data for block " +
        log.blockNumber +
        "incase this is a restart."
    );
  console.log(log.transactionHash); // ... do stuff.
  return undefined;
});

What if there is a failure!?

If/when your log processing function, or anything within this module fails for any reason in the middle of processing logs for a block, Errors will bubble-up, and that block will be considered "unprocessed." This means that in the event of a restart of your failed process, your onLogEvent handler may be invoked with logs from a block it has already partially processed. To ensure that you don't double-record, it's encouraged that you delete any transfer events you have recorded before recording anything for a new block (Note the second param in your callback function).