Migrate to localforage to support asyncStorage mode
This commit is contained in:
parent
068bcdbfc6
commit
76f54932bf
@ -19,6 +19,7 @@
|
|||||||
"@mdi/font": "^3.3.92",
|
"@mdi/font": "^3.3.92",
|
||||||
"file-saver": "^2.0.0",
|
"file-saver": "^2.0.0",
|
||||||
"gps-to-gpx": "git://github.com/phyks/gps-to-gpx.git#1cb5adf4dd382266d076d7df3cb5aa3a4d7dd27b",
|
"gps-to-gpx": "git://github.com/phyks/gps-to-gpx.git#1cb5adf4dd382266d076d7df3cb5aa3a4d7dd27b",
|
||||||
|
"localforage": "^1.7.3",
|
||||||
"nosleep.js": "^0.9.0",
|
"nosleep.js": "^0.9.0",
|
||||||
"ol": "^5.3.0",
|
"ol": "^5.3.0",
|
||||||
"roboto-fontface": "^0.10.0",
|
"roboto-fontface": "^0.10.0",
|
||||||
|
@ -82,7 +82,7 @@
|
|||||||
<script>
|
<script>
|
||||||
import runtime from 'serviceworker-webpack-plugin/lib/runtime';
|
import runtime from 'serviceworker-webpack-plugin/lib/runtime';
|
||||||
|
|
||||||
import { DELAY_BETWEEN_API_BATCH_REQUESTS } from '@/constants';
|
import { APP_NAME, DELAY_BETWEEN_API_BATCH_REQUESTS } from '@/constants';
|
||||||
|
|
||||||
import Alert from '@/components/Alert.vue';
|
import Alert from '@/components/Alert.vue';
|
||||||
import ReportIssueModal from '@/components/ReportIssueModal.vue';
|
import ReportIssueModal from '@/components/ReportIssueModal.vue';
|
||||||
@ -127,7 +127,7 @@ export default {
|
|||||||
isSearchModalShown: false,
|
isSearchModalShown: false,
|
||||||
isSendingReports: false,
|
isSendingReports: false,
|
||||||
isShareMapViewModalShown: false,
|
isShareMapViewModalShown: false,
|
||||||
title: "Cycl'Assist",
|
title: APP_NAME,
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
export const VERSION = '0.3';
|
export const APP_NAME = 'Cygnal';
|
||||||
|
export const VERSION = '0.4';
|
||||||
|
|
||||||
export const NORMAL_ICON_SCALE = 0.625;
|
export const NORMAL_ICON_SCALE = 0.625;
|
||||||
export const LARGE_ICON_SCALE = 1.0;
|
export const LARGE_ICON_SCALE = 1.0;
|
||||||
|
11
src/main.js
11
src/main.js
@ -15,12 +15,14 @@ import router from '@/router';
|
|||||||
import store from '@/store';
|
import store from '@/store';
|
||||||
import '@/vuetify';
|
import '@/vuetify';
|
||||||
|
|
||||||
// Ensure locale is correctly set from the store value
|
|
||||||
store.dispatch('setLocale', { locale: store.state.settings.locale });
|
|
||||||
|
|
||||||
Vue.config.productionTip = false;
|
Vue.config.productionTip = false;
|
||||||
|
|
||||||
new Vue({ // eslint-disable-line no-new
|
// Populate the store with settings from the storage
|
||||||
|
store.dispatch('populateInitialStateFromStorage').then(() => {
|
||||||
|
// Ensure locale is correctly set from the store value
|
||||||
|
store.dispatch('setLocale', { locale: store.state.settings.locale });
|
||||||
|
|
||||||
|
new Vue({ // eslint-disable-line no-new
|
||||||
el: '#app',
|
el: '#app',
|
||||||
router,
|
router,
|
||||||
i18n,
|
i18n,
|
||||||
@ -29,4 +31,5 @@ new Vue({ // eslint-disable-line no-new
|
|||||||
render(h) {
|
render(h) {
|
||||||
return h('App');
|
return h('App');
|
||||||
},
|
},
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
119
src/storage/index.js
Normal file
119
src/storage/index.js
Normal file
@ -0,0 +1,119 @@
|
|||||||
|
import localforage from 'localforage';
|
||||||
|
|
||||||
|
import { APP_NAME } from '@/constants';
|
||||||
|
|
||||||
|
// Initialize localforage
|
||||||
|
localforage.config({
|
||||||
|
// Prefer IndexedDB
|
||||||
|
driver: [localforage.INDEXEDDB, localforage.WEBSQL, localforage.LOCALSTORAGE],
|
||||||
|
name: APP_NAME,
|
||||||
|
});
|
||||||
|
|
||||||
|
export function loadDataFromStorage(table, keys) {
|
||||||
|
// If a single key is requested, get it
|
||||||
|
if (!Array.isArray(keys)) {
|
||||||
|
return localforage.getItem(`${table}.${keys}`).catch(
|
||||||
|
e => console.error(
|
||||||
|
`Unable to load data from storage using table ${table} and keys ${keys}: ${e}.`,
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
// Else, return an array of values
|
||||||
|
return Promise.all(keys.map(
|
||||||
|
key => localforage.getItem(`${table}.${key}`),
|
||||||
|
)).then((arrayValues) => {
|
||||||
|
const values = {};
|
||||||
|
arrayValues.forEach((value, i) => {
|
||||||
|
values[keys[i]] = value;
|
||||||
|
});
|
||||||
|
return values;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle migrations across storage schemes
|
||||||
|
export function handleMigrations() {
|
||||||
|
return localforage.getItem('settings.version').then((localForageVersion) => {
|
||||||
|
const promises = [];
|
||||||
|
|
||||||
|
// Get (legacy) version from local storage
|
||||||
|
let localStorageVersion = null;
|
||||||
|
try {
|
||||||
|
// Try to load version from local storage if available
|
||||||
|
if (localforage.supports(localforage.LOCALSTORAGE)) {
|
||||||
|
localStorageVersion = (
|
||||||
|
localStorage.getItem('settings.version') // for versions > 0.3
|
||||||
|
|| localStorage.getItem('version') // for versions <= 0.3
|
||||||
|
);
|
||||||
|
if (localStorageVersion) {
|
||||||
|
localStorageVersion = JSON.parse(localStorageVersion);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
// Pass, ignore error
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pre-0.4
|
||||||
|
if (!localForageVersion) {
|
||||||
|
// First migration, to 0.1
|
||||||
|
if (!localStorageVersion) {
|
||||||
|
console.log('Migrating local storage to version 0.1...');
|
||||||
|
const preventSuspend = localStorage.getItem('preventSuspend');
|
||||||
|
if (preventSuspend !== null) {
|
||||||
|
localStorage.setItem('hasPreventSuspendPermission', JSON.stringify(preventSuspend));
|
||||||
|
}
|
||||||
|
localStorage.removeItem('preventSuspend');
|
||||||
|
localStorageVersion = '0.1';
|
||||||
|
localStorage.setItem('version', JSON.stringify(localStorageVersion));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Migration to 0.4
|
||||||
|
// Migrate to localforage API and purge localStorage values.
|
||||||
|
if (localStorageVersion < '0.4') {
|
||||||
|
console.log('Migrating local storage to version 0.4...');
|
||||||
|
// Migrate settings
|
||||||
|
[
|
||||||
|
'hasGeolocationPermission',
|
||||||
|
'hasPermanentNotificationPermission',
|
||||||
|
'hasPlaySoundPermission',
|
||||||
|
'hasPreventSuspendPermission',
|
||||||
|
'hasVibratePermission',
|
||||||
|
'locale',
|
||||||
|
'shouldAutorotateMap',
|
||||||
|
'skipOnboarding',
|
||||||
|
'tileServer',
|
||||||
|
'version',
|
||||||
|
].forEach((key) => {
|
||||||
|
let value = localStorage.getItem(key);
|
||||||
|
if (value) {
|
||||||
|
// Put value in localforage
|
||||||
|
try {
|
||||||
|
value = JSON.parse(value);
|
||||||
|
} catch (e) {
|
||||||
|
// Pass, ignore error
|
||||||
|
}
|
||||||
|
promises.push(
|
||||||
|
localforage.setItem(`settings.${key}`, value),
|
||||||
|
);
|
||||||
|
// Remove value from localStorage
|
||||||
|
localStorage.removeItem(key);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
// Migrate unsent reports
|
||||||
|
const unsentReports = localStorage.getItem('unsentReports');
|
||||||
|
if (unsentReports) {
|
||||||
|
// Put value in localforage
|
||||||
|
promises.push(
|
||||||
|
localforage.setItem('unsentReports.items', unsentReports),
|
||||||
|
);
|
||||||
|
// Remove value from localStorage
|
||||||
|
localStorage.removeItem('unsentReports');
|
||||||
|
}
|
||||||
|
promises.push(
|
||||||
|
localforage.setItem('settings.version', '0.4'),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return Promise.all(promises);
|
||||||
|
});
|
||||||
|
}
|
@ -1,7 +1,8 @@
|
|||||||
import * as api from '@/api';
|
import * as api from '@/api';
|
||||||
import * as constants from '@/constants';
|
import * as constants from '@/constants';
|
||||||
|
import i18n, { messages, getBrowserLocales } from '@/i18n';
|
||||||
|
import { handleMigrations, loadDataFromStorage } from '@/storage';
|
||||||
import { pointToPointDistance } from '@/tools/geometry';
|
import { pointToPointDistance } from '@/tools/geometry';
|
||||||
import i18n from '@/i18n';
|
|
||||||
|
|
||||||
import {
|
import {
|
||||||
DELETE_REPORT,
|
DELETE_REPORT,
|
||||||
@ -10,6 +11,7 @@ import {
|
|||||||
INTRO_WAS_UNSEEN,
|
INTRO_WAS_UNSEEN,
|
||||||
IS_DONE_LOADING,
|
IS_DONE_LOADING,
|
||||||
IS_LOADING,
|
IS_LOADING,
|
||||||
|
LOAD_UNSENT_REPORTS,
|
||||||
PUSH_REPORT,
|
PUSH_REPORT,
|
||||||
PUSH_UNSENT_REPORT,
|
PUSH_UNSENT_REPORT,
|
||||||
REMOVE_UNSENT_REPORT,
|
REMOVE_UNSENT_REPORT,
|
||||||
@ -24,6 +26,135 @@ import {
|
|||||||
STORE_REPORTS,
|
STORE_REPORTS,
|
||||||
} from './mutations-types';
|
} from './mutations-types';
|
||||||
|
|
||||||
|
export function populateInitialStateFromStorage({ commit }) {
|
||||||
|
return handleMigrations().then(() => {
|
||||||
|
// Load unsent reports from storage
|
||||||
|
const unsentReportsPromise = loadDataFromStorage(
|
||||||
|
'unsentReports', 'items',
|
||||||
|
).then(
|
||||||
|
unsentReports => commit(LOAD_UNSENT_REPORTS, {
|
||||||
|
unsentReports: unsentReports || [],
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
|
||||||
|
// Load settings from storage
|
||||||
|
const settingsPromise = loadDataFromStorage('settings', [
|
||||||
|
'hasGeolocationPermission',
|
||||||
|
'hasPermanentNotificationPermission',
|
||||||
|
'hasPlaySoundPermission',
|
||||||
|
'hasPreventSuspendPermission',
|
||||||
|
'hasVibratePermission',
|
||||||
|
'locale',
|
||||||
|
'shouldAutorotateMap',
|
||||||
|
'skipOnboarding',
|
||||||
|
'tileCachingDuration',
|
||||||
|
'tileServer',
|
||||||
|
], null).then((dbSettings) => {
|
||||||
|
const settings = dbSettings || {};
|
||||||
|
|
||||||
|
if (!(settings.locale in messages)) {
|
||||||
|
settings.locale = null;
|
||||||
|
}
|
||||||
|
if (!settings.locale) {
|
||||||
|
// Get best matching locale from browser
|
||||||
|
const locales = getBrowserLocales();
|
||||||
|
for (let i = 0; i < locales.length; i += 1) {
|
||||||
|
if (messages[locales[i]]) {
|
||||||
|
settings.locale = locales[i];
|
||||||
|
break; // Break at first matching locale
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (
|
||||||
|
settings.tileCachingDuration !== null
|
||||||
|
&& !Number.isInteger(settings.tileCachingDuration)
|
||||||
|
) {
|
||||||
|
settings.tileCachingDuration = null;
|
||||||
|
}
|
||||||
|
if (
|
||||||
|
settings.tileServer
|
||||||
|
&& !constants.TILE_SERVERS[settings.tileServer]
|
||||||
|
&& !settings.tileServer.startsWith('custom:')
|
||||||
|
) {
|
||||||
|
settings.tileServer = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'locale',
|
||||||
|
value: settings.locale || 'en',
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'hasGeolocationPermission',
|
||||||
|
value: (
|
||||||
|
settings.hasGeolocationPermission !== null
|
||||||
|
? settings.hasGeolocationPermission
|
||||||
|
: true
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'hasPermanentNotificationPermission',
|
||||||
|
value: (
|
||||||
|
settings.hasPermanentNotificationPermission !== null
|
||||||
|
? settings.hasPermanentNotificationPermission
|
||||||
|
: true
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'hasPlaySoundPermission',
|
||||||
|
value: (
|
||||||
|
settings.hasPlaySoundPermission !== null
|
||||||
|
? settings.hasPlaySoundPermission
|
||||||
|
: true
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'hasPreventSuspendPermission',
|
||||||
|
value: (
|
||||||
|
settings.hasPreventSuspendPermission !== null
|
||||||
|
? settings.hasPreventSuspendPermission
|
||||||
|
: true
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'hasVibratePermission',
|
||||||
|
value: (
|
||||||
|
settings.hasVibratePermission !== null
|
||||||
|
? settings.hasVibratePermission
|
||||||
|
: true
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'shouldAutorotateMap',
|
||||||
|
value: (
|
||||||
|
settings.shouldAutorotateMap !== null
|
||||||
|
? settings.shouldAutorotateMap
|
||||||
|
: false
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'skipOnboarding',
|
||||||
|
value: settings.skipOnboarding || false,
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'tileCachingDuration',
|
||||||
|
value: (
|
||||||
|
settings.tileCachingDuration !== null
|
||||||
|
? settings.tileCachingDuration
|
||||||
|
: constants.DEFAULT_TILE_CACHING_DURATION
|
||||||
|
),
|
||||||
|
});
|
||||||
|
commit(SET_SETTING, {
|
||||||
|
setting: 'tileServer',
|
||||||
|
value: settings.tileServer || constants.DEFAULT_TILE_SERVER,
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
return Promise.all(
|
||||||
|
[settingsPromise, unsentReportsPromise],
|
||||||
|
);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
export function fetchReports({ commit, state }) {
|
export function fetchReports({ commit, state }) {
|
||||||
commit(IS_LOADING);
|
commit(IS_LOADING);
|
||||||
return api.getActiveReports()
|
return api.getActiveReports()
|
||||||
|
@ -4,6 +4,7 @@ export const INTRO_WAS_SEEN = 'INTRO_WAS_SEEN';
|
|||||||
export const INTRO_WAS_UNSEEN = 'INTRO_WAS_UNSEEN';
|
export const INTRO_WAS_UNSEEN = 'INTRO_WAS_UNSEEN';
|
||||||
export const IS_DONE_LOADING = 'IS_DONE_LOADING';
|
export const IS_DONE_LOADING = 'IS_DONE_LOADING';
|
||||||
export const IS_LOADING = 'IS_LOADING';
|
export const IS_LOADING = 'IS_LOADING';
|
||||||
|
export const LOAD_UNSENT_REPORTS = 'LOAD_UNSENT_REPORTS';
|
||||||
export const PUSH_REPORT = 'PUSH_REPORT';
|
export const PUSH_REPORT = 'PUSH_REPORT';
|
||||||
export const PUSH_UNSENT_REPORT = 'PUSH_UNSENT_REPORT';
|
export const PUSH_UNSENT_REPORT = 'PUSH_UNSENT_REPORT';
|
||||||
export const REMOVE_UNSENT_REPORT = 'REMOVE_UNSENT_REPORT';
|
export const REMOVE_UNSENT_REPORT = 'REMOVE_UNSENT_REPORT';
|
||||||
|
@ -1,99 +1,13 @@
|
|||||||
import Vue from 'vue';
|
import Vue from 'vue';
|
||||||
|
import localforage from 'localforage';
|
||||||
|
|
||||||
import { messages, getBrowserLocales } from '@/i18n';
|
|
||||||
import { storageAvailable } from '@/tools';
|
|
||||||
import {
|
import {
|
||||||
DEFAULT_TILE_CACHING_DURATION,
|
DEFAULT_TILE_CACHING_DURATION,
|
||||||
DEFAULT_TILE_SERVER,
|
DEFAULT_TILE_SERVER,
|
||||||
TILE_SERVERS,
|
|
||||||
VERSION,
|
|
||||||
} from '@/constants';
|
} from '@/constants';
|
||||||
import * as types from './mutations-types';
|
import * as types from './mutations-types';
|
||||||
|
|
||||||
function loadDataFromStorage(name) {
|
// Handle the required migrations
|
||||||
try {
|
|
||||||
const value = localStorage.getItem(name);
|
|
||||||
if (value) {
|
|
||||||
return JSON.parse(value);
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
} catch (e) {
|
|
||||||
console.error(`Unable to load data from storage using key ${name}: ${e}.`);
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function handleMigrations() {
|
|
||||||
if (!storageAvailable('localStorage')) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
const version = loadDataFromStorage('version');
|
|
||||||
|
|
||||||
// Migration from pre-0.1 to 0.1
|
|
||||||
if (version === null) {
|
|
||||||
const preventSuspend = loadDataFromStorage('preventSuspend');
|
|
||||||
if (preventSuspend !== null) {
|
|
||||||
localStorage.setItem('hasPreventSuspendPermission', JSON.stringify(preventSuspend));
|
|
||||||
}
|
|
||||||
localStorage.removeItem('preventSuspend');
|
|
||||||
localStorage.setItem('version', JSON.stringify(VERSION));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Load unsent reports from storage
|
|
||||||
let unsentReports = null;
|
|
||||||
if (storageAvailable('localStorage')) {
|
|
||||||
unsentReports = loadDataFromStorage('unsentReports');
|
|
||||||
}
|
|
||||||
|
|
||||||
// Load settings from storage
|
|
||||||
let locale = null;
|
|
||||||
let hasGeolocationPermission = null;
|
|
||||||
let hasPermanentNotificationPermission = null;
|
|
||||||
let hasPlaySoundPermission = null;
|
|
||||||
let hasPreventSuspendPermission = null;
|
|
||||||
let hasVibratePermission = null;
|
|
||||||
let shouldAutorotateMap = null;
|
|
||||||
let skipOnboarding = null;
|
|
||||||
let tileCachingDuration = null;
|
|
||||||
let tileServer = null;
|
|
||||||
if (storageAvailable('localStorage')) {
|
|
||||||
handleMigrations();
|
|
||||||
|
|
||||||
hasGeolocationPermission = loadDataFromStorage('hasGeolocationPermission');
|
|
||||||
hasPermanentNotificationPermission = loadDataFromStorage('hasPermanentNotificationPermission');
|
|
||||||
hasPlaySoundPermission = loadDataFromStorage('hasPlaySoundPermission');
|
|
||||||
hasPreventSuspendPermission = loadDataFromStorage('hasPreventSuspendPermission');
|
|
||||||
hasVibratePermission = loadDataFromStorage('hasVibratePermission');
|
|
||||||
shouldAutorotateMap = loadDataFromStorage('shouldAutorotateMap');
|
|
||||||
skipOnboarding = loadDataFromStorage('skipOnboarding');
|
|
||||||
|
|
||||||
tileServer = loadDataFromStorage('tileServer');
|
|
||||||
if (tileServer && !TILE_SERVERS[tileServer] && !tileServer.startsWith('custom:')) {
|
|
||||||
tileServer = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
tileCachingDuration = loadDataFromStorage('tileCachingDuration');
|
|
||||||
if (tileCachingDuration !== null && !Number.isInteger(tileCachingDuration)) {
|
|
||||||
tileCachingDuration = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
locale = loadDataFromStorage('locale');
|
|
||||||
if (!(locale in messages)) {
|
|
||||||
locale = null;
|
|
||||||
}
|
|
||||||
if (!locale) {
|
|
||||||
// Get best matching locale from browser
|
|
||||||
const locales = getBrowserLocales();
|
|
||||||
for (let i = 0; i < locales.length; i += 1) {
|
|
||||||
if (messages[locales[i]]) {
|
|
||||||
locale = locales[i];
|
|
||||||
break; // Break at first matching locale
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export const initialState = {
|
export const initialState = {
|
||||||
hasGoneThroughIntro: false,
|
hasGoneThroughIntro: false,
|
||||||
hasVibratedOnce: false,
|
hasVibratedOnce: false,
|
||||||
@ -114,30 +28,18 @@ export const initialState = {
|
|||||||
userAsked: null,
|
userAsked: null,
|
||||||
},
|
},
|
||||||
reports: [],
|
reports: [],
|
||||||
unsentReports: unsentReports || [],
|
unsentReports: [],
|
||||||
settings: {
|
settings: {
|
||||||
locale: locale || 'en',
|
locale: 'en',
|
||||||
hasGeolocationPermission: (
|
hasGeolocationPermission: true,
|
||||||
hasGeolocationPermission !== null ? hasGeolocationPermission : true
|
hasPermanentNotificationPermission: true,
|
||||||
),
|
hasPlaySoundPermission: true,
|
||||||
hasPermanentNotificationPermission: (
|
hasPreventSuspendPermission: true,
|
||||||
hasPermanentNotificationPermission !== null ? hasPermanentNotificationPermission : true
|
hasVibratePermission: true,
|
||||||
),
|
shouldAutorotateMap: false,
|
||||||
hasPlaySoundPermission: (
|
skipOnboarding: false,
|
||||||
hasPlaySoundPermission !== null ? hasPlaySoundPermission : true
|
tileCachingDuration: DEFAULT_TILE_CACHING_DURATION,
|
||||||
),
|
tileServer: DEFAULT_TILE_SERVER,
|
||||||
hasPreventSuspendPermission: (
|
|
||||||
hasPreventSuspendPermission !== null ? hasPreventSuspendPermission : true
|
|
||||||
),
|
|
||||||
hasVibratePermission: (
|
|
||||||
hasVibratePermission !== null ? hasVibratePermission : true
|
|
||||||
),
|
|
||||||
shouldAutorotateMap: shouldAutorotateMap !== null ? shouldAutorotateMap : false,
|
|
||||||
skipOnboarding: skipOnboarding || false,
|
|
||||||
tileCachingDuration: (
|
|
||||||
tileCachingDuration !== null ? tileCachingDuration : DEFAULT_TILE_CACHING_DURATION
|
|
||||||
),
|
|
||||||
tileServer: tileServer || DEFAULT_TILE_SERVER,
|
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -163,6 +65,9 @@ export const mutations = {
|
|||||||
[types.IS_LOADING](state) {
|
[types.IS_LOADING](state) {
|
||||||
state.isLoading = true;
|
state.isLoading = true;
|
||||||
},
|
},
|
||||||
|
[types.LOAD_UNSENT_REPORTS](state, { unsentReports }) {
|
||||||
|
state.unsentReports = unsentReports;
|
||||||
|
},
|
||||||
[types.PUSH_REPORT](state, { report }) {
|
[types.PUSH_REPORT](state, { report }) {
|
||||||
const reportIndex = state.reports.findIndex(item => item.id === report.id);
|
const reportIndex = state.reports.findIndex(item => item.id === report.id);
|
||||||
if (reportIndex === -1) {
|
if (reportIndex === -1) {
|
||||||
@ -173,15 +78,11 @@ export const mutations = {
|
|||||||
},
|
},
|
||||||
[types.PUSH_UNSENT_REPORT](state, { report }) {
|
[types.PUSH_UNSENT_REPORT](state, { report }) {
|
||||||
state.unsentReports.push(report);
|
state.unsentReports.push(report);
|
||||||
if (storageAvailable('localStorage')) {
|
localforage.setItem('unsentReports.items', state.unsentReports);
|
||||||
localStorage.setItem('unsentReports', JSON.stringify(state.unsentReports));
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
[types.REMOVE_UNSENT_REPORT](state, { index }) {
|
[types.REMOVE_UNSENT_REPORT](state, { index }) {
|
||||||
state.unsentReports.splice(index, 1);
|
state.unsentReports.splice(index, 1);
|
||||||
if (storageAvailable('localStorage')) {
|
localforage.setItem('unsentReports.items', state.unsentReports);
|
||||||
localStorage.setItem('unsentReports', JSON.stringify(state.unsentReports));
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
[types.SET_CURRENT_MAP_CENTER](state, { center }) {
|
[types.SET_CURRENT_MAP_CENTER](state, { center }) {
|
||||||
Vue.set(state.map, 'center', center);
|
Vue.set(state.map, 'center', center);
|
||||||
@ -202,9 +103,7 @@ export const mutations = {
|
|||||||
Vue.set(state.location, 'watcherID', id);
|
Vue.set(state.location, 'watcherID', id);
|
||||||
},
|
},
|
||||||
[types.SET_SETTING](state, { setting, value }) {
|
[types.SET_SETTING](state, { setting, value }) {
|
||||||
if (storageAvailable('localStorage')) {
|
localforage.setItem(`settings.${setting}`, value);
|
||||||
localStorage.setItem(setting, JSON.stringify(value));
|
|
||||||
}
|
|
||||||
state.settings[setting] = value;
|
state.settings[setting] = value;
|
||||||
},
|
},
|
||||||
[types.SHOW_REPORT_DETAILS](state, { id, userAsked }) {
|
[types.SHOW_REPORT_DETAILS](state, { id, userAsked }) {
|
||||||
|
@ -71,31 +71,6 @@ export function mockLocation(setPosition) {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function storageAvailable(type) {
|
|
||||||
let storage;
|
|
||||||
try {
|
|
||||||
storage = window[type];
|
|
||||||
const x = '__storage_test__';
|
|
||||||
storage.setItem(x, x);
|
|
||||||
storage.removeItem(x);
|
|
||||||
return true;
|
|
||||||
} catch (e) {
|
|
||||||
return e instanceof DOMException && (
|
|
||||||
// everything except Firefox
|
|
||||||
e.code === 22
|
|
||||||
// Firefox
|
|
||||||
|| e.code === 1014
|
|
||||||
// test name field too, because code might not be present
|
|
||||||
// everything except Firefox
|
|
||||||
|| e.name === 'QuotaExceededError'
|
|
||||||
// Firefox
|
|
||||||
|| e.name === 'NS_ERROR_DOM_QUOTA_REACHED'
|
|
||||||
)
|
|
||||||
// acknowledge QuotaExceededError only if there's something already stored
|
|
||||||
&& storage.length !== 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export function capitalize(string) {
|
export function capitalize(string) {
|
||||||
return string.charAt(0).toUpperCase() + string.slice(1);
|
return string.charAt(0).toUpperCase() + string.slice(1);
|
||||||
}
|
}
|
||||||
|
@ -34,6 +34,7 @@
|
|||||||
item-value="duration"
|
item-value="duration"
|
||||||
:label="$t('settings.tileCachingDuration')"
|
:label="$t('settings.tileCachingDuration')"
|
||||||
required
|
required
|
||||||
|
v-if="tileCachingEnabled"
|
||||||
></v-select>
|
></v-select>
|
||||||
|
|
||||||
<v-text-field
|
<v-text-field
|
||||||
@ -58,6 +59,8 @@
|
|||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
|
import localforage from 'localforage';
|
||||||
|
|
||||||
import { TILE_SERVERS } from '@/constants';
|
import { TILE_SERVERS } from '@/constants';
|
||||||
import { AVAILABLE_LOCALES } from '@/i18n';
|
import { AVAILABLE_LOCALES } from '@/i18n';
|
||||||
import { capitalize } from '@/tools';
|
import { capitalize } from '@/tools';
|
||||||
@ -169,6 +172,11 @@ export default {
|
|||||||
}));
|
}));
|
||||||
i18nItems.sort((a, b) => a.iso > b.iso);
|
i18nItems.sort((a, b) => a.iso > b.iso);
|
||||||
|
|
||||||
|
// Only IndexedDB backend can be used in service workers
|
||||||
|
const tileCachingEnabled = (
|
||||||
|
localforage.driver() === localforage.INDEXEDDB
|
||||||
|
);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
i18nItems,
|
i18nItems,
|
||||||
orientationModes: [
|
orientationModes: [
|
||||||
@ -181,6 +189,7 @@ export default {
|
|||||||
value: true,
|
value: true,
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
tileCachingEnabled,
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
19
yarn.lock
19
yarn.lock
@ -4340,6 +4340,11 @@ imagemin@^5.3.1:
|
|||||||
pify "^2.3.0"
|
pify "^2.3.0"
|
||||||
replace-ext "^1.0.0"
|
replace-ext "^1.0.0"
|
||||||
|
|
||||||
|
immediate@~3.0.5:
|
||||||
|
version "3.0.6"
|
||||||
|
resolved "https://registry.yarnpkg.com/immediate/-/immediate-3.0.6.tgz#9db1dbd0faf8de6fbe0f5dd5e56bb606280de69b"
|
||||||
|
integrity sha1-nbHb0Pr43m++D13V5Wu2BigN5ps=
|
||||||
|
|
||||||
import-cwd@^2.0.0:
|
import-cwd@^2.0.0:
|
||||||
version "2.1.0"
|
version "2.1.0"
|
||||||
resolved "https://registry.yarnpkg.com/import-cwd/-/import-cwd-2.1.0.tgz#aa6cf36e722761285cb371ec6519f53e2435b0a9"
|
resolved "https://registry.yarnpkg.com/import-cwd/-/import-cwd-2.1.0.tgz#aa6cf36e722761285cb371ec6519f53e2435b0a9"
|
||||||
@ -4991,6 +4996,13 @@ levn@^0.3.0, levn@~0.3.0:
|
|||||||
prelude-ls "~1.1.2"
|
prelude-ls "~1.1.2"
|
||||||
type-check "~0.3.2"
|
type-check "~0.3.2"
|
||||||
|
|
||||||
|
lie@3.1.1:
|
||||||
|
version "3.1.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/lie/-/lie-3.1.1.tgz#9a436b2cc7746ca59de7a41fa469b3efb76bd87e"
|
||||||
|
integrity sha1-mkNrLMd0bKWd56QfpGmz77dr2H4=
|
||||||
|
dependencies:
|
||||||
|
immediate "~3.0.5"
|
||||||
|
|
||||||
load-bmfont@^1.2.3:
|
load-bmfont@^1.2.3:
|
||||||
version "1.3.0"
|
version "1.3.0"
|
||||||
resolved "https://registry.yarnpkg.com/load-bmfont/-/load-bmfont-1.3.0.tgz#bb7e7c710de6bcafcb13cb3b8c81e0c0131ecbc9"
|
resolved "https://registry.yarnpkg.com/load-bmfont/-/load-bmfont-1.3.0.tgz#bb7e7c710de6bcafcb13cb3b8c81e0c0131ecbc9"
|
||||||
@ -5059,6 +5071,13 @@ loader-utils@^1.2.1:
|
|||||||
emojis-list "^2.0.0"
|
emojis-list "^2.0.0"
|
||||||
json5 "^1.0.1"
|
json5 "^1.0.1"
|
||||||
|
|
||||||
|
localforage@^1.7.3:
|
||||||
|
version "1.7.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/localforage/-/localforage-1.7.3.tgz#0082b3ca9734679e1bd534995bdd3b24cf10f204"
|
||||||
|
integrity sha512-1TulyYfc4udS7ECSBT2vwJksWbkwwTX8BzeUIiq8Y07Riy7bDAAnxDaPU/tWyOVmQAcWJIEIFP9lPfBGqVoPgQ==
|
||||||
|
dependencies:
|
||||||
|
lie "3.1.1"
|
||||||
|
|
||||||
locate-path@^2.0.0:
|
locate-path@^2.0.0:
|
||||||
version "2.0.0"
|
version "2.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e"
|
resolved "https://registry.yarnpkg.com/locate-path/-/locate-path-2.0.0.tgz#2b568b265eec944c6d9c0de9c3dbbbca0354cd8e"
|
||||||
|
Loading…
Reference in New Issue
Block a user