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

@node101/merkle-tree

v0.0.8

Published

A JavaScript library to generate a Merkle Tree using SHA-256. The library is designed for applications that require data integrity verification through cryptographic hashing. It supports a range of key functionalities, including:

Downloads

20

Readme

merkle-tree

A JavaScript library to generate a Merkle Tree using SHA-256. The library is designed for applications that require data integrity verification through cryptographic hashing. It supports a range of key functionalities, including:

  • Building a Merkle tree from an array of leaves
  • Generating the Merkle root and cryptographic proofs for leaf inclusion
  • Verifying proofs to ensure data integrity
  • Adding and removing leaves dynamically

The complexity for operations like proof generation and verification is optimized to $O(\log n)$, making this library well-suited for use in blockchain, distributed systems, or any application where cryptographic data validation is critical.

Building a Tree

const leaves = ['leaf_1', 'leaf_2', 'leaf_3'];

generateMerkleTree(leaves, (err, merkleTree) => {
  if (err)
    return console.log(err);

  console.log(merkleTree);
});

Provide an array of unique leaves and generate a merkle tree. Merkle tree object has 3 field.

  • tree: a merkle tree which is complete binary tree
  • root: root of the merkle tree which also can be reach through the last element of the merkleTree.tree
  • leavesArray: an array of the leaves
tree: [
    'b21f0bed6bc4671035b48fe4117223eee394129878eb69ccc1bd4bc9cfb1a8c0',
    '6bdcde01c11dde7a0b532df991ffa39b970f6cb184d02905525442cae311734c',
    '05f086386b21d049fd52fddf71840f86f0bf9dcd3b5b0cbce7737f257a252232',
    '05f086386b21d049fd52fddf71840f86f0bf9dcd3b5b0cbce7737f257a252232',
    '9788694eb5052fc7871acbe154843bcca9fb5ec11aaa9558c026f709b2ca179b',
    '9ff73710cb11aebc2ee63953f795f5f7fe8d659e20c3ca0702a98a184c84d414',
    'f0992f51777c5b571c57c12db014dcba83dd3b93ca71a4d437067b3367d385e9'
  ],
  root: 'f0992f51777c5b571c57c12db014dcba83dd3b93ca71a4d437067b3367d385e9',
  leavesArray: [ 'leaf_1', 'leaf_2', 'leaf_3' ]

The generateMerkleTree function first checks whether the provided leaves array contains unique elements. Although, in theory, a Merkle tree can consist of non-unique elements, we avoid them to ensure data integrity and mitigate denial-of-service attacks, such as CVE-2012-2459.

After confirming the uniqueness of the leaves, generateMerkleTree verifies the length of the array to ensure that it has an even number of elements, which is required for building a balanced binary tree. For this there is two option we will discuss.

Adding leaves

For adding a leaf or leaves to the merkle tree we need to use addLeaf method. addLeaf method takes an array of leaves or a leaf string and it creates the new merkle tree with the new leavesArray. For ensuring non-duplicated leavesArray also we check uniqueness of the updated leavesArray

For only one leaf adition:

const leaves = ['leaf_1', 'leaf_2', 'leaf_3'];

generateMerkleTree(leaves, (err, merkleTree) => {
  if (err)
    return console.log(err);

  addLeaf('induvidual_leaf', merkleTree, (err, updatedMerkleTree) => {
    if (err)
      return console.log(err)

    console.log(updatedMerkleTree);
  })
})

For multiple leaf adition:

const leaves = ['leaf_1', 'leaf_2', 'leaf_3'];

generateMerkleTree(leaves, (err, merkleTree) => {
  if (err)
    return console.log(err);

  addLeaf(['leaf_4', 'leaf_5', 'leaf_6'], merkleTree, (err, updatedMerkleTree) => {
    if (err)
      return console.log(err)

    console.log(updatedMerkleTree);
  })
})

Deleting leaves

Getting Merkle Root

After creating merkleTree object we can directly reach root my merkleTree.root. Also we have a method to reach the Merkle Root getMerkleRoot

const leaves = ['leaf_1', 'leaf_2', 'leaf_3'];

generateMerkleTree(leaves, (err, merkleTree) => {
  if (err)
    return console.log(err);

  console.log(merkleTree.root);
  //or
  getMerkleRoot(merkleTree , (err, merkleRoot) => {
    if (err)
      return console.log(err);

    console.log(merkleRoot);
  })
});

Obtaining a Merkle Proof Path

A Merkle proof is a cryptographic proof used to verify that a particular piece of data (a "leaf") is part of a larger dataset (represented by a Merkle tree) without having to reveal the entire dataset. It’s a key feature in ensuring data integrity and efficiency in verification processes. (change here)

const leaves = ['leaf_1', 'leaf_2', 'leaf_3'];

generateMerkleTree(leaves, (err, merkleTree) => {
  if (err)
    return console.log(err);

  generateMerkleProof('leaf_1', merkleTree, (err, merkleProof) => {
    if (err)
      return console.log(err);

    console.log(merkleProof);
  })
});

Validating a Merkle Proof

Validating a Merkle proof is essential for ensuring the integrity and authenticity of data in systems where it's important to verify that a particular piece of data is part of a larger dataset (represented by a Merkle tree) without having to download or trust the entire dataset.

For our package a validation process look like:

verifyMerkleProof('target_data', merklePath, (err, isPartOfTheTree) => {
  if (err)
    return console.log(err);

  console.log(isPartOfTheTree);
});

Discussion

Different Aproach for Creating Merkle Tree

Our aproach to generate Merkle tree is checking each layer recursively and ensure the each layer has even node.

example 1

The other option is to round the number of nodes to the nearest multiple of 2. By doing this, we ensure that the number of nodes in each layer is even.

example 2

The reason why we chose the first aproach is for the worst case we only need $\log n$ extra nodes. But in the second aproach for the worst case we need $2^{n - 1} - 1$ extra nodes.

aproach 1

aproach 2

Why there is no duplication on Merkle Set

Weaknesses of Hash Functions

Lenght Extension Attack

Denial-of-service attack (CVE-2012-2459)

Related readings

Why you should probably never sort your Merkle tree's leaves

License

MIT