diff options
Diffstat (limited to 'node_modules/concordance/lib')
47 files changed, 0 insertions, 5398 deletions
diff --git a/node_modules/concordance/lib/Circular.js b/node_modules/concordance/lib/Circular.js deleted file mode 100644 index c5c020267..000000000 --- a/node_modules/concordance/lib/Circular.js +++ /dev/null @@ -1,35 +0,0 @@ -'use strict' - -class Circular { - constructor () { - this.stack = new Map() - } - - add (descriptor) { - if (this.stack.has(descriptor)) throw new Error('Already in stack') - - if (descriptor.isItem !== true && descriptor.isMapEntry !== true && descriptor.isProperty !== true) { - this.stack.set(descriptor, this.stack.size + 1) - } - return this - } - - delete (descriptor) { - if (this.stack.has(descriptor)) { - if (this.stack.get(descriptor) !== this.stack.size) throw new Error('Not on top of stack') - this.stack.delete(descriptor) - } - return this - } - - has (descriptor) { - return this.stack.has(descriptor) - } - - get (descriptor) { - return this.stack.has(descriptor) - ? this.stack.get(descriptor) - : 0 - } -} -module.exports = Circular diff --git a/node_modules/concordance/lib/Indenter.js b/node_modules/concordance/lib/Indenter.js deleted file mode 100644 index deeca842e..000000000 --- a/node_modules/concordance/lib/Indenter.js +++ /dev/null @@ -1,22 +0,0 @@ -'use strict' - -class Indenter { - constructor (level, step) { - this.level = level - this.step = step - this.value = step.repeat(level) - } - - increase () { - return new Indenter(this.level + 1, this.step) - } - - decrease () { - return new Indenter(this.level - 1, this.step) - } - - toString () { - return this.value - } -} -module.exports = Indenter diff --git a/node_modules/concordance/lib/Registry.js b/node_modules/concordance/lib/Registry.js deleted file mode 100644 index f4a4b6808..000000000 --- a/node_modules/concordance/lib/Registry.js +++ /dev/null @@ -1,24 +0,0 @@ -'use strict' - -class Registry { - constructor () { - this.counter = 0 - this.map = new WeakMap() - } - - has (value) { - return this.map.has(value) - } - - get (value) { - return this.map.get(value).descriptor - } - - alloc (value) { - const index = ++this.counter - const pointer = {descriptor: null, index} - this.map.set(value, pointer) - return pointer - } -} -module.exports = Registry diff --git a/node_modules/concordance/lib/compare.js b/node_modules/concordance/lib/compare.js deleted file mode 100644 index 7e24228e6..000000000 --- a/node_modules/concordance/lib/compare.js +++ /dev/null @@ -1,103 +0,0 @@ -'use strict' - -const constants = require('./constants') -const describe = require('./describe') -const recursorUtils = require('./recursorUtils') -const shouldCompareDeep = require('./shouldCompareDeep') -const symbolProperties = require('./symbolProperties') -const Circular = require('./Circular') - -const AMBIGUOUS = constants.AMBIGUOUS -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function shortcircuitPrimitive (value) { - if (value === null || value === undefined || value === true || value === false) return true - - const type = typeof value - if (type === 'string' || type === 'symbol') return true - // Don't shortcircuit NaN values - if (type === 'number') return !isNaN(value) - - return false -} - -function compareDescriptors (lhs, rhs) { - const lhsCircular = new Circular() - const rhsCircular = new Circular() - - const lhsStack = [] - const rhsStack = [] - let topIndex = -1 - - do { - let result - if (lhsCircular.has(lhs)) { - result = lhsCircular.get(lhs) === rhsCircular.get(rhs) - ? DEEP_EQUAL - : UNEQUAL - } else if (rhsCircular.has(rhs)) { - result = UNEQUAL - } else { - result = lhs.compare(rhs) - } - - if (result === UNEQUAL) return false - if (result !== DEEP_EQUAL) { - if (!shouldCompareDeep(result, lhs, rhs)) return false - - if (result === AMBIGUOUS && lhs.isProperty === true) { - // Replace both sides by a pseudo-descriptor which collects symbol - // properties instead. - lhs = new symbolProperties.Collector(lhs, lhsStack[topIndex].recursor) - rhs = new symbolProperties.Collector(rhs, rhsStack[topIndex].recursor) - // Replace the current recursors so they can continue correctly after - // the collectors have been "compared". This is necessary since the - // collectors eat the first value after the last symbol property. - lhsStack[topIndex].recursor = recursorUtils.unshift(lhsStack[topIndex].recursor, lhs.collectAll()) - rhsStack[topIndex].recursor = recursorUtils.unshift(rhsStack[topIndex].recursor, rhs.collectAll()) - } - - lhsCircular.add(lhs) - rhsCircular.add(rhs) - - lhsStack.push({ subject: lhs, recursor: lhs.createRecursor() }) - rhsStack.push({ subject: rhs, recursor: rhs.createRecursor() }) - topIndex++ - } - - while (topIndex >= 0) { - lhs = lhsStack[topIndex].recursor() - rhs = rhsStack[topIndex].recursor() - if (lhs !== null && rhs !== null) { - break - } - - if (lhs === null && rhs === null) { - const lhsRecord = lhsStack.pop() - const rhsRecord = rhsStack.pop() - lhsCircular.delete(lhsRecord.subject) - rhsCircular.delete(rhsRecord.subject) - topIndex-- - } else { - return false - } - } - } while (topIndex >= 0) - - return true -} -exports.compareDescriptors = compareDescriptors - -function compare (actual, expected, options) { - if (Object.is(actual, expected)) return { pass: true } - // Primitive values should be the same, so if actual or expected is primitive - // then the values will never compare. - if (shortcircuitPrimitive(actual) || shortcircuitPrimitive(expected)) return { pass: false } - - actual = describe(actual, options) - expected = describe(expected, options) - const pass = compareDescriptors(actual, expected) - return { actual, expected, pass } -} -exports.compare = compare diff --git a/node_modules/concordance/lib/complexValues/arguments.js b/node_modules/concordance/lib/complexValues/arguments.js deleted file mode 100644 index 446407222..000000000 --- a/node_modules/concordance/lib/complexValues/arguments.js +++ /dev/null @@ -1,48 +0,0 @@ -'use strict' - -const constants = require('../constants') -const object = require('./object') - -const AMBIGUOUS = constants.AMBIGUOUS -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - return new DescribedArgumentsValue(Object.assign({ - // Treat as an array, to allow comparisons with arrays - isArray: true, - isList: true - }, props, { ctor: 'Arguments' })) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedArgumentsValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('ArgumentsValue') -exports.tag = tag - -class ArgumentsValue extends object.ObjectValue { - compare (expected) { - if (expected.isComplex !== true) return UNEQUAL - - // When used on the left-hand side of a comparison, argument values may be - // compared to arrays. - if (expected.stringTag === 'Array') return AMBIGUOUS - - return super.compare(expected) - } -} -Object.defineProperty(ArgumentsValue.prototype, 'tag', { value: tag }) - -const DescribedArgumentsValue = object.DescribedMixin(ArgumentsValue) - -class DeserializedArgumentsValue extends object.DeserializedMixin(ArgumentsValue) { - compare (expected) { - // Deserialized argument values may only be compared to argument values. - return expected.isComplex === true && expected.stringTag === 'Array' - ? UNEQUAL - : super.compare(expected) - } -} diff --git a/node_modules/concordance/lib/complexValues/arrayBuffer.js b/node_modules/concordance/lib/complexValues/arrayBuffer.js deleted file mode 100644 index 1053b893e..000000000 --- a/node_modules/concordance/lib/complexValues/arrayBuffer.js +++ /dev/null @@ -1,30 +0,0 @@ -'use strict' - -const typedArray = require('./typedArray') - -function describe (props) { - return new DescribedArrayBufferValue(Object.assign({ - // Assume at least Node.js 4.5.0, which introduces Buffer.from() - buffer: Buffer.from(props.value), - // Set isArray and isList so the property recursor excludes the byte accessors - isArray: true, - isList: true - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedArrayBufferValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('ArrayBufferValue') -exports.tag = tag - -// ArrayBuffers can be represented as regular Buffers, allowing them to be -// treated as TypedArrays for the purposes of this package. -class ArrayBufferValue extends typedArray.TypedArrayValue {} -Object.defineProperty(ArrayBufferValue.prototype, 'tag', { value: tag }) - -const DescribedArrayBufferValue = typedArray.DescribedMixin(ArrayBufferValue) -const DeserializedArrayBufferValue = typedArray.DeserializedMixin(ArrayBufferValue) diff --git a/node_modules/concordance/lib/complexValues/boxed.js b/node_modules/concordance/lib/complexValues/boxed.js deleted file mode 100644 index 3736ad137..000000000 --- a/node_modules/concordance/lib/complexValues/boxed.js +++ /dev/null @@ -1,51 +0,0 @@ -'use strict' - -const recursorUtils = require('../recursorUtils') -const stringPrimitive = require('../primitiveValues/string').tag -const object = require('./object') - -function describe (props) { - return new DescribedBoxedValue(props) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedBoxedValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('BoxedValue') -exports.tag = tag - -class BoxedValue extends object.ObjectValue {} -Object.defineProperty(BoxedValue.prototype, 'tag', {value: tag}) - -class DescribedBoxedValue extends object.DescribedMixin(BoxedValue) { - constructor (props) { - super(props) - this.unboxed = props.unboxed - } - - createListRecursor () { - return recursorUtils.NOOP_RECURSOR - } - - createPropertyRecursor () { - if (this.unboxed.tag !== stringPrimitive) return super.createPropertyRecursor() - - // Just so that createPropertyRecursor() skips the index-based character - // properties. - try { - this.isList = true - return super.createPropertyRecursor() - } finally { - this.isList = false - } - } - - createRecursor () { - return recursorUtils.unshift(super.createRecursor(), this.unboxed) - } -} - -const DeserializedBoxedValue = object.DeserializedMixin(BoxedValue) diff --git a/node_modules/concordance/lib/complexValues/dataView.js b/node_modules/concordance/lib/complexValues/dataView.js deleted file mode 100644 index 0dd6199f6..000000000 --- a/node_modules/concordance/lib/complexValues/dataView.js +++ /dev/null @@ -1,29 +0,0 @@ -'use strict' - -const typedArray = require('./typedArray') - -function describe (props) { - return new DescribedDataViewValue(Object.assign({ - buffer: typedArray.getBuffer(props.value), - // Set isArray and isList so the property recursor excludes the byte accessors - isArray: true, - isList: true - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedDataViewValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('DataViewValue') -exports.tag = tag - -// DataViews can be represented as regular Buffers, allowing them to be treated -// as TypedArrays for the purposes of this package. -class DataViewValue extends typedArray.TypedArrayValue {} -Object.defineProperty(DataViewValue.prototype, 'tag', { value: tag }) - -const DescribedDataViewValue = typedArray.DescribedMixin(DataViewValue) -const DeserializedDataViewValue = typedArray.DeserializedMixin(DataViewValue) diff --git a/node_modules/concordance/lib/complexValues/date.js b/node_modules/concordance/lib/complexValues/date.js deleted file mode 100644 index b437456b8..000000000 --- a/node_modules/concordance/lib/complexValues/date.js +++ /dev/null @@ -1,89 +0,0 @@ -'use strict' - -const dateTime = require('date-time') - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') -const object = require('./object') - -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - const date = props.value - const invalid = isNaN(date.valueOf()) - return new DescribedDateValue(Object.assign({}, props, {invalid})) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedDateValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('DateValue') -exports.tag = tag - -function formatDate (date) { - // Always format in UTC. The local timezone shouldn't be used since it's most - // likely different from that of CI servers. - return dateTime({ - date, - local: false, - showTimeZone: true, - showMilliseconds: true - }) -} - -class DateValue extends object.ObjectValue { - constructor (props) { - super(props) - this.invalid = props.invalid - } - - compare (expected) { - const result = super.compare(expected) - if (result !== SHALLOW_EQUAL) return result - - return (this.invalid && expected.invalid) || Object.is(this.value.getTime(), expected.value.getTime()) - ? SHALLOW_EQUAL - : UNEQUAL - } - - formatShallow (theme, indent) { - const string = formatUtils.formatCtorAndStringTag(theme, this) + ' ' + - (this.invalid ? theme.date.invalid : formatUtils.wrap(theme.date.value, formatDate(this.value))) + ' ' + - theme.object.openBracket - - return super.formatShallow(theme, indent).customize({ - finalize (innerLines) { - return innerLines.isEmpty - ? lineBuilder.single(string + theme.object.closeBracket) - : lineBuilder.first(string) - .concat(innerLines.withFirstPrefixed(indent.increase()).stripFlags()) - .append(lineBuilder.last(indent + theme.object.closeBracket)) - }, - - maxDepth () { - return lineBuilder.single(string + ' ' + theme.maxDepth + ' ' + theme.object.closeBracket) - } - }) - } - - serialize () { - const iso = this.invalid ? null : this.value.toISOString() - return [this.invalid, iso, super.serialize()] - } -} -Object.defineProperty(DateValue.prototype, 'tag', { value: tag }) - -const DescribedDateValue = object.DescribedMixin(DateValue) - -class DeserializedDateValue extends object.DeserializedMixin(DateValue) { - constructor (state, recursor) { - super(state[2], recursor) - this.invalid = state[0] - this.value = new Date(this.invalid ? NaN : state[1]) - } -} diff --git a/node_modules/concordance/lib/complexValues/error.js b/node_modules/concordance/lib/complexValues/error.js deleted file mode 100644 index 781dd7e87..000000000 --- a/node_modules/concordance/lib/complexValues/error.js +++ /dev/null @@ -1,133 +0,0 @@ -'use strict' - -const constants = require('../constants') -const isEnumerable = require('../isEnumerable') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') -const NOOP_RECURSOR = require('../recursorUtils').NOOP_RECURSOR -const object = require('./object') - -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - const error = props.value - return new DescribedErrorValue(Object.assign({ - nameIsEnumerable: isEnumerable(error, 'name'), - name: error.name, - messageIsEnumerable: isEnumerable(error, 'message'), - message: error.message - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedErrorValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('ErrorValue') -exports.tag = tag - -class ErrorValue extends object.ObjectValue { - constructor (props) { - super(props) - this.name = props.name - } - - compare (expected) { - return this.tag === expected.tag && this.name === expected.name - ? super.compare(expected) - : UNEQUAL - } - - formatShallow (theme, indent) { - const name = this.name || this.ctor - - let string = name - ? formatUtils.wrap(theme.error.name, name) - : formatUtils.wrap(theme.object.stringTag, this.stringTag) - if (this.ctor && this.ctor !== name) { - string += ' ' + formatUtils.wrap(theme.error.ctor, this.ctor) - } - if (this.stringTag && this.stringTag !== this.ctor && this.name && !this.name.includes(this.stringTag)) { - string += ' ' + formatUtils.wrap(theme.object.secondaryStringTag, this.stringTag) - } - string += ' ' + theme.object.openBracket - - return super.formatShallow(theme, indent).customize({ - finalize (innerLines) { - return innerLines.isEmpty - ? lineBuilder.single(string + theme.object.closeBracket) - : lineBuilder.first(string) - .concat(innerLines.withFirstPrefixed(indent.increase()).stripFlags()) - .append(lineBuilder.last(indent + theme.object.closeBracket)) - }, - - maxDepth () { - return lineBuilder.single(string + ' ' + theme.maxDepth + ' ' + theme.object.closeBracket) - } - }) - } - - serialize () { - return [this.name, super.serialize()] - } -} -Object.defineProperty(ErrorValue.prototype, 'tag', { value: tag }) - -class DescribedErrorValue extends object.DescribedMixin(ErrorValue) { - constructor (props) { - super(props) - this.nameIsEnumerable = props.nameIsEnumerable - this.messageIsEnumerable = props.messageIsEnumerable - this.message = props.message - } - - createPropertyRecursor () { - const recursor = super.createPropertyRecursor() - - let skipName = this.nameIsEnumerable - let emitMessage = !this.messageIsEnumerable - - let size = recursor.size - if (skipName && size > 0) { - size -= 1 - } - if (emitMessage) { - size += 1 - } - - if (size === 0) return NOOP_RECURSOR - - let done = false - const next = () => { - if (done) return null - - const property = recursor.next() - if (property) { - if (skipName && property.key.value === 'name') { - skipName = false - return next() - } - return property - } - - if (emitMessage) { - emitMessage = false - return this.describeProperty('message', this.describeAny(this.message)) - } - - done = true - return null - } - - return { size, next } - } -} - -class DeserializedErrorValue extends object.DeserializedMixin(ErrorValue) { - constructor (state, recursor) { - super(state[1], recursor) - this.name = state[0] - } -} diff --git a/node_modules/concordance/lib/complexValues/function.js b/node_modules/concordance/lib/complexValues/function.js deleted file mode 100644 index 4ddd38f39..000000000 --- a/node_modules/concordance/lib/complexValues/function.js +++ /dev/null @@ -1,159 +0,0 @@ -'use strict' - -const functionNameSupport = require('function-name-support') - -const constants = require('../constants') -const getStringTag = require('../getStringTag') -const isEnumerable = require('../isEnumerable') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') -const NOOP_RECURSOR = require('../recursorUtils').NOOP_RECURSOR -const object = require('./object') - -const UNEQUAL = constants.UNEQUAL -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL - -// Node.js 4 provides Function, more recent versions use GeneratorFunction -const generatorsHaveGeneratorTag = getStringTag(function * () {}) === 'GeneratorFunction' - -function describe (props) { - const fn = props.value - return new DescribedFunctionValue(Object.assign({ - nameIsEnumerable: isEnumerable(fn, 'name'), - name: typeof fn.name === 'string' ? fn.name : null - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedFunctionValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('FunctionValue') -exports.tag = tag - -class FunctionValue extends object.ObjectValue { - constructor (props) { - super(props) - this.name = props.name - } - - formatShallow (theme, indent) { - const string = formatUtils.wrap(theme.function.stringTag, this.stringTag) + - (this.name ? ' ' + formatUtils.wrap(theme.function.name, this.name) : '') + - ' ' + theme.object.openBracket - - return super.formatShallow(theme, indent).customize({ - finalize (innerLines) { - return innerLines.isEmpty - ? lineBuilder.single(string + theme.object.closeBracket) - : lineBuilder.first(string) - .concat(innerLines.withFirstPrefixed(indent.increase()).stripFlags()) - .append(lineBuilder.last(indent + theme.object.closeBracket)) - }, - - maxDepth () { - return lineBuilder.single(string + ' ' + theme.maxDepth + ' ' + theme.object.closeBracket) - } - }) - } -} -Object.defineProperty(FunctionValue.prototype, 'tag', { value: tag }) - -class DescribedFunctionValue extends object.DescribedMixin(FunctionValue) { - constructor (props) { - super(props) - this.nameIsEnumerable = props.nameIsEnumerable - } - - compare (expected) { - if (this.tag !== expected.tag) return UNEQUAL - if (this.name !== expected.name) return UNEQUAL - if (this.value && expected.value && this.value !== expected.value) return UNEQUAL - - return super.compare(expected) - } - - createPropertyRecursor () { - const recursor = super.createPropertyRecursor() - - const skipName = this.nameIsEnumerable - if (!skipName) return recursor - - let size = recursor.size - if (skipName) { - size -= 1 - } - - if (size === 0) return NOOP_RECURSOR - - const next = () => { - const property = recursor.next() - if (property) { - if (skipName && property.key.value === 'name') { - return next() - } - return property - } - - return null - } - - return { size, next } - } - - serialize () { - return [this.name, generatorsHaveGeneratorTag, super.serialize()] - } -} - -class DeserializedFunctionValue extends object.DeserializedMixin(FunctionValue) { - constructor (state, recursor) { - super(state[2], recursor) - this.name = state[0] - this.trustStringTag = state[1] - } - - compare (expected) { - if (this.tag !== expected.tag) return UNEQUAL - - if (this.name !== expected.name) { - if (this.functionNameSupportFlags === functionNameSupport.bitFlags) { - // The engine used to create the serialization supports the same - // function name inference as the current engine. That said, unless - // the engine has full support for name inference, it's possible that - // names were lost simply due to refactoring. Names are unequal if - // the engine has full support, or if names were inferred. - if (functionNameSupport.hasFullSupport === true || (this.name !== '' && expected.name !== '')) return UNEQUAL - } else if (functionNameSupport.isSubsetOf(this.functionNameSupportFlags)) { - // The engine used to create the serialization could infer more function - // names than the current engine. Assume `expected.name` comes from the - // current engine and treat the names as unequal only if the current - // engine could infer a name. - if (expected.name !== '') return UNEQUAL - } else { - /* istanbul ignore else */ - if (functionNameSupport.isSupersetOf(this.functionNameSupportFlags)) { - // The engine used to create the serialization could infer fewer - // function names than the current engine. Treat the names as unequal - // only if a name was in the serialization. - if (this.name !== '') return UNEQUAL - } - } - } - - // Assume `stringTag` is either 'Function' or 'GeneratorFunction', and that - // it always equals `ctor`. Since Node.js 4 only provides 'Function', even - // for generator functions, only compare `stringTag` if the serialized value - // legitimately would have been `Function`, and the expected `stringTag` can - // reliably be inferred. - if (this.trustStringTag && generatorsHaveGeneratorTag && this.stringTag !== expected.stringTag) return UNEQUAL - - return SHALLOW_EQUAL - } - - serialize () { - return [this.name, this.trustStringTag, super.serialize()] - } -} diff --git a/node_modules/concordance/lib/complexValues/global.js b/node_modules/concordance/lib/complexValues/global.js deleted file mode 100644 index 6acd66d7a..000000000 --- a/node_modules/concordance/lib/complexValues/global.js +++ /dev/null @@ -1,33 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe () { - return new GlobalValue() -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('GlobalValue') -exports.tag = tag - -class GlobalValue { - compare (expected) { - return this.tag === expected.tag - ? DEEP_EQUAL - : UNEQUAL - } - - formatDeep (theme) { - return lineBuilder.single( - formatUtils.wrap(theme.global, 'Global') + ' ' + theme.object.openBracket + theme.object.closeBracket) - } -} -Object.defineProperty(GlobalValue.prototype, 'isComplex', { value: true }) -Object.defineProperty(GlobalValue.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/complexValues/map.js b/node_modules/concordance/lib/complexValues/map.js deleted file mode 100644 index 7ff13b217..000000000 --- a/node_modules/concordance/lib/complexValues/map.js +++ /dev/null @@ -1,78 +0,0 @@ -'use strict' - -const constants = require('../constants') -const recursorUtils = require('../recursorUtils') -const object = require('./object') - -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - return new DescribedMapValue(Object.assign({ - size: props.value.size - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedMapValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('MapValue') -exports.tag = tag - -class MapValue extends object.ObjectValue { - constructor (props) { - super(props) - this.size = props.size - } - - compare (expected) { - const result = super.compare(expected) - if (result !== SHALLOW_EQUAL) return result - - return this.size === expected.size - ? SHALLOW_EQUAL - : UNEQUAL - } - - prepareDiff (expected) { - // Maps should be compared, even if they have a different number of entries. - return {compareResult: super.compare(expected)} - } - - serialize () { - return [this.size, super.serialize()] - } -} -Object.defineProperty(MapValue.prototype, 'tag', { value: tag }) - -class DescribedMapValue extends object.DescribedMixin(MapValue) { - createIterableRecursor () { - const size = this.size - if (size === 0) return recursorUtils.NOOP_RECURSOR - - let index = 0 - let entries - const next = () => { - if (index === size) return null - - if (!entries) { - entries = Array.from(this.value) - } - - const entry = entries[index++] - return this.describeMapEntry(this.describeAny(entry[0]), this.describeAny(entry[1])) - } - - return { size, next } - } -} - -class DeserializedMapValue extends object.DeserializedMixin(MapValue) { - constructor (state, recursor) { - super(state[1], recursor) - this.size = state[0] - } -} diff --git a/node_modules/concordance/lib/complexValues/object.js b/node_modules/concordance/lib/complexValues/object.js deleted file mode 100644 index 97a59285c..000000000 --- a/node_modules/concordance/lib/complexValues/object.js +++ /dev/null @@ -1,283 +0,0 @@ -'use strict' - -const functionNameSupport = require('function-name-support') - -const constants = require('../constants') -const getObjectKeys = require('../getObjectKeys') -const ObjectFormatter = require('../formatUtils').ObjectFormatter -const hasLength = require('../hasLength') -const recursorUtils = require('../recursorUtils') -const stats = require('../metaDescriptors/stats') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - const isArray = props.stringTag === 'Array' - const object = props.value - return new DescribedObjectValue(Object.assign({ - isArray, - isIterable: object[Symbol.iterator] !== undefined, - isList: isArray || hasLength(object) - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedObjectValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('ObjectValue') -exports.tag = tag - -class ObjectValue { - constructor (props) { - this.ctor = props.ctor - this.pointer = props.pointer - this.stringTag = props.stringTag - - this.isArray = props.isArray === true - this.isIterable = props.isIterable === true - this.isList = props.isList === true - } - - compare (expected) { - if (this.tag !== expected.tag) return UNEQUAL - if (this.stringTag !== expected.stringTag || !this.hasSameCtor(expected)) return UNEQUAL - return SHALLOW_EQUAL - } - - hasSameCtor (expected) { - return this.ctor === expected.ctor - } - - formatShallow (theme, indent) { - return new ObjectFormatter(this, theme, indent) - } - - serialize () { - return [ - this.ctor, this.pointer, this.stringTag, - this.isArray, this.isIterable, this.isList, - functionNameSupport.bitFlags - ] - } -} -Object.defineProperty(ObjectValue.prototype, 'isComplex', { value: true }) -Object.defineProperty(ObjectValue.prototype, 'tag', { value: tag }) -exports.ObjectValue = ObjectValue - -const DescribedObjectValue = DescribedMixin(ObjectValue) -const DeserializedObjectValue = DeserializedMixin(ObjectValue) - -function DescribedMixin (base) { - return class extends base { - constructor (props) { - super(props) - - this.value = props.value - this.describeAny = props.describeAny - this.describeItem = props.describeItem - this.describeMapEntry = props.describeMapEntry - this.describeProperty = props.describeProperty - - this.iterableState = null - this.listState = null - this.propertyState = null - } - - compare (expected) { - return this.value === expected.value - ? DEEP_EQUAL - : super.compare(expected) - } - - createPropertyRecursor () { - const objectKeys = getObjectKeys(this.value, this.isList ? this.value.length : 0) - const size = objectKeys.size - if (size === 0) return recursorUtils.NOOP_RECURSOR - - let index = 0 - const next = () => { - if (index === size) return null - - const key = objectKeys.keys[index++] - return this.describeProperty(key, this.describeAny(this.value[key])) - } - - return { size, next } - } - - createListRecursor () { - if (!this.isList) return recursorUtils.NOOP_RECURSOR - - const size = this.value.length - if (size === 0) return recursorUtils.NOOP_RECURSOR - - let index = 0 - const next = () => { - if (index === size) return null - - const current = index - index++ - return this.describeItem(current, this.describeAny(this.value[current])) - } - - return { size, next } - } - - createIterableRecursor () { - if (this.isArray || !this.isIterable) return recursorUtils.NOOP_RECURSOR - - const iterator = this.value[Symbol.iterator]() - let first = iterator.next() - - let done = false - let size = -1 - if (first.done) { - if (first.value === undefined) { - size = 0 - done = true - } else { - size = 1 - } - } - - let index = 0 - const next = () => { - if (done) return null - - while (!done) { - const current = first || iterator.next() - if (current === first) { - first = null - } - if (current.done) { - done = true - } - - const item = current.value - if (done && item === undefined) return null - - if (this.isList && this.value[index] === item) { - index++ - } else { - return this.describeItem(index++, this.describeAny(item)) - } - } - } - - return { size, next } - } - - createRecursor () { - let recursedProperty = false - let recursedList = false - let recursedIterable = false - - let recursor = null - return () => { - let retval = null - do { - if (recursor !== null) { - retval = recursor.next() - if (retval === null) { - recursor = null - } - } - - while (recursor === null && (!recursedList || !recursedProperty || !recursedIterable)) { - // Prioritize recursing lists - if (!recursedList) { - const replay = recursorUtils.replay(this.listState, () => this.createListRecursor()) - this.listState = replay.state - recursor = replay.recursor - recursedList = true - if (recursor !== recursorUtils.NOOP_RECURSOR) { - retval = stats.describeListRecursor(recursor) - } - } else if (!recursedProperty) { - const replay = recursorUtils.replay(this.propertyState, () => this.createPropertyRecursor()) - this.propertyState = replay.state - recursor = replay.recursor - recursedProperty = true - if (recursor !== recursorUtils.NOOP_RECURSOR) { - retval = stats.describePropertyRecursor(recursor) - } - } else if (!recursedIterable) { - const replay = recursorUtils.replay(this.iterableState, () => this.createIterableRecursor()) - this.iterableState = replay.state - recursor = replay.recursor - recursedIterable = true - if (recursor !== recursorUtils.NOOP_RECURSOR) { - retval = stats.describeIterableRecursor(recursor) - } - } - } - } while (recursor !== null && retval === null) - - return retval - } - } - } -} -exports.DescribedMixin = DescribedMixin - -function DeserializedMixin (base) { - return class extends base { - constructor (state, recursor) { - super({ - ctor: state[0], - pointer: state[1], - stringTag: state[2], - isArray: state[3], - isIterable: state[4], - isList: state[5] - }) - - this.functionNameSupportFlags = state[6] - this.deserializedRecursor = recursor - this.replayState = null - } - - createRecursor () { - if (!this.deserializedRecursor) return () => null - - const replay = recursorUtils.replay(this.replayState, () => ({ size: -1, next: this.deserializedRecursor })) - this.replayState = replay.state - return replay.recursor.next - } - - hasSameCtor (expected) { - if (this.ctor === expected.ctor) return true - - if (this.functionNameSupportFlags === functionNameSupport.bitFlags) { - // The engine used to create the serialization supports the same - // function name inference as the current engine. That said, unless - // the engine has full support for name inference, it's possible that - // names were lost simply due to refactoring. Ctors are not the same - // only if the engine has full support, or if ctors were inferred. - if (functionNameSupport.hasFullSupport === true || (this.ctor !== null && expected.ctor !== null)) return false - } else if (functionNameSupport.isSubsetOf(this.functionNameSupportFlags)) { - // The engine used to create the serialization could infer more function - // names than the current engine. Assume `expected.ctor` comes from the - // current engine and treat the ctors as unequal only if the current - // engine could infer a ctor. - if (expected.ctor !== null) return false - } else { - /* istanbul ignore else */ - if (functionNameSupport.isSupersetOf(this.functionNameSupportFlags)) { - // The engine used to create the serialization could infer fewer - // function names than the current engine. Treat the ctors as unequal - // only if a ctor was in the serialization. - if (this.ctor !== null) return false - } - } - - return true - } - } -} -exports.DeserializedMixin = DeserializedMixin diff --git a/node_modules/concordance/lib/complexValues/promise.js b/node_modules/concordance/lib/complexValues/promise.js deleted file mode 100644 index 823d45386..000000000 --- a/node_modules/concordance/lib/complexValues/promise.js +++ /dev/null @@ -1,40 +0,0 @@ -'use strict' - -const constants = require('../constants') -const object = require('./object') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - return new DescribedPromiseValue(props) -} -exports.describe = describe - -function deserialize (props) { - return new DeserializedPromiseValue(props) -} -exports.deserialize = deserialize - -const tag = Symbol('PromiseValue') -exports.tag = tag - -class PromiseValue extends object.ObjectValue {} -Object.defineProperty(PromiseValue.prototype, 'tag', { value: tag }) - -class DescribedPromiseValue extends object.DescribedMixin(PromiseValue) { - compare (expected) { - // When comparing described promises, require them to be the exact same - // object. - return super.compare(expected) === DEEP_EQUAL - ? DEEP_EQUAL - : UNEQUAL - } -} - -class DeserializedPromiseValue extends object.DeserializedMixin(PromiseValue) { - compare (expected) { - // Deserialized promises can never be compared using object references. - return super.compare(expected) - } -} diff --git a/node_modules/concordance/lib/complexValues/regexp.js b/node_modules/concordance/lib/complexValues/regexp.js deleted file mode 100644 index 1c66a2fd8..000000000 --- a/node_modules/concordance/lib/complexValues/regexp.js +++ /dev/null @@ -1,90 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') -const object = require('./object') - -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - const regexp = props.value - return new DescribedRegexpValue(Object.assign({ - flags: getSortedFlags(regexp), - source: regexp.source - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedRegexpValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('RegexpValue') -exports.tag = tag - -function getSortedFlags (regexp) { - const flags = regexp.flags || String(regexp).slice(regexp.source.length + 2) - return flags.split('').sort().join('') -} - -class RegexpValue extends object.ObjectValue { - constructor (props) { - super(props) - this.flags = props.flags - this.source = props.source - } - - compare (expected) { - return this.tag === expected.tag && this.flags === expected.flags && this.source === expected.source - ? super.compare(expected) - : UNEQUAL - } - - formatShallow (theme, indent) { - const ctor = this.ctor || this.stringTag - const regexp = formatUtils.wrap(theme.regexp.source, this.source) + formatUtils.wrap(theme.regexp.flags, this.flags) - - return super.formatShallow(theme, indent).customize({ - finalize: innerLines => { - if (ctor === 'RegExp' && innerLines.isEmpty) return lineBuilder.single(regexp) - - const innerIndentation = indent.increase() - const header = lineBuilder.first(formatUtils.formatCtorAndStringTag(theme, this) + ' ' + theme.object.openBracket) - .concat(lineBuilder.line(innerIndentation + regexp)) - - if (!innerLines.isEmpty) { - header.append(lineBuilder.line(innerIndentation + theme.regexp.separator)) - header.append(innerLines.withFirstPrefixed(innerIndentation).stripFlags()) - } - - return header.append(lineBuilder.last(indent + theme.object.closeBracket)) - }, - - maxDepth: () => { - return lineBuilder.single( - formatUtils.formatCtorAndStringTag(theme, this) + ' ' + - theme.object.openBracket + ' ' + - regexp + ' ' + - theme.maxDepth + ' ' + - theme.object.closeBracket) - } - }) - } - - serialize () { - return [this.flags, this.source, super.serialize()] - } -} -Object.defineProperty(RegexpValue.prototype, 'tag', { value: tag }) - -const DescribedRegexpValue = object.DescribedMixin(RegexpValue) - -class DeserializedRegexpValue extends object.DeserializedMixin(RegexpValue) { - constructor (state, recursor) { - super(state[2], recursor) - this.flags = state[0] - this.source = state[1] - } -} diff --git a/node_modules/concordance/lib/complexValues/set.js b/node_modules/concordance/lib/complexValues/set.js deleted file mode 100644 index fc3623ace..000000000 --- a/node_modules/concordance/lib/complexValues/set.js +++ /dev/null @@ -1,78 +0,0 @@ -'use strict' - -const constants = require('../constants') -const recursorUtils = require('../recursorUtils') -const object = require('./object') - -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (props) { - return new DescribedSetValue(Object.assign({ - size: props.value.size - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedSetValue(state, recursor) -} -exports.deserialize = deserialize - -const tag = Symbol('SetValue') -exports.tag = tag - -class SetValue extends object.ObjectValue { - constructor (props) { - super(props) - this.size = props.size - } - - compare (expected) { - const result = super.compare(expected) - if (result !== SHALLOW_EQUAL) return result - - return this.size === expected.size - ? SHALLOW_EQUAL - : UNEQUAL - } - - prepareDiff (expected) { - // Sets should be compared, even if they have a different number of items. - return {compareResult: super.compare(expected)} - } - - serialize () { - return [this.size, super.serialize()] - } -} -Object.defineProperty(SetValue.prototype, 'tag', { value: tag }) - -class DescribedSetValue extends object.DescribedMixin(SetValue) { - createIterableRecursor () { - const size = this.size - if (size === 0) return recursorUtils.NOOP_RECURSOR - - let index = 0 - let members - const next = () => { - if (index === size) return null - - if (!members) { - members = Array.from(this.value) - } - - const value = members[index] - return this.describeItem(index++, this.describeAny(value)) - } - - return { size, next } - } -} - -class DeserializedSetValue extends object.DeserializedMixin(SetValue) { - constructor (state, recursor) { - super(state[1], recursor) - this.size = state[0] - } -} diff --git a/node_modules/concordance/lib/complexValues/typedArray.js b/node_modules/concordance/lib/complexValues/typedArray.js deleted file mode 100644 index 5c482ff1f..000000000 --- a/node_modules/concordance/lib/complexValues/typedArray.js +++ /dev/null @@ -1,162 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') -const recursorUtils = require('../recursorUtils') -const propertyStatsTag = require('../metaDescriptors/stats').propertyTag -const object = require('./object') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function getBuffer (value) { - // Assume at least Node.js 4.5.0, which introduces Buffer.from() - const buffer = Buffer.from(value.buffer) - return value.byteLength !== value.buffer.byteLength - ? buffer.slice(value.byteOffset, value.byteOffset + value.byteLength) - : buffer -} -exports.getBuffer = getBuffer - -function describe (props) { - return new DescribedTypedArrayValue(Object.assign({ - buffer: getBuffer(props.value), - // Set isArray and isList so the property recursor excludes the byte accessors - isArray: true, - isList: true - }, props)) -} -exports.describe = describe - -function deserialize (state, recursor) { - return new DeserializedTypedArrayValue(state, recursor) -} -exports.deserialize = deserialize - -function deserializeBytes (buffer) { - return new Bytes(buffer) -} -exports.deserializeBytes = deserializeBytes - -const bytesTag = Symbol('Bytes') -exports.bytesTag = bytesTag - -const tag = Symbol('TypedArrayValue') -exports.tag = tag - -class Bytes { - constructor (buffer) { - this.buffer = buffer - } - - compare (expected) { - return expected.tag === bytesTag && this.buffer.equals(expected.buffer) - ? DEEP_EQUAL - : UNEQUAL - } - - formatDeep (theme, indent) { - const indentation = indent - const lines = lineBuilder.buffer() - - // Display 4-byte words, 8 per line - let string = '' - let isFirst = true - for (let offset = 0; offset < this.buffer.length; offset += 4) { - if (offset > 0) { - if (offset % 32 === 0) { - if (isFirst) { - lines.append(lineBuilder.first(string)) - isFirst = false - } else { - lines.append(lineBuilder.line(string)) - } - string = String(indentation) - } else { - string += ' ' - } - } - string += formatUtils.wrap(theme.typedArray.bytes, this.buffer.toString('hex', offset, offset + 4)) - } - - return isFirst - ? lineBuilder.single(string) - : lines.append(lineBuilder.last(string)) - } - - serialize () { - return this.buffer - } -} -Object.defineProperty(Bytes.prototype, 'tag', { value: bytesTag }) - -class TypedArrayValue extends object.ObjectValue { - constructor (props) { - super(props) - this.buffer = props.buffer - } - - formatShallow (theme, indent) { - return super.formatShallow(theme, indent).customize({ - shouldFormat (subject) { - if (subject.tag === propertyStatsTag) return subject.size > 1 - if (subject.isProperty === true) return subject.key.value !== 'byteLength' - if (subject.tag === bytesTag) return subject.buffer.byteLength > 0 - return true - } - }) - } -} -Object.defineProperty(TypedArrayValue.prototype, 'tag', { value: tag }) -exports.TypedArrayValue = TypedArrayValue - -function DescribedMixin (base) { - return class extends object.DescribedMixin(base) { - // The list isn't recursed. Instead a Bytes instance is returned by the main - // recursor. - createListRecursor () { - return recursorUtils.NOOP_RECURSOR - } - - createPropertyRecursor () { - const recursor = super.createPropertyRecursor() - const size = recursor.size + 1 - - let done = false - const next = () => { - if (done) return null - - const property = recursor.next() - if (property) return property - - done = true - return this.describeProperty('byteLength', this.describeAny(this.buffer.byteLength)) - } - - return { size, next } - } - - createRecursor () { - return recursorUtils.unshift(super.createRecursor(), new Bytes(this.buffer)) - } - } -} -exports.DescribedMixin = DescribedMixin - -const DescribedTypedArrayValue = DescribedMixin(TypedArrayValue) - -function DeserializedMixin (base) { - return class extends object.DeserializedMixin(base) { - constructor (state, recursor) { - super(state, recursor) - - // Get the Bytes descriptor from the recursor. It contains the buffer. - const bytesDescriptor = this.createRecursor()() - this.buffer = bytesDescriptor.buffer - } - } -} -exports.DeserializedMixin = DeserializedMixin - -const DeserializedTypedArrayValue = DeserializedMixin(TypedArrayValue) diff --git a/node_modules/concordance/lib/constants.js b/node_modules/concordance/lib/constants.js deleted file mode 100644 index f85235faa..000000000 --- a/node_modules/concordance/lib/constants.js +++ /dev/null @@ -1,13 +0,0 @@ -'use strict' - -const AMBIGUOUS = Symbol('AMBIGUOUS') -const DEEP_EQUAL = Symbol('DEEP_EQUAL') -const SHALLOW_EQUAL = Symbol('SHALLOW_EQUAL') -const UNEQUAL = Symbol('UNEQUAL') - -module.exports = { - AMBIGUOUS, - DEEP_EQUAL, - SHALLOW_EQUAL, - UNEQUAL -} diff --git a/node_modules/concordance/lib/describe.js b/node_modules/concordance/lib/describe.js deleted file mode 100644 index a8aa94572..000000000 --- a/node_modules/concordance/lib/describe.js +++ /dev/null @@ -1,170 +0,0 @@ -'use strict' - -const argumentsValue = require('./complexValues/arguments') -const arrayBufferValue = require('./complexValues/arrayBuffer') -const boxedValue = require('./complexValues/boxed') -const dataViewValue = require('./complexValues/dataView') -const dateValue = require('./complexValues/date') -const errorValue = require('./complexValues/error') -const functionValue = require('./complexValues/function') -const globalValue = require('./complexValues/global') -const mapValue = require('./complexValues/map') -const objectValue = require('./complexValues/object') -const promiseValue = require('./complexValues/promise') -const regexpValue = require('./complexValues/regexp') -const setValue = require('./complexValues/set') -const typedArrayValue = require('./complexValues/typedArray') - -const itemDescriptor = require('./metaDescriptors/item') -const mapEntryDescriptor = require('./metaDescriptors/mapEntry') -const propertyDescriptor = require('./metaDescriptors/property') - -const booleanValue = require('./primitiveValues/boolean') -const nullValue = require('./primitiveValues/null') -const numberValue = require('./primitiveValues/number') -const stringValue = require('./primitiveValues/string') -const symbolValue = require('./primitiveValues/symbol') -const undefinedValue = require('./primitiveValues/undefined') - -const getCtor = require('./getCtor') -const getStringTag = require('./getStringTag') -const pluginRegistry = require('./pluginRegistry') -const Registry = require('./Registry') - -const SpecializedComplexes = new Map([ - ['Arguments', argumentsValue.describe], - ['ArrayBuffer', arrayBufferValue.describe], - ['DataView', dataViewValue.describe], - ['Date', dateValue.describe], - ['Error', errorValue.describe], - ['Float32Array', typedArrayValue.describe], - ['Float64Array', typedArrayValue.describe], - ['Function', functionValue.describe], - ['GeneratorFunction', functionValue.describe], - ['global', globalValue.describe], - ['Int16Array', typedArrayValue.describe], - ['Int32Array', typedArrayValue.describe], - ['Int8Array', typedArrayValue.describe], - ['Map', mapValue.describe], - ['Promise', promiseValue.describe], - ['RegExp', regexpValue.describe], - ['Set', setValue.describe], - ['Uint16Array', typedArrayValue.describe], - ['Uint32Array', typedArrayValue.describe], - ['Uint8Array', typedArrayValue.describe], - ['Uint8ClampedArray', typedArrayValue.describe] -]) - -function describePrimitive (value) { - if (value === null) return nullValue.describe() - if (value === undefined) return undefinedValue.describe() - if (value === true || value === false) return booleanValue.describe(value) - - const type = typeof value - if (type === 'number') return numberValue.describe(value) - if (type === 'string') return stringValue.describe(value) - if (type === 'symbol') return symbolValue.describe(value) - - return null -} - -function unboxComplex (tag, complex) { - // Try to unbox by calling `valueOf()`. `describePrimitive()` will return - // `null` if the resulting value is not a primitive, in which case it's - // ignored. - if (typeof complex.valueOf === 'function') { - const value = complex.valueOf() - if (value !== complex) return describePrimitive(value) - } - - return null -} - -function registerPlugins (plugins) { - if (!Array.isArray(plugins) || plugins.length === 0) return () => null - - const tryFns = pluginRegistry.getTryDescribeValues(plugins) - return (value, stringTag, ctor) => { - for (const tryDescribeValue of tryFns) { - const describeValue = tryDescribeValue(value, stringTag, ctor) - if (describeValue) return describeValue - } - - return null - } -} - -function describeComplex (value, registry, tryPlugins, describeAny, describeItem, describeMapEntry, describeProperty) { - if (registry.has(value)) return registry.get(value) - - const stringTag = getStringTag(value) - const ctor = getCtor(stringTag, value) - const pointer = registry.alloc(value) - - let unboxed - let describeValue = tryPlugins(value, stringTag, ctor) - if (describeValue === null) { - if (SpecializedComplexes.has(stringTag)) { - describeValue = SpecializedComplexes.get(stringTag) - } else { - unboxed = unboxComplex(stringTag, value) - if (unboxed !== null) { - describeValue = boxedValue.describe - } else { - describeValue = objectValue.describe - } - } - } - - const descriptor = describeValue({ - ctor, - describeAny, - describeItem, - describeMapEntry, - describeProperty, - pointer: pointer.index, - stringTag, - unboxed, - value - }) - pointer.descriptor = descriptor - return descriptor -} - -function describe (value, options) { - const primitive = describePrimitive(value) - if (primitive !== null) return primitive - - const registry = new Registry() - const tryPlugins = registerPlugins(options && options.plugins) - const curriedComplex = c => { - return describeComplex(c, registry, tryPlugins, describeAny, describeItem, describeMapEntry, describeProperty) - } - - const describeAny = any => { - const descriptor = describePrimitive(any) - return descriptor !== null - ? descriptor - : curriedComplex(any) - } - - const describeItem = (index, valueDescriptor) => { - return valueDescriptor.isPrimitive === true - ? itemDescriptor.describePrimitive(index, valueDescriptor) - : itemDescriptor.describeComplex(index, valueDescriptor) - } - - const describeMapEntry = (keyDescriptor, valueDescriptor) => { - return mapEntryDescriptor.describe(keyDescriptor, valueDescriptor) - } - - const describeProperty = (key, valueDescriptor) => { - const keyDescriptor = describePrimitive(key) - return valueDescriptor.isPrimitive === true - ? propertyDescriptor.describePrimitive(keyDescriptor, valueDescriptor) - : propertyDescriptor.describeComplex(keyDescriptor, valueDescriptor) - } - - return curriedComplex(value) -} -module.exports = describe diff --git a/node_modules/concordance/lib/diff.js b/node_modules/concordance/lib/diff.js deleted file mode 100644 index 16191143f..000000000 --- a/node_modules/concordance/lib/diff.js +++ /dev/null @@ -1,391 +0,0 @@ -'use strict' - -const constants = require('./constants') -const describe = require('./describe') -const lineBuilder = require('./lineBuilder') -const recursorUtils = require('./recursorUtils') -const shouldCompareDeep = require('./shouldCompareDeep') -const symbolProperties = require('./symbolProperties') -const themeUtils = require('./themeUtils') -const Circular = require('./Circular') -const Indenter = require('./Indenter') - -const AMBIGUOUS = constants.AMBIGUOUS -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL -const NOOP = Symbol('NOOP') - -const alwaysFormat = () => true - -function compareComplexShape (lhs, rhs) { - let result = lhs.compare(rhs) - if (result === DEEP_EQUAL) return DEEP_EQUAL - if (result === UNEQUAL || !shouldCompareDeep(result, lhs, rhs)) return UNEQUAL - - let collectedSymbolProperties = false - let lhsRecursor = lhs.createRecursor() - let rhsRecursor = rhs.createRecursor() - - do { - lhs = lhsRecursor() - rhs = rhsRecursor() - - if (lhs === null && rhs === null) return SHALLOW_EQUAL - if (lhs === null || rhs === null) return UNEQUAL - - result = lhs.compare(rhs) - if (result === UNEQUAL) return UNEQUAL - if ( - result === AMBIGUOUS && - lhs.isProperty === true && !collectedSymbolProperties && - shouldCompareDeep(result, lhs, rhs) - ) { - collectedSymbolProperties = true - const lhsCollector = new symbolProperties.Collector(lhs, lhsRecursor) - const rhsCollector = new symbolProperties.Collector(rhs, rhsRecursor) - - lhsRecursor = recursorUtils.sequence( - lhsCollector.createRecursor(), - recursorUtils.unshift(lhsRecursor, lhsCollector.collectAll())) - rhsRecursor = recursorUtils.sequence( - rhsCollector.createRecursor(), - recursorUtils.unshift(rhsRecursor, rhsCollector.collectAll())) - } - } while (true) -} - -function diffDescriptors (lhs, rhs, options) { - const theme = themeUtils.normalize(options) - const invert = options ? options.invert === true : false - - const lhsCircular = new Circular() - const rhsCircular = new Circular() - const maxDepth = (options && options.maxDepth) || 0 - - let indent = new Indenter(0, ' ') - - const lhsStack = [] - const rhsStack = [] - let topIndex = -1 - - const buffer = lineBuilder.buffer() - const diffStack = [] - let diffIndex = -1 - - const isCircular = descriptor => lhsCircular.has(descriptor) || rhsCircular.has(descriptor) - - const format = (builder, subject, circular) => { - if (diffIndex >= 0 && !diffStack[diffIndex].shouldFormat(subject)) return - - if (circular.has(subject)) { - diffStack[diffIndex].formatter.append(builder.single(theme.circular)) - return - } - - const formatStack = [] - let formatIndex = -1 - - do { - if (circular.has(subject)) { - formatStack[formatIndex].formatter.append(builder.single(theme.circular), subject) - } else { - let didFormat = false - if (typeof subject.formatDeep === 'function') { - let formatted = subject.formatDeep(themeUtils.applyModifiers(subject, theme), indent) - if (formatted !== null) { - didFormat = true - - if (formatIndex === -1) { - formatted = builder.setDefaultGutter(formatted) - if (diffIndex === -1) { - buffer.append(formatted) - } else { - diffStack[diffIndex].formatter.append(formatted, subject) - } - } else { - formatStack[formatIndex].formatter.append(formatted, subject) - } - } - } - - if (!didFormat && typeof subject.formatShallow === 'function') { - const formatter = subject.formatShallow(themeUtils.applyModifiers(subject, theme), indent) - const recursor = subject.createRecursor() - - if (formatter.increaseIndent && maxDepth > 0 && indent.level === maxDepth) { - const isEmpty = recursor() === null - let formatted = !isEmpty && typeof formatter.maxDepth === 'function' - ? formatter.maxDepth() - : formatter.finalize() - - if (formatIndex === -1) { - formatted = builder.setDefaultGutter(formatted) - diffStack[diffIndex].formatter.append(formatted, subject) - } else { - formatStack[formatIndex].formatter.append(formatted, subject) - } - } else { - formatStack.push({ - formatter, - recursor, - decreaseIndent: formatter.increaseIndent, - shouldFormat: formatter.shouldFormat || alwaysFormat, - subject - }) - formatIndex++ - - if (formatter.increaseIndent) indent = indent.increase() - circular.add(subject) - } - } - } - - while (formatIndex >= 0) { - do { - subject = formatStack[formatIndex].recursor() - } while (subject && !formatStack[formatIndex].shouldFormat(subject)) - - if (subject) { - break - } - - const record = formatStack.pop() - formatIndex-- - if (record.decreaseIndent) indent = indent.decrease() - circular.delete(record.subject) - - let formatted = record.formatter.finalize() - if (formatIndex === -1) { - formatted = builder.setDefaultGutter(formatted) - if (diffIndex === -1) { - buffer.append(formatted) - } else { - diffStack[diffIndex].formatter.append(formatted, record.subject) - } - } else { - formatStack[formatIndex].formatter.append(formatted, record.subject) - } - } - } while (formatIndex >= 0) - } - - do { - let compareResult = NOOP - if (lhsCircular.has(lhs)) { - compareResult = lhsCircular.get(lhs) === rhsCircular.get(rhs) - ? DEEP_EQUAL - : UNEQUAL - } else if (rhsCircular.has(rhs)) { - compareResult = UNEQUAL - } - - let firstPassSymbolProperty = false - if (lhs.isProperty === true) { - compareResult = lhs.compare(rhs) - if (compareResult === AMBIGUOUS) { - const parent = lhsStack[topIndex].subject - firstPassSymbolProperty = parent.isSymbolPropertiesCollector !== true && parent.isSymbolPropertiesComparable !== true - } - } - - let didFormat = false - let mustRecurse = false - if (compareResult !== DEEP_EQUAL && !firstPassSymbolProperty && typeof lhs.prepareDiff === 'function') { - const lhsRecursor = topIndex === -1 ? null : lhsStack[topIndex].recursor - const rhsRecursor = topIndex === -1 ? null : rhsStack[topIndex].recursor - - const instructions = lhs.prepareDiff( - rhs, - lhsRecursor, - rhsRecursor, - compareComplexShape, - isCircular) - - if (instructions !== null) { - if (topIndex >= 0) { - if (typeof instructions.lhsRecursor === 'function') { - lhsStack[topIndex].recursor = instructions.lhsRecursor - } - if (typeof instructions.rhsRecursor === 'function') { - rhsStack[topIndex].recursor = instructions.rhsRecursor - } - } - - if (instructions.compareResult) { - compareResult = instructions.compareResult - } - if (instructions.mustRecurse === true) { - mustRecurse = true - } else { - if (instructions.actualIsExtraneous === true) { - format(lineBuilder.actual, lhs, lhsCircular) - didFormat = true - } else if (instructions.multipleAreExtraneous === true) { - for (const extraneous of instructions.descriptors) { - format(lineBuilder.actual, extraneous, lhsCircular) - } - didFormat = true - } else if (instructions.expectedIsMissing === true) { - format(lineBuilder.expected, rhs, rhsCircular) - didFormat = true - } else if (instructions.multipleAreMissing === true) { - for (const missing of instructions.descriptors) { - format(lineBuilder.expected, missing, rhsCircular) - } - didFormat = true - } else if (instructions.isUnequal === true) { - format(lineBuilder.actual, lhs, lhsCircular) - format(lineBuilder.expected, rhs, rhsCircular) - didFormat = true - } else if (!instructions.compareResult) { - // TODO: Throw a useful, custom error - throw new Error('Illegal result of prepareDiff()') - } - } - } - } - - if (!didFormat) { - if (compareResult === NOOP) { - compareResult = lhs.compare(rhs) - } - - if (!mustRecurse) { - mustRecurse = shouldCompareDeep(compareResult, lhs, rhs) - } - - if (compareResult === DEEP_EQUAL) { - format(lineBuilder, lhs, lhsCircular) - } else if (mustRecurse) { - if (compareResult === AMBIGUOUS && lhs.isProperty === true) { - // Replace both sides by a pseudo-descriptor which collects symbol - // properties instead. - lhs = new symbolProperties.Collector(lhs, lhsStack[topIndex].recursor) - rhs = new symbolProperties.Collector(rhs, rhsStack[topIndex].recursor) - // Replace the current recursors so they can continue correctly after - // the collectors have been "compared". This is necessary since the - // collectors eat the first value after the last symbol property. - lhsStack[topIndex].recursor = recursorUtils.unshift(lhsStack[topIndex].recursor, lhs.collectAll()) - rhsStack[topIndex].recursor = recursorUtils.unshift(rhsStack[topIndex].recursor, rhs.collectAll()) - } - - if (typeof lhs.diffShallow === 'function') { - const formatter = lhs.diffShallow(rhs, themeUtils.applyModifiers(lhs, theme), indent) - diffStack.push({ - formatter, - origin: lhs, - decreaseIndent: formatter.increaseIndent, - exceedsMaxDepth: formatter.increaseIndent && maxDepth > 0 && indent.level >= maxDepth, - shouldFormat: formatter.shouldFormat || alwaysFormat - }) - diffIndex++ - - if (formatter.increaseIndent) indent = indent.increase() - } else if (typeof lhs.formatShallow === 'function') { - const formatter = lhs.formatShallow(themeUtils.applyModifiers(lhs, theme), indent) - diffStack.push({ - formatter, - decreaseIndent: formatter.increaseIndent, - exceedsMaxDepth: formatter.increaseIndent && maxDepth > 0 && indent.level >= maxDepth, - shouldFormat: formatter.shouldFormat || alwaysFormat, - subject: lhs - }) - diffIndex++ - - if (formatter.increaseIndent) indent = indent.increase() - } - - lhsCircular.add(lhs) - rhsCircular.add(rhs) - - lhsStack.push({ diffIndex, subject: lhs, recursor: lhs.createRecursor() }) - rhsStack.push({ diffIndex, subject: rhs, recursor: rhs.createRecursor() }) - topIndex++ - } else { - const diffed = typeof lhs.diffDeep === 'function' - ? lhs.diffDeep(rhs, themeUtils.applyModifiers(lhs, theme), indent) - : null - - if (diffed === null) { - format(lineBuilder.actual, lhs, lhsCircular) - format(lineBuilder.expected, rhs, rhsCircular) - } else { - if (diffIndex === -1) { - buffer.append(diffed) - } else { - diffStack[diffIndex].formatter.append(diffed, lhs) - } - } - } - } - - while (topIndex >= 0) { - lhs = lhsStack[topIndex].recursor() - rhs = rhsStack[topIndex].recursor() - - if (lhs !== null && rhs !== null) { - break - } - - if (lhs === null && rhs === null) { - const lhsRecord = lhsStack.pop() - const rhsRecord = rhsStack.pop() - lhsCircular.delete(lhsRecord.subject) - rhsCircular.delete(rhsRecord.subject) - topIndex-- - - if (lhsRecord.diffIndex === diffIndex) { - const record = diffStack.pop() - diffIndex-- - if (record.decreaseIndent) indent = indent.decrease() - - let formatted = record.formatter.finalize() - if (record.exceedsMaxDepth && !formatted.hasGutter) { - // The record exceeds the max depth, but contains no actual diff. - // Discard the potentially deep formatting and format just the - // original subject. - const subject = lhsRecord.subject - const formatter = subject.formatShallow(themeUtils.applyModifiers(subject, theme), indent) - const isEmpty = subject.createRecursor()() === null - formatted = !isEmpty && typeof formatter.maxDepth === 'function' - ? formatter.maxDepth() - : formatter.finalize() - } - - if (diffIndex === -1) { - buffer.append(formatted) - } else { - diffStack[diffIndex].formatter.append(formatted, record.subject) - } - } - } else { - let builder, circular, stack, subject - if (lhs === null) { - builder = lineBuilder.expected - circular = rhsCircular - stack = rhsStack - subject = rhs - } else { - builder = lineBuilder.actual - circular = lhsCircular - stack = lhsStack - subject = lhs - } - - do { - format(builder, subject, circular) - subject = stack[topIndex].recursor() - } while (subject !== null) - } - } - } while (topIndex >= 0) - - return buffer.toString({diff: true, invert, theme}) -} -exports.diffDescriptors = diffDescriptors - -function diff (actual, expected, options) { - return diffDescriptors(describe(actual, options), describe(expected, options), options) -} -exports.diff = diff diff --git a/node_modules/concordance/lib/encoder.js b/node_modules/concordance/lib/encoder.js deleted file mode 100644 index ea1be3855..000000000 --- a/node_modules/concordance/lib/encoder.js +++ /dev/null @@ -1,293 +0,0 @@ -'use strict' - -const flattenDeep = require('lodash.flattendeep') - -// Indexes are hexadecimal to make reading the binary output easier. -const valueTypes = { - zero: 0x00, - int8: 0x01, // Note that the hex value equals the number of bytes required - int16: 0x02, // to store the integer. - int24: 0x03, - int32: 0x04, - int40: 0x05, - int48: 0x06, - // Leave room for int56 and int64 - numberString: 0x09, - negativeZero: 0x0A, - notANumber: 0x0B, - infinity: 0x0C, - negativeInfinity: 0x0D, - undefined: 0x0E, - null: 0x0F, - true: 0x10, - false: 0x11, - utf8: 0x12, - bytes: 0x13, - list: 0x14, - descriptor: 0x15 -} - -const descriptorSymbol = Symbol('descriptor') -exports.descriptorSymbol = descriptorSymbol - -function encodeInteger (type, value) { - const encoded = Buffer.alloc(type) - encoded.writeIntLE(value, 0, type) - return [type, encoded] -} - -function encodeValue (value) { - if (Object.is(value, 0)) return valueTypes.zero - if (Object.is(value, -0)) return valueTypes.negativeZero - if (Object.is(value, NaN)) return valueTypes.notANumber - if (value === Infinity) return valueTypes.infinity - if (value === -Infinity) return valueTypes.negativeInfinity - if (value === undefined) return valueTypes.undefined - if (value === null) return valueTypes.null - if (value === true) return valueTypes.true - if (value === false) return valueTypes.false - - const type = typeof value - if (type === 'number') { - if (Number.isInteger(value)) { - // The integer types are signed, so int8 can only store 7 bits, int16 - // only 15, etc. - if (value >= -0x80 && value < 0x80) return encodeInteger(valueTypes.int8, value) - if (value >= -0x8000 && value < 0x8000) return encodeInteger(valueTypes.int16, value) - if (value >= -0x800000 && value < 0x800000) return encodeInteger(valueTypes.int24, value) - if (value >= -0x80000000 && value < 0x80000000) return encodeInteger(valueTypes.int32, value) - if (value >= -0x8000000000 && value < 0x8000000000) return encodeInteger(valueTypes.int40, value) - if (value >= -0x800000000000 && value < 0x800000000000) return encodeInteger(valueTypes.int48, value) - // Fall through to encoding the value as a number string. - } - - const encoded = Buffer.from(String(value), 'utf8') - return [valueTypes.numberString, encodeValue(encoded.length), encoded] - } - - if (type === 'string') { - const encoded = Buffer.from(value, 'utf8') - return [valueTypes.utf8, encodeValue(encoded.length), encoded] - } - - if (Buffer.isBuffer(value)) { - return [valueTypes.bytes, encodeValue(value.byteLength), value] - } - - if (Array.isArray(value)) { - return [ - value[descriptorSymbol] === true ? valueTypes.descriptor : valueTypes.list, - encodeValue(value.length), - value.map(encodeValue) - ] - } - - const hex = `0x${type.toString(16).toUpperCase()}` - throw new TypeError(`Unexpected value with type ${hex}`) -} - -function decodeValue (buffer, byteOffset) { - const type = buffer.readUInt8(byteOffset) - byteOffset += 1 - - if (type === valueTypes.zero) return { byteOffset, value: 0 } - if (type === valueTypes.negativeZero) return { byteOffset, value: -0 } - if (type === valueTypes.notANumber) return { byteOffset, value: NaN } - if (type === valueTypes.infinity) return { byteOffset, value: Infinity } - if (type === valueTypes.negativeInfinity) return { byteOffset, value: -Infinity } - if (type === valueTypes.undefined) return { byteOffset, value: undefined } - if (type === valueTypes.null) return { byteOffset, value: null } - if (type === valueTypes.true) return { byteOffset, value: true } - if (type === valueTypes.false) return { byteOffset, value: false } - - if ( - type === valueTypes.int8 || type === valueTypes.int16 || type === valueTypes.int24 || - type === valueTypes.int32 || type === valueTypes.int40 || type === valueTypes.int48 - ) { - const value = buffer.readIntLE(byteOffset, type) - byteOffset += type - return { byteOffset, value } - } - - if (type === valueTypes.numberString || type === valueTypes.utf8 || type === valueTypes.bytes) { - const length = decodeValue(buffer, byteOffset) - const start = length.byteOffset - const end = start + length.value - - if (type === valueTypes.numberString) { - const value = Number(buffer.toString('utf8', start, end)) - return { byteOffset: end, value } - } - - if (type === valueTypes.utf8) { - const value = buffer.toString('utf8', start, end) - return { byteOffset: end, value } - } - - const value = buffer.slice(start, end) - return { byteOffset: end, value } - } - - if (type === valueTypes.list || type === valueTypes.descriptor) { - const length = decodeValue(buffer, byteOffset) - byteOffset = length.byteOffset - - const value = new Array(length.value) - if (type === valueTypes.descriptor) { - value[descriptorSymbol] = true - } - - for (let index = 0; index < length.value; index++) { - const item = decodeValue(buffer, byteOffset) - byteOffset = item.byteOffset - value[index] = item.value - } - - return { byteOffset, value } - } - - const hex = `0x${type.toString(16).toUpperCase()}` - throw new TypeError(`Could not decode type ${hex}`) -} - -function buildBuffer (numberOrArray) { - if (typeof numberOrArray === 'number') { - const byte = Buffer.alloc(1) - byte.writeUInt8(numberOrArray) - return byte - } - - const array = flattenDeep(numberOrArray) - const buffers = new Array(array.length) - let byteLength = 0 - for (let index = 0; index < array.length; index++) { - if (typeof array[index] === 'number') { - byteLength += 1 - const byte = Buffer.alloc(1) - byte.writeUInt8(array[index]) - buffers[index] = byte - } else { - byteLength += array[index].byteLength - buffers[index] = array[index] - } - } - return Buffer.concat(buffers, byteLength) -} - -function encode (serializerVersion, rootRecord, usedPlugins) { - const buffers = [] - let byteOffset = 0 - - const versionHeader = Buffer.alloc(2) - versionHeader.writeUInt16LE(serializerVersion) - buffers.push(versionHeader) - byteOffset += versionHeader.byteLength - - const rootOffset = Buffer.alloc(4) - buffers.push(rootOffset) - byteOffset += rootOffset.byteLength - - const numPlugins = buildBuffer(encodeValue(usedPlugins.size)) - buffers.push(numPlugins) - byteOffset += numPlugins.byteLength - - for (const name of usedPlugins.keys()) { - const plugin = usedPlugins.get(name) - const record = buildBuffer([ - encodeValue(name), - encodeValue(plugin.serializerVersion) - ]) - buffers.push(record) - byteOffset += record.byteLength - } - - const queue = [rootRecord] - const pointers = [rootOffset] - while (queue.length > 0) { - pointers.shift().writeUInt32LE(byteOffset, 0) - - const record = queue.shift() - const recordHeader = buildBuffer([ - encodeValue(record.pluginIndex), - encodeValue(record.id), - encodeValue(record.children.length) - ]) - buffers.push(recordHeader) - byteOffset += recordHeader.byteLength - - // Add pointers before encoding the state. This allows, if it ever becomes - // necessary, for records to be extracted from a buffer without having to - // parse the (variable length) state field. - for (const child of record.children) { - queue.push(child) - - const pointer = Buffer.alloc(4) - pointers.push(pointer) - buffers.push(pointer) - byteOffset += 4 - } - - const state = buildBuffer(encodeValue(record.state)) - buffers.push(state) - byteOffset += state.byteLength - } - - return Buffer.concat(buffers, byteOffset) -} -exports.encode = encode - -function decodePlugins (buffer) { - const $numPlugins = decodeValue(buffer, 0) - let byteOffset = $numPlugins.byteOffset - - const usedPlugins = new Map() - const lastIndex = $numPlugins.value - for (let index = 1; index <= lastIndex; index++) { - const $name = decodeValue(buffer, byteOffset) - const name = $name.value - byteOffset = $name.byteOffset - - const serializerVersion = decodeValue(buffer, byteOffset).value - usedPlugins.set(index, {name, serializerVersion}) - } - - return usedPlugins -} -exports.decodePlugins = decodePlugins - -function decodeRecord (buffer, byteOffset) { - const $pluginIndex = decodeValue(buffer, byteOffset) - const pluginIndex = $pluginIndex.value - byteOffset = $pluginIndex.byteOffset - - const $id = decodeValue(buffer, byteOffset) - const id = $id.value - byteOffset = $id.byteOffset - - const $numPointers = decodeValue(buffer, byteOffset) - const numPointers = $numPointers.value - byteOffset = $numPointers.byteOffset - - const pointerAddresses = new Array(numPointers) - for (let index = 0; index < numPointers; index++) { - pointerAddresses[index] = buffer.readUInt32LE(byteOffset) - byteOffset += 4 - } - - const state = decodeValue(buffer, byteOffset).value - return {id, pluginIndex, state, pointerAddresses} -} -exports.decodeRecord = decodeRecord - -function extractVersion (buffer) { - return buffer.readUInt16LE(0) -} -exports.extractVersion = extractVersion - -function decode (buffer) { - const rootOffset = buffer.readUInt32LE(2) - const pluginBuffer = buffer.slice(6, rootOffset) - const rootRecord = decodeRecord(buffer, rootOffset) - return {pluginBuffer, rootRecord} -} -exports.decode = decode diff --git a/node_modules/concordance/lib/format.js b/node_modules/concordance/lib/format.js deleted file mode 100644 index 7629579d7..000000000 --- a/node_modules/concordance/lib/format.js +++ /dev/null @@ -1,101 +0,0 @@ -'use strict' - -const describe = require('./describe') -const lineBuilder = require('./lineBuilder') -const themeUtils = require('./themeUtils') -const Circular = require('./Circular') -const Indenter = require('./Indenter') - -const alwaysFormat = () => true -const fixedIndent = new Indenter(0, ' ') - -function formatDescriptor (subject, options) { - const theme = themeUtils.normalize(options) - if (subject.isPrimitive === true) { - const formatted = subject.formatDeep(themeUtils.applyModifiers(subject, theme), fixedIndent) - return formatted.toString({diff: false}) - } - - const circular = new Circular() - const maxDepth = (options && options.maxDepth) || 0 - - let indent = fixedIndent - - const buffer = lineBuilder.buffer() - const stack = [] - let topIndex = -1 - - do { - if (circular.has(subject)) { - stack[topIndex].formatter.append(lineBuilder.single(theme.circular), subject) - } else { - let didFormat = false - if (typeof subject.formatDeep === 'function') { - const formatted = subject.formatDeep(themeUtils.applyModifiers(subject, theme), indent) - if (formatted !== null) { - didFormat = true - if (topIndex === -1) { - buffer.append(formatted) - } else { - stack[topIndex].formatter.append(formatted, subject) - } - } - } - - if (!didFormat && typeof subject.formatShallow === 'function') { - const formatter = subject.formatShallow(themeUtils.applyModifiers(subject, theme), indent) - const recursor = subject.createRecursor() - - if (formatter.increaseIndent && maxDepth > 0 && indent.level === maxDepth) { - const isEmpty = recursor() === null - const formatted = !isEmpty && typeof formatter.maxDepth === 'function' - ? formatter.maxDepth() - : formatter.finalize() - stack[topIndex].formatter.append(formatted, subject) - } else { - stack.push({ - formatter, - recursor, - decreaseIndent: formatter.increaseIndent, - shouldFormat: formatter.shouldFormat || alwaysFormat, - subject - }) - topIndex++ - - if (formatter.increaseIndent) indent = indent.increase() - circular.add(subject) - } - } - } - - while (topIndex >= 0) { - do { - subject = stack[topIndex].recursor() - } while (subject && !stack[topIndex].shouldFormat(subject)) - - if (subject) { - break - } - - const record = stack.pop() - topIndex-- - if (record.decreaseIndent) indent = indent.decrease() - circular.delete(record.subject) - - const formatted = record.formatter.finalize() - if (topIndex === -1) { - buffer.append(formatted) - } else { - stack[topIndex].formatter.append(formatted, record.subject) - } - } - } while (topIndex >= 0) - - return buffer.toString({diff: false}) -} -exports.formatDescriptor = formatDescriptor - -function format (value, options) { - return formatDescriptor(describe(value, options), options) -} -exports.format = format diff --git a/node_modules/concordance/lib/formatUtils.js b/node_modules/concordance/lib/formatUtils.js deleted file mode 100644 index 07e8b2c57..000000000 --- a/node_modules/concordance/lib/formatUtils.js +++ /dev/null @@ -1,123 +0,0 @@ -'use strict' - -const lineBuilder = require('./lineBuilder') - -function wrap (fromTheme, value) { - return fromTheme.open + value + fromTheme.close -} -exports.wrap = wrap - -function formatCtorAndStringTag (theme, object) { - if (!object.ctor) return wrap(theme.object.stringTag, object.stringTag) - - let retval = wrap(theme.object.ctor, object.ctor) - if (object.stringTag && object.stringTag !== object.ctor && object.stringTag !== 'Object') { - retval += ' ' + wrap(theme.object.secondaryStringTag, object.stringTag) - } - return retval -} -exports.formatCtorAndStringTag = formatCtorAndStringTag - -class ObjectFormatter { - constructor (object, theme, indent) { - this.object = object - this.theme = theme - this.indent = indent - - this.increaseIndent = true - - this.innerLines = lineBuilder.buffer() - this.pendingStats = null - } - - append (formatted, origin) { - if (origin.isStats === true) { - this.pendingStats = formatted - } else { - if (this.pendingStats !== null) { - if (!this.innerLines.isEmpty) { - this.innerLines.append(this.pendingStats) - } - this.pendingStats = null - } - this.innerLines.append(formatted) - } - } - - finalize () { - const variant = this.object.isList - ? this.theme.list - : this.theme.object - - const ctor = this.object.ctor - const stringTag = this.object.stringTag - const prefix = (ctor === 'Array' || ctor === 'Object') && ctor === stringTag - ? '' - : formatCtorAndStringTag(this.theme, this.object) + ' ' - - if (this.innerLines.isEmpty) { - return lineBuilder.single(prefix + variant.openBracket + variant.closeBracket) - } - - return lineBuilder.first(prefix + variant.openBracket) - .concat(this.innerLines.withFirstPrefixed(this.indent.increase()).stripFlags()) - .append(lineBuilder.last(this.indent + variant.closeBracket)) - } - - maxDepth () { - const variant = this.object.isList - ? this.theme.list - : this.theme.object - - return lineBuilder.single( - formatCtorAndStringTag(this.theme, this.object) + ' ' + variant.openBracket + - ' ' + this.theme.maxDepth + ' ' + variant.closeBracket) - } - - shouldFormat () { - return true - } - - customize (methods) { - if (methods.finalize) { - this.finalize = () => methods.finalize(this.innerLines) - } - if (methods.maxDepth) { - this.maxDepth = methods.maxDepth - } - if (methods.shouldFormat) { - this.shouldFormat = methods.shouldFormat - } - - return this - } -} -exports.ObjectFormatter = ObjectFormatter - -class SingleValueFormatter { - constructor (theme, finalizeFn, increaseIndent) { - this.theme = theme - this.finalizeFn = finalizeFn - this.hasValue = false - this.increaseIndent = increaseIndent === true - this.value = null - } - - append (formatted) { - if (this.hasValue) throw new Error('Formatter buffer can only take one formatted value.') - - this.hasValue = true - this.value = formatted - } - - finalize () { - if (!this.hasValue) throw new Error('Formatter buffer never received a formatted value.') - - return this.finalizeFn(this.value) - } - - maxDepth () { - return this.finalizeFn(lineBuilder.single(this.theme.maxDepth)) - } -} -exports.SingleValueFormatter = SingleValueFormatter diff --git a/node_modules/concordance/lib/getCtor.js b/node_modules/concordance/lib/getCtor.js deleted file mode 100644 index 4bbdfd158..000000000 --- a/node_modules/concordance/lib/getCtor.js +++ /dev/null @@ -1,43 +0,0 @@ -'use strict' - -const hop = Object.prototype.hasOwnProperty - -function getCtor (stringTag, value) { - if (value.constructor) { - const name = value.constructor.name - return typeof name === 'string' && name !== '' - ? name - : null - } - - if (value.constructor === undefined) { - if (stringTag !== 'Object' || value instanceof Object) return null - - // Values without a constructor, that do not inherit from `Object`, but are - // tagged as objects, may come from `Object.create(null)`. Or they can come - // from a different realm, e.g.: - // - // ``` - // require('vm').runInNewContext(` - // const Foo = function () {} - // Foo.prototype.constructor = undefined - // return new Foo() - // `) - // ``` - // - // Treat such objects as if they came from `Object.create(null)` (in the - // current realm) only if they do not have inherited properties. This allows - // these objects to be compared with object literals. - // - // This means `Object.create(null)` is not differentiated from `{}`. - - // Using `const` prevents Crankshaft optimizations - for (var p in value) { // eslint-disable-line no-var - if (!hop.call(value, p)) return null - } - return stringTag - } - - return null -} -module.exports = getCtor diff --git a/node_modules/concordance/lib/getObjectKeys.js b/node_modules/concordance/lib/getObjectKeys.js deleted file mode 100644 index 4b0c3e368..000000000 --- a/node_modules/concordance/lib/getObjectKeys.js +++ /dev/null @@ -1,36 +0,0 @@ -'use strict' - -function getObjectKeys (obj, excludeListItemAccessorsBelowLength) { - const keys = [] - let size = 0 - - // Sort property names, they should never be order-sensitive - const nameCandidates = Object.getOwnPropertyNames(obj).sort() - // Comparators should verify symbols in an order-insensitive manner if - // possible. - const symbolCandidates = Object.getOwnPropertySymbols(obj) - - for (let i = 0; i < nameCandidates.length; i++) { - const name = nameCandidates[i] - - let accept = true - if (excludeListItemAccessorsBelowLength > 0) { - const index = Number(name) - accept = (index % 1 !== 0) || index >= excludeListItemAccessorsBelowLength - } - - if (accept && Object.getOwnPropertyDescriptor(obj, name).enumerable) { - keys[size++] = name - } - } - - for (let i = 0; i < symbolCandidates.length; i++) { - const symbol = symbolCandidates[i] - if (Object.getOwnPropertyDescriptor(obj, symbol).enumerable) { - keys[size++] = symbol - } - } - - return { keys, size } -} -module.exports = getObjectKeys diff --git a/node_modules/concordance/lib/getStringTag.js b/node_modules/concordance/lib/getStringTag.js deleted file mode 100644 index 994ec4bec..000000000 --- a/node_modules/concordance/lib/getStringTag.js +++ /dev/null @@ -1,30 +0,0 @@ -'use strict' - -const ts = Object.prototype.toString -function getStringTag (value) { - return ts.call(value).slice(8, -1) -} - -const fts = Function.prototype.toString -const promiseCtorString = fts.call(Promise) -const isPromise = value => { - if (!value.constructor) return false - - try { - return fts.call(value.constructor) === promiseCtorString - } catch (err) { - return false - } -} - -if (getStringTag(Promise.resolve()) === 'Promise') { - module.exports = getStringTag -} else { - const getStringTagWithPromiseWorkaround = value => { - const stringTag = getStringTag(value) - return stringTag === 'Object' && isPromise(value) - ? 'Promise' - : stringTag - } - module.exports = getStringTagWithPromiseWorkaround -} diff --git a/node_modules/concordance/lib/hasLength.js b/node_modules/concordance/lib/hasLength.js deleted file mode 100644 index 18df0d369..000000000 --- a/node_modules/concordance/lib/hasLength.js +++ /dev/null @@ -1,7 +0,0 @@ -'use strict' - -const hop = Object.prototype.hasOwnProperty -function hasLength (obj) { - return Array.isArray(obj) || (hop.call(obj, 'length') && typeof obj.length === 'number') -} -module.exports = hasLength diff --git a/node_modules/concordance/lib/isEnumerable.js b/node_modules/concordance/lib/isEnumerable.js deleted file mode 100644 index 90c2df1e1..000000000 --- a/node_modules/concordance/lib/isEnumerable.js +++ /dev/null @@ -1,7 +0,0 @@ -'use strict' - -function isEnumerable (obj, key) { - const desc = Object.getOwnPropertyDescriptor(obj, key) - return desc && desc.enumerable -} -module.exports = isEnumerable diff --git a/node_modules/concordance/lib/lineBuilder.js b/node_modules/concordance/lib/lineBuilder.js deleted file mode 100644 index 934ac0095..000000000 --- a/node_modules/concordance/lib/lineBuilder.js +++ /dev/null @@ -1,309 +0,0 @@ -'use strict' - -const ACTUAL = Symbol('lineBuilder.gutters.ACTUAL') -const EXPECTED = Symbol('lineBuilder.gutters.EXPECTED') - -function translateGutter (theme, invert, gutter) { - if (invert) { - if (gutter === ACTUAL) return theme.diffGutters.expected - if (gutter === EXPECTED) return theme.diffGutters.actual - } else { - if (gutter === ACTUAL) return theme.diffGutters.actual - if (gutter === EXPECTED) return theme.diffGutters.expected - } - return theme.diffGutters.padding -} - -class Line { - constructor (isFirst, isLast, gutter, stringValue) { - this.isFirst = isFirst - this.isLast = isLast - this.gutter = gutter - this.stringValue = stringValue - } - - * [Symbol.iterator] () { - yield this - } - - get isEmpty () { - return false - } - - get hasGutter () { - return this.gutter !== null - } - - get isSingle () { - return this.isFirst && this.isLast - } - - append (other) { - return this.concat(other) - } - - concat (other) { - return new Collection() - .append(this) - .append(other) - } - - toString (options) { - if (options.diff === false) return this.stringValue - - return translateGutter(options.theme, options.invert, this.gutter) + this.stringValue - } - - mergeWithInfix (infix, other) { - if (other.isLine !== true) { - return new Collection() - .append(this) - .mergeWithInfix(infix, other) - } - - return new Line(this.isFirst, other.isLast, other.gutter, this.stringValue + infix + other.stringValue) - } - - withFirstPrefixed (prefix) { - if (!this.isFirst) return this - - return new Line(true, this.isLast, this.gutter, prefix + this.stringValue) - } - - withLastPostfixed (postfix) { - if (!this.isLast) return this - - return new Line(this.isFirst, true, this.gutter, this.stringValue + postfix) - } - - stripFlags () { - return new Line(false, false, this.gutter, this.stringValue) - } - - decompose () { - return new Collection() - .append(this) - .decompose() - } -} -Object.defineProperty(Line.prototype, 'isLine', {value: true}) - -class Collection { - constructor () { - this.buffer = [] - } - - * [Symbol.iterator] () { - for (const appended of this.buffer) { - for (const line of appended) yield line - } - } - - get isEmpty () { - return this.buffer.length === 0 - } - - get hasGutter () { - for (const line of this) { - if (line.hasGutter) return true - } - return false - } - - get isSingle () { - const iterator = this[Symbol.iterator]() - iterator.next() - return iterator.next().done === true - } - - append (lineOrLines) { - if (!lineOrLines.isEmpty) this.buffer.push(lineOrLines) - return this - } - - concat (other) { - return new Collection() - .append(this) - .append(other) - } - - toString (options) { - let lines = this - - if (options.invert) { - lines = new Collection() - let buffer = new Collection() - - let prev = null - for (const line of this) { - if (line.gutter === ACTUAL) { - if (prev !== null && prev.gutter !== ACTUAL && !buffer.isEmpty) { - lines.append(buffer) - buffer = new Collection() - } - - buffer.append(line) - } else if (line.gutter === EXPECTED) { - lines.append(line) - } else { - if (!buffer.isEmpty) { - lines.append(buffer) - buffer = new Collection() - } - - lines.append(line) - } - - prev = line - } - lines.append(buffer) - } - - return Array.from(lines, line => line.toString(options)).join('\n') - } - - mergeWithInfix (infix, from) { - if (from.isEmpty) throw new Error('Cannot merge, `from` is empty.') - - const otherLines = Array.from(from) - if (!otherLines[0].isFirst) throw new Error('Cannot merge, `from` has no first line.') - - const merged = new Collection() - let seenLast = false - for (const line of this) { - if (seenLast) throw new Error('Cannot merge line, the last line has already been seen.') - - if (!line.isLast) { - merged.append(line) - continue - } - - seenLast = true - for (const other of otherLines) { - if (other.isFirst) { - merged.append(line.mergeWithInfix(infix, other)) - } else { - merged.append(other) - } - } - } - return merged - } - - withFirstPrefixed (prefix) { - return new Collection() - .append(Array.from(this, line => line.withFirstPrefixed(prefix))) - } - - withLastPostfixed (postfix) { - return new Collection() - .append(Array.from(this, line => line.withLastPostfixed(postfix))) - } - - stripFlags () { - return new Collection() - .append(Array.from(this, line => line.stripFlags())) - } - - decompose () { - const first = {actual: new Collection(), expected: new Collection()} - const last = {actual: new Collection(), expected: new Collection()} - const remaining = new Collection() - - for (const line of this) { - if (line.isFirst && line.gutter === ACTUAL) { - first.actual.append(line) - } else if (line.isFirst && line.gutter === EXPECTED) { - first.expected.append(line) - } else if (line.isLast && line.gutter === ACTUAL) { - last.actual.append(line) - } else if (line.isLast && line.gutter === EXPECTED) { - last.expected.append(line) - } else { - remaining.append(line) - } - } - - return {first, last, remaining} - } -} -Object.defineProperty(Collection.prototype, 'isCollection', {value: true}) - -function setDefaultGutter (iterable, gutter) { - return new Collection() - .append(Array.from(iterable, line => { - return line.gutter === null - ? new Line(line.isFirst, line.isLast, gutter, line.stringValue) - : line - })) -} - -module.exports = { - buffer () { - return new Collection() - }, - - first (stringValue) { - return new Line(true, false, null, stringValue) - }, - - last (stringValue) { - return new Line(false, true, null, stringValue) - }, - - line (stringValue) { - return new Line(false, false, null, stringValue) - }, - - single (stringValue) { - return new Line(true, true, null, stringValue) - }, - - setDefaultGutter (lineOrCollection) { - return lineOrCollection - }, - - actual: { - first (stringValue) { - return new Line(true, false, ACTUAL, stringValue) - }, - - last (stringValue) { - return new Line(false, true, ACTUAL, stringValue) - }, - - line (stringValue) { - return new Line(false, false, ACTUAL, stringValue) - }, - - single (stringValue) { - return new Line(true, true, ACTUAL, stringValue) - }, - - setDefaultGutter (lineOrCollection) { - return setDefaultGutter(lineOrCollection, ACTUAL) - } - }, - - expected: { - first (stringValue) { - return new Line(true, false, EXPECTED, stringValue) - }, - - last (stringValue) { - return new Line(false, true, EXPECTED, stringValue) - }, - - line (stringValue) { - return new Line(false, false, EXPECTED, stringValue) - }, - - single (stringValue) { - return new Line(true, true, EXPECTED, stringValue) - }, - - setDefaultGutter (lineOrCollection) { - return setDefaultGutter(lineOrCollection, EXPECTED) - } - } -} diff --git a/node_modules/concordance/lib/metaDescriptors/item.js b/node_modules/concordance/lib/metaDescriptors/item.js deleted file mode 100644 index 1539b624a..000000000 --- a/node_modules/concordance/lib/metaDescriptors/item.js +++ /dev/null @@ -1,254 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const recursorUtils = require('../recursorUtils') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describeComplex (index, value) { - return new ComplexItem(index, value) -} -exports.describeComplex = describeComplex - -function deserializeComplex (index, recursor) { - const value = recursor() - return new ComplexItem(index, value) -} -exports.deserializeComplex = deserializeComplex - -function describePrimitive (index, value) { - return new PrimitiveItem(index, value) -} -exports.describePrimitive = describePrimitive - -function deserializePrimitive (state) { - const index = state[0] - const value = state[1] - return new PrimitiveItem(index, value) -} -exports.deserializePrimitive = deserializePrimitive - -const complexTag = Symbol('ComplexItem') -exports.complexTag = complexTag - -const primitiveTag = Symbol('PrimitiveItem') -exports.primitiveTag = primitiveTag - -class ComplexItem { - constructor (index, value) { - this.index = index - this.value = value - } - - createRecursor () { - return recursorUtils.singleValue(this.value) - } - - compare (expected) { - return expected.tag === complexTag && this.index === expected.index - ? this.value.compare(expected.value) - : UNEQUAL - } - - formatShallow (theme, indent) { - const increaseValueIndent = theme.item.increaseValueIndent === true - return new formatUtils.SingleValueFormatter(theme, value => { - if (typeof theme.item.customFormat === 'function') { - return theme.item.customFormat(theme, indent, value) - } - - return value.withLastPostfixed(theme.item.after) - }, increaseValueIndent) - } - - prepareDiff (expected, lhsRecursor, rhsRecursor, compareComplexShape, isCircular) { - // Circular values cannot be compared. They must be treated as being unequal when diffing. - if (isCircular(this.value) || isCircular(expected.value)) return {compareResult: UNEQUAL} - - // Try to line up this or remaining items with the expected items. - const lhsFork = recursorUtils.fork(lhsRecursor) - const rhsFork = recursorUtils.fork(rhsRecursor) - const initialExpected = expected - - let expectedIsMissing = false - while (!expectedIsMissing && expected !== null && expected.isItem === true) { - if (expected.tag === complexTag) { - expectedIsMissing = compareComplexShape(this.value, expected.value) !== UNEQUAL - } - - expected = rhsFork.shared() - } - - let actualIsExtraneous = false - if (initialExpected.tag === complexTag) { - let actual = this - while (!actualIsExtraneous && actual !== null && actual.isItem === true) { - if (actual.tag === complexTag) { - actualIsExtraneous = compareComplexShape(actual.value, initialExpected.value) !== UNEQUAL - } - - actual = lhsFork.shared() - } - } else if (initialExpected.tag === primitiveTag) { - let actual = this - while (!actualIsExtraneous && actual !== null && actual.isItem === true) { - if (actual.tag === primitiveTag) { - actualIsExtraneous = initialExpected.value.compare(actual.value) === DEEP_EQUAL - } - - actual = lhsFork.shared() - } - } - - if (actualIsExtraneous && !expectedIsMissing) { - return { - actualIsExtraneous: true, - lhsRecursor: lhsFork.recursor, - rhsRecursor: recursorUtils.map( - recursorUtils.unshift(rhsFork.recursor, initialExpected), - next => { - if (next.isItem !== true) return next - - next.index++ - return next - }) - } - } - - if (expectedIsMissing && !actualIsExtraneous) { - return { - expectedIsMissing: true, - lhsRecursor: recursorUtils.map( - recursorUtils.unshift(lhsFork.recursor, this), - next => { - if (next.isItem !== true) return next - - next.index++ - return next - }), - rhsRecursor: rhsFork.recursor - } - } - - const mustRecurse = this.tag === complexTag && initialExpected.tag === complexTag && - this.value.compare(initialExpected.value) !== UNEQUAL - return { - mustRecurse, - isUnequal: !mustRecurse, - lhsRecursor: lhsFork.recursor, - rhsRecursor: rhsFork.recursor - } - } - - serialize () { - return this.index - } -} -Object.defineProperty(ComplexItem.prototype, 'isItem', { value: true }) -Object.defineProperty(ComplexItem.prototype, 'tag', { value: complexTag }) - -class PrimitiveItem { - constructor (index, value) { - this.index = index - this.value = value - } - - compare (expected) { - return expected.tag === primitiveTag && this.index === expected.index - ? this.value.compare(expected.value) - : UNEQUAL - } - - formatDeep (theme, indent) { - const increaseValueIndent = theme.item.increaseValueIndent === true - const valueIndent = increaseValueIndent ? indent.increase() : indent - - // Since the value is formatted directly, modifiers are not applied. Apply - // modifiers to the item descriptor instead. - const formatted = this.value.formatDeep(theme, valueIndent) - - if (typeof theme.item.customFormat === 'function') { - return theme.item.customFormat(theme, indent, formatted) - } - - return formatted.withLastPostfixed(theme.item.after) - } - - prepareDiff (expected, lhsRecursor, rhsRecursor, compareComplexShape, isCircular) { - const compareResult = this.compare(expected) - // Short-circuit when values are deeply equal. - if (compareResult === DEEP_EQUAL) return {compareResult} - - // Short-circut when values can be diffed directly. - if ( - expected.tag === primitiveTag && - this.value.tag === expected.value.tag && typeof this.value.diffDeep === 'function' - ) { - return {compareResult} - } - - // Try to line up this or remaining items with the expected items. - const rhsFork = recursorUtils.fork(rhsRecursor) - const initialExpected = expected - - do { - if (expected === null || expected.isItem !== true) { - return { - actualIsExtraneous: true, - rhsRecursor: recursorUtils.map( - recursorUtils.unshift(rhsFork.recursor, initialExpected), - next => { - if (next.isItem !== true) return next - - next.index++ - return next - }) - } - } - - if (this.value.compare(expected.value) === DEEP_EQUAL) { - return { - expectedIsMissing: true, - lhsRecursor: recursorUtils.map( - recursorUtils.unshift(lhsRecursor, this), - next => { - if (next.isItem !== true) return next - - next.index++ - return next - }), - rhsRecursor: rhsFork.recursor - } - } - - expected = rhsFork.shared() - } while (true) - } - - diffDeep (expected, theme, indent) { - // Verify a diff can be returned. - if (this.tag !== expected.tag || typeof this.value.diffDeep !== 'function') return null - - const increaseValueIndent = theme.property.increaseValueIndent === true - const valueIndent = increaseValueIndent ? indent.increase() : indent - - // Since the value is diffed directly, modifiers are not applied. Apply - // modifiers to the item descriptor instead. - const diff = this.value.diffDeep(expected.value, theme, valueIndent) - if (diff === null) return null - - if (typeof theme.item.customFormat === 'function') { - return theme.item.customFormat(theme, indent, diff) - } - - return diff.withLastPostfixed(theme.item.after) - } - - serialize () { - return [this.index, this.value] - } -} -Object.defineProperty(PrimitiveItem.prototype, 'isItem', { value: true }) -Object.defineProperty(PrimitiveItem.prototype, 'tag', { value: primitiveTag }) diff --git a/node_modules/concordance/lib/metaDescriptors/mapEntry.js b/node_modules/concordance/lib/metaDescriptors/mapEntry.js deleted file mode 100644 index f1c100e4e..000000000 --- a/node_modules/concordance/lib/metaDescriptors/mapEntry.js +++ /dev/null @@ -1,223 +0,0 @@ -'use strict' - -const constants = require('../constants') -const lineBuilder = require('../lineBuilder') -const recursorUtils = require('../recursorUtils') -const themeUtils = require('../themeUtils') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL - -function describe (keyDescriptor, valueDescriptor) { - const keyIsPrimitive = keyDescriptor.isPrimitive === true - const valueIsPrimitive = valueDescriptor.isPrimitive === true - - return new MapEntry(keyDescriptor, valueDescriptor, keyIsPrimitive, valueIsPrimitive) -} -exports.describe = describe - -function deserialize (state, recursor) { - const keyIsPrimitive = state[0] - const valueIsPrimitive = state[1] - const keyDescriptor = recursor() - const valueDescriptor = recursor() - - return new MapEntry(keyDescriptor, valueDescriptor, keyIsPrimitive, valueIsPrimitive) -} -exports.deserialize = deserialize - -const tag = Symbol('MapEntry') -exports.tag = tag - -function mergeWithKey (theme, key, values) { - const lines = lineBuilder.buffer() - const keyRemainder = lineBuilder.buffer() - for (const line of key) { - if (!line.isLast && !line.hasGutter) { - lines.append(line) - } else { - keyRemainder.append(line) - } - } - for (const value of values) { - lines.append(keyRemainder.mergeWithInfix(theme.mapEntry.separator, value).withLastPostfixed(theme.mapEntry.after)) - } - return lines -} - -class MapEntry { - constructor (key, value, keyIsPrimitive, valueIsPrimitive) { - this.key = key - this.value = value - this.keyIsPrimitive = keyIsPrimitive - this.valueIsPrimitive = valueIsPrimitive - } - - createRecursor () { - let emitKey = true - let emitValue = true - - return () => { - if (emitKey) { - emitKey = false - return this.key - } - - if (emitValue) { - emitValue = false - return this.value - } - - return null - } - } - - compare (expected) { - if (this.tag !== expected.tag) return UNEQUAL - if (this.keyIsPrimitive !== expected.keyIsPrimitive) return UNEQUAL - if (this.valueIsPrimitive !== expected.valueIsPrimitive) return UNEQUAL - - if (!this.keyIsPrimitive) return SHALLOW_EQUAL - - const keyResult = this.key.compare(expected.key) - if (keyResult !== DEEP_EQUAL) return keyResult - - if (!this.valueIsPrimitive) return SHALLOW_EQUAL - return this.value.compare(expected.value) - } - - formatDeep (theme, indent) { - // Verify the map entry can be formatted directly. - if (!this.keyIsPrimitive || typeof this.value.formatDeep !== 'function') return null - - // Since formatShallow() would result in theme modifiers being applied - // before the key and value are formatted, do the same here. - const value = this.value.formatDeep(themeUtils.applyModifiersToOriginal(this.value, theme), indent) - if (value === null) return null - - const key = this.key.formatDeep(themeUtils.applyModifiersToOriginal(this.key, theme), indent) - return mergeWithKey(theme, key, [value]) - } - - formatShallow (theme, indent) { - let key = null - const values = [] - return { - append: (formatted, origin) => { - if (this.key === origin) { - key = formatted - } else { - values.push(formatted) - } - }, - finalize () { - return mergeWithKey(theme, key, values) - } - } - } - - diffDeep (expected, theme, indent) { - // Verify a diff can be returned. - if (this.tag !== expected.tag || typeof this.value.diffDeep !== 'function') return null - // Only use this logic to format value diffs when the keys are primitive and equal. - if (!this.keyIsPrimitive || !expected.keyIsPrimitive || this.key.compare(expected.key) !== DEEP_EQUAL) { - return null - } - - // Since formatShallow() would result in theme modifiers being applied - // before the key and value are formatted, do the same here. - const diff = this.value.diffDeep(expected.value, themeUtils.applyModifiersToOriginal(this.value, theme), indent) - if (diff === null) return null - - const key = this.key.formatDeep(themeUtils.applyModifiersToOriginal(this.key, theme), indent, '') - return mergeWithKey(theme, key, [diff]) - } - - prepareDiff (expected, lhsRecursor, rhsRecursor, compareComplexShape, isCircular) { - // Circular values cannot be compared. They must be treated as being unequal when diffing. - if (isCircular(this.value) || isCircular(expected.value)) return {compareResult: UNEQUAL} - - const compareResult = this.compare(expected) - const keysAreEqual = this.tag === expected.tag && this.key.compare(expected.key) === DEEP_EQUAL - // Short-circuit when keys and/or values are deeply equal. - if (compareResult === DEEP_EQUAL || keysAreEqual) return {compareResult} - - // Try to line up this or remaining map entries with the expected entries. - const lhsFork = recursorUtils.fork(lhsRecursor) - const rhsFork = recursorUtils.fork(rhsRecursor) - const initialExpected = expected - - let expectedIsMissing = false - while (!expectedIsMissing && expected !== null && this.tag === expected.tag) { - if (expected.keyIsPrimitive) { - expectedIsMissing = this.key.compare(expected.key) !== UNEQUAL - } else { - expectedIsMissing = compareComplexShape(this.key, expected.key) !== UNEQUAL - } - - expected = rhsFork.shared() - } - - let actualIsExtraneous = false - if (this.tag === initialExpected.tag) { - if (initialExpected.keyIsPrimitive) { - let actual = this - while (!actualIsExtraneous && actual !== null && this.tag === actual.tag) { - if (actual.keyIsPrimitive) { - actualIsExtraneous = initialExpected.key.compare(actual.key) === DEEP_EQUAL - } - - actual = lhsFork.shared() - } - } else { - let actual = this - while (!actualIsExtraneous && actual !== null && this.tag === actual.tag) { - if (!actual.keyIsPrimitive) { - actualIsExtraneous = compareComplexShape(actual.key, initialExpected.key) !== UNEQUAL - } - - actual = lhsFork.shared() - } - } - } - - if (actualIsExtraneous && !expectedIsMissing) { - return { - actualIsExtraneous: true, - lhsRecursor: lhsFork.recursor, - rhsRecursor: recursorUtils.unshift(rhsFork.recursor, initialExpected) - } - } - - if (expectedIsMissing && !actualIsExtraneous) { - return { - expectedIsMissing: true, - lhsRecursor: recursorUtils.unshift(lhsFork.recursor, this), - rhsRecursor: rhsFork.recursor - } - } - - let mustRecurse = false - if (!this.keyIsPrimitive && !initialExpected.keyIsPrimitive) { - if (this.valueIsPrimitive || initialExpected.valueIsPrimitive) { - mustRecurse = this.value.compare(initialExpected.value) !== UNEQUAL - } else { - mustRecurse = compareComplexShape(this.value, initialExpected.value) !== UNEQUAL - } - } - - return { - mustRecurse, - isUnequal: !mustRecurse, - lhsRecursor: lhsFork.recursor, - rhsRecursor: rhsFork.recursor - } - } - - serialize () { - return [this.keyIsPrimitive, this.valueIsPrimitive] - } -} -Object.defineProperty(MapEntry.prototype, 'isMapEntry', { value: true }) -Object.defineProperty(MapEntry.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/metaDescriptors/pointer.js b/node_modules/concordance/lib/metaDescriptors/pointer.js deleted file mode 100644 index f569d2891..000000000 --- a/node_modules/concordance/lib/metaDescriptors/pointer.js +++ /dev/null @@ -1,31 +0,0 @@ -'use strict' - -const UNEQUAL = require('../constants').UNEQUAL - -function describe (index) { - return new Pointer(index) -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('Pointer') -exports.tag = tag - -class Pointer { - constructor (index) { - this.index = index - } - - // Pointers cannot be compared, and are not expected to be part of the - // comparisons. - compare (expected) { - return UNEQUAL - } - - serialize () { - return this.index - } -} -Object.defineProperty(Pointer.prototype, 'isPointer', { value: true }) -Object.defineProperty(Pointer.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/metaDescriptors/property.js b/node_modules/concordance/lib/metaDescriptors/property.js deleted file mode 100644 index b5d34271d..000000000 --- a/node_modules/concordance/lib/metaDescriptors/property.js +++ /dev/null @@ -1,190 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const recursorUtils = require('../recursorUtils') -const symbolPrimitive = require('../primitiveValues/symbol').tag - -const AMBIGUOUS = constants.AMBIGUOUS -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describeComplex (key, value) { - return new ComplexProperty(key, value) -} -exports.describeComplex = describeComplex - -function deserializeComplex (key, recursor) { - const value = recursor() - return new ComplexProperty(key, value) -} -exports.deserializeComplex = deserializeComplex - -function describePrimitive (key, value) { - return new PrimitiveProperty(key, value) -} -exports.describePrimitive = describePrimitive - -function deserializePrimitive (state) { - const key = state[0] - const value = state[1] - return new PrimitiveProperty(key, value) -} -exports.deserializePrimitive = deserializePrimitive - -const complexTag = Symbol('ComplexProperty') -exports.complexTag = complexTag - -const primitiveTag = Symbol('PrimitiveProperty') -exports.primitiveTag = primitiveTag - -class Property { - constructor (key) { - this.key = key - } - - compareKeys (expected) { - const result = this.key.compare(expected.key) - // Return AMBIGUOUS if symbol keys are unequal. It's likely that properties - // are compared in order of declaration, which is not the desired strategy. - // Returning AMBIGUOUS allows compare() and diff() to recognize this - // situation and sort the symbol properties before comparing them. - return result === UNEQUAL && this.key.tag === symbolPrimitive && expected.key.tag === symbolPrimitive - ? AMBIGUOUS - : result - } - - prepareDiff (expected, lhsRecursor, rhsRecursor, compareComplexShape, isCircular) { - // Circular values cannot be compared. They must be treated as being unequal when diffing. - if (isCircular(this.value) || isCircular(expected.value)) return {compareResult: UNEQUAL} - - // Try to line up this or remaining properties with the expected properties. - const rhsFork = recursorUtils.fork(rhsRecursor) - const initialExpected = expected - - do { - if (expected === null || expected.isProperty !== true) { - return { - actualIsExtraneous: true, - rhsRecursor: recursorUtils.unshift(rhsFork.recursor, initialExpected) - } - } else if (this.key.compare(expected.key) === DEEP_EQUAL) { - if (expected === initialExpected) { - return null - } else { - return { - expectedIsMissing: true, - lhsRecursor: recursorUtils.unshift(lhsRecursor, this), - rhsRecursor: rhsFork.recursor - } - } - } - - expected = rhsFork.shared() - } while (true) - } -} -Object.defineProperty(Property.prototype, 'isProperty', { value: true }) - -class ComplexProperty extends Property { - constructor (key, value) { - super(key) - this.value = value - } - - createRecursor () { - return recursorUtils.singleValue(this.value) - } - - compare (expected) { - if (expected.isProperty !== true) return UNEQUAL - - const keyResult = this.compareKeys(expected) - if (keyResult !== DEEP_EQUAL) return keyResult - - return this.tag === expected.tag - ? this.value.compare(expected.value) - : UNEQUAL - } - - formatShallow (theme, indent) { - const increaseValueIndent = theme.property.increaseValueIndent === true - return new formatUtils.SingleValueFormatter(theme, value => { - if (typeof theme.property.customFormat === 'function') { - return theme.property.customFormat(theme, indent, this.key, value) - } - - return value - .withFirstPrefixed(this.key.formatAsKey(theme) + theme.property.separator) - .withLastPostfixed(theme.property.after) - }, increaseValueIndent) - } - - serialize () { - return this.key - } -} -Object.defineProperty(ComplexProperty.prototype, 'tag', { value: complexTag }) - -class PrimitiveProperty extends Property { - constructor (key, value) { - super(key) - this.value = value - } - - compare (expected) { - if (expected.isProperty !== true) return UNEQUAL - - const keyResult = this.compareKeys(expected) - if (keyResult !== DEEP_EQUAL) return keyResult - - return this.tag !== expected.tag - ? UNEQUAL - : this.value.compare(expected.value) - } - - formatDeep (theme, indent) { - const increaseValueIndent = theme.property.increaseValueIndent === true - const valueIndent = increaseValueIndent ? indent.increase() : indent - - // Since the key and value are formatted directly, modifiers are not - // applied. Apply modifiers to the property descriptor instead. - const formatted = this.value.formatDeep(theme, valueIndent) - - if (typeof theme.property.customFormat === 'function') { - return theme.property.customFormat(theme, indent, this.key, formatted) - } - - return formatted - .withFirstPrefixed(this.key.formatAsKey(theme) + theme.property.separator) - .withLastPostfixed(theme.property.after) - } - - diffDeep (expected, theme, indent) { - // Verify a diff can be returned. - if (this.tag !== expected.tag || typeof this.value.diffDeep !== 'function') return null - // Only use this logic to diff values when the keys are the same. - if (this.key.compare(expected.key) !== DEEP_EQUAL) return null - - const increaseValueIndent = theme.property.increaseValueIndent === true - const valueIndent = increaseValueIndent ? indent.increase() : indent - - // Since the key and value are diffed directly, modifiers are not - // applied. Apply modifiers to the property descriptor instead. - const diff = this.value.diffDeep(expected.value, theme, valueIndent) - if (diff === null) return null - - if (typeof theme.property.customFormat === 'function') { - return theme.property.customFormat(theme, indent, this.key, diff) - } - - return diff - .withFirstPrefixed(this.key.formatAsKey(theme) + theme.property.separator) - .withLastPostfixed(theme.property.after) - } - - serialize () { - return [this.key, this.value] - } -} -Object.defineProperty(PrimitiveProperty.prototype, 'tag', { value: primitiveTag }) diff --git a/node_modules/concordance/lib/metaDescriptors/stats.js b/node_modules/concordance/lib/metaDescriptors/stats.js deleted file mode 100644 index 93bde9d1e..000000000 --- a/node_modules/concordance/lib/metaDescriptors/stats.js +++ /dev/null @@ -1,136 +0,0 @@ -'use strict' - -const constants = require('../constants') -const lineBuilder = require('../lineBuilder') -const recursorUtils = require('../recursorUtils') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describeIterableRecursor (recursor) { - return new IterableStats(recursor.size) -} -exports.describeIterableRecursor = describeIterableRecursor - -function describeListRecursor (recursor) { - return new ListStats(recursor.size) -} -exports.describeListRecursor = describeListRecursor - -function describePropertyRecursor (recursor) { - return new PropertyStats(recursor.size) -} -exports.describePropertyRecursor = describePropertyRecursor - -function deserializeIterableStats (size) { - return new IterableStats(size) -} -exports.deserializeIterableStats = deserializeIterableStats - -function deserializeListStats (size) { - return new ListStats(size) -} -exports.deserializeListStats = deserializeListStats - -function deserializePropertyStats (size) { - return new PropertyStats(size) -} -exports.deserializePropertyStats = deserializePropertyStats - -const iterableTag = Symbol('IterableStats') -exports.iterableTag = iterableTag - -const listTag = Symbol('ListStats') -exports.listTag = listTag - -const propertyTag = Symbol('PropertyStats') -exports.propertyTag = propertyTag - -class Stats { - constructor (size) { - this.size = size - } - - formatDeep (theme) { - return lineBuilder.single(theme.stats.separator) - } - - prepareDiff (expected, lhsRecursor, rhsRecursor, compareComplexShape) { - if (expected.isStats !== true || expected.tag === this.tag) return null - - // Try to line up stats descriptors with the same tag. - const rhsFork = recursorUtils.fork(rhsRecursor) - const initialExpected = expected - - const missing = [] - while (expected !== null && this.tag !== expected.tag) { - missing.push(expected) - expected = rhsFork.shared() - } - - if (expected !== null && missing.length > 0) { - return { - multipleAreMissing: true, - descriptors: missing, - lhsRecursor: recursorUtils.unshift(lhsRecursor, this), - // Use original `rhsRecursor`, not `rhsFork`, since the consumed - // descriptors are returned with the `missing` array. - rhsRecursor: recursorUtils.unshift(rhsRecursor, expected) - } - } - - const lhsFork = recursorUtils.fork(lhsRecursor) - let actual = this - - const extraneous = [] - while (actual !== null && actual.tag !== initialExpected.tag) { - extraneous.push(actual) - actual = lhsFork.shared() - } - - if (actual !== null && extraneous.length > 0) { - return { - multipleAreExtraneous: true, - descriptors: extraneous, - // Use original `lhsRecursor`, not `lhsFork`, since the consumed - // descriptors are returned with the `extraneous` array. - lhsRecursor: recursorUtils.unshift(lhsRecursor, actual), - rhsRecursor: recursorUtils.unshift(rhsFork.recursor, initialExpected) - } - } - - return null - } - - serialize () { - return this.size - } -} -Object.defineProperty(Stats.prototype, 'isStats', { value: true }) - -class IterableStats extends Stats { - compare (expected) { - return expected.tag === iterableTag && this.size === expected.size - ? DEEP_EQUAL - : UNEQUAL - } -} -Object.defineProperty(IterableStats.prototype, 'tag', { value: iterableTag }) - -class ListStats extends Stats { - compare (expected) { - return expected.tag === listTag && this.size === expected.size - ? DEEP_EQUAL - : UNEQUAL - } -} -Object.defineProperty(ListStats.prototype, 'tag', { value: listTag }) - -class PropertyStats extends Stats { - compare (expected) { - return expected.tag === propertyTag && this.size === expected.size - ? DEEP_EQUAL - : UNEQUAL - } -} -Object.defineProperty(PropertyStats.prototype, 'tag', { value: propertyTag }) diff --git a/node_modules/concordance/lib/pluginRegistry.js b/node_modules/concordance/lib/pluginRegistry.js deleted file mode 100644 index b4fb76b37..000000000 --- a/node_modules/concordance/lib/pluginRegistry.js +++ /dev/null @@ -1,222 +0,0 @@ -'use strict' - -const semver = require('semver') - -const pkg = require('../package.json') -const constants = require('./constants') -const object = require('./complexValues/object') -const lineBuilder = require('./lineBuilder') -const formatUtils = require('./formatUtils') -const itemDescriptor = require('./metaDescriptors/item') -const propertyDescriptor = require('./metaDescriptors/property') -const stringDescriptor = require('./primitiveValues/string') -const recursorUtils = require('./recursorUtils') -const themeUtils = require('./themeUtils') - -const API_VERSION = 1 -const CONCORDANCE_VERSION = pkg.version - -const descriptorRegistry = new Map() -const registry = new Map() - -class PluginError extends Error { - constructor (message, plugin) { - super(message) - this.name = 'PluginError' - this.plugin = plugin - } -} - -class PluginTypeError extends TypeError { - constructor (message, plugin) { - super(message) - this.name = 'PluginTypeError' - this.plugin = plugin - } -} - -class UnsupportedApiError extends PluginError { - constructor (plugin) { - super('Plugin requires an unsupported API version', plugin) - this.name = 'UnsupportedApiError' - } -} - -class UnsupportedError extends PluginError { - constructor (plugin) { - super('Plugin does not support this version of Concordance', plugin) - this.name = 'UnsupportedError' - } -} - -class DuplicateDescriptorTagError extends PluginError { - constructor (tag, plugin) { - super(`Could not add descriptor: tag ${String(tag)} has already been registered`, plugin) - this.name = 'DuplicateDescriptorTagError' - this.tag = tag - } -} - -class DuplicateDescriptorIdError extends PluginError { - constructor (id, plugin) { - const printed = typeof id === 'number' - ? `0x${id.toString(16).toUpperCase()}` - : String(id) - super(`Could not add descriptor: id ${printed} has already been registered`, plugin) - this.name = 'DuplicateDescriptorIdError' - this.id = id - } -} - -function verify (plugin) { - if (typeof plugin.name !== 'string' || !plugin.name) { - throw new PluginTypeError('Plugin must have a `name`', plugin) - } - - if (plugin.apiVersion !== API_VERSION) { - throw new UnsupportedApiError(plugin) - } - - if ('minimalConcordanceVersion' in plugin) { - if (!semver.valid(plugin.minimalConcordanceVersion)) { - throw new PluginTypeError('If specified, `minimalConcordanceVersion` must be a valid SemVer version', plugin) - } - - const range = `>=${plugin.minimalConcordanceVersion}` - if (!semver.satisfies(CONCORDANCE_VERSION, range)) { - throw new UnsupportedError(plugin) - } - } -} - -// Selectively expose descriptor tags. -const publicDescriptorTags = Object.freeze({ - complexItem: itemDescriptor.complexTag, - primitiveItem: itemDescriptor.primitiveTag, - primitiveProperty: propertyDescriptor.primitiveTag, - string: stringDescriptor.tag -}) - -// Don't expose `setDefaultGutter()`. -const publicLineBuilder = Object.freeze({ - buffer: lineBuilder.buffer, - first: lineBuilder.first, - last: lineBuilder.last, - line: lineBuilder.line, - single: lineBuilder.single, - actual: Object.freeze({ - buffer: lineBuilder.actual.buffer, - first: lineBuilder.actual.first, - last: lineBuilder.actual.last, - line: lineBuilder.actual.line, - single: lineBuilder.actual.single - }), - expected: Object.freeze({ - buffer: lineBuilder.expected.buffer, - first: lineBuilder.expected.first, - last: lineBuilder.expected.last, - line: lineBuilder.expected.line, - single: lineBuilder.expected.single - }) -}) - -function modifyTheme (descriptor, modifier) { - themeUtils.addModifier(descriptor, modifier) - return descriptor -} - -function add (plugin) { - verify(plugin) - - const name = plugin.name - if (registry.has(name)) return registry.get(name) - - const id2deserialize = new Map() - const tag2id = new Map() - const addDescriptor = (id, tag, deserialize) => { - if (id2deserialize.has(id)) throw new DuplicateDescriptorIdError(id, plugin) - if (descriptorRegistry.has(tag) || tag2id.has(tag)) throw new DuplicateDescriptorTagError(tag, plugin) - - id2deserialize.set(id, deserialize) - tag2id.set(tag, id) - } - - const tryDescribeValue = plugin.register({ - // Concordance makes assumptions about when AMBIGUOUS occurs. Do not expose - // it to plugins. - UNEQUAL: constants.UNEQUAL, - SHALLOW_EQUAL: constants.SHALLOW_EQUAL, - DEEP_EQUAL: constants.DEEP_EQUAL, - - ObjectValue: object.ObjectValue, - DescribedMixin: object.DescribedMixin, - DeserializedMixin: object.DeserializedMixin, - - addDescriptor, - applyThemeModifiers: themeUtils.applyModifiers, - descriptorTags: publicDescriptorTags, - lineBuilder: publicLineBuilder, - mapRecursor: recursorUtils.map, - modifyTheme, - wrapFromTheme: formatUtils.wrap - }) - - const registered = { - id2deserialize, - serializerVersion: plugin.serializerVersion, - name, - tag2id, - theme: plugin.theme || {}, - tryDescribeValue - } - - registry.set(name, registered) - for (const tag of tag2id.keys()) { - descriptorRegistry.set(tag, registered) - } - - return registered -} -exports.add = add - -function getDeserializers (plugins) { - return plugins.map(plugin => { - const registered = add(plugin) - return { - id2deserialize: registered.id2deserialize, - name: registered.name, - serializerVersion: registered.serializerVersion - } - }) -} -exports.getDeserializers = getDeserializers - -function getThemes (plugins) { - return plugins.map(plugin => { - const registered = add(plugin) - return { - name: registered.name, - theme: registered.theme - } - }) -} -exports.getThemes = getThemes - -function getTryDescribeValues (plugins) { - return plugins.map(plugin => add(plugin).tryDescribeValue) -} -exports.getTryDescribeValues = getTryDescribeValues - -function resolveDescriptorRef (tag) { - if (!descriptorRegistry.has(tag)) return null - - const registered = descriptorRegistry.get(tag) - return { - id: registered.tag2id.get(tag), - name: registered.name, - serialization: { - serializerVersion: registered.serializerVersion - } - } -} -exports.resolveDescriptorRef = resolveDescriptorRef diff --git a/node_modules/concordance/lib/primitiveValues/boolean.js b/node_modules/concordance/lib/primitiveValues/boolean.js deleted file mode 100644 index 7bad50408..000000000 --- a/node_modules/concordance/lib/primitiveValues/boolean.js +++ /dev/null @@ -1,40 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (value) { - return new BooleanValue(value) -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('BooleanValue') -exports.tag = tag - -class BooleanValue { - constructor (value) { - this.value = value - } - - compare (expected) { - return this.tag === expected.tag && this.value === expected.value - ? DEEP_EQUAL - : UNEQUAL - } - - formatDeep (theme) { - return lineBuilder.single(formatUtils.wrap(theme.boolean, this.value === true ? 'true' : 'false')) - } - - serialize () { - return this.value - } -} -Object.defineProperty(BooleanValue.prototype, 'isPrimitive', { value: true }) -Object.defineProperty(BooleanValue.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/primitiveValues/null.js b/node_modules/concordance/lib/primitiveValues/null.js deleted file mode 100644 index 9436ed9a1..000000000 --- a/node_modules/concordance/lib/primitiveValues/null.js +++ /dev/null @@ -1,32 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe () { - return new NullValue() -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('NullValue') -exports.tag = tag - -class NullValue { - compare (expected) { - return expected.tag === tag - ? DEEP_EQUAL - : UNEQUAL - } - - formatDeep (theme) { - return lineBuilder.single(formatUtils.wrap(theme.null, 'null')) - } -} -Object.defineProperty(NullValue.prototype, 'isPrimitive', { value: true }) -Object.defineProperty(NullValue.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/primitiveValues/number.js b/node_modules/concordance/lib/primitiveValues/number.js deleted file mode 100644 index d1dec8edb..000000000 --- a/node_modules/concordance/lib/primitiveValues/number.js +++ /dev/null @@ -1,41 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (value) { - return new NumberValue(value) -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('NumberValue') -exports.tag = tag - -class NumberValue { - constructor (value) { - this.value = value - } - - compare (expected) { - return expected.tag === tag && Object.is(this.value, expected.value) - ? DEEP_EQUAL - : UNEQUAL - } - - formatDeep (theme) { - const string = Object.is(this.value, -0) ? '-0' : String(this.value) - return lineBuilder.single(formatUtils.wrap(theme.number, string)) - } - - serialize () { - return this.value - } -} -Object.defineProperty(NumberValue.prototype, 'isPrimitive', { value: true }) -Object.defineProperty(NumberValue.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/primitiveValues/string.js b/node_modules/concordance/lib/primitiveValues/string.js deleted file mode 100644 index af120022f..000000000 --- a/node_modules/concordance/lib/primitiveValues/string.js +++ /dev/null @@ -1,306 +0,0 @@ -'use strict' - -const fastDiff = require('fast-diff') -const keyword = require('esutils').keyword - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (value) { - return new StringValue(value) -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('StringValue') -exports.tag = tag - -// TODO: Escape invisible characters (e.g. zero-width joiner, non-breaking space), -// ambiguous characters (other kinds of spaces, combining characters). Use -// http://graphemica.com/blocks/control-pictures where applicable. -function basicEscape (string) { - return string.replace(/\\/g, '\\\\') -} - -const CRLF_CONTROL_PICTURE = '\u240D\u240A' -const LF_CONTROL_PICTURE = '\u240A' -const CR_CONTROL_PICTURE = '\u240D' - -const MATCH_CONTROL_PICTURES = new RegExp(`${CR_CONTROL_PICTURE}|${LF_CONTROL_PICTURE}|${CR_CONTROL_PICTURE}`, 'g') - -function escapeLinebreak (string) { - if (string === '\r\n') return CRLF_CONTROL_PICTURE - if (string === '\n') return LF_CONTROL_PICTURE - if (string === '\r') return CR_CONTROL_PICTURE - return string -} - -function themeControlPictures (theme, resetWrap, str) { - return str.replace(MATCH_CONTROL_PICTURES, picture => { - return resetWrap.close + formatUtils.wrap(theme.string.controlPicture, picture) + resetWrap.open - }) -} - -const MATCH_SINGLE_QUOTE = /'/g -const MATCH_DOUBLE_QUOTE = /"/g -const MATCH_BACKTICKS = /`/g -function escapeQuotes (line, string) { - const quote = line.escapeQuote - if (quote === '\'') return string.replace(MATCH_SINGLE_QUOTE, "\\'") - if (quote === '"') return string.replace(MATCH_DOUBLE_QUOTE, '\\"') - if (quote === '`') return string.replace(MATCH_BACKTICKS, '\\`') - return string -} - -function includesLinebreaks (string) { - return string.includes('\r') || string.includes('\n') -} - -function diffLine (theme, actual, expected) { - const outcome = fastDiff(actual, expected) - - // TODO: Compute when line is mostly unequal (80%? 90%?) and treat it as being - // completely unequal. - const isPartiallyEqual = !( - (outcome.length === 2 && outcome[0][1] === actual && outcome[1][1] === expected) || - // Discount line ending control pictures, which will be equal even when the - // rest of the line isn't. - ( - outcome.length === 3 && - outcome[2][0] === fastDiff.EQUAL && - MATCH_CONTROL_PICTURES.test(outcome[2][1]) && - outcome[0][1] + outcome[2][1] === actual && - outcome[1][1] + outcome[2][1] === expected - ) - ) - - let stringActual = '' - let stringExpected = '' - - const noopWrap = { open: '', close: '' } - const deleteWrap = isPartiallyEqual ? theme.string.diff.delete : noopWrap - const insertWrap = isPartiallyEqual ? theme.string.diff.insert : noopWrap - const equalWrap = isPartiallyEqual ? theme.string.diff.equal : noopWrap - for (const diff of outcome) { - if (diff[0] === fastDiff.DELETE) { - stringActual += formatUtils.wrap(deleteWrap, diff[1]) - } else if (diff[0] === fastDiff.INSERT) { - stringExpected += formatUtils.wrap(insertWrap, diff[1]) - } else { - const string = formatUtils.wrap(equalWrap, themeControlPictures(theme, equalWrap, diff[1])) - stringActual += string - stringExpected += string - } - } - - if (!isPartiallyEqual) { - stringActual = formatUtils.wrap(theme.string.diff.deleteLine, stringActual) - stringExpected = formatUtils.wrap(theme.string.diff.insertLine, stringExpected) - } - - return [stringActual, stringExpected] -} - -const LINEBREAKS = /\r\n|\r|\n/g - -function gatherLines (string) { - const lines = [] - let prevIndex = 0 - for (let match; (match = LINEBREAKS.exec(string)); prevIndex = match.index + match[0].length) { - lines.push(string.slice(prevIndex, match.index) + escapeLinebreak(match[0])) - } - lines.push(string.slice(prevIndex)) - return lines -} - -class StringValue { - constructor (value) { - this.value = value - } - - compare (expected) { - return expected.tag === tag && this.value === expected.value - ? DEEP_EQUAL - : UNEQUAL - } - - get includesLinebreaks () { - return includesLinebreaks(this.value) - } - - formatDeep (theme, indent) { - // Escape backslashes - let escaped = basicEscape(this.value) - - if (!this.includesLinebreaks) { - escaped = escapeQuotes(theme.string.line, escaped) - return lineBuilder.single(formatUtils.wrap(theme.string.line, formatUtils.wrap(theme.string, escaped))) - } - - escaped = escapeQuotes(theme.string.multiline, escaped) - const lineStrings = gatherLines(escaped).map(string => { - return formatUtils.wrap(theme.string, themeControlPictures(theme, theme.string, string)) - }) - const lastIndex = lineStrings.length - 1 - const indentation = indent - return lineBuilder.buffer() - .append( - lineStrings.map((string, index) => { - if (index === 0) return lineBuilder.first(theme.string.multiline.start + string) - if (index === lastIndex) return lineBuilder.last(indentation + string + theme.string.multiline.end) - return lineBuilder.line(indentation + string) - })) - } - - formatAsKey (theme) { - const key = this.value - if (keyword.isIdentifierNameES6(key, true) || String(parseInt(key, 10)) === key) { - return key - } - - const escaped = basicEscape(key) - .replace(/\n/g, '\\n') - .replace(/\r/g, '\\r') - .replace(/'/g, "\\'") - return formatUtils.wrap(theme.string.line, formatUtils.wrap(theme.string, escaped)) - } - - diffDeep (expected, theme, indent) { - if (expected.tag !== tag) return null - - const escapedActual = basicEscape(this.value) - const escapedExpected = basicEscape(expected.value) - - if (!includesLinebreaks(escapedActual) && !includesLinebreaks(escapedExpected)) { - const result = diffLine(theme, - escapeQuotes(theme.string.line, escapedActual), - escapeQuotes(theme.string.line, escapedExpected)) - - return lineBuilder.actual.single(formatUtils.wrap(theme.string.line, result[0])) - .concat(lineBuilder.expected.single(formatUtils.wrap(theme.string.line, result[1]))) - } - - const actualLines = gatherLines(escapeQuotes(theme.string.multiline, escapedActual)) - const expectedLines = gatherLines(escapeQuotes(theme.string.multiline, escapedExpected)) - - const indentation = indent - const lines = lineBuilder.buffer() - const lastActualIndex = actualLines.length - 1 - const lastExpectedIndex = expectedLines.length - 1 - - let actualBuffer = [] - let expectedBuffer = [] - let mustOpenNextExpected = false - for (let actualIndex = 0, expectedIndex = 0, extraneousOffset = 0; actualIndex < actualLines.length;) { - if (actualLines[actualIndex] === expectedLines[expectedIndex]) { - lines.append(actualBuffer) - lines.append(expectedBuffer) - actualBuffer = [] - expectedBuffer = [] - - let string = actualLines[actualIndex] - string = themeControlPictures(theme, theme.string.diff.equal, string) - string = formatUtils.wrap(theme.string.diff.equal, string) - - if (actualIndex === 0) { - lines.append(lineBuilder.first(theme.string.multiline.start + string)) - } else if (actualIndex === lastActualIndex && expectedIndex === lastExpectedIndex) { - lines.append(lineBuilder.last(indentation + string + theme.string.multiline.end)) - } else { - lines.append(lineBuilder.line(indentation + string)) - } - - actualIndex++ - expectedIndex++ - continue - } - - let expectedIsMissing = false - { - const compare = actualLines[actualIndex] - for (let index = expectedIndex; !expectedIsMissing && index < expectedLines.length; index++) { - expectedIsMissing = compare === expectedLines[index] - } - } - - let actualIsExtraneous = (actualIndex - extraneousOffset) > lastExpectedIndex - if (!actualIsExtraneous) { - const compare = expectedLines[expectedIndex] - for (let index = actualIndex; !actualIsExtraneous && index < actualLines.length; index++) { - actualIsExtraneous = compare === actualLines[index] - } - - if (!actualIsExtraneous && (actualIndex - extraneousOffset) === lastExpectedIndex && actualIndex < lastActualIndex) { - actualIsExtraneous = true - } - } - - if (actualIsExtraneous && !expectedIsMissing) { - const string = formatUtils.wrap(theme.string.diff.deleteLine, actualLines[actualIndex]) - - if (actualIndex === 0) { - actualBuffer.push(lineBuilder.actual.first(theme.string.multiline.start + string)) - mustOpenNextExpected = true - } else if (actualIndex === lastActualIndex) { - actualBuffer.push(lineBuilder.actual.last(indentation + string + theme.string.multiline.end)) - } else { - actualBuffer.push(lineBuilder.actual.line(indentation + string)) - } - - actualIndex++ - extraneousOffset++ - } else if (expectedIsMissing && !actualIsExtraneous) { - const string = formatUtils.wrap(theme.string.diff.insertLine, expectedLines[expectedIndex]) - - if (mustOpenNextExpected) { - expectedBuffer.push(lineBuilder.expected.first(theme.string.multiline.start + string)) - mustOpenNextExpected = false - } else if (expectedIndex === lastExpectedIndex) { - expectedBuffer.push(lineBuilder.expected.last(indentation + string + theme.string.multiline.end)) - } else { - expectedBuffer.push(lineBuilder.expected.line(indentation + string)) - } - - expectedIndex++ - } else { - const result = diffLine(theme, actualLines[actualIndex], expectedLines[expectedIndex]) - - if (actualIndex === 0) { - actualBuffer.push(lineBuilder.actual.first(theme.string.multiline.start + result[0])) - mustOpenNextExpected = true - } else if (actualIndex === lastActualIndex) { - actualBuffer.push(lineBuilder.actual.last(indentation + result[0] + theme.string.multiline.end)) - } else { - actualBuffer.push(lineBuilder.actual.line(indentation + result[0])) - } - - if (mustOpenNextExpected) { - expectedBuffer.push(lineBuilder.expected.first(theme.string.multiline.start + result[1])) - mustOpenNextExpected = false - } else if (expectedIndex === lastExpectedIndex) { - expectedBuffer.push(lineBuilder.expected.last(indentation + result[1] + theme.string.multiline.end)) - } else { - expectedBuffer.push(lineBuilder.expected.line(indentation + result[1])) - } - - actualIndex++ - expectedIndex++ - } - } - - lines.append(actualBuffer) - lines.append(expectedBuffer) - return lines - } - - serialize () { - return this.value - } -} -Object.defineProperty(StringValue.prototype, 'isPrimitive', { value: true }) -Object.defineProperty(StringValue.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/primitiveValues/symbol.js b/node_modules/concordance/lib/primitiveValues/symbol.js deleted file mode 100644 index 3778b4118..000000000 --- a/node_modules/concordance/lib/primitiveValues/symbol.js +++ /dev/null @@ -1,114 +0,0 @@ -'use strict' - -const stringEscape = require('js-string-escape') -const wellKnownSymbols = require('well-known-symbols') - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe (value) { - let stringCompare = null - - const key = Symbol.keyFor(value) - if (key !== undefined) { - stringCompare = `Symbol.for(${stringEscape(key)})` - } else if (wellKnownSymbols.isWellKnown(value)) { - stringCompare = wellKnownSymbols.getLabel(value) - } - - return new SymbolValue({ - stringCompare, - value - }) -} -exports.describe = describe - -function deserialize (state) { - const stringCompare = state[0] - const string = state[1] || state[0] - - return new DeserializedSymbolValue({ - string, - stringCompare, - value: null - }) -} -exports.deserialize = deserialize - -const tag = Symbol('SymbolValue') -exports.tag = tag - -class SymbolValue { - constructor (props) { - this.stringCompare = props.stringCompare - this.value = props.value - } - - compare (expected) { - if (expected.tag !== tag) return UNEQUAL - - if (this.stringCompare !== null) { - return this.stringCompare === expected.stringCompare - ? DEEP_EQUAL - : UNEQUAL - } - - return this.value === expected.value - ? DEEP_EQUAL - : UNEQUAL - } - - formatString () { - if (this.stringCompare !== null) return this.stringCompare - return stringEscape(this.value.toString()) - } - - formatDeep (theme) { - return lineBuilder.single(formatUtils.wrap(theme.symbol, this.formatString())) - } - - formatAsKey (theme) { - return formatUtils.wrap(theme.property.keyBracket, formatUtils.wrap(theme.symbol, this.formatString())) - } - - serialize () { - const string = this.formatString() - return this.stringCompare === string - ? [this.stringCompare] - : [this.stringCompare, string] - } -} -Object.defineProperty(SymbolValue.prototype, 'isPrimitive', { value: true }) -Object.defineProperty(SymbolValue.prototype, 'tag', { value: tag }) - -class DeserializedSymbolValue extends SymbolValue { - constructor (props) { - super(props) - this.string = props.string - } - - compare (expected) { - if (expected.tag !== tag) return UNEQUAL - - if (this.stringCompare !== null) { - return this.stringCompare === expected.stringCompare - ? DEEP_EQUAL - : UNEQUAL - } - - // Symbols that are not in the global symbol registry, and are not - // well-known, cannot be compared when deserialized. Treat symbols - // as equal if they are formatted the same. - return this.string === expected.formatString() - ? DEEP_EQUAL - : UNEQUAL - } - - formatString () { - return this.string - } -} diff --git a/node_modules/concordance/lib/primitiveValues/undefined.js b/node_modules/concordance/lib/primitiveValues/undefined.js deleted file mode 100644 index 507556e61..000000000 --- a/node_modules/concordance/lib/primitiveValues/undefined.js +++ /dev/null @@ -1,32 +0,0 @@ -'use strict' - -const constants = require('../constants') -const formatUtils = require('../formatUtils') -const lineBuilder = require('../lineBuilder') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const UNEQUAL = constants.UNEQUAL - -function describe () { - return new UndefinedValue() -} -exports.describe = describe - -exports.deserialize = describe - -const tag = Symbol('UndefinedValue') -exports.tag = tag - -class UndefinedValue { - compare (expected) { - return expected.tag === tag - ? DEEP_EQUAL - : UNEQUAL - } - - formatDeep (theme) { - return lineBuilder.single(formatUtils.wrap(theme.undefined, 'undefined')) - } -} -Object.defineProperty(UndefinedValue.prototype, 'isPrimitive', { value: true }) -Object.defineProperty(UndefinedValue.prototype, 'tag', { value: tag }) diff --git a/node_modules/concordance/lib/recursorUtils.js b/node_modules/concordance/lib/recursorUtils.js deleted file mode 100644 index ff639b5b8..000000000 --- a/node_modules/concordance/lib/recursorUtils.js +++ /dev/null @@ -1,110 +0,0 @@ -'use strict' - -const NOOP_RECURSOR = { - size: 0, - next () { return null } -} -exports.NOOP_RECURSOR = NOOP_RECURSOR - -function fork (recursor) { - const buffer = [] - - return { - shared () { - const next = recursor() - if (next !== null) buffer.push(next) - return next - }, - - recursor () { - if (buffer.length > 0) return buffer.shift() - return recursor() - } - } -} -exports.fork = fork - -function map (recursor, mapFn) { - return () => { - const next = recursor() - if (next === null) return null - - return mapFn(next) - } -} -exports.map = map - -function replay (state, create) { - if (!state) { - const recursor = create() - if (recursor === NOOP_RECURSOR) { - state = recursor - } else { - state = Object.assign({ - buffer: [], - done: false - }, recursor) - } - } - - if (state === NOOP_RECURSOR) return {state, recursor: state} - - let done = false - let index = 0 - const next = () => { - if (done) return null - - let retval = state.buffer[index] - if (retval === undefined) { - retval = state.buffer[index] = state.next() - } - - index++ - if (retval === null) { - done = true - } - return retval - } - - return {state, recursor: {next, size: state.size}} -} -exports.replay = replay - -function sequence (first, second) { - let fromFirst = true - return () => { - if (fromFirst) { - const next = first() - if (next !== null) return next - - fromFirst = false - } - - return second() - } -} -exports.sequence = sequence - -function singleValue (value) { - let done = false - return () => { - if (done) return null - - done = true - return value - } -} -exports.singleValue = singleValue - -function unshift (recursor, value) { - return () => { - if (value !== null) { - const next = value - value = null - return next - } - - return recursor() - } -} -exports.unshift = unshift diff --git a/node_modules/concordance/lib/serialize.js b/node_modules/concordance/lib/serialize.js deleted file mode 100644 index 07f568415..000000000 --- a/node_modules/concordance/lib/serialize.js +++ /dev/null @@ -1,339 +0,0 @@ -'use strict' - -const md5hex = require('md5-hex') - -const encoder = require('./encoder') -const pluginRegistry = require('./pluginRegistry') - -const argumentsValue = require('./complexValues/arguments') -const arrayBufferValue = require('./complexValues/arrayBuffer') -const boxedValue = require('./complexValues/boxed') -const dataViewValue = require('./complexValues/dataView') -const dateValue = require('./complexValues/date') -const errorValue = require('./complexValues/error') -const functionValue = require('./complexValues/function') -const globalValue = require('./complexValues/global') -const mapValue = require('./complexValues/map') -const objectValue = require('./complexValues/object') -const promiseValue = require('./complexValues/promise') -const regexpValue = require('./complexValues/regexp') -const setValue = require('./complexValues/set') -const typedArrayValue = require('./complexValues/typedArray') - -const itemDescriptor = require('./metaDescriptors/item') -const mapEntryDescriptor = require('./metaDescriptors/mapEntry') -const pointerDescriptor = require('./metaDescriptors/pointer') -const propertyDescriptor = require('./metaDescriptors/property') -const statsDescriptors = require('./metaDescriptors/stats') - -const booleanValue = require('./primitiveValues/boolean') -const nullValue = require('./primitiveValues/null') -const numberValue = require('./primitiveValues/number') -const stringValue = require('./primitiveValues/string') -const symbolValue = require('./primitiveValues/symbol') -const undefinedValue = require('./primitiveValues/undefined') - -// Increment if encoding layout, descriptor IDs, or value types change. Previous -// Concordance versions will not be able to decode buffers generated by a newer -// version, so changing this value will require a major version bump of -// Concordance itself. The version is encoded as an unsigned 16 bit integer. -const VERSION = 2 - -// Adding or removing mappings or changing an index requires the version in -// encoder.js to be bumped, which necessitates a major version bump of -// Concordance itself. Indexes are hexadecimal to make reading the binary -// output easier. -const mappings = [ - [0x01, booleanValue.tag, booleanValue.deserialize], - [0x02, nullValue.tag, nullValue.deserialize], - [0x03, numberValue.tag, numberValue.deserialize], - [0x04, stringValue.tag, stringValue.deserialize], - [0x05, symbolValue.tag, symbolValue.deserialize], - [0x06, undefinedValue.tag, undefinedValue.deserialize], - - [0x07, objectValue.tag, objectValue.deserialize], - [0x08, statsDescriptors.iterableTag, statsDescriptors.deserializeIterableStats], - [0x09, statsDescriptors.listTag, statsDescriptors.deserializeListStats], - [0x0A, itemDescriptor.complexTag, itemDescriptor.deserializeComplex], - [0x0B, itemDescriptor.primitiveTag, itemDescriptor.deserializePrimitive], - [0x0C, statsDescriptors.propertyTag, statsDescriptors.deserializePropertyStats], - [0x0D, propertyDescriptor.complexTag, propertyDescriptor.deserializeComplex], - [0x0E, propertyDescriptor.primitiveTag, propertyDescriptor.deserializePrimitive], - [0x0F, pointerDescriptor.tag, pointerDescriptor.deserialize], - - [0x10, mapValue.tag, mapValue.deserialize], - [0x11, mapEntryDescriptor.tag, mapEntryDescriptor.deserialize], - - [0x12, argumentsValue.tag, argumentsValue.deserialize], - [0x13, arrayBufferValue.tag, arrayBufferValue.deserialize], - [0x14, boxedValue.tag, boxedValue.deserialize], - [0x15, dataViewValue.tag, dataViewValue.deserialize], - [0x16, dateValue.tag, dateValue.deserialize], - [0x17, errorValue.tag, errorValue.deserialize], - [0x18, functionValue.tag, functionValue.deserialize], - [0x19, globalValue.tag, globalValue.deserialize], - [0x1A, promiseValue.tag, promiseValue.deserialize], - [0x1B, regexpValue.tag, regexpValue.deserialize], - [0x1C, setValue.tag, setValue.deserialize], - [0x1D, typedArrayValue.tag, typedArrayValue.deserialize], - [0x1E, typedArrayValue.bytesTag, typedArrayValue.deserializeBytes] -] -const tag2id = new Map(mappings.map(mapping => [mapping[1], mapping[0]])) -const id2deserialize = new Map(mappings.map(mapping => [mapping[0], mapping[2]])) - -class DescriptorSerializationError extends Error { - constructor (descriptor) { - super('Could not serialize descriptor') - this.name = 'DescriptorSerializationError' - this.descriptor = descriptor - } -} - -class MissingPluginError extends Error { - constructor (pluginName) { - super(`Could not deserialize buffer: missing plugin ${JSON.stringify(pluginName)}`) - this.name = 'MissingPluginError' - this.pluginName = pluginName - } -} - -class PointerLookupError extends Error { - constructor (index) { - super(`Could not deserialize buffer: pointer ${index} could not be resolved`) - this.name = 'PointerLookupError' - this.index = index - } -} - -class UnsupportedPluginError extends Error { - constructor (pluginName, serializerVersion) { - super(`Could not deserialize buffer: plugin ${JSON.stringify(pluginName)} expects a different serialization`) - this.name = 'UnsupportedPluginError' - this.pluginName = pluginName - this.serializerVersion = serializerVersion - } -} - -class UnsupportedVersion extends Error { - constructor (serializerVersion) { - super('Could not deserialize buffer: a different serialization was expected') - this.name = 'UnsupportedVersion' - this.serializerVersion = serializerVersion - } -} - -function shallowSerializeDescriptor (descriptor, resolvePluginRef) { - if (!descriptor.serialize) return undefined - - return serializeState(descriptor.serialize(), resolvePluginRef) -} - -function serializeState (state, resolvePluginRef) { - if (Array.isArray(state)) return state.map(serializeState) - - if (state && state.tag) { - let id, pluginIndex - if (tag2id.has(state.tag)) { - id = tag2id.get(state.tag) - pluginIndex = 0 - } else { - const ref = resolvePluginRef(state.tag) - if (ref) { - id = ref.id - pluginIndex = ref.pluginIndex - } - } - - if (id !== undefined) { - const serialized = [pluginIndex, id, shallowSerializeDescriptor(state, resolvePluginRef)] - serialized[encoder.descriptorSymbol] = true - return serialized - } - } - - return state -} - -function serialize (descriptor) { - const usedPlugins = new Map() - const resolvePluginRef = tag => { - const ref = pluginRegistry.resolveDescriptorRef(tag) - if (!ref) return null - - if (!usedPlugins.has(ref.name)) { - // Start at 1, since 0 is reserved for Concordance's descriptors. - const index = usedPlugins.size + 1 - usedPlugins.set(ref.name, Object.assign({index}, ref.serialization)) - } - - return { - id: ref.id, - pluginIndex: usedPlugins.get(ref.name).index - } - } - - const seen = new Set() - - const stack = [] - let topIndex = -1 - - let rootRecord - do { - if (descriptor.isComplex === true) { - if (seen.has(descriptor.pointer)) { - descriptor = pointerDescriptor.describe(descriptor.pointer) - } else { - seen.add(descriptor.pointer) - } - } - - let id - let pluginIndex = 0 - if (tag2id.has(descriptor.tag)) { - id = tag2id.get(descriptor.tag) - } else { - const ref = resolvePluginRef(descriptor.tag) - if (!ref) throw new DescriptorSerializationError(descriptor) - - id = ref.id - pluginIndex = ref.pluginIndex - } - - const record = { - id, - pluginIndex, - children: [], - state: shallowSerializeDescriptor(descriptor, resolvePluginRef) - } - if (!rootRecord) { - rootRecord = record - } else { - stack[topIndex].children.push(record) - } - - if (descriptor.createRecursor) { - stack.push({ recursor: descriptor.createRecursor(), children: record.children }) - topIndex++ - } - - while (topIndex >= 0) { - descriptor = stack[topIndex].recursor() - if (descriptor === null) { - stack.pop() - topIndex-- - } else { - break - } - } - } while (topIndex >= 0) - - return encoder.encode(VERSION, rootRecord, usedPlugins) -} -exports.serialize = serialize - -function deserializeState (state, getDescriptorDeserializer) { - if (state && state[encoder.descriptorSymbol] === true) { - return shallowDeserializeDescriptor(state, getDescriptorDeserializer) - } - - return Array.isArray(state) - ? state.map(item => deserializeState(item, getDescriptorDeserializer)) - : state -} - -function shallowDeserializeDescriptor (entry, getDescriptorDeserializer) { - const deserializeDescriptor = getDescriptorDeserializer(entry[0], entry[1]) - return deserializeDescriptor(entry[2]) -} - -function deserializeRecord (record, getDescriptorDeserializer, buffer) { - const deserializeDescriptor = getDescriptorDeserializer(record.pluginIndex, record.id) - const state = deserializeState(record.state, getDescriptorDeserializer) - - if (record.pointerAddresses.length === 0) { - return deserializeDescriptor(state) - } - - const endIndex = record.pointerAddresses.length - let index = 0 - const recursor = () => { - if (index === endIndex) return null - - const recursorRecord = encoder.decodeRecord(buffer, record.pointerAddresses[index++]) - return deserializeRecord(recursorRecord, getDescriptorDeserializer, buffer) - } - - return deserializeDescriptor(state, recursor) -} - -function buildPluginMap (buffer, options) { - const cache = options && options.deserializedPluginsCache - const cacheKey = md5hex(buffer) - if (cache && cache.has(cacheKey)) return cache.get(cacheKey) - - const decodedPlugins = encoder.decodePlugins(buffer) - if (decodedPlugins.size === 0) { - const pluginMap = new Map() - if (cache) cache.set(cacheKey, pluginMap) - return pluginMap - } - - const deserializerLookup = new Map() - if (Array.isArray(options && options.plugins)) { - for (const deserializer of pluginRegistry.getDeserializers(options.plugins)) { - deserializerLookup.set(deserializer.name, deserializer) - } - } - - const pluginMap = new Map() - for (const index of decodedPlugins.keys()) { - const used = decodedPlugins.get(index) - const pluginName = used.name - const serializerVersion = used.serializerVersion - - // TODO: Allow plugin author to encode a helpful message in its serialization - if (!deserializerLookup.has(pluginName)) { - throw new MissingPluginError(pluginName) - } - if (serializerVersion !== deserializerLookup.get(pluginName).serializerVersion) { - throw new UnsupportedPluginError(pluginName, serializerVersion) - } - - pluginMap.set(index, deserializerLookup.get(pluginName).id2deserialize) - } - - if (cache) cache.set(cacheKey, pluginMap) - return pluginMap -} - -function deserialize (buffer, options) { - const version = encoder.extractVersion(buffer) - if (version !== VERSION) throw new UnsupportedVersion(version) - - const decoded = encoder.decode(buffer) - const pluginMap = buildPluginMap(decoded.pluginBuffer, options) - - const descriptorsByPointerIndex = new Map() - const mapPointerDescriptor = descriptor => { - if (descriptor.isPointer === true) { - if (!descriptorsByPointerIndex.has(descriptor.index)) throw new PointerLookupError(descriptor.index) - - return descriptorsByPointerIndex.get(descriptor.index) - } else if (descriptor.isComplex === true) { - descriptorsByPointerIndex.set(descriptor.pointer, descriptor) - } - return descriptor - } - - const getDescriptorDeserializer = (pluginIndex, id) => { - return (state, recursor) => { - const deserializeDescriptor = pluginIndex === 0 - ? id2deserialize.get(id) - : pluginMap.get(pluginIndex).get(id) - - return mapPointerDescriptor(deserializeDescriptor(state, recursor)) - } - } - return deserializeRecord(decoded.rootRecord, getDescriptorDeserializer, buffer) -} -exports.deserialize = deserialize diff --git a/node_modules/concordance/lib/shouldCompareDeep.js b/node_modules/concordance/lib/shouldCompareDeep.js deleted file mode 100644 index a59135507..000000000 --- a/node_modules/concordance/lib/shouldCompareDeep.js +++ /dev/null @@ -1,17 +0,0 @@ -'use strict' - -const argumentsObject = require('./complexValues/arguments').tag -const constants = require('./constants') - -const AMBIGUOUS = constants.AMBIGUOUS -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL - -function shouldCompareDeep (result, lhs, rhs) { - if (result === SHALLOW_EQUAL) return true - if (result !== AMBIGUOUS) return false - - // Properties are only ambiguous if they have symbol keys. These properties - // must be compared in an order-insensitive manner. - return lhs.tag === argumentsObject || lhs.isProperty === true -} -module.exports = shouldCompareDeep diff --git a/node_modules/concordance/lib/symbolProperties.js b/node_modules/concordance/lib/symbolProperties.js deleted file mode 100644 index 623a428fc..000000000 --- a/node_modules/concordance/lib/symbolProperties.js +++ /dev/null @@ -1,106 +0,0 @@ -'use strict' - -const constants = require('./constants') -const recursorUtils = require('./recursorUtils') - -const DEEP_EQUAL = constants.DEEP_EQUAL -const SHALLOW_EQUAL = constants.SHALLOW_EQUAL -const UNEQUAL = constants.UNEQUAL - -class Comparable { - constructor (properties) { - this.properties = properties - this.ordered = properties.slice() - } - - createRecursor () { - const length = this.ordered.length - let index = 0 - return () => { - if (index === length) return null - - return this.ordered[index++] - } - } - - compare (expected) { - if (this.properties.length !== expected.properties.length) return UNEQUAL - - // Compare property keys, reordering the expected properties in the process - // so values can be compared if all keys are equal. - const ordered = [] - const processed = new Set() - for (const property of this.properties) { - let extraneous = true - for (const other of expected.properties) { - if (processed.has(other.key)) continue - - if (property.key.compare(other.key) === DEEP_EQUAL) { - extraneous = false - processed.add(other.key) - ordered.push(other) - break - } - } - - if (extraneous) return UNEQUAL - } - expected.ordered = ordered - - return SHALLOW_EQUAL - } - - prepareDiff (expected) { - // Reorder the expected properties before recursion starts. - const missingProperties = [] - const ordered = [] - const processed = new Set() - for (const other of expected.properties) { - let missing = true - for (const property of this.properties) { - if (processed.has(property.key)) continue - - if (property.key.compare(other.key) === DEEP_EQUAL) { - missing = false - processed.add(property.key) - ordered.push(other) - break - } - } - - if (missing) { - missingProperties.push(other) - } - } - expected.ordered = ordered.concat(missingProperties) - - return {mustRecurse: true} - } -} -Object.defineProperty(Comparable.prototype, 'isSymbolPropertiesComparable', { value: true }) -exports.Comparable = Comparable - -class Collector { - constructor (firstProperty, recursor) { - this.properties = [firstProperty] - this.recursor = recursor - this.remainder = null - } - - collectAll () { - do { - const next = this.recursor() - if (next && next.isProperty === true) { // All properties will have symbol keys - this.properties.push(next) - } else { - return next - } - } while (true) - } - - createRecursor () { - return recursorUtils.singleValue(new Comparable(this.properties)) - } -} -Object.defineProperty(Collector.prototype, 'isSymbolPropertiesCollector', { value: true }) -exports.Collector = Collector diff --git a/node_modules/concordance/lib/themeUtils.js b/node_modules/concordance/lib/themeUtils.js deleted file mode 100644 index a0a64b586..000000000 --- a/node_modules/concordance/lib/themeUtils.js +++ /dev/null @@ -1,195 +0,0 @@ -'use strict' - -const cloneDeep = require('lodash.clonedeep') -const merge = require('lodash.merge') - -const pluginRegistry = require('./pluginRegistry') - -function freezeTheme (theme) { - const queue = [theme] - while (queue.length > 0) { - const object = queue.shift() - Object.freeze(object) - - for (const key of Object.keys(object)) { - const value = object[key] - if (value !== null && typeof value === 'object') { - queue.push(value) - } - } - } - - return theme -} - -const defaultTheme = freezeTheme({ - boolean: { open: '', close: '' }, - circular: '[Circular]', - date: { - invalid: 'invalid', - value: { open: '', close: '' } - }, - diffGutters: { - actual: '- ', - expected: '+ ', - padding: ' ' - }, - error: { - ctor: { open: '(', close: ')' }, - name: { open: '', close: '' } - }, - function: { - name: { open: '', close: '' }, - stringTag: { open: '', close: '' } - }, - global: { open: '', close: '' }, - item: { - after: ',', - customFormat: null, - increaseValueIndent: false - }, - list: { openBracket: '[', closeBracket: ']' }, - mapEntry: { - after: ',', - separator: ' => ' - }, - maxDepth: '…', - null: { open: '', close: '' }, - number: { open: '', close: '' }, - object: { - openBracket: '{', - closeBracket: '}', - ctor: { open: '', close: '' }, - stringTag: { open: '@', close: '' }, - secondaryStringTag: { open: '@', close: '' } - }, - property: { - after: ',', - customFormat: null, - keyBracket: { open: '[', close: ']' }, - separator: ': ', - increaseValueIndent: false - }, - regexp: { - source: { open: '/', close: '/' }, - flags: { open: '', close: '' }, - separator: '---' - }, - stats: { separator: '---' }, - string: { - open: '', - close: '', - line: { open: "'", close: "'", escapeQuote: "'" }, - multiline: { start: '`', end: '`', escapeQuote: '``' }, - controlPicture: { open: '', close: '' }, - diff: { - insert: { open: '', close: '' }, - delete: { open: '', close: '' }, - equal: { open: '', close: '' }, - insertLine: { open: '', close: '' }, - deleteLine: { open: '', close: '' } - } - }, - symbol: { open: '', close: '' }, - typedArray: { - bytes: { open: '', close: '' } - }, - undefined: { open: '', close: '' } -}) - -const pluginRefs = new Map() -pluginRefs.count = 0 -const normalizedPluginThemes = new Map() -function normalizePlugins (plugins) { - if (!Array.isArray(plugins) || plugins.length === 0) return null - - const refs = [] - const themes = [] - for (const fromPlugin of pluginRegistry.getThemes(plugins)) { - if (!pluginRefs.has(fromPlugin.name)) { - pluginRefs.set(fromPlugin.name, pluginRefs.count++) - } - - refs.push(pluginRefs.get(fromPlugin.name)) - themes.push(fromPlugin.theme) - } - - const ref = refs.join('.') - if (normalizedPluginThemes.has(ref)) { - return { - ref, - theme: normalizedPluginThemes.get(ref) - } - } - - const theme = freezeTheme(themes.reduce((acc, pluginTheme) => { - return merge(acc, pluginTheme) - }, cloneDeep(defaultTheme))) - normalizedPluginThemes.set(ref, theme) - return {ref, theme} -} - -const normalizedCache = new WeakMap() -function normalize (options) { - options = Object.assign({plugins: [], theme: null}, options) - - const normalizedPlugins = normalizePlugins(options.plugins) - if (!options.theme) { - return normalizedPlugins ? normalizedPlugins.theme : defaultTheme - } - - const entry = normalizedCache.get(options.theme) || {theme: null, withPlugins: new Map()} - if (!normalizedCache.has(options.theme)) normalizedCache.set(options.theme, entry) - - if (normalizedPlugins) { - if (entry.withPlugins.has(normalizedPlugins.ref)) { - return entry.withPlugins.get(normalizedPlugins.ref) - } - - const theme = freezeTheme(merge(cloneDeep(normalizedPlugins.theme), options.theme)) - entry.withPlugins.set(normalizedPlugins.ref, theme) - return theme - } - - if (!entry.theme) { - entry.theme = freezeTheme(merge(cloneDeep(defaultTheme), options.theme)) - } - return entry.theme -} -exports.normalize = normalize - -const modifiers = new WeakMap() -function addModifier (descriptor, modifier) { - if (modifiers.has(descriptor)) { - modifiers.get(descriptor).add(modifier) - } else { - modifiers.set(descriptor, new Set([modifier])) - } -} -exports.addModifier = addModifier - -const modifierCache = new WeakMap() -const originalCache = new WeakMap() -function applyModifiers (descriptor, theme) { - if (!modifiers.has(descriptor)) return theme - - return Array.from(modifiers.get(descriptor)).reduce((prev, modifier) => { - const cache = modifierCache.get(modifier) || new WeakMap() - if (!modifierCache.has(modifier)) modifierCache.set(modifier, cache) - - if (cache.has(prev)) return cache.get(prev) - - const modifiedTheme = cloneDeep(prev) - modifier(modifiedTheme) - freezeTheme(modifiedTheme) - cache.set(prev, modifiedTheme) - originalCache.set(modifiedTheme, theme) - return modifiedTheme - }, theme) -} -exports.applyModifiers = applyModifiers - -function applyModifiersToOriginal (descriptor, theme) { - return applyModifiers(descriptor, originalCache.get(theme) || theme) -} -exports.applyModifiersToOriginal = applyModifiersToOriginal |