Skip to content

Commit a460be0

Browse files
committed
resolves #4059 - throw error msg about "missing style"
... when trying to plot a mapbox subplot w/o a Mapbox access token and w/o setting a Mapbox-served style as opposed to simply throwing a "missing token" msg. Also, rename constants.styles -> constants.stylesNonMapbox
1 parent d4a2308 commit a460be0

File tree

4 files changed

+169
-136
lines changed

4 files changed

+169
-136
lines changed

src/plots/mapbox/constants.js

Lines changed: 136 additions & 129 deletions
Original file line numberDiff line numberDiff line change
@@ -10,147 +10,148 @@
1010

1111
var requiredVersion = '1.1.1';
1212

13-
module.exports = {
14-
requiredVersion: requiredVersion,
15-
16-
styleUrlPrefix: 'mapbox://styles/mapbox/',
17-
styleUrlSuffix: 'v9',
18-
19-
styleValuesMapbox: ['basic', 'streets', 'outdoors', 'light', 'dark', 'satellite', 'satellite-streets'],
20-
styleValueOSM: 'open-street-map',
21-
styleValueDflt: 'basic',
22-
23-
styles: {
24-
'open-street-map': {
25-
id: 'osm',
26-
version: 8,
27-
sources: {
28-
'plotly-osm-tiles': {
29-
type: 'raster',
30-
attribution: '<a href="http://www.openstreetmap.org/about/" target="_blank">© OpenStreetMap</a>',
31-
tiles: [
32-
'https://a.tile.openstreetmap.org/{z}/{x}/{y}.png',
33-
'https://b.tile.openstreetmap.org/{z}/{x}/{y}.png'
34-
],
35-
tileSize: 256
36-
}
37-
},
38-
layers: [{
39-
id: 'plotly-osm-tiles',
13+
var stylesNonMapbox = {
14+
'open-street-map': {
15+
id: 'osm',
16+
version: 8,
17+
sources: {
18+
'plotly-osm-tiles': {
4019
type: 'raster',
41-
source: 'plotly-osm-tiles',
42-
minzoom: 0,
43-
maxzoom: 22
44-
}]
20+
attribution: '<a href="http://www.openstreetmap.org/about/" target="_blank">© OpenStreetMap</a>',
21+
tiles: [
22+
'https://a.tile.openstreetmap.org/{z}/{x}/{y}.png',
23+
'https://b.tile.openstreetmap.org/{z}/{x}/{y}.png'
24+
],
25+
tileSize: 256
26+
}
4527
},
46-
'white-bg': {
28+
layers: [{
29+
id: 'plotly-osm-tiles',
30+
type: 'raster',
31+
source: 'plotly-osm-tiles',
32+
minzoom: 0,
33+
maxzoom: 22
34+
}]
35+
},
36+
'white-bg': {
37+
id: 'white-bg',
38+
version: 8,
39+
sources: {},
40+
layers: [{
4741
id: 'white-bg',
48-
version: 8,
49-
sources: {},
50-
layers: [{
51-
id: 'white-bg',
52-
type: 'background',
53-
paint: {'background-color': '#FFFFFF'},
54-
minzoom: 0,
55-
maxzoom: 22
56-
}]
57-
},
58-
'carto-positron': {
59-
id: 'carto-positron',
60-
version: 8,
61-
sources: {
62-
'plotly-carto-positron': {
63-
type: 'raster',
64-
attribution: '<a href="https://carto.com/" target="_blank">© CARTO</a>',
65-
tiles: ['https://cartodb-basemaps-c.global.ssl.fastly.net/light_all/{z}/{x}/{y}.png'],
66-
tileSize: 256
67-
}
68-
},
69-
layers: [{
70-
id: 'plotly-carto-positron',
42+
type: 'background',
43+
paint: {'background-color': '#FFFFFF'},
44+
minzoom: 0,
45+
maxzoom: 22
46+
}]
47+
},
48+
'carto-positron': {
49+
id: 'carto-positron',
50+
version: 8,
51+
sources: {
52+
'plotly-carto-positron': {
7153
type: 'raster',
72-
source: 'plotly-carto-positron',
73-
minzoom: 0,
74-
maxzoom: 22
75-
}]
54+
attribution: '<a href="https://carto.com/" target="_blank">© CARTO</a>',
55+
tiles: ['https://cartodb-basemaps-c.global.ssl.fastly.net/light_all/{z}/{x}/{y}.png'],
56+
tileSize: 256
57+
}
7658
},
77-
'carto-darkmatter': {
78-
id: 'carto-darkmatter',
79-
version: 8,
80-
sources: {
81-
'plotly-carto-darkmatter': {
82-
type: 'raster',
83-
attribution: '<a href="https://carto.com/" target="_blank">© CARTO</a>',
84-
tiles: ['https://cartodb-basemaps-c.global.ssl.fastly.net/dark_all/{z}/{x}/{y}.png'],
85-
tileSize: 256
86-
}
87-
},
88-
layers: [{
89-
id: 'plotly-carto-darkmatter',
59+
layers: [{
60+
id: 'plotly-carto-positron',
61+
type: 'raster',
62+
source: 'plotly-carto-positron',
63+
minzoom: 0,
64+
maxzoom: 22
65+
}]
66+
},
67+
'carto-darkmatter': {
68+
id: 'carto-darkmatter',
69+
version: 8,
70+
sources: {
71+
'plotly-carto-darkmatter': {
9072
type: 'raster',
91-
source: 'plotly-carto-darkmatter',
92-
minzoom: 0,
93-
maxzoom: 22
94-
}]
73+
attribution: '<a href="https://carto.com/" target="_blank">© CARTO</a>',
74+
tiles: ['https://cartodb-basemaps-c.global.ssl.fastly.net/dark_all/{z}/{x}/{y}.png'],
75+
tileSize: 256
76+
}
9577
},
96-
'stamen-terrain': {
97-
id: 'stamen-terrain',
98-
version: 8,
99-
sources: {
100-
'plotly-stamen-terrain': {
101-
type: 'raster',
102-
attribution: 'Map tiles by <a href="http://stamen.com">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> | Data by <a href="http://openstreetmap.org">OpenStreetMap</a>, under <a href="http://www.openstreetmap.org/copyright">ODbL</a>.',
103-
tiles: ['https://stamen-tiles.a.ssl.fastly.net/terrain/{z}/{x}/{y}.png'],
104-
tileSize: 256
105-
}
106-
},
107-
layers: [{
108-
id: 'plotly-stamen-terrain',
78+
layers: [{
79+
id: 'plotly-carto-darkmatter',
80+
type: 'raster',
81+
source: 'plotly-carto-darkmatter',
82+
minzoom: 0,
83+
maxzoom: 22
84+
}]
85+
},
86+
'stamen-terrain': {
87+
id: 'stamen-terrain',
88+
version: 8,
89+
sources: {
90+
'plotly-stamen-terrain': {
10991
type: 'raster',
110-
source: 'plotly-stamen-terrain',
111-
minzoom: 0,
112-
maxzoom: 22
113-
}]
92+
attribution: 'Map tiles by <a href="http://stamen.com">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> | Data by <a href="http://openstreetmap.org">OpenStreetMap</a>, under <a href="http://www.openstreetmap.org/copyright">ODbL</a>.',
93+
tiles: ['https://stamen-tiles.a.ssl.fastly.net/terrain/{z}/{x}/{y}.png'],
94+
tileSize: 256
95+
}
11496
},
115-
'stamen-toner': {
116-
id: 'stamen-toner',
117-
version: 8,
118-
sources: {
119-
'plotly-stamen-toner': {
120-
type: 'raster',
121-
attribution: 'Map tiles by <a href="http://stamen.com">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> | Data by <a href="http://openstreetmap.org">OpenStreetMap</a>, under <a href="http://www.openstreetmap.org/copyright">ODbL</a>.',
122-
tiles: ['https://stamen-tiles.a.ssl.fastly.net/toner/{z}/{x}/{y}.png'],
123-
tileSize: 256
124-
}
125-
},
126-
layers: [{
127-
id: 'plotly-stamen-toner',
97+
layers: [{
98+
id: 'plotly-stamen-terrain',
99+
type: 'raster',
100+
source: 'plotly-stamen-terrain',
101+
minzoom: 0,
102+
maxzoom: 22
103+
}]
104+
},
105+
'stamen-toner': {
106+
id: 'stamen-toner',
107+
version: 8,
108+
sources: {
109+
'plotly-stamen-toner': {
128110
type: 'raster',
129-
source: 'plotly-stamen-toner',
130-
minzoom: 0,
131-
maxzoom: 22
132-
}]
111+
attribution: 'Map tiles by <a href="http://stamen.com">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> | Data by <a href="http://openstreetmap.org">OpenStreetMap</a>, under <a href="http://www.openstreetmap.org/copyright">ODbL</a>.',
112+
tiles: ['https://stamen-tiles.a.ssl.fastly.net/toner/{z}/{x}/{y}.png'],
113+
tileSize: 256
114+
}
133115
},
134-
'stamen-watercolor': {
135-
id: 'stamen-watercolor',
136-
version: 8,
137-
sources: {
138-
'plotly-stamen-watercolor': {
139-
type: 'raster',
140-
attribution: 'Map tiles by <a href="http://stamen.com">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> | Data by <a href="http://openstreetmap.org">OpenStreetMap</a>, under <a href="http://creativecommons.org/licenses/by-sa/3.0">CC BY SA</a>.',
141-
tiles: ['https://stamen-tiles.a.ssl.fastly.net/watercolor/{z}/{x}/{y}.png'],
142-
tileSize: 256
143-
}
144-
},
145-
layers: [{
146-
id: 'plotly-stamen-watercolor',
147-
type: 'raster',
148-
source: 'plotly-stamen-watercolor',
149-
minzoom: 0,
150-
maxzoom: 22
151-
}]
152-
}
116+
layers: [{
117+
id: 'plotly-stamen-toner',
118+
type: 'raster',
119+
source: 'plotly-stamen-toner',
120+
minzoom: 0,
121+
maxzoom: 22
122+
}]
153123
},
124+
'stamen-watercolor': {
125+
id: 'stamen-watercolor',
126+
version: 8,
127+
sources: {
128+
'plotly-stamen-watercolor': {
129+
type: 'raster',
130+
attribution: 'Map tiles by <a href="http://stamen.com">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0">CC BY 3.0</a> | Data by <a href="http://openstreetmap.org">OpenStreetMap</a>, under <a href="http://creativecommons.org/licenses/by-sa/3.0">CC BY SA</a>.',
131+
tiles: ['https://stamen-tiles.a.ssl.fastly.net/watercolor/{z}/{x}/{y}.png'],
132+
tileSize: 256
133+
}
134+
},
135+
layers: [{
136+
id: 'plotly-stamen-watercolor',
137+
type: 'raster',
138+
source: 'plotly-stamen-watercolor',
139+
minzoom: 0,
140+
maxzoom: 22
141+
}]
142+
}
143+
};
144+
145+
module.exports = {
146+
requiredVersion: requiredVersion,
147+
148+
styleUrlPrefix: 'mapbox://styles/mapbox/',
149+
styleUrlSuffix: 'v9',
150+
151+
styleValuesMapbox: ['basic', 'streets', 'outdoors', 'light', 'dark', 'satellite', 'satellite-streets'],
152+
styleValueOSM: 'open-street-map',
153+
styleValueDflt: 'basic',
154+
stylesNonMapbox: stylesNonMapbox,
154155

155156
traceLayerPrefix: 'plotly-trace-layer-',
156157
layoutLayerPrefix: 'plotly-layout-layer-',
@@ -168,6 +169,12 @@ module.exports = {
168169
'More info here: https://www.mapbox.com/help/define-access-token/'
169170
].join('\n'),
170171

172+
missingStyleErrorMsg: [
173+
'No valid mapbox style found, please set `mapbox.style` to one of:',
174+
Object.keys(stylesNonMapbox).join(', '),
175+
'or register a Mapbox access token to use a Mapbox-served style.'
176+
].join('\n'),
177+
171178
multipleTokensErrorMsg: [
172179
'Set multiple mapbox access token across different mapbox subplot,',
173180
'using first token found as mapbox-gl does not allow multiple' +

src/plots/mapbox/index.js

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -220,20 +220,23 @@ function findAccessToken(gd, mapboxIds) {
220220

221221
var tokensUseful = [];
222222
var tokensListed = [];
223+
var hasOneSetMapboxStyle = false;
223224
var wontWork = false;
224225

225226
// Take the first token we find in a mapbox subplot.
226227
// These default to the context value but may be overridden.
227228
for(var i = 0; i < mapboxIds.length; i++) {
228229
var opts = fullLayout[mapboxIds[i]];
229-
var style = opts.style;
230230
var token = opts.accesstoken;
231231

232-
if(typeof style === 'string' && constants.styleValuesMapbox.indexOf(style) !== -1) {
232+
if(isMapboxStyle(opts.style)) {
233233
if(token) {
234234
Lib.pushUnique(tokensUseful, token);
235235
} else {
236-
Lib.error('Uses Mapbox map style, but did not set an access token.');
236+
if(isMapboxStyle(opts._input.style)) {
237+
Lib.error('Uses Mapbox map style, but did not set an access token.');
238+
hasOneSetMapboxStyle = true;
239+
}
237240
wontWork = true;
238241
}
239242
}
@@ -244,7 +247,10 @@ function findAccessToken(gd, mapboxIds) {
244247
}
245248

246249
if(wontWork) {
247-
throw new Error(constants.noAccessTokenErrorMsg);
250+
var msg = hasOneSetMapboxStyle ?
251+
constants.noAccessTokenErrorMsg :
252+
constants.missingStyleErrorMsg;
253+
throw new Error(msg);
248254
}
249255

250256
if(tokensUseful.length) {
@@ -263,6 +269,10 @@ function findAccessToken(gd, mapboxIds) {
263269
}
264270
}
265271

272+
function isMapboxStyle(s) {
273+
return typeof s === 'string' && constants.styleValuesMapbox.indexOf(s) !== -1;
274+
}
275+
266276
exports.updateFx = function(gd) {
267277
var fullLayout = gd._fullLayout;
268278
var subplotIds = fullLayout._subplots[MAPBOX];

src/plots/mapbox/mapbox.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -769,8 +769,8 @@ function getStyleObj(val) {
769769

770770
if(constants.styleValuesMapbox.indexOf(val) !== -1) {
771771
styleObj.style = convertStyleVal(val);
772-
} else if(constants.styles[val]) {
773-
styleObj.style = constants.styles[val];
772+
} else if(constants.stylesNonMapbox[val]) {
773+
styleObj.style = constants.stylesNonMapbox[val];
774774
} else {
775775
styleObj.style = val;
776776
}

test/jasmine/tests/mapbox_test.js

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -283,7 +283,7 @@ describe('mapbox credentials', function() {
283283
});
284284
});
285285

286-
it('@gl should throw error if token is not registered', function() {
286+
it('@gl should throw error when no non-mapbox style is set and missing a mapbox access token token', function() {
287287
spyOn(Lib, 'error');
288288

289289
expect(function() {
@@ -292,6 +292,22 @@ describe('mapbox credentials', function() {
292292
lon: [10, 20, 30],
293293
lat: [10, 20, 30]
294294
}]);
295+
}).toThrow(new Error(constants.missingStyleErrorMsg));
296+
297+
expect(Lib.error).toHaveBeenCalledTimes(0);
298+
}, LONG_TIMEOUT_INTERVAL);
299+
300+
it('@gl should throw error when setting a Mapbox style w/o a registered token', function() {
301+
spyOn(Lib, 'error');
302+
303+
expect(function() {
304+
Plotly.plot(gd, [{
305+
type: 'scattermapbox',
306+
lon: [10, 20, 30],
307+
lat: [10, 20, 30]
308+
}], {
309+
mapbox: {style: 'basic'}
310+
});
295311
}).toThrow(new Error(constants.noAccessTokenErrorMsg));
296312

297313
expect(Lib.error).toHaveBeenCalledWith('Uses Mapbox map style, but did not set an access token.');

0 commit comments

Comments
 (0)