Comparing version 0.3.2 to 0.4.2
{ | ||
"name": "is-ipfs", | ||
"version": "0.3.2", | ||
"version": "0.4.2", | ||
"description": "A set of utilities to help identify IPFS resources", | ||
@@ -10,12 +10,12 @@ "main": "src/index.js", | ||
"scripts": { | ||
"test:node": "aegir-test node", | ||
"test:browser": "aegir-test browser", | ||
"test": "aegir-test", | ||
"lint": "aegir-lint", | ||
"release": "aegir-release", | ||
"release-minor": "aegir-release --type minor", | ||
"release-major": "aegir-release --type major", | ||
"build": "aegir-build", | ||
"coverage": "aegir-coverage", | ||
"coverage-publish": "aegir-coverage publish" | ||
"test:node": "aegir test --target node", | ||
"test:browser": "aegir test --target browser", | ||
"test": "aegir test", | ||
"lint": "aegir lint", | ||
"release": "aegir release", | ||
"release-minor": "aegir release --type minor", | ||
"release-major": "aegir release --type major", | ||
"build": "aegir build", | ||
"coverage": "aegir coverage", | ||
"coverage-publish": "aegir coverage --upload" | ||
}, | ||
@@ -27,2 +27,3 @@ "pre-commit": [ | ||
"keywords": [ | ||
"js-ipfs", | ||
"ipfs" | ||
@@ -33,25 +34,27 @@ ], | ||
"dependencies": { | ||
"cids": "~0.5.1", | ||
"bs58": "^4.0.1", | ||
"multihashes": "~0.4.9" | ||
"bs58": "4.0.1", | ||
"cids": "0.5.3", | ||
"multibase": "0.4.0", | ||
"multihashes": "0.4.13" | ||
}, | ||
"devDependencies": { | ||
"aegir": "^11.0.2", | ||
"chai": "^4.1.2", | ||
"pre-commit": "^1.2.2" | ||
"aegir": "15.0.1", | ||
"chai": "4.1.2", | ||
"pre-commit": "1.2.2" | ||
}, | ||
"repository": { | ||
"type": "git", | ||
"url": "https://github.com/xicombd/is-ipfs.git" | ||
"url": "https://github.com/ipfs/is-ipfs.git" | ||
}, | ||
"bugs": { | ||
"url": "https://github.com/xicombd/is-ipfs/issues" | ||
"url": "https://github.com/ipfs/is-ipfs/issues" | ||
}, | ||
"homepage": "https://github.com/xicombd/is-ipfs", | ||
"homepage": "https://github.com/ipfs/is-ipfs", | ||
"contributors": [ | ||
"David Dias <daviddias.p@gmail.com>", | ||
"Francisco Baio Dias <xicombd@gmail.com>", | ||
"Henrique Dias <hacdias@gmail.com>", | ||
"Marcin Rataj <lidel@lidel.org>", | ||
"nginnever <ginneversource@gmail.com>" | ||
] | ||
} | ||
} |
is-ipfs | ||
==== | ||
[![build status](https://secure.travis-ci.org/xicombd/is-ipfs.svg)](http://travis-ci.org/xicombd/is-ipfs) | ||
[![dignified.js](https://img.shields.io/badge/follows-dignified.js-blue.svg?style=flat-square)](https://github.com/dignifiedquire/dignified.js) | ||
[![](https://img.shields.io/github/release/ipfs/is-ipfs.svg)](https://github.com/ipfs/is-ipfs/releases/latest) | ||
[![](https://img.shields.io/badge/freenode-%23ipfs-blue.svg?style=flat-square)](https://webchat.freenode.net/?channels=%23ipfs) | ||
A set of utilities to help identify [IPFS](https://ipfs.io/) resources. | ||
> A set of utilities to help identify [IPFS](https://ipfs.io/) resources | ||
## Lead Maintainer | ||
## Install | ||
[Marcin Rataj](https://github.com/lidel) | ||
# Install | ||
### In Node.js through npm | ||
@@ -37,3 +40,3 @@ | ||
## Usage | ||
# Usage | ||
```javascript | ||
@@ -45,2 +48,9 @@ const isIPFS = require('is-ipfs') | ||
isIPFS.cid('QmYjtig7VJQ6XsnUjqqJvj7QaMcCAwtrgNdahSiFofrE7o') // true (CIDv0) | ||
isIPFS.cid('zdj7WWeQ43G6JJvLWQWZpyHuAMq6uYWRjkBXFad11vE2LHhQ7') // true (CIDv1) | ||
isIPFS.cid('noop') // false | ||
isIPFS.base32cid('bafybeie5gq4jxvzmsym6hjlwxej4rwdoxt7wadqvmmwbqi7r27fclha2va') // true | ||
isIPFS.base32cid('QmYjtig7VJQ6XsnUjqqJvj7QaMcCAwtrgNdahSiFofrE7o') // false | ||
isIPFS.url('https://ipfs.io/ipfs/QmYjtig7VJQ6XsnUjqqJvj7QaMcCAwtrgNdahSiFofrE7o') // true | ||
@@ -72,6 +82,28 @@ isIPFS.url('https://ipfs.io/ipns/github.com') // true | ||
isIPFS.ipnsPath('/ipns/github.com') // true | ||
isIPFS.subdomain('http://bafybeie5gq4jxvzmsym6hjlwxej4rwdoxt7wadqvmmwbqi7r27fclha2va.ipfs.dweb.link') // true | ||
isIPFS.subdomain('http://bafybeiabc2xofh6tdi6vutusorpumwcikw3hf3st4ecjugo6j52f6xwc6q.ipns.dweb.link') // true | ||
isIPFS.subdomain('http://www.bafybeie5gq4jxvzmsym6hjlwxej4rwdoxt7wadqvmmwbqi7r27fclha2va.ipfs.dweb.link') // false | ||
isIPFS.subdomain('http://bafybeie5gq4jxvzmsym6hjlwxej4rwdoxt7wadqvmmwbqi7r27fclha2va.dweb.link') // false | ||
isIPFS.ipfsSubdomain('http://bafybeie5gq4jxvzmsym6hjlwxej4rwdoxt7wadqvmmwbqi7r27fclha2va.ipfs.dweb.link') // true | ||
isIPFS.ipfsSubdomain('http://bafybeie5gq4jxvzmsym6hjlwxej4rwdoxt7wadqvmmwbqi7r27fclha2va.dweb.link') // false | ||
isIPFS.ipnsSubdomain('http://bafybeiabc2xofh6tdi6vutusorpumwcikw3hf3st4ecjugo6j52f6xwc6q.ipns.dweb.link') // true | ||
isIPFS.ipnsSubdomain('http://bafybeiabc2xofh6tdi6vutusorpumwcikw3hf3st4ecjugo6j52f6xwc6q.dweb.link') // false | ||
isIPFS.ipnsSubdomain('http://QmcNioXSC1bfJj1dcFErhUfyjFzoX2HodkRccsFFVJJvg8.ipns.dweb.link') // false | ||
isIPFS.ipnsSubdomain('http://foo-bar.ipns.dweb.link') // false (not a PeerID) | ||
``` | ||
## API | ||
# API | ||
A suite of util methods that provides efficient validation. | ||
Detection of IPFS Paths and identifiers in URLs is a two-stage process: | ||
1. `urlPattern`/`pathPattern`/`subdomainPattern` regex is applied to quickly identify potential candidates | ||
2. proper CID validation is applied to remove false-positives | ||
## Utils | ||
### `isIPFS.multihash(hash)` | ||
@@ -81,14 +113,16 @@ | ||
### `isIPFS.url(url)` | ||
### `isIPFS.cid(hash)` | ||
Returns `true` if the provided string is a valid IPFS or IPNS url or `false` otherwise. | ||
Returns `true` if the provided string is a valid `CID` or `false` otherwise. | ||
### `isIPFS.path(path)` | ||
### `isIPFS.base32cid(hash)` | ||
Returns `true` if the provided string is a valid IPFS or IPNS path or `false` otherwise. | ||
Returns `true` if the provided string is a valid `CID` in Base32 encoding or `false` otherwise. | ||
### `isIPFS.urlOrPath(path)` | ||
## URLs | ||
Returns `true` if the provided string is a valid IPFS or IPNS url or path or `false` otherwise. | ||
### `isIPFS.url(url)` | ||
Returns `true` if the provided string is a valid IPFS or IPNS url or `false` otherwise. | ||
### `isIPFS.ipfsUrl(url)` | ||
@@ -102,2 +136,15 @@ | ||
## Paths | ||
Standalone validation of IPFS Paths: `/ip(f|n)s/<cid>/..` | ||
### `isIPFS.path(path)` | ||
Returns `true` if the provided string is a valid IPFS or IPNS path or `false` otherwise. | ||
### `isIPFS.urlOrPath(path)` | ||
Returns `true` if the provided string is a valid IPFS or IPNS url or path or `false` otherwise. | ||
### `isIPFS.ipfsPath(path)` | ||
@@ -111,8 +158,21 @@ | ||
## Subdomains | ||
**Note:** the regex used for these checks is also exported as `isIPFS.urlPattern` | ||
Validated subdomain convention: `cidv1b32.ip(f|n)s.domain.tld` | ||
## License | ||
### `isIPFS.subdomain(url)` | ||
Returns `true` if the provided string includes a valid IPFS or IPNS subdomain or `false` otherwise. | ||
### `isIPFS.ipfsSubdomain(url)` | ||
Returns `true` if the provided string includes a valid IPFS subdomain or `false` otherwise. | ||
### `isIPFS.ipnsSubdomain(url)` | ||
Returns `true` if the provided string includes a valid IPNS subdomain or `false` otherwise. | ||
# License | ||
MIT |
@@ -5,2 +5,3 @@ 'use strict' | ||
const multihash = require('multihashes') | ||
const multibase = require('multibase') | ||
const CID = require('cids') | ||
@@ -10,7 +11,13 @@ | ||
const pathPattern = /^\/(ip(f|n)s)\/((\w+).*)/ | ||
const defaultProtocolMatch = 1 | ||
const defaultHashMath = 4 | ||
const fqdnPattern = /^https?:\/\/([^/]+)\.(ip(?:f|n)s)\.[^/]+/ | ||
const fqdnHashMatch = 1 | ||
const fqdnProtocolMatch = 2 | ||
function isMultihash (hash) { | ||
const formatted = convertToString(hash) | ||
try { | ||
const buffer = new Buffer(base58.decode(formatted)) | ||
const buffer = Buffer.from(base58.decode(formatted)) | ||
multihash.decode(buffer) | ||
@@ -23,2 +30,10 @@ return true | ||
function isMultibase (hash) { | ||
try { | ||
return multibase.isEncoded(hash) | ||
} catch (e) { | ||
return false | ||
} | ||
} | ||
function isCID (hash) { | ||
@@ -32,3 +47,3 @@ try { | ||
function isIpfs (input, pattern) { | ||
function isIpfs (input, pattern, protocolMatch = defaultProtocolMatch, hashMatch = defaultHashMath) { | ||
const formatted = convertToString(input) | ||
@@ -44,11 +59,19 @@ if (!formatted) { | ||
if (match[1] !== 'ipfs') { | ||
if (match[protocolMatch] !== 'ipfs') { | ||
return false | ||
} | ||
const hash = match[4] | ||
let hash = match[hashMatch] | ||
if (hash && pattern === fqdnPattern) { | ||
// when doing checks for subdomain context | ||
// ensure hash is case-insensitive | ||
// (browsers force-lowercase authority compotent anyway) | ||
hash = hash.toLowerCase() | ||
} | ||
return isCID(hash) | ||
} | ||
function isIpns (input, pattern) { | ||
function isIpns (input, pattern, protocolMatch = defaultProtocolMatch, hashMatch) { | ||
const formatted = convertToString(input) | ||
@@ -63,6 +86,15 @@ if (!formatted) { | ||
if (match[1] !== 'ipns') { | ||
if (match[protocolMatch] !== 'ipns') { | ||
return false | ||
} | ||
if (hashMatch && pattern === fqdnPattern) { | ||
let hash = match[hashMatch] | ||
// when doing checks for subdomain context | ||
// ensure hash is case-insensitive | ||
// (browsers force-lowercase authority compotent anyway) | ||
hash = hash.toLowerCase() | ||
return isCID(hash) | ||
} | ||
return true | ||
@@ -83,5 +115,13 @@ } | ||
const ipfsSubdomain = (url) => isIpfs(url, fqdnPattern, fqdnProtocolMatch, fqdnHashMatch) | ||
const ipnsSubdomain = (url) => isIpns(url, fqdnPattern, fqdnProtocolMatch, fqdnHashMatch) | ||
module.exports = { | ||
multihash: isMultihash, | ||
cid: isCID, | ||
base32cid: (cid) => (isMultibase(cid) === 'base32' && isCID(cid)), | ||
ipfsSubdomain: ipfsSubdomain, | ||
ipnsSubdomain: ipnsSubdomain, | ||
subdomain: (url) => (ipfsSubdomain(url) || ipnsSubdomain(url)), | ||
subdomainPattern: fqdnPattern, | ||
ipfsUrl: (url) => isIpfs(url, urlPattern), | ||
@@ -88,0 +128,0 @@ ipnsUrl: (url) => isIpns(url, urlPattern), |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is too big to display
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
New author
Supply chain riskA new npm collaborator published a version of the package for the first time. New collaborators are usually benign additions to a project, but do indicate a change to the security surface area of a package.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
755639
12
173
4
376
2
+ Addedmultibase@0.4.0
+ Addedbase-x@3.0.4(transitive)
+ Addedcids@0.5.3(transitive)
+ Addedmultibase@0.4.0(transitive)
+ Addedmulticodec@0.2.7(transitive)
+ Addedmultihashes@0.4.13(transitive)
- Removedbase64-js@1.5.1(transitive)
- Removedbuffer@5.7.1(transitive)
- Removedcids@0.5.8(transitive)
- Removedclass-is@1.1.0(transitive)
- Removedieee754@1.2.1(transitive)
- Removedmultibase@0.6.10.7.0(transitive)
- Removedmulticodec@0.5.7(transitive)
- Removedmultihashes@0.4.21(transitive)
Updatedbs58@4.0.1
Updatedcids@0.5.3
Updatedmultihashes@0.4.13