Skip to content
This repository has been archived by the owner on Feb 12, 2024. It is now read-only.

Add support for --only-hash - Calculating a multihash without adding the content to IPFS #1205

Closed
fazo96 opened this issue Feb 6, 2018 · 13 comments
Assignees
Labels
exp/expert Having worked on the specific codebase is important help wanted Seeking public contribution on this issue P2 Medium: Good to have, but can wait until someone steps up

Comments

@fazo96
Copy link

fazo96 commented Feb 6, 2018

  • Version: 0.27.7
  • Platform: any

Type:

Enhancement

Severity:

Low

Description:

go-ipfs has the --only-hash option when calling ipfs add. It is useful in the strange case where you need to store a multihash of some data somewhere before actually adding the data to IPFS.

Maybe this is already possibile? I tried looking around but it seems the option is only in go-ipfs. I thought about adding the data then deleting from the local node but it looks like this can't be done either

@mitra42
Copy link

mitra42 commented Feb 6, 2018

While I don't need this currently, this was something one of our earlier demos wanted. The scenario was building a data structure that referred to a IPFS, I wanted something that would synchronously return the hash to add to that data structure while I was in the background asynchronously adding the content.

@fazo96
Copy link
Author

fazo96 commented Feb 7, 2018

We found that using https://github.com/ipld/js-ipld-dag-pb (for protobuf) and https://github.com/ipld/js-ipld-dag-cbor (for cbor) directly allows us to easily compute hashes, however this cannot be used when adding a directory tree, only with small self-contained pieces of information

@JonKrone
Copy link
Contributor

JonKrone commented Feb 8, 2018

@fazo96, there was some discussion of --only-hash in ipfs-inactive/js-ipfs-http-client#509. Is that what you're looking for? I looked at adding it and it's on my list but haven't found the time yet to work on it. You're welcome to take it on if you're interested :)

@fazo96
Copy link
Author

fazo96 commented Feb 9, 2018

@JonKrone yes, that's exactly what I was looking for, I think it should also be implemented in js-ipfs directly not only in the api client

For now my problem is solved by creating DAGNodes directly, I'd still like to contribute but I need to see if I can find the time

@daviddias daviddias added the status/ready Ready to be worked label Feb 12, 2018
@daviddias daviddias changed the title Calculating a multihash without adding the content to IPFS Add support for --only-hash - Calculating a multihash without adding the content to IPFS Feb 21, 2018
@daviddias daviddias added exp/expert Having worked on the specific codebase is important help wanted Seeking public contribution on this issue P2 Medium: Good to have, but can wait until someone steps up labels Feb 21, 2018
@JonKrone JonKrone self-assigned this Feb 22, 2018
@alexanderattar
Copy link

@fazo96 can you elaborate a little using DAGNode.create to compute the hash? I so far have been unable to get hashes to match from node.files.add. Here's an example that demonstrated different CIDs for each output:

'use strict'

const series = require('async/series')
const IPFS = require('ipfs')
const {
  DAGNode,
  DAGLink
} = require('ipld-dag-pb')

const node = new IPFS()
let fileMultihash

series([
  (cb) => node.on('ready', cb),
  (cb) => node.version((err, version) => {
    if (err) { return cb(err) }
    console.log('Version:', version.version)
    cb()
  }),
  (cb) => DAGNode.create(Buffer.from('Hello'), (err, dagNode) => {
    if (err) {
      return cb(err)
    }
    const mh = dagNode.toJSON().multihash
    console.log('\nComputed hash:', mh)
    cb(null, mh)
  }),
  (cb) => node.files.add(Buffer.from('Hello'), (err, filesAdded) => {
    if (err) { return cb(err) }
    console.log('\nAdded file:', filesAdded[0].path, filesAdded[0].hash)
    fileMultihash = filesAdded[0].hash
    cb()
  }),
  (cb) => node.files.cat(fileMultihash, (err, data) => {
    if (err) { return cb(err) }
    console.log('\nFile content:')
    process.stdout.write(data)
  })
])

