From b466d1c227c79939fb0e91176645c2e364456531 Mon Sep 17 00:00:00 2001 From: Molly Lloyd Date: Tue, 20 Nov 2018 15:33:24 -0800 Subject: [PATCH 1/2] add validation option to style setters --- src/style/light.js | 14 +++-- src/style/style.js | 16 +++--- src/style/style_layer.js | 6 +- src/ui/map.js | 25 ++++++--- test/unit/style/light.test.js | 39 +++++++++++-- test/unit/style/style.test.js | 103 ++++++++++++++++++++++++++++++++++ 6 files changed, 174 insertions(+), 29 deletions(-) diff --git a/src/style/light.js b/src/style/light.js index 2ed7f92e00b..7de9ba793f2 100644 --- a/src/style/light.js +++ b/src/style/light.js @@ -86,13 +86,13 @@ class Light extends Evented { return this._transitionable.serialize(); } - setLight(options?: LightSpecification) { - if (this._validate(validateLight, options)) { + setLight(light?: LightSpecification, options?: {validate?: boolean}) { + if (this._validate(validateLight, light, options)) { return; } - for (const name in options) { - const value = options[name]; + for (const name in light) { + const value = light[name]; if (endsWith(name, TRANSITION_SUFFIX)) { this._transitionable.setTransition(name.slice(0, -TRANSITION_SUFFIX.length), value); } else { @@ -113,7 +113,11 @@ class Light extends Evented { this.properties = this._transitioning.possiblyEvaluate(parameters); } - _validate(validate: Function, value: mixed) { + _validate(validate: Function, value: mixed, options?: {validate?: boolean}) { + if (options && options.validate === false) { + return false; + } + return emitValidationErrors(this, validate.call(validateStyle, extend({ value, // Workaround for https://github.com/mapbox/mapbox-gl-js/issues/2407 diff --git a/src/style/style.js b/src/style/style.js index ec55b10b8a5..05b31bd6217 100644 --- a/src/style/style.js +++ b/src/style/style.js @@ -733,7 +733,7 @@ class Style extends Evented { this._updateLayer(layer); } - setFilter(layerId: string, filter: ?FilterSpecification) { + setFilter(layerId: string, filter: ?FilterSpecification, options?: {validate?: boolean}) { this._checkLoaded(); const layer = this.getLayer(layerId); @@ -752,7 +752,7 @@ class Style extends Evented { return; } - if (this._validate(validateStyle.filter, `layers.${layer.id}.filter`, filter)) { + if (this._validate(validateStyle.filter, `layers.${layer.id}.filter`, filter, null, options)) { return; } @@ -769,7 +769,7 @@ class Style extends Evented { return clone(this.getLayer(layer).filter); } - setLayoutProperty(layerId: string, name: string, value: any) { + setLayoutProperty(layerId: string, name: string, value: any, options?: {validate?: boolean}) { this._checkLoaded(); const layer = this.getLayer(layerId); @@ -780,7 +780,7 @@ class Style extends Evented { if (deepEqual(layer.getLayoutProperty(name), value)) return; - layer.setLayoutProperty(name, value); + layer.setLayoutProperty(name, value, options); this._updateLayer(layer); } @@ -800,7 +800,7 @@ class Style extends Evented { return layer.getLayoutProperty(name); } - setPaintProperty(layerId: string, name: string, value: any) { + setPaintProperty(layerId: string, name: string, value: any, options?: {validate?: boolean}) { this._checkLoaded(); const layer = this.getLayer(layerId); @@ -811,7 +811,7 @@ class Style extends Evented { if (deepEqual(layer.getPaintProperty(name), value)) return; - const requiresRelayout = layer.setPaintProperty(name, value); + const requiresRelayout = layer.setPaintProperty(name, value, options); if (requiresRelayout) { this._updateLayer(layer); } @@ -1001,7 +1001,7 @@ class Style extends Evented { return this.light.getLight(); } - setLight(lightOptions: LightSpecification) { + setLight(lightOptions: LightSpecification, options?: {validate?: boolean}) { this._checkLoaded(); const light = this.light.getLight(); @@ -1022,7 +1022,7 @@ class Style extends Evented { }, this.stylesheet.transition) }; - this.light.setLight(lightOptions); + this.light.setLight(lightOptions, options); this.light.updateTransitions(parameters); } diff --git a/src/style/style_layer.js b/src/style/style_layer.js index 88d6acf4b39..6c8834c3889 100644 --- a/src/style/style_layer.js +++ b/src/style/style_layer.js @@ -115,7 +115,7 @@ class StyleLayer extends Evented { return this._unevaluatedLayout.getValue(name); } - setLayoutProperty(name: string, value: mixed, options: {validate: boolean}) { + setLayoutProperty(name: string, value: mixed, options?: {validate?: boolean}) { if (value !== null && value !== undefined) { const key = `layers.${this.id}.layout.${name}`; if (this._validate(validateLayoutProperty, key, name, value, options)) { @@ -139,7 +139,7 @@ class StyleLayer extends Evented { } } - setPaintProperty(name: string, value: mixed, options: {validate: boolean}) { + setPaintProperty(name: string, value: mixed, options?: {validate?: boolean}) { if (value !== null && value !== undefined) { const key = `layers.${this.id}.paint.${name}`; if (this._validate(validatePaintProperty, key, name, value, options)) { @@ -221,7 +221,7 @@ class StyleLayer extends Evented { }); } - _validate(validate: Function, key: string, name: string, value: mixed, options: {validate: boolean}) { + _validate(validate: Function, key: string, name: string, value: mixed, options?: {validate?: boolean}) { if (options && options.validate === false) { return false; } diff --git a/src/ui/map.js b/src/ui/map.js index 4ab3142c291..66d18af9c88 100755 --- a/src/ui/map.js +++ b/src/ui/map.js @@ -1264,6 +1264,9 @@ class Map extends Camera { * @param {string} layer The ID of the layer to which the filter will be applied. * @param {Array | null | undefined} filter The filter, conforming to the Mapbox Style Specification's * [filter definition](https://www.mapbox.com/mapbox-gl-js/style-spec/#other-filter). If `null` or `undefined` is provided, the function removes any existing filter from the layer. + * @param {Object} [options] + * @param {boolean} [options.validate=true] Whether to check if the filter conforms to the Mapbox GL Style Specification. Disabling validation is a performance optimization that should only be used if you have previously validated the values you will be passing to this function. + * * @returns {Map} `this` * @example * map.setFilter('my-layer', ['==', 'name', 'USA']); @@ -1271,8 +1274,8 @@ class Map extends Camera { * @see [Highlight features containing similar data](https://www.mapbox.com/mapbox-gl-js/example/query-similar-features/) * @see [Create a timeline animation](https://www.mapbox.com/mapbox-gl-js/example/timeline-animation/) */ - setFilter(layer: string, filter: ?FilterSpecification) { - this.style.setFilter(layer, filter); + setFilter(layer: string, filter: ?FilterSpecification, options?: {validate?: boolean}) { + this.style.setFilter(layer, filter, options); return this._update(true); } @@ -1308,6 +1311,8 @@ class Map extends Camera { * @param {string} name The name of the paint property to set. * @param {*} value The value of the paint propery to set. * Must be of a type appropriate for the property, as defined in the [Mapbox Style Specification](https://www.mapbox.com/mapbox-gl-style-spec/). + * @param {Object} [options] + * @param {boolean} [options.validate=true] Whether to check if `value` conforms to the Mapbox GL Style Specification. Disabling validation is a performance optimization that should only be used if you have previously validated the values you will be passing to this function. * @returns {Map} `this` * @example * map.setPaintProperty('my-layer', 'fill-color', '#faafee'); @@ -1315,8 +1320,8 @@ class Map extends Camera { * @see [Adjust a layer's opacity](https://www.mapbox.com/mapbox-gl-js/example/adjust-layer-opacity/) * @see [Create a draggable point](https://www.mapbox.com/mapbox-gl-js/example/drag-a-point/) */ - setPaintProperty(layer: string, name: string, value: any) { - this.style.setPaintProperty(layer, name, value); + setPaintProperty(layer: string, name: string, value: any, options?: {validate?: boolean}) { + this.style.setPaintProperty(layer, name, value, options); return this._update(true); } @@ -1337,12 +1342,14 @@ class Map extends Camera { * @param {string} layer The ID of the layer to set the layout property in. * @param {string} name The name of the layout property to set. * @param {*} value The value of the layout propery. Must be of a type appropriate for the property, as defined in the [Mapbox Style Specification](https://www.mapbox.com/mapbox-gl-style-spec/). + * @param {Object} [options] + * @param {boolean} [options.validate=true] Whether to check if `value` conforms to the Mapbox GL Style Specification. Disabling validation is a performance optimization that should only be used if you have previously validated the values you will be passing to this function. * @returns {Map} `this` * @example * map.setLayoutProperty('my-layer', 'visibility', 'none'); */ - setLayoutProperty(layer: string, name: string, value: any) { - this.style.setLayoutProperty(layer, name, value); + setLayoutProperty(layer: string, name: string, value: any, options?: {validate?: boolean}) { + this.style.setLayoutProperty(layer, name, value, options); return this._update(true); } @@ -1361,10 +1368,12 @@ class Map extends Camera { * Sets the any combination of light values. * * @param light Light properties to set. Must conform to the [Mapbox Style Specification](https://www.mapbox.com/mapbox-gl-style-spec/#light). + * @param {Object} [options] + * @param {boolean} [options.validate=true] Whether to check if the filter conforms to the Mapbox GL Style Specification. Disabling validation is a performance optimization that should only be used if you have previously validated the values you will be passing to this function. * @returns {Map} `this` */ - setLight(light: LightSpecification) { - this.style.setLight(light); + setLight(light: LightSpecification, options?: {validate?: boolean}) { + this.style.setLight(light, options); return this._update(true); } diff --git a/test/unit/style/light.test.js b/test/unit/style/light.test.js index 737556bc627..9adb1785bad 100644 --- a/test/unit/style/light.test.js +++ b/test/unit/style/light.test.js @@ -58,12 +58,41 @@ test('Light#getLight', (t) => { }); test('Light#setLight', (t) => { - const light = new Light({}); - light.setLight({ color: 'red', "color-transition": { duration: 3000 }}); - light.updateTransitions({ transition: true }, {}); - light.recalculate({zoom: 16, zoomHistory: {}, now: 1500}); + t.test('sets light', (t) => { + const light = new Light({}); + light.setLight({ color: 'red', "color-transition": { duration: 3000 }}); + light.updateTransitions({ transition: true }, {}); + light.recalculate({zoom: 16, zoomHistory: {}, now: 1500}); + t.deepEqual(light.properties.get('color'), new Color(1, 0.5, 0.5, 1)); + t.end(); + }); + + t.test('validates by default', (t) => { + const light = new Light({}); + const lightSpy = t.spy(light, '_validate'); + t.stub(console, 'error'); + light.setLight({ color: 'notacolor'}); + light.updateTransitions({ transition: false}, {}); + light.recalculate({zoom: 16, zoomHistory: {}, now: 10}); + t.ok(lightSpy.calledOnce); + t.ok(console.error.calledOnce); + t.deepEqual(lightSpy.args[0][2], undefined); + t.end(); + }); - t.deepEqual(light.properties.get('color'), new Color(1, 0.5, 0.5, 1)); + t.test('respects validation option', (t) => { + const light = new Light({}); + + const lightSpy = t.spy(light, '_validate'); + light.setLight({ color: [999]}, {validate: false}); + light.updateTransitions({ transition: false}, {}); + light.recalculate({zoom: 16, zoomHistory: {}, now: 10}); + + t.ok(lightSpy.calledOnce); + t.deepEqual(lightSpy.args[0][2], {validate: false}); + t.deepEqual(light.properties.get('color'), [999]); + t.end(); + }); t.end(); }); diff --git a/test/unit/style/style.test.js b/test/unit/style/style.test.js index 91e14ed76f1..0e44af55daf 100644 --- a/test/unit/style/style.test.js +++ b/test/unit/style/style.test.js @@ -1390,6 +1390,39 @@ test('Style#setPaintProperty', (t) => { }); }); + t.test('respects validate option', (t) => { + const style = new Style(new StubMap()); + style.loadJSON({ + "version": 8, + "sources": {}, + "layers": [ + { + "id": "background", + "type": "background" + } + ] + }); + + style.on('style.load', () => { + const backgroundLayer = style.getLayer('background'); + t.stub(console, 'error'); + const validate = t.spy(backgroundLayer, '_validate'); + + style.setPaintProperty('background', 'background-color', 'notacolor', {validate: false}); + t.deepEqual(validate.args[0][4], {validate: false}); + t.ok(console.error.notCalled); + + t.ok(style._changed); + style.update({}); + + style.setPaintProperty('background', 'background-color', 'alsonotacolor'); + t.ok(console.error.calledOnce, 'validates input by default'); + t.deepEqual(validate.args[1][4], undefined); + + t.end(); + }); + }); + t.end(); }); @@ -1464,6 +1497,47 @@ test('Style#setLayoutProperty', (t) => { }); }); + t.test('respects validate option', (t) => { + const style = new Style(new StubMap()); + style.loadJSON({ + "version": 8, + "sources": { + "geojson": { + "type": "geojson", + "data": { + "type": "FeatureCollection", + "features": [] + } + } + }, + "layers": [ + { + "id": "line", + "type": "line", + "source": "geojson" + } + ] + }); + + style.on('style.load', () => { + const lineLayer = style.getLayer('line'); + t.stub(console, 'error'); + const validate = t.spy(lineLayer, '_validate'); + + style.setLayoutProperty('line', 'line-cap', 'invalidcap', {validate: false}); + t.deepEqual(validate.args[0][4], {validate: false}); + t.ok(console.error.notCalled); + t.ok(style._changed); + style.update({}); + + style.setLayoutProperty('line', 'line-cap', 'differentinvalidcap'); + t.ok(console.error.calledOnce, 'validates input by default'); + t.deepEqual(validate.args[1][4], undefined); + + t.end(); + }); + }); + t.end(); }); @@ -1614,6 +1688,35 @@ test('Style#setFilter', (t) => { }); }); + t.test('validates filter by default', (t) => { + const style = createStyle(); + t.stub(console, 'error'); + style.on('style.load', () => { + style.setFilter('symbol', 'notafilter'); + t.deepEqual(style.getFilter('symbol'), ['==', 'id', 0]); + t.ok(console.error.calledOnce); + style.update({}); // trigger dispatcher broadcast + t.end(); + }); + }); + + t.test('respects validate option', (t) => { + const style = createStyle(); + + style.on('style.load', () => { + style.dispatcher.broadcast = function(key, value) { + t.equal(key, 'updateLayers'); + t.deepEqual(value.layers[0].id, 'symbol'); + t.deepEqual(value.layers[0].filter, 'notafilter'); + t.end(); + }; + + style.setFilter('symbol', 'notafilter', {validate: false}); + t.deepEqual(style.getFilter('symbol'), 'notafilter'); + style.update({}); // trigger dispatcher broadcast + }); + }); + t.end(); }); From 3195c0b85b1fbabc8da8281fd43e336afd2193af Mon Sep 17 00:00:00 2001 From: Molly Lloyd Date: Mon, 26 Nov 2018 11:25:53 -0800 Subject: [PATCH 2/2] add StyleSetterOptions type --- src/style/light.js | 4 ++-- src/style/style.js | 21 +++++++++++---------- src/style/style_layer.js | 7 ++++--- src/ui/map.js | 11 +++++------ test/unit/style/light.test.js | 2 +- test/unit/style/style.test.js | 4 ++-- 6 files changed, 25 insertions(+), 24 deletions(-) diff --git a/src/style/light.js b/src/style/light.js index 7de9ba793f2..14beb4e3e59 100644 --- a/src/style/light.js +++ b/src/style/light.js @@ -14,7 +14,7 @@ import { number as interpolate } from '../style-spec/util/interpolate'; import type {StylePropertySpecification} from '../style-spec/style-spec'; import type EvaluationParameters from './evaluation_parameters'; - +import type {StyleSetterOptions} from '../style/style'; import { Properties, Transitionable, Transitioning, PossiblyEvaluated, DataConstantProperty } from './properties'; import type { @@ -86,7 +86,7 @@ class Light extends Evented { return this._transitionable.serialize(); } - setLight(light?: LightSpecification, options?: {validate?: boolean}) { + setLight(light?: LightSpecification, options: StyleSetterOptions = {}) { if (this._validate(validateLight, light, options)) { return; } diff --git a/src/style/style.js b/src/style/style.js index 05b31bd6217..5679e3ab562 100644 --- a/src/style/style.js +++ b/src/style/style.js @@ -89,6 +89,9 @@ export type StyleOptions = { localIdeographFontFamily?: string }; +export type StyleSetterOptions = { + validate?: boolean +}; /** * @private */ @@ -200,9 +203,7 @@ class Style extends Evented { }); } - loadJSON(json: StyleSpecification, options: { - validate?: boolean - } = {}) { + loadJSON(json: StyleSpecification, options: StyleSetterOptions = {}) { this.fire(new Event('dataloading', {dataType: 'style'})); this._request = browser.frame(() => { @@ -481,7 +482,7 @@ class Style extends Evented { return this.imageManager.listImages(); } - addSource(id: string, source: SourceSpecification, options?: {validate?: boolean}) { + addSource(id: string, source: SourceSpecification, options: StyleSetterOptions = {}) { this._checkLoaded(); if (this.sourceCaches[id] !== undefined) { @@ -567,7 +568,7 @@ class Style extends Evented { * ID `before`, or appended if `before` is omitted. * @param {string} [before] ID of an existing layer to insert before */ - addLayer(layerObject: LayerSpecification | CustomLayerInterface, before?: string, options?: {validate?: boolean}) { + addLayer(layerObject: LayerSpecification | CustomLayerInterface, before?: string, options: StyleSetterOptions = {}) { this._checkLoaded(); const id = layerObject.id; @@ -733,7 +734,7 @@ class Style extends Evented { this._updateLayer(layer); } - setFilter(layerId: string, filter: ?FilterSpecification, options?: {validate?: boolean}) { + setFilter(layerId: string, filter: ?FilterSpecification, options: StyleSetterOptions = {}) { this._checkLoaded(); const layer = this.getLayer(layerId); @@ -769,7 +770,7 @@ class Style extends Evented { return clone(this.getLayer(layer).filter); } - setLayoutProperty(layerId: string, name: string, value: any, options?: {validate?: boolean}) { + setLayoutProperty(layerId: string, name: string, value: any, options: StyleSetterOptions = {}) { this._checkLoaded(); const layer = this.getLayer(layerId); @@ -800,7 +801,7 @@ class Style extends Evented { return layer.getLayoutProperty(name); } - setPaintProperty(layerId: string, name: string, value: any, options?: {validate?: boolean}) { + setPaintProperty(layerId: string, name: string, value: any, options: StyleSetterOptions = {}) { this._checkLoaded(); const layer = this.getLayer(layerId); @@ -1001,7 +1002,7 @@ class Style extends Evented { return this.light.getLight(); } - setLight(lightOptions: LightSpecification, options?: {validate?: boolean}) { + setLight(lightOptions: LightSpecification, options: StyleSetterOptions = {}) { this._checkLoaded(); const light = this.light.getLight(); @@ -1026,7 +1027,7 @@ class Style extends Evented { this.light.updateTransitions(parameters); } - _validate(validate: ({}) => void, key: string, value: any, props: any, options?: {validate?: boolean}) { + _validate(validate: ({}) => void, key: string, value: any, props: any, options: StyleSetterOptions = {}) { if (options && options.validate === false) { return false; } diff --git a/src/style/style_layer.js b/src/style/style_layer.js index 6c8834c3889..8ddef032738 100644 --- a/src/style/style_layer.js +++ b/src/style/style_layer.js @@ -26,6 +26,7 @@ import type { } from '../style-spec/types'; import type {CustomLayerInterface} from './style_layer/custom_style_layer'; import type Map from '../ui/map'; +import type {StyleSetterOptions} from './style'; const TRANSITION_SUFFIX = '-transition'; @@ -115,7 +116,7 @@ class StyleLayer extends Evented { return this._unevaluatedLayout.getValue(name); } - setLayoutProperty(name: string, value: mixed, options?: {validate?: boolean}) { + setLayoutProperty(name: string, value: mixed, options: StyleSetterOptions = {}) { if (value !== null && value !== undefined) { const key = `layers.${this.id}.layout.${name}`; if (this._validate(validateLayoutProperty, key, name, value, options)) { @@ -139,7 +140,7 @@ class StyleLayer extends Evented { } } - setPaintProperty(name: string, value: mixed, options?: {validate?: boolean}) { + setPaintProperty(name: string, value: mixed, options: StyleSetterOptions = {}) { if (value !== null && value !== undefined) { const key = `layers.${this.id}.paint.${name}`; if (this._validate(validatePaintProperty, key, name, value, options)) { @@ -221,7 +222,7 @@ class StyleLayer extends Evented { }); } - _validate(validate: Function, key: string, name: string, value: mixed, options?: {validate?: boolean}) { + _validate(validate: Function, key: string, name: string, value: mixed, options: StyleSetterOptions = {}) { if (options && options.validate === false) { return false; } diff --git a/src/ui/map.js b/src/ui/map.js index 66d18af9c88..93612a5a7a1 100755 --- a/src/ui/map.js +++ b/src/ui/map.js @@ -30,7 +30,7 @@ import type {PointLike} from '@mapbox/point-geometry'; import type {LngLatLike} from '../geo/lng_lat'; import type {LngLatBoundsLike} from '../geo/lng_lat_bounds'; import type {RequestParameters} from '../util/ajax'; -import type {StyleOptions} from '../style/style'; +import type {StyleOptions, StyleSetterOptions} from '../style/style'; import type {MapEvent, MapDataEvent} from './events'; import type {CustomLayerInterface} from '../style/style_layer/custom_style_layer'; @@ -52,7 +52,6 @@ import type { } from '../style-spec/types'; type ControlPosition = 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right'; - /* eslint-disable no-use-before-define */ type IControl = { onAdd(map: Map): HTMLElement; @@ -1274,7 +1273,7 @@ class Map extends Camera { * @see [Highlight features containing similar data](https://www.mapbox.com/mapbox-gl-js/example/query-similar-features/) * @see [Create a timeline animation](https://www.mapbox.com/mapbox-gl-js/example/timeline-animation/) */ - setFilter(layer: string, filter: ?FilterSpecification, options?: {validate?: boolean}) { + setFilter(layer: string, filter: ?FilterSpecification, options: StyleSetterOptions = {}) { this.style.setFilter(layer, filter, options); return this._update(true); } @@ -1320,7 +1319,7 @@ class Map extends Camera { * @see [Adjust a layer's opacity](https://www.mapbox.com/mapbox-gl-js/example/adjust-layer-opacity/) * @see [Create a draggable point](https://www.mapbox.com/mapbox-gl-js/example/drag-a-point/) */ - setPaintProperty(layer: string, name: string, value: any, options?: {validate?: boolean}) { + setPaintProperty(layer: string, name: string, value: any, options: StyleSetterOptions = {}) { this.style.setPaintProperty(layer, name, value, options); return this._update(true); } @@ -1348,7 +1347,7 @@ class Map extends Camera { * @example * map.setLayoutProperty('my-layer', 'visibility', 'none'); */ - setLayoutProperty(layer: string, name: string, value: any, options?: {validate?: boolean}) { + setLayoutProperty(layer: string, name: string, value: any, options: StyleSetterOptions = {}) { this.style.setLayoutProperty(layer, name, value, options); return this._update(true); } @@ -1372,7 +1371,7 @@ class Map extends Camera { * @param {boolean} [options.validate=true] Whether to check if the filter conforms to the Mapbox GL Style Specification. Disabling validation is a performance optimization that should only be used if you have previously validated the values you will be passing to this function. * @returns {Map} `this` */ - setLight(light: LightSpecification, options?: {validate?: boolean}) { + setLight(light: LightSpecification, options: StyleSetterOptions = {}) { this.style.setLight(light, options); return this._update(true); } diff --git a/test/unit/style/light.test.js b/test/unit/style/light.test.js index 9adb1785bad..d16ad737207 100644 --- a/test/unit/style/light.test.js +++ b/test/unit/style/light.test.js @@ -76,7 +76,7 @@ test('Light#setLight', (t) => { light.recalculate({zoom: 16, zoomHistory: {}, now: 10}); t.ok(lightSpy.calledOnce); t.ok(console.error.calledOnce); - t.deepEqual(lightSpy.args[0][2], undefined); + t.deepEqual(lightSpy.args[0][2], {}); t.end(); }); diff --git a/test/unit/style/style.test.js b/test/unit/style/style.test.js index 0e44af55daf..8facc942fcb 100644 --- a/test/unit/style/style.test.js +++ b/test/unit/style/style.test.js @@ -1417,7 +1417,7 @@ test('Style#setPaintProperty', (t) => { style.setPaintProperty('background', 'background-color', 'alsonotacolor'); t.ok(console.error.calledOnce, 'validates input by default'); - t.deepEqual(validate.args[1][4], undefined); + t.deepEqual(validate.args[1][4], {}); t.end(); }); @@ -1532,7 +1532,7 @@ test('Style#setLayoutProperty', (t) => { style.setLayoutProperty('line', 'line-cap', 'differentinvalidcap'); t.ok(console.error.calledOnce, 'validates input by default'); - t.deepEqual(validate.args[1][4], undefined); + t.deepEqual(validate.args[1][4], {}); t.end(); });