-
Notifications
You must be signed in to change notification settings - Fork 57
/
hashring.test.js
130 lines (104 loc) · 4.3 KB
/
hashring.test.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
var should = require('should')
, hashring = require('../lib/hashring');
module.exports = {
'Library version': function(){
hashring.version.should.match(/^\d+\.\d+\.\d+$/);
}
, 'Constructing with a string': function(){
var ring = new hashring('192.168.0.102:11212');
ring.nodes.should.have.length(1);
ring.sortedKeys.length.should.be.above(1);
Object.keys(ring.weights).should.have.length(0);
}
, 'Constructing with a array': function(){
var ring = new hashring(['192.168.0.102:11212', '192.168.0.103:11212', '192.168.0.104:11212']);
ring.nodes.should.have.length(3);
ring.sortedKeys.length.should.be.above(1);
Object.keys(ring.weights).should.have.length(0);
}
, 'Constructing with a object': function(){
var ring = new hashring({'192.168.0.102:11212': 1, '192.168.0.103:11212': 2, '192.168.0.104:11212': 1});
ring.nodes.should.have.length(3);
ring.sortedKeys.length.should.be.above(1);
Object.keys(ring.weights).should.have.length(3);
}
, 'Constructing with a different algorithm': function(){
var ring = new hashring('192.168.0.102:11212', 'md5');
ring.nodes.should.have.length(1);
ring.algorithm.should.equal('md5');
ring.sortedKeys.length.should.be.above(1);
Object.keys(ring.weights).should.have.length(0);
}
, 'Looking up keys': function(){
var ring = new hashring(['192.168.0.102:11212', '192.168.0.103:11212', '192.168.0.104:11212']);
ring.nodes.indexOf(ring.getNode('foo')).should.be.above(-1);
// NOTE we are going to do some flaky testing ;P
ring.getNode('foo').should.equal('192.168.0.104:11212');
ring.getNode('pewpew').should.equal('192.168.0.103:11212');
// we are not gonna verify the results
// we are just gonna test if we don't fuck something up in the code, so it throws errors or whatever
// unicode keys, just because people roll like that
ring.nodes.indexOf(ring.getNode('привет мир, Memcached и nodejs для победы')).should.be.above(-1);
// other odd keys
ring.nodes.indexOf(ring.getNode(1)).should.be.above(-1);
ring.nodes.indexOf(ring.getNode(0)).should.be.above(-1);
ring.nodes.indexOf(ring.getNode([])).should.be.above(-1);
ring.nodes.indexOf(ring.getNode({wtf:'lol'})).should.be.above(-1);
ring.getNode({wtf:'lol'}).should.equal(ring.getNode({wtf:'amazing .toStringing'}));
}
, 'Replacing servers': function(){
var ring = new hashring(['192.168.0.102:11212', '192.168.0.103:11212', '192.168.0.104:11212'])
, amazon = ring.getNode('justdied')
, skynet = '192.168.0.128:11212'
ring.replaceServer(amazon, skynet);
ring.cache.justdied.should.equal(skynet);
ring.cache = {}; // clear cache
ring.getNode('justdied').should.equal(skynet);
}
, 'Removing servers': function(){
var ring = new hashring(['192.168.0.102:11212', '192.168.0.103:11212', '192.168.0.104:11212']);
ring.removeServer('192.168.0.102:11212');
ring.nodes.indexOf('192.168.0.102:11212').should.equal(-1);
}
// kindly lended from `node-hash-ring` :)
, 'Distribution': function(){
var iterations = 100000
, nodes = {'192.168.0.102:11212': 1, '192.168.0.103:11212': 1, '192.168.0.104:11212': 1}
, ring = new hashring(nodes)
, genCode = function(length){
length = length || 10;
var chars = "QWERTYUIOPASDFGHJKLZXCVBNMqwertyuiopasdfghjklzxcvbnm1234567890"
, numChars = chars.length
, ret = ""
, i = 0;
for (; i < length; i++) {
ret += chars[parseInt(Math.random() * numChars, 10)];
}
return ret;
}
var counts = {}
, node
, i
, len
, word;
for (i = 0, len = nodes.length; i < len; i++) {
node = nodes[i];
counts[node] = 0;
}
for (i = 0, len = iterations; i < len; i++) {
word = genCode(10);
node = ring.getNode(word);
counts[node] = counts[node] || 0;
counts[node]++;
}
var total = Object.keys(counts).reduce(function(sum, node) {
return sum += counts[node];
}, 0.0);
var delta = 0.05
, lower = 1.0 / 3 - 0.05
, upper = 1.0 / 3 + 0.05;
for(node in counts) {
(counts[node] / total).should.be.within(lower, upper);
}
}
};