Skip to content
This repository has been archived by the owner on Mar 10, 2020. It is now read-only.

Support specify hash algorithm in files.add #597

Merged
merged 4 commits into from
Sep 8, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 21 additions & 1 deletion src/files/add.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,27 @@ module.exports = (send) => {
return callback(new Error('"files" must be a buffer, readable stream, or array of objects'))
}

const request = { path: 'add', files: files, qs: opts }
const qs = {}

if (opts['cid-version'] != null) {
qs['cid-version'] = opts['cid-version']
} else if (opts.cidVersion != null) {
qs['cid-version'] = opts.cidVersion
}

if (opts['raw-leaves'] != null) {
qs['raw-leaves'] = opts['raw-leaves']
} else if (opts.rawLeaves != null) {
qs['raw-leaves'] = opts.rawLeaves
}

if (opts.hash != null) {
qs.hash = opts.hash
} else if (opts.hashAlg != null) {
qs.hash = opts.hashAlg
}

const request = { path: 'add', files: files, qs: qs }

// Transform the response stream to DAGNode values
const transform = (res, callback) => DAGNodeStream.streamToValue(send, res, callback)
Expand Down
13 changes: 8 additions & 5 deletions src/object/data.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

const promisify = require('promisify-es6')
const streamToValue = require('../utils/stream-to-value')
const cleanMultihash = require('../utils/clean-multihash')
const CID = require('cids')
const LRU = require('lru-cache')
const lruOptions = {
max: 128
Expand All @@ -11,7 +11,7 @@ const lruOptions = {
const cache = LRU(lruOptions)

module.exports = (send) => {
return promisify((multihash, options, callback) => {
return promisify((cid, options, callback) => {
if (typeof options === 'function') {
callback = options
options = {}
Expand All @@ -20,21 +20,24 @@ module.exports = (send) => {
options = {}
}

let cidB58Str

try {
multihash = cleanMultihash(multihash, options)
cid = new CID(cid)
cidB58Str = cid.toBaseEncodedString()
} catch (err) {
return callback(err)
}

const node = cache.get(multihash)
const node = cache.get(cidB58Str)

if (node) {
return callback(null, node.data)
}

send({
path: 'object/data',
args: multihash
args: cidB58Str
}, (err, result) => {
if (err) {
return callback(err)
Expand Down
15 changes: 9 additions & 6 deletions src/object/get.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ const dagPB = require('ipld-dag-pb')
const DAGNode = dagPB.DAGNode
const DAGLink = dagPB.DAGLink
const bs58 = require('bs58')
const cleanMultihash = require('../utils/clean-multihash')
const CID = require('cids')
const LRU = require('lru-cache')
const lruOptions = {
max: 128
Expand All @@ -14,7 +14,7 @@ const lruOptions = {
const cache = LRU(lruOptions)

module.exports = (send) => {
return promisify((multihash, options, callback) => {
return promisify((cid, options, callback) => {
if (typeof options === 'function') {
callback = options
options = {}
Expand All @@ -24,21 +24,24 @@ module.exports = (send) => {
options = {}
}

let cidB58Str

try {
multihash = cleanMultihash(multihash, options)
cid = new CID(cid)
cidB58Str = cid.toBaseEncodedString()
} catch (err) {
return callback(err)
}

const node = cache.get(multihash)
const node = cache.get(cidB58Str)

if (node) {
return callback(null, node)
}

send({
path: 'object/get',
args: multihash
args: cidB58Str
}, (err, result) => {
if (err) {
return callback(err)
Expand All @@ -52,7 +55,7 @@ module.exports = (send) => {
if (err) {
return callback(err)
}
cache.set(multihash, node)
cache.set(cidB58Str, node)
callback(null, node)
})
})
Expand Down
15 changes: 9 additions & 6 deletions src/utils/get-dagnode.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,21 +3,24 @@
const DAGNode = require('ipld-dag-pb').DAGNode
const parallel = require('async/parallel')
const CID = require('cids')
const mh = require('multihashes')
const streamToValue = require('./stream-to-value')

module.exports = function (send, hash, callback) {
// Until js-ipfs supports object/get and object/data by CID
// we need to convert our CID or multihash hash into a multihash
const multihash = mh.toB58String(new CID(hash).multihash)
let cid

try {
cid = new CID(hash)
} catch (err) {
return callback(err)
}

// Retrieve the object and its data in parallel, then produce a DAGNode
// instance using this information.
parallel([
(done) => {
send({
path: 'object/get',
args: multihash
args: cid.toBaseEncodedString()
}, done)
},
(done) => {
Expand All @@ -26,7 +29,7 @@ module.exports = function (send, hash, callback) {
// See https://github.com/ipfs/go-ipfs/issues/1582 for more details.
send({
path: 'object/data',
args: multihash
args: cid.toBaseEncodedString()
}, done)
}
], (err, res) => {
Expand Down
51 changes: 51 additions & 0 deletions test/files.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,27 @@ const expect = chai.expect
chai.use(dirtyChai)
const isNode = require('detect-node')
const loadFixture = require('aegir/fixtures')
const mh = require('multihashes')
const CID = require('cids')

const FactoryClient = require('./ipfs-factory/client')

const testfile = isNode
? loadFixture(__dirname, '/fixtures/testfile.txt')
: loadFixture(__dirname, 'fixtures/testfile.txt')

// TODO: Test against all algorithms Object.keys(mh.names)
// This subset is known to work with both go-ipfs and js-ipfs as of 2017-09-05
const HASH_ALGS = [
'sha1',
'sha2-256',
'sha2-512',
'keccak-224',
'keccak-256',
'keccak-384',
'keccak-512'
]

describe('.files (the MFS API part)', function () {
this.timeout(120 * 1000)

Expand Down Expand Up @@ -73,6 +87,25 @@ describe('.files (the MFS API part)', function () {
})
})

HASH_ALGS.forEach((name) => {
it(`files.add with hash=${name} and raw-leaves=false`, (done) => {
const content = String(Math.random() + Date.now())
const file = {
path: content + '.txt',
content: Buffer.from(content)
}
const options = { hash: name, 'raw-leaves': false }

ipfs.files.add([file], options, (err, res) => {
if (err) return done(err)
expect(res).to.have.length(1)
const cid = new CID(res[0].hash)
expect(mh.decode(cid.multihash).name).to.equal(name)
done()
})
})
})

it('files.mkdir', (done) => {
ipfs.files.mkdir('/test-folder', done)
})
Expand Down Expand Up @@ -230,6 +263,24 @@ describe('.files (the MFS API part)', function () {
})
})

HASH_ALGS.forEach((name) => {
it(`files.add with hash=${name} and raw-leaves=false`, () => {
const content = String(Math.random() + Date.now())
const file = {
path: content + '.txt',
content: Buffer.from(content)
}
const options = { hash: name, 'raw-leaves': false }

return ipfs.files.add([file], options)
.then((res) => {
expect(res).to.have.length(1)
const cid = new CID(res[0].hash)
expect(mh.decode(cid.multihash).name).to.equal(name)
})
})
})

it('files.mkdir', () => {
return ipfs.files.mkdir('/test-folder')
})
Expand Down