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

ipfs-repo

v17.0.0

Published

IPFS Repo implementation

Downloads

19,430

Readme

ipfs-repo

ipfs.tech Discuss codecov CI

IPFS Repo implementation

Table of contents

Install

$ npm i ipfs-repo

This is the implementation of the IPFS repo spec in JavaScript.

Background

Here is the architectural reasoning for this repo:

                          ┌────────────────────────────────────────┐
                          │                IPFSRepo                │
                          └────────────────────────────────────────┘
                                      ┌─────────────────┐
                                      │        /        │
                                      ├─────────────────┤
                                      │    Datastore    │
                                      └─────────────────┘
                                   ┌───────────┴───────────┐
                          ┌─────────────────┐     ┌─────────────────┐
                          │     /blocks     │     │   /datastore    │
                          ├─────────────────┤     ├─────────────────┤
                          │    Datastore    │     │ LevelDatastore  │
                          └─────────────────┘     └─────────────────┘

┌────────────────────────────────────────┐          ┌────────────────────────────────────────┐
│       IPFSRepo - Default Node.js       │          │       IPFSRepo - Default Browser       │
└────────────────────────────────────────┘          └────────────────────────────────────────┘
            ┌─────────────────┐                                 ┌─────────────────┐
            │        /        │                                 │        /        │
            ├─────────────────┤                                 ├─────────────────┤
            │   FsDatastore   │                                 │  IdbDatastore   │
            └─────────────────┘                                 └─────────────────┘
         ┌───────────┴───────────┐                           ┌───────────┴───────────┐
┌─────────────────┐     ┌─────────────────┐         ┌─────────────────┐     ┌─────────────────┐
│     /blocks     │     │   /datastore    │         │     /blocks     │     │   /datastore    │
├─────────────────┤     ├─────────────────┤         ├─────────────────┤     ├─────────────────┤
│ FlatfsDatastore │     │LevelDBDatastore │         │  IdbDatastore   │     │  IdbDatastore   │
└─────────────────┘     └─────────────────┘         └─────────────────┘     └─────────────────┘

This provides a well defined interface for creating and interacting with an IPFS repo.

> npm install ipfs-repo
import { createRepo } from 'ipfs-repo'

Usage

Example:

import { createRepo } from 'ipfs-repo'

const repo = createRepo('/tmp/ipfs-repo')

await repo.init({ cool: 'config' })
await repo.open()
console.log('repo is ready')

This now has created the following structure, either on disk or as an in memory representation:

├── blocks
│   ├── SHARDING
│   └── _README
├── config
├── datastore
├── keys
└── version

API

Setup

createRepo(path[, options])

Creates an IPFS Repo.

Arguments:

  • path (string, mandatory): the path for this repo
  • options (object, optional): may contain the following values
    • autoMigrate (bool, defaults to true): controls automatic migrations of repository.
    • onMigrationProgress (function(version, percentComplete, message)): callback function to be notified of migration progress
    • lock (Lock or string Deprecated): what type of lock to use. Lock has to be acquired when opening. string can be "fs" or "memory".
    • storageBackends (object, optional): may contain the following values, which should each be a class implementing the datastore interface:
      • root (defaults to datastore-fs in Node.js and datastore-level in the browser). Defines the back-end type used for gets and puts of values at the root (repo.set(), repo.get())
      • blocks (defaults to datastore-fs in Node.js and datastore-level in the browser). Defines the back-end type used for gets and puts of values at repo.blocks.
      • keys (defaults to datastore-fs in Node.js and datastore-level in the browser). Defines the back-end type used for gets and puts of encrypted keys at repo.keys
      • datastore (defaults to datastore-level). Defines the back-end type used as the key-value store used for gets and puts of values at repo.datastore.
const repo = createRepo('path/to/repo')

Promise repo.init()

Creates the necessary folder structure inside the repo

Promise repo.open()

Locks the repo to prevent conflicts arising from simultaneous access

Promise repo.close()

Unlocks the repo.

Promise<boolean> repo.exists()

Tells whether this repo exists or not. Returned promise resolves to a boolean

Promise<Boolean> repo.isInitialized()

The returned promise resolves to false if the repo has not been initialized and true if it has

Repos

Root repo:

Promise repo.put(key, value:Uint8Array)

Put a value at the root of the repo

  • key can be a Uint8Array, a string or a Key

Promise<Uint8Array> repo.get(key)

Get a value at the root of the repo

  • key can be a Uint8Array, a string or a Key

Blocks

Promise<Block> repo.blocks.put(block:Block)

  • block should be of type Block

AsyncIterator<Block> repo.blocks.putMany(source:AsyncIterable<Block>)

Put many blocks.

  • source should be an AsyncIterable that yields entries of type Block

Promise<Block> repo.blocks.get(cid:CID)

Get block.

  • cid is the content id of type CID

AsyncIterable<Block> repo.blocks.getMany(source:AsyncIterable<CID>)

Get many blocks

  • source should be an AsyncIterable that yields entries of type CID

Promise<boolean> repo.blocks.has (cid:CID)

Indicate if a block is present for the passed CID

  • cid should be of the type CID

Promise<boolean> repo.blocks.delete (cid:CID)

Deletes a block

  • cid should be of the type CID

AsyncIterator<Block|CID> repo.blocks.query (query)

Query what blocks are available in blockstore.

If query.keysOnly is true, the returned iterator will yield CIDs, otherwise it will yield Blocks

Datastore:

Promise<CID> repo.blocks.delete(cid:CID)

  • cid should be of the type CID

Delete a block

AsyncIterator<CID> repo.blocks.deleteMany(source:AsyncIterable<CID>)

  • source should be an Iterable or AsyncIterable that yields entries of the type CID

Delete many blocks

Datastore

repo.datastore

This contains a full implementation of the interface-datastore API.

Config

Instead of using repo.set('config') this exposes an API that allows you to set and get a decoded config object, as well as, in a safe manner, change any of the config values individually.

Promise repo.config.set(key:String, value:Object)

Set a config value. value can be any object that is serializable to JSON.

  • key is a string specifying the object path. Example:
await repo.config.set('a.b.c', 'c value')
const config = await repo.config.get()
assert.equal(config.a.b.c, 'c value')

Promise repo.config.replace(value:Object)

Set the whole config value. value can be any object that is serializable to JSON.

Promise<?> repo.config.get(key:String)

Get a config value. Returned promise resolves to the same type that was set before.

  • key is a string specifying the object path. Example:
const value = await repo.config.get('a.b.c')
console.log('config.a.b.c = ', value)

Promise<Object> repo.config.getAll()

Get the entire config value.

Promise<boolean> repo.config.exists()

Whether the config sub-repo exists.

Version

Promise<Number> repo.version.get()

Gets the repo version (an integer).

Promise repo.version.set (version:Number)

Sets the repo version

API Addr

Promise<String> repo.apiAddr.get()

Gets the API address.

Promise repo.apiAddr.set(value)

Sets the API address.

  • value should be a Multiaddr or a String representing a valid one.

Status

Promise<Object> repo.stat()

Gets the repo status.

Returned promise resolves to an Object with the following keys:

  • numObjects
  • repoPath
  • repoSize
  • version
  • storageMax

Lock

IPFS Repo comes with two built in locks: memory and fs. These can be imported via the following:

import { FSLock } from 'ipfs-repo/locks/fs'  // Default in Node.js
import { MemoryLock } from 'ipfs-repo/locks/memory'  // Default in browser

You can also provide your own custom Lock. It must be an object with the following interface:

Promise lock.lock(dir)

Sets the lock if one does not already exist. If a lock already exists, should throw an error.

dir is a string to the directory the lock should be created at. The repo typically creates the lock at its root.

Returns closer, where closer has a close method for removing the lock.

Promise closer.close()

Closes the lock created by lock.open

If no error was thrown, the lock was successfully removed.

Promise<boolean> lock.locked(dir)

Checks the existence of the lock.

dir is the path to the directory to check for the lock. The repo typically checks for the lock at its root.

Returned promise resolves to a boolean indicating the existence of the lock.

Notes

Migrations

When there is a new repo migration and the version of the repo is increased, don't forget to propagate the changes into the test repo (test/test-repo).

For tools that run mainly in the browser environment, be aware that disabling automatic migrations leaves the user with no way to run the migrations because there is no CLI in the browser. In such a case, you should provide a way to trigger migrations manually.

License

Licensed under either of

Contribute

Contributions welcome! Please check out the issues.

Also see our contributing document for more information on how we work, and about contributing in general.

Please be aware that all interactions related to this repo are subject to the IPFS Code of Conduct.

Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.