ndn-js-contrib
Version:
Reusable 'Classes' for Named Data Networking: NameTree, PIT, FIB, ContentStore, Interfaces, and Transports
137 lines (110 loc) • 3.89 kB
JavaScript
var NameTree = require("./NameTree.js");
var crypto = require("ndn-js/js/crypto.js");
function PIT(){
this._nameTree = new NameTree();
}
PIT.prototype.insert = function PIT_insert(interest, face){
var self = this;
var nameTreeNode = self._nameTree.get(interest.name);
if (!nameTreeNode.getItem())
nameTreeNode.setItem(new PIT.Node());
var pitNode = nameTreeNode.getItem();
return pitNode.addEntry(interest, face);
};
PIT.prototype.lookup = function PIT_lookup(data, face){
var self = this;
var dataFace = face;
return new Promise(function PIT_lookup_Promise(resolve,reject){
var nameWithDigest = data.name.getPrefix(data.name.size());
nameWithDigest.append("sha256digest=" + crypto.createHash('sha256')
.update(data.wireEncode()
.buffer)
.digest()
.toString('hex'));
self._nameTree.up(nameWithDigest);
self._nameTree.skip(function(node){
return (!node.getItem());
});
var results = [];
for(var ntnode of self._nameTree){
var pitNode = ntnode.getItem();
//console.log("checking pitNode", pitNode)
for(var entry in pitNode._entries){
//console.log("checking entry", pitNode._entries[entry].interest, data)
if (pitNode._entries[entry].interest.matchesName(data.name)){
//console.log("found match")
var ent = pitNode._entries.splice(entry, 1)[0];
clearTimeout(ent.timeID);
ent.resolve({
data : data
, face : dataFace
, rtt : Date.now() - ent.inserted
});
if (ent.face){
//console.log("entry has face")
var dup = false;
for (var face in results){
//console.log("checking dup")
if (results[face] === ent.face){
dup = true;
}
}
if (!dup){
//console.log("pushing inface", results)
results.push(ent.face);
//console.log("results",results);
}
}
}
}
if (!pitNode._entries)
self._nameTree.remove(ntnode.prefix)
}
if (results.length > 0)
resolve(results);
else
reject(new Error("PIT.lookup(data): no outbound pitentries for that data"));
});
};
PIT.Node = function PIT_Node(){
this._entries = [];
};
PIT.Node.prototype.timeout = function PIT_Node_timeout(interest){
for (var index in this._entries)
if (this._entries[index].interest === interest){
this._entries[index].reject();
return this._entries.splice(index, 1)[0];
}
}
PIT.Node.prototype.addEntry = function PIT_Node_addEntry(interest, face){
var self = this;
for (var entry of this._entries){
//console.log("checking for duplicate", entry.interest.getNonceAsBuffer(), interest.getNonceAsBuffer())
if (entry.interest.getNonce().equals(interest.getNonce()))
return Promise.reject("Interest is Duplicate");
}
return new Promise(function PIT_Node_addEntry_Promise(resolve,reject){
//console.log("interest", interest)
self._entries.push({
interest : interest
, resolve : function(res){
//console.log("resolving Pit entry", res)
resolve(res);
}
, reject : function(){
reject(interest)
}
, face : face
, inserted : Date.now()
, timeID : setTimeout(function PIT_Node_entry_timeout(){
self.timeout(interest);
}, interest.getInterestLifetimeMilliseconds() || 1)
});
});
}
/**Pending Interest Table
*@constructor
*@param {NameTree} nameTree the nameTree to build the table on top of
*@returns {PIT} a new PIT
*/
module.exports = PIT;