Skip to content
This repository was archived by the owner on Apr 29, 2020. It is now read-only.

Commit 55c5dba

Browse files
authored
fix: validate rabin args (#32)
* fix: validate rabin args go-ipfs requires a min chunk size of 16 and will use that for the max/avg if they are set smaller than the min, so perform the same sort of validation.
1 parent 78d75cc commit 55c5dba

File tree

2 files changed

+66
-1
lines changed

2 files changed

+66
-1
lines changed

src/chunker/rabin.js

+16
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
const BufferList = require('bl')
44
const { create } = require('rabin-wasm')
5+
const errcode = require('err-code')
56

67
module.exports = async function * rabinChunker (source, options) {
78
const rabin = jsRabin()
@@ -12,12 +13,27 @@ module.exports = async function * rabinChunker (source, options) {
1213
avg = options.avgChunkSize
1314
min = options.minChunkSize
1415
max = options.maxChunkSize
16+
} else if (!options.avgChunkSize) {
17+
throw errcode(new Error('please specify an average chunk size'), 'ERR_INVALID_AVG_CHUNK_SIZE')
1518
} else {
1619
avg = options.avgChunkSize
1720
min = avg / 3
1821
max = avg + (avg / 2)
1922
}
2023

24+
// validate min/max/avg in the same way as go
25+
if (min < 16) {
26+
throw errcode(new Error('rabin min must be greater than 16'), 'ERR_INVALID_MIN_CHUNK_SIZE')
27+
}
28+
29+
if (max < min) {
30+
max = min
31+
}
32+
33+
if (avg < min) {
34+
avg = min
35+
}
36+
2137
const sizepow = Math.floor(Math.log2(avg))
2238

2339
for await (const chunk of rabin(source, {

test/chunker-rabin.spec.js

+50-1
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ describe('chunker: rabin', function () {
5656
const chunks = await all(chunker([b1], {
5757
...defaultOptions,
5858
maxChunkSize: 262144,
59-
minChunkSize: 1,
59+
minChunkSize: 18,
6060
avgChunkSize: 256
6161
}))
6262

@@ -83,4 +83,53 @@ describe('chunker: rabin', function () {
8383
expect(chunk).to.have.length.lte(opts.maxChunkSize)
8484
})
8585
})
86+
87+
it('throws when min chunk size is too small', async () => {
88+
const opts = {
89+
...defaultOptions,
90+
minChunkSize: 1,
91+
maxChunkSize: 100
92+
}
93+
94+
try {
95+
await all(chunker([], opts))
96+
throw new Error('Should have thrown')
97+
} catch (err) {
98+
expect(err.code).to.equal('ERR_INVALID_MIN_CHUNK_SIZE')
99+
}
100+
})
101+
102+
it('throws when avg chunk size is not specified', async () => {
103+
const opts = {
104+
...defaultOptions,
105+
avgChunkSize: undefined
106+
}
107+
108+
try {
109+
await all(chunker([], opts))
110+
throw new Error('Should have thrown')
111+
} catch (err) {
112+
expect(err.code).to.equal('ERR_INVALID_AVG_CHUNK_SIZE')
113+
}
114+
})
115+
116+
it('uses the min chunk size when max and avg are too small', async () => {
117+
let file = Buffer.concat([rawFile, Buffer.from('hello')])
118+
const opts = {
119+
...defaultOptions,
120+
minChunkSize: 100,
121+
maxChunkSize: 5,
122+
avgChunkSize: 5
123+
}
124+
125+
const chunks = await all(chunker([file], opts))
126+
127+
chunks.forEach((chunk, index) => {
128+
if (index === chunks.length - 1) {
129+
expect(chunk.length).to.equal(81)
130+
} else {
131+
expect(chunk.length).to.equal(100)
132+
}
133+
})
134+
})
86135
})

0 commit comments

Comments
 (0)