Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

node-ipfs is getting form :) #1

Merged
merged 6 commits into from
Jul 6, 2015
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
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
node_modules/
**/node_modules/
**/*.log
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
21 changes: 17 additions & 4 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
{
"name": "ipfs",
"version": "0.1.1",
"version": "0.0.0",
"description": "ipfs implementation in node",
"main": "index.js",
"main": "src/index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
"test": "echo \"Error: no test specified\" && exit 1",
"start": "IPFS_LOG=* node src/index.js | ./node_modules/.bin/bunyan -o short"
},
"repository": {
"type": "git",
Expand All @@ -18,5 +19,17 @@
"bugs": {
"url": "https:/jbenet/node-ipfs/issues"
},
"homepage": "https:/jbenet/node-ipfs"
"homepage": "https:/jbenet/node-ipfs",
"devDependencies": {
"standard": "^4.5.1"
},
"dependencies": {
"bs58": "^2.0.1",
"bunyan": "^1.4.0",
"k-bucket": "^0.5.0",
"multiaddr": "^0.1.2",
"multicast-dns": "^2.2.0",
"multihashing": "^0.1.2",
"network": "^0.1.3"
}
}
5 changes: 5 additions & 0 deletions src/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
var Routing = require('./routing')

var r = new Routing()

r.start()
107 changes: 107 additions & 0 deletions src/routing/discovery/mdns/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
var mdns = require('multicast-dns')()
var Id = require('./../../routers/dht/peer/id')
var Peer = require('./../../routers/dht/peer')
var Multiaddr = require('multiaddr')
var log = require('ipfs-logger').group('discovery')

exports = module.exports = sonar

function sonar (cb) {
var serviceTag = 'discovery.ipfs.io.local'

mdns.on('warning', function (err) {
cb(err)
})

mdns.on('response', function (response) {
if (!response.answers) {
return
}

var answers = {
ptr: {},
srv: {},
txt: {},
a: []
}

response.answers.forEach(function (answer) {
switch (answer.type) {
case 'PTR': answers.ptr = answer; break
case 'SRV': answers.srv = answer; break
case 'TXT': answers.txt = answer; break
case 'A': answers.a.push(answer); break
default: break
}
})

if (answers.ptr.name !== serviceTag) {
return
}

var b58Id = answers.txt.data
var port = answers.srv.data.port
var multiaddrs = []

answers.a.forEach(function (a) {
multiaddrs.push(new Multiaddr('/ip4/' + a.data + '/tcp/' + port))
})

log.info('peer found -', b58Id)
var peerId = Id.createFromB58String(b58Id)
cb(null, new Peer(peerId, multiaddrs))
})

mdns.on('query', function (query) {
// answer with PTR, SRV and A for several IP addr
})

setInterval(function () {
mdns.query({
questions: [{
name: serviceTag,
type: 'PTR'
}]
})
}, 1e3 * 5)
}

/* for reference

[ { name: 'discovery.ipfs.io.local',
type: 'PTR',
class: 1,
ttl: 120,
data: 'QmbBHw1Xx9pUpAbrVZUKTPL5Rsph5Q9GQhRvcWVBPFgGtC.discovery.ipfs.io.local' },

{ name: 'QmbBHw1Xx9pUpAbrVZUKTPL5Rsph5Q9GQhRvcWVBPFgGtC.discovery.ipfs.io.local',
type: 'SRV',
class: 1,
ttl: 120,
data: { priority: 10, weight: 1, port: 4001, target: 'lorien.local' } },

{ name: 'lorien.local',
type: 'A',
class: 1,
ttl: 120,
data: '127.0.0.1' },

{ name: 'lorien.local',
type: 'A',
class: 1,
ttl: 120,
data: '127.94.0.1' },

{ name: 'lorien.local',
type: 'A',
class: 1,
ttl: 120,
data: '172.16.38.224' },

{ name: 'QmbBHw1Xx9pUpAbrVZUKTPL5Rsph5Q9GQhRvcWVBPFgGtC.discovery.ipfs.io.local',
type: 'TXT',
class: 1,
ttl: 120,
data: 'QmbBHw1Xx9pUpAbrVZUKTPL5Rsph5Q9GQhRvcWVBPFgGtC' } ],

*/
76 changes: 76 additions & 0 deletions src/routing/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
/*
* routing/index.js Routing is the front door for everything that happens on the routing layer.
* Other modules present in the remaining layers should not require to interact with modules
* behind this level
*/

var mDNSDiscovery = require('./discovery/mdns')
var Peer = require('./routers/dht/peer')
var Id = require('./routers/dht/peer/id')
var network = require('network')
var Multiaddr = require('multiaddr')
var DHT = require('./routers/dht')

exports = module.exports = Routing

