Skip to content

Commit a316b12

Browse files
authored
fix: faster toString for integrity (#75)
Note that the ordering of hashes in the result varies slightly.
1 parent 6e6877d commit a316b12

File tree

1 file changed

+48
-6
lines changed

1 file changed

+48
-6
lines changed

lib/index.js

Lines changed: 48 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
const crypto = require('crypto')
44
const MiniPass = require('minipass')
55

6-
const SPEC_ALGORITHMS = ['sha256', 'sha384', 'sha512']
6+
const SPEC_ALGORITHMS = ['sha512', 'sha384', 'sha256']
77
const DEFAULT_ALGORITHMS = ['sha512']
88

99
// TODO: this should really be a hardcoded list of algorithms we support,
@@ -186,6 +186,39 @@ class Hash {
186186
}
187187
}
188188

189+
function integrityHashToString (toString, sep, opts, hashes) {
190+
const toStringIsNotEmpty = toString !== ''
191+
192+
let shouldAddFirstSep = false
193+
let complement = ''
194+
195+
const lastIndex = hashes.length - 1
196+
197+
for (let i = 0; i < lastIndex; i++) {
198+
const hashString = Hash.prototype.toString.call(hashes[i], opts)
199+
200+
if (hashString) {
201+
shouldAddFirstSep = true
202+
203+
complement += hashString
204+
complement += sep
205+
}
206+
}
207+
208+
const finalHashString = Hash.prototype.toString.call(hashes[lastIndex], opts)
209+
210+
if (finalHashString) {
211+
shouldAddFirstSep = true
212+
complement += finalHashString
213+
}
214+
215+
if (toStringIsNotEmpty && shouldAddFirstSep) {
216+
return toString + sep + complement
217+
}
218+
219+
return toString + complement
220+
}
221+
189222
class Integrity {
190223
get isIntegrity () {
191224
return true
@@ -201,15 +234,24 @@ class Integrity {
201234

202235
toString (opts) {
203236
let sep = opts?.sep || ' '
237+
let toString = ''
238+
204239
if (opts?.strict) {
205240
// Entries must be separated by whitespace, according to spec.
206241
sep = sep.replace(/\S+/g, ' ')
242+
243+
for (const hash of SPEC_ALGORITHMS) {
244+
if (this[hash]) {
245+
toString = integrityHashToString(toString, sep, opts, this[hash])
246+
}
247+
}
248+
} else {
249+
for (const hash of Object.keys(this)) {
250+
toString = integrityHashToString(toString, sep, opts, this[hash])
251+
}
207252
}
208-
return Object.keys(this).map(k => {
209-
return this[k].map(hash => {
210-
return Hash.prototype.toString.call(hash, opts)
211-
}).filter(x => x.length).join(sep)
212-
}).filter(x => x.length).join(sep)
253+
254+
return toString
213255
}
214256

215257
concat (integrity, opts) {

0 commit comments

Comments
 (0)