-
Notifications
You must be signed in to change notification settings - Fork 8
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
resolves #2 License: MIT Signed-off-by: Alan Shaw <[email protected]>
- Loading branch information
Alan Shaw
committed
Sep 13, 2018
1 parent
d6b2e86
commit a7b8fa7
Showing
6 changed files
with
395 additions
and
7 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,65 @@ | ||
'use strict' | ||
|
||
const CIDTool = require('../../') | ||
|
||
module.exports = { | ||
command: 'format [cids...]', | ||
|
||
describe: 'Format and convert a CID in various useful ways.', | ||
|
||
builder: { | ||
format: { | ||
describe: `Printf style format string: | ||
%% literal % | ||
%b multibase name | ||
%B multibase code | ||
%v version string | ||
%V version number | ||
%c codec name | ||
%C codec code | ||
%h multihash name | ||
%H multihash code | ||
%L hash digest length | ||
%m multihash encoded in base %b (with multibase prefix) | ||
%M multihash encoded in base %b without multibase prefix | ||
%d hash digest encoded in base %b (with multibase prefix) | ||
%D hash digest encoded in base %b without multibase prefix | ||
%s cid string encoded in base %b (1) | ||
%S cid string encoded in base %b without multibase prefix | ||
%P cid prefix: %v-%c-%h-%L | ||
(1) For CID version 0 the multibase must be base58btc and no prefix is used. For Cid version 1 the multibase prefix is included.`, | ||
alias: 'f', | ||
type: 'string', | ||
default: '%s' | ||
}, | ||
'cid-version': { | ||
describe: 'CID version to convert to.', | ||
alias: 'v', | ||
type: 'number' | ||
}, | ||
base: { | ||
describe: 'Multibase to display output in.', | ||
alias: 'b', | ||
type: 'string' | ||
} | ||
}, | ||
|
||
handler (argv) { | ||
const options = { | ||
format: argv.format, | ||
cidVersion: argv.cidVersion, | ||
base: argv.base | ||
} | ||
|
||
if (argv.cids && argv.cids.length) { | ||
return argv.cids.forEach(cid => console.log(CIDTool.format(cid, options))) | ||
} | ||
|
||
process.stdin.on('data', data => { | ||
const cid = data.toString().trim() | ||
console.log(CIDTool.format(cid, options)) | ||
}) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,110 @@ | ||
'use strict' | ||
|
||
const CID = require('cids') | ||
const bases = require('./bases') | ||
const codecs = require('./codecs') | ||
const explain = require('explain-error') | ||
const multibase = require('multibase') | ||
const multihash = require('multihashes') | ||
|
||
module.exports = function format (cid, options) { | ||
options = options || {} | ||
|
||
let formatStr = options.format || '%s' | ||
|
||
if (formatStr === 'prefix') { | ||
formatStr = '%P' | ||
} | ||
|
||
if (!isString(formatStr) || formatStr.indexOf('%') === -1) { | ||
throw new Error(`invalid format string: ${formatStr}`) | ||
} | ||
|
||
const originalCid = cid | ||
|
||
try { | ||
cid = new CID(cid) | ||
} catch (err) { | ||
throw explain(err, `invalid cid: ${cid}`) | ||
} | ||
|
||
if (options.cidVersion != null && cid.version !== options.cidVersion) { | ||
if (options.cidVersion === 0) { | ||
cid = cid.toV0() | ||
} else if (options.cidVersion === 1) { | ||
cid = cid.toV1() | ||
} else { | ||
throw new Error(`invalid cid version: ${options.cidVersion}`) | ||
} | ||
} | ||
|
||
let base | ||
|
||
if (options.base) { | ||
base = options.base | ||
} else if (isString(originalCid)) { | ||
// Use base of input CID if string | ||
base = multibase.isEncoded(originalCid) | ||
} | ||
|
||
base = base || 'base58btc' | ||
|
||
// Using multibase code instead of name | ||
if (base.length === 1) { | ||
const baseNameCode = bases().find(b => b.code === base) | ||
if (!baseNameCode) throw new Error(`invalid multibase: ${base}`) | ||
base = baseNameCode.name | ||
} | ||
|
||
return formatStr.replace(/%([a-zA-Z%])/g, replacer(cid, base, options)) | ||
} | ||
|
||
function isString (obj) { | ||
return Object.prototype.toString.call(obj) === '[object String]' | ||
} | ||
|
||
function replacer (cid, base, options) { | ||
return (match, specifier) => { | ||
switch (specifier) { | ||
case '%': | ||
return '%' | ||
case 'b': // base name | ||
return base | ||
case 'B': // base code | ||
return bases().find(b => b.name === base).code | ||
case 'v': // version string | ||
return `cidv${cid.version}` | ||
case 'V': // version num | ||
return cid.version | ||
case 'c': // codec name | ||
return cid.codec | ||
case 'C': // codec code | ||
return codecs().find(c => c.name === cid.codec).code | ||
case 'h': // hash fun name | ||
return multihash.decode(cid.multihash).name | ||
case 'H': // hash fun code | ||
return multihash.decode(cid.multihash).code | ||
case 'L': // hash length | ||
return multihash.decode(cid.multihash).length | ||
case 'm': // multihash encoded in base %b | ||
return multibase.encode(base, cid.multihash) | ||
case 'M': // multihash encoded in base %b without base prefix | ||
return multibase.encode(base, cid.multihash).slice(1) | ||
case 'd': // hash digest encoded in base %b | ||
return multibase.encode(base, multihash.decode(cid.multihash).digest) | ||
case 'D': // hash digest encoded in base %b without base prefix | ||
return multibase.encode(base, multihash.decode(cid.multihash).digest).slice(1) | ||
case 's': // cid string encoded in base %b | ||
return cid.toBaseEncodedString(base) | ||
case 'S': // cid string without base prefix | ||
return cid.version === 1 | ||
? cid.toBaseEncodedString(base).slice(1) | ||
: multibase.encode(base, cid.buffer).toString().slice(1) | ||
case 'P': // prefix | ||
const { name, length } = multihash.decode(cid.multihash) | ||
return `cidv${cid.version}-${cid.codec}-${name}-${length}` | ||
default: | ||
throw new Error(`unrecognized specifier in format string: ${specifier}`) | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
/* eslint-env mocha */ | ||
'use strict' | ||
|
||
const chai = require('chai') | ||
const dirtyChai = require('dirty-chai') | ||
const expect = chai.expect | ||
chai.use(dirtyChai) | ||
const CIDToolCli = require('./utils/cid-tool-cli') | ||
const TestCID = require('../fixtures/test-cid') | ||
|
||
describe('cli format', () => { | ||
it('should format CID and change to CIDv1', async () => { | ||
const cli = CIDToolCli() | ||
const expectedOutput = TestCID.b58 + '\n' | ||
const { stdout } = await cli(`format ${TestCID.v0} --cid-version=1`) | ||
expect(stdout).to.equal(expectedOutput) | ||
}) | ||
|
||
it('should format CID and change to base64', async () => { | ||
const cli = CIDToolCli() | ||
const expectedOutput = TestCID.b64 + '\n' | ||
const { stdout } = await cli(`format ${TestCID.b32} --base=base64`) | ||
expect(stdout).to.equal(expectedOutput) | ||
}) | ||
|
||
it('should format CID and change to CIDv1 and base32', async () => { | ||
const cli = CIDToolCli() | ||
const expectedOutput = TestCID.b32 + '\n' | ||
const { stdout } = await cli(`format ${TestCID.v0} --cid-version=1 --base=base32`) | ||
expect(stdout).to.equal(expectedOutput) | ||
}) | ||
}) |
Oops, something went wrong.