function Routing () {
var self = this

if (!(self instanceof Routing)) {
throw new Error('Routing should be called with new')
}

self.router
self.peer

// instantiate this peer

self.start = function (cb) {
network.get_private_ip(function (err, ip) {
if (err) {
cb(err)
}
var multiaddrs = []
multiaddrs.push(new Multiaddr('/ip4/' + ip + '/tcp/' + 4001))
self.peer = new Peer(Id.create(), multiaddrs)
self.useRouterDHT()
self.useDiscoveryMDNS()
if (cb) {
cb()
}
})
}

// routing interface

self.putValue = function (key, buf) {}
self.getValue = function (key) {}
self.provide = function (key) {}
self.findPeer = function (key) {}
self.ping = function (key) {}

// select strategies (plugins) used

self.useRouterDHT = function () {
self.router = new DHT(self.peer)
}

self.useRouterMDNS = function () {}

self.useDiscoveryBootstrapList = function () {}

self.useDiscoveryMDNS = function () {
mDNSDiscovery(function (err, peer) {
if (err) {
return console.log('mDNS Discovery err: ', err)
}
self.router.addPeer(peer)
})
}

self.useDiscoveryRandomWalk = function () {
// use router to find a random peer
}

}

46 changes: 46 additions & 0 deletions src/routing/routers/dht/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
/*
* DHT routing plugin for router
*/

var KBucket = require('k-bucket')
var log = require('ipfs-logger').group('router')

exports = module.exports = DHT

function DHT (peerSelf) {
var self = this

if (!(self instanceof DHT)) {
throw new Error('DHT must be called with new')
}

var kBucket = new KBucket({
localNodeId: peerSelf.id.toBytes(),
numberOfNodesPerKBucket: 20 // same as go-ipfs
})

kBucket.on('ping', function (oldContacts, newContact) {
log.info('kbucket ping')
log.info('old', oldContacts)
log.info('new', newContact)
// 1. ping each oldContact
// 2. those who respond should be readded (kBucket.add)
// 3. those who didn't respond should be removed (kBucket.remove)
// 4. if at least one is removed, then newContact can be added (kBucket.add)
})

self.addPeer = function (peer) {
log.info('New DHT candidate -', peer.id.toB58String())
kBucket.add({
id: peer.id.toBytes(),
peer: peer
})
}

self.candidatesToId = function (id) {
return kBucket.closest({
id: id.toBytes(),
n: 3
})
}
}
79 changes: 79 additions & 0 deletions src/routing/routers/dht/peer/id.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
/*
* Id is an object representation of a peer Id. a peer Id is a multihash
*/

var multihashing = require('multihashing')
var base58 = require('bs58')
var crypto = require('crypto')

exports = module.exports = Id

function Id (id, pubKey, privKey) {
var self = this

if (!(self instanceof Id)) {
throw new Error('Id must be called with new')
}

self.privKey = privKey
self.pubKey = pubKey
self.id = id // multihash - sha256 - buffer

// pretty print

self.toPrint = function () {
return {
id: id.toHexString(),
privKey: privKey.toString('hex'),
pubKey: pubKey.toString('hex')
}
}

// encode/decode functions

self.toHexString = function () {
return self.id.toString('hex')
}

self.toBytes = function () {
return self.id
}

self.toB58String = function () {
return base58.encode(self.id)
}

}

// generation

exports.create = function () {
var ecdh = crypto.createECDH('secp256k1')
ecdh.generateKeys()

var mhId = multihashing(ecdh.getPublicKey(), 'sha2-256')

return new Id(mhId, ecdh.getPrivateKey(), ecdh.getPublicKey())
}

exports.createFromHexString = function (str) {
return new Id(new Buffer(str), 'hex')
}

exports.createFromBytes = function (buf) {
return new Id(buf)
}

exports.createFromB58String = function (str) {
return new Id(new Buffer(base58.decode(str)))
}

exports.createFromPubKey = function (pubKey) {
var mhId = multihashing(pubKey, 'sha2-256')

return new Id(mhId, null, pubKey)
}

exports.createFromPrivKey = function () {
// TODO(daviddias) derive PubKey from priv
}
22 changes: 22 additions & 0 deletions src/routing/routers/dht/peer/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
/*
* Peer represents a peer on the IPFS network
*/

var Id = require('./id.js')

exports = module.exports = Peer

function Peer (peerId, multiaddrs) {
var self = this

if (!(self instanceof Peer)) {
throw new Error('Peer must be called with new')
}

if (!(peerId instanceof Id)) {
throw new Error('Peer must be created with an instance of Id')
}

self.id = peerId
self.multiaddrs = multiaddrs
}
20 changes: 20 additions & 0 deletions src/utils/ipfs-logger/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
{
"name": "ipfs-logger",
"version": "0.0.0",
"description": "IPFS logging module (wrapper of bunyan) for the Node.js implementation of IPFS",
"main": "src/index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"keywords": [
"IPFS"
],
"author": "David Dias <[email protected]>",
"license": "MIT",
"dependencies": {
"bunyan": "^1.4.0"
},
"devDependencies": {
"standard": "^4.5.2"
}
}
Loading