@fazo96
Copy link
Author

fazo96 commented Mar 7, 2018

@alexanderattar In my case what I needed was the same result between creating a DAGNode (without storing it in IPFS) using DAGNode.create(buffer) and the result of calling ipfs.object.put(buffer) where the buffer is identical between the two.

This works, I modified your example to show it:

'use strict'

const series = require('async/series')
const IPFS = require('ipfs')
const {
  DAGNode,
  DAGLink
} = require('ipld-dag-pb')

const node = new IPFS()
let fileMultihash

series([
  (cb) => node.on('ready', cb),
  (cb) => node.version((err, version) => {
    if (err) { return cb(err) }
    console.log('Version:', version.version)
    cb()
  }),
  (cb) => DAGNode.create(Buffer.from('Hello'), (err, dagNode) => {
    if (err) {
      return cb(err)
    }
    const mh = dagNode.toJSON().multihash
    console.log('\nComputed hash (dagnode):', mh)
    cb(null, mh)
  }),
  (cb) => node.object.put(Buffer.from('Hello'), (err, dagNode) => {
    if (err) {
      return cb(err)
    }
    const mh = dagNode.toJSON().multihash
    console.log('\nComputed hash (put):', mh)
    console.log('\nBuffer (put):', dagNode.toJSON().data)
    cb(null, mh)
  }),
  (cb) => node.files.add(Buffer.from('Hello'), (err, filesAdded) => {
    if (err) { return cb(err) }
    console.log('\nAdded file:', filesAdded[0].path, filesAdded[0].hash)
    fileMultihash = filesAdded[0].hash
    cb()
  }),
  (cb) => node.object.get(fileMultihash, (err, dagNode) => {
    if (err) {
      return cb(err)
    }
    console.log('\nBuffer (get after add):', dagNode.toJSON().data)
    cb(null, dagNode.toJSON().multihash)
  }),
  (cb) => node.files.cat(fileMultihash, (err, data) => {
    if (err) { return cb(err) }
    console.log('\nFile content:')
    process.stdout.write(data)
  })
])

I also tried to diff the data of the content added using files.add and added using object.put in the same script. It looks like there are some bytes added before the actual content when files.add is used which would explain the different hash.

I am not sure why this happens though, probably the files API is higher level and does some extra work

@alexanderattar
Copy link

Awesome! Thank you @fazo96. This is helpful

@JonKrone
Copy link
Contributor

Merged to master, will be available at next release :).

@ANUDAVIS
Copy link

ANUDAVIS commented Nov 20, 2018

I have a doubt.. Can anyone please help me to clear..
I am asking a case: We can hash a file or data using multihash or sha256 and whether we can retrieve the same data or file from the hash obtained?
or any case or methods are there inorder to retrieve the file or data from hash without using IPFS?
or is there any encryption method which encrypts a 5mb file and outputs some hash like 32 bytes content so that we can retrieve the file from that 32 byte content?

@haywirez
Copy link

Is there a simple, lightweight and reliable way to compute a file's IPFS hash right now? While I'm not using IPFS at the moment, I'd still like to add an info header with the IPFS hash to all uploads in my storage backend.

@alanshaw
Copy link
Member

Does this help @haywirez? https://www.npmjs.com/package/ipfs-only-hash

@xmaysonnave
Copy link

I'm looking for a --only-hash while adding a dag-pb node through IPLD.
The ipfs.add or ipfs.addAll have such optional onlyHash attribute.
However ipfs.dag.put doesn't seem to have it.
Am I missing something ?
Thanks

@awantoch
Copy link

awantoch commented Feb 6, 2021

Just wanted to share this link for anyone coming across this: https://github.com/ipfs/js-ipfs/blob/master/docs/core-api/FILES.md#options

This is now built in to the js client's ipfs.add function by using the onlyHash option. No need for an external library anymore :)

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
exp/expert Having worked on the specific codebase is important help wanted Seeking public contribution on this issue P2 Medium: Good to have, but can wait until someone steps up
Projects
None yet
Development

No branches or pull requests

10 participants