From 09d8d36678ec97cbb971010dbebbefa6a7f896df Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Wed, 23 Mar 2022 16:21:06 +0100 Subject: [PATCH 01/22] Apply code changes from migration guide for Vue 3 --- client/build/webpack.base.conf.js | 2 +- client/src/App.vue | 68 ++-- client/src/components/HeaderBar.vue | 17 +- client/src/components/MobileHeader.vue | 2 +- client/src/components/ScrollUp.vue | 2 +- client/src/components/StudentSubmission.vue | 28 +- .../book-navigation/ContentNavigation.vue | 10 +- .../book-navigation/TopicNavigation.vue | 2 +- .../content-block-form/ContentBlockForm.vue | 4 +- .../ContentElementActions.vue | 4 +- .../src/components/content-forms/TipTap.vue | 46 +++ .../components/instruments/FilterGroup.vue | 5 +- .../components/page-form/PageFormInput.vue | 2 +- .../components/portfolio/ProjectEntryForm.vue | 37 +- .../src/components/portfolio/ProjectForm.vue | 32 ++ .../src/components/profile/EditNameWizard.vue | 24 ++ .../ui/file-upload/SimpleFileUpload.vue | 12 + .../file-upload/SimpleFileUploadWithIcon.vue | 2 +- .../directives/{auto-grow.js => auto-grow.ts} | 6 +- client/src/directives/click-outside.js | 14 - client/src/directives/click-outside.ts | 23 ++ client/src/layouts/DefaultFooter.vue | 217 +++++++----- client/src/layouts/PublicLayout.vue | 103 +++--- client/src/main.js | 160 +++++---- client/src/pages/article.vue | 212 ++++++------ client/src/pages/createContentBlock.vue | 145 ++++---- client/src/pages/portfolio/project.vue | 2 +- client/src/pages/topic-page.vue | 324 +++++++++--------- client/src/plugins/modal.ts | 51 +-- client/src/shims-vue.d.ts | 20 +- 30 files changed, 903 insertions(+), 673 deletions(-) rename client/src/directives/{auto-grow.js => auto-grow.ts} (80%) delete mode 100644 client/src/directives/click-outside.js create mode 100644 client/src/directives/click-outside.ts diff --git a/client/build/webpack.base.conf.js b/client/build/webpack.base.conf.js index 6ef67bcb..1e4a0590 100644 --- a/client/build/webpack.base.conf.js +++ b/client/build/webpack.base.conf.js @@ -42,7 +42,7 @@ module.exports = { '@': resolve('src'), styles: resolve('src/styles'), gql: resolve('src/graphql/gql'), - // vue: '@vue/compat', + vue: '@vue/compat', }, }, module: { diff --git a/client/src/App.vue b/client/src/App.vue index 253967df..8eda5d14 100644 --- a/client/src/App.vue +++ b/client/src/App.vue @@ -9,38 +9,54 @@ diff --git a/client/src/components/book-navigation/ContentNavigation.vue b/client/src/components/book-navigation/ContentNavigation.vue index 5edec89a..dd1d171d 100644 --- a/client/src/components/book-navigation/ContentNavigation.vue +++ b/client/src/components/book-navigation/ContentNavigation.vue @@ -7,7 +7,7 @@ :to="topicRoute" active-class="content-navigation__link--active" class="content-navigation__link" - @click.native="close" + @click="close" > {{ $flavor.textTopics }} @@ -20,7 +20,7 @@ to="/instruments" active-class="content-navigation__link--active" class="content-navigation__link" - @click.native="close" + @click="close" > {{ $flavor.textInstruments }} @@ -33,7 +33,7 @@ class="content-navigation__link" data-cy="news-navigation-link" v-if="!me.readOnly" - @click.native="close" + @click="close" > News @@ -51,7 +51,7 @@ to="/rooms" active-class="content-navigation__link--active" class="content-navigation__link content-navigation__link--secondary" - @click.native="close" + @click="close" > Räume @@ -62,7 +62,7 @@ to="/portfolio" active-class="content-navigation__link--active" class="content-navigation__link content-navigation__link--secondary" - @click.native="close" + @click="close" > Portfolio diff --git a/client/src/components/book-navigation/TopicNavigation.vue b/client/src/components/book-navigation/TopicNavigation.vue index f42e7c55..77fc9e34 100644 --- a/client/src/components/book-navigation/TopicNavigation.vue +++ b/client/src/components/book-navigation/TopicNavigation.vue @@ -8,7 +8,7 @@ class="topic-navigation__topic book-subnavigation__item" v-for="topic in topics" :key="topic.id" - @click.native="closeSidebar('navigation')" + @click="closeSidebar('navigation')" > {{ topic.order }}. {{ topic.title }} diff --git a/client/src/components/content-block-form/ContentBlockForm.vue b/client/src/components/content-block-form/ContentBlockForm.vue index 96408ad4..d49b3f78 100644 --- a/client/src/components/content-block-form/ContentBlockForm.vue +++ b/client/src/components/content-block-form/ContentBlockForm.vue @@ -105,7 +105,7 @@ diff --git a/client/src/layouts/PublicLayout.vue b/client/src/layouts/PublicLayout.vue index 83152953..319b4f70 100644 --- a/client/src/layouts/PublicLayout.vue +++ b/client/src/layouts/PublicLayout.vue @@ -1,73 +1,80 @@ + diff --git a/client/src/main.js b/client/src/main.js index 00ee9f5b..7a10cf2d 100644 --- a/client/src/main.js +++ b/client/src/main.js @@ -1,5 +1,5 @@ import '@babel/polyfill'; -import Vue from 'vue'; +import {createApp, inject} from 'vue'; import VueVimeoPlayer from 'vue-vimeo-player'; import apolloClientFactory from './graphql/client'; import VueApollo from 'vue-apollo'; @@ -13,42 +13,9 @@ import ME_QUERY from '@/graphql/gql/queries/meQuery.gql'; import VueModal from '@/plugins/modal'; import VueRemoveEdges from '@/plugins/edges'; import VueMatomo from 'vue-matomo'; +import VueLogger from 'vuejs3-logger'; import { joiningClass, loginRequired, unauthorizedAccess } from '@/router/guards'; import flavorPlugin from '@/plugins/flavor'; -import log from 'loglevel'; - -window.log = log; // make log available in app when built, to change log level: log.setLevel('debug') - -Vue.config.productionTip = false; -const isProduction = process.env.NODE_ENV === 'production'; - -const logLevel = isProduction ? 'error' : 'warn'; - -log.setDefaultLevel(logLevel); - -Vue.use(VueModal); -Vue.use(VueRemoveEdges); -Vue.use(VueApollo); -Vue.use(VueVimeoPlayer); - -Vue.use(VueScrollTo, { - duration: 500, - easing: 'ease-out', - offset: -50, -}); - -Vue.use(flavorPlugin); - -if (process.env.MATOMO_HOST) { - Vue.use(VueMatomo, { - host: process.env.MATOMO_HOST, - siteId: process.env.MATOMO_SITE_ID, - router: router, - }); -} - -Vue.directive('click-outside', clickOutside); -Vue.directive('auto-grow', autoGrow); const publicApolloClient = apolloClientFactory('/api/graphql-public/', null); const privateApolloClient = apolloClientFactory('/api/graphql/', networkErrorCallback); @@ -60,56 +27,96 @@ const apolloProvider = new VueApollo({ defaultClient: privateApolloClient, }); +const app = createApp({ + store, + router, + apolloProvider, + render: h => h(App), +}); + + +const isProduction = process.env.NODE_ENV === 'production'; + +app.use(VueModal); +app.use(VueRemoveEdges); +app.use(VueApollo); +app.use(VueVimeoPlayer); +app.use(VueLogger, { + isEnabled: true, + logLevel: isProduction ? 'error' : 'debug', + stringifyArguments: false, + showConsoleColors: true, +}); + +// VueScrollTo.setDefaults({ +// duration: 500, +// easing: 'ease-out', +// offset: -50, +// }); + +app.directive('scroll-to', VueScrollTo); + + +app.use(flavorPlugin); + +if (process.env.MATOMO_HOST) { + app.use(VueMatomo, { + host: process.env.MATOMO_HOST, + siteId: process.env.MATOMO_SITE_ID, + router: router, + }); +} + +app.directive('click-outside', clickOutside); +app.directive('auto-grow', autoGrow); + /* guards */ + + function redirectUsersWithoutValidLicense() { - return privateApolloClient - .query({ - query: ME_QUERY, - }) - .then(({ data }) => data.me.expiryDate == null); + return privateApolloClient.query({ + query: ME_QUERY, + }).then(({data}) => data.me.expiryDate == null); } function redirectStudentsWithoutClass() { - return privateApolloClient - .query({ - query: ME_QUERY, - }) - .then(({ data }) => data.me.schoolClasses.length === 0 && !data.me.isTeacher); + return privateApolloClient.query({ + query: ME_QUERY, + }).then(({data}) => data.me.schoolClasses.length === 0 && !data.me.isTeacher); } function redirectUsersToOnboarding() { - return privateApolloClient - .query({ - query: ME_QUERY, - }) - .then(({ data }) => !data.me.onboardingVisited); + return privateApolloClient.query({ + query: ME_QUERY, + }).then(({data}) => !data.me.onboardingVisited); } function networkErrorCallback(statusCode) { if (statusCode === 402) { - log.debug('status code 402, redirecting'); - router.push({ name: 'licenseActivation' }); + router.push({name: 'licenseActivation'}); } } + router.beforeEach(async (to, from, next) => { - log.debug('navigation guard called', to, from); + // todo: make logger work outside vue app + // const logger = inject('vuejs3-logger'); + // logger.$log.debug('navigation guard called', to, from); if (to.path === '/logout') { - log.debug('logout', to); - publicApolloClient.resetStore(); + await publicApolloClient.resetStore(); if (process.env.LOGOUT_REDIRECT_URL) { location.replace(`https://sso.hep-verlag.ch/logout?return_to=${process.env.LOGOUT_REDIRECT_URL}`); next(false); return; } else { - next({ name: 'hello' }); + next({name: 'hello'}); return; } } if (unauthorizedAccess(to)) { - log.debug('unauthorized', to); + //logger.$log.debug('unauthorized', to); const postLoginRedirectionUrl = to.path; const redirectUrl = `/hello/`; @@ -117,46 +124,33 @@ router.beforeEach(async (to, from, next) => { localStorage.setItem(postLoginRedirectUrlKey, postLoginRedirectionUrl); } - log.debug('redirecting to hello', to); + // logger.$log.debug('redirecting to hello', to); next(redirectUrl); return; } - if (to.name && to.name !== 'licenseActivation' && loginRequired(to) && (await redirectUsersWithoutValidLicense())) { - log.debug('redirecting to licenseActivation', to, null); + if (to.name && to.name !== 'licenseActivation' && loginRequired(to) && await redirectUsersWithoutValidLicense()) { + // logger.$log.debug('redirecting to licenseActivation', to, null); console.log('redirecting to licenseActivation', to, null); - next({ name: 'licenseActivation' }); + next({name: 'licenseActivation'}); return; } - if (!joiningClass(to) && loginRequired(to) && (await redirectStudentsWithoutClass())) { - log.debug('redirecting to join-class', to); - log.debug('await redirectStudentsWithoutClass()', await redirectStudentsWithoutClass()); - next({ name: 'join-class' }); + if (!joiningClass(to) && loginRequired(to) && await redirectStudentsWithoutClass()) { + //logger.$log.debug('redirecting to join-class', to); + //logger.$log.debug('await redirectStudentsWithoutClass()', await redirectStudentsWithoutClass()); + next({name: 'join-class'}); return; } - if ( - to.name && - to.name.indexOf('onboarding') === -1 && - !joiningClass(to) && - loginRequired(to) && - (await redirectUsersToOnboarding()) - ) { - log.debug('redirecting to onboarding-start', to); - next({ name: 'onboarding-start' }); + if ((to.name && to.name.indexOf('onboarding') === -1) && !joiningClass(to) && loginRequired(to) && await redirectUsersToOnboarding()) { + //logger.$log.debug('redirecting to onboarding-start', to); + next({name: 'onboarding-start'}); return; } - log.debug('End of Guard reached', to); + //logger.$log.debug('End of Guard reached', to); next(); }); -/* eslint-disable no-new */ -new Vue({ - el: '#app', - store, - router, - apolloProvider, - render: (h) => h(App), -}); +app.mount('#app'); diff --git a/client/src/pages/article.vue b/client/src/pages/article.vue index 9e781ef6..1781fc08 100644 --- a/client/src/pages/article.vue +++ b/client/src/pages/article.vue @@ -4,128 +4,132 @@
-

+

{{ roomEntry.title }}

- +
- +
diff --git a/client/src/pages/createContentBlock.vue b/client/src/pages/createContentBlock.vue index e9e3fa0b..725a77cd 100644 --- a/client/src/pages/createContentBlock.vue +++ b/client/src/pages/createContentBlock.vue @@ -1,82 +1,85 @@ diff --git a/client/src/pages/portfolio/project.vue b/client/src/pages/portfolio/project.vue index 8614e71e..966eb8a8 100644 --- a/client/src/pages/portfolio/project.vue +++ b/client/src/pages/portfolio/project.vue @@ -8,7 +8,7 @@ :final="project.final" data-cy="project-share-link" class="project__share" - @click.native="updateProjectShareState(project.slug, !project.final)" + @click="updateProjectShareState(project.slug, !project.final)" /> diff --git a/client/src/pages/topic-page.vue b/client/src/pages/topic-page.vue index 379f6b89..fe29f0ad 100644 --- a/client/src/pages/topic-page.vue +++ b/client/src/pages/topic-page.vue @@ -5,14 +5,21 @@
-

+

{{ topic.title }}

{{ topic.teaser }}

diff --git a/client/src/plugins/modal.ts b/client/src/plugins/modal.ts index 8f8f2b00..1fde72e7 100644 --- a/client/src/plugins/modal.ts +++ b/client/src/plugins/modal.ts @@ -1,51 +1,51 @@ // adapted from // https://stackoverflow.com/questions/41791193/vuejs-reactive-binding-for-a-plugin-how-to/41801107#41801107 -import Vue, { VueConstructor } from 'vue'; +import {reactive, App} from 'vue'; class ModalStore { - vm: Vue; + data: any; constructor() { - this.vm = new Vue({ - data: () => ({ - component: '', - payload: {}, - }), + this.data = reactive({ + component: '', + payload: {} }); } get state() { - return this.vm.$data; + return this.data; } } interface Modal { - state: any; - component: string; - payload?: any; - confirm: (res: any) => void; - open: (component: string, payload?: any) => Promise<(resolve: () => any, reject: () => any) => void>; - cancel: () => void; - _resolve: (r?: any) => any; - _reject: (r?: any) => any; + state: any, + component: string, + payload?: any, + confirm: (res: any) => void, + open: (component: string, payload?: any) => Promise<(resolve: () => any, reject: () => any) => void>, + cancel: () => void, + _resolve: (r?: any) => any, + _reject: (r?: any) => any } -declare module 'vue/types/vue' { - interface Vue { - $modal: Modal; +declare module '@vue/runtime-core' { + interface ComponentCustomProperties { + $modal: Modal } } const ModalPlugin = { - install(Vue: VueConstructor) { + install(app: App) { const store = new ModalStore(); + console.log('installing modal plugin'); + const reset = () => { store.state.component = ''; store.state.payload = {}; }; - const modal: Modal = { + app.config.globalProperties.$modal = { state: store.state, component: store.state.component, payload: store.state.payload, @@ -65,12 +65,13 @@ const ModalPlugin = { reset(); this._reject(); }, - _resolve: () => {}, - _reject: () => {}, + _resolve: () => { + }, + _reject: () => { + }, }; - Vue.prototype.$modal = modal; - }, + } }; export default ModalPlugin; diff --git a/client/src/shims-vue.d.ts b/client/src/shims-vue.d.ts index cbcbd6f8..aec01676 100644 --- a/client/src/shims-vue.d.ts +++ b/client/src/shims-vue.d.ts @@ -1,13 +1,13 @@ // from https://stackoverflow.com/questions/64213461/vuejs-typescript-cannot-find-module-components-navigation-or-its-correspon -declare module '*.vue' { - import Vue from 'vue'; - export default Vue; -} +// declare module "*.vue" { +// import Vue from 'vue'; +// export default Vue; +// } // for Vue 3 -// declare module '*.vue' { -// import type { DefineComponent } from 'vue' -// const component: DefineComponent<{}, {}, any> -// export default component -// } -// +declare module '*.vue' { + import type { DefineComponent } from 'vue'; + const component: DefineComponent<{}, {}, any>; + export default component; +} + From 578b563b7b6047f9e1a8ab060aa2d746f8b15363 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Wed, 23 Mar 2022 16:22:36 +0100 Subject: [PATCH 02/22] Update npm dependencies --- client/package.json | 41 +++++++++++++++-------------------------- 1 file changed, 15 insertions(+), 26 deletions(-) diff --git a/client/package.json b/client/package.json index 0ea63120..8c608b45 100644 --- a/client/package.json +++ b/client/package.json @@ -4,9 +4,6 @@ "description": "skillbox vue client", "author": "ramon / chrigu", "private": true, - "prettier": { - "singleQuote": true - }, "scripts": { "dev": "webpack serve --progress --config build/webpack.dev.conf.js", "analyze": "webpack --profile --json --config build/webpack.dev.conf.js > dist/stats.json && webpack-bundle-analyzer dist/stats.json", @@ -25,9 +22,7 @@ "install:cypress": "cypress install", "test:unit": "jest", "cypress:parallel": "CYPRESS_API_URL=\"https://iterativ-cypress-director.herokuapp.com/\" cy2 run --parallel --record --key somekey --config-file cypress.frontend.json --ci-build-id some-id", - "cypress:parallel:run": "cy2 run --parallel --record --config-file cypress.frontend.json --ci-build-id ", - "prettier": "prettier . --write", - "prettier:check": "prettier . --check" + "cypress:parallel:run": "cy2 run --parallel --record --config-file cypress.frontend.json --ci-build-id " }, "dependencies": { "@apollo/client": "^3.5.8", @@ -51,6 +46,7 @@ "@tiptap/vue-2": "^2.0.0-beta.77", "@typescript-eslint/eslint-plugin": "^5.10.0", "@typescript-eslint/parser": "^5.10.0", + "@vue/compat": "3.2.31", "@vue/test-utils": "^1.3.0", "@vue/vue2-jest": "^27.0.0", "autoprefixer": "^10.4.12", @@ -65,7 +61,6 @@ "cypress": "^10", "dayjs": "^1.10.7", "eslint": "^7.32.0", - "eslint-config-prettier": "^8.6.0", "eslint-formatter-friendly": "^7.0.0", "eslint-plugin-cypress": "^2.12.1", "eslint-plugin-vue": "^9.6.0", @@ -82,41 +77,41 @@ "jest-transform-stub": "^2.0.0", "jest-watch-typeahead": "^2.1.2", "lodash": "^4.17.10", - "loglevel": "^1.8.0", "mini-css-extract-plugin": "^2.4.5", "mock-apollo-client": "^1.2.0", + "node-sass": "^7.0.3", "ora": "^1.2.0", "portfinder": "^1.0.13", "postcss-import": "^15.0.0", "postcss-loader": "^7.0.1", "postcss-url": "^10.1.3", - "prettier": "2.8.2", "rimraf": "^2.6.0", - "sass": "^1.56.1", "sass-loader": "^12.6.0", "semver": "^5.3.0", "shelljs": "^0.8.5", - "survey-knockout": "^1.9.41", + "survey-core": "1.9.41", + "survey-knockout-ui": "1.9.41", "ts-loader": "^8.3.0", "typescript": "^4.5.4", "uploadcare-widget": "^3.6.0", - "url-loader": "^4.1.1", - "vee-validate": "^3.4.14", - "vue": "^2.7.13", + "url-loader": "^1.0.1", + "vee-validate": "^4.5.10", + "@vee-validate/rules": "^4.5.10", + "vue": "^3.2.31", "vue-apollo": "^3.1.0", - "vue-loader": "^15.10.0", + "vue-loader": "^16.8.3", "vue-matomo": "^4.1.0", "vue-router": "^3.5.3", - "vue-scrollto": "^2.11.0", + "vue-scrollto": "^2.20.0", "vue-style-loader": "^3.0.1", - "vue-template-compiler": "^2.7.13", "vue-vimeo-player": "^0.2.2", + "vuejs3-logger": "1.0.0", "vuex": "^3.0.1", "webpack": "^5.67.0", "webpack-bundle-analyzer": "^4.5.0", - "webpack-cli": "^4.9.1", "webpack-dev-server": "^4.6.0", - "webpack-merge": "^5.8.0" + "webpack-merge": "^5.8.0", + "webpack-cli": "^4.9.1" }, "engines": { "node": ">= 14.x", @@ -126,11 +121,5 @@ "> 1%", "last 2 versions", "not ie <= 8" - ], - "resolutions": { - "vue": "2.6.14" - }, - "optionalDependencies": { - "fsevents": "^2.3.2" - } + ] } From 6cf9457dca70969a51295a7b7388ffdfb5273236 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Wed, 23 Mar 2022 18:16:11 +0100 Subject: [PATCH 03/22] Update vue router version --- client/package.json | 10 +- client/src/components/BackLink.vue | 107 ++++---- client/src/components/ScrollUp.vue | 113 +++++---- .../book-navigation/NavigationSidebar.vue | 167 ++++++------ .../content-blocks/ContentComponent.vue | 178 +++++++------ .../components/content-blocks/Solution.vue | 141 ++++++----- .../components/modules/ModuleNavigation.vue | 1 + client/src/components/profile/Avatar.vue | 220 ++++++++-------- .../src/components/profile/ProfileSidebar.vue | 237 ++++++++++-------- client/src/main.js | 9 +- client/src/router/guards.ts | 8 +- client/src/router/index.js | 58 +++-- 12 files changed, 664 insertions(+), 585 deletions(-) diff --git a/client/package.json b/client/package.json index 8c608b45..1831a831 100644 --- a/client/package.json +++ b/client/package.json @@ -25,7 +25,7 @@ "cypress:parallel:run": "cy2 run --parallel --record --config-file cypress.frontend.json --ci-build-id " }, "dependencies": { - "@apollo/client": "^3.5.8", + "@apollo/client": "^3.5.10", "@babel/core": "^7.16.7", "@babel/eslint-plugin": "^7.16.5", "@babel/plugin-transform-runtime": "^7.5.0", @@ -46,6 +46,8 @@ "@tiptap/vue-2": "^2.0.0-beta.77", "@typescript-eslint/eslint-plugin": "^5.10.0", "@typescript-eslint/parser": "^5.10.0", + "@vue/apollo-option": "^4.0.0-alpha.16", + "@vue/compiler-sfc": "3.2.30", "@vue/compat": "3.2.31", "@vue/test-utils": "^1.3.0", "@vue/vue2-jest": "^27.0.0", @@ -96,12 +98,10 @@ "uploadcare-widget": "^3.6.0", "url-loader": "^1.0.1", "vee-validate": "^4.5.10", - "@vee-validate/rules": "^4.5.10", - "vue": "^3.2.31", - "vue-apollo": "^3.1.0", + "vue": "3.2.30", "vue-loader": "^16.8.3", "vue-matomo": "^4.1.0", - "vue-router": "^3.5.3", + "vue-router": "^4.0.14", "vue-scrollto": "^2.20.0", "vue-style-loader": "^3.0.1", "vue-vimeo-player": "^0.2.2", diff --git a/client/src/components/BackLink.vue b/client/src/components/BackLink.vue index 0fb0651f..89613070 100644 --- a/client/src/components/BackLink.vue +++ b/client/src/components/BackLink.vue @@ -1,68 +1,75 @@ diff --git a/client/src/components/ScrollUp.vue b/client/src/components/ScrollUp.vue index 10fd05fb..b031cdef 100644 --- a/client/src/components/ScrollUp.vue +++ b/client/src/components/ScrollUp.vue @@ -1,73 +1,78 @@ diff --git a/client/src/components/book-navigation/NavigationSidebar.vue b/client/src/components/book-navigation/NavigationSidebar.vue index 5ca4ed74..6b015508 100644 --- a/client/src/components/book-navigation/NavigationSidebar.vue +++ b/client/src/components/book-navigation/NavigationSidebar.vue @@ -1,8 +1,18 @@ diff --git a/client/src/components/content-blocks/ContentComponent.vue b/client/src/components/content-blocks/ContentComponent.vue index 9a9e9b60..93177354 100644 --- a/client/src/components/content-blocks/ContentComponent.vue +++ b/client/src/components/content-blocks/ContentComponent.vue @@ -1,5 +1,9 @@ diff --git a/client/src/components/content-blocks/Solution.vue b/client/src/components/content-blocks/Solution.vue index 287e9114..ac08d40d 100644 --- a/client/src/components/content-blocks/Solution.vue +++ b/client/src/components/content-blocks/Solution.vue @@ -1,95 +1,114 @@ diff --git a/client/src/components/modules/ModuleNavigation.vue b/client/src/components/modules/ModuleNavigation.vue index 54d4cc81..250edb26 100644 --- a/client/src/components/modules/ModuleNavigation.vue +++ b/client/src/components/modules/ModuleNavigation.vue @@ -5,6 +5,7 @@ :slug="module.topic.slug" class="module-navigation__topic-link" type="topic" + v-if="module.topic" />
diff --git a/client/src/components/profile/Avatar.vue b/client/src/components/profile/Avatar.vue index ee7ea5f2..94772cd5 100644 --- a/client/src/components/profile/Avatar.vue +++ b/client/src/components/profile/Avatar.vue @@ -2,23 +2,31 @@
- + -
- +
+
@@ -26,121 +34,119 @@ diff --git a/client/src/components/profile/ProfileSidebar.vue b/client/src/components/profile/ProfileSidebar.vue index 0244e4e7..bd1d9a61 100644 --- a/client/src/components/profile/ProfileSidebar.vue +++ b/client/src/components/profile/ProfileSidebar.vue @@ -1,31 +1,69 @@ diff --git a/client/src/main.js b/client/src/main.js index 7a10cf2d..817a23b9 100644 --- a/client/src/main.js +++ b/client/src/main.js @@ -1,8 +1,7 @@ import '@babel/polyfill'; -import {createApp, inject} from 'vue'; +import {createApp} from 'vue'; import VueVimeoPlayer from 'vue-vimeo-player'; import apolloClientFactory from './graphql/client'; -import VueApollo from 'vue-apollo'; import App from './App.vue'; import { postLoginRedirectUrlKey, router } from './router'; import store from '@/store/index'; @@ -14,13 +13,14 @@ import VueModal from '@/plugins/modal'; import VueRemoveEdges from '@/plugins/edges'; import VueMatomo from 'vue-matomo'; import VueLogger from 'vuejs3-logger'; +import { createApolloProvider } from '@vue/apollo-option'; import { joiningClass, loginRequired, unauthorizedAccess } from '@/router/guards'; import flavorPlugin from '@/plugins/flavor'; const publicApolloClient = apolloClientFactory('/api/graphql-public/', null); const privateApolloClient = apolloClientFactory('/api/graphql/', networkErrorCallback); -const apolloProvider = new VueApollo({ +const apolloProvider = createApolloProvider({ clients: { publicClient: publicApolloClient, }, @@ -39,7 +39,6 @@ const isProduction = process.env.NODE_ENV === 'production'; app.use(VueModal); app.use(VueRemoveEdges); -app.use(VueApollo); app.use(VueVimeoPlayer); app.use(VueLogger, { isEnabled: true, @@ -47,6 +46,8 @@ app.use(VueLogger, { stringifyArguments: false, showConsoleColors: true, }); +app.use(apolloProvider); +app.use(router); // VueScrollTo.setDefaults({ // duration: 500, diff --git a/client/src/router/guards.ts b/client/src/router/guards.ts index 69c7e6ac..9bf105d3 100644 --- a/client/src/router/guards.ts +++ b/client/src/router/guards.ts @@ -1,4 +1,4 @@ -import { Route } from 'vue-router'; +import {RouteLocationNormalized} from "vue-router"; function getCookieValue(cookieName: string) { // https://stackoverflow.com/questions/5639346/what-is-the-shortest-function-for-reading-a-cookie-by-name-in-javascript @@ -6,16 +6,16 @@ function getCookieValue(cookieName: string) { return cookieValue ? cookieValue.pop() : ''; } -export function loginRequired(to: Route) { +export function loginRequired(to: RouteLocationNormalized) { // public pages have the meta.public property set to true const isPublic = to.meta && to.meta.public; return !isPublic; } -export function unauthorizedAccess(to: Route) { +export function unauthorizedAccess(to: RouteLocationNormalized) { return loginRequired(to) && getCookieValue('loginStatus') !== 'true'; } -export function joiningClass(to: Route) { +export function joiningClass(to: RouteLocationNormalized) { return to.name && (to.name === 'join-class' || to.name === 'licenseActivation'); } diff --git a/client/src/router/index.js b/client/src/router/index.js index e2dc764c..f5013956 100644 --- a/client/src/router/index.js +++ b/client/src/router/index.js @@ -1,6 +1,4 @@ -import Vue from 'vue'; - -import Router from 'vue-router'; +import {createRouter, createWebHistory} from 'vue-router'; import moduleRoutes from './module.routes'; import portfolioRoutes from './portfolio.routes'; @@ -10,26 +8,26 @@ import authRoutes from './auth.routes'; import roomRoutes from './room.routes'; import store from '@/store/index'; -import { LAYOUT_SIMPLE } from '@/router/core.constants'; -import { EMAIL_NOT_VERIFIED_STATE, NO_VALID_LICENSE_STATE, SUCCESS_STATE } from './oauth.names'; +import {LAYOUT_SIMPLE} from '@/router/core.constants'; +import {EMAIL_NOT_VERIFIED_STATE, NO_VALID_LICENSE_STATE, SUCCESS_STATE} from './oauth.names'; import start from '@/pages/start'; -const instrument = () => import(/* webpackChunkName: "instruments" */ '@/pages/instrument'); -const instrumentOverview = () => import(/* webpackChunkName: "instruments" */ '@/pages/instrumentOverview'); +const instrument = () => import(/* webpackChunkName: "instruments" */'@/pages/instrument'); +const instrumentOverview = () => import(/* webpackChunkName: "instruments" */'@/pages/instrumentOverview'); -const article = () => import(/* webpackChunkName: "news" */ '@/pages/article'); -const news = () => import(/* webpackChunkName: "news" */ '@/pages/news'); +const article = () => import(/* webpackChunkName: "news" */'@/pages/article'); +const news = () => import(/* webpackChunkName: "news" */'@/pages/news'); -const surveyPage = () => import(/* webpackChunkName: "survey" */ '@/pages/survey'); +const surveyPage = () => import(/* webpackChunkName: "survey" */'@/pages/survey'); -const styleGuidePage = () => import('@/pages/styleguide.vue'); -const joinClass = () => import('@/pages/joinClass.vue'); +const styleGuidePage = () => import('@/pages/styleguide'); +const joinClass = () => import('@/pages/joinClass'); -const topic = () => import('@/pages/topic-page.vue'); +const topic = () => import('@/pages/topic-page'); -const p404 = () => import('@/pages/p404.vue'); -const submission = () => import('@/pages/studentSubmission.vue'); +const p404 = () => import('@/pages/p404'); +const submission = () => import('@/pages/studentSubmission'); const postLoginRedirectUrlKey = 'postLoginRedirectionUrl'; @@ -52,22 +50,22 @@ const routes = [ ...onboardingRoutes, ...portfolioRoutes, ...meRoutes, - { path: '/article/:slug', name: 'article', component: article, meta: { layout: LAYOUT_SIMPLE } }, + {path: '/article/:slug', name: 'article', component: article, meta: {layout: LAYOUT_SIMPLE}}, { path: '/instruments/', name: 'instrument-overview', component: instrumentOverview, }, - { path: '/instrument/:slug', name: 'instrument', component: instrument, meta: { layout: LAYOUT_SIMPLE } }, - { path: '/submission/:id', name: 'submission', component: submission, meta: { layout: LAYOUT_SIMPLE } }, - { path: '/topic/:topicSlug', name: 'topic', component: topic, alias: '/book/topic/:topicSlug' }, - { path: '/join-class', name: 'join-class', component: joinClass, meta: { layout: LAYOUT_SIMPLE } }, + {path: '/instrument/:slug', name: 'instrument', component: instrument, meta: {layout: LAYOUT_SIMPLE}}, + {path: '/submission/:id', name: 'submission', component: submission, meta: {layout: LAYOUT_SIMPLE}}, + {path: '/topic/:topicSlug', name: 'topic', component: topic, alias: '/book/topic/:topicSlug'}, + {path: '/join-class', name: 'join-class', component: joinClass, meta: {layout: LAYOUT_SIMPLE}}, { path: '/survey/:id', component: surveyPage, name: 'survey', props: true, - meta: { layout: LAYOUT_SIMPLE }, + meta: {layout: LAYOUT_SIMPLE}, }, { path: '/news', @@ -76,7 +74,7 @@ const routes = [ }, { path: '/oauth-redirect', - redirect: (to) => { + redirect: to => { switch (to.query.state) { case EMAIL_NOT_VERIFIED_STATE: return '/verify-email'; @@ -94,28 +92,28 @@ const routes = [ } }, }, - { path: '/styleguide', component: styleGuidePage }, + {path: '/styleguide', component: styleGuidePage}, { path: '/not-found', name: 'not-found', - ...notFoundRoute, + ...notFoundRoute }, { - path: '*', - ...notFoundRoute, + path: '/:pathMatch(.*)*', + ...notFoundRoute }, ]; -Vue.use(Router); -const router = new Router({ +const router = createRouter({ routes, + history: createWebHistory(), mode: 'history', scrollBehavior(to, from, savedPosition) { if (savedPosition) { return savedPosition; } - return { x: 0, y: 0 }; + return {left: 0, top: 0}; }, }); @@ -124,4 +122,4 @@ router.afterEach(() => { store.dispatch('showMobileNavigation', false); }); -export { router, postLoginRedirectUrlKey }; +export {router, postLoginRedirectUrlKey}; From e116da3a5768e3c3ba1fdd3d2eb1929e0b520399 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Thu, 24 Mar 2022 07:10:22 +0100 Subject: [PATCH 04/22] Disable validation temporarily --- .../components/validation/ValidatedInput.vue | 171 ++++++++------- client/src/pages/beta-login.vue | 194 ++++++++++-------- 2 files changed, 210 insertions(+), 155 deletions(-) diff --git a/client/src/components/validation/ValidatedInput.vue b/client/src/components/validation/ValidatedInput.vue index 71908c15..c537be50 100644 --- a/client/src/components/validation/ValidatedInput.vue +++ b/client/src/components/validation/ValidatedInput.vue @@ -1,85 +1,108 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/client/src/pages/beta-login.vue b/client/src/pages/beta-login.vue index d5ce9361..5b1add29 100644 --- a/client/src/pages/beta-login.vue +++ b/client/src/pages/beta-login.vue @@ -1,81 +1,112 @@ From 07eb3062b3386ff33c65e18e37008a90ce357065 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Thu, 24 Mar 2022 07:11:48 +0100 Subject: [PATCH 05/22] Specify property --- client/src/components/HeaderBar.vue | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/src/components/HeaderBar.vue b/client/src/components/HeaderBar.vue index 696ee402..8f6e725c 100644 --- a/client/src/components/HeaderBar.vue +++ b/client/src/components/HeaderBar.vue @@ -13,7 +13,7 @@ From 097c353919923c3affe2660c8b4b2353ca679c28 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Thu, 24 Mar 2022 17:23:21 +0100 Subject: [PATCH 06/22] Update dependencies --- client/build/webpack.base.conf.js | 2 +- client/package.json | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/client/build/webpack.base.conf.js b/client/build/webpack.base.conf.js index 1e4a0590..eb381a30 100644 --- a/client/build/webpack.base.conf.js +++ b/client/build/webpack.base.conf.js @@ -60,7 +60,7 @@ module.exports = { }, compilerOptions: { compatConfig: { - MODE: 2, + MODE: 2 }, }, }, diff --git a/client/package.json b/client/package.json index 1831a831..8139f166 100644 --- a/client/package.json +++ b/client/package.json @@ -43,12 +43,12 @@ "@tiptap/extension-list-item": "^2.0.0-beta.20", "@tiptap/extension-paragraph": "^2.0.0-beta.23", "@tiptap/extension-text": "^2.0.0-beta.15", - "@tiptap/vue-2": "^2.0.0-beta.77", + "@tiptap/vue-3": "^2.0.0-beta.90", "@typescript-eslint/eslint-plugin": "^5.10.0", "@typescript-eslint/parser": "^5.10.0", "@vue/apollo-option": "^4.0.0-alpha.16", + "@vue/compat": "3.2.30", "@vue/compiler-sfc": "3.2.30", - "@vue/compat": "3.2.31", "@vue/test-utils": "^1.3.0", "@vue/vue2-jest": "^27.0.0", "autoprefixer": "^10.4.12", @@ -106,8 +106,8 @@ "vue-style-loader": "^3.0.1", "vue-vimeo-player": "^0.2.2", "vuejs3-logger": "1.0.0", - "vuex": "^3.0.1", "webpack": "^5.67.0", + "vuex": "4.0.1", "webpack-bundle-analyzer": "^4.5.0", "webpack-dev-server": "^4.6.0", "webpack-merge": "^5.8.0", From 5bc0c29ea0ff35d8cf690ab3061cb915f4a98519 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Thu, 24 Mar 2022 17:25:23 +0100 Subject: [PATCH 07/22] Update store to v4 --- .../EditContentBlockWizard.vue | 102 +++++++++--------- client/src/main.js | 16 +-- client/src/router/index.js | 2 +- client/src/store/index.js | 8 +- 4 files changed, 64 insertions(+), 64 deletions(-) diff --git a/client/src/components/content-block-form/EditContentBlockWizard.vue b/client/src/components/content-block-form/EditContentBlockWizard.vue index 26ed1b82..2549b675 100644 --- a/client/src/components/content-block-form/EditContentBlockWizard.vue +++ b/client/src/components/content-block-form/EditContentBlockWizard.vue @@ -1,75 +1,77 @@ diff --git a/client/src/main.js b/client/src/main.js index 817a23b9..0380d6eb 100644 --- a/client/src/main.js +++ b/client/src/main.js @@ -1,10 +1,10 @@ import '@babel/polyfill'; -import {createApp} from 'vue'; +import {createApp, configureCompat } from 'vue'; import VueVimeoPlayer from 'vue-vimeo-player'; import apolloClientFactory from './graphql/client'; import App from './App.vue'; -import { postLoginRedirectUrlKey, router } from './router'; -import store from '@/store/index'; +import {postLoginRedirectUrlKey, router} from './router'; +import { store } from '@/store'; import VueScrollTo from 'vue-scrollto'; import autoGrow from '@/directives/auto-grow'; import clickOutside from '@/directives/click-outside'; @@ -27,13 +27,13 @@ const apolloProvider = createApolloProvider({ defaultClient: privateApolloClient, }); -const app = createApp({ - store, - router, - apolloProvider, - render: h => h(App), +configureCompat({ + MODE: 2 }); +const app = createApp(App); + +app.use(store); const isProduction = process.env.NODE_ENV === 'production'; diff --git a/client/src/router/index.js b/client/src/router/index.js index f5013956..ddb1bbcc 100644 --- a/client/src/router/index.js +++ b/client/src/router/index.js @@ -7,7 +7,7 @@ import meRoutes from './me.routes'; import authRoutes from './auth.routes'; import roomRoutes from './room.routes'; -import store from '@/store/index'; +import {store} from '@/store'; import {LAYOUT_SIMPLE} from '@/router/core.constants'; import {EMAIL_NOT_VERIFIED_STATE, NO_VALID_LICENSE_STATE, SUCCESS_STATE} from './oauth.names'; diff --git a/client/src/store/index.js b/client/src/store/index.js index 293ac9d8..39f4848a 100644 --- a/client/src/store/index.js +++ b/client/src/store/index.js @@ -1,10 +1,8 @@ -import Vue from 'vue'; -import Vuex from 'vuex'; - -Vue.use(Vuex); +import {createStore} from 'vuex'; // WARNING fixme todo: please do not use this anymore, use the local GraphQL cache -export default new Vuex.Store({ +// export default new Vuex.Store({ +export const store = createStore({ modules: {}, state: { From 39e7d275871e762f964167968fd232b2cfd582c9 Mon Sep 17 00:00:00 2001 From: Ramon Wenger Date: Thu, 24 Mar 2022 17:31:18 +0100 Subject: [PATCH 08/22] Update async component definitions --- client/src/components/AddContentButton.vue | 159 ++--- client/src/components/AddContentElement.vue | 50 +- client/src/components/AddWidget.vue | 110 ++-- client/src/components/BackLink.vue | 3 +- client/src/components/ColorChooser.vue | 127 ++-- client/src/components/ContentBlock.vue | 618 +++++++++--------- .../src/components/FullscreenInfographic.vue | 54 +- client/src/components/HeaderBar.vue | 197 +++--- client/src/components/HelpfulTooltip.vue | 100 +-- client/src/components/LoadingButton.vue | 75 ++- client/src/components/MobileHeader.vue | 79 ++- client/src/components/Modal.vue | 270 ++++---- client/src/components/MoreOptionsWidget.vue | 85 +-- client/src/components/ScrollUp.vue | 3 +- .../components/StudentSubmissionDocument.vue | 48 +- .../book-navigation/ContentNavigation.vue | 258 ++++---- .../book-navigation/NavigationSidebar.vue | 3 +- .../book-navigation/SubNavigationItem.vue | 65 +- .../content-block-form/ContentElement.vue | 594 +++++++++-------- .../content-block-form/ContentsForm.vue | 241 +++---- .../content-blocks/ContentListBlock.vue | 61 +- .../content-blocks/DocumentBlock.vue | 113 ++-- .../components/content-blocks/Instruction.vue | 73 ++- .../components/content-blocks/LinkBlock.vue | 76 ++- .../content-blocks/assignment/Assignment.vue | 420 ++++++------ .../assignment/FinalSubmission.vue | 166 ++--- .../assignment/SubmissionForm.vue | 191 +++--- .../assignment/SubmissionInput.vue | 91 +-- .../content-forms/AssignmentForm.vue | 67 +- .../components/content-forms/DocumentForm.vue | 198 +++--- .../components/content-forms/VideoForm.vue | 125 ++-- .../components/instruments/FilterEntry.vue | 272 ++++---- client/src/components/modals/index.js | 17 +- .../src/components/notes/BookmarkActions.vue | 114 ++-- .../objective-groups/ObjectiveForm.vue | 40 +- .../components/portfolio/AddProjectEntry.vue | 64 +- .../portfolio/PortfolioOnboarding.vue | 71 +- .../components/portfolio/ProjectActions.vue | 107 +-- .../src/components/portfolio/ProjectEntry.vue | 222 ++++--- .../components/portfolio/ProjectEntryForm.vue | 168 ++--- client/src/components/portfolio/ShareLink.vue | 47 +- .../src/components/profile/ActivityEntry.vue | 84 +-- client/src/components/profile/Avatar.vue | 5 +- .../components/profile/ContentBookmark.vue | 67 +- .../src/components/profile/EditGroupName.vue | 33 +- client/src/components/profile/Profile.vue | 128 ++-- .../src/components/profile/ProfileSidebar.vue | 3 +- .../components/rooms/AddRoomEntryButton.vue | 91 +-- .../src/components/rooms/EntryCountWidget.vue | 76 +-- client/src/components/rooms/MoreActions.vue | 81 +-- .../src/components/rooms/RoomGroupWidget.vue | 43 +- .../components/rooms/RoomVisibilityWidget.vue | 56 +- .../src/components/rooms/RoomsOnboarding.vue | 79 ++- .../school-class/ClassSelectionWidget.vue | 178 ++--- client/src/components/ui/BaseInput.vue | 54 +- client/src/components/ui/PopoverLink.vue | 87 +-- .../components/ui/file-upload/FileUpload.vue | 38 +- .../ui/file-upload/SimpleFileUpload.vue | 104 ++- .../ui/file-upload/SimpleFileUploadIcon.vue | 21 +- .../file-upload/SimpleFileUploadWithIcon.vue | 71 +- .../src/components/ui/form-element-icons.js | 31 +- .../visibility/VisibilityAction.vue | 137 ++-- client/src/layouts/FullScreenLayout.vue | 62 +- client/src/layouts/SimpleLayout.vue | 143 ++-- client/src/layouts/SplitLayout.vue | 255 ++++---- client/src/pages/article.vue | 15 +- client/src/pages/hello.vue | 269 ++++---- client/src/pages/instrument.vue | 123 ++-- client/src/pages/license-activation.vue | 176 ++--- client/src/pages/module/moduleVisibility.vue | 170 ++--- client/src/pages/onboarding/start.vue | 21 +- client/src/pages/survey.vue | 424 ++++++------ client/src/pages/topic-page.vue | 6 +- 73 files changed, 4697 insertions(+), 4276 deletions(-) diff --git a/client/src/components/AddContentButton.vue b/client/src/components/AddContentButton.vue index 529c2578..a948808c 100644 --- a/client/src/components/AddContentButton.vue +++ b/client/src/components/AddContentButton.vue @@ -1,98 +1,105 @@ diff --git a/client/src/components/AddContentElement.vue b/client/src/components/AddContentElement.vue index 5afa10e8..bd917b94 100644 --- a/client/src/components/AddContentElement.vue +++ b/client/src/components/AddContentElement.vue @@ -1,38 +1,42 @@ diff --git a/client/src/components/AddWidget.vue b/client/src/components/AddWidget.vue index 2856a11e..4ee2a0e7 100644 --- a/client/src/components/AddWidget.vue +++ b/client/src/components/AddWidget.vue @@ -11,71 +11,69 @@ diff --git a/client/src/components/BackLink.vue b/client/src/components/BackLink.vue index 89613070..70fe125f 100644 --- a/client/src/components/BackLink.vue +++ b/client/src/components/BackLink.vue @@ -12,8 +12,9 @@ import { MODULE_PAGE } from '@/router/module.names'; import { ROOMS_PAGE } from '@/router/room.names'; import { PROJECTS_PAGE } from '@/router/portfolio.names'; + import {defineAsyncComponent} from 'vue'; - const ChevronLeft = () => import(/* webpackChunkName: "icons" */'@/components/icons/ChevronLeft'); + const ChevronLeft = defineAsyncComponent(() => import(/* webpackChunkName: "icons" */'@/components/icons/ChevronLeft')); export default { props: { diff --git a/client/src/components/ColorChooser.vue b/client/src/components/ColorChooser.vue index 498a212e..b5d65abf 100644 --- a/client/src/components/ColorChooser.vue +++ b/client/src/components/ColorChooser.vue @@ -1,86 +1,93 @@ diff --git a/client/src/components/ContentBlock.vue b/client/src/components/ContentBlock.vue index 9571dbab..e2c1bcab 100644 --- a/client/src/components/ContentBlock.vue +++ b/client/src/components/ContentBlock.vue @@ -1,20 +1,38 @@ diff --git a/client/src/components/FullscreenInfographic.vue b/client/src/components/FullscreenInfographic.vue index 2197ebc2..d024973e 100644 --- a/client/src/components/FullscreenInfographic.vue +++ b/client/src/components/FullscreenInfographic.vue @@ -1,35 +1,37 @@ diff --git a/client/src/components/HeaderBar.vue b/client/src/components/HeaderBar.vue index 8f6e725c..8e6fcde4 100644 --- a/client/src/components/HeaderBar.vue +++ b/client/src/components/HeaderBar.vue @@ -1,4 +1,10 @@ - + diff --git a/client/src/components/HelpfulTooltip.vue b/client/src/components/HelpfulTooltip.vue index 01d24917..74cc397c 100644 --- a/client/src/components/HelpfulTooltip.vue +++ b/client/src/components/HelpfulTooltip.vue @@ -10,65 +10,67 @@ diff --git a/client/src/components/LoadingButton.vue b/client/src/components/LoadingButton.vue index 390d16b7..6b1bfa7e 100644 --- a/client/src/components/LoadingButton.vue +++ b/client/src/components/LoadingButton.vue @@ -1,51 +1,58 @@ diff --git a/client/src/components/MobileHeader.vue b/client/src/components/MobileHeader.vue index 21fc9fa5..99ed4535 100644 --- a/client/src/components/MobileHeader.vue +++ b/client/src/components/MobileHeader.vue @@ -4,59 +4,66 @@ - + - +
diff --git a/client/src/components/Modal.vue b/client/src/components/Modal.vue index 9757bd2e..badc8229 100644 --- a/client/src/components/Modal.vue +++ b/client/src/components/Modal.vue @@ -1,11 +1,7 @@ diff --git a/client/src/components/MoreOptionsWidget.vue b/client/src/components/MoreOptionsWidget.vue index 74e092c1..3e97ec48 100644 --- a/client/src/components/MoreOptionsWidget.vue +++ b/client/src/components/MoreOptionsWidget.vue @@ -1,59 +1,68 @@ diff --git a/client/src/components/ScrollUp.vue b/client/src/components/ScrollUp.vue index b031cdef..315663ef 100644 --- a/client/src/components/ScrollUp.vue +++ b/client/src/components/ScrollUp.vue @@ -11,7 +11,8 @@ diff --git a/client/src/components/book-navigation/ContentNavigation.vue b/client/src/components/book-navigation/ContentNavigation.vue index dd1d171d..cdcfeac4 100644 --- a/client/src/components/book-navigation/ContentNavigation.vue +++ b/client/src/components/book-navigation/ContentNavigation.vue @@ -1,9 +1,12 @@ diff --git a/client/src/components/book-navigation/NavigationSidebar.vue b/client/src/components/book-navigation/NavigationSidebar.vue index 6b015508..40a3c0e4 100644 --- a/client/src/components/book-navigation/NavigationSidebar.vue +++ b/client/src/components/book-navigation/NavigationSidebar.vue @@ -23,8 +23,9 @@ import ContentNavigation from '@/components/book-navigation/ContentNavigation'; import sidebarMixin from '@/mixins/sidebar'; + import {defineAsyncComponent} from 'vue'; - const Cross = () => import(/* webpackChunkName: "icons" */'@/components/icons/CrossIcon'); + const Cross = defineAsyncComponent(() => import(/* webpackChunkName: "icons" */'@/components/icons/CrossIcon')); export default { mixins: [sidebarMixin], diff --git a/client/src/components/book-navigation/SubNavigationItem.vue b/client/src/components/book-navigation/SubNavigationItem.vue index 347d1755..47c7ef0e 100644 --- a/client/src/components/book-navigation/SubNavigationItem.vue +++ b/client/src/components/book-navigation/SubNavigationItem.vue @@ -1,44 +1,55 @@ diff --git a/client/src/components/content-block-form/ContentElement.vue b/client/src/components/content-block-form/ContentElement.vue index 05df19db..88a8a074 100644 --- a/client/src/components/content-block-form/ContentElement.vue +++ b/client/src/components/content-block-form/ContentElement.vue @@ -26,10 +26,14 @@ :class="['content-element__component']" v-bind="element" :is="component" + @change-text="changeText" + @link-change-url="changeUrl" @change-url="changeUrl" + @switch-to-document="switchToDocument" + @assignment-change-title="changeAssignmentTitle" @assignment-change-assignment="changeAssignmentAssignment" /> @@ -39,321 +43,313 @@ diff --git a/client/src/components/content-block-form/ContentsForm.vue b/client/src/components/content-block-form/ContentsForm.vue index 930969f4..ab47ca0c 100644 --- a/client/src/components/content-block-form/ContentsForm.vue +++ b/client/src/components/content-block-form/ContentsForm.vue @@ -18,150 +18,167 @@ /> - -
- + +
+ - +
diff --git a/client/src/components/content-blocks/ContentListBlock.vue b/client/src/components/content-blocks/ContentListBlock.vue index eaaab5bb..a2fa7346 100644 --- a/client/src/components/content-blocks/ContentListBlock.vue +++ b/client/src/components/content-blocks/ContentListBlock.vue @@ -1,40 +1,43 @@ - + computed: { + contentBlocks() { + return this.contents.map(contentBlock => { + const contents = contentBlock.value ? [...contentBlock.value] : []; + return Object.assign({}, contentBlock, { + contents, + indent: true, + bookmarks: this.parent.bookmarks, + notes: this.parent.notes, + root: this.parent.id + }); + }); + } + } + }; + diff --git a/client/src/components/content-blocks/DocumentBlock.vue b/client/src/components/content-blocks/DocumentBlock.vue index d31b6797..447ac2f3 100644 --- a/client/src/components/content-blocks/DocumentBlock.vue +++ b/client/src/components/content-blocks/DocumentBlock.vue @@ -1,71 +1,80 @@ diff --git a/client/src/components/content-blocks/Instruction.vue b/client/src/components/content-blocks/Instruction.vue index a07b54d8..00f3786c 100644 --- a/client/src/components/content-blocks/Instruction.vue +++ b/client/src/components/content-blocks/Instruction.vue @@ -1,50 +1,57 @@ diff --git a/client/src/components/content-blocks/LinkBlock.vue b/client/src/components/content-blocks/LinkBlock.vue index 423d955a..821c0880 100644 --- a/client/src/components/content-blocks/LinkBlock.vue +++ b/client/src/components/content-blocks/LinkBlock.vue @@ -1,52 +1,60 @@ diff --git a/client/src/components/content-blocks/assignment/Assignment.vue b/client/src/components/content-blocks/assignment/Assignment.vue index f268a07f..6f0453e3 100644 --- a/client/src/components/content-blocks/assignment/Assignment.vue +++ b/client/src/components/content-blocks/assignment/Assignment.vue @@ -1,9 +1,19 @@ diff --git a/client/src/components/content-blocks/assignment/FinalSubmission.vue b/client/src/components/content-blocks/assignment/FinalSubmission.vue index dbb8c56b..0cf04327 100644 --- a/client/src/components/content-blocks/assignment/FinalSubmission.vue +++ b/client/src/components/content-blocks/assignment/FinalSubmission.vue @@ -1,99 +1,109 @@ diff --git a/client/src/components/content-blocks/assignment/SubmissionForm.vue b/client/src/components/content-blocks/assignment/SubmissionForm.vue index 621296df..e5c89470 100644 --- a/client/src/components/content-blocks/assignment/SubmissionForm.vue +++ b/client/src/components/content-blocks/assignment/SubmissionForm.vue @@ -10,7 +10,10 @@ />
-
+
- +
@@ -41,112 +48,116 @@ diff --git a/client/src/components/content-blocks/assignment/SubmissionInput.vue b/client/src/components/content-blocks/assignment/SubmissionInput.vue index 3176fa49..867480bf 100644 --- a/client/src/components/content-blocks/assignment/SubmissionInput.vue +++ b/client/src/components/content-blocks/assignment/SubmissionInput.vue @@ -4,68 +4,75 @@ :placeholder="placeholder" :readonly="readonly" :value="inputText" - :class="{ 'submission-form__textarea--readonly': readonly }" + :class="{'submission-form__textarea--readonly': readonly}" data-cy="submission-textarea" rows="1" class="submission-form__textarea" v-auto-grow @input="$emit('input', $event.target.value)" /> -
+
-
+
diff --git a/client/src/components/content-forms/AssignmentForm.vue b/client/src/components/content-forms/AssignmentForm.vue index cac3003c..a3719f1e 100644 --- a/client/src/components/content-forms/AssignmentForm.vue +++ b/client/src/components/content-forms/AssignmentForm.vue @@ -5,7 +5,7 @@ class="assignment-form__title skillbox-input" placeholder="Aufgabentitel" @input="$emit('assignment-change-title', $event.target.value, index)" - /> + >