Skip to main content


web3.storage

The main JavaScript client for the w3up platform by https://web3.storage

⚠️❗ w3up-client and the underlying APIs are currently beta preview features

Please read the beta Terms of Service for more details.

Open an issue on the repo or reach out to the #web3-storage channel on IPFS Discord if you have any questions!

About

@web3-storage/w3up-client is a JavaScript libary that provides a convenient interface to the w3up platform, a simple "on-ramp" to the content-addressed decentralized IPFS network.

This library is the user-facing "porcelain" client for interacting with w3up services from JavaScript. It wraps the lower-level @web3-storage/access and @web3-storage/upload-client client packages, which target individual w3up services. We recommend using w3up-client instead of using those "plumbing" packages directly, but you may find them useful if you need more context on w3up's architecture and internals.

Install

You can add the @web3-storage/w3up-client package to your JavaScript or TypeScript project with npm:

npm install @web3-storage/w3up-client

Core concepts

w3up services use ucanto, a Remote Procedure Call (RPC) framework built around UCAN, or User Controlled Authorization Networks. UCANs are a powerful capability-based authorization system that allows fine-grained sharing of permissions through a process called delegation. See our intro to UCAN for an overview of UCAN.

w3up-client and ucanto take care of the details of UCANs for you, but a few of the underlying terms and concepts may "bubble up" to the surface of the API, so we'll cover the basics here. We'll also go over some terms that are specific to w3up that you might not have encountered elsewhere.

UCAN-based APIs are centered around capabilities, which are comprised of an ability and a resource. Together, the ability and resource determine what action a client can perform and what objects in the system can be acted upon. When invoking a service method, a client will present a UCAN token that includes an ability and resource, along with proofs that verify that they should be allowed to exercise the capability.

To invoke a capability, the client must have a private signing key, which is managed by a component called an Agent. When you create a client object with w3up-client, an Agent is automatically created for you and used when making requests. The Agent's keys and metadata are securely stored and are loaded the next time you create a client.

Each device or browser should create its own Agent, so that private keys are never shared across multiple devices. Instead of sharing keys, a user can delegate some or all of their capabilites from one Agent to another.

When you upload data to w3up, your uploads are linked to a unique Space acts as a "namespace" for the data you upload. Spaces are used to keep track of which uploads belong to which users, among other things.

When invoking storage capabilities, the Space ID is the "resource" portion of the capability, while the ability is an action like store/add or store/remove.

Both Agents and Spaces are identified using DIDs, or Decentralized Identity Documents. DIDs are a W3C specification for verifiable identities in decentralized systems. There are several DID "methods," but the ones most commonly used by w3up are did:key, which includes a public key directly in the DID string. Agents and Spaces both use did:key URI strings as their primary identifiers. The other DID method used by w3up is did:web, which is used to identify the service providers.

Agents and Spaces are both generated by w3up-client on the user's local machine. Before they can be used for storage, the user will need to register the space by confirming their email address. Once registered, a Space can be used to upload files and directories.

Basic usage

This section shows some of the basic operations available in the w3up-client package.

Creating a client object

The package provides a static create function that returns a Client object.

import { create } from '@web3-storage/w3up-client'

const client = await create()

By default, clients will be configured to use the production w3up service endpoints, and the client will create a new Agent with a persistent Store if it can't find one locally to load.

Agents are entities that control the private signing keys used to interact with the w3up service layer. You can access the client's Agent with the agent() accessor method.

create accepts an optional ClientFactoryOptions object, which can be used to target a non-production instance of the w3up access and upload services, or to use a non-default persistent Store. See the @web3-storage/access docs for more about Store configuration.

Creating and registering Spaces

Before you can upload data, you'll need to create a Space and register it with the service.

A Space acts as a namespace for your uploads. Spaces are created using the createSpace client method:

const space = await client.createSpace('my-awesome-space')

The name parameter is optional. If provided, it will be stored in your client's local state store and can be used to provide a friendly name for user interfaces.

After creating a Space, you'll need to register it with the w3up service before you can upload data.

First, set the space as your "current" space using the setCurrentSpace method, passing in the DID of the space object you created above:

await client.setCurrentSpace(space.did())

Next, call the registerSpace method, passing in an email address to register as the primary contact for the space:

try {
await client.registerSpace('[email protected]')
} catch (err) {
console.error('registration failed: ', err)
}

Calling registerSpace will cause an email to be sent to the given address. Once a user clicks the confirmation link in the email, the registerSpace method will resolve. Make sure to check for errors, as registerSpace will fail if the email is not confirmed within the expiration timeout.

Registering a space enrolls it in web3.storage's free usage tier, allowing you to store files, list uploads, etc.

Uploading data

Once you've created and registered a space, you can upload files to the w3up platform.

Call uploadFile to upload a single file, or uploadDirectory to upload multiple files.

uploadFile expects a "Blob like" input, which can be a Blob or File when running in a browser. On node.js, see the filesFromPath library, which can load compatible objects from the local filesystem.

uploadDirectory requires File-like objects instead of Blobs, as the file's name property is used to build the directory hierarchy.

You can control the directory layout and create nested directory structures by using / delimited paths in your filenames:

const files = [
new File(['some-file-content'], 'readme.md'),
new File(['import foo'], 'src/main.py'),
new File([someBinaryData], 'images/example.png'),
]

const directoryCid = await client.storeDirectory(files)

In the example above, directoryCid resolves to an IPFS directory with the following layout:

.
├── images
│   └── example.png
├── readme.md
└── src
└── main.py