diff --git a/.eslintrc.js b/.eslintrc.js index e872f32e6b..a75cef168d 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -80,7 +80,7 @@ module.exports = { // TypeScript quotes: ['warn', 'single', { avoidEscape: true }], '@typescript-eslint/explicit-function-return-type': 'off', - "@typescript-eslint/unbound-method": "off", + '@typescript-eslint/unbound-method': 'off', '@typescript-eslint/no-unsafe-assignment': 'off', '@typescript-eslint/no-unsafe-member-access': 'off', diff --git a/.gitignore b/.gitignore index 553e1345ce..ba040ccf8e 100644 --- a/.gitignore +++ b/.gitignore @@ -3,7 +3,6 @@ node_modules # Quasar core related directories -.quasar /dist # Cordova related directories and files diff --git a/.quasar/app.js b/.quasar/app.js new file mode 100644 index 0000000000..98059068be --- /dev/null +++ b/.quasar/app.js @@ -0,0 +1,39 @@ +/** + * THIS FILE IS GENERATED AUTOMATICALLY. + * DO NOT EDIT. + * + * You are probably looking on adding startup/initialization code. + * Use "quasar new boot " and add it there. + * One boot file per concern. Then reference the file(s) in quasar.conf.js > boot: + * boot: ['file', ...] // do not add ".js" extension to it. + * + * Boot files are your "main.js" + **/ + +import { Quasar } from 'quasar'; +import RootComponent from 'app/src/App.vue'; + +import createRouter from 'app/src/router/index'; + +export default async function (createAppFn, quasarUserOptions) { + // create store and router instances + + const router = typeof createRouter === 'function' ? await createRouter({}) : createRouter; + + // Create the app instance. + // Here we inject into it the Quasar UI, the router & possibly the store. + const app = createAppFn(RootComponent); + + app.config.devtools = true; + + app.use(Quasar, quasarUserOptions); + + // Expose the app, the router and the store. + // Note that we are not mounting the app here, since bootstrapping will be + // different depending on whether we are in a browser or on the server. + return { + app, + + router, + }; +} diff --git a/.quasar/client-entry.js b/.quasar/client-entry.js new file mode 100644 index 0000000000..347747d8da --- /dev/null +++ b/.quasar/client-entry.js @@ -0,0 +1,100 @@ +/** + * THIS FILE IS GENERATED AUTOMATICALLY. + * DO NOT EDIT. + * + * You are probably looking on adding startup/initialization code. + * Use "quasar new boot " and add it there. + * One boot file per concern. Then reference the file(s) in quasar.conf.js > boot: + * boot: ['file', ...] // do not add ".js" extension to it. + * + * Boot files are your "main.js" + **/ + +import { createApp } from 'vue'; + +import '@quasar/extras/roboto-font/roboto-font.css'; + +import '@quasar/extras/material-icons/material-icons.css'; + +// We load Quasar stylesheet file +import 'quasar/dist/quasar.sass'; + +import 'src/css/app.scss'; + +import createQuasarApp from './app.js'; +import quasarUserOptions from './quasar-user-options.js'; + +console.info('[Quasar] Running SPA.'); + +const publicPath = ``; + +async function start({ app, router }, bootFiles) { + let hasRedirected = false; + const getRedirectUrl = (url) => { + try { + return router.resolve(url).href; + } catch (err) {} + + return Object(url) === url ? null : url; + }; + const redirect = (url) => { + hasRedirected = true; + + if (typeof url === 'string' && /^https?:\/\//.test(url)) { + window.location.href = url; + return; + } + + const href = getRedirectUrl(url); + + // continue if we didn't fail to resolve the url + if (href !== null) { + window.location.href = href; + window.location.reload(); + } + }; + + const urlPath = window.location.href.replace(window.location.origin, ''); + + for (let i = 0; hasRedirected === false && i < bootFiles.length; i++) { + try { + await bootFiles[i]({ + app, + router, + + ssrContext: null, + redirect, + urlPath, + publicPath, + }); + } catch (err) { + if (err && err.url) { + redirect(err.url); + return; + } + + console.error('[Quasar] boot error:', err); + return; + } + } + + if (hasRedirected === true) { + return; + } + + app.use(router); + + app.mount('#q-app'); +} + +createQuasarApp(createApp, quasarUserOptions).then((app) => { + return Promise.all([ + import(/* webpackMode: "eager" */ 'boot/i18n'), + + import(/* webpackMode: "eager" */ 'boot/axios'), + ]).then((bootFiles) => { + const boot = bootFiles.map((entry) => entry.default).filter((entry) => typeof entry === 'function'); + + start(app, boot); + }); +}); diff --git a/.quasar/client-prefetch.js b/.quasar/client-prefetch.js new file mode 100644 index 0000000000..d8a377bc65 --- /dev/null +++ b/.quasar/client-prefetch.js @@ -0,0 +1,113 @@ +/** + * THIS FILE IS GENERATED AUTOMATICALLY. + * DO NOT EDIT. + * + * You are probably looking on adding startup/initialization code. + * Use "quasar new boot " and add it there. + * One boot file per concern. Then reference the file(s) in quasar.conf.js > boot: + * boot: ['file', ...] // do not add ".js" extension to it. + * + * Boot files are your "main.js" + **/ + +import App from 'app/src/App.vue'; +let appPrefetch = + typeof App.preFetch === 'function' + ? App.preFetch + : // Class components return the component options (and the preFetch hook) inside __c property + App.__c !== void 0 && typeof App.__c.preFetch === 'function' + ? App.__c.preFetch + : false; + +function getMatchedComponents(to, router) { + const route = to ? (to.matched ? to : router.resolve(to).route) : router.currentRoute; + + if (!route) { + return []; + } + + return Array.prototype.concat.apply( + [], + route.matched.map((m) => { + return Object.keys(m.components).map((key) => { + const comp = m.components[key]; + return { + path: m.path, + c: comp, + }; + }); + }) + ); +} + +export function addPreFetchHooks(router, publicPath) { + // Add router hook for handling preFetch. + // Doing it after initial route is resolved so that we don't double-fetch + // the data that we already have. Using router.beforeResolve() so that all + // async components are resolved. + router.beforeResolve((to, from, next) => { + const urlPath = window.location.href.replace(window.location.origin, ''), + matched = getMatchedComponents(to, router), + prevMatched = getMatchedComponents(from, router); + + let diffed = false; + const preFetchList = matched + .filter((m, i) => { + return ( + diffed || + (diffed = + !prevMatched[i] || prevMatched[i].c !== m.c || m.path.indexOf('/:') > -1) // does it has params? + ); + }) + .filter( + (m) => + m.c !== void 0 && + (typeof m.c.preFetch === 'function' || + // Class components return the component options (and the preFetch hook) inside __c property + (m.c.__c !== void 0 && typeof m.c.__c.preFetch === 'function')) + ) + .map((m) => (m.c.__c !== void 0 ? m.c.__c.preFetch : m.c.preFetch)); + + if (appPrefetch !== false) { + preFetchList.unshift(appPrefetch); + appPrefetch = false; + } + + if (preFetchList.length === 0) { + return next(); + } + + let hasRedirected = false; + const redirect = (url) => { + hasRedirected = true; + next(url); + }; + const proceed = () => { + if (hasRedirected === false) { + next(); + } + }; + + preFetchList + .reduce( + (promise, preFetch) => + promise.then( + () => + hasRedirected === false && + preFetch({ + currentRoute: to, + previousRoute: from, + redirect, + urlPath, + publicPath, + }) + ), + Promise.resolve() + ) + .then(proceed) + .catch((e) => { + console.error(e); + proceed(); + }); + }); +} diff --git a/.quasar/quasar-user-options.js b/.quasar/quasar-user-options.js new file mode 100644 index 0000000000..2067ab15ec --- /dev/null +++ b/.quasar/quasar-user-options.js @@ -0,0 +1,15 @@ +/** + * THIS FILE IS GENERATED AUTOMATICALLY. + * DO NOT EDIT. + * + * You are probably looking on adding startup/initialization code. + * Use "quasar new boot " and add it there. + * One boot file per concern. Then reference the file(s) in quasar.conf.js > boot: + * boot: ['file', ...] // do not add ".js" extension to it. + * + * Boot files are your "main.js" + **/ + +import { Notify } from 'quasar'; + +export default { config: {}, plugins: { Notify } }; diff --git a/.vscode/extensions.json b/.vscode/extensions.json deleted file mode 100644 index 7ea549438c..0000000000 --- a/.vscode/extensions.json +++ /dev/null @@ -1,15 +0,0 @@ -{ - "recommendations": [ - "dbaeumer.vscode-eslint", - "esbenp.prettier-vscode", - "editorconfig.editorconfig", - "johnsoncodehk.volar", - "wayou.vscode-todo-highlight" - ], - "unwantedRecommendations": [ - "octref.vetur", - "hookyqr.beautify", - "dbaeumer.jshint", - "ms-vscode.vscode-typescript-tslint-plugin" - ] -} \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json index 8524288200..d5d3d57022 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,42 +1,7 @@ { - "editor.bracketPairColorization.enabled": true, - "editor.guides.bracketPairs": true, - "editor.formatOnSave": true, - "editor.defaultFormatter": "esbenp.prettier-vscode", - "editor.codeActionsOnSave": [ - "source.fixAll.eslint" - ], - "eslint.validate": [ - "javascript", - "javascriptreact", - "typescript", - "vue" - ], - "typescript.tsdk": "node_modules/typescript/lib", - "[typescript]": { - "editor.defaultFormatter": "vscode.typescript-language-features" - }, - "[jsonc]": { - "editor.defaultFormatter": "vscode.json-language-features" - }, - "[json]": { - "editor.defaultFormatter": "vscode.json-language-features" - }, - "[javascript]": { - "editor.defaultFormatter": "vscode.typescript-language-features" - }, - "[vue]": { - "editor.defaultFormatter": "johnsoncodehk.volar" - }, - "[html]": { - "editor.defaultFormatter": "vscode.html-language-features" - }, - "json.schemas": [ - { - "fileMatch": [ - "cypress.json" - ], - "url": "https://on.cypress.io/cypress.schema.json" - } - ] -} \ No newline at end of file + "editor.bracketPairColorization.enabled": true, + "editor.guides.bracketPairs": true, + "editor.formatOnSave": true, + "editor.codeActionsOnSave": ["source.fixAll.eslint"], + "eslint.validate": ["javascript", "javascriptreact", "typescript", "vue"] +} diff --git a/cypress.json b/cypress.json index b61558fc1b..a8b2f0d73d 100644 --- a/cypress.json +++ b/cypress.json @@ -12,4 +12,4 @@ "testFiles": "**/*.spec.js", "supportFile": "test/cypress/support/unit.js" } -} \ No newline at end of file +} diff --git a/jest.config.js b/jest.config.js index 2d0e5062bf..6b689d0c99 100755 --- a/jest.config.js +++ b/jest.config.js @@ -74,8 +74,7 @@ module.exports = { // (sync) .babelrc, .babelrc.js, babel.config.js, package.json // https://github.com/tleunen/find-babel-config/issues/33 '.*\\.vue$': 'vue-jest', - '.+\\.(css|styl|less|sass|scss|svg|png|jpg|ttf|woff|woff2)$': - 'jest-transform-stub', + '.+\\.(css|styl|less|sass|scss|svg|png|jpg|ttf|woff|woff2)$': 'jest-transform-stub', }, transformIgnorePatterns: [`node_modules/(?!(${esModules}))`], snapshotSerializers: ['/node_modules/jest-serializer-vue'], diff --git a/package.json b/package.json index 0e37483d64..ed712847b5 100644 --- a/package.json +++ b/package.json @@ -57,4 +57,4 @@ "npm": ">= 6.13.4", "yarn": ">= 1.21.1" } -} \ No newline at end of file +} diff --git a/quasar.extensions.json b/quasar.extensions.json index 2166ebc4fd..7360342421 100644 --- a/quasar.extensions.json +++ b/quasar.extensions.json @@ -1,14 +1,9 @@ { "@quasar/testing-unit-jest": { "babel": "babelrc", - "options": [ - "scripts", - "typescript" - ] + "options": ["scripts", "typescript"] }, "@quasar/testing-e2e-cypress": { - "options": [ - "scripts" - ] + "options": ["scripts"] } -} \ No newline at end of file +} diff --git a/quasar.testing.json b/quasar.testing.json index 80ed137c23..7aeb565382 100644 --- a/quasar.testing.json +++ b/quasar.testing.json @@ -8,4 +8,4 @@ "unit-cypress": { "runnerCommand": "cypress run-ct" } -} \ No newline at end of file +} diff --git a/src/boot/axios.ts b/src/boot/axios.ts index 2fff62c648..016306dbfd 100644 --- a/src/boot/axios.ts +++ b/src/boot/axios.ts @@ -4,7 +4,6 @@ import axios, { AxiosInstance } from 'axios'; import { useSession } from 'src/composables/useSession'; const { getToken } = useSession(); - declare module '@vue/runtime-core' { interface ComponentCustomProperties { $axios: AxiosInstance; @@ -34,7 +33,6 @@ axios.interceptors.request.use( } ); - export default boot(({ app }) => { // for use inside Vue files (Options API) through this.$axios and this.$api diff --git a/src/boot/i18n.ts b/src/boot/i18n.ts index d6b5586576..4f2a91f01a 100644 --- a/src/boot/i18n.ts +++ b/src/boot/i18n.ts @@ -13,4 +13,4 @@ export default boot(({ app }) => { app.use(i18n); }); -export { i18n }; \ No newline at end of file +export { i18n }; diff --git a/src/components/Navbar.vue b/src/components/Navbar.vue index 1534c0a2e3..ef05399299 100644 --- a/src/components/Navbar.vue +++ b/src/components/Navbar.vue @@ -1,7 +1,7 @@