· Nacho Coll · Guides · 8 мин чтения
IPFS CID объяснён: что это и как работает контент-адресация
Чёткое техническое объяснение Content Identifiers (CIDs) в IPFS. Как работает контент-адресация, версии CID и создание вашего первого CID.

Если вы работали с IPFS (InterPlanetary File System), скорее всего, вы встречали строки вроде QmYwAPJzv5CZsnA625s3Xf2nemtYgPpHdWEz79ojWnPbdG или bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi. Это не случайная бессмыслица — это Content Identifiers (CIDs), основа системы контент-адресации IPFS.
Понимание CID критически важно для всех, кто строит на IPFS, будь то загрузка файлов, создание децентрализованных приложений или внедрение систем распространения контента. Это руководство разложит всё, что вам нужно знать об IPFS CID, как работает контент-адресация и как начать использовать их в своих проектах.

Что такое IPFS CID?
Content Identifier (CID) — это уникальный отпечаток, представляющий фрагмент контента в IPFS. В отличие от традиционных веб-URL, указывающих на расположение (например, https://example.com/file.pdf), CID указывают на сам контент, независимо от того, где он хранится.
Представьте так:
- Адресация на основе расположения: «Идите на Главную улицу 123 и попросите красную книгу»
- Адресация на основе контента: «Найдите книгу с ISBN 978-0-123456-78-9» (не важно, в какой библиотеке она лежит)
CID работают аналогично — они идентифицируют контент по его криптографическому хешу, делая контент неизменяемым и проверяемым. Если в файле изменится хотя бы один байт, CID полностью изменится.
Почему контент-адресация важна
Традиционная веб-архитектура опирается на адресацию по расположению. Когда вы посещаете https://example.com/image.jpg, вы доверяете тому, что:
- Владелец домена не изменил контент
- Сервер онлайн и доступен
- Контент не был подделан
С контент-адресацией через CID:
- Неизменяемость: CID гарантирует, что контент не изменился
- Децентрализация: Контент можно получить с любого IPFS-узла, у которого он есть
- Верификация: Можно криптографически проверить, что получен правильный контент
- Эффективность: Идентичный контент автоматически дедуплицируется
Анатомия CID
Разберём типичный CID, чтобы понять его компоненты:
bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi
└─┬─┘└─────────────────┬─────────────────────────────────┘
│ │
│ └─ Хеш контента (закодирован Base32)
└─ Префикс Multibase (указывает кодировку)CID содержит несколько информационных частей:
1. Префикс Multibase
Первый символ указывает, как закодирован CID:
Q= Кодировка Base58 (CIDv0)b= Кодировка Base32 (CIDv1)f= Base16/шестнадцатеричный (CIDv1)z= Base58 (CIDv1)
2. Версия CID
- CIDv0: Всегда начинается с
Qm, использует SHA-256, ограничен кодеком DAG-PB - CIDv1: Более гибкий, поддерживает несколько хеш-функций и кодеков
3. Multicodec
Указывает, как структурирован контент (DAG-PB, DAG-CBOR, сырые байты и т. д.)
4. Multihash
Фактический криптографический хеш контента, включающий:
- Идентификатор хеш-функции (обычно SHA-256)
- Длину хеша
- Сам хеш-дайджест
CIDv0 vs CIDv1: Понимание различий
IPFS прошёл через две основные версии CID, каждая с отличительными характеристиками:
CIDv0: Изначальный формат
CID версии CIDv0 всегда начинаются с Qm и выглядят так:
QmYwAPJzv5CZsnA625s3Xf2nemtYgPpHdWEz79ojWnPbdGХарактеристики:
- Только кодировка Base58
- Только хеш-функция SHA-256
- Только кодек DAG-PB (Protobuf)
- Длина 46 символов
- Обратно совместимы со всеми реализациями IPFS
Когда использовать CIDv0:
- Максимальная совместимость со старыми IPFS-узлами
- Работа с существующими системами, ожидающими префикс
Qm - Хранение файлов (самый распространённый случай)
CIDv1: Современный стандарт
CID версии CIDv1 более гибкие и могут выглядеть так:
bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi # Base32
zb2rhj7crUKTQYRGCRATFaQ6YFLTde2YzdqbbhAASkL9uRDXn # Base58
f01551220d1e2c35... # Base16Характеристики:
- Несколько форматов кодирования (Base32, Base58, Base16)
- Поддержка разных хеш-функций (SHA-256, SHA-512, BLAKE2 и т. д.)
- Несколько кодеков (Raw, DAG-CBOR, DAG-JSON и т. д.)
- Самоописательный формат
- Не чувствителен к регистру при использовании Base32
Когда использовать CIDv1:
- Создание новых приложений
- Необходимость идентификаторов, нечувствительных к регистру
- Работа со структурированными данными (JSON, CBOR)
- Использование альтернативных хеш-функций
Конвертация между версиями
Можно конвертировать CID между версиями, сохраняя ту же ссылку на контент:
// CIDv0
const cidv0 = "QmYwAPJzv5CZsnA625s3Xf2nemtYgPpHdWEz79ojWnPbdG";
// Convert to CIDv1 Base32
const cidv1 = "bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi";
// Both reference the same content!Как работает контент-адресация
Контент-адресация в IPFS следует детерминированному процессу, который гарантирует, что один и тот же контент всегда даёт один и тот же CID:
1. Подготовка контента
Когда вы добавляете контент в IPFS, он сначала разбивается:
- Маленькие файлы: Хранятся как одиночные блоки
- Большие файлы: Разбиваются на чанки и организуются в Merkle DAG (направленный ациклический граф)
- Каталоги: Представлены как DAG-структуры, связывающие файлы
2. Процесс хеширования
Каждая часть контента проходит:
- Сериализация: Контент форматируется согласно своему кодеку
- Хеширование: Криптографическая хеш-функция обрабатывает сериализованные данные
- Создание Multihash: Хеш оборачивается информацией об алгоритме и длине
- Сборка CID: Версия, кодек и multihash объединяются
3. Структура Merkle DAG
IPFS организует контент в Merkle DAG, где:
- Каждый узел имеет CID
- Родительские узлы ссылаются на дочерние по CID
- Изменения в любом узле распространяются вверх по дереву
- Всю структуру можно верифицировать криптографически
Root CID: bafybeigdyrzt5sfp7udm7hu76uh7y26nf3efuylqabf3oclgtqy55fbzdi
├── file1.txt (QmHash1...)
├── file2.jpg (QmHash2...)
└── subdirectory/
├── file3.pdf (QmHash3...)
└── file4.mp4 (QmHash4...)Практические примеры: работа с CID
Рассмотрим, как работать с CID на практике, используя API IPFS Ninja:
Загрузка контента и получение CID
// Upload a file and get its CID
const uploadFile = async (content, filename) => {
const response = await fetch('https://api.ipfs.ninja/upload/new', {
method: 'POST',
headers: {
'X-Api-Key': 'bws_1234567890abcdef1234567890abcdef12345678',
'Content-Type': 'application/json'
},
body: JSON.stringify({
content: btoa(content), // Base64 encode binary content
description: `Upload of ${filename}`
})
});
const result = await response.json();
console.log('CID:', result.cid);
console.log('IPFS URL:', result.uris.ipfs);
console.log('HTTP URL:', result.uris.url);
return result.cid;
};
// Example usage
uploadFile('Hello, IPFS!', 'greeting.txt');
// Returns: bafkreifjxz6zwqh27k5xnr5qfbx4w6n5vuwwwdcngguwjewzj2e3xxfgviПиннинг существующего контента по CID
Если у вас уже есть CID, можно его запиннить, чтобы обеспечить доступность:
const pinByCID = async (cid) => {
const response = await fetch('https://api.ipfs.ninja/pin', {
method: 'POST',
headers: {
'X-Api-Key': 'bws_1234567890abcdef1234567890abcdef12345678',
'Content-Type': 'application/json'
},
body: JSON.stringify({
cid: cid,
description: 'Pinned via API'
})
});
const result = await response.json();
console.log('Pinned CID:', result.cid);
return result;
};
// Pin the "Hello World" of IPFS
pinByCID('QmWATWQ7fVPP2EFGu71UkfnqhYXDYH566qy47CnJDgvs8u');Доступ к контенту через CID
Получив CID, можно обратиться к контенту разными способами:
// Direct IPFS gateway access
const ipfsUrl = `https://ipfs.ninja/ipfs/${cid}`;
// Custom gateway (if configured)
const customGatewayUrl = `https://my-app.gw.ipfs.ninja/ipfs/${cid}`;
// Fetch content programmatically
const fetchContent = async (cid) => {
const response = await fetch(`https://ipfs.ninja/ipfs/${cid}`);
const content = await response.text();
return content;
};Лучшие практики работы с CID для разработчиков
1. Всегда валидируйте CID
Перед использованием CID в приложении проверьте его формат:
const isValidCID = (cid) => {
// Basic validation patterns
const cidv0Pattern = /^Qm[1-9A-HJ-NP-Za-km-z]{44}$/;
const cidv1Pattern = /^[bf][a-z2-7]{58}$/;
return cidv0Pattern.test(cid) || cidv1Pattern.test(cid);
};2. Обрабатывайте обе версии CID
Ваше приложение должно работать как с CIDv0, так и с CIDv1:
const normalizeCID = (cid) => {
if (cid.startsWith('Qm')) {
// CIDv0 - can convert to CIDv1 if needed
return cid;
} else if (cid.startsWith('b') || cid.startsWith('f') || cid.startsWith('z')) {
// CIDv1
return cid;
} else {
throw new Error('Invalid CID format');
}
};3. Кэшируйте сопоставления CID
Если CID генерируются часто, рассмотрите кэширование:
const cidCache = new Map();
const getCachedCID = (content) => {
const contentHash = btoa(content);
if (cidCache.has(contentHash)) {
return cidCache.get(contentHash);
}
// Upload and cache result
return uploadFile(content).then(cid => {
cidCache.set(contentHash, cid);
return cid;
});
};4. Используйте осмысленные описания
При загрузке контента добавляйте описательные метаданные:
const uploadWithMetadata = async (content, metadata) => {
return fetch('https://api.ipfs.ninja/upload/new', {
method: 'POST',
headers: {
'X-Api-Key': 'bws_1234567890abcdef1234567890abcdef12345678',
'Content-Type': 'application/json'
},
body: JSON.stringify({
content: btoa(content),
description: metadata.name || 'Uploaded file',
metadata: {
filename: metadata.filename,
contentType: metadata.contentType,
uploadedAt: new Date().toISOString(),
version: metadata.version || '1.0'
}
})
});
};Общие сценарии использования CID
1. Развёртывание статических сайтов
Разверните целые сайты в IPFS и ссылайтесь на них по CID:
// Upload website directory structure
const deployWebsite = async (files) => {
const uploads = await Promise.all(
files.map(file => uploadFile(file.content, file.path))
);
// Root CID references entire site
const rootCID = uploads.find(u => u.path === 'index.html').cid;
console.log(`Website deployed: https://ipfs.ninja/ipfs/${rootCID}`);
return rootCID;
};Подробнее о развёртывании сайтов — в нашем руководстве о том, как загружать файлы в IPFS.
2. Хранение метаданных NFT
Храните метаданные NFT неизменно с помощью CID:
const nftMetadata = {
name: "My Awesome NFT",
description: "A unique digital collectible",
image: "ipfs://bafkreibc5sgo2plmjkq2tzmhrn54bk3crhnqekiy7u66fqvqm37pu2e5gw",
attributes: [
{ trait_type: "Color", value: "Blue" },
{ trait_type: "Rarity", value: "Epic" }
]
};
const metadataCID = await uploadFile(
JSON.stringify(nftMetadata, null, 2),
'metadata.json'
);
// Use in smart contract
console.log(`Token URI: ipfs://${metadataCID}`);3. Распределение контента
Используйте CID для распределённой доставки контента:
// Upload once, access everywhere
const distributeContent = async (content) => {
const cid = await uploadFile(content, 'content.txt');
// Content available via multiple gateways
const gateways = [
`https://ipfs.ninja/ipfs/${cid}`,
`https://ipfs.io/ipfs/${cid}`,
`https://cloudflare-ipfs.com/ipfs/${cid}`
];
return { cid, gateways };
};Понимание пиннинга IPFS с CID
CID по умолчанию временные — их нужно «запиннить», чтобы оставались доступны. Подробнее об этом ключевом понятии — в нашем подробном руководстве о том, что такое пиннинг IPFS.
При выборе сервиса пиннинга IPFS рассмотрите наше сравнение IPFS Ninja vs Pinata или изучите наш обзор лучших сервисов пиннинга IPFS, доступных сегодня.
Создайте свой первый CID за 30 секунд
Готовы сгенерировать свой первый CID? Вот быстрый пример с API IPFS Ninja:
# Using curl (replace with your actual API key)
curl -X POST https://api.ipfs.ninja/upload/new \
-H "X-Api-Key: bws_YOUR_API_KEY_HERE" \
-H "Content-Type: application/json" \
-d '{
"content": "SGVsbG8sIElQRlMgV29ybGQh",
"description": "My first IPFS upload"
}'// Using JavaScript
const createFirstCID = async () => {
const response = await fetch('https://api.ipfs.ninja/upload/new', {
method: 'POST',
headers: {
'X-Api-Key': 'bws_YOUR_API_KEY_HERE',
'Content-Type': 'application/json'
},
body: JSON.stringify({
content: btoa('Hello, IPFS World!'), // Base64: "SGVsbG8sIElQRlMgV29ybGQh"
description: 'My first IPFS upload'
})
});
const result = await response.json();
console.log('🎉 Your first CID:', result.cid);
console.log('🌐 Access it at:', result.uris.url);
return result;
};
createFirstCID();Это вернёт нечто вроде:
{
"cid": "bafkreif2pall7dybz7vecqka3zo24irdwabf7rbiiweuhau7a2hjlqvfjw",
"sizeMB": 0.000017,
"uris": {
"ipfs": "ipfs://bafkreif2pall7dybz7vecqka3zo24irdwabf7rbiiweuhau7a2hjlqvfjw",
"url": "https://ipfs.ninja/ipfs/bafkreif2pall7dybz7vecqka3zo24irdwabf7rbiiweuhau7a2hjlqvfjw"
}
}Больше детальных примеров API — в нашем руководстве по API загрузки IPFS.
Заключение
CID — это фундамент системы контент-адресации IPFS, обеспечивающий неизменяемую, проверяемую и децентрализованную идентификацию контента. Понимание того, как они работают — от технических деталей CIDv0 vs CIDv1 до практических паттернов реализации — необходимо для построения надёжных децентрализованных приложений.
Ключевые выводы:
- CID уникально идентифицируют контент, а не расположение
- CIDv0 обеспечивает максимальную совместимость, CIDv1 — гибкость
- Контент-адресация обеспечивает верификацию и дедупликацию
- Правильная работа с CID критична для продакшн-приложений
Храните ли вы метаданные NFT, разворачиваете ли децентрализованные сайты или строите системы распространения контента — CID дают надёжный фундамент для по-настоящему децентрализованных приложений.
Готовы начать пиннить? Создать бесплатный аккаунт — 50 файлов, 1 ГБ хранилища, 2 ГБ трафика/мес. Без банковской карты.
