From 4c34a1bade182633bccdd74bb97aecc2edc413c5 Mon Sep 17 00:00:00 2001 From: Jan Date: Sat, 4 Oct 2025 10:47:52 +0200 Subject: [PATCH] - Introduced "devpage" to show calculation dumps and change active user in "dev"-profile --- src/frontend/src/backend.js | 21 +- src/frontend/src/components/UI/Checkbox.vue | 6 +- .../layout/dev/CalculationDump.vue} | 11 +- .../layout/dev/CalculationDumpList.vue | 95 +++++++++ .../components/layout/dev/DevUserControl.vue | 123 ++++++++++++ .../components/layout/edit/MaterialEdit.vue | 134 +++++++++---- .../components/layout/edit/PackagingEdit.vue | 183 ++++++++++++++++-- .../src/components/layout/edit/PriceEdit.vue | 82 ++++++-- .../components/layout/edit/SupplierView.vue | 2 +- .../destination/DestinationEditRoutes.vue | 2 +- .../edit/destination/DestinationRoute.vue | 26 ++- .../src/pages/CalculationMassEdit.vue | 3 +- .../src/pages/CalculationSingleEdit.vue | 71 +++---- src/frontend/src/pages/DevPage.vue | 65 +++++++ src/frontend/src/router.js | 13 +- .../java/de/avatic/lcc/config/CorsConfig.java | 2 +- .../de/avatic/lcc/config/SecurityConfig.java | 77 +++++++- .../lcc/controller/ErrorController.java | 9 +- .../lcc/controller/dev/DevController.java | 76 ++++++++ .../users/ActiveUserController.java | 29 +++ .../repositories/error/DumpRepository.java | 136 ++++++++----- .../repositories/users/UserRepository.java | 14 +- .../lcc/service/access/PremisesService.java | 6 - .../avatic/lcc/service/users/UserService.java | 20 ++ .../authorization/AuthorizationService.java | 12 ++ .../DefaultAuthorizationService.java | 15 ++ .../SimulatedAuthorizationService.java | 36 ++++ src/test/resources/master_data/users.sql | 10 +- 28 files changed, 1071 insertions(+), 208 deletions(-) rename src/frontend/src/{pages/CalcualtionDump.vue => components/layout/dev/CalculationDump.vue} (80%) create mode 100644 src/frontend/src/components/layout/dev/CalculationDumpList.vue create mode 100644 src/frontend/src/components/layout/dev/DevUserControl.vue create mode 100644 src/frontend/src/pages/DevPage.vue create mode 100644 src/main/java/de/avatic/lcc/controller/dev/DevController.java create mode 100644 src/main/java/de/avatic/lcc/controller/users/ActiveUserController.java create mode 100644 src/main/java/de/avatic/lcc/service/users/authorization/AuthorizationService.java create mode 100644 src/main/java/de/avatic/lcc/service/users/authorization/DefaultAuthorizationService.java create mode 100644 src/main/java/de/avatic/lcc/service/users/authorization/SimulatedAuthorizationService.java diff --git a/src/frontend/src/backend.js b/src/frontend/src/backend.js index bd00238..6a6b33c 100644 --- a/src/frontend/src/backend.js +++ b/src/frontend/src/backend.js @@ -1,12 +1,23 @@ import logger from "@/logger.js"; import {useErrorStore} from "@/store/error.js"; +const getCsrfToken = () => { + const value = `; ${document.cookie}`; + const parts = value.split(`; XSRF-TOKEN=`); + if (parts.length === 2) { + return decodeURIComponent(parts.pop().split(';').shift()); + } + return null; +} + const performRequest = async (requestingStore, method, url, body, expectResponse = true, expectedException = null) => { const params = { method: method, + credentials: 'include', headers: { - 'Content-Type': 'application/json' + 'Content-Type': 'application/json', + 'X-XSRF-TOKEN': getCsrfToken() } }; @@ -27,6 +38,10 @@ const performDownload = async (url, toFile, expectResponse = true, expectedExcep const params = { method: 'GET', + credentials: 'include', + headers: { + 'X-XSRF-TOKEN': getCsrfToken() + } }; const request = {url: url, params: params, expectResponse: expectResponse, expectedException: expectedException, type: 'blob'}; @@ -56,6 +71,10 @@ const performUpload = async (url, file, expectResponse = true, expectedException const params = { method: 'POST', + credentials: 'include', + headers: { + 'X-XSRF-TOKEN': getCsrfToken() + }, body: formData }; diff --git a/src/frontend/src/components/UI/Checkbox.vue b/src/frontend/src/components/UI/Checkbox.vue index 0fd04dc..9cf701b 100644 --- a/src/frontend/src/components/UI/Checkbox.vue +++ b/src/frontend/src/components/UI/Checkbox.vue @@ -60,7 +60,6 @@ export default{ } } - \ No newline at end of file diff --git a/src/frontend/src/components/layout/dev/DevUserControl.vue b/src/frontend/src/components/layout/dev/DevUserControl.vue new file mode 100644 index 0000000..63bb062 --- /dev/null +++ b/src/frontend/src/components/layout/dev/DevUserControl.vue @@ -0,0 +1,123 @@ + + + + + + \ No newline at end of file diff --git a/src/frontend/src/components/layout/edit/MaterialEdit.vue b/src/frontend/src/components/layout/edit/MaterialEdit.vue index 865d270..b2f1f14 100644 --- a/src/frontend/src/components/layout/edit/MaterialEdit.vue +++ b/src/frontend/src/components/layout/edit/MaterialEdit.vue @@ -1,47 +1,46 @@ @@ -88,6 +87,10 @@ export default { openSelectDirect: { type: Boolean, default: false, + }, + responsive: { + type: Boolean, + default: true, } }, computed: { @@ -164,16 +167,63 @@ export default { display: flex; align-items: center; gap: 0.8rem; + width: 100%; } .container { display: grid; grid-template-columns: auto 1fr; - grid-template-rows: repeat(3, fit-content(0)); + grid-template-rows: repeat(4, fit-content(0)); gap: 1.6rem; flex: 1 1 auto; } +/* Responsive Layout für Breiten unter 1500px - nur wenn responsive aktiviert ist */ +@media (max-width: 1500px) { + .container.responsive { + grid-template-columns: + minmax(auto, max-content) /* Spalte 1: Label */ + minmax(120px, 1fr) /* Spalte 2: Input */ + minmax(auto, max-content) /* Spalte 3: Label */ + minmax(120px, 1fr) /* Spalte 4: Input/Dropdown */ + minmax(auto, max-content) /* Spalte 5: Label */ + minmax(120px, 1fr) /* Spalte 6: Input */ + minmax(auto, max-content) /* Spalte 7: Label */ + minmax(120px, 1fr); /* Spalte 8: Input/Dropdown */ + grid-template-rows: auto; + gap: 1.2rem 1rem; + align-items: center; + } + + .container.responsive .field-group { + display: contents; + } + + .container.responsive .caption-column { + justify-self: start; + } + + .container.responsive .input-column { + min-width: 0; + } + + .container.responsive .field-group { + display: contents; + } + + .container.responsive .caption-column { + justify-self: start; + } + + .container.responsive .input-column { + min-width: 0; + } +} + +.field-group { + display: contents; +} + .input-column { display: flex; justify-content: space-between; @@ -201,7 +251,6 @@ export default { background: white; border-radius: 0.4rem; padding: 0.6rem 1.2rem; - /* box-shadow: 0 8px 32px rgba(0, 0, 0, 0.1);*/ border: 0.2rem solid #E3EDFF; transition: all 0.1s ease; flex: 1 1 auto; @@ -210,7 +259,6 @@ export default { .text-container:hover { background: #EEF4FF; border: 0.2rem solid #8DB3FE; - /*transform: translateY(2px);*/ transform: scale(1.01); } @@ -224,8 +272,16 @@ export default { } .input-field-tariffrate { - min-width: 10rem; + min-width: 20rem; flex: 0 1 10rem; } +/* Optimierung für kleinere Bildschirme unter 1500px - nur wenn responsive aktiviert ist */ +@media (max-width: 1500px) { + .container.responsive .input-field-tariffrate { + min-width: auto; + flex: 1 1 auto; + } +} + \ No newline at end of file diff --git a/src/frontend/src/components/layout/edit/PackagingEdit.vue b/src/frontend/src/components/layout/edit/PackagingEdit.vue index 1df58c0..731f35f 100644 --- a/src/frontend/src/components/layout/edit/PackagingEdit.vue +++ b/src/frontend/src/components/layout/edit/PackagingEdit.vue @@ -1,14 +1,16 @@