
The AIOZ Pin Node.js SDK gets you from "I have an API key" to "I've pinned a file" in about five lines of code, once you know the right package name and method signatures. This guide covers both, install, authenticate, pin a file, pin an NFT, and check pin status, using the actual method names shipped in the real package rather than what AIOZ's own quick-start docs happen to say, since the two don't always agree (see the note on pinFilesToIPFS below).
TL;DR:
@aioznetwork/aioz-pin-sdk, not the unscoped aioz-pin-sdk some docs mention, that package doesn't existnew AiozPinClient(apiKey, secretKey)pinFilesToIPFS(), pinNft(), or getPinList() depending on what you're pinningThe correct, currently-published package is scoped to AIOZ's npm org:
npm install @aioznetwork/aioz-pin-sdk
If you've seen npm install aioz-pin-sdk in AIOZ's own documentation, that's the unscoped name, and it returns a 404 on the npm registry. It doesn't exist as a real package. Use the scoped name above.
Generate an API key and secret from your AIOZ Pin dashboard, scoped to whatever operations you actually need (pinning-only, for example, if that's all this integration does), then initialize the client:
import AiozPinClient from '@aioznetwork/aioz-pin-sdk'
const client = new AiozPinClient('your-api-key', 'your-secret-key')
Before building anything further, call testAuthentication() to confirm the keys actually work. Catching an auth failure here is a lot less confusing than debugging a failed pin three steps into a larger script.
await client.pinFilesToIPFS({
filePaths: ['./image.png'],
options: {
name: 'my-image',
keyvalues: { project: 'demo' }
}
})
filePaths takes an array, so batching multiple files in one call works the same way as pinning one. The options.name field is what shows up as the pin's display name, and keyvalues lets you attach your own arbitrary metadata for filtering later. Note the exact method name: it's pinFilesToIPFS, plural. AIOZ's own quick-start guide writes it as singular pinFileToIPFS, but that's not what the published package exports, if you copy that name literally, your code won't run.
For an entire directory instead of a list of files, pinFolderToIPFS({depth, sourcePath, options}) does the same job with a folder path and a depth limit instead of a file array.
await client.pinNft({
fileStream: fs.createReadStream('./nft-image.png'),
metadata: {
name: 'My NFT',
description: 'A demo NFT',
properties: [
{ trait_type: 'Background', value: 'Blue' }
]
}
})
This pins the asset and its metadata together in one call, in the standard trait_type/value attribute format most marketplaces expect, the same approach covered in AIOZ Pin's NFT Management component. That matters more than it sounds like it should, pinning an asset and its metadata as two separate calls means there's a window where one exists on IPFS and the other doesn't, and if your process fails between the two, you end up with orphaned metadata or an asset nothing points to. One call removes that failure mode.
const pins = await client.getPinList({
offset: 0,
limit: 20,
sortBy: 'date_pinned',
sortOrder: 'desc'
})
getPinList() supports offset and limit for pagination, plus filtering by pinned status and sorting, useful once you're managing more than a handful of pins and need to find something specific rather than pulling everything back at once. For a single pin, getPinByID() and getPinByCID() fetch by whichever identifier you have on hand.
Strung together, the pieces above form a real, minimal script, authenticate, pin, verify the pin actually resolved, then read it back:
import AiozPinClient from '@aioznetwork/aioz-pin-sdk'
async function main() {
const client = new AiozPinClient(
process.env.AIOZ_PIN_KEY,
process.env.AIOZ_PIN_SECRET
)
await client.testAuthentication()
const { cid } = await client.pinFilesToIPFS({
filePaths: ['./image.png'],
options: { name: 'my-image' }
})
const pin = await client.getPinByCID(cid)
if (pin.status !== 'pinned') {
throw new Error(`Pin did not resolve: ${pin.status}`)
}
console.log(`Pinned: ipfs://${cid}`)
}
main().catch(console.error)
Reading credentials from environment variables here, rather than hardcoding them, follows the same secure-storage guidance covered in this blog's dedicated article on AIOZ Pin API key handling. The status check after pinning is the step easiest to skip and most likely to matter, catching a pin that's still processing or failed before anything downstream, a smart contract call, a database record, a customer-facing URL, depends on a CID that doesn't actually resolve yet.
Beyond the methods above, the SDK covers: pinByHash() for pinning content you already have a CID for, unpin() and unpinNft() for removal, pinNftByStreamMetadata() and pinNftByHash() for NFT pinning variants that take a metadata file instead of an inline object, and optimizeImage() for gateway-side image transforms (width, height, quality, fit, format), which requires at least one transform option to be set or it won't activate. For anything the SDK doesn't wrap, the full API and CLI cover the rest.
Pinning more than a handful of files, an image library, an NFT collection's asset set, works the same way through pinFilesToIPFS(), since filePaths already accepts an array, but it's worth pinning in reasonably sized batches rather than one enormous call with thousands of paths. A batch that fails partway through a single giant request leaves unclear which files actually made it and which didn't; breaking a large job into batches of a few hundred files, checking each batch's result before moving to the next, makes partial failures something a retry loop can handle cleanly instead of a full re-run of everything, some of it redundantly, from scratch.
What is the correct package name for the AIOZ Pin Node.js SDK? @aioznetwork/aioz-pin-sdk. The unscoped name aioz-pin-sdk, shown in some AIOZ documentation, does not exist as a published package.
What's the exact method for pinning a file with the SDK? pinFilesToIPFS({filePaths, options}), plural. AIOZ's quick-start guide shows a singular pinFileToIPFS, which is not what the real package exports.
How do I pin an NFT with its metadata using the SDK? Call pinNft({fileStream, metadata}), where metadata includes name, description, and a properties array of trait_type/value pairs. This pins the asset and metadata together in one call.
How do I check if my API credentials work before pinning anything? Call client.testAuthentication() first. It validates your key and secret without requiring a real pin operation.
Can I pin an entire folder instead of individual files? Yes, with pinFolderToIPFS({depth, sourcePath, options}), which takes a folder path and depth limit instead of a file array.
How do I list or search my existing pins? getPinList({offset, limit, pinned, sortBy, sortOrder, metadata}) supports pagination, filtering, and sorting. For a single known pin, use getPinByID() or getPinByCID() instead.

IPFS defaults to 256 KiB fixed-size chunks, but also ships Rabin and Buzhash content-defined chunkers. Here is why the choice affects deduplication.

An IPFS CID is not a random string. It encodes a version, a codec, and a hash algorithm plus digest. Here is how to decode a real CID piece by piece.

IPFS does not use a B-tree for large directories. It uses a HAMT, a Hash Array Mapped Trie. Here is exactly how it shards a folder once it outgrows one block.

AIOZ Pin image resizing happens straight in the gateway URL, no upload step or separate service. Here is every img- parameter, with real srcset examples.

x402 payments let ERC-8004 weight a paid AI agent interaction more heavily than free work in its reputation score. Here is exactly how that link works.

AIOZ Pin NFT API calls pin an asset and its metadata as two tracked pins under one record. Here is how to automate it directly over REST, no SDK needed.