diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index ca9b96403403231ff452d8fd94b9fe9207c104be..90a63db2bdc441892231c4fe8d228dba7477e08a 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -2,6 +2,7 @@ stages:
   - test
   - sonar
   - build
+  - mend
 
 test:
   stage: test
@@ -27,7 +28,7 @@ sonar:
 
 build_and_push_latest_image:
   stage: build
-  image: korvoj/docker-git:26.1.3
+  image: korvoj/docker-git:26.1.4
   only:
     - develop
   variables:
@@ -54,7 +55,7 @@ build_and_push_alfa_image:
 
 build_and_push_release_image:
   stage: build
-  image: korvoj/docker-git:26.1.3
+  image: korvoj/docker-git:26.1.4
   only:
     - tags
   script:
@@ -64,4 +65,23 @@ build_and_push_release_image:
       docker login -u $DOCKER_USERNAME -p $DOCKER_PASSWORD $DOCKER_REPOSITORY
       docker build -t $DOCKER_REPOSITORY_LOCAL:$IMAGE_TAG .
       docker push $DOCKER_REPOSITORY_LOCAL:$IMAGE_TAG
-      docker logout $DOCKER_REPOSITORY
\ No newline at end of file
+      docker logout $DOCKER_REPOSITORY
+
+mend:
+  stage: mend
+  image: openjdk:17-jdk-slim
+  only:
+    - /^release/
+  variables:
+    PRODUCT_NAME: "nmaas"
+    PROJECT_NAME: "nmaas-portal"
+  script:
+    - |
+      export PRODUCT_VERSION=$(echo $CI_COMMIT_BRANCH | cut -c 9-)
+      export PROJECT_VERSION=$PRODUCT_VERSION
+      apt-get update && apt-get install -y curl nodejs npm
+      npm install -g @angular/cli
+      npm ci
+      chmod +x ./gradlew
+      curl -LJO https://github.com/whitesource/unified-agent-distribution/releases/latest/download/wss-unified-agent.jar
+      java -jar wss-unified-agent.jar -userKey ${MEND_USER_KEY} -apiKey ${MEND_API_KEY} -projectVersion ${PROJECT_VERSION} -project ${PROJECT_NAME} -productVersion ${PRODUCT_VERSION} -product ${PRODUCT_NAME} -c ./ws/ws.config -d ./
\ No newline at end of file
diff --git a/Dockerfile b/Dockerfile
index 4b9e926d9c2c34de45e0f75578bdc449abae29ec..5adcf622271c5f6fa7efa21a5687cb066cc76ab8 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -8,7 +8,7 @@ RUN npm install -g @angular/cli@17
 RUN npm i --force 
 RUN ng build --base-href / --configuration production
 
-FROM nginx:1.27-alpine
+FROM nginx:1.28-alpine
 MAINTAINER nmaas@lists.geant.org
 
 ARG webdir=/usr/share/nginx/html
diff --git a/angular.json b/angular.json
index 7293e9a6ec3bd6115a05c4cf4d8e668648648f8c..8492ebcbc23ad486ee46289147b0c724f361f397 100644
--- a/angular.json
+++ b/angular.json
@@ -96,7 +96,8 @@
             "tsConfig": "tsconfig.spec.json",
             "codeCoverage": true,
             "codeCoverageExclude": [
-              "src/app/test/**"
+              "src/app/test/**",
+               "**/*.spec.ts"
             ],
             "scripts": [
               "node_modules/jquery/dist/jquery.min.js",
diff --git a/build.gradle b/build.gradle
index a443e5382e46befdc5870955a7650591f7e79e96..8ac5811585e0a6ccca6fa68e856bc18098b97d06 100644
--- a/build.gradle
+++ b/build.gradle
@@ -2,10 +2,10 @@ import org.gradle.internal.os.OperatingSystem;
 
 plugins {
 	id "com.moowork.node" version "1.3.1"
-	id "org.sonarqube" version "3.2.0"
+	id "org.sonarqube" version "6.1.0.5360"
 }
 
-version = '1.7.0-SNAPSHOT'
+version = '1.7.0'
 
 task buildGUI(type: Exec) {
 	println 'Building using Angular CLI'
@@ -58,7 +58,7 @@ sonarqube {
     properties
 		{
 			property "sonar.sources", "src"
-			property "sonar.exclusions", "**/node_modules/**,**/*.spec.ts,**/bootstrap.js,**/src/app/service/**,**/src/app/model/**"
+			property "sonar.exclusions", ["**/node_modules/**","**/*.spec.ts","**/bootstrap.js","**/src/app/service/**","**/src/app/model/**"]
 			property "sonar.tests", "src"
 			property "sonar.test.inclusions", "**/*.spec.ts"
 			property "sonar.typescript.lcov.reportPaths", "coverage/lcov.info"
diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar
index 9ca236b7bcce1835850cad748b58cb9719f26655..94336fcae912db8a11d55634156fa011f4686124 100644
Binary files a/gradle/wrapper/gradle-wrapper.jar and b/gradle/wrapper/gradle-wrapper.jar differ
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index 5b8cb7fbc8711fc2ef9087feb9161670a7d3ac0d..5c82cb03242098aebc387e4b8faf85068bea988c 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -1,6 +1,5 @@
-#Mon Jun 18 14:34:36 CEST 2018
 distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
+distributionUrl=https\://services.gradle.org/distributions/gradle-8.14-bin.zip
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-4.8-bin.zip
diff --git a/gradlew b/gradlew
index 4453ccea33d960069d9137ee65f6b21fc65e7e92..cccdd3d517fc5249beaefa600691cf150f2fa3e6 100644
--- a/gradlew
+++ b/gradlew
@@ -33,11 +33,11 @@ DEFAULT_JVM_OPTS=""
 # Use the maximum available, or set MAX_FD != -1 to use that value.
 MAX_FD="maximum"
 
-warn ( ) {
+warn () {
     echo "$*"
 }
 
-die ( ) {
+die () {
     echo
     echo "$*"
     echo
@@ -155,7 +155,7 @@ if $cygwin ; then
 fi
 
 # Escape application args
-save ( ) {
+save () {
     for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
     echo " "
 }
diff --git a/gradlew.bat b/gradlew.bat
index f9553162f122c71b34635112e717c3e733b5b212..e95643d6a2ca62258464e83c72f5156dc941c609 100644
--- a/gradlew.bat
+++ b/gradlew.bat
@@ -1,84 +1,84 @@
-@if "%DEBUG%" == "" @echo off
-@rem ##########################################################################
-@rem
-@rem  Gradle startup script for Windows
-@rem
-@rem ##########################################################################
-
-@rem Set local scope for the variables with windows NT shell
-if "%OS%"=="Windows_NT" setlocal
-
-set DIRNAME=%~dp0
-if "%DIRNAME%" == "" set DIRNAME=.
-set APP_BASE_NAME=%~n0
-set APP_HOME=%DIRNAME%
-
-@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
-set DEFAULT_JVM_OPTS=
-
-@rem Find java.exe
-if defined JAVA_HOME goto findJavaFromJavaHome
-
-set JAVA_EXE=java.exe
-%JAVA_EXE% -version >NUL 2>&1
-if "%ERRORLEVEL%" == "0" goto init
-
-echo.
-echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
-echo.
-echo Please set the JAVA_HOME variable in your environment to match the
-echo location of your Java installation.
-
-goto fail
-
-:findJavaFromJavaHome
-set JAVA_HOME=%JAVA_HOME:"=%
-set JAVA_EXE=%JAVA_HOME%/bin/java.exe
-
-if exist "%JAVA_EXE%" goto init
-
-echo.
-echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
-echo.
-echo Please set the JAVA_HOME variable in your environment to match the
-echo location of your Java installation.
-
-goto fail
-
-:init
-@rem Get command-line arguments, handling Windows variants
-
-if not "%OS%" == "Windows_NT" goto win9xME_args
-
-:win9xME_args
-@rem Slurp the command line arguments.
-set CMD_LINE_ARGS=
-set _SKIP=2
-
-:win9xME_args_slurp
-if "x%~1" == "x" goto execute
-
-set CMD_LINE_ARGS=%*
-
-:execute
-@rem Setup the command line
-
-set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
-
-@rem Execute Gradle
-"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
-
-:end
-@rem End local scope for the variables with windows NT shell
-if "%ERRORLEVEL%"=="0" goto mainEnd
-
-:fail
-rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
-rem the _cmd.exe /c_ return code!
-if  not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
-exit /b 1
-
-:mainEnd
-if "%OS%"=="Windows_NT" endlocal
-
-:omega
+@if "%DEBUG%" == "" @echo off
+@rem ##########################################################################
+@rem
+@rem  Gradle startup script for Windows
+@rem
+@rem ##########################################################################
+
+@rem Set local scope for the variables with windows NT shell
+if "%OS%"=="Windows_NT" setlocal
+
+set DIRNAME=%~dp0
+if "%DIRNAME%" == "" set DIRNAME=.
+set APP_BASE_NAME=%~n0
+set APP_HOME=%DIRNAME%
+
+@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
+set DEFAULT_JVM_OPTS=
+
+@rem Find java.exe
+if defined JAVA_HOME goto findJavaFromJavaHome
+
+set JAVA_EXE=java.exe
+%JAVA_EXE% -version >NUL 2>&1
+if "%ERRORLEVEL%" == "0" goto init
+
+echo.
+echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
+echo.
+echo Please set the JAVA_HOME variable in your environment to match the
+echo location of your Java installation.
+
+goto fail
+
+:findJavaFromJavaHome
+set JAVA_HOME=%JAVA_HOME:"=%
+set JAVA_EXE=%JAVA_HOME%/bin/java.exe
+
+if exist "%JAVA_EXE%" goto init
+
+echo.
+echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
+echo.
+echo Please set the JAVA_HOME variable in your environment to match the
+echo location of your Java installation.
+
+goto fail
+
+:init
+@rem Get command-line arguments, handling Windows variants
+
+if not "%OS%" == "Windows_NT" goto win9xME_args
+
+:win9xME_args
+@rem Slurp the command line arguments.
+set CMD_LINE_ARGS=
+set _SKIP=2
+
+:win9xME_args_slurp
+if "x%~1" == "x" goto execute
+
+set CMD_LINE_ARGS=%*
+
+:execute
+@rem Setup the command line
+
+set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
+
+@rem Execute Gradle
+"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
+
+:end
+@rem End local scope for the variables with windows NT shell
+if "%ERRORLEVEL%"=="0" goto mainEnd
+
+:fail
+rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
+rem the _cmd.exe /c_ return code!
+if  not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
+exit /b 1
+
+:mainEnd
+if "%OS%"=="Windows_NT" endlocal
+
+:omega
diff --git a/karma.conf.js b/karma.conf.js
index ba90f3360f44634aff4d5256a95ca96c8e7742a9..a385b0a180d5158703d862e2913e52303d341452 100644
--- a/karma.conf.js
+++ b/karma.conf.js
@@ -35,7 +35,9 @@ module.exports = function (config) {
             coverageReporter: {
                 dir: require('path').join(__dirname, 'coverage'),
                 subdir: '.',
-                exclude: ['**/*.spec.ts'],
+                exclude: ['**/*.spec.ts',
+                    '**/*.service.ts'
+                ],
                 reporters: [
                     {type: 'html', subdir: '.'},
                     {type: 'lcovonly', subdir: '.', file: 'lcov.info'},
@@ -43,7 +45,7 @@ module.exports = function (config) {
                 check: {
                     global: {
                         statements: 40,
-                        branches: 20,
+                        branches: 19,
                         functions: 30,
                         lines: 30,
                     },
diff --git a/package-lock.json b/package-lock.json
index 9587e3edb93829b96b09f645a89e4907917c705d..f61f5e9255306db709c48725cefda03a03fd3821 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -1,12 +1,12 @@
 {
   "name": "nmaas-portal",
-  "version": "1.7.0",
+  "version": "1.7.1",
   "lockfileVersion": 2,
   "requires": true,
   "packages": {
     "": {
       "name": "nmaas-portal",
-      "version": "1.7.0",
+      "version": "1.7.1",
       "license": "Apache 2.0",
       "dependencies": {
         "@angular/animations": "17.3.12",
@@ -23,24 +23,25 @@
         "@formio/angular": "7.0.0",
         "@formio/js": "^5.0.0",
         "@ngx-translate/core": "^14.0.0",
-        "@ngx-translate/http-loader": "^7.0.0",
+        "@ngx-translate/http-loader": "^16.0.0",
         "@types/semver": "^7.3.8",
         "@types/zxcvbn": "^4.4.1",
         "@zxcvbn-ts/core": "^3.0.0",
         "@zxcvbn-ts/language-en": "^3.0.0",
-        "ajv": "^6.12.6",
+        "ajv": "^8.0.0",
         "angular-password-strength-meter": "^11.0.0",
         "bootstrap": "^3.4.1",
+        "chart.js": "^4.4.8",
         "document-register-element": "^1.14.10",
         "jquery": "^3.6.0",
         "lodash": "^4.17.21",
         "ng-event-source": "^1.0.14",
-        "ng-recaptcha": "^13.0.0",
+        "ng-recaptcha": "^13.2.1",
         "ng-terminal": "^6.3.0",
         "ngx-pagination": "^6.0.3",
         "ngx-webstorage-service": "^5.0.0",
         "primeflex": "^3.3.1",
-        "primeicons": "^6.0.1",
+        "primeicons": "^7.0.0",
         "primeng": "^17.18.15",
         "rxjs": "^7.8.1",
         "semver": "^7.5.4",
@@ -53,14 +54,14 @@
         "@angular-devkit/build-angular": "^17.3.11",
         "@angular/cli": "^17.3.11",
         "@angular/compiler-cli": "^17.3.12",
-        "@types/jasmine": "~3.6.0",
+        "@types/jasmine": "~5.1.0",
         "@types/node": "^12.20.13",
         "codelyzer": "^6.0.0",
         "intl": "^1.2.5",
         "jasmine-core": "~4.6.0",
         "jasmine-spec-reporter": "~5.0.0",
         "karma": "^6.3.14",
-        "karma-chrome-launcher": "~3.1.0",
+        "karma-chrome-launcher": "~3.2.0",
         "karma-cli": "^1.0.1",
         "karma-coverage": "^2.0.3",
         "karma-jasmine": "~4.0.0",
@@ -89,12 +90,12 @@
       }
     },
     "node_modules/@angular-devkit/architect": {
-      "version": "0.1703.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/architect/-/architect-0.1703.11.tgz",
-      "integrity": "sha512-YNasVZk4rYdcM6M+KRH8PUBhVyJfqzUYLpO98GgRokW+taIDgifckSlmfDZzQRbw45qiwei1IKCLqcpC8nM5Tw==",
+      "version": "0.1703.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/architect/-/architect-0.1703.16.tgz",
+      "integrity": "sha512-wuqKu20ekgzzikUTZD28dS72F6vjniZuiQ7RgAYhykmsU0z0br2tksHQvjD/auzVArtgQir1+V9wp6BN4dSdNQ==",
       "dev": true,
       "dependencies": {
-        "@angular-devkit/core": "17.3.11",
+        "@angular-devkit/core": "17.3.16",
         "rxjs": "7.8.1"
       },
       "engines": {
@@ -103,27 +104,36 @@
         "yarn": ">= 1.13.0"
       }
     },
+    "node_modules/@angular-devkit/architect/node_modules/rxjs": {
+      "version": "7.8.1",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "dev": true,
+      "dependencies": {
+        "tslib": "^2.1.0"
+      }
+    },
     "node_modules/@angular-devkit/build-angular": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/build-angular/-/build-angular-17.3.11.tgz",
-      "integrity": "sha512-lHX5V2dSts328yvo/9E2u9QMGcvJhbEKKDDp9dBecwvIG9s+4lTOJgi9DPUE7W+AtmPcmbbhwC2JRQ/SLQhAoA==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/build-angular/-/build-angular-17.3.16.tgz",
+      "integrity": "sha512-5JiR1NK3MOwzipAn4UmvJ8yQa6NaBtHBWbLrY0Ps6a21kHWn42C+dpvVdlXN/ZZSpEll/nzA+b77zA3kDrGlKw==",
       "dev": true,
       "dependencies": {
         "@ampproject/remapping": "2.3.0",
-        "@angular-devkit/architect": "0.1703.11",
-        "@angular-devkit/build-webpack": "0.1703.11",
-        "@angular-devkit/core": "17.3.11",
-        "@babel/core": "7.24.0",
-        "@babel/generator": "7.23.6",
-        "@babel/helper-annotate-as-pure": "7.22.5",
-        "@babel/helper-split-export-declaration": "7.22.6",
-        "@babel/plugin-transform-async-generator-functions": "7.23.9",
-        "@babel/plugin-transform-async-to-generator": "7.23.3",
-        "@babel/plugin-transform-runtime": "7.24.0",
-        "@babel/preset-env": "7.24.0",
-        "@babel/runtime": "7.24.0",
+        "@angular-devkit/architect": "0.1703.16",
+        "@angular-devkit/build-webpack": "0.1703.16",
+        "@angular-devkit/core": "17.3.16",
+        "@babel/core": "7.26.10",
+        "@babel/generator": "7.26.10",
+        "@babel/helper-annotate-as-pure": "7.25.9",
+        "@babel/helper-split-export-declaration": "7.24.7",
+        "@babel/plugin-transform-async-generator-functions": "7.26.8",
+        "@babel/plugin-transform-async-to-generator": "7.25.9",
+        "@babel/plugin-transform-runtime": "7.26.10",
+        "@babel/preset-env": "7.26.9",
+        "@babel/runtime": "7.26.10",
         "@discoveryjs/json-ext": "0.5.7",
-        "@ngtools/webpack": "17.3.11",
+        "@ngtools/webpack": "17.3.16",
         "@vitejs/plugin-basic-ssl": "1.1.0",
         "ansi-colors": "4.1.3",
         "autoprefixer": "10.4.18",
@@ -164,8 +174,7 @@
         "terser": "5.29.1",
         "tree-kill": "1.2.2",
         "tslib": "2.6.2",
-        "undici": "6.11.1",
-        "vite": "5.1.8",
+        "vite": "~5.4.17",
         "watchpack": "2.4.0",
         "webpack": "5.94.0",
         "webpack-dev-middleware": "6.1.2",
@@ -233,21 +242,21 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@babel/core": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.24.0.tgz",
-      "integrity": "sha512-fQfkg0Gjkza3nf0c7/w6Xf34BW4YvzNfACRLmmb7XRLa6XHdR+K9AlJlxneFfWYf6uhOzuzZVTjF/8KfndZANw==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.26.10.tgz",
+      "integrity": "sha512-vMqyb7XCDMPvJFFOaT9kxtiRh42GwlZEg1/uIgtZshS5a/8OaduUfCi7kynKgc3Tw/6Uo2D+db9qBttghhmxwQ==",
       "dev": true,
       "dependencies": {
         "@ampproject/remapping": "^2.2.0",
-        "@babel/code-frame": "^7.23.5",
-        "@babel/generator": "^7.23.6",
-        "@babel/helper-compilation-targets": "^7.23.6",
-        "@babel/helper-module-transforms": "^7.23.3",
-        "@babel/helpers": "^7.24.0",
-        "@babel/parser": "^7.24.0",
-        "@babel/template": "^7.24.0",
-        "@babel/traverse": "^7.24.0",
-        "@babel/types": "^7.24.0",
+        "@babel/code-frame": "^7.26.2",
+        "@babel/generator": "^7.26.10",
+        "@babel/helper-compilation-targets": "^7.26.5",
+        "@babel/helper-module-transforms": "^7.26.0",
+        "@babel/helpers": "^7.26.10",
+        "@babel/parser": "^7.26.10",
+        "@babel/template": "^7.26.9",
+        "@babel/traverse": "^7.26.10",
+        "@babel/types": "^7.26.10",
         "convert-source-map": "^2.0.0",
         "debug": "^4.1.0",
         "gensync": "^1.0.0-beta.2",
@@ -272,9 +281,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/aix-ppc64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.19.12.tgz",
-      "integrity": "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.21.5.tgz",
+      "integrity": "sha512-1SDgH6ZSPTlggy1yI6+Dbkiz8xzpHJEVAlF/AM1tHPLsf5STom9rwtjE4hKAF20FfXXNTFqEYXyJNWh1GiZedQ==",
       "cpu": [
         "ppc64"
       ],
@@ -288,9 +297,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/android-arm": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.19.12.tgz",
-      "integrity": "sha512-qg/Lj1mu3CdQlDEEiWrlC4eaPZ1KztwGJ9B6J+/6G+/4ewxJg7gqj8eVYWvao1bXrqGiW2rsBZFSX3q2lcW05w==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.21.5.tgz",
+      "integrity": "sha512-vCPvzSjpPHEi1siZdlvAlsPxXl7WbOVUBBAowWug4rJHb68Ox8KualB+1ocNvT5fjv6wpkX6o/iEpbDrf68zcg==",
       "cpu": [
         "arm"
       ],
@@ -304,9 +313,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/android-arm64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.19.12.tgz",
-      "integrity": "sha512-P0UVNGIienjZv3f5zq0DP3Nt2IE/3plFzuaS96vihvD0Hd6H/q4WXUGpCxD/E8YrSXfNyRPbpTq+T8ZQioSuPA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.21.5.tgz",
+      "integrity": "sha512-c0uX9VAUBQ7dTDCjq+wdyGLowMdtR/GoC2U5IYk/7D1H1JYC0qseD7+11iMP2mRLN9RcCMRcjC4YMclCzGwS/A==",
       "cpu": [
         "arm64"
       ],
@@ -320,9 +329,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/android-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.19.12.tgz",
-      "integrity": "sha512-3k7ZoUW6Q6YqhdhIaq/WZ7HwBpnFBlW905Fa4s4qWJyiNOgT1dOqDiVAQFwBH7gBRZr17gLrlFCRzF6jFh7Kew==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.21.5.tgz",
+      "integrity": "sha512-D7aPRUUNHRBwHxzxRvp856rjUHRFW1SdQATKXH2hqA0kAZb1hKmi02OpYRacl0TxIGz/ZmXWlbZgjwWYaCakTA==",
       "cpu": [
         "x64"
       ],
@@ -336,9 +345,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/darwin-arm64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.19.12.tgz",
-      "integrity": "sha512-B6IeSgZgtEzGC42jsI+YYu9Z3HKRxp8ZT3cqhvliEHovq8HSX2YX8lNocDn79gCKJXOSaEot9MVYky7AKjCs8g==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.21.5.tgz",
+      "integrity": "sha512-DwqXqZyuk5AiWWf3UfLiRDJ5EDd49zg6O9wclZ7kUMv2WRFr4HKjXp/5t8JZ11QbQfUS6/cRCKGwYhtNAY88kQ==",
       "cpu": [
         "arm64"
       ],
@@ -352,9 +361,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/darwin-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.19.12.tgz",
-      "integrity": "sha512-hKoVkKzFiToTgn+41qGhsUJXFlIjxI/jSYeZf3ugemDYZldIXIxhvwN6erJGlX4t5h417iFuheZ7l+YVn05N3A==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.21.5.tgz",
+      "integrity": "sha512-se/JjF8NlmKVG4kNIuyWMV/22ZaerB+qaSi5MdrXtd6R08kvs2qCN4C09miupktDitvh8jRFflwGFBQcxZRjbw==",
       "cpu": [
         "x64"
       ],
@@ -368,9 +377,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/freebsd-arm64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.19.12.tgz",
-      "integrity": "sha512-4aRvFIXmwAcDBw9AueDQ2YnGmz5L6obe5kmPT8Vd+/+x/JMVKCgdcRwH6APrbpNXsPz+K653Qg8HB/oXvXVukA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.21.5.tgz",
+      "integrity": "sha512-5JcRxxRDUJLX8JXp/wcBCy3pENnCgBR9bN6JsY4OmhfUtIHe3ZW0mawA7+RDAcMLrMIZaf03NlQiX9DGyB8h4g==",
       "cpu": [
         "arm64"
       ],
@@ -384,9 +393,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/freebsd-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.19.12.tgz",
-      "integrity": "sha512-EYoXZ4d8xtBoVN7CEwWY2IN4ho76xjYXqSXMNccFSx2lgqOG/1TBPW0yPx1bJZk94qu3tX0fycJeeQsKovA8gg==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.21.5.tgz",
+      "integrity": "sha512-J95kNBj1zkbMXtHVH29bBriQygMXqoVQOQYA+ISs0/2l3T9/kj42ow2mpqerRBxDJnmkUDCaQT/dfNXWX/ZZCQ==",
       "cpu": [
         "x64"
       ],
@@ -400,9 +409,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-arm": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.19.12.tgz",
-      "integrity": "sha512-J5jPms//KhSNv+LO1S1TX1UWp1ucM6N6XuL6ITdKWElCu8wXP72l9MM0zDTzzeikVyqFE6U8YAV9/tFyj0ti+w==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.21.5.tgz",
+      "integrity": "sha512-bPb5AHZtbeNGjCKVZ9UGqGwo8EUu4cLq68E95A53KlxAPRmUyYv2D6F0uUI65XisGOL1hBP5mTronbgo+0bFcA==",
       "cpu": [
         "arm"
       ],
@@ -416,9 +425,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-arm64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.19.12.tgz",
-      "integrity": "sha512-EoTjyYyLuVPfdPLsGVVVC8a0p1BFFvtpQDB/YLEhaXyf/5bczaGeN15QkR+O4S5LeJ92Tqotve7i1jn35qwvdA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.21.5.tgz",
+      "integrity": "sha512-ibKvmyYzKsBeX8d8I7MH/TMfWDXBF3db4qM6sy+7re0YXya+K1cem3on9XgdT2EQGMu4hQyZhan7TeQ8XkGp4Q==",
       "cpu": [
         "arm64"
       ],
@@ -432,9 +441,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-ia32": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.19.12.tgz",
-      "integrity": "sha512-Thsa42rrP1+UIGaWz47uydHSBOgTUnwBwNq59khgIwktK6x60Hivfbux9iNR0eHCHzOLjLMLfUMLCypBkZXMHA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.21.5.tgz",
+      "integrity": "sha512-YvjXDqLRqPDl2dvRODYmmhz4rPeVKYvppfGYKSNGdyZkA01046pLWyRKKI3ax8fbJoK5QbxblURkwK/MWY18Tg==",
       "cpu": [
         "ia32"
       ],
@@ -448,9 +457,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-loong64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.19.12.tgz",
-      "integrity": "sha512-LiXdXA0s3IqRRjm6rV6XaWATScKAXjI4R4LoDlvO7+yQqFdlr1Bax62sRwkVvRIrwXxvtYEHHI4dm50jAXkuAA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.21.5.tgz",
+      "integrity": "sha512-uHf1BmMG8qEvzdrzAqg2SIG/02+4/DHB6a9Kbya0XDvwDEKCoC8ZRWI5JJvNdUjtciBGFQ5PuBlpEOXQj+JQSg==",
       "cpu": [
         "loong64"
       ],
@@ -464,9 +473,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-mips64el": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.19.12.tgz",
-      "integrity": "sha512-fEnAuj5VGTanfJ07ff0gOA6IPsvrVHLVb6Lyd1g2/ed67oU1eFzL0r9WL7ZzscD+/N6i3dWumGE1Un4f7Amf+w==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.21.5.tgz",
+      "integrity": "sha512-IajOmO+KJK23bj52dFSNCMsz1QP1DqM6cwLUv3W1QwyxkyIWecfafnI555fvSGqEKwjMXVLokcV5ygHW5b3Jbg==",
       "cpu": [
         "mips64el"
       ],
@@ -480,9 +489,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-ppc64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.19.12.tgz",
-      "integrity": "sha512-nYJA2/QPimDQOh1rKWedNOe3Gfc8PabU7HT3iXWtNUbRzXS9+vgB0Fjaqr//XNbd82mCxHzik2qotuI89cfixg==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.21.5.tgz",
+      "integrity": "sha512-1hHV/Z4OEfMwpLO8rp7CvlhBDnjsC3CttJXIhBi+5Aj5r+MBvy4egg7wCbe//hSsT+RvDAG7s81tAvpL2XAE4w==",
       "cpu": [
         "ppc64"
       ],
@@ -496,9 +505,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-riscv64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.19.12.tgz",
-      "integrity": "sha512-2MueBrlPQCw5dVJJpQdUYgeqIzDQgw3QtiAHUC4RBz9FXPrskyyU3VI1hw7C0BSKB9OduwSJ79FTCqtGMWqJHg==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.21.5.tgz",
+      "integrity": "sha512-2HdXDMd9GMgTGrPWnJzP2ALSokE/0O5HhTUvWIbD3YdjME8JwvSCnNGBnTThKGEB91OZhzrJ4qIIxk/SBmyDDA==",
       "cpu": [
         "riscv64"
       ],
@@ -512,9 +521,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-s390x": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.19.12.tgz",
-      "integrity": "sha512-+Pil1Nv3Umes4m3AZKqA2anfhJiVmNCYkPchwFJNEJN5QxmTs1uzyy4TvmDrCRNT2ApwSari7ZIgrPeUx4UZDg==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.21.5.tgz",
+      "integrity": "sha512-zus5sxzqBJD3eXxwvjN1yQkRepANgxE9lgOW2qLnmr8ikMTphkjgXu1HR01K4FJg8h1kEEDAqDcZQtbrRnB41A==",
       "cpu": [
         "s390x"
       ],
@@ -528,9 +537,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/linux-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.19.12.tgz",
-      "integrity": "sha512-B71g1QpxfwBvNrfyJdVDexenDIt1CiDN1TIXLbhOw0KhJzE78KIFGX6OJ9MrtC0oOqMWf+0xop4qEU8JrJTwCg==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.21.5.tgz",
+      "integrity": "sha512-1rYdTpyv03iycF1+BhzrzQJCdOuAOtaqHTWJZCWvijKD2N5Xu0TtVC8/+1faWqcP9iBCWOmjmhoH94dH82BxPQ==",
       "cpu": [
         "x64"
       ],
@@ -544,9 +553,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/netbsd-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.19.12.tgz",
-      "integrity": "sha512-3ltjQ7n1owJgFbuC61Oj++XhtzmymoCihNFgT84UAmJnxJfm4sYCiSLTXZtE00VWYpPMYc+ZQmB6xbSdVh0JWA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.21.5.tgz",
+      "integrity": "sha512-Woi2MXzXjMULccIwMnLciyZH4nCIMpWQAs049KEeMvOcNADVxo0UBIQPfSmxB3CWKedngg7sWZdLvLczpe0tLg==",
       "cpu": [
         "x64"
       ],
@@ -560,9 +569,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/openbsd-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.19.12.tgz",
-      "integrity": "sha512-RbrfTB9SWsr0kWmb9srfF+L933uMDdu9BIzdA7os2t0TXhCRjrQyCeOt6wVxr79CKD4c+p+YhCj31HBkYcXebw==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.21.5.tgz",
+      "integrity": "sha512-HLNNw99xsvx12lFBUwoT8EVCsSvRNDVxNpjZ7bPn947b8gJPzeHWyNVhFsaerc0n3TsbOINvRP2byTZ5LKezow==",
       "cpu": [
         "x64"
       ],
@@ -576,9 +585,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/sunos-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.19.12.tgz",
-      "integrity": "sha512-HKjJwRrW8uWtCQnQOz9qcU3mUZhTUQvi56Q8DPTLLB+DawoiQdjsYq+j+D3s9I8VFtDr+F9CjgXKKC4ss89IeA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.21.5.tgz",
+      "integrity": "sha512-6+gjmFpfy0BHU5Tpptkuh8+uw3mnrvgs+dSPQXQOv3ekbordwnzTVEb4qnIvQcYXq6gzkyTnoZ9dZG+D4garKg==",
       "cpu": [
         "x64"
       ],
@@ -592,9 +601,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/win32-arm64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.19.12.tgz",
-      "integrity": "sha512-URgtR1dJnmGvX864pn1B2YUYNzjmXkuJOIqG2HdU62MVS4EHpU2946OZoTMnRUHklGtJdJZ33QfzdjGACXhn1A==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.21.5.tgz",
+      "integrity": "sha512-Z0gOTd75VvXqyq7nsl93zwahcTROgqvuAcYDUr+vOv8uHhNSKROyU961kgtCD1e95IqPKSQKH7tBTslnS3tA8A==",
       "cpu": [
         "arm64"
       ],
@@ -608,9 +617,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/win32-ia32": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.19.12.tgz",
-      "integrity": "sha512-+ZOE6pUkMOJfmxmBZElNOx72NKpIa/HFOMGzu8fqzQJ5kgf6aTGrcJaFsNiVMH4JKpMipyK+7k0n2UXN7a8YKQ==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.21.5.tgz",
+      "integrity": "sha512-SWXFF1CL2RVNMaVs+BBClwtfZSvDgtL//G/smwAc5oVK/UPu2Gu9tIaRgFmYFFKrmg3SyAjSrElf0TiJ1v8fYA==",
       "cpu": [
         "ia32"
       ],
@@ -624,9 +633,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@esbuild/win32-x64": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.19.12.tgz",
-      "integrity": "sha512-T1QyPSDCyMXaO3pzBkF96E8xMkiRYbUEZADd29SyPGabqxMViNoii+NcK7eWJAEoU6RZyEm5lVSIjTmcdoB9HA==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.21.5.tgz",
+      "integrity": "sha512-tQd/1efJuzPC6rCFwEvLtci/xNFcTZknmXs98FYDfGE4wP9ClFV98nyKrzJKVPMhdDnjzLhdUyMX4PsQAPjwIw==",
       "cpu": [
         "x64"
       ],
@@ -640,14 +649,14 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@types/node": {
-      "version": "22.10.7",
-      "resolved": "https://registry.npmjs.org/@types/node/-/node-22.10.7.tgz",
-      "integrity": "sha512-V09KvXxFiutGp6B7XkpaDXlNadZxrzajcY50EuoLIpQ6WWYCSvf19lVIazzfIzQvhUN2HjX12spLojTnhuKlGg==",
+      "version": "22.14.1",
+      "resolved": "https://registry.npmjs.org/@types/node/-/node-22.14.1.tgz",
+      "integrity": "sha512-u0HuPQwe/dHrItgHHpmw3N2fYCR6x4ivMNbPHRkBVP4CvN+kiRrKHWk3i8tXiO/joPwXLMYvF9TTF0eqgHIuOw==",
       "dev": true,
       "optional": true,
       "peer": true,
       "dependencies": {
-        "undici-types": "~6.20.0"
+        "undici-types": "~6.21.0"
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/@vitejs/plugin-basic-ssl": {
@@ -662,12 +671,34 @@
         "vite": "^3.0.0 || ^4.0.0 || ^5.0.0"
       }
     },
+    "node_modules/@angular-devkit/build-angular/node_modules/ajv": {
+      "version": "6.12.6",
+      "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+      "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+      "dev": true,
+      "dependencies": {
+        "fast-deep-equal": "^3.1.1",
+        "fast-json-stable-stringify": "^2.0.0",
+        "json-schema-traverse": "^0.4.1",
+        "uri-js": "^4.2.2"
+      },
+      "funding": {
+        "type": "github",
+        "url": "https://github.com/sponsors/epoberezkin"
+      }
+    },
     "node_modules/@angular-devkit/build-angular/node_modules/convert-source-map": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz",
       "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==",
       "dev": true
     },
+    "node_modules/@angular-devkit/build-angular/node_modules/json-schema-traverse": {
+      "version": "0.4.1",
+      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
+      "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==",
+      "dev": true
+    },
     "node_modules/@angular-devkit/build-angular/node_modules/picomatch": {
       "version": "4.0.1",
       "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.1.tgz",
@@ -680,6 +711,15 @@
         "url": "https://github.com/sponsors/jonschlinkert"
       }
     },
+    "node_modules/@angular-devkit/build-angular/node_modules/rxjs": {
+      "version": "7.8.1",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "dev": true,
+      "dependencies": {
+        "tslib": "^2.1.0"
+      }
+    },
     "node_modules/@angular-devkit/build-angular/node_modules/schema-utils": {
       "version": "3.3.0",
       "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz",
@@ -720,14 +760,14 @@
       "dev": true
     },
     "node_modules/@angular-devkit/build-angular/node_modules/vite": {
-      "version": "5.1.8",
-      "resolved": "https://registry.npmjs.org/vite/-/vite-5.1.8.tgz",
-      "integrity": "sha512-mB8ToUuSmzODSpENgvpFk2fTiU/YQ1tmcVJJ4WZbq4fPdGJkFNVcmVL5k7iDug6xzWjjuGDKAuSievIsD6H7Xw==",
+      "version": "5.4.18",
+      "resolved": "https://registry.npmjs.org/vite/-/vite-5.4.18.tgz",
+      "integrity": "sha512-1oDcnEp3lVyHCuQ2YFelM4Alm2o91xNoMncRm1U7S+JdYfYOvbiGZ3/CxGttrOu2M/KcGz7cRC2DoNUA6urmMA==",
       "dev": true,
       "dependencies": {
-        "esbuild": "^0.19.3",
-        "postcss": "^8.4.35",
-        "rollup": "^4.2.0"
+        "esbuild": "^0.21.3",
+        "postcss": "^8.4.43",
+        "rollup": "^4.20.0"
       },
       "bin": {
         "vite": "bin/vite.js"
@@ -746,6 +786,7 @@
         "less": "*",
         "lightningcss": "^1.21.0",
         "sass": "*",
+        "sass-embedded": "*",
         "stylus": "*",
         "sugarss": "*",
         "terser": "^5.4.0"
@@ -763,6 +804,9 @@
         "sass": {
           "optional": true
         },
+        "sass-embedded": {
+          "optional": true
+        },
         "stylus": {
           "optional": true
         },
@@ -775,9 +819,9 @@
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/vite/node_modules/esbuild": {
-      "version": "0.19.12",
-      "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.19.12.tgz",
-      "integrity": "sha512-aARqgq8roFBj054KvQr5f1sFu0D65G+miZRCuJyJ0G13Zwx7vRar5Zhn2tkQNzIXcBrNVsv/8stehpj+GAjgbg==",
+      "version": "0.21.5",
+      "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.21.5.tgz",
+      "integrity": "sha512-mg3OPMV4hXywwpoDxu3Qda5xCKQi+vCTZq8S9J/EpkhB2HzKXq4SNFZE3+NK93JYxc8VMSep+lOUSC/RVKaBqw==",
       "dev": true,
       "hasInstallScript": true,
       "bin": {
@@ -787,29 +831,57 @@
         "node": ">=12"
       },
       "optionalDependencies": {
-        "@esbuild/aix-ppc64": "0.19.12",
-        "@esbuild/android-arm": "0.19.12",
-        "@esbuild/android-arm64": "0.19.12",
-        "@esbuild/android-x64": "0.19.12",
-        "@esbuild/darwin-arm64": "0.19.12",
-        "@esbuild/darwin-x64": "0.19.12",
-        "@esbuild/freebsd-arm64": "0.19.12",
-        "@esbuild/freebsd-x64": "0.19.12",
-        "@esbuild/linux-arm": "0.19.12",
-        "@esbuild/linux-arm64": "0.19.12",
-        "@esbuild/linux-ia32": "0.19.12",
-        "@esbuild/linux-loong64": "0.19.12",
-        "@esbuild/linux-mips64el": "0.19.12",
-        "@esbuild/linux-ppc64": "0.19.12",
-        "@esbuild/linux-riscv64": "0.19.12",
-        "@esbuild/linux-s390x": "0.19.12",
-        "@esbuild/linux-x64": "0.19.12",
-        "@esbuild/netbsd-x64": "0.19.12",
-        "@esbuild/openbsd-x64": "0.19.12",
-        "@esbuild/sunos-x64": "0.19.12",
-        "@esbuild/win32-arm64": "0.19.12",
-        "@esbuild/win32-ia32": "0.19.12",
-        "@esbuild/win32-x64": "0.19.12"
+        "@esbuild/aix-ppc64": "0.21.5",
+        "@esbuild/android-arm": "0.21.5",
+        "@esbuild/android-arm64": "0.21.5",
+        "@esbuild/android-x64": "0.21.5",
+        "@esbuild/darwin-arm64": "0.21.5",
+        "@esbuild/darwin-x64": "0.21.5",
+        "@esbuild/freebsd-arm64": "0.21.5",
+        "@esbuild/freebsd-x64": "0.21.5",
+        "@esbuild/linux-arm": "0.21.5",
+        "@esbuild/linux-arm64": "0.21.5",
+        "@esbuild/linux-ia32": "0.21.5",
+        "@esbuild/linux-loong64": "0.21.5",
+        "@esbuild/linux-mips64el": "0.21.5",
+        "@esbuild/linux-ppc64": "0.21.5",
+        "@esbuild/linux-riscv64": "0.21.5",
+        "@esbuild/linux-s390x": "0.21.5",
+        "@esbuild/linux-x64": "0.21.5",
+        "@esbuild/netbsd-x64": "0.21.5",
+        "@esbuild/openbsd-x64": "0.21.5",
+        "@esbuild/sunos-x64": "0.21.5",
+        "@esbuild/win32-arm64": "0.21.5",
+        "@esbuild/win32-ia32": "0.21.5",
+        "@esbuild/win32-x64": "0.21.5"
+      }
+    },
+    "node_modules/@angular-devkit/build-angular/node_modules/vite/node_modules/postcss": {
+      "version": "8.5.3",
+      "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.3.tgz",
+      "integrity": "sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==",
+      "dev": true,
+      "funding": [
+        {
+          "type": "opencollective",
+          "url": "https://opencollective.com/postcss/"
+        },
+        {
+          "type": "tidelift",
+          "url": "https://tidelift.com/funding/github/npm/postcss"
+        },
+        {
+          "type": "github",
+          "url": "https://github.com/sponsors/ai"
+        }
+      ],
+      "dependencies": {
+        "nanoid": "^3.3.8",
+        "picocolors": "^1.1.1",
+        "source-map-js": "^1.2.1"
+      },
+      "engines": {
+        "node": "^10 || ^12 || >=14"
       }
     },
     "node_modules/@angular-devkit/build-angular/node_modules/watchpack": {
@@ -899,12 +971,12 @@
       }
     },
     "node_modules/@angular-devkit/build-webpack": {
-      "version": "0.1703.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/build-webpack/-/build-webpack-0.1703.11.tgz",
-      "integrity": "sha512-qbCiiHuoVkD7CtLyWoRi/Vzz6nrEztpF5XIyWUcQu67An1VlxbMTE4yoSQiURjCQMnB/JvS1GPVed7wOq3SJ/w==",
+      "version": "0.1703.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/build-webpack/-/build-webpack-0.1703.16.tgz",
+      "integrity": "sha512-ybZr+2F4siu0MztyhSkzN3lIMF0YFeyMaoTygWKjMeGMrkdj4IOAHiR+le2dQ+W4RhwEwQwkV2lvyDJzbivWhg==",
       "dev": true,
       "dependencies": {
-        "@angular-devkit/architect": "0.1703.11",
+        "@angular-devkit/architect": "0.1703.16",
         "rxjs": "7.8.1"
       },
       "engines": {
@@ -917,10 +989,19 @@
         "webpack-dev-server": "^4.0.0"
       }
     },
+    "node_modules/@angular-devkit/build-webpack/node_modules/rxjs": {
+      "version": "7.8.1",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "dev": true,
+      "dependencies": {
+        "tslib": "^2.1.0"
+      }
+    },
     "node_modules/@angular-devkit/core": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-17.3.11.tgz",
-      "integrity": "sha512-vTNDYNsLIWpYk2I969LMQFH29GTsLzxNk/0cLw5q56ARF0v5sIWfHYwGTS88jdDqIpuuettcSczbxeA7EuAmqQ==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-17.3.16.tgz",
+      "integrity": "sha512-3Dhb/pE3c6P9bDfYLhYb0ArTFYmYSx5QgEUVMuowXJtP/3EyU7lWB2kcuiBZgScxrhRLOiMGMPgcF9jVmvovug==",
       "dev": true,
       "dependencies": {
         "ajv": "8.12.0",
@@ -960,12 +1041,6 @@
         "url": "https://github.com/sponsors/epoberezkin"
       }
     },
-    "node_modules/@angular-devkit/core/node_modules/json-schema-traverse": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
-      "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
-      "dev": true
-    },
     "node_modules/@angular-devkit/core/node_modules/picomatch": {
       "version": "4.0.1",
       "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.1.tgz",
@@ -978,13 +1053,22 @@
         "url": "https://github.com/sponsors/jonschlinkert"
       }
     },
+    "node_modules/@angular-devkit/core/node_modules/rxjs": {
+      "version": "7.8.1",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "dev": true,
+      "dependencies": {
+        "tslib": "^2.1.0"
+      }
+    },
     "node_modules/@angular-devkit/schematics": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-17.3.11.tgz",
-      "integrity": "sha512-I5wviiIqiFwar9Pdk30Lujk8FczEEc18i22A5c6Z9lbmhPQdTroDnEQdsfXjy404wPe8H62s0I15o4pmMGfTYQ==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-17.3.16.tgz",
+      "integrity": "sha512-EcKBdQ02RIwYLHrExOvtrj8FXtTT/Z0IQe8maUy+YkOWjJHsjpdRBOwi3JOICyjnkopOtkkHy/bxu5VKh6rL7A==",
       "dev": true,
       "dependencies": {
-        "@angular-devkit/core": "17.3.11",
+        "@angular-devkit/core": "17.3.16",
         "jsonc-parser": "3.2.1",
         "magic-string": "0.30.8",
         "ora": "5.4.1",
@@ -996,6 +1080,15 @@
         "yarn": ">= 1.13.0"
       }
     },
+    "node_modules/@angular-devkit/schematics/node_modules/rxjs": {
+      "version": "7.8.1",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "dev": true,
+      "dependencies": {
+        "tslib": "^2.1.0"
+      }
+    },
     "node_modules/@angular/animations": {
       "version": "17.3.12",
       "resolved": "https://registry.npmjs.org/@angular/animations/-/animations-17.3.12.tgz",
@@ -1027,15 +1120,15 @@
       }
     },
     "node_modules/@angular/cli": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular/cli/-/cli-17.3.11.tgz",
-      "integrity": "sha512-8R9LwAGL8hGAWJ4mNG9ZPUrBUzIdmst0Ldua6RJJ+PrqgjX+8IbO+lNnfrOY/XY+Z3LXbCEJflL26f9czCvTPQ==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular/cli/-/cli-17.3.16.tgz",
+      "integrity": "sha512-cG/+aAW7z/o8Tl75U6d+pa+zygV9cvdeY/vb6ve16o4MS6Ifwbls6L51gekYGdWpLl1QnWHLbZFz7+mOa7Um2w==",
       "dev": true,
       "dependencies": {
-        "@angular-devkit/architect": "0.1703.11",
-        "@angular-devkit/core": "17.3.11",
-        "@angular-devkit/schematics": "17.3.11",
-        "@schematics/angular": "17.3.11",
+        "@angular-devkit/architect": "0.1703.16",
+        "@angular-devkit/core": "17.3.16",
+        "@angular-devkit/schematics": "17.3.16",
+        "@schematics/angular": "17.3.16",
         "@yarnpkg/lockfile": "1.1.0",
         "ansi-colors": "4.1.3",
         "ini": "4.1.2",
@@ -1347,9 +1440,9 @@
       }
     },
     "node_modules/@babel/compat-data": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.5.tgz",
-      "integrity": "sha512-XvcZi1KWf88RVbF9wn8MN6tYFloU5qX8KjuF3E1PVBmJ9eypXfs4GRiJwLuTZL0iSnJUKn1BFPa5BPZZJyFzPg==",
+      "version": "7.26.8",
+      "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.8.tgz",
+      "integrity": "sha512-oH5UPLMWR3L2wEFLnFJ1TZXqHufiTKAiLfqw5zkhS4dKXLJ10yVztfil/twG8EDTA4F/tvVNw9nOl4ZMslB8rQ==",
       "dev": true,
       "engines": {
         "node": ">=6.9.0"
@@ -1385,40 +1478,12 @@
         "url": "https://opencollective.com/babel"
       }
     },
-    "node_modules/@babel/core/node_modules/@babel/generator": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.5.tgz",
-      "integrity": "sha512-2caSP6fN9I7HOe6nqhtft7V4g7/V/gfDsC3Ag4W7kEzzvRGKqiv0pu0HogPiZ3KaVSoNDhUws6IJjDjpfmYIXw==",
-      "dev": true,
-      "dependencies": {
-        "@babel/parser": "^7.26.5",
-        "@babel/types": "^7.26.5",
-        "@jridgewell/gen-mapping": "^0.3.5",
-        "@jridgewell/trace-mapping": "^0.3.25",
-        "jsesc": "^3.0.2"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/core/node_modules/convert-source-map": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz",
       "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==",
       "dev": true
     },
-    "node_modules/@babel/core/node_modules/jsesc": {
-      "version": "3.1.0",
-      "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz",
-      "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==",
-      "dev": true,
-      "bin": {
-        "jsesc": "bin/jsesc"
-      },
-      "engines": {
-        "node": ">=6"
-      }
-    },
     "node_modules/@babel/core/node_modules/semver": {
       "version": "6.3.1",
       "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
@@ -1429,27 +1494,28 @@
       }
     },
     "node_modules/@babel/generator": {
-      "version": "7.23.6",
-      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.23.6.tgz",
-      "integrity": "sha512-qrSfCYxYQB5owCmGLbl8XRpX1ytXlpueOb0N0UmQwA073KZxejgQTzAmJezxvpwQD9uGtK2shHdi55QT+MbjIw==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.10.tgz",
+      "integrity": "sha512-rRHT8siFIXQrAYOYqZQVsAr8vJ+cBNqcVAY6m5V8/4QqzaPl+zDBe6cLEPRDuNOUf3ww8RfJVlOyQMoSI+5Ang==",
       "dev": true,
       "dependencies": {
-        "@babel/types": "^7.23.6",
-        "@jridgewell/gen-mapping": "^0.3.2",
-        "@jridgewell/trace-mapping": "^0.3.17",
-        "jsesc": "^2.5.1"
+        "@babel/parser": "^7.26.10",
+        "@babel/types": "^7.26.10",
+        "@jridgewell/gen-mapping": "^0.3.5",
+        "@jridgewell/trace-mapping": "^0.3.25",
+        "jsesc": "^3.0.2"
       },
       "engines": {
         "node": ">=6.9.0"
       }
     },
     "node_modules/@babel/helper-annotate-as-pure": {
-      "version": "7.22.5",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.22.5.tgz",
-      "integrity": "sha512-LvBTxu8bQSQkcyKOU+a1btnNFQ1dMAd0R6PyW3arXes06F6QLWLIrd681bxRPIXlrMGR3XYnW9JyML7dP3qgxg==",
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
+      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
       "dev": true,
       "dependencies": {
-        "@babel/types": "^7.22.5"
+        "@babel/types": "^7.25.9"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -1516,18 +1582,6 @@
         "@babel/core": "^7.0.0"
       }
     },
-    "node_modules/@babel/helper-create-class-features-plugin/node_modules/@babel/helper-annotate-as-pure": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-      "dev": true,
-      "dependencies": {
-        "@babel/types": "^7.25.9"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/helper-create-class-features-plugin/node_modules/semver": {
       "version": "6.3.1",
       "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
@@ -1554,18 +1608,6 @@
         "@babel/core": "^7.0.0"
       }
     },
-    "node_modules/@babel/helper-create-regexp-features-plugin/node_modules/@babel/helper-annotate-as-pure": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-      "dev": true,
-      "dependencies": {
-        "@babel/types": "^7.25.9"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/helper-create-regexp-features-plugin/node_modules/semver": {
       "version": "6.3.1",
       "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
@@ -1576,9 +1618,9 @@
       }
     },
     "node_modules/@babel/helper-define-polyfill-provider": {
-      "version": "0.6.3",
-      "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.3.tgz",
-      "integrity": "sha512-HK7Bi+Hj6H+VTHA3ZvBis7V/6hu9QuTrnMXNybfUf2iiuU/N97I8VjB+KbhFF8Rld/Lx5MzoCwPCpPjfK+n8Cg==",
+      "version": "0.6.4",
+      "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.4.tgz",
+      "integrity": "sha512-jljfR1rGnXXNWnmQg2K3+bvhkxB51Rl32QRaOTuwwjviGrHzIbSc8+x9CpraDtbT7mfyjXObULP4w/adunNwAw==",
       "dev": true,
       "dependencies": {
         "@babel/helper-compilation-targets": "^7.22.6",
@@ -1591,18 +1633,6 @@
         "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0"
       }
     },
-    "node_modules/@babel/helper-environment-visitor": {
-      "version": "7.24.7",
-      "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.24.7.tgz",
-      "integrity": "sha512-DoiN84+4Gnd0ncbBOM9AZENV4a5ZiL39HYMyZJGZ/AZEykHYdJw0wW3kdcsh9/Kn+BRXHLkkklZ51ecPKmI1CQ==",
-      "dev": true,
-      "dependencies": {
-        "@babel/types": "^7.24.7"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/helper-member-expression-to-functions": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.25.9.tgz",
@@ -1684,18 +1714,6 @@
         "@babel/core": "^7.0.0"
       }
     },
-    "node_modules/@babel/helper-remap-async-to-generator/node_modules/@babel/helper-annotate-as-pure": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-      "dev": true,
-      "dependencies": {
-        "@babel/types": "^7.25.9"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/helper-replace-supers": {
       "version": "7.26.5",
       "resolved": "https://registry.npmjs.org/@babel/helper-replace-supers/-/helper-replace-supers-7.26.5.tgz",
@@ -1727,12 +1745,12 @@
       }
     },
     "node_modules/@babel/helper-split-export-declaration": {
-      "version": "7.22.6",
-      "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.22.6.tgz",
-      "integrity": "sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g==",
+      "version": "7.24.7",
+      "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.24.7.tgz",
+      "integrity": "sha512-oy5V7pD+UvfkEATUKvIjvIAH/xCzfsFVw7ygW2SI6NClZzquT+mwdTfgfdbUiceh6iQO0CHtCPsyze/MZ2YbAA==",
       "dev": true,
       "dependencies": {
-        "@babel/types": "^7.22.5"
+        "@babel/types": "^7.24.7"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -1780,25 +1798,25 @@
       }
     },
     "node_modules/@babel/helpers": {
-      "version": "7.26.0",
-      "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.26.0.tgz",
-      "integrity": "sha512-tbhNuIxNcVb21pInl3ZSjksLCvgdZy9KwJ8brv993QtIVKJBBkYXz4q4ZbAv31GdnC+R90np23L5FbEBlthAEw==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.27.0.tgz",
+      "integrity": "sha512-U5eyP/CTFPuNE3qk+WZMxFkp/4zUzdceQlfzf7DdGdhp+Fezd7HD+i8Y24ZuTMKX3wQBld449jijbGq6OdGNQg==",
       "dev": true,
       "dependencies": {
-        "@babel/template": "^7.25.9",
-        "@babel/types": "^7.26.0"
+        "@babel/template": "^7.27.0",
+        "@babel/types": "^7.27.0"
       },
       "engines": {
         "node": ">=6.9.0"
       }
     },
     "node_modules/@babel/parser": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.26.5.tgz",
-      "integrity": "sha512-SRJ4jYmXRqV1/Xc+TIVG84WjHBXKlxO9sHQnA2Pf12QQEAp1LOh6kDzNHXcUnbH1QI0FDoPPVOt+vyUDucxpaw==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.27.0.tgz",
+      "integrity": "sha512-iaepho73/2Pz7w2eMS0Q5f83+0RKI7i4xmiYeBmDzfRVbQtTOG7Ts0S4HzJVsTMGI9keU8rNfuZr8DKfSt7Yyg==",
       "dev": true,
       "dependencies": {
-        "@babel/types": "^7.26.5"
+        "@babel/types": "^7.27.0"
       },
       "bin": {
         "parser": "bin/babel-parser.js"
@@ -1807,6 +1825,37 @@
         "node": ">=6.0.0"
       }
     },
+    "node_modules/@babel/plugin-bugfix-firefox-class-in-computed-class-key": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-firefox-class-in-computed-class-key/-/plugin-bugfix-firefox-class-in-computed-class-key-7.25.9.tgz",
+      "integrity": "sha512-ZkRyVkThtxQ/J6nv3JFYv1RYY+JT5BvU0y3k5bWrmuG4woXypRa4PXmm9RhOwodRkYFWqC0C0cqcJ4OqR7kW+g==",
+      "dev": true,
+      "dependencies": {
+        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/traverse": "^7.25.9"
+      },
+      "engines": {
+        "node": ">=6.9.0"
+      },
+      "peerDependencies": {
+        "@babel/core": "^7.0.0"
+      }
+    },
+    "node_modules/@babel/plugin-bugfix-safari-class-field-initializer-scope": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-class-field-initializer-scope/-/plugin-bugfix-safari-class-field-initializer-scope-7.25.9.tgz",
+      "integrity": "sha512-MrGRLZxLD/Zjj0gdU15dfs+HH/OXvnw/U4jJD8vpcP2CJQapPEv1IWwjc/qMg7ItBlPwSv1hRBbb7LeuANdcnw==",
+      "dev": true,
+      "dependencies": {
+        "@babel/helper-plugin-utils": "^7.25.9"
+      },
+      "engines": {
+        "node": ">=6.9.0"
+      },
+      "peerDependencies": {
+        "@babel/core": "^7.0.0"
+      }
+    },
     "node_modules/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.25.9.tgz",
@@ -1867,69 +1916,6 @@
         "@babel/core": "^7.0.0-0"
       }
     },
-    "node_modules/@babel/plugin-syntax-async-generators": {
-      "version": "7.8.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-async-generators/-/plugin-syntax-async-generators-7.8.4.tgz",
-      "integrity": "sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-class-properties": {
-      "version": "7.12.13",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-properties/-/plugin-syntax-class-properties-7.12.13.tgz",
-      "integrity": "sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.12.13"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-class-static-block": {
-      "version": "7.14.5",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-static-block/-/plugin-syntax-class-static-block-7.14.5.tgz",
-      "integrity": "sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.14.5"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-dynamic-import": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-dynamic-import/-/plugin-syntax-dynamic-import-7.8.3.tgz",
-      "integrity": "sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-export-namespace-from": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-export-namespace-from/-/plugin-syntax-export-namespace-from-7.8.3.tgz",
-      "integrity": "sha512-MXf5laXo6c1IbEbegDmzGPwGNTsHZmEy6QGznu5Sh2UCWvueywb2ee+CCE4zQiZstxU9BMoQO9i6zUFSY0Kj0Q==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.3"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
     "node_modules/@babel/plugin-syntax-import-assertions": {
       "version": "7.26.0",
       "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.26.0.tgz",
@@ -1947,137 +1933,11 @@
     },
     "node_modules/@babel/plugin-syntax-import-attributes": {
       "version": "7.26.0",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.26.0.tgz",
-      "integrity": "sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.25.9"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-import-meta": {
-      "version": "7.10.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-meta/-/plugin-syntax-import-meta-7.10.4.tgz",
-      "integrity": "sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.10.4"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-json-strings": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.8.3.tgz",
-      "integrity": "sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-logical-assignment-operators": {
-      "version": "7.10.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-logical-assignment-operators/-/plugin-syntax-logical-assignment-operators-7.10.4.tgz",
-      "integrity": "sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.10.4"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-nullish-coalescing-operator": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-nullish-coalescing-operator/-/plugin-syntax-nullish-coalescing-operator-7.8.3.tgz",
-      "integrity": "sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-numeric-separator": {
-      "version": "7.10.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.10.4.tgz",
-      "integrity": "sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.10.4"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-object-rest-spread": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz",
-      "integrity": "sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-optional-catch-binding": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-catch-binding/-/plugin-syntax-optional-catch-binding-7.8.3.tgz",
-      "integrity": "sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-optional-chaining": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-chaining/-/plugin-syntax-optional-chaining-7.8.3.tgz",
-      "integrity": "sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-private-property-in-object": {
-      "version": "7.14.5",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-private-property-in-object/-/plugin-syntax-private-property-in-object-7.14.5.tgz",
-      "integrity": "sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-plugin-utils": "^7.14.5"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.0.0-0"
-      }
-    },
-    "node_modules/@babel/plugin-syntax-top-level-await": {
-      "version": "7.14.5",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-top-level-await/-/plugin-syntax-top-level-await-7.14.5.tgz",
-      "integrity": "sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.26.0.tgz",
+      "integrity": "sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-plugin-utils": "^7.14.5"
+        "@babel/helper-plugin-utils": "^7.25.9"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -2118,15 +1978,14 @@
       }
     },
     "node_modules/@babel/plugin-transform-async-generator-functions": {
-      "version": "7.23.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.23.9.tgz",
-      "integrity": "sha512-8Q3veQEDGe14dTYuwagbRtwxQDnytyg1JFu4/HwEMETeofocrB0U0ejBJIXoeG/t2oXZ8kzCyI0ZZfbT80VFNQ==",
+      "version": "7.26.8",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.26.8.tgz",
+      "integrity": "sha512-He9Ej2X7tNf2zdKMAGOsmg2MrFc+hfoAhd3po4cWfo/NWjzEAKa0oQruj1ROVUdl0e6fb6/kE/G3SSxE0lRJOg==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-environment-visitor": "^7.22.20",
-        "@babel/helper-plugin-utils": "^7.22.5",
-        "@babel/helper-remap-async-to-generator": "^7.22.20",
-        "@babel/plugin-syntax-async-generators": "^7.8.4"
+        "@babel/helper-plugin-utils": "^7.26.5",
+        "@babel/helper-remap-async-to-generator": "^7.25.9",
+        "@babel/traverse": "^7.26.8"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -2136,14 +1995,14 @@
       }
     },
     "node_modules/@babel/plugin-transform-async-to-generator": {
-      "version": "7.23.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.23.3.tgz",
-      "integrity": "sha512-A7LFsKi4U4fomjqXJlZg/u0ft/n8/7n7lpffUP/ZULx/DtV9SGlNKZolHH6PE8Xl1ngCc0M11OaeZptXVkfKSw==",
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.25.9.tgz",
+      "integrity": "sha512-NT7Ejn7Z/LjUH0Gv5KsBCxh7BH3fbLTV0ptHvpeMvrt3cPThHfJfst9Wrb7S8EvJ7vRTFI7z+VAvFVEQn/m5zQ==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-module-imports": "^7.22.15",
-        "@babel/helper-plugin-utils": "^7.22.5",
-        "@babel/helper-remap-async-to-generator": "^7.22.20"
+        "@babel/helper-module-imports": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/helper-remap-async-to-generator": "^7.25.9"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -2234,18 +2093,6 @@
         "@babel/core": "^7.0.0-0"
       }
     },
-    "node_modules/@babel/plugin-transform-classes/node_modules/@babel/helper-annotate-as-pure": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-      "dev": true,
-      "dependencies": {
-        "@babel/types": "^7.25.9"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/plugin-transform-computed-properties": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-transform-computed-properties/-/plugin-transform-computed-properties-7.25.9.tgz",
@@ -2308,6 +2155,22 @@
         "@babel/core": "^7.0.0-0"
       }
     },
+    "node_modules/@babel/plugin-transform-duplicate-named-capturing-groups-regex": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-named-capturing-groups-regex/-/plugin-transform-duplicate-named-capturing-groups-regex-7.25.9.tgz",
+      "integrity": "sha512-0UfuJS0EsXbRvKnwcLjFtJy/Sxc5J5jhLHnFhy7u4zih97Hz6tJkLU+O+FMMrNZrosUPxDi6sYxJ/EA8jDiAog==",
+      "dev": true,
+      "dependencies": {
+        "@babel/helper-create-regexp-features-plugin": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.25.9"
+      },
+      "engines": {
+        "node": ">=6.9.0"
+      },
+      "peerDependencies": {
+        "@babel/core": "^7.0.0"
+      }
+    },
     "node_modules/@babel/plugin-transform-dynamic-import": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dynamic-import/-/plugin-transform-dynamic-import-7.25.9.tgz",
@@ -2354,12 +2217,12 @@
       }
     },
     "node_modules/@babel/plugin-transform-for-of": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.25.9.tgz",
-      "integrity": "sha512-LqHxduHoaGELJl2uhImHwRQudhCM50pT46rIBNvtT/Oql3nqiS3wOwP+5ten7NpYSXrrVLgtZU3DZmPtWZo16A==",
+      "version": "7.26.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.26.9.tgz",
+      "integrity": "sha512-Hry8AusVm8LW5BVFgiyUReuoGzPUpdHQQqJY5bZnbbf+ngOHWuCuYFKw/BqaaWlvEUrF91HMhDtEaI1hZzNbLg==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.26.5",
         "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9"
       },
       "engines": {
@@ -2685,18 +2548,6 @@
         "@babel/core": "^7.0.0-0"
       }
     },
-    "node_modules/@babel/plugin-transform-private-property-in-object/node_modules/@babel/helper-annotate-as-pure": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-      "dev": true,
-      "dependencies": {
-        "@babel/types": "^7.25.9"
-      },
-      "engines": {
-        "node": ">=6.9.0"
-      }
-    },
     "node_modules/@babel/plugin-transform-property-literals": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-transform-property-literals/-/plugin-transform-property-literals-7.25.9.tgz",
@@ -2728,6 +2579,22 @@
         "@babel/core": "^7.0.0-0"
       }
     },
+    "node_modules/@babel/plugin-transform-regexp-modifiers": {
+      "version": "7.26.0",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regexp-modifiers/-/plugin-transform-regexp-modifiers-7.26.0.tgz",
+      "integrity": "sha512-vN6saax7lrA2yA/Pak3sCxuD6F5InBjn9IcrIKQPjpsLvuHYLVroTxjdlVRHjjBWxKOqIwpTXDkOssYT4BFdRw==",
+      "dev": true,
+      "dependencies": {
+        "@babel/helper-create-regexp-features-plugin": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.25.9"
+      },
+      "engines": {
+        "node": ">=6.9.0"
+      },
+      "peerDependencies": {
+        "@babel/core": "^7.0.0"
+      }
+    },
     "node_modules/@babel/plugin-transform-reserved-words": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.25.9.tgz",
@@ -2744,16 +2611,16 @@
       }
     },
     "node_modules/@babel/plugin-transform-runtime": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.24.0.tgz",
-      "integrity": "sha512-zc0GA5IitLKJrSfXlXmp8KDqLrnGECK7YRfQBmEKg1NmBOQ7e+KuclBEKJgzifQeUYLdNiAw4B4bjyvzWVLiSA==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.26.10.tgz",
+      "integrity": "sha512-NWaL2qG6HRpONTnj4JvDU6th4jYeZOJgu3QhmFTCihib0ermtOJqktA5BduGm3suhhVe9EMP9c9+mfJ/I9slqw==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-module-imports": "^7.22.15",
-        "@babel/helper-plugin-utils": "^7.24.0",
-        "babel-plugin-polyfill-corejs2": "^0.4.8",
-        "babel-plugin-polyfill-corejs3": "^0.9.0",
-        "babel-plugin-polyfill-regenerator": "^0.5.5",
+        "@babel/helper-module-imports": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.26.5",
+        "babel-plugin-polyfill-corejs2": "^0.4.10",
+        "babel-plugin-polyfill-corejs3": "^0.11.0",
+        "babel-plugin-polyfill-regenerator": "^0.6.1",
         "semver": "^6.3.1"
       },
       "engines": {
@@ -2819,12 +2686,12 @@
       }
     },
     "node_modules/@babel/plugin-transform-template-literals": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.25.9.tgz",
-      "integrity": "sha512-o97AE4syN71M/lxrCtQByzphAdlYluKPDBzDVzMmfCobUjjhAryZV0AIpRPrxN0eAkxXO6ZLEScmt+PNhj2OTw==",
+      "version": "7.26.8",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.26.8.tgz",
+      "integrity": "sha512-OmGDL5/J0CJPJZTHZbi2XpO0tyT2Ia7fzpW5GURwdtp2X3fMmN8au/ej6peC/T33/+CRiIpA8Krse8hFGVmT5Q==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-plugin-utils": "^7.25.9"
+        "@babel/helper-plugin-utils": "^7.26.5"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -2834,12 +2701,12 @@
       }
     },
     "node_modules/@babel/plugin-transform-typeof-symbol": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.25.9.tgz",
-      "integrity": "sha512-v61XqUMiueJROUv66BVIOi0Fv/CUuZuZMl5NkRoCVxLAnMexZ0A3kMe7vvZ0nulxMuMp0Mk6S5hNh48yki08ZA==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.27.0.tgz",
+      "integrity": "sha512-+LLkxA9rKJpNoGsbLnAgOCdESl73vwYn+V6b+5wHbrE7OGKVDPHIQvbFSzqE6rwqaCw2RE+zdJrlLkcf8YOA0w==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-plugin-utils": "^7.25.9"
+        "@babel/helper-plugin-utils": "^7.26.5"
       },
       "engines": {
         "node": ">=6.9.0"
@@ -2912,90 +2779,79 @@
       }
     },
     "node_modules/@babel/preset-env": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.24.0.tgz",
-      "integrity": "sha512-ZxPEzV9IgvGn73iK0E6VB9/95Nd7aMFpbE0l8KQFDG70cOV9IxRP7Y2FUPmlK0v6ImlLqYX50iuZ3ZTVhOF2lA==",
+      "version": "7.26.9",
+      "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.26.9.tgz",
+      "integrity": "sha512-vX3qPGE8sEKEAZCWk05k3cpTAE3/nOYca++JA+Rd0z2NCNzabmYvEiSShKzm10zdquOIAVXsy2Ei/DTW34KlKQ==",
       "dev": true,
       "dependencies": {
-        "@babel/compat-data": "^7.23.5",
-        "@babel/helper-compilation-targets": "^7.23.6",
-        "@babel/helper-plugin-utils": "^7.24.0",
-        "@babel/helper-validator-option": "^7.23.5",
-        "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.23.3",
-        "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.23.3",
-        "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.23.7",
+        "@babel/compat-data": "^7.26.8",
+        "@babel/helper-compilation-targets": "^7.26.5",
+        "@babel/helper-plugin-utils": "^7.26.5",
+        "@babel/helper-validator-option": "^7.25.9",
+        "@babel/plugin-bugfix-firefox-class-in-computed-class-key": "^7.25.9",
+        "@babel/plugin-bugfix-safari-class-field-initializer-scope": "^7.25.9",
+        "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.25.9",
+        "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.25.9",
+        "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.25.9",
         "@babel/plugin-proposal-private-property-in-object": "7.21.0-placeholder-for-preset-env.2",
-        "@babel/plugin-syntax-async-generators": "^7.8.4",
-        "@babel/plugin-syntax-class-properties": "^7.12.13",
-        "@babel/plugin-syntax-class-static-block": "^7.14.5",
-        "@babel/plugin-syntax-dynamic-import": "^7.8.3",
-        "@babel/plugin-syntax-export-namespace-from": "^7.8.3",
-        "@babel/plugin-syntax-import-assertions": "^7.23.3",
-        "@babel/plugin-syntax-import-attributes": "^7.23.3",
-        "@babel/plugin-syntax-import-meta": "^7.10.4",
-        "@babel/plugin-syntax-json-strings": "^7.8.3",
-        "@babel/plugin-syntax-logical-assignment-operators": "^7.10.4",
-        "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3",
-        "@babel/plugin-syntax-numeric-separator": "^7.10.4",
-        "@babel/plugin-syntax-object-rest-spread": "^7.8.3",
-        "@babel/plugin-syntax-optional-catch-binding": "^7.8.3",
-        "@babel/plugin-syntax-optional-chaining": "^7.8.3",
-        "@babel/plugin-syntax-private-property-in-object": "^7.14.5",
-        "@babel/plugin-syntax-top-level-await": "^7.14.5",
+        "@babel/plugin-syntax-import-assertions": "^7.26.0",
+        "@babel/plugin-syntax-import-attributes": "^7.26.0",
         "@babel/plugin-syntax-unicode-sets-regex": "^7.18.6",
-        "@babel/plugin-transform-arrow-functions": "^7.23.3",
-        "@babel/plugin-transform-async-generator-functions": "^7.23.9",
-        "@babel/plugin-transform-async-to-generator": "^7.23.3",
-        "@babel/plugin-transform-block-scoped-functions": "^7.23.3",
-        "@babel/plugin-transform-block-scoping": "^7.23.4",
-        "@babel/plugin-transform-class-properties": "^7.23.3",
-        "@babel/plugin-transform-class-static-block": "^7.23.4",
-        "@babel/plugin-transform-classes": "^7.23.8",
-        "@babel/plugin-transform-computed-properties": "^7.23.3",
-        "@babel/plugin-transform-destructuring": "^7.23.3",
-        "@babel/plugin-transform-dotall-regex": "^7.23.3",
-        "@babel/plugin-transform-duplicate-keys": "^7.23.3",
-        "@babel/plugin-transform-dynamic-import": "^7.23.4",
-        "@babel/plugin-transform-exponentiation-operator": "^7.23.3",
-        "@babel/plugin-transform-export-namespace-from": "^7.23.4",
-        "@babel/plugin-transform-for-of": "^7.23.6",
-        "@babel/plugin-transform-function-name": "^7.23.3",
-        "@babel/plugin-transform-json-strings": "^7.23.4",
-        "@babel/plugin-transform-literals": "^7.23.3",
-        "@babel/plugin-transform-logical-assignment-operators": "^7.23.4",
-        "@babel/plugin-transform-member-expression-literals": "^7.23.3",
-        "@babel/plugin-transform-modules-amd": "^7.23.3",
-        "@babel/plugin-transform-modules-commonjs": "^7.23.3",
-        "@babel/plugin-transform-modules-systemjs": "^7.23.9",
-        "@babel/plugin-transform-modules-umd": "^7.23.3",
-        "@babel/plugin-transform-named-capturing-groups-regex": "^7.22.5",
-        "@babel/plugin-transform-new-target": "^7.23.3",
-        "@babel/plugin-transform-nullish-coalescing-operator": "^7.23.4",
-        "@babel/plugin-transform-numeric-separator": "^7.23.4",
-        "@babel/plugin-transform-object-rest-spread": "^7.24.0",
-        "@babel/plugin-transform-object-super": "^7.23.3",
-        "@babel/plugin-transform-optional-catch-binding": "^7.23.4",
-        "@babel/plugin-transform-optional-chaining": "^7.23.4",
-        "@babel/plugin-transform-parameters": "^7.23.3",
-        "@babel/plugin-transform-private-methods": "^7.23.3",
-        "@babel/plugin-transform-private-property-in-object": "^7.23.4",
-        "@babel/plugin-transform-property-literals": "^7.23.3",
-        "@babel/plugin-transform-regenerator": "^7.23.3",
-        "@babel/plugin-transform-reserved-words": "^7.23.3",
-        "@babel/plugin-transform-shorthand-properties": "^7.23.3",
-        "@babel/plugin-transform-spread": "^7.23.3",
-        "@babel/plugin-transform-sticky-regex": "^7.23.3",
-        "@babel/plugin-transform-template-literals": "^7.23.3",
-        "@babel/plugin-transform-typeof-symbol": "^7.23.3",
-        "@babel/plugin-transform-unicode-escapes": "^7.23.3",
-        "@babel/plugin-transform-unicode-property-regex": "^7.23.3",
-        "@babel/plugin-transform-unicode-regex": "^7.23.3",
-        "@babel/plugin-transform-unicode-sets-regex": "^7.23.3",
+        "@babel/plugin-transform-arrow-functions": "^7.25.9",
+        "@babel/plugin-transform-async-generator-functions": "^7.26.8",
+        "@babel/plugin-transform-async-to-generator": "^7.25.9",
+        "@babel/plugin-transform-block-scoped-functions": "^7.26.5",
+        "@babel/plugin-transform-block-scoping": "^7.25.9",
+        "@babel/plugin-transform-class-properties": "^7.25.9",
+        "@babel/plugin-transform-class-static-block": "^7.26.0",
+        "@babel/plugin-transform-classes": "^7.25.9",
+        "@babel/plugin-transform-computed-properties": "^7.25.9",
+        "@babel/plugin-transform-destructuring": "^7.25.9",
+        "@babel/plugin-transform-dotall-regex": "^7.25.9",
+        "@babel/plugin-transform-duplicate-keys": "^7.25.9",
+        "@babel/plugin-transform-duplicate-named-capturing-groups-regex": "^7.25.9",
+        "@babel/plugin-transform-dynamic-import": "^7.25.9",
+        "@babel/plugin-transform-exponentiation-operator": "^7.26.3",
+        "@babel/plugin-transform-export-namespace-from": "^7.25.9",
+        "@babel/plugin-transform-for-of": "^7.26.9",
+        "@babel/plugin-transform-function-name": "^7.25.9",
+        "@babel/plugin-transform-json-strings": "^7.25.9",
+        "@babel/plugin-transform-literals": "^7.25.9",
+        "@babel/plugin-transform-logical-assignment-operators": "^7.25.9",
+        "@babel/plugin-transform-member-expression-literals": "^7.25.9",
+        "@babel/plugin-transform-modules-amd": "^7.25.9",
+        "@babel/plugin-transform-modules-commonjs": "^7.26.3",
+        "@babel/plugin-transform-modules-systemjs": "^7.25.9",
+        "@babel/plugin-transform-modules-umd": "^7.25.9",
+        "@babel/plugin-transform-named-capturing-groups-regex": "^7.25.9",
+        "@babel/plugin-transform-new-target": "^7.25.9",
+        "@babel/plugin-transform-nullish-coalescing-operator": "^7.26.6",
+        "@babel/plugin-transform-numeric-separator": "^7.25.9",
+        "@babel/plugin-transform-object-rest-spread": "^7.25.9",
+        "@babel/plugin-transform-object-super": "^7.25.9",
+        "@babel/plugin-transform-optional-catch-binding": "^7.25.9",
+        "@babel/plugin-transform-optional-chaining": "^7.25.9",
+        "@babel/plugin-transform-parameters": "^7.25.9",
+        "@babel/plugin-transform-private-methods": "^7.25.9",
+        "@babel/plugin-transform-private-property-in-object": "^7.25.9",
+        "@babel/plugin-transform-property-literals": "^7.25.9",
+        "@babel/plugin-transform-regenerator": "^7.25.9",
+        "@babel/plugin-transform-regexp-modifiers": "^7.26.0",
+        "@babel/plugin-transform-reserved-words": "^7.25.9",
+        "@babel/plugin-transform-shorthand-properties": "^7.25.9",
+        "@babel/plugin-transform-spread": "^7.25.9",
+        "@babel/plugin-transform-sticky-regex": "^7.25.9",
+        "@babel/plugin-transform-template-literals": "^7.26.8",
+        "@babel/plugin-transform-typeof-symbol": "^7.26.7",
+        "@babel/plugin-transform-unicode-escapes": "^7.25.9",
+        "@babel/plugin-transform-unicode-property-regex": "^7.25.9",
+        "@babel/plugin-transform-unicode-regex": "^7.25.9",
+        "@babel/plugin-transform-unicode-sets-regex": "^7.25.9",
         "@babel/preset-modules": "0.1.6-no-external-plugins",
-        "babel-plugin-polyfill-corejs2": "^0.4.8",
-        "babel-plugin-polyfill-corejs3": "^0.9.0",
-        "babel-plugin-polyfill-regenerator": "^0.5.5",
-        "core-js-compat": "^3.31.0",
+        "babel-plugin-polyfill-corejs2": "^0.4.10",
+        "babel-plugin-polyfill-corejs3": "^0.11.0",
+        "babel-plugin-polyfill-regenerator": "^0.6.1",
+        "core-js-compat": "^3.40.0",
         "semver": "^6.3.1"
       },
       "engines": {
@@ -3029,9 +2885,9 @@
       }
     },
     "node_modules/@babel/runtime": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.24.0.tgz",
-      "integrity": "sha512-Chk32uHMg6TnQdvw2e9IlqPpFX/6NLuK0Ys2PqLb7/gL5uFn9mXvK715FGLlOLQrcO4qIkNHkvPGktzzXexsFw==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.26.10.tgz",
+      "integrity": "sha512-2WJMeRQPHKSPemqk/awGrAiuFfzBmOIPXKizAsVhWH9YJqLZ0H+HS4c8loHGgW6utJ3E/ejXQUsiGaQy2NZ9Fw==",
       "dependencies": {
         "regenerator-runtime": "^0.14.0"
       },
@@ -3040,30 +2896,30 @@
       }
     },
     "node_modules/@babel/template": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.25.9.tgz",
-      "integrity": "sha512-9DGttpmPvIxBb/2uwpVo3dqJ+O6RooAFOS+lB+xDqoE2PVCE8nfoHMdZLpfCQRLwvohzXISPZcgxt80xLfsuwg==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.27.0.tgz",
+      "integrity": "sha512-2ncevenBqXI6qRMukPlXwHKHchC7RyMuu4xv5JBXRfOGVcTy1mXCD12qrp7Jsoxll1EV3+9sE4GugBVRjT2jFA==",
       "dev": true,
       "dependencies": {
-        "@babel/code-frame": "^7.25.9",
-        "@babel/parser": "^7.25.9",
-        "@babel/types": "^7.25.9"
+        "@babel/code-frame": "^7.26.2",
+        "@babel/parser": "^7.27.0",
+        "@babel/types": "^7.27.0"
       },
       "engines": {
         "node": ">=6.9.0"
       }
     },
     "node_modules/@babel/traverse": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.26.5.tgz",
-      "integrity": "sha512-rkOSPOw+AXbgtwUga3U4u8RpoK9FEFWBNAlTpcnkLFjL5CT+oyHNuUUC/xx6XefEJ16r38r8Bc/lfp6rYuHeJQ==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.27.0.tgz",
+      "integrity": "sha512-19lYZFzYVQkkHkl4Cy4WrAVcqBkgvV2YM2TU3xG6DIwO7O3ecbDPfW3yM3bjAGcqcQHi+CCtjMR3dIEHxsd6bA==",
       "dev": true,
       "dependencies": {
         "@babel/code-frame": "^7.26.2",
-        "@babel/generator": "^7.26.5",
-        "@babel/parser": "^7.26.5",
-        "@babel/template": "^7.25.9",
-        "@babel/types": "^7.26.5",
+        "@babel/generator": "^7.27.0",
+        "@babel/parser": "^7.27.0",
+        "@babel/template": "^7.27.0",
+        "@babel/types": "^7.27.0",
         "debug": "^4.3.1",
         "globals": "^11.1.0"
       },
@@ -3072,13 +2928,13 @@
       }
     },
     "node_modules/@babel/traverse/node_modules/@babel/generator": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.5.tgz",
-      "integrity": "sha512-2caSP6fN9I7HOe6nqhtft7V4g7/V/gfDsC3Ag4W7kEzzvRGKqiv0pu0HogPiZ3KaVSoNDhUws6IJjDjpfmYIXw==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.27.0.tgz",
+      "integrity": "sha512-VybsKvpiN1gU1sdMZIp7FcqphVVKEwcuj02x73uvcHE0PTihx1nlBcowYWhDwjpoAXRv43+gDzyggGnn1XZhVw==",
       "dev": true,
       "dependencies": {
-        "@babel/parser": "^7.26.5",
-        "@babel/types": "^7.26.5",
+        "@babel/parser": "^7.27.0",
+        "@babel/types": "^7.27.0",
         "@jridgewell/gen-mapping": "^0.3.5",
         "@jridgewell/trace-mapping": "^0.3.25",
         "jsesc": "^3.0.2"
@@ -3087,22 +2943,10 @@
         "node": ">=6.9.0"
       }
     },
-    "node_modules/@babel/traverse/node_modules/jsesc": {
-      "version": "3.1.0",
-      "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz",
-      "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==",
-      "dev": true,
-      "bin": {
-        "jsesc": "bin/jsesc"
-      },
-      "engines": {
-        "node": ">=6"
-      }
-    },
     "node_modules/@babel/types": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.26.5.tgz",
-      "integrity": "sha512-L6mZmwFDK6Cjh1nRCLXpa6no13ZIioJDz7mdkzHv399pThrTa/k0nUlNaenOeh2kWu/iaOQYElEpKPUswUa9Vg==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.27.0.tgz",
+      "integrity": "sha512-H45s8fVLYjbhFH62dIJ3WtmJ6RSPt/3DRO0ZcT2SUiYiQyz3BLVb9ADEnLl91m74aQPS3AzzeajZHYOalWe3bg==",
       "dev": true,
       "dependencies": {
         "@babel/helper-string-parser": "^7.25.9",
@@ -3519,9 +3363,9 @@
       }
     },
     "node_modules/@formio/bootstrap": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/@formio/bootstrap/-/bootstrap-3.0.0.tgz",
-      "integrity": "sha512-9a2JMY/qU/UUQ3BvlxrZfAjy/v5unwkXXBdy98+MiUbmQVaLi8ITIsA/YeYkRKFQW8V6BSbOoTlJhmVvxdvPnA=="
+      "version": "3.0.2-rc.1",
+      "resolved": "https://registry.npmjs.org/@formio/bootstrap/-/bootstrap-3.0.2-rc.1.tgz",
+      "integrity": "sha512-CfwnU04l8yMc0kr1j2Y7mj193Z5BfqoNiCGBsTz1bDIr/tnaQkfEOZ21zJ15KVpCXVGc6SjW7QQ1JY8UVsE0lQ=="
     },
     "node_modules/@formio/bootstrap3": {
       "version": "2.12.4-rc.1",
@@ -3543,9 +3387,9 @@
       }
     },
     "node_modules/@formio/core": {
-      "version": "2.3.0",
-      "resolved": "https://registry.npmjs.org/@formio/core/-/core-2.3.0.tgz",
-      "integrity": "sha512-jAlNm0vaSZQ9RSxt79PqeHdXYv/1i+zNfasVWbH1xRJSicJK0JcdodrBaDw8kKnEh0UmflW6RyIiaMyDbww4Ug==",
+      "version": "2.3.3",
+      "resolved": "https://registry.npmjs.org/@formio/core/-/core-2.3.3.tgz",
+      "integrity": "sha512-Tgv5FEwEf9xQtl/cqviaWyBCFcwGCb1pVXwTjIH7KxtWMwsyXtbxGotjfFyZY9unOw6Snk2ik/sln80yQe5y9A==",
       "dependencies": {
         "@types/json-logic-js": "^2.0.7",
         "browser-cookies": "^1.2.0",
@@ -3567,14 +3411,14 @@
       "integrity": "sha512-GWkBvjiSZK87ELrYOSESUYeVIc9mvLLf/nXalMOS5dYrgZq9o5OVkbZAVM06CVxYsCwH9BDZFPlQTlPA1j4ahA=="
     },
     "node_modules/@formio/js": {
-      "version": "5.0.0",
-      "resolved": "https://registry.npmjs.org/@formio/js/-/js-5.0.0.tgz",
-      "integrity": "sha512-Ly3f7q2wo5oFjlECKFtkIMy+Ah9HyAkf6ob70OrF/6MooSPF3hEu9euXouEWOoNdI+Tokr690/GdM2sDZtYzww==",
+      "version": "5.0.2",
+      "resolved": "https://registry.npmjs.org/@formio/js/-/js-5.0.2.tgz",
+      "integrity": "sha512-zAuCUuxBPCJ7Nmt8+xPE5XyLkVg550a//I9ke8bhI7EGlRkN6xF1Ve7Nomsi8ruohiw2BVcMH+5SS3LXWUm0uQ==",
       "dependencies": {
-        "@formio/bootstrap": "3.0.0",
+        "@formio/bootstrap": "3.0.2-rc.1",
         "@formio/choices.js": "^10.2.1",
-        "@formio/core": "2.3.0",
-        "@formio/text-mask-addons": "^3.8.0-formio.3",
+        "@formio/core": "2.3.3",
+        "@formio/text-mask-addons": "3.8.0-formio.4",
         "@formio/vanilla-text-mask": "^5.1.1-formio.1",
         "abortcontroller-polyfill": "^1.7.5",
         "autocompleter": "^8.0.4",
@@ -3614,9 +3458,9 @@
       "integrity": "sha512-q334YswwucSBphN5djVkEt3beVhHotrCtPGNIXmyilw9UnXV9Cb+gNAZ2yhZSfiBSzP6rxHLLT2gpr57xgbcwQ=="
     },
     "node_modules/@formio/js/node_modules/bootstrap": {
-      "version": "5.3.3",
-      "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.3.tgz",
-      "integrity": "sha512-8HLCdWgyoMguSO9o+aH+iuZ+aht+mzW0u3HIMzVu7Srrpv7EBBxTnrFlSCskwdY1+EOFQSm7uMJhNQHkdPcmjg==",
+      "version": "5.3.5",
+      "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.5.tgz",
+      "integrity": "sha512-ct1CHKtiobRimyGzmsSldEtM03E8fcEX4Tb3dGXz1V8faRwM50+vfHwTzOxB3IlKO7m+9vTH3s/3C6T2EAPeTA==",
       "funding": [
         {
           "type": "github",
@@ -3853,6 +3697,12 @@
       "resolved": "https://registry.npmjs.org/@juggle/resize-observer/-/resize-observer-3.4.0.tgz",
       "integrity": "sha512-dfLbk+PwWvFzSxwk3n5ySL0hfBog779o8h68wK/7/APo/7cgyWp5jcXockbxdk5kFRkbeXWm4Fbi9FrdN381sA=="
     },
+    "node_modules/@kurkle/color": {
+      "version": "0.3.4",
+      "resolved": "https://registry.npmjs.org/@kurkle/color/-/color-0.3.4.tgz",
+      "integrity": "sha512-M5UknZPHRu3DEDWoipU6sE8PdkZ6Z/S+v4dD+Ke8IaNlpdSQah50lz1KtcFBa2vsdOnwbbnxJwVM4wty6udA5w==",
+      "license": "MIT"
+    },
     "node_modules/@leichtgewicht/ip-codec": {
       "version": "2.0.5",
       "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.5.tgz",
@@ -3872,9 +3722,9 @@
       }
     },
     "node_modules/@ngtools/webpack": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@ngtools/webpack/-/webpack-17.3.11.tgz",
-      "integrity": "sha512-SfTCbplt4y6ak5cf2IfqdoVOsnoNdh/j6Vu+wb8WWABKwZ5yfr2S/Gk6ithSKcdIZhAF8DNBOoyk1EJuf8Xkfg==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@ngtools/webpack/-/webpack-17.3.16.tgz",
+      "integrity": "sha512-Wxtiut1o9rj3+HumyXoYWg4iCuPDEt4nf1Y9bRCo3y5evEKp0ZTO7IFPpZLaZ0JGGrpROiQErjvHdDQBOuXwWQ==",
       "dev": true,
       "engines": {
         "node": "^18.13.0 || >=20.9.0",
@@ -3900,16 +3750,15 @@
       }
     },
     "node_modules/@ngx-translate/http-loader": {
-      "version": "7.0.0",
-      "resolved": "https://registry.npmjs.org/@ngx-translate/http-loader/-/http-loader-7.0.0.tgz",
-      "integrity": "sha512-j+NpXXlcGVdyUNyY/qsJrqqeAdJdizCd+GKh3usXExSqy1aE9866jlAIL+xrfDU4w+LiMoma5pgE4emvFebZmA==",
+      "version": "16.0.1",
+      "resolved": "https://registry.npmjs.org/@ngx-translate/http-loader/-/http-loader-16.0.1.tgz",
+      "integrity": "sha512-xJEOUpvs6Zfc8G4cmQmegFOEpfYSoplTHHoisPNrATXjRBjpaKsBaPOXlZsuFUW2XV00s16gIyI4+9z1XkO5bw==",
       "dependencies": {
         "tslib": "^2.3.0"
       },
       "peerDependencies": {
-        "@angular/common": ">=13.0.0",
-        "@ngx-translate/core": ">=14.0.0",
-        "rxjs": "^6.5.3 || ^7.4.0"
+        "@angular/common": ">=16",
+        "@angular/core": ">=16"
       }
     },
     "node_modules/@nodelib/fs.scandir": {
@@ -4506,13 +4355,13 @@
       ]
     },
     "node_modules/@schematics/angular": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@schematics/angular/-/angular-17.3.11.tgz",
-      "integrity": "sha512-tvJpTgYC+hCnTyLszYRUZVyNTpPd+C44gh5CPTcG3qkqStzXQwynQAf6X/DjtwXbUiPQF0XfF0+0R489GpdZPA==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@schematics/angular/-/angular-17.3.16.tgz",
+      "integrity": "sha512-Ts/cAZmxlIL+AOLbmBylCMjXdHeqWZE2IIYmP5334tQNERSharOlKbLIz5PeESmBDGpH9KRa0wSMK5KXI5ixnQ==",
       "dev": true,
       "dependencies": {
-        "@angular-devkit/core": "17.3.11",
-        "@angular-devkit/schematics": "17.3.11",
+        "@angular-devkit/core": "17.3.16",
+        "@angular-devkit/schematics": "17.3.16",
         "jsonc-parser": "3.2.1"
       },
       "engines": {
@@ -4797,9 +4646,9 @@
       }
     },
     "node_modules/@types/jasmine": {
-      "version": "3.6.11",
-      "resolved": "https://registry.npmjs.org/@types/jasmine/-/jasmine-3.6.11.tgz",
-      "integrity": "sha512-S6pvzQDvMZHrkBz2Mcn/8Du7cpr76PlRJBAoHnSDNbulULsH5dp0Gns+WRyNX5LHejz/ljxK4/vIHK/caHt6SQ==",
+      "version": "5.1.7",
+      "resolved": "https://registry.npmjs.org/@types/jasmine/-/jasmine-5.1.7.tgz",
+      "integrity": "sha512-DVOfk9FaClQfNFpSfaML15jjB5cjffDMvjtph525sroR5BEAW2uKnTOYUTqTFuZFjNvH0T5XMIydvIctnUKufw==",
       "dev": true
     },
     "node_modules/@types/json-logic-js": {
@@ -4864,9 +4713,9 @@
       "dev": true
     },
     "node_modules/@types/semver": {
-      "version": "7.3.8",
-      "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.3.8.tgz",
-      "integrity": "sha512-D/2EJvAlCEtYFEYmmlGwbGXuK886HzyCc3nZX/tkFTQdEU8jZDAgiv08P162yB17y4ZXZoq7yFAnW4GDBb9Now=="
+      "version": "7.7.0",
+      "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.7.0.tgz",
+      "integrity": "sha512-k107IF4+Xr7UHjwDc7Cfd6PRQfbdkiRabXGRjo07b4WyPahFBZCZ1sE+BNxYIJPPg73UkfOsVOLwqVc/6ETrIA=="
     },
     "node_modules/@types/send": {
       "version": "0.17.4",
@@ -4943,9 +4792,9 @@
       }
     },
     "node_modules/@types/zxcvbn": {
-      "version": "4.4.1",
-      "resolved": "https://registry.npmjs.org/@types/zxcvbn/-/zxcvbn-4.4.1.tgz",
-      "integrity": "sha512-3NoqvZC2W5gAC5DZbTpCeJ251vGQmgcWIHQJGq2J240HY6ErQ9aWKkwfoKJlHLx+A83WPNTZ9+3cd2ILxbvr1w=="
+      "version": "4.4.5",
+      "resolved": "https://registry.npmjs.org/@types/zxcvbn/-/zxcvbn-4.4.5.tgz",
+      "integrity": "sha512-FZJgC5Bxuqg7Rhsm/bx6gAruHHhDQ55r+s0JhDh8CQ16fD7NsJJ+p8YMMQDhSQoIrSmjpqqYWA96oQVMNkjRyA=="
     },
     "node_modules/@webassemblyjs/ast": {
       "version": "1.14.1",
@@ -5125,17 +4974,17 @@
       "dev": true
     },
     "node_modules/@zxcvbn-ts/core": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/core/-/core-3.0.0.tgz",
-      "integrity": "sha512-AuuYc66+5csSLd/mJ1CXuTUsjLdYw4X0zh8WvDCLztTOye0b+HrKCu8WzAEmq6Ja1u+cSbCNrKLW7m4ZCeg0FA==",
+      "version": "3.0.4",
+      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/core/-/core-3.0.4.tgz",
+      "integrity": "sha512-aQeiT0F09FuJaAqNrxynlAwZ2mW/1MdXakKWNmGM1Qp/VaY6CnB/GfnMS2T8gB2231Esp1/maCWd8vTG4OuShw==",
       "dependencies": {
         "fastest-levenshtein": "1.0.16"
       }
     },
     "node_modules/@zxcvbn-ts/language-en": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/language-en/-/language-en-3.0.0.tgz",
-      "integrity": "sha512-JJ0H3ovVIO4EEpYXk5qq6NbxyZ8b3/qkpwEFIOu0m8bb54vXtRy2EbdfzUm0XKdtw9gfx15MaHAn0pWv0hTzYg=="
+      "version": "3.0.2",
+      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/language-en/-/language-en-3.0.2.tgz",
+      "integrity": "sha512-Zp+zL+I6Un2Bj0tRXNs6VUBq3Djt+hwTwUz4dkt2qgsQz47U0/XthZ4ULrT/RxjwJRl5LwiaKOOZeOtmixHnjg=="
     },
     "node_modules/abbrev": {
       "version": "2.0.0",
@@ -5244,14 +5093,14 @@
       }
     },
     "node_modules/ajv": {
-      "version": "6.12.6",
-      "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
-      "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+      "version": "8.17.1",
+      "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz",
+      "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==",
       "dependencies": {
-        "fast-deep-equal": "^3.1.1",
-        "fast-json-stable-stringify": "^2.0.0",
-        "json-schema-traverse": "^0.4.1",
-        "uri-js": "^4.2.2"
+        "fast-deep-equal": "^3.1.3",
+        "fast-uri": "^3.0.1",
+        "json-schema-traverse": "^1.0.0",
+        "require-from-string": "^2.0.2"
       },
       "funding": {
         "type": "github",
@@ -5275,28 +5124,6 @@
         }
       }
     },
-    "node_modules/ajv-formats/node_modules/ajv": {
-      "version": "8.12.0",
-      "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz",
-      "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==",
-      "dev": true,
-      "dependencies": {
-        "fast-deep-equal": "^3.1.1",
-        "json-schema-traverse": "^1.0.0",
-        "require-from-string": "^2.0.2",
-        "uri-js": "^4.2.2"
-      },
-      "funding": {
-        "type": "github",
-        "url": "https://github.com/sponsors/epoberezkin"
-      }
-    },
-    "node_modules/ajv-formats/node_modules/json-schema-traverse": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
-      "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
-      "dev": true
-    },
     "node_modules/ajv-keywords": {
       "version": "3.5.2",
       "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.5.2.tgz",
@@ -5622,31 +5449,6 @@
         "node": ">=8"
       }
     },
-    "node_modules/babel-plugin-istanbul/node_modules/istanbul-lib-instrument": {
-      "version": "5.2.1",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-5.2.1.tgz",
-      "integrity": "sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==",
-      "dev": true,
-      "dependencies": {
-        "@babel/core": "^7.12.3",
-        "@babel/parser": "^7.14.7",
-        "@istanbuljs/schema": "^0.1.2",
-        "istanbul-lib-coverage": "^3.2.0",
-        "semver": "^6.3.0"
-      },
-      "engines": {
-        "node": ">=8"
-      }
-    },
-    "node_modules/babel-plugin-istanbul/node_modules/semver": {
-      "version": "6.3.1",
-      "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
-      "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==",
-      "dev": true,
-      "bin": {
-        "semver": "bin/semver.js"
-      }
-    },
     "node_modules/babel-plugin-polyfill-corejs2": {
       "version": "0.4.12",
       "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs2/-/babel-plugin-polyfill-corejs2-0.4.12.tgz",
@@ -5671,57 +5473,25 @@
       }
     },
     "node_modules/babel-plugin-polyfill-corejs3": {
-      "version": "0.9.0",
-      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.9.0.tgz",
-      "integrity": "sha512-7nZPG1uzK2Ymhy/NbaOWTg3uibM2BmGASS4vHS4szRZAIR8R6GwA/xAujpdrXU5iyklrimWnLWU+BLF9suPTqg==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-define-polyfill-provider": "^0.5.0",
-        "core-js-compat": "^3.34.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0"
-      }
-    },
-    "node_modules/babel-plugin-polyfill-corejs3/node_modules/@babel/helper-define-polyfill-provider": {
-      "version": "0.5.0",
-      "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.5.0.tgz",
-      "integrity": "sha512-NovQquuQLAQ5HuyjCz7WQP9MjRj7dx++yspwiyUiGl9ZyadHRSql1HZh5ogRd8W8w6YM6EQ/NTB8rgjLt5W65Q==",
+      "version": "0.11.1",
+      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.11.1.tgz",
+      "integrity": "sha512-yGCqvBT4rwMczo28xkH/noxJ6MZ4nJfkVYdoDaC/utLtWrXxv27HVrzAeSbqR8SxDsp46n0YF47EbHoixy6rXQ==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-compilation-targets": "^7.22.6",
-        "@babel/helper-plugin-utils": "^7.22.5",
-        "debug": "^4.1.1",
-        "lodash.debounce": "^4.0.8",
-        "resolve": "^1.14.2"
+        "@babel/helper-define-polyfill-provider": "^0.6.3",
+        "core-js-compat": "^3.40.0"
       },
       "peerDependencies": {
         "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0"
       }
     },
     "node_modules/babel-plugin-polyfill-regenerator": {
-      "version": "0.5.5",
-      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.5.5.tgz",
-      "integrity": "sha512-OJGYZlhLqBh2DDHeqAxWB1XIvr49CxiJ2gIt61/PU55CQK4Z58OzMqjDe1zwQdQk+rBYsRc+1rJmdajM3gimHg==",
-      "dev": true,
-      "dependencies": {
-        "@babel/helper-define-polyfill-provider": "^0.5.0"
-      },
-      "peerDependencies": {
-        "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0"
-      }
-    },
-    "node_modules/babel-plugin-polyfill-regenerator/node_modules/@babel/helper-define-polyfill-provider": {
-      "version": "0.5.0",
-      "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.5.0.tgz",
-      "integrity": "sha512-NovQquuQLAQ5HuyjCz7WQP9MjRj7dx++yspwiyUiGl9ZyadHRSql1HZh5ogRd8W8w6YM6EQ/NTB8rgjLt5W65Q==",
+      "version": "0.6.4",
+      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.6.4.tgz",
+      "integrity": "sha512-7gD3pRadPrbjhjLyxebmx/WrFYcuSjZ0XbdUujQMZ/fcE9oeewk2U/7PCvez84UeuK3oSjmPZ0Ch0dlupQvGzw==",
       "dev": true,
       "dependencies": {
-        "@babel/helper-compilation-targets": "^7.22.6",
-        "@babel/helper-plugin-utils": "^7.22.5",
-        "debug": "^4.1.1",
-        "lodash.debounce": "^4.0.8",
-        "resolve": "^1.14.2"
+        "@babel/helper-define-polyfill-provider": "^0.6.4"
       },
       "peerDependencies": {
         "@babel/core": "^7.4.0 || ^8.0.0-0 <8.0.0"
@@ -6271,6 +6041,17 @@
       "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==",
       "dev": true
     },
+    "node_modules/chart.js": {
+      "version": "4.4.9",
+      "resolved": "https://registry.npmjs.org/chart.js/-/chart.js-4.4.9.tgz",
+      "integrity": "sha512-EyZ9wWKgpAU0fLJ43YAEIF8sr5F2W3LqbS40ZJyHIner2lY14ufqv2VMp69MAiZ2rpwxEUxEhIH/0U3xyRynxg==",
+      "dependencies": {
+        "@kurkle/color": "^0.3.0"
+      },
+      "engines": {
+        "pnpm": ">=8"
+      }
+    },
     "node_modules/chokidar": {
       "version": "3.5.3",
       "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz",
@@ -6823,12 +6604,12 @@
       }
     },
     "node_modules/core-js-compat": {
-      "version": "3.40.0",
-      "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.40.0.tgz",
-      "integrity": "sha512-0XEDpr5y5mijvw8Lbc6E5AkjrHfp7eEoPlu36SWeAbcL8fn1G1ANe8DBlo2XoNN89oVpxWwOjYIPVzR4ZvsKCQ==",
+      "version": "3.41.0",
+      "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.41.0.tgz",
+      "integrity": "sha512-RFsU9LySVue9RTwdDVX/T0e2Y6jRYWXERKElIjpuEOEnxaXffI0X7RUwVzfYLfzuLXSNJDYoRYUAmRUcyln20A==",
       "dev": true,
       "dependencies": {
-        "browserslist": "^4.24.3"
+        "browserslist": "^4.24.4"
       },
       "funding": {
         "type": "opencollective",
@@ -8228,13 +8009,13 @@
     "node_modules/fast-json-stable-stringify": {
       "version": "2.1.0",
       "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz",
-      "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw=="
+      "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==",
+      "dev": true
     },
     "node_modules/fast-uri": {
       "version": "3.0.5",
       "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.5.tgz",
       "integrity": "sha512-5JnBCWpFlMo0a3ciDy/JckMzzv1U9coZrIhedq+HXxxUfDTAiS0LA8OKVao4G9BxmCVck/jtA5r3KAtRWEyD8Q==",
-      "dev": true,
       "funding": [
         {
           "type": "github",
@@ -8816,6 +8597,28 @@
         "node": ">=6"
       }
     },
+    "node_modules/har-validator/node_modules/ajv": {
+      "version": "6.12.6",
+      "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+      "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+      "dev": true,
+      "dependencies": {
+        "fast-deep-equal": "^3.1.1",
+        "fast-json-stable-stringify": "^2.0.0",
+        "json-schema-traverse": "^0.4.1",
+        "uri-js": "^4.2.2"
+      },
+      "funding": {
+        "type": "github",
+        "url": "https://github.com/sponsors/epoberezkin"
+      }
+    },
+    "node_modules/har-validator/node_modules/json-schema-traverse": {
+      "version": "0.4.1",
+      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
+      "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==",
+      "dev": true
+    },
     "node_modules/has-ansi": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz",
@@ -9725,14 +9528,15 @@
       }
     },
     "node_modules/istanbul-lib-instrument": {
-      "version": "4.0.3",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-4.0.3.tgz",
-      "integrity": "sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==",
+      "version": "5.2.1",
+      "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-5.2.1.tgz",
+      "integrity": "sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==",
       "dev": true,
       "dependencies": {
-        "@babel/core": "^7.7.5",
+        "@babel/core": "^7.12.3",
+        "@babel/parser": "^7.14.7",
         "@istanbuljs/schema": "^0.1.2",
-        "istanbul-lib-coverage": "^3.0.0",
+        "istanbul-lib-coverage": "^3.2.0",
         "semver": "^6.3.0"
       },
       "engines": {
@@ -9784,9 +9588,9 @@
       }
     },
     "node_modules/istanbul-lib-source-maps": {
-      "version": "4.0.0",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-4.0.0.tgz",
-      "integrity": "sha512-c16LpFRkR8vQXyHZ5nLpY35JZtzj1PQY1iZmesUbf1FZHbIupcWfjgOXBY9YHkLEQ6puz1u4Dgj6qmU/DisrZg==",
+      "version": "4.0.1",
+      "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-4.0.1.tgz",
+      "integrity": "sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==",
       "dev": true,
       "dependencies": {
         "debug": "^4.1.1",
@@ -9794,7 +9598,7 @@
         "source-map": "^0.6.1"
       },
       "engines": {
-        "node": ">=8"
+        "node": ">=10"
       }
     },
     "node_modules/istanbul-lib-source-maps/node_modules/source-map": {
@@ -9807,9 +9611,9 @@
       }
     },
     "node_modules/istanbul-reports": {
-      "version": "3.0.2",
-      "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.0.2.tgz",
-      "integrity": "sha512-9tZvz7AiR3PEDNGiV9vIouQ/EAcqMXFmkcA1CDFTwOB98OZVDL0PH9glHotf5Ugp6GCOTypfzGWI/OqjWNCRUw==",
+      "version": "3.1.7",
+      "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.1.7.tgz",
+      "integrity": "sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g==",
       "dev": true,
       "dependencies": {
         "html-escaper": "^2.0.0",
@@ -9849,9 +9653,9 @@
       }
     },
     "node_modules/jasmine-core": {
-      "version": "4.6.0",
-      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.6.0.tgz",
-      "integrity": "sha512-O236+gd0ZXS8YAjFx8xKaJ94/erqUliEkJTDedyE7iHvv4ZVqi+q+8acJxu05/WJDKm512EUNn809In37nWlAQ==",
+      "version": "4.6.1",
+      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.6.1.tgz",
+      "integrity": "sha512-VYz/BjjmC3klLJlLwA4Kw8ytk0zDSmbbDLNs794VnWmkcCB7I9aAL/D48VNQtmITyPvea2C3jdUMfc3kAoy0PQ==",
       "dev": true
     },
     "node_modules/jasmine-spec-reporter": {
@@ -9938,9 +9742,9 @@
       }
     },
     "node_modules/jquery": {
-      "version": "3.6.0",
-      "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.6.0.tgz",
-      "integrity": "sha512-JVzAR/AjBvVt2BmYhxRCSYysDsPcssdmTFnzyLEts9qNwmjmu4JTAMYubEfwVOSwpQ1I1sKKFcxhZCI2buerfw=="
+      "version": "3.7.1",
+      "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.7.1.tgz",
+      "integrity": "sha512-m4avr8yL8kmFN8psrbFFFmB/If14iN5o9nw/NgnnM+kybDJpRsAynV2BsfpTYrTRysYUdADVD7CkUUizgkpLfg=="
     },
     "node_modules/js-tokens": {
       "version": "4.0.0",
@@ -9968,15 +9772,15 @@
       "dev": true
     },
     "node_modules/jsesc": {
-      "version": "2.5.2",
-      "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz",
-      "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==",
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz",
+      "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==",
       "dev": true,
       "bin": {
         "jsesc": "bin/jsesc"
       },
       "engines": {
-        "node": ">=4"
+        "node": ">=6"
       }
     },
     "node_modules/json-logic-js": {
@@ -9997,9 +9801,9 @@
       "dev": true
     },
     "node_modules/json-schema-traverse": {
-      "version": "0.4.1",
-      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
-      "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg=="
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
+      "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug=="
     },
     "node_modules/json-stringify-safe": {
       "version": "5.0.1",
@@ -10105,9 +9909,9 @@
       "integrity": "sha512-UfpWE/VZn0iP50d8cz9NrZLM9lSWhcJ+0Gt/nm4by88UL+J1SiKN8/5dkjMmbEzwL2CAe+67GsegCbIKtbp75A=="
     },
     "node_modules/karma": {
-      "version": "6.4.1",
-      "resolved": "https://registry.npmjs.org/karma/-/karma-6.4.1.tgz",
-      "integrity": "sha512-Cj57NKOskK7wtFWSlMvZf459iX+kpYIPXmkNUzP2WAFcA7nhr/ALn5R7sw3w+1udFDcpMx/tuB8d5amgm3ijaA==",
+      "version": "6.4.4",
+      "resolved": "https://registry.npmjs.org/karma/-/karma-6.4.4.tgz",
+      "integrity": "sha512-LrtUxbdvt1gOpo3gxG+VAJlJAEMhbWlM4YrFQgql98FwF7+K8K12LYO4hnDdUkNjeztYrOXEMqgTajSWgmtI/w==",
       "dev": true,
       "dependencies": {
         "@colors/colors": "1.5.0",
@@ -10129,7 +9933,7 @@
         "qjobs": "^1.2.0",
         "range-parser": "^1.2.1",
         "rimraf": "^3.0.2",
-        "socket.io": "^4.4.1",
+        "socket.io": "^4.7.2",
         "source-map": "^0.6.1",
         "tmp": "^0.2.1",
         "ua-parser-js": "^0.7.30",
@@ -10143,9 +9947,9 @@
       }
     },
     "node_modules/karma-chrome-launcher": {
-      "version": "3.1.0",
-      "resolved": "https://registry.npmjs.org/karma-chrome-launcher/-/karma-chrome-launcher-3.1.0.tgz",
-      "integrity": "sha512-3dPs/n7vgz1rxxtynpzZTvb9y/GIaW8xjAwcIGttLbycqoFtI7yo1NGnQi6oFTherRE+GIhCAHZC4vEqWGhNvg==",
+      "version": "3.2.0",
+      "resolved": "https://registry.npmjs.org/karma-chrome-launcher/-/karma-chrome-launcher-3.2.0.tgz",
+      "integrity": "sha512-rE9RkUPI7I9mAxByQWkGJFXfFD6lE4gC5nPuZdobf/QdTEJI6EU4yIay/cfU/xV4ZxlM5JiTv7zWYgA64NpS5Q==",
       "dev": true,
       "dependencies": {
         "which": "^1.2.1"
@@ -10167,16 +9971,16 @@
       }
     },
     "node_modules/karma-coverage": {
-      "version": "2.0.3",
-      "resolved": "https://registry.npmjs.org/karma-coverage/-/karma-coverage-2.0.3.tgz",
-      "integrity": "sha512-atDvLQqvPcLxhED0cmXYdsPMCQuh6Asa9FMZW1bhNqlVEhJoB9qyZ2BY1gu7D/rr5GLGb5QzYO4siQskxaWP/g==",
+      "version": "2.2.1",
+      "resolved": "https://registry.npmjs.org/karma-coverage/-/karma-coverage-2.2.1.tgz",
+      "integrity": "sha512-yj7hbequkQP2qOSb20GuNSIyE//PgJWHwC2IydLE6XRtsnaflv+/OSGNssPjobYUlhVVagy99TQpqUt3vAUG7A==",
       "dev": true,
       "dependencies": {
-        "istanbul-lib-coverage": "^3.0.0",
-        "istanbul-lib-instrument": "^4.0.1",
+        "istanbul-lib-coverage": "^3.2.0",
+        "istanbul-lib-instrument": "^5.1.0",
         "istanbul-lib-report": "^3.0.0",
-        "istanbul-lib-source-maps": "^4.0.0",
-        "istanbul-reports": "^3.0.0",
+        "istanbul-lib-source-maps": "^4.0.1",
+        "istanbul-reports": "^3.0.5",
         "minimatch": "^3.0.4"
       },
       "engines": {
@@ -10184,9 +9988,9 @@
       }
     },
     "node_modules/karma-jasmine": {
-      "version": "4.0.1",
-      "resolved": "https://registry.npmjs.org/karma-jasmine/-/karma-jasmine-4.0.1.tgz",
-      "integrity": "sha512-h8XDAhTiZjJKzfkoO1laMH+zfNlra+dEQHUAjpn5JV1zCPtOIVWGQjLBrqhnzQa/hrU2XrZwSyBa6XjEBzfXzw==",
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/karma-jasmine/-/karma-jasmine-4.0.2.tgz",
+      "integrity": "sha512-ggi84RMNQffSDmWSyyt4zxzh2CQGwsxvYYsprgyR1j8ikzIduEdOlcLvXjZGwXG/0j41KUXOWsUCBfbEHPWP9g==",
       "dev": true,
       "dependencies": {
         "jasmine-core": "^3.6.0"
@@ -10252,51 +10056,19 @@
     },
     "node_modules/karma-webpack/node_modules/minimatch": {
       "version": "9.0.5",
-      "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz",
-      "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==",
-      "dev": true,
-      "dependencies": {
-        "brace-expansion": "^2.0.1"
-      },
-      "engines": {
-        "node": ">=16 || 14 >=14.17"
-      },
-      "funding": {
-        "url": "https://github.com/sponsors/isaacs"
-      }
-    },
-    "node_modules/karma/node_modules/glob": {
-      "version": "7.2.3",
-      "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz",
-      "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==",
+      "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-9.0.5.tgz",
+      "integrity": "sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==",
       "dev": true,
       "dependencies": {
-        "fs.realpath": "^1.0.0",
-        "inflight": "^1.0.4",
-        "inherits": "2",
-        "minimatch": "^3.1.1",
-        "once": "^1.3.0",
-        "path-is-absolute": "^1.0.0"
+        "brace-expansion": "^2.0.1"
       },
       "engines": {
-        "node": "*"
+        "node": ">=16 || 14 >=14.17"
       },
       "funding": {
         "url": "https://github.com/sponsors/isaacs"
       }
     },
-    "node_modules/karma/node_modules/glob/node_modules/minimatch": {
-      "version": "3.1.2",
-      "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz",
-      "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==",
-      "dev": true,
-      "dependencies": {
-        "brace-expansion": "^1.1.7"
-      },
-      "engines": {
-        "node": "*"
-      }
-    },
     "node_modules/karma/node_modules/mkdirp": {
       "version": "0.5.6",
       "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz",
@@ -10319,15 +10091,12 @@
       }
     },
     "node_modules/karma/node_modules/tmp": {
-      "version": "0.2.1",
-      "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz",
-      "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==",
+      "version": "0.2.3",
+      "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.3.tgz",
+      "integrity": "sha512-nZD7m9iCPC5g0pYmcaxogYKggSfLsdxl8of3Q/oIbqCqLLIO9IAF0GWjX1z9NZRHPiXv8Wex4yDCaZsgEw0Y8w==",
       "dev": true,
-      "dependencies": {
-        "rimraf": "^3.0.0"
-      },
       "engines": {
-        "node": ">=8.17.0"
+        "node": ">=14.14"
       }
     },
     "node_modules/kind-of": {
@@ -10655,6 +10424,7 @@
       "version": "6.0.0",
       "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz",
       "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==",
+      "dev": true,
       "dependencies": {
         "yallist": "^4.0.0"
       },
@@ -12418,9 +12188,9 @@
       "integrity": "sha512-zaOq3YvcOYytbAmKv3zYc+0VNS9Wg5d37dfxZnveKBFPr7vEIwfV5ydrpiouTft8MVW6qNjfkaQphHSnvgQbpQ=="
     },
     "node_modules/primeicons": {
-      "version": "6.0.1",
-      "resolved": "https://registry.npmjs.org/primeicons/-/primeicons-6.0.1.tgz",
-      "integrity": "sha512-KDeO94CbWI4pKsPnYpA1FPjo79EsY9I+M8ywoPBSf9XMXoe/0crjbUK7jcQEDHuc0ZMRIZsxH3TYLv4TUtHmAA=="
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/primeicons/-/primeicons-7.0.0.tgz",
+      "integrity": "sha512-jK3Et9UzwzTsd6tzl2RmwrVY/b8raJ3QZLzoDACj+oTJ0oX7L9Hy+XnVwgo4QVKlKpnP/Ur13SXV/pVh4LzaDw=="
     },
     "node_modules/primeng": {
       "version": "17.18.15",
@@ -12776,6 +12546,7 @@
       "version": "2.3.1",
       "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz",
       "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==",
+      "dev": true,
       "engines": {
         "node": ">=6"
       }
@@ -13237,7 +13008,6 @@
       "version": "2.0.2",
       "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz",
       "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==",
-      "dev": true,
       "engines": {
         "node": ">=0.10.0"
       }
@@ -13449,9 +13219,9 @@
       }
     },
     "node_modules/rxjs": {
-      "version": "7.8.1",
-      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
-      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "version": "7.8.2",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.2.tgz",
+      "integrity": "sha512-dhKf903U/PQZY6boNNtAGdWbG85WAbjT/1xYoZIC7FAY0yWapOBQVsVrDl58W86//e1VpMNBtRV4MaXfdMySFA==",
       "dependencies": {
         "tslib": "^2.1.0"
       }
@@ -13596,22 +13366,6 @@
         "url": "https://opencollective.com/webpack"
       }
     },
-    "node_modules/schema-utils/node_modules/ajv": {
-      "version": "8.17.1",
-      "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz",
-      "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==",
-      "dev": true,
-      "dependencies": {
-        "fast-deep-equal": "^3.1.3",
-        "fast-uri": "^3.0.1",
-        "json-schema-traverse": "^1.0.0",
-        "require-from-string": "^2.0.2"
-      },
-      "funding": {
-        "type": "github",
-        "url": "https://github.com/sponsors/epoberezkin"
-      }
-    },
     "node_modules/schema-utils/node_modules/ajv-keywords": {
       "version": "5.1.0",
       "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz",
@@ -13624,12 +13378,6 @@
         "ajv": "^8.8.2"
       }
     },
-    "node_modules/schema-utils/node_modules/json-schema-traverse": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
-      "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
-      "dev": true
-    },
     "node_modules/select-hose": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/select-hose/-/select-hose-2.0.0.tgz",
@@ -13690,12 +13438,9 @@
       }
     },
     "node_modules/semver": {
-      "version": "7.5.4",
-      "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz",
-      "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==",
-      "dependencies": {
-        "lru-cache": "^6.0.0"
-      },
+      "version": "7.7.1",
+      "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.1.tgz",
+      "integrity": "sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA==",
       "bin": {
         "semver": "bin/semver.js"
       },
@@ -15088,19 +14833,10 @@
         "node": "*"
       }
     },
-    "node_modules/undici": {
-      "version": "6.11.1",
-      "resolved": "https://registry.npmjs.org/undici/-/undici-6.11.1.tgz",
-      "integrity": "sha512-KyhzaLJnV1qa3BSHdj4AZ2ndqI0QWPxYzaIOio0WzcEJB9gvuysprJSLtpvc2D9mhR9jPDUk7xlJlZbH2KR5iw==",
-      "dev": true,
-      "engines": {
-        "node": ">=18.0"
-      }
-    },
     "node_modules/undici-types": {
-      "version": "6.20.0",
-      "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.20.0.tgz",
-      "integrity": "sha512-Ny6QZ2Nju20vw1SRHe3d9jVu6gJ+4e3+MMpqu7pqE5HT6WsTSlce++GQmK5UXS8mzV8DSYHrQH+Xrf2jVcuKNg==",
+      "version": "6.21.0",
+      "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz",
+      "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==",
       "dev": true,
       "optional": true,
       "peer": true
@@ -15197,6 +14933,7 @@
       "version": "4.4.1",
       "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz",
       "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==",
+      "dev": true,
       "dependencies": {
         "punycode": "^2.1.0"
       }
@@ -15670,6 +15407,28 @@
         }
       }
     },
+    "node_modules/webpack/node_modules/ajv": {
+      "version": "6.12.6",
+      "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+      "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+      "dev": true,
+      "dependencies": {
+        "fast-deep-equal": "^3.1.1",
+        "fast-json-stable-stringify": "^2.0.0",
+        "json-schema-traverse": "^0.4.1",
+        "uri-js": "^4.2.2"
+      },
+      "funding": {
+        "type": "github",
+        "url": "https://github.com/sponsors/epoberezkin"
+      }
+    },
+    "node_modules/webpack/node_modules/json-schema-traverse": {
+      "version": "0.4.1",
+      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
+      "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==",
+      "dev": true
+    },
     "node_modules/webpack/node_modules/schema-utils": {
       "version": "3.3.0",
       "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz",
@@ -15900,7 +15659,8 @@
     "node_modules/yallist": {
       "version": "4.0.0",
       "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz",
-      "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A=="
+      "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==",
+      "dev": true
     },
     "node_modules/yargs": {
       "version": "16.2.0",
@@ -15991,36 +15751,47 @@
       }
     },
     "@angular-devkit/architect": {
-      "version": "0.1703.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/architect/-/architect-0.1703.11.tgz",
-      "integrity": "sha512-YNasVZk4rYdcM6M+KRH8PUBhVyJfqzUYLpO98GgRokW+taIDgifckSlmfDZzQRbw45qiwei1IKCLqcpC8nM5Tw==",
+      "version": "0.1703.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/architect/-/architect-0.1703.16.tgz",
+      "integrity": "sha512-wuqKu20ekgzzikUTZD28dS72F6vjniZuiQ7RgAYhykmsU0z0br2tksHQvjD/auzVArtgQir1+V9wp6BN4dSdNQ==",
       "dev": true,
       "requires": {
-        "@angular-devkit/core": "17.3.11",
+        "@angular-devkit/core": "17.3.16",
         "rxjs": "7.8.1"
+      },
+      "dependencies": {
+        "rxjs": {
+          "version": "7.8.1",
+          "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+          "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+          "dev": true,
+          "requires": {
+            "tslib": "^2.1.0"
+          }
+        }
       }
     },
     "@angular-devkit/build-angular": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/build-angular/-/build-angular-17.3.11.tgz",
-      "integrity": "sha512-lHX5V2dSts328yvo/9E2u9QMGcvJhbEKKDDp9dBecwvIG9s+4lTOJgi9DPUE7W+AtmPcmbbhwC2JRQ/SLQhAoA==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/build-angular/-/build-angular-17.3.16.tgz",
+      "integrity": "sha512-5JiR1NK3MOwzipAn4UmvJ8yQa6NaBtHBWbLrY0Ps6a21kHWn42C+dpvVdlXN/ZZSpEll/nzA+b77zA3kDrGlKw==",
       "dev": true,
       "requires": {
         "@ampproject/remapping": "2.3.0",
-        "@angular-devkit/architect": "0.1703.11",
-        "@angular-devkit/build-webpack": "0.1703.11",
-        "@angular-devkit/core": "17.3.11",
-        "@babel/core": "7.24.0",
-        "@babel/generator": "7.23.6",
-        "@babel/helper-annotate-as-pure": "7.22.5",
-        "@babel/helper-split-export-declaration": "7.22.6",
-        "@babel/plugin-transform-async-generator-functions": "7.23.9",
-        "@babel/plugin-transform-async-to-generator": "7.23.3",
-        "@babel/plugin-transform-runtime": "7.24.0",
-        "@babel/preset-env": "7.24.0",
-        "@babel/runtime": "7.24.0",
+        "@angular-devkit/architect": "0.1703.16",
+        "@angular-devkit/build-webpack": "0.1703.16",
+        "@angular-devkit/core": "17.3.16",
+        "@babel/core": "7.26.10",
+        "@babel/generator": "7.26.10",
+        "@babel/helper-annotate-as-pure": "7.25.9",
+        "@babel/helper-split-export-declaration": "7.24.7",
+        "@babel/plugin-transform-async-generator-functions": "7.26.8",
+        "@babel/plugin-transform-async-to-generator": "7.25.9",
+        "@babel/plugin-transform-runtime": "7.26.10",
+        "@babel/preset-env": "7.26.9",
+        "@babel/runtime": "7.26.10",
         "@discoveryjs/json-ext": "0.5.7",
-        "@ngtools/webpack": "17.3.11",
+        "@ngtools/webpack": "17.3.16",
         "@vitejs/plugin-basic-ssl": "1.1.0",
         "ansi-colors": "4.1.3",
         "autoprefixer": "10.4.18",
@@ -16062,8 +15833,7 @@
         "terser": "5.29.1",
         "tree-kill": "1.2.2",
         "tslib": "2.6.2",
-        "undici": "6.11.1",
-        "vite": "5.1.8",
+        "vite": "~5.4.17",
         "watchpack": "2.4.0",
         "webpack": "5.94.0",
         "webpack-dev-middleware": "6.1.2",
@@ -16073,21 +15843,21 @@
       },
       "dependencies": {
         "@babel/core": {
-          "version": "7.24.0",
-          "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.24.0.tgz",
-          "integrity": "sha512-fQfkg0Gjkza3nf0c7/w6Xf34BW4YvzNfACRLmmb7XRLa6XHdR+K9AlJlxneFfWYf6uhOzuzZVTjF/8KfndZANw==",
+          "version": "7.26.10",
+          "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.26.10.tgz",
+          "integrity": "sha512-vMqyb7XCDMPvJFFOaT9kxtiRh42GwlZEg1/uIgtZshS5a/8OaduUfCi7kynKgc3Tw/6Uo2D+db9qBttghhmxwQ==",
           "dev": true,
           "requires": {
             "@ampproject/remapping": "^2.2.0",
-            "@babel/code-frame": "^7.23.5",
-            "@babel/generator": "^7.23.6",
-            "@babel/helper-compilation-targets": "^7.23.6",
-            "@babel/helper-module-transforms": "^7.23.3",
-            "@babel/helpers": "^7.24.0",
-            "@babel/parser": "^7.24.0",
-            "@babel/template": "^7.24.0",
-            "@babel/traverse": "^7.24.0",
-            "@babel/types": "^7.24.0",
+            "@babel/code-frame": "^7.26.2",
+            "@babel/generator": "^7.26.10",
+            "@babel/helper-compilation-targets": "^7.26.5",
+            "@babel/helper-module-transforms": "^7.26.0",
+            "@babel/helpers": "^7.26.10",
+            "@babel/parser": "^7.26.10",
+            "@babel/template": "^7.26.9",
+            "@babel/traverse": "^7.26.10",
+            "@babel/types": "^7.26.10",
             "convert-source-map": "^2.0.0",
             "debug": "^4.1.0",
             "gensync": "^1.0.0-beta.2",
@@ -16104,175 +15874,175 @@
           }
         },
         "@esbuild/aix-ppc64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.19.12.tgz",
-          "integrity": "sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.21.5.tgz",
+          "integrity": "sha512-1SDgH6ZSPTlggy1yI6+Dbkiz8xzpHJEVAlF/AM1tHPLsf5STom9rwtjE4hKAF20FfXXNTFqEYXyJNWh1GiZedQ==",
           "dev": true,
           "optional": true
         },
         "@esbuild/android-arm": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.19.12.tgz",
-          "integrity": "sha512-qg/Lj1mu3CdQlDEEiWrlC4eaPZ1KztwGJ9B6J+/6G+/4ewxJg7gqj8eVYWvao1bXrqGiW2rsBZFSX3q2lcW05w==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.21.5.tgz",
+          "integrity": "sha512-vCPvzSjpPHEi1siZdlvAlsPxXl7WbOVUBBAowWug4rJHb68Ox8KualB+1ocNvT5fjv6wpkX6o/iEpbDrf68zcg==",
           "dev": true,
           "optional": true
         },
         "@esbuild/android-arm64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.19.12.tgz",
-          "integrity": "sha512-P0UVNGIienjZv3f5zq0DP3Nt2IE/3plFzuaS96vihvD0Hd6H/q4WXUGpCxD/E8YrSXfNyRPbpTq+T8ZQioSuPA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.21.5.tgz",
+          "integrity": "sha512-c0uX9VAUBQ7dTDCjq+wdyGLowMdtR/GoC2U5IYk/7D1H1JYC0qseD7+11iMP2mRLN9RcCMRcjC4YMclCzGwS/A==",
           "dev": true,
           "optional": true
         },
         "@esbuild/android-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.19.12.tgz",
-          "integrity": "sha512-3k7ZoUW6Q6YqhdhIaq/WZ7HwBpnFBlW905Fa4s4qWJyiNOgT1dOqDiVAQFwBH7gBRZr17gLrlFCRzF6jFh7Kew==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.21.5.tgz",
+          "integrity": "sha512-D7aPRUUNHRBwHxzxRvp856rjUHRFW1SdQATKXH2hqA0kAZb1hKmi02OpYRacl0TxIGz/ZmXWlbZgjwWYaCakTA==",
           "dev": true,
           "optional": true
         },
         "@esbuild/darwin-arm64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.19.12.tgz",
-          "integrity": "sha512-B6IeSgZgtEzGC42jsI+YYu9Z3HKRxp8ZT3cqhvliEHovq8HSX2YX8lNocDn79gCKJXOSaEot9MVYky7AKjCs8g==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.21.5.tgz",
+          "integrity": "sha512-DwqXqZyuk5AiWWf3UfLiRDJ5EDd49zg6O9wclZ7kUMv2WRFr4HKjXp/5t8JZ11QbQfUS6/cRCKGwYhtNAY88kQ==",
           "dev": true,
           "optional": true
         },
         "@esbuild/darwin-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.19.12.tgz",
-          "integrity": "sha512-hKoVkKzFiToTgn+41qGhsUJXFlIjxI/jSYeZf3ugemDYZldIXIxhvwN6erJGlX4t5h417iFuheZ7l+YVn05N3A==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.21.5.tgz",
+          "integrity": "sha512-se/JjF8NlmKVG4kNIuyWMV/22ZaerB+qaSi5MdrXtd6R08kvs2qCN4C09miupktDitvh8jRFflwGFBQcxZRjbw==",
           "dev": true,
           "optional": true
         },
         "@esbuild/freebsd-arm64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.19.12.tgz",
-          "integrity": "sha512-4aRvFIXmwAcDBw9AueDQ2YnGmz5L6obe5kmPT8Vd+/+x/JMVKCgdcRwH6APrbpNXsPz+K653Qg8HB/oXvXVukA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.21.5.tgz",
+          "integrity": "sha512-5JcRxxRDUJLX8JXp/wcBCy3pENnCgBR9bN6JsY4OmhfUtIHe3ZW0mawA7+RDAcMLrMIZaf03NlQiX9DGyB8h4g==",
           "dev": true,
           "optional": true
         },
         "@esbuild/freebsd-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.19.12.tgz",
-          "integrity": "sha512-EYoXZ4d8xtBoVN7CEwWY2IN4ho76xjYXqSXMNccFSx2lgqOG/1TBPW0yPx1bJZk94qu3tX0fycJeeQsKovA8gg==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.21.5.tgz",
+          "integrity": "sha512-J95kNBj1zkbMXtHVH29bBriQygMXqoVQOQYA+ISs0/2l3T9/kj42ow2mpqerRBxDJnmkUDCaQT/dfNXWX/ZZCQ==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-arm": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.19.12.tgz",
-          "integrity": "sha512-J5jPms//KhSNv+LO1S1TX1UWp1ucM6N6XuL6ITdKWElCu8wXP72l9MM0zDTzzeikVyqFE6U8YAV9/tFyj0ti+w==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.21.5.tgz",
+          "integrity": "sha512-bPb5AHZtbeNGjCKVZ9UGqGwo8EUu4cLq68E95A53KlxAPRmUyYv2D6F0uUI65XisGOL1hBP5mTronbgo+0bFcA==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-arm64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.19.12.tgz",
-          "integrity": "sha512-EoTjyYyLuVPfdPLsGVVVC8a0p1BFFvtpQDB/YLEhaXyf/5bczaGeN15QkR+O4S5LeJ92Tqotve7i1jn35qwvdA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.21.5.tgz",
+          "integrity": "sha512-ibKvmyYzKsBeX8d8I7MH/TMfWDXBF3db4qM6sy+7re0YXya+K1cem3on9XgdT2EQGMu4hQyZhan7TeQ8XkGp4Q==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-ia32": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.19.12.tgz",
-          "integrity": "sha512-Thsa42rrP1+UIGaWz47uydHSBOgTUnwBwNq59khgIwktK6x60Hivfbux9iNR0eHCHzOLjLMLfUMLCypBkZXMHA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.21.5.tgz",
+          "integrity": "sha512-YvjXDqLRqPDl2dvRODYmmhz4rPeVKYvppfGYKSNGdyZkA01046pLWyRKKI3ax8fbJoK5QbxblURkwK/MWY18Tg==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-loong64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.19.12.tgz",
-          "integrity": "sha512-LiXdXA0s3IqRRjm6rV6XaWATScKAXjI4R4LoDlvO7+yQqFdlr1Bax62sRwkVvRIrwXxvtYEHHI4dm50jAXkuAA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.21.5.tgz",
+          "integrity": "sha512-uHf1BmMG8qEvzdrzAqg2SIG/02+4/DHB6a9Kbya0XDvwDEKCoC8ZRWI5JJvNdUjtciBGFQ5PuBlpEOXQj+JQSg==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-mips64el": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.19.12.tgz",
-          "integrity": "sha512-fEnAuj5VGTanfJ07ff0gOA6IPsvrVHLVb6Lyd1g2/ed67oU1eFzL0r9WL7ZzscD+/N6i3dWumGE1Un4f7Amf+w==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.21.5.tgz",
+          "integrity": "sha512-IajOmO+KJK23bj52dFSNCMsz1QP1DqM6cwLUv3W1QwyxkyIWecfafnI555fvSGqEKwjMXVLokcV5ygHW5b3Jbg==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-ppc64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.19.12.tgz",
-          "integrity": "sha512-nYJA2/QPimDQOh1rKWedNOe3Gfc8PabU7HT3iXWtNUbRzXS9+vgB0Fjaqr//XNbd82mCxHzik2qotuI89cfixg==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.21.5.tgz",
+          "integrity": "sha512-1hHV/Z4OEfMwpLO8rp7CvlhBDnjsC3CttJXIhBi+5Aj5r+MBvy4egg7wCbe//hSsT+RvDAG7s81tAvpL2XAE4w==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-riscv64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.19.12.tgz",
-          "integrity": "sha512-2MueBrlPQCw5dVJJpQdUYgeqIzDQgw3QtiAHUC4RBz9FXPrskyyU3VI1hw7C0BSKB9OduwSJ79FTCqtGMWqJHg==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.21.5.tgz",
+          "integrity": "sha512-2HdXDMd9GMgTGrPWnJzP2ALSokE/0O5HhTUvWIbD3YdjME8JwvSCnNGBnTThKGEB91OZhzrJ4qIIxk/SBmyDDA==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-s390x": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.19.12.tgz",
-          "integrity": "sha512-+Pil1Nv3Umes4m3AZKqA2anfhJiVmNCYkPchwFJNEJN5QxmTs1uzyy4TvmDrCRNT2ApwSari7ZIgrPeUx4UZDg==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.21.5.tgz",
+          "integrity": "sha512-zus5sxzqBJD3eXxwvjN1yQkRepANgxE9lgOW2qLnmr8ikMTphkjgXu1HR01K4FJg8h1kEEDAqDcZQtbrRnB41A==",
           "dev": true,
           "optional": true
         },
         "@esbuild/linux-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.19.12.tgz",
-          "integrity": "sha512-B71g1QpxfwBvNrfyJdVDexenDIt1CiDN1TIXLbhOw0KhJzE78KIFGX6OJ9MrtC0oOqMWf+0xop4qEU8JrJTwCg==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.21.5.tgz",
+          "integrity": "sha512-1rYdTpyv03iycF1+BhzrzQJCdOuAOtaqHTWJZCWvijKD2N5Xu0TtVC8/+1faWqcP9iBCWOmjmhoH94dH82BxPQ==",
           "dev": true,
           "optional": true
         },
         "@esbuild/netbsd-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.19.12.tgz",
-          "integrity": "sha512-3ltjQ7n1owJgFbuC61Oj++XhtzmymoCihNFgT84UAmJnxJfm4sYCiSLTXZtE00VWYpPMYc+ZQmB6xbSdVh0JWA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.21.5.tgz",
+          "integrity": "sha512-Woi2MXzXjMULccIwMnLciyZH4nCIMpWQAs049KEeMvOcNADVxo0UBIQPfSmxB3CWKedngg7sWZdLvLczpe0tLg==",
           "dev": true,
           "optional": true
         },
         "@esbuild/openbsd-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.19.12.tgz",
-          "integrity": "sha512-RbrfTB9SWsr0kWmb9srfF+L933uMDdu9BIzdA7os2t0TXhCRjrQyCeOt6wVxr79CKD4c+p+YhCj31HBkYcXebw==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.21.5.tgz",
+          "integrity": "sha512-HLNNw99xsvx12lFBUwoT8EVCsSvRNDVxNpjZ7bPn947b8gJPzeHWyNVhFsaerc0n3TsbOINvRP2byTZ5LKezow==",
           "dev": true,
           "optional": true
         },
         "@esbuild/sunos-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.19.12.tgz",
-          "integrity": "sha512-HKjJwRrW8uWtCQnQOz9qcU3mUZhTUQvi56Q8DPTLLB+DawoiQdjsYq+j+D3s9I8VFtDr+F9CjgXKKC4ss89IeA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.21.5.tgz",
+          "integrity": "sha512-6+gjmFpfy0BHU5Tpptkuh8+uw3mnrvgs+dSPQXQOv3ekbordwnzTVEb4qnIvQcYXq6gzkyTnoZ9dZG+D4garKg==",
           "dev": true,
           "optional": true
         },
         "@esbuild/win32-arm64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.19.12.tgz",
-          "integrity": "sha512-URgtR1dJnmGvX864pn1B2YUYNzjmXkuJOIqG2HdU62MVS4EHpU2946OZoTMnRUHklGtJdJZ33QfzdjGACXhn1A==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.21.5.tgz",
+          "integrity": "sha512-Z0gOTd75VvXqyq7nsl93zwahcTROgqvuAcYDUr+vOv8uHhNSKROyU961kgtCD1e95IqPKSQKH7tBTslnS3tA8A==",
           "dev": true,
           "optional": true
         },
         "@esbuild/win32-ia32": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.19.12.tgz",
-          "integrity": "sha512-+ZOE6pUkMOJfmxmBZElNOx72NKpIa/HFOMGzu8fqzQJ5kgf6aTGrcJaFsNiVMH4JKpMipyK+7k0n2UXN7a8YKQ==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.21.5.tgz",
+          "integrity": "sha512-SWXFF1CL2RVNMaVs+BBClwtfZSvDgtL//G/smwAc5oVK/UPu2Gu9tIaRgFmYFFKrmg3SyAjSrElf0TiJ1v8fYA==",
           "dev": true,
           "optional": true
         },
         "@esbuild/win32-x64": {
-          "version": "0.19.12",
-          "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.19.12.tgz",
-          "integrity": "sha512-T1QyPSDCyMXaO3pzBkF96E8xMkiRYbUEZADd29SyPGabqxMViNoii+NcK7eWJAEoU6RZyEm5lVSIjTmcdoB9HA==",
+          "version": "0.21.5",
+          "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.21.5.tgz",
+          "integrity": "sha512-tQd/1efJuzPC6rCFwEvLtci/xNFcTZknmXs98FYDfGE4wP9ClFV98nyKrzJKVPMhdDnjzLhdUyMX4PsQAPjwIw==",
           "dev": true,
           "optional": true
         },
         "@types/node": {
-          "version": "22.10.7",
-          "resolved": "https://registry.npmjs.org/@types/node/-/node-22.10.7.tgz",
-          "integrity": "sha512-V09KvXxFiutGp6B7XkpaDXlNadZxrzajcY50EuoLIpQ6WWYCSvf19lVIazzfIzQvhUN2HjX12spLojTnhuKlGg==",
+          "version": "22.14.1",
+          "resolved": "https://registry.npmjs.org/@types/node/-/node-22.14.1.tgz",
+          "integrity": "sha512-u0HuPQwe/dHrItgHHpmw3N2fYCR6x4ivMNbPHRkBVP4CvN+kiRrKHWk3i8tXiO/joPwXLMYvF9TTF0eqgHIuOw==",
           "dev": true,
           "optional": true,
           "peer": true,
           "requires": {
-            "undici-types": "~6.20.0"
+            "undici-types": "~6.21.0"
           }
         },
         "@vitejs/plugin-basic-ssl": {
@@ -16282,18 +16052,45 @@
           "dev": true,
           "requires": {}
         },
+        "ajv": {
+          "version": "6.12.6",
+          "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+          "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+          "dev": true,
+          "requires": {
+            "fast-deep-equal": "^3.1.1",
+            "fast-json-stable-stringify": "^2.0.0",
+            "json-schema-traverse": "^0.4.1",
+            "uri-js": "^4.2.2"
+          }
+        },
         "convert-source-map": {
           "version": "2.0.0",
           "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz",
           "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==",
           "dev": true
         },
+        "json-schema-traverse": {
+          "version": "0.4.1",
+          "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
+          "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==",
+          "dev": true
+        },
         "picomatch": {
           "version": "4.0.1",
           "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.1.tgz",
           "integrity": "sha512-xUXwsxNjwTQ8K3GnT4pCJm+xq3RUPQbmkYJTP5aFIfNIvbcc/4MUxgBaaRSZJ6yGJZiGSyYlM6MzwTsRk8SYCg==",
           "dev": true
         },
+        "rxjs": {
+          "version": "7.8.1",
+          "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+          "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+          "dev": true,
+          "requires": {
+            "tslib": "^2.1.0"
+          }
+        },
         "schema-utils": {
           "version": "3.3.0",
           "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz",
@@ -16321,46 +16118,57 @@
           "dev": true
         },
         "vite": {
-          "version": "5.1.8",
-          "resolved": "https://registry.npmjs.org/vite/-/vite-5.1.8.tgz",
-          "integrity": "sha512-mB8ToUuSmzODSpENgvpFk2fTiU/YQ1tmcVJJ4WZbq4fPdGJkFNVcmVL5k7iDug6xzWjjuGDKAuSievIsD6H7Xw==",
+          "version": "5.4.18",
+          "resolved": "https://registry.npmjs.org/vite/-/vite-5.4.18.tgz",
+          "integrity": "sha512-1oDcnEp3lVyHCuQ2YFelM4Alm2o91xNoMncRm1U7S+JdYfYOvbiGZ3/CxGttrOu2M/KcGz7cRC2DoNUA6urmMA==",
           "dev": true,
           "requires": {
-            "esbuild": "^0.19.3",
+            "esbuild": "^0.21.3",
             "fsevents": "~2.3.3",
-            "postcss": "^8.4.35",
-            "rollup": "^4.2.0"
+            "postcss": "^8.4.43",
+            "rollup": "^4.20.0"
           },
           "dependencies": {
             "esbuild": {
-              "version": "0.19.12",
-              "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.19.12.tgz",
-              "integrity": "sha512-aARqgq8roFBj054KvQr5f1sFu0D65G+miZRCuJyJ0G13Zwx7vRar5Zhn2tkQNzIXcBrNVsv/8stehpj+GAjgbg==",
+              "version": "0.21.5",
+              "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.21.5.tgz",
+              "integrity": "sha512-mg3OPMV4hXywwpoDxu3Qda5xCKQi+vCTZq8S9J/EpkhB2HzKXq4SNFZE3+NK93JYxc8VMSep+lOUSC/RVKaBqw==",
+              "dev": true,
+              "requires": {
+                "@esbuild/aix-ppc64": "0.21.5",
+                "@esbuild/android-arm": "0.21.5",
+                "@esbuild/android-arm64": "0.21.5",
+                "@esbuild/android-x64": "0.21.5",
+                "@esbuild/darwin-arm64": "0.21.5",
+                "@esbuild/darwin-x64": "0.21.5",
+                "@esbuild/freebsd-arm64": "0.21.5",
+                "@esbuild/freebsd-x64": "0.21.5",
+                "@esbuild/linux-arm": "0.21.5",
+                "@esbuild/linux-arm64": "0.21.5",
+                "@esbuild/linux-ia32": "0.21.5",
+                "@esbuild/linux-loong64": "0.21.5",
+                "@esbuild/linux-mips64el": "0.21.5",
+                "@esbuild/linux-ppc64": "0.21.5",
+                "@esbuild/linux-riscv64": "0.21.5",
+                "@esbuild/linux-s390x": "0.21.5",
+                "@esbuild/linux-x64": "0.21.5",
+                "@esbuild/netbsd-x64": "0.21.5",
+                "@esbuild/openbsd-x64": "0.21.5",
+                "@esbuild/sunos-x64": "0.21.5",
+                "@esbuild/win32-arm64": "0.21.5",
+                "@esbuild/win32-ia32": "0.21.5",
+                "@esbuild/win32-x64": "0.21.5"
+              }
+            },
+            "postcss": {
+              "version": "8.5.3",
+              "resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.3.tgz",
+              "integrity": "sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==",
               "dev": true,
               "requires": {
-                "@esbuild/aix-ppc64": "0.19.12",
-                "@esbuild/android-arm": "0.19.12",
-                "@esbuild/android-arm64": "0.19.12",
-                "@esbuild/android-x64": "0.19.12",
-                "@esbuild/darwin-arm64": "0.19.12",
-                "@esbuild/darwin-x64": "0.19.12",
-                "@esbuild/freebsd-arm64": "0.19.12",
-                "@esbuild/freebsd-x64": "0.19.12",
-                "@esbuild/linux-arm": "0.19.12",
-                "@esbuild/linux-arm64": "0.19.12",
-                "@esbuild/linux-ia32": "0.19.12",
-                "@esbuild/linux-loong64": "0.19.12",
-                "@esbuild/linux-mips64el": "0.19.12",
-                "@esbuild/linux-ppc64": "0.19.12",
-                "@esbuild/linux-riscv64": "0.19.12",
-                "@esbuild/linux-s390x": "0.19.12",
-                "@esbuild/linux-x64": "0.19.12",
-                "@esbuild/netbsd-x64": "0.19.12",
-                "@esbuild/openbsd-x64": "0.19.12",
-                "@esbuild/sunos-x64": "0.19.12",
-                "@esbuild/win32-arm64": "0.19.12",
-                "@esbuild/win32-ia32": "0.19.12",
-                "@esbuild/win32-x64": "0.19.12"
+                "nanoid": "^3.3.8",
+                "picocolors": "^1.1.1",
+                "source-map-js": "^1.2.1"
               }
             }
           }
@@ -16432,19 +16240,30 @@
       }
     },
     "@angular-devkit/build-webpack": {
-      "version": "0.1703.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/build-webpack/-/build-webpack-0.1703.11.tgz",
-      "integrity": "sha512-qbCiiHuoVkD7CtLyWoRi/Vzz6nrEztpF5XIyWUcQu67An1VlxbMTE4yoSQiURjCQMnB/JvS1GPVed7wOq3SJ/w==",
+      "version": "0.1703.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/build-webpack/-/build-webpack-0.1703.16.tgz",
+      "integrity": "sha512-ybZr+2F4siu0MztyhSkzN3lIMF0YFeyMaoTygWKjMeGMrkdj4IOAHiR+le2dQ+W4RhwEwQwkV2lvyDJzbivWhg==",
       "dev": true,
       "requires": {
-        "@angular-devkit/architect": "0.1703.11",
+        "@angular-devkit/architect": "0.1703.16",
         "rxjs": "7.8.1"
+      },
+      "dependencies": {
+        "rxjs": {
+          "version": "7.8.1",
+          "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+          "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+          "dev": true,
+          "requires": {
+            "tslib": "^2.1.0"
+          }
+        }
       }
     },
     "@angular-devkit/core": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-17.3.11.tgz",
-      "integrity": "sha512-vTNDYNsLIWpYk2I969LMQFH29GTsLzxNk/0cLw5q56ARF0v5sIWfHYwGTS88jdDqIpuuettcSczbxeA7EuAmqQ==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/core/-/core-17.3.16.tgz",
+      "integrity": "sha512-3Dhb/pE3c6P9bDfYLhYb0ArTFYmYSx5QgEUVMuowXJtP/3EyU7lWB2kcuiBZgScxrhRLOiMGMPgcF9jVmvovug==",
       "dev": true,
       "requires": {
         "ajv": "8.12.0",
@@ -16467,31 +16286,45 @@
             "uri-js": "^4.2.2"
           }
         },
-        "json-schema-traverse": {
-          "version": "1.0.0",
-          "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
-          "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
-          "dev": true
-        },
         "picomatch": {
           "version": "4.0.1",
           "resolved": "https://registry.npmjs.org/picomatch/-/picomatch-4.0.1.tgz",
           "integrity": "sha512-xUXwsxNjwTQ8K3GnT4pCJm+xq3RUPQbmkYJTP5aFIfNIvbcc/4MUxgBaaRSZJ6yGJZiGSyYlM6MzwTsRk8SYCg==",
           "dev": true
+        },
+        "rxjs": {
+          "version": "7.8.1",
+          "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+          "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+          "dev": true,
+          "requires": {
+            "tslib": "^2.1.0"
+          }
         }
       }
     },
     "@angular-devkit/schematics": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-17.3.11.tgz",
-      "integrity": "sha512-I5wviiIqiFwar9Pdk30Lujk8FczEEc18i22A5c6Z9lbmhPQdTroDnEQdsfXjy404wPe8H62s0I15o4pmMGfTYQ==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular-devkit/schematics/-/schematics-17.3.16.tgz",
+      "integrity": "sha512-EcKBdQ02RIwYLHrExOvtrj8FXtTT/Z0IQe8maUy+YkOWjJHsjpdRBOwi3JOICyjnkopOtkkHy/bxu5VKh6rL7A==",
       "dev": true,
       "requires": {
-        "@angular-devkit/core": "17.3.11",
+        "@angular-devkit/core": "17.3.16",
         "jsonc-parser": "3.2.1",
         "magic-string": "0.30.8",
         "ora": "5.4.1",
         "rxjs": "7.8.1"
+      },
+      "dependencies": {
+        "rxjs": {
+          "version": "7.8.1",
+          "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
+          "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+          "dev": true,
+          "requires": {
+            "tslib": "^2.1.0"
+          }
+        }
       }
     },
     "@angular/animations": {
@@ -16512,15 +16345,15 @@
       }
     },
     "@angular/cli": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@angular/cli/-/cli-17.3.11.tgz",
-      "integrity": "sha512-8R9LwAGL8hGAWJ4mNG9ZPUrBUzIdmst0Ldua6RJJ+PrqgjX+8IbO+lNnfrOY/XY+Z3LXbCEJflL26f9czCvTPQ==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@angular/cli/-/cli-17.3.16.tgz",
+      "integrity": "sha512-cG/+aAW7z/o8Tl75U6d+pa+zygV9cvdeY/vb6ve16o4MS6Ifwbls6L51gekYGdWpLl1QnWHLbZFz7+mOa7Um2w==",
       "dev": true,
       "requires": {
-        "@angular-devkit/architect": "0.1703.11",
-        "@angular-devkit/core": "17.3.11",
-        "@angular-devkit/schematics": "17.3.11",
-        "@schematics/angular": "17.3.11",
+        "@angular-devkit/architect": "0.1703.16",
+        "@angular-devkit/core": "17.3.16",
+        "@angular-devkit/schematics": "17.3.16",
+        "@schematics/angular": "17.3.16",
         "@yarnpkg/lockfile": "1.1.0",
         "ansi-colors": "4.1.3",
         "ini": "4.1.2",
@@ -16714,9 +16547,9 @@
       }
     },
     "@babel/compat-data": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.5.tgz",
-      "integrity": "sha512-XvcZi1KWf88RVbF9wn8MN6tYFloU5qX8KjuF3E1PVBmJ9eypXfs4GRiJwLuTZL0iSnJUKn1BFPa5BPZZJyFzPg==",
+      "version": "7.26.8",
+      "resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.26.8.tgz",
+      "integrity": "sha512-oH5UPLMWR3L2wEFLnFJ1TZXqHufiTKAiLfqw5zkhS4dKXLJ10yVztfil/twG8EDTA4F/tvVNw9nOl4ZMslB8rQ==",
       "dev": true
     },
     "@babel/core": {
@@ -16742,31 +16575,12 @@
         "semver": "^6.3.1"
       },
       "dependencies": {
-        "@babel/generator": {
-          "version": "7.26.5",
-          "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.5.tgz",
-          "integrity": "sha512-2caSP6fN9I7HOe6nqhtft7V4g7/V/gfDsC3Ag4W7kEzzvRGKqiv0pu0HogPiZ3KaVSoNDhUws6IJjDjpfmYIXw==",
-          "dev": true,
-          "requires": {
-            "@babel/parser": "^7.26.5",
-            "@babel/types": "^7.26.5",
-            "@jridgewell/gen-mapping": "^0.3.5",
-            "@jridgewell/trace-mapping": "^0.3.25",
-            "jsesc": "^3.0.2"
-          }
-        },
         "convert-source-map": {
           "version": "2.0.0",
           "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz",
           "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==",
           "dev": true
         },
-        "jsesc": {
-          "version": "3.1.0",
-          "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz",
-          "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==",
-          "dev": true
-        },
         "semver": {
           "version": "6.3.1",
           "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
@@ -16776,24 +16590,25 @@
       }
     },
     "@babel/generator": {
-      "version": "7.23.6",
-      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.23.6.tgz",
-      "integrity": "sha512-qrSfCYxYQB5owCmGLbl8XRpX1ytXlpueOb0N0UmQwA073KZxejgQTzAmJezxvpwQD9uGtK2shHdi55QT+MbjIw==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.10.tgz",
+      "integrity": "sha512-rRHT8siFIXQrAYOYqZQVsAr8vJ+cBNqcVAY6m5V8/4QqzaPl+zDBe6cLEPRDuNOUf3ww8RfJVlOyQMoSI+5Ang==",
       "dev": true,
       "requires": {
-        "@babel/types": "^7.23.6",
-        "@jridgewell/gen-mapping": "^0.3.2",
-        "@jridgewell/trace-mapping": "^0.3.17",
-        "jsesc": "^2.5.1"
+        "@babel/parser": "^7.26.10",
+        "@babel/types": "^7.26.10",
+        "@jridgewell/gen-mapping": "^0.3.5",
+        "@jridgewell/trace-mapping": "^0.3.25",
+        "jsesc": "^3.0.2"
       }
     },
     "@babel/helper-annotate-as-pure": {
-      "version": "7.22.5",
-      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.22.5.tgz",
-      "integrity": "sha512-LvBTxu8bQSQkcyKOU+a1btnNFQ1dMAd0R6PyW3arXes06F6QLWLIrd681bxRPIXlrMGR3XYnW9JyML7dP3qgxg==",
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
+      "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
       "dev": true,
       "requires": {
-        "@babel/types": "^7.22.5"
+        "@babel/types": "^7.25.9"
       }
     },
     "@babel/helper-compilation-targets": {
@@ -16847,15 +16662,6 @@
         "semver": "^6.3.1"
       },
       "dependencies": {
-        "@babel/helper-annotate-as-pure": {
-          "version": "7.25.9",
-          "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-          "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-          "dev": true,
-          "requires": {
-            "@babel/types": "^7.25.9"
-          }
-        },
         "semver": {
           "version": "6.3.1",
           "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
@@ -16875,15 +16681,6 @@
         "semver": "^6.3.1"
       },
       "dependencies": {
-        "@babel/helper-annotate-as-pure": {
-          "version": "7.25.9",
-          "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-          "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-          "dev": true,
-          "requires": {
-            "@babel/types": "^7.25.9"
-          }
-        },
         "semver": {
           "version": "6.3.1",
           "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
@@ -16893,9 +16690,9 @@
       }
     },
     "@babel/helper-define-polyfill-provider": {
-      "version": "0.6.3",
-      "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.3.tgz",
-      "integrity": "sha512-HK7Bi+Hj6H+VTHA3ZvBis7V/6hu9QuTrnMXNybfUf2iiuU/N97I8VjB+KbhFF8Rld/Lx5MzoCwPCpPjfK+n8Cg==",
+      "version": "0.6.4",
+      "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.6.4.tgz",
+      "integrity": "sha512-jljfR1rGnXXNWnmQg2K3+bvhkxB51Rl32QRaOTuwwjviGrHzIbSc8+x9CpraDtbT7mfyjXObULP4w/adunNwAw==",
       "dev": true,
       "requires": {
         "@babel/helper-compilation-targets": "^7.22.6",
@@ -16905,15 +16702,6 @@
         "resolve": "^1.14.2"
       }
     },
-    "@babel/helper-environment-visitor": {
-      "version": "7.24.7",
-      "resolved": "https://registry.npmjs.org/@babel/helper-environment-visitor/-/helper-environment-visitor-7.24.7.tgz",
-      "integrity": "sha512-DoiN84+4Gnd0ncbBOM9AZENV4a5ZiL39HYMyZJGZ/AZEykHYdJw0wW3kdcsh9/Kn+BRXHLkkklZ51ecPKmI1CQ==",
-      "dev": true,
-      "requires": {
-        "@babel/types": "^7.24.7"
-      }
-    },
     "@babel/helper-member-expression-to-functions": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/helper-member-expression-to-functions/-/helper-member-expression-to-functions-7.25.9.tgz",
@@ -16969,17 +16757,6 @@
         "@babel/helper-annotate-as-pure": "^7.25.9",
         "@babel/helper-wrap-function": "^7.25.9",
         "@babel/traverse": "^7.25.9"
-      },
-      "dependencies": {
-        "@babel/helper-annotate-as-pure": {
-          "version": "7.25.9",
-          "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-          "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-          "dev": true,
-          "requires": {
-            "@babel/types": "^7.25.9"
-          }
-        }
       }
     },
     "@babel/helper-replace-supers": {
@@ -17004,12 +16781,12 @@
       }
     },
     "@babel/helper-split-export-declaration": {
-      "version": "7.22.6",
-      "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.22.6.tgz",
-      "integrity": "sha512-AsUnxuLhRYsisFiaJwvp1QF+I3KjD5FOxut14q/GzovUe6orHLesW2C7d754kRm53h5gqrz6sFl6sxc4BVtE/g==",
+      "version": "7.24.7",
+      "resolved": "https://registry.npmjs.org/@babel/helper-split-export-declaration/-/helper-split-export-declaration-7.24.7.tgz",
+      "integrity": "sha512-oy5V7pD+UvfkEATUKvIjvIAH/xCzfsFVw7ygW2SI6NClZzquT+mwdTfgfdbUiceh6iQO0CHtCPsyze/MZ2YbAA==",
       "dev": true,
       "requires": {
-        "@babel/types": "^7.22.5"
+        "@babel/types": "^7.24.7"
       }
     },
     "@babel/helper-string-parser": {
@@ -17042,212 +16819,96 @@
       }
     },
     "@babel/helpers": {
-      "version": "7.26.0",
-      "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.26.0.tgz",
-      "integrity": "sha512-tbhNuIxNcVb21pInl3ZSjksLCvgdZy9KwJ8brv993QtIVKJBBkYXz4q4ZbAv31GdnC+R90np23L5FbEBlthAEw==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/helpers/-/helpers-7.27.0.tgz",
+      "integrity": "sha512-U5eyP/CTFPuNE3qk+WZMxFkp/4zUzdceQlfzf7DdGdhp+Fezd7HD+i8Y24ZuTMKX3wQBld449jijbGq6OdGNQg==",
       "dev": true,
       "requires": {
-        "@babel/template": "^7.25.9",
-        "@babel/types": "^7.26.0"
+        "@babel/template": "^7.27.0",
+        "@babel/types": "^7.27.0"
       }
     },
     "@babel/parser": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.26.5.tgz",
-      "integrity": "sha512-SRJ4jYmXRqV1/Xc+TIVG84WjHBXKlxO9sHQnA2Pf12QQEAp1LOh6kDzNHXcUnbH1QI0FDoPPVOt+vyUDucxpaw==",
-      "dev": true,
-      "requires": {
-        "@babel/types": "^7.26.5"
-      }
-    },
-    "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.25.9.tgz",
-      "integrity": "sha512-2qUwwfAFpJLZqxd02YW9btUCZHl+RFvdDkNfZwaIJrvB8Tesjsk8pEQkTvGwZXLqXUx/2oyY3ySRhm6HOXuCug==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.25.9"
-      }
-    },
-    "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.25.9.tgz",
-      "integrity": "sha512-6xWgLZTJXwilVjlnV7ospI3xi+sl8lN8rXXbBD6vYn3UYDlGsag8wrZkKcSI8G6KgqKP7vNFaDgeDnfAABq61g==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.27.0.tgz",
+      "integrity": "sha512-iaepho73/2Pz7w2eMS0Q5f83+0RKI7i4xmiYeBmDzfRVbQtTOG7Ts0S4HzJVsTMGI9keU8rNfuZr8DKfSt7Yyg==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.25.9",
-        "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9",
-        "@babel/plugin-transform-optional-chaining": "^7.25.9"
+        "@babel/types": "^7.27.0"
       }
     },
-    "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": {
+    "@babel/plugin-bugfix-firefox-class-in-computed-class-key": {
       "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly/-/plugin-bugfix-v8-static-class-fields-redefine-readonly-7.25.9.tgz",
-      "integrity": "sha512-aLnMXYPnzwwqhYSCyXfKkIkYgJ8zv9RK+roo9DkTXz38ynIhd9XCbN08s3MGvqL2MYGVUGdRQLL/JqBIeJhJBg==",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-firefox-class-in-computed-class-key/-/plugin-bugfix-firefox-class-in-computed-class-key-7.25.9.tgz",
+      "integrity": "sha512-ZkRyVkThtxQ/J6nv3JFYv1RYY+JT5BvU0y3k5bWrmuG4woXypRa4PXmm9RhOwodRkYFWqC0C0cqcJ4OqR7kW+g==",
       "dev": true,
       "requires": {
         "@babel/helper-plugin-utils": "^7.25.9",
         "@babel/traverse": "^7.25.9"
       }
     },
-    "@babel/plugin-proposal-private-property-in-object": {
-      "version": "7.21.0-placeholder-for-preset-env.2",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.21.0-placeholder-for-preset-env.2.tgz",
-      "integrity": "sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==",
-      "dev": true,
-      "requires": {}
-    },
-    "@babel/plugin-syntax-async-generators": {
-      "version": "7.8.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-async-generators/-/plugin-syntax-async-generators-7.8.4.tgz",
-      "integrity": "sha512-tycmZxkGfZaxhMRbXlPXuVFpdWlXpir2W4AMhSJgRKzk/eDlIXOhb2LHWoLpDF7TEHylV5zNhykX6KAgHJmTNw==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      }
-    },
-    "@babel/plugin-syntax-class-properties": {
-      "version": "7.12.13",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-properties/-/plugin-syntax-class-properties-7.12.13.tgz",
-      "integrity": "sha512-fm4idjKla0YahUNgFNLCB0qySdsoPiZP3iQE3rky0mBUtMZ23yDJ9SJdg6dXTSDnulOVqiF3Hgr9nbXvXTQZYA==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.12.13"
-      }
-    },
-    "@babel/plugin-syntax-class-static-block": {
-      "version": "7.14.5",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-class-static-block/-/plugin-syntax-class-static-block-7.14.5.tgz",
-      "integrity": "sha512-b+YyPmr6ldyNnM6sqYeMWE+bgJcJpO6yS4QD7ymxgH34GBPNDM/THBh8iunyvKIZztiwLH4CJZ0RxTk9emgpjw==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.14.5"
-      }
-    },
-    "@babel/plugin-syntax-dynamic-import": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-dynamic-import/-/plugin-syntax-dynamic-import-7.8.3.tgz",
-      "integrity": "sha512-5gdGbFon+PszYzqs83S3E5mpi7/y/8M9eC90MRTZfduQOYW76ig6SOSPNe41IG5LoP3FGBn2N0RjVDSQiS94kQ==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      }
-    },
-    "@babel/plugin-syntax-export-namespace-from": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-export-namespace-from/-/plugin-syntax-export-namespace-from-7.8.3.tgz",
-      "integrity": "sha512-MXf5laXo6c1IbEbegDmzGPwGNTsHZmEy6QGznu5Sh2UCWvueywb2ee+CCE4zQiZstxU9BMoQO9i6zUFSY0Kj0Q==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.8.3"
-      }
-    },
-    "@babel/plugin-syntax-import-assertions": {
-      "version": "7.26.0",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.26.0.tgz",
-      "integrity": "sha512-QCWT5Hh830hK5EQa7XzuqIkQU9tT/whqbDz7kuaZMHFl1inRRg7JnuAEOQ0Ur0QUl0NufCk1msK2BeY79Aj/eg==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.25.9"
-      }
-    },
-    "@babel/plugin-syntax-import-attributes": {
-      "version": "7.26.0",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.26.0.tgz",
-      "integrity": "sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==",
+    "@babel/plugin-bugfix-safari-class-field-initializer-scope": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-class-field-initializer-scope/-/plugin-bugfix-safari-class-field-initializer-scope-7.25.9.tgz",
+      "integrity": "sha512-MrGRLZxLD/Zjj0gdU15dfs+HH/OXvnw/U4jJD8vpcP2CJQapPEv1IWwjc/qMg7ItBlPwSv1hRBbb7LeuANdcnw==",
       "dev": true,
       "requires": {
         "@babel/helper-plugin-utils": "^7.25.9"
       }
     },
-    "@babel/plugin-syntax-import-meta": {
-      "version": "7.10.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-meta/-/plugin-syntax-import-meta-7.10.4.tgz",
-      "integrity": "sha512-Yqfm+XDx0+Prh3VSeEQCPU81yC+JWZ2pDPFSS4ZdpfZhp4MkFMaDC1UqseovEKwSUpnIL7+vK+Clp7bfh0iD7g==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.10.4"
-      }
-    },
-    "@babel/plugin-syntax-json-strings": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-json-strings/-/plugin-syntax-json-strings-7.8.3.tgz",
-      "integrity": "sha512-lY6kdGpWHvjoe2vk4WrAapEuBR69EMxZl+RoGRhrFGNYVK8mOPAW8VfbT/ZgrFbXlDNiiaxQnAtgVCZ6jv30EA==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      }
-    },
-    "@babel/plugin-syntax-logical-assignment-operators": {
-      "version": "7.10.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-logical-assignment-operators/-/plugin-syntax-logical-assignment-operators-7.10.4.tgz",
-      "integrity": "sha512-d8waShlpFDinQ5MtvGU9xDAOzKH47+FFoney2baFIoMr952hKOLp1HR7VszoZvOsV/4+RRszNY7D17ba0te0ig==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.10.4"
-      }
-    },
-    "@babel/plugin-syntax-nullish-coalescing-operator": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-nullish-coalescing-operator/-/plugin-syntax-nullish-coalescing-operator-7.8.3.tgz",
-      "integrity": "sha512-aSff4zPII1u2QD7y+F8oDsz19ew4IGEJg9SVW+bqwpwtfFleiQDMdzA/R+UlWDzfnHFCxxleFT0PMIrR36XLNQ==",
-      "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      }
-    },
-    "@babel/plugin-syntax-numeric-separator": {
-      "version": "7.10.4",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-numeric-separator/-/plugin-syntax-numeric-separator-7.10.4.tgz",
-      "integrity": "sha512-9H6YdfkcK/uOnY/K7/aA2xpzaAgkQn37yzWUMRK7OaPOqOpGS1+n0H5hxT9AUw9EsSjPW8SVyMJwYRtWs3X3ug==",
+    "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression/-/plugin-bugfix-safari-id-destructuring-collision-in-function-expression-7.25.9.tgz",
+      "integrity": "sha512-2qUwwfAFpJLZqxd02YW9btUCZHl+RFvdDkNfZwaIJrvB8Tesjsk8pEQkTvGwZXLqXUx/2oyY3ySRhm6HOXuCug==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.10.4"
+        "@babel/helper-plugin-utils": "^7.25.9"
       }
     },
-    "@babel/plugin-syntax-object-rest-spread": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-object-rest-spread/-/plugin-syntax-object-rest-spread-7.8.3.tgz",
-      "integrity": "sha512-XoqMijGZb9y3y2XskN+P1wUGiVwWZ5JmoDRwx5+3GmEplNyVM2s2Dg8ILFQm8rWM48orGy5YpI5Bl8U1y7ydlA==",
+    "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.25.9.tgz",
+      "integrity": "sha512-6xWgLZTJXwilVjlnV7ospI3xi+sl8lN8rXXbBD6vYn3UYDlGsag8wrZkKcSI8G6KgqKP7vNFaDgeDnfAABq61g==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
+        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9",
+        "@babel/plugin-transform-optional-chaining": "^7.25.9"
       }
     },
-    "@babel/plugin-syntax-optional-catch-binding": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-catch-binding/-/plugin-syntax-optional-catch-binding-7.8.3.tgz",
-      "integrity": "sha512-6VPD0Pc1lpTqw0aKoeRTMiB+kWhAoT24PA+ksWSBrFtl5SIRVpZlwN3NNPQjehA2E/91FV3RjLWoVTglWcSV3Q==",
+    "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly/-/plugin-bugfix-v8-static-class-fields-redefine-readonly-7.25.9.tgz",
+      "integrity": "sha512-aLnMXYPnzwwqhYSCyXfKkIkYgJ8zv9RK+roo9DkTXz38ynIhd9XCbN08s3MGvqL2MYGVUGdRQLL/JqBIeJhJBg==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
+        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/traverse": "^7.25.9"
       }
     },
-    "@babel/plugin-syntax-optional-chaining": {
-      "version": "7.8.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-optional-chaining/-/plugin-syntax-optional-chaining-7.8.3.tgz",
-      "integrity": "sha512-KoK9ErH1MBlCPxV0VANkXW2/dw4vlbGDrFgz8bmUsBGYkFRcbRwMh6cIJubdPrkxRwuGdtCk0v/wPTKbQgBjkg==",
+    "@babel/plugin-proposal-private-property-in-object": {
+      "version": "7.21.0-placeholder-for-preset-env.2",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-proposal-private-property-in-object/-/plugin-proposal-private-property-in-object-7.21.0-placeholder-for-preset-env.2.tgz",
+      "integrity": "sha512-SOSkfJDddaM7mak6cPEpswyTRnuRltl429hMraQEglW+OkovnCzsiszTmsrlY//qLFjCpQDFRvjdm2wA5pPm9w==",
       "dev": true,
-      "requires": {
-        "@babel/helper-plugin-utils": "^7.8.0"
-      }
+      "requires": {}
     },
-    "@babel/plugin-syntax-private-property-in-object": {
-      "version": "7.14.5",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-private-property-in-object/-/plugin-syntax-private-property-in-object-7.14.5.tgz",
-      "integrity": "sha512-0wVnp9dxJ72ZUJDV27ZfbSj6iHLoytYZmh3rFcxNnvsJF3ktkzLDZPy/mA17HGsaQT3/DQsWYX1f1QGWkCoVUg==",
+    "@babel/plugin-syntax-import-assertions": {
+      "version": "7.26.0",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-assertions/-/plugin-syntax-import-assertions-7.26.0.tgz",
+      "integrity": "sha512-QCWT5Hh830hK5EQa7XzuqIkQU9tT/whqbDz7kuaZMHFl1inRRg7JnuAEOQ0Ur0QUl0NufCk1msK2BeY79Aj/eg==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.14.5"
+        "@babel/helper-plugin-utils": "^7.25.9"
       }
     },
-    "@babel/plugin-syntax-top-level-await": {
-      "version": "7.14.5",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-top-level-await/-/plugin-syntax-top-level-await-7.14.5.tgz",
-      "integrity": "sha512-hx++upLv5U1rgYfwe1xBQUhRmU41NEvpUvrp8jkrSCdvGSnM5/qdRMtylJ6PG5OFkBaHkbTAKTnd3/YyESRHFw==",
+    "@babel/plugin-syntax-import-attributes": {
+      "version": "7.26.0",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-syntax-import-attributes/-/plugin-syntax-import-attributes-7.26.0.tgz",
+      "integrity": "sha512-e2dttdsJ1ZTpi3B9UYGLw41hifAubg19AtCu/2I/F1QNVclOBr1dYpTdmdyZ84Xiz43BS/tCUkMAZNLv12Pi+A==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.14.5"
+        "@babel/helper-plugin-utils": "^7.25.9"
       }
     },
     "@babel/plugin-syntax-unicode-sets-regex": {
@@ -17270,26 +16931,25 @@
       }
     },
     "@babel/plugin-transform-async-generator-functions": {
-      "version": "7.23.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.23.9.tgz",
-      "integrity": "sha512-8Q3veQEDGe14dTYuwagbRtwxQDnytyg1JFu4/HwEMETeofocrB0U0ejBJIXoeG/t2oXZ8kzCyI0ZZfbT80VFNQ==",
+      "version": "7.26.8",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-generator-functions/-/plugin-transform-async-generator-functions-7.26.8.tgz",
+      "integrity": "sha512-He9Ej2X7tNf2zdKMAGOsmg2MrFc+hfoAhd3po4cWfo/NWjzEAKa0oQruj1ROVUdl0e6fb6/kE/G3SSxE0lRJOg==",
       "dev": true,
       "requires": {
-        "@babel/helper-environment-visitor": "^7.22.20",
-        "@babel/helper-plugin-utils": "^7.22.5",
-        "@babel/helper-remap-async-to-generator": "^7.22.20",
-        "@babel/plugin-syntax-async-generators": "^7.8.4"
+        "@babel/helper-plugin-utils": "^7.26.5",
+        "@babel/helper-remap-async-to-generator": "^7.25.9",
+        "@babel/traverse": "^7.26.8"
       }
     },
     "@babel/plugin-transform-async-to-generator": {
-      "version": "7.23.3",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.23.3.tgz",
-      "integrity": "sha512-A7LFsKi4U4fomjqXJlZg/u0ft/n8/7n7lpffUP/ZULx/DtV9SGlNKZolHH6PE8Xl1ngCc0M11OaeZptXVkfKSw==",
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-async-to-generator/-/plugin-transform-async-to-generator-7.25.9.tgz",
+      "integrity": "sha512-NT7Ejn7Z/LjUH0Gv5KsBCxh7BH3fbLTV0ptHvpeMvrt3cPThHfJfst9Wrb7S8EvJ7vRTFI7z+VAvFVEQn/m5zQ==",
       "dev": true,
       "requires": {
-        "@babel/helper-module-imports": "^7.22.15",
-        "@babel/helper-plugin-utils": "^7.22.5",
-        "@babel/helper-remap-async-to-generator": "^7.22.20"
+        "@babel/helper-module-imports": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/helper-remap-async-to-generator": "^7.25.9"
       }
     },
     "@babel/plugin-transform-block-scoped-functions": {
@@ -17342,17 +17002,6 @@
         "@babel/helper-replace-supers": "^7.25.9",
         "@babel/traverse": "^7.25.9",
         "globals": "^11.1.0"
-      },
-      "dependencies": {
-        "@babel/helper-annotate-as-pure": {
-          "version": "7.25.9",
-          "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-          "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-          "dev": true,
-          "requires": {
-            "@babel/types": "^7.25.9"
-          }
-        }
       }
     },
     "@babel/plugin-transform-computed-properties": {
@@ -17393,6 +17042,16 @@
         "@babel/helper-plugin-utils": "^7.25.9"
       }
     },
+    "@babel/plugin-transform-duplicate-named-capturing-groups-regex": {
+      "version": "7.25.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-duplicate-named-capturing-groups-regex/-/plugin-transform-duplicate-named-capturing-groups-regex-7.25.9.tgz",
+      "integrity": "sha512-0UfuJS0EsXbRvKnwcLjFtJy/Sxc5J5jhLHnFhy7u4zih97Hz6tJkLU+O+FMMrNZrosUPxDi6sYxJ/EA8jDiAog==",
+      "dev": true,
+      "requires": {
+        "@babel/helper-create-regexp-features-plugin": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.25.9"
+      }
+    },
     "@babel/plugin-transform-dynamic-import": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-transform-dynamic-import/-/plugin-transform-dynamic-import-7.25.9.tgz",
@@ -17421,12 +17080,12 @@
       }
     },
     "@babel/plugin-transform-for-of": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.25.9.tgz",
-      "integrity": "sha512-LqHxduHoaGELJl2uhImHwRQudhCM50pT46rIBNvtT/Oql3nqiS3wOwP+5ten7NpYSXrrVLgtZU3DZmPtWZo16A==",
+      "version": "7.26.9",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-for-of/-/plugin-transform-for-of-7.26.9.tgz",
+      "integrity": "sha512-Hry8AusVm8LW5BVFgiyUReuoGzPUpdHQQqJY5bZnbbf+ngOHWuCuYFKw/BqaaWlvEUrF91HMhDtEaI1hZzNbLg==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.26.5",
         "@babel/helper-skip-transparent-expression-wrappers": "^7.25.9"
       }
     },
@@ -17624,17 +17283,6 @@
         "@babel/helper-annotate-as-pure": "^7.25.9",
         "@babel/helper-create-class-features-plugin": "^7.25.9",
         "@babel/helper-plugin-utils": "^7.25.9"
-      },
-      "dependencies": {
-        "@babel/helper-annotate-as-pure": {
-          "version": "7.25.9",
-          "resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.25.9.tgz",
-          "integrity": "sha512-gv7320KBUFJz1RnylIg5WWYPRXKZ884AGkYpgpWW02TH66Dl+HaC1t1CKd0z3R4b6hdYEcmrNZHUmfCP+1u3/g==",
-          "dev": true,
-          "requires": {
-            "@babel/types": "^7.25.9"
-          }
-        }
       }
     },
     "@babel/plugin-transform-property-literals": {
@@ -17656,6 +17304,16 @@
         "regenerator-transform": "^0.15.2"
       }
     },
+    "@babel/plugin-transform-regexp-modifiers": {
+      "version": "7.26.0",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-regexp-modifiers/-/plugin-transform-regexp-modifiers-7.26.0.tgz",
+      "integrity": "sha512-vN6saax7lrA2yA/Pak3sCxuD6F5InBjn9IcrIKQPjpsLvuHYLVroTxjdlVRHjjBWxKOqIwpTXDkOssYT4BFdRw==",
+      "dev": true,
+      "requires": {
+        "@babel/helper-create-regexp-features-plugin": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.25.9"
+      }
+    },
     "@babel/plugin-transform-reserved-words": {
       "version": "7.25.9",
       "resolved": "https://registry.npmjs.org/@babel/plugin-transform-reserved-words/-/plugin-transform-reserved-words-7.25.9.tgz",
@@ -17666,16 +17324,16 @@
       }
     },
     "@babel/plugin-transform-runtime": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.24.0.tgz",
-      "integrity": "sha512-zc0GA5IitLKJrSfXlXmp8KDqLrnGECK7YRfQBmEKg1NmBOQ7e+KuclBEKJgzifQeUYLdNiAw4B4bjyvzWVLiSA==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.26.10.tgz",
+      "integrity": "sha512-NWaL2qG6HRpONTnj4JvDU6th4jYeZOJgu3QhmFTCihib0ermtOJqktA5BduGm3suhhVe9EMP9c9+mfJ/I9slqw==",
       "dev": true,
       "requires": {
-        "@babel/helper-module-imports": "^7.22.15",
-        "@babel/helper-plugin-utils": "^7.24.0",
-        "babel-plugin-polyfill-corejs2": "^0.4.8",
-        "babel-plugin-polyfill-corejs3": "^0.9.0",
-        "babel-plugin-polyfill-regenerator": "^0.5.5",
+        "@babel/helper-module-imports": "^7.25.9",
+        "@babel/helper-plugin-utils": "^7.26.5",
+        "babel-plugin-polyfill-corejs2": "^0.4.10",
+        "babel-plugin-polyfill-corejs3": "^0.11.0",
+        "babel-plugin-polyfill-regenerator": "^0.6.1",
         "semver": "^6.3.1"
       },
       "dependencies": {
@@ -17716,21 +17374,21 @@
       }
     },
     "@babel/plugin-transform-template-literals": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.25.9.tgz",
-      "integrity": "sha512-o97AE4syN71M/lxrCtQByzphAdlYluKPDBzDVzMmfCobUjjhAryZV0AIpRPrxN0eAkxXO6ZLEScmt+PNhj2OTw==",
+      "version": "7.26.8",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-template-literals/-/plugin-transform-template-literals-7.26.8.tgz",
+      "integrity": "sha512-OmGDL5/J0CJPJZTHZbi2XpO0tyT2Ia7fzpW5GURwdtp2X3fMmN8au/ej6peC/T33/+CRiIpA8Krse8hFGVmT5Q==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.25.9"
+        "@babel/helper-plugin-utils": "^7.26.5"
       }
     },
     "@babel/plugin-transform-typeof-symbol": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.25.9.tgz",
-      "integrity": "sha512-v61XqUMiueJROUv66BVIOi0Fv/CUuZuZMl5NkRoCVxLAnMexZ0A3kMe7vvZ0nulxMuMp0Mk6S5hNh48yki08ZA==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/plugin-transform-typeof-symbol/-/plugin-transform-typeof-symbol-7.27.0.tgz",
+      "integrity": "sha512-+LLkxA9rKJpNoGsbLnAgOCdESl73vwYn+V6b+5wHbrE7OGKVDPHIQvbFSzqE6rwqaCw2RE+zdJrlLkcf8YOA0w==",
       "dev": true,
       "requires": {
-        "@babel/helper-plugin-utils": "^7.25.9"
+        "@babel/helper-plugin-utils": "^7.26.5"
       }
     },
     "@babel/plugin-transform-unicode-escapes": {
@@ -17773,90 +17431,79 @@
       }
     },
     "@babel/preset-env": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.24.0.tgz",
-      "integrity": "sha512-ZxPEzV9IgvGn73iK0E6VB9/95Nd7aMFpbE0l8KQFDG70cOV9IxRP7Y2FUPmlK0v6ImlLqYX50iuZ3ZTVhOF2lA==",
+      "version": "7.26.9",
+      "resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.26.9.tgz",
+      "integrity": "sha512-vX3qPGE8sEKEAZCWk05k3cpTAE3/nOYca++JA+Rd0z2NCNzabmYvEiSShKzm10zdquOIAVXsy2Ei/DTW34KlKQ==",
       "dev": true,
       "requires": {
-        "@babel/compat-data": "^7.23.5",
-        "@babel/helper-compilation-targets": "^7.23.6",
-        "@babel/helper-plugin-utils": "^7.24.0",
-        "@babel/helper-validator-option": "^7.23.5",
-        "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.23.3",
-        "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.23.3",
-        "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.23.7",
+        "@babel/compat-data": "^7.26.8",
+        "@babel/helper-compilation-targets": "^7.26.5",
+        "@babel/helper-plugin-utils": "^7.26.5",
+        "@babel/helper-validator-option": "^7.25.9",
+        "@babel/plugin-bugfix-firefox-class-in-computed-class-key": "^7.25.9",
+        "@babel/plugin-bugfix-safari-class-field-initializer-scope": "^7.25.9",
+        "@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.25.9",
+        "@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.25.9",
+        "@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.25.9",
         "@babel/plugin-proposal-private-property-in-object": "7.21.0-placeholder-for-preset-env.2",
-        "@babel/plugin-syntax-async-generators": "^7.8.4",
-        "@babel/plugin-syntax-class-properties": "^7.12.13",
-        "@babel/plugin-syntax-class-static-block": "^7.14.5",
-        "@babel/plugin-syntax-dynamic-import": "^7.8.3",
-        "@babel/plugin-syntax-export-namespace-from": "^7.8.3",
-        "@babel/plugin-syntax-import-assertions": "^7.23.3",
-        "@babel/plugin-syntax-import-attributes": "^7.23.3",
-        "@babel/plugin-syntax-import-meta": "^7.10.4",
-        "@babel/plugin-syntax-json-strings": "^7.8.3",
-        "@babel/plugin-syntax-logical-assignment-operators": "^7.10.4",
-        "@babel/plugin-syntax-nullish-coalescing-operator": "^7.8.3",
-        "@babel/plugin-syntax-numeric-separator": "^7.10.4",
-        "@babel/plugin-syntax-object-rest-spread": "^7.8.3",
-        "@babel/plugin-syntax-optional-catch-binding": "^7.8.3",
-        "@babel/plugin-syntax-optional-chaining": "^7.8.3",
-        "@babel/plugin-syntax-private-property-in-object": "^7.14.5",
-        "@babel/plugin-syntax-top-level-await": "^7.14.5",
+        "@babel/plugin-syntax-import-assertions": "^7.26.0",
+        "@babel/plugin-syntax-import-attributes": "^7.26.0",
         "@babel/plugin-syntax-unicode-sets-regex": "^7.18.6",
-        "@babel/plugin-transform-arrow-functions": "^7.23.3",
-        "@babel/plugin-transform-async-generator-functions": "^7.23.9",
-        "@babel/plugin-transform-async-to-generator": "^7.23.3",
-        "@babel/plugin-transform-block-scoped-functions": "^7.23.3",
-        "@babel/plugin-transform-block-scoping": "^7.23.4",
-        "@babel/plugin-transform-class-properties": "^7.23.3",
-        "@babel/plugin-transform-class-static-block": "^7.23.4",
-        "@babel/plugin-transform-classes": "^7.23.8",
-        "@babel/plugin-transform-computed-properties": "^7.23.3",
-        "@babel/plugin-transform-destructuring": "^7.23.3",
-        "@babel/plugin-transform-dotall-regex": "^7.23.3",
-        "@babel/plugin-transform-duplicate-keys": "^7.23.3",
-        "@babel/plugin-transform-dynamic-import": "^7.23.4",
-        "@babel/plugin-transform-exponentiation-operator": "^7.23.3",
-        "@babel/plugin-transform-export-namespace-from": "^7.23.4",
-        "@babel/plugin-transform-for-of": "^7.23.6",
-        "@babel/plugin-transform-function-name": "^7.23.3",
-        "@babel/plugin-transform-json-strings": "^7.23.4",
-        "@babel/plugin-transform-literals": "^7.23.3",
-        "@babel/plugin-transform-logical-assignment-operators": "^7.23.4",
-        "@babel/plugin-transform-member-expression-literals": "^7.23.3",
-        "@babel/plugin-transform-modules-amd": "^7.23.3",
-        "@babel/plugin-transform-modules-commonjs": "^7.23.3",
-        "@babel/plugin-transform-modules-systemjs": "^7.23.9",
-        "@babel/plugin-transform-modules-umd": "^7.23.3",
-        "@babel/plugin-transform-named-capturing-groups-regex": "^7.22.5",
-        "@babel/plugin-transform-new-target": "^7.23.3",
-        "@babel/plugin-transform-nullish-coalescing-operator": "^7.23.4",
-        "@babel/plugin-transform-numeric-separator": "^7.23.4",
-        "@babel/plugin-transform-object-rest-spread": "^7.24.0",
-        "@babel/plugin-transform-object-super": "^7.23.3",
-        "@babel/plugin-transform-optional-catch-binding": "^7.23.4",
-        "@babel/plugin-transform-optional-chaining": "^7.23.4",
-        "@babel/plugin-transform-parameters": "^7.23.3",
-        "@babel/plugin-transform-private-methods": "^7.23.3",
-        "@babel/plugin-transform-private-property-in-object": "^7.23.4",
-        "@babel/plugin-transform-property-literals": "^7.23.3",
-        "@babel/plugin-transform-regenerator": "^7.23.3",
-        "@babel/plugin-transform-reserved-words": "^7.23.3",
-        "@babel/plugin-transform-shorthand-properties": "^7.23.3",
-        "@babel/plugin-transform-spread": "^7.23.3",
-        "@babel/plugin-transform-sticky-regex": "^7.23.3",
-        "@babel/plugin-transform-template-literals": "^7.23.3",
-        "@babel/plugin-transform-typeof-symbol": "^7.23.3",
-        "@babel/plugin-transform-unicode-escapes": "^7.23.3",
-        "@babel/plugin-transform-unicode-property-regex": "^7.23.3",
-        "@babel/plugin-transform-unicode-regex": "^7.23.3",
-        "@babel/plugin-transform-unicode-sets-regex": "^7.23.3",
+        "@babel/plugin-transform-arrow-functions": "^7.25.9",
+        "@babel/plugin-transform-async-generator-functions": "^7.26.8",
+        "@babel/plugin-transform-async-to-generator": "^7.25.9",
+        "@babel/plugin-transform-block-scoped-functions": "^7.26.5",
+        "@babel/plugin-transform-block-scoping": "^7.25.9",
+        "@babel/plugin-transform-class-properties": "^7.25.9",
+        "@babel/plugin-transform-class-static-block": "^7.26.0",
+        "@babel/plugin-transform-classes": "^7.25.9",
+        "@babel/plugin-transform-computed-properties": "^7.25.9",
+        "@babel/plugin-transform-destructuring": "^7.25.9",
+        "@babel/plugin-transform-dotall-regex": "^7.25.9",
+        "@babel/plugin-transform-duplicate-keys": "^7.25.9",
+        "@babel/plugin-transform-duplicate-named-capturing-groups-regex": "^7.25.9",
+        "@babel/plugin-transform-dynamic-import": "^7.25.9",
+        "@babel/plugin-transform-exponentiation-operator": "^7.26.3",
+        "@babel/plugin-transform-export-namespace-from": "^7.25.9",
+        "@babel/plugin-transform-for-of": "^7.26.9",
+        "@babel/plugin-transform-function-name": "^7.25.9",
+        "@babel/plugin-transform-json-strings": "^7.25.9",
+        "@babel/plugin-transform-literals": "^7.25.9",
+        "@babel/plugin-transform-logical-assignment-operators": "^7.25.9",
+        "@babel/plugin-transform-member-expression-literals": "^7.25.9",
+        "@babel/plugin-transform-modules-amd": "^7.25.9",
+        "@babel/plugin-transform-modules-commonjs": "^7.26.3",
+        "@babel/plugin-transform-modules-systemjs": "^7.25.9",
+        "@babel/plugin-transform-modules-umd": "^7.25.9",
+        "@babel/plugin-transform-named-capturing-groups-regex": "^7.25.9",
+        "@babel/plugin-transform-new-target": "^7.25.9",
+        "@babel/plugin-transform-nullish-coalescing-operator": "^7.26.6",
+        "@babel/plugin-transform-numeric-separator": "^7.25.9",
+        "@babel/plugin-transform-object-rest-spread": "^7.25.9",
+        "@babel/plugin-transform-object-super": "^7.25.9",
+        "@babel/plugin-transform-optional-catch-binding": "^7.25.9",
+        "@babel/plugin-transform-optional-chaining": "^7.25.9",
+        "@babel/plugin-transform-parameters": "^7.25.9",
+        "@babel/plugin-transform-private-methods": "^7.25.9",
+        "@babel/plugin-transform-private-property-in-object": "^7.25.9",
+        "@babel/plugin-transform-property-literals": "^7.25.9",
+        "@babel/plugin-transform-regenerator": "^7.25.9",
+        "@babel/plugin-transform-regexp-modifiers": "^7.26.0",
+        "@babel/plugin-transform-reserved-words": "^7.25.9",
+        "@babel/plugin-transform-shorthand-properties": "^7.25.9",
+        "@babel/plugin-transform-spread": "^7.25.9",
+        "@babel/plugin-transform-sticky-regex": "^7.25.9",
+        "@babel/plugin-transform-template-literals": "^7.26.8",
+        "@babel/plugin-transform-typeof-symbol": "^7.26.7",
+        "@babel/plugin-transform-unicode-escapes": "^7.25.9",
+        "@babel/plugin-transform-unicode-property-regex": "^7.25.9",
+        "@babel/plugin-transform-unicode-regex": "^7.25.9",
+        "@babel/plugin-transform-unicode-sets-regex": "^7.25.9",
         "@babel/preset-modules": "0.1.6-no-external-plugins",
-        "babel-plugin-polyfill-corejs2": "^0.4.8",
-        "babel-plugin-polyfill-corejs3": "^0.9.0",
-        "babel-plugin-polyfill-regenerator": "^0.5.5",
-        "core-js-compat": "^3.31.0",
+        "babel-plugin-polyfill-corejs2": "^0.4.10",
+        "babel-plugin-polyfill-corejs3": "^0.11.0",
+        "babel-plugin-polyfill-regenerator": "^0.6.1",
+        "core-js-compat": "^3.40.0",
         "semver": "^6.3.1"
       },
       "dependencies": {
@@ -17880,64 +17527,58 @@
       }
     },
     "@babel/runtime": {
-      "version": "7.24.0",
-      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.24.0.tgz",
-      "integrity": "sha512-Chk32uHMg6TnQdvw2e9IlqPpFX/6NLuK0Ys2PqLb7/gL5uFn9mXvK715FGLlOLQrcO4qIkNHkvPGktzzXexsFw==",
+      "version": "7.26.10",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.26.10.tgz",
+      "integrity": "sha512-2WJMeRQPHKSPemqk/awGrAiuFfzBmOIPXKizAsVhWH9YJqLZ0H+HS4c8loHGgW6utJ3E/ejXQUsiGaQy2NZ9Fw==",
       "requires": {
         "regenerator-runtime": "^0.14.0"
       }
     },
     "@babel/template": {
-      "version": "7.25.9",
-      "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.25.9.tgz",
-      "integrity": "sha512-9DGttpmPvIxBb/2uwpVo3dqJ+O6RooAFOS+lB+xDqoE2PVCE8nfoHMdZLpfCQRLwvohzXISPZcgxt80xLfsuwg==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/template/-/template-7.27.0.tgz",
+      "integrity": "sha512-2ncevenBqXI6qRMukPlXwHKHchC7RyMuu4xv5JBXRfOGVcTy1mXCD12qrp7Jsoxll1EV3+9sE4GugBVRjT2jFA==",
       "dev": true,
       "requires": {
-        "@babel/code-frame": "^7.25.9",
-        "@babel/parser": "^7.25.9",
-        "@babel/types": "^7.25.9"
+        "@babel/code-frame": "^7.26.2",
+        "@babel/parser": "^7.27.0",
+        "@babel/types": "^7.27.0"
       }
     },
     "@babel/traverse": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.26.5.tgz",
-      "integrity": "sha512-rkOSPOw+AXbgtwUga3U4u8RpoK9FEFWBNAlTpcnkLFjL5CT+oyHNuUUC/xx6XefEJ16r38r8Bc/lfp6rYuHeJQ==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/traverse/-/traverse-7.27.0.tgz",
+      "integrity": "sha512-19lYZFzYVQkkHkl4Cy4WrAVcqBkgvV2YM2TU3xG6DIwO7O3ecbDPfW3yM3bjAGcqcQHi+CCtjMR3dIEHxsd6bA==",
       "dev": true,
       "requires": {
         "@babel/code-frame": "^7.26.2",
-        "@babel/generator": "^7.26.5",
-        "@babel/parser": "^7.26.5",
-        "@babel/template": "^7.25.9",
-        "@babel/types": "^7.26.5",
+        "@babel/generator": "^7.27.0",
+        "@babel/parser": "^7.27.0",
+        "@babel/template": "^7.27.0",
+        "@babel/types": "^7.27.0",
         "debug": "^4.3.1",
         "globals": "^11.1.0"
       },
       "dependencies": {
         "@babel/generator": {
-          "version": "7.26.5",
-          "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.26.5.tgz",
-          "integrity": "sha512-2caSP6fN9I7HOe6nqhtft7V4g7/V/gfDsC3Ag4W7kEzzvRGKqiv0pu0HogPiZ3KaVSoNDhUws6IJjDjpfmYIXw==",
+          "version": "7.27.0",
+          "resolved": "https://registry.npmjs.org/@babel/generator/-/generator-7.27.0.tgz",
+          "integrity": "sha512-VybsKvpiN1gU1sdMZIp7FcqphVVKEwcuj02x73uvcHE0PTihx1nlBcowYWhDwjpoAXRv43+gDzyggGnn1XZhVw==",
           "dev": true,
           "requires": {
-            "@babel/parser": "^7.26.5",
-            "@babel/types": "^7.26.5",
+            "@babel/parser": "^7.27.0",
+            "@babel/types": "^7.27.0",
             "@jridgewell/gen-mapping": "^0.3.5",
             "@jridgewell/trace-mapping": "^0.3.25",
             "jsesc": "^3.0.2"
           }
-        },
-        "jsesc": {
-          "version": "3.1.0",
-          "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz",
-          "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==",
-          "dev": true
         }
       }
     },
     "@babel/types": {
-      "version": "7.26.5",
-      "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.26.5.tgz",
-      "integrity": "sha512-L6mZmwFDK6Cjh1nRCLXpa6no13ZIioJDz7mdkzHv399pThrTa/k0nUlNaenOeh2kWu/iaOQYElEpKPUswUa9Vg==",
+      "version": "7.27.0",
+      "resolved": "https://registry.npmjs.org/@babel/types/-/types-7.27.0.tgz",
+      "integrity": "sha512-H45s8fVLYjbhFH62dIJ3WtmJ6RSPt/3DRO0ZcT2SUiYiQyz3BLVb9ADEnLl91m74aQPS3AzzeajZHYOalWe3bg==",
       "dev": true,
       "requires": {
         "@babel/helper-string-parser": "^7.25.9",
@@ -18126,9 +17767,9 @@
       }
     },
     "@formio/bootstrap": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/@formio/bootstrap/-/bootstrap-3.0.0.tgz",
-      "integrity": "sha512-9a2JMY/qU/UUQ3BvlxrZfAjy/v5unwkXXBdy98+MiUbmQVaLi8ITIsA/YeYkRKFQW8V6BSbOoTlJhmVvxdvPnA=="
+      "version": "3.0.2-rc.1",
+      "resolved": "https://registry.npmjs.org/@formio/bootstrap/-/bootstrap-3.0.2-rc.1.tgz",
+      "integrity": "sha512-CfwnU04l8yMc0kr1j2Y7mj193Z5BfqoNiCGBsTz1bDIr/tnaQkfEOZ21zJ15KVpCXVGc6SjW7QQ1JY8UVsE0lQ=="
     },
     "@formio/bootstrap3": {
       "version": "2.12.4-rc.1",
@@ -18150,9 +17791,9 @@
       }
     },
     "@formio/core": {
-      "version": "2.3.0",
-      "resolved": "https://registry.npmjs.org/@formio/core/-/core-2.3.0.tgz",
-      "integrity": "sha512-jAlNm0vaSZQ9RSxt79PqeHdXYv/1i+zNfasVWbH1xRJSicJK0JcdodrBaDw8kKnEh0UmflW6RyIiaMyDbww4Ug==",
+      "version": "2.3.3",
+      "resolved": "https://registry.npmjs.org/@formio/core/-/core-2.3.3.tgz",
+      "integrity": "sha512-Tgv5FEwEf9xQtl/cqviaWyBCFcwGCb1pVXwTjIH7KxtWMwsyXtbxGotjfFyZY9unOw6Snk2ik/sln80yQe5y9A==",
       "requires": {
         "@types/json-logic-js": "^2.0.7",
         "browser-cookies": "^1.2.0",
@@ -18176,14 +17817,14 @@
       }
     },
     "@formio/js": {
-      "version": "5.0.0",
-      "resolved": "https://registry.npmjs.org/@formio/js/-/js-5.0.0.tgz",
-      "integrity": "sha512-Ly3f7q2wo5oFjlECKFtkIMy+Ah9HyAkf6ob70OrF/6MooSPF3hEu9euXouEWOoNdI+Tokr690/GdM2sDZtYzww==",
+      "version": "5.0.2",
+      "resolved": "https://registry.npmjs.org/@formio/js/-/js-5.0.2.tgz",
+      "integrity": "sha512-zAuCUuxBPCJ7Nmt8+xPE5XyLkVg550a//I9ke8bhI7EGlRkN6xF1Ve7Nomsi8ruohiw2BVcMH+5SS3LXWUm0uQ==",
       "requires": {
-        "@formio/bootstrap": "3.0.0",
+        "@formio/bootstrap": "3.0.2-rc.1",
         "@formio/choices.js": "^10.2.1",
-        "@formio/core": "2.3.0",
-        "@formio/text-mask-addons": "^3.8.0-formio.3",
+        "@formio/core": "2.3.3",
+        "@formio/text-mask-addons": "3.8.0-formio.4",
         "@formio/vanilla-text-mask": "^5.1.1-formio.1",
         "abortcontroller-polyfill": "^1.7.5",
         "autocompleter": "^8.0.4",
@@ -18223,9 +17864,9 @@
           "integrity": "sha512-q334YswwucSBphN5djVkEt3beVhHotrCtPGNIXmyilw9UnXV9Cb+gNAZ2yhZSfiBSzP6rxHLLT2gpr57xgbcwQ=="
         },
         "bootstrap": {
-          "version": "5.3.3",
-          "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.3.tgz",
-          "integrity": "sha512-8HLCdWgyoMguSO9o+aH+iuZ+aht+mzW0u3HIMzVu7Srrpv7EBBxTnrFlSCskwdY1+EOFQSm7uMJhNQHkdPcmjg==",
+          "version": "5.3.5",
+          "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-5.3.5.tgz",
+          "integrity": "sha512-ct1CHKtiobRimyGzmsSldEtM03E8fcEX4Tb3dGXz1V8faRwM50+vfHwTzOxB3IlKO7m+9vTH3s/3C6T2EAPeTA==",
           "requires": {}
         },
         "compare-versions": {
@@ -18401,6 +18042,11 @@
       "resolved": "https://registry.npmjs.org/@juggle/resize-observer/-/resize-observer-3.4.0.tgz",
       "integrity": "sha512-dfLbk+PwWvFzSxwk3n5ySL0hfBog779o8h68wK/7/APo/7cgyWp5jcXockbxdk5kFRkbeXWm4Fbi9FrdN381sA=="
     },
+    "@kurkle/color": {
+      "version": "0.3.4",
+      "resolved": "https://registry.npmjs.org/@kurkle/color/-/color-0.3.4.tgz",
+      "integrity": "sha512-M5UknZPHRu3DEDWoipU6sE8PdkZ6Z/S+v4dD+Ke8IaNlpdSQah50lz1KtcFBa2vsdOnwbbnxJwVM4wty6udA5w=="
+    },
     "@leichtgewicht/ip-codec": {
       "version": "2.0.5",
       "resolved": "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.5.tgz",
@@ -18417,9 +18063,9 @@
       }
     },
     "@ngtools/webpack": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@ngtools/webpack/-/webpack-17.3.11.tgz",
-      "integrity": "sha512-SfTCbplt4y6ak5cf2IfqdoVOsnoNdh/j6Vu+wb8WWABKwZ5yfr2S/Gk6ithSKcdIZhAF8DNBOoyk1EJuf8Xkfg==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@ngtools/webpack/-/webpack-17.3.16.tgz",
+      "integrity": "sha512-Wxtiut1o9rj3+HumyXoYWg4iCuPDEt4nf1Y9bRCo3y5evEKp0ZTO7IFPpZLaZ0JGGrpROiQErjvHdDQBOuXwWQ==",
       "dev": true,
       "requires": {}
     },
@@ -18432,9 +18078,9 @@
       }
     },
     "@ngx-translate/http-loader": {
-      "version": "7.0.0",
-      "resolved": "https://registry.npmjs.org/@ngx-translate/http-loader/-/http-loader-7.0.0.tgz",
-      "integrity": "sha512-j+NpXXlcGVdyUNyY/qsJrqqeAdJdizCd+GKh3usXExSqy1aE9866jlAIL+xrfDU4w+LiMoma5pgE4emvFebZmA==",
+      "version": "16.0.1",
+      "resolved": "https://registry.npmjs.org/@ngx-translate/http-loader/-/http-loader-16.0.1.tgz",
+      "integrity": "sha512-xJEOUpvs6Zfc8G4cmQmegFOEpfYSoplTHHoisPNrATXjRBjpaKsBaPOXlZsuFUW2XV00s16gIyI4+9z1XkO5bw==",
       "requires": {
         "tslib": "^2.3.0"
       }
@@ -18832,13 +18478,13 @@
       "optional": true
     },
     "@schematics/angular": {
-      "version": "17.3.11",
-      "resolved": "https://registry.npmjs.org/@schematics/angular/-/angular-17.3.11.tgz",
-      "integrity": "sha512-tvJpTgYC+hCnTyLszYRUZVyNTpPd+C44gh5CPTcG3qkqStzXQwynQAf6X/DjtwXbUiPQF0XfF0+0R489GpdZPA==",
+      "version": "17.3.16",
+      "resolved": "https://registry.npmjs.org/@schematics/angular/-/angular-17.3.16.tgz",
+      "integrity": "sha512-Ts/cAZmxlIL+AOLbmBylCMjXdHeqWZE2IIYmP5334tQNERSharOlKbLIz5PeESmBDGpH9KRa0wSMK5KXI5ixnQ==",
       "dev": true,
       "requires": {
-        "@angular-devkit/core": "17.3.11",
-        "@angular-devkit/schematics": "17.3.11",
+        "@angular-devkit/core": "17.3.16",
+        "@angular-devkit/schematics": "17.3.16",
         "jsonc-parser": "3.2.1"
       }
     },
@@ -19091,9 +18737,9 @@
       }
     },
     "@types/jasmine": {
-      "version": "3.6.11",
-      "resolved": "https://registry.npmjs.org/@types/jasmine/-/jasmine-3.6.11.tgz",
-      "integrity": "sha512-S6pvzQDvMZHrkBz2Mcn/8Du7cpr76PlRJBAoHnSDNbulULsH5dp0Gns+WRyNX5LHejz/ljxK4/vIHK/caHt6SQ==",
+      "version": "5.1.7",
+      "resolved": "https://registry.npmjs.org/@types/jasmine/-/jasmine-5.1.7.tgz",
+      "integrity": "sha512-DVOfk9FaClQfNFpSfaML15jjB5cjffDMvjtph525sroR5BEAW2uKnTOYUTqTFuZFjNvH0T5XMIydvIctnUKufw==",
       "dev": true
     },
     "@types/json-logic-js": {
@@ -19158,9 +18804,9 @@
       "dev": true
     },
     "@types/semver": {
-      "version": "7.3.8",
-      "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.3.8.tgz",
-      "integrity": "sha512-D/2EJvAlCEtYFEYmmlGwbGXuK886HzyCc3nZX/tkFTQdEU8jZDAgiv08P162yB17y4ZXZoq7yFAnW4GDBb9Now=="
+      "version": "7.7.0",
+      "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.7.0.tgz",
+      "integrity": "sha512-k107IF4+Xr7UHjwDc7Cfd6PRQfbdkiRabXGRjo07b4WyPahFBZCZ1sE+BNxYIJPPg73UkfOsVOLwqVc/6ETrIA=="
     },
     "@types/send": {
       "version": "0.17.4",
@@ -19237,9 +18883,9 @@
       }
     },
     "@types/zxcvbn": {
-      "version": "4.4.1",
-      "resolved": "https://registry.npmjs.org/@types/zxcvbn/-/zxcvbn-4.4.1.tgz",
-      "integrity": "sha512-3NoqvZC2W5gAC5DZbTpCeJ251vGQmgcWIHQJGq2J240HY6ErQ9aWKkwfoKJlHLx+A83WPNTZ9+3cd2ILxbvr1w=="
+      "version": "4.4.5",
+      "resolved": "https://registry.npmjs.org/@types/zxcvbn/-/zxcvbn-4.4.5.tgz",
+      "integrity": "sha512-FZJgC5Bxuqg7Rhsm/bx6gAruHHhDQ55r+s0JhDh8CQ16fD7NsJJ+p8YMMQDhSQoIrSmjpqqYWA96oQVMNkjRyA=="
     },
     "@webassemblyjs/ast": {
       "version": "1.14.1",
@@ -19417,17 +19063,17 @@
       "dev": true
     },
     "@zxcvbn-ts/core": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/core/-/core-3.0.0.tgz",
-      "integrity": "sha512-AuuYc66+5csSLd/mJ1CXuTUsjLdYw4X0zh8WvDCLztTOye0b+HrKCu8WzAEmq6Ja1u+cSbCNrKLW7m4ZCeg0FA==",
+      "version": "3.0.4",
+      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/core/-/core-3.0.4.tgz",
+      "integrity": "sha512-aQeiT0F09FuJaAqNrxynlAwZ2mW/1MdXakKWNmGM1Qp/VaY6CnB/GfnMS2T8gB2231Esp1/maCWd8vTG4OuShw==",
       "requires": {
         "fastest-levenshtein": "1.0.16"
       }
     },
     "@zxcvbn-ts/language-en": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/language-en/-/language-en-3.0.0.tgz",
-      "integrity": "sha512-JJ0H3ovVIO4EEpYXk5qq6NbxyZ8b3/qkpwEFIOu0m8bb54vXtRy2EbdfzUm0XKdtw9gfx15MaHAn0pWv0hTzYg=="
+      "version": "3.0.2",
+      "resolved": "https://registry.npmjs.org/@zxcvbn-ts/language-en/-/language-en-3.0.2.tgz",
+      "integrity": "sha512-Zp+zL+I6Un2Bj0tRXNs6VUBq3Djt+hwTwUz4dkt2qgsQz47U0/XthZ4ULrT/RxjwJRl5LwiaKOOZeOtmixHnjg=="
     },
     "abbrev": {
       "version": "2.0.0",
@@ -19509,14 +19155,14 @@
       }
     },
     "ajv": {
-      "version": "6.12.6",
-      "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
-      "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+      "version": "8.17.1",
+      "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz",
+      "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==",
       "requires": {
-        "fast-deep-equal": "^3.1.1",
-        "fast-json-stable-stringify": "^2.0.0",
-        "json-schema-traverse": "^0.4.1",
-        "uri-js": "^4.2.2"
+        "fast-deep-equal": "^3.1.3",
+        "fast-uri": "^3.0.1",
+        "json-schema-traverse": "^1.0.0",
+        "require-from-string": "^2.0.2"
       }
     },
     "ajv-formats": {
@@ -19526,26 +19172,6 @@
       "dev": true,
       "requires": {
         "ajv": "^8.0.0"
-      },
-      "dependencies": {
-        "ajv": {
-          "version": "8.12.0",
-          "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.12.0.tgz",
-          "integrity": "sha512-sRu1kpcO9yLtYxBKvqfTeh9KzZEwO3STyX1HT+4CaDzC6HpTGYhIhPIzj9XuKU7KYDwnaeh5hcOwjy1QuJzBPA==",
-          "dev": true,
-          "requires": {
-            "fast-deep-equal": "^3.1.1",
-            "json-schema-traverse": "^1.0.0",
-            "require-from-string": "^2.0.2",
-            "uri-js": "^4.2.2"
-          }
-        },
-        "json-schema-traverse": {
-          "version": "1.0.0",
-          "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
-          "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
-          "dev": true
-        }
       }
     },
     "ajv-keywords": {
@@ -19787,27 +19413,6 @@
         "@istanbuljs/schema": "^0.1.2",
         "istanbul-lib-instrument": "^5.0.4",
         "test-exclude": "^6.0.0"
-      },
-      "dependencies": {
-        "istanbul-lib-instrument": {
-          "version": "5.2.1",
-          "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-5.2.1.tgz",
-          "integrity": "sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==",
-          "dev": true,
-          "requires": {
-            "@babel/core": "^7.12.3",
-            "@babel/parser": "^7.14.7",
-            "@istanbuljs/schema": "^0.1.2",
-            "istanbul-lib-coverage": "^3.2.0",
-            "semver": "^6.3.0"
-          }
-        },
-        "semver": {
-          "version": "6.3.1",
-          "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
-          "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==",
-          "dev": true
-        }
       }
     },
     "babel-plugin-polyfill-corejs2": {
@@ -19830,52 +19435,22 @@
       }
     },
     "babel-plugin-polyfill-corejs3": {
-      "version": "0.9.0",
-      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.9.0.tgz",
-      "integrity": "sha512-7nZPG1uzK2Ymhy/NbaOWTg3uibM2BmGASS4vHS4szRZAIR8R6GwA/xAujpdrXU5iyklrimWnLWU+BLF9suPTqg==",
+      "version": "0.11.1",
+      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-corejs3/-/babel-plugin-polyfill-corejs3-0.11.1.tgz",
+      "integrity": "sha512-yGCqvBT4rwMczo28xkH/noxJ6MZ4nJfkVYdoDaC/utLtWrXxv27HVrzAeSbqR8SxDsp46n0YF47EbHoixy6rXQ==",
       "dev": true,
       "requires": {
-        "@babel/helper-define-polyfill-provider": "^0.5.0",
-        "core-js-compat": "^3.34.0"
-      },
-      "dependencies": {
-        "@babel/helper-define-polyfill-provider": {
-          "version": "0.5.0",
-          "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.5.0.tgz",
-          "integrity": "sha512-NovQquuQLAQ5HuyjCz7WQP9MjRj7dx++yspwiyUiGl9ZyadHRSql1HZh5ogRd8W8w6YM6EQ/NTB8rgjLt5W65Q==",
-          "dev": true,
-          "requires": {
-            "@babel/helper-compilation-targets": "^7.22.6",
-            "@babel/helper-plugin-utils": "^7.22.5",
-            "debug": "^4.1.1",
-            "lodash.debounce": "^4.0.8",
-            "resolve": "^1.14.2"
-          }
-        }
+        "@babel/helper-define-polyfill-provider": "^0.6.3",
+        "core-js-compat": "^3.40.0"
       }
     },
     "babel-plugin-polyfill-regenerator": {
-      "version": "0.5.5",
-      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.5.5.tgz",
-      "integrity": "sha512-OJGYZlhLqBh2DDHeqAxWB1XIvr49CxiJ2gIt61/PU55CQK4Z58OzMqjDe1zwQdQk+rBYsRc+1rJmdajM3gimHg==",
+      "version": "0.6.4",
+      "resolved": "https://registry.npmjs.org/babel-plugin-polyfill-regenerator/-/babel-plugin-polyfill-regenerator-0.6.4.tgz",
+      "integrity": "sha512-7gD3pRadPrbjhjLyxebmx/WrFYcuSjZ0XbdUujQMZ/fcE9oeewk2U/7PCvez84UeuK3oSjmPZ0Ch0dlupQvGzw==",
       "dev": true,
       "requires": {
-        "@babel/helper-define-polyfill-provider": "^0.5.0"
-      },
-      "dependencies": {
-        "@babel/helper-define-polyfill-provider": {
-          "version": "0.5.0",
-          "resolved": "https://registry.npmjs.org/@babel/helper-define-polyfill-provider/-/helper-define-polyfill-provider-0.5.0.tgz",
-          "integrity": "sha512-NovQquuQLAQ5HuyjCz7WQP9MjRj7dx++yspwiyUiGl9ZyadHRSql1HZh5ogRd8W8w6YM6EQ/NTB8rgjLt5W65Q==",
-          "dev": true,
-          "requires": {
-            "@babel/helper-compilation-targets": "^7.22.6",
-            "@babel/helper-plugin-utils": "^7.22.5",
-            "debug": "^4.1.1",
-            "lodash.debounce": "^4.0.8",
-            "resolve": "^1.14.2"
-          }
-        }
+        "@babel/helper-define-polyfill-provider": "^0.6.4"
       }
     },
     "balanced-match": {
@@ -20278,6 +19853,14 @@
       "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==",
       "dev": true
     },
+    "chart.js": {
+      "version": "4.4.9",
+      "resolved": "https://registry.npmjs.org/chart.js/-/chart.js-4.4.9.tgz",
+      "integrity": "sha512-EyZ9wWKgpAU0fLJ43YAEIF8sr5F2W3LqbS40ZJyHIner2lY14ufqv2VMp69MAiZ2rpwxEUxEhIH/0U3xyRynxg==",
+      "requires": {
+        "@kurkle/color": "^0.3.0"
+      }
+    },
     "chokidar": {
       "version": "3.5.3",
       "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz",
@@ -20705,12 +20288,12 @@
       "integrity": "sha512-7vsMc/Lty6AGnn7uFpYT56QesI5D2Y/UkgKounk87OP9Z2H9Z8kj6jzcSGAxFmUtDOS0ntK6lbQz+Nsa0Jj6mQ=="
     },
     "core-js-compat": {
-      "version": "3.40.0",
-      "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.40.0.tgz",
-      "integrity": "sha512-0XEDpr5y5mijvw8Lbc6E5AkjrHfp7eEoPlu36SWeAbcL8fn1G1ANe8DBlo2XoNN89oVpxWwOjYIPVzR4ZvsKCQ==",
+      "version": "3.41.0",
+      "resolved": "https://registry.npmjs.org/core-js-compat/-/core-js-compat-3.41.0.tgz",
+      "integrity": "sha512-RFsU9LySVue9RTwdDVX/T0e2Y6jRYWXERKElIjpuEOEnxaXffI0X7RUwVzfYLfzuLXSNJDYoRYUAmRUcyln20A==",
       "dev": true,
       "requires": {
-        "browserslist": "^4.24.3"
+        "browserslist": "^4.24.4"
       }
     },
     "core-util-is": {
@@ -21790,13 +21373,13 @@
     "fast-json-stable-stringify": {
       "version": "2.1.0",
       "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz",
-      "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw=="
+      "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==",
+      "dev": true
     },
     "fast-uri": {
       "version": "3.0.5",
       "resolved": "https://registry.npmjs.org/fast-uri/-/fast-uri-3.0.5.tgz",
-      "integrity": "sha512-5JnBCWpFlMo0a3ciDy/JckMzzv1U9coZrIhedq+HXxxUfDTAiS0LA8OKVao4G9BxmCVck/jtA5r3KAtRWEyD8Q==",
-      "dev": true
+      "integrity": "sha512-5JnBCWpFlMo0a3ciDy/JckMzzv1U9coZrIhedq+HXxxUfDTAiS0LA8OKVao4G9BxmCVck/jtA5r3KAtRWEyD8Q=="
     },
     "fastest-levenshtein": {
       "version": "1.0.16",
@@ -22219,6 +21802,26 @@
       "requires": {
         "ajv": "^6.12.3",
         "har-schema": "^2.0.0"
+      },
+      "dependencies": {
+        "ajv": {
+          "version": "6.12.6",
+          "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+          "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+          "dev": true,
+          "requires": {
+            "fast-deep-equal": "^3.1.1",
+            "fast-json-stable-stringify": "^2.0.0",
+            "json-schema-traverse": "^0.4.1",
+            "uri-js": "^4.2.2"
+          }
+        },
+        "json-schema-traverse": {
+          "version": "0.4.1",
+          "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
+          "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==",
+          "dev": true
+        }
       }
     },
     "has-ansi": {
@@ -22892,14 +22495,15 @@
       "dev": true
     },
     "istanbul-lib-instrument": {
-      "version": "4.0.3",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-4.0.3.tgz",
-      "integrity": "sha512-BXgQl9kf4WTCPCCpmFGoJkz/+uhvm7h7PFKUYxh7qarQd3ER33vHG//qaE8eN25l07YqZPpHXU9I09l/RD5aGQ==",
+      "version": "5.2.1",
+      "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-5.2.1.tgz",
+      "integrity": "sha512-pzqtp31nLv/XFOzXGuvhCb8qhjmTVo5vjVk19XE4CRlSWz0KoeJ3bw9XsA7nOp9YBf4qHjwBxkDzKcME/J29Yg==",
       "dev": true,
       "requires": {
-        "@babel/core": "^7.7.5",
+        "@babel/core": "^7.12.3",
+        "@babel/parser": "^7.14.7",
         "@istanbuljs/schema": "^0.1.2",
-        "istanbul-lib-coverage": "^3.0.0",
+        "istanbul-lib-coverage": "^3.2.0",
         "semver": "^6.3.0"
       },
       "dependencies": {
@@ -22940,9 +22544,9 @@
       }
     },
     "istanbul-lib-source-maps": {
-      "version": "4.0.0",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-4.0.0.tgz",
-      "integrity": "sha512-c16LpFRkR8vQXyHZ5nLpY35JZtzj1PQY1iZmesUbf1FZHbIupcWfjgOXBY9YHkLEQ6puz1u4Dgj6qmU/DisrZg==",
+      "version": "4.0.1",
+      "resolved": "https://registry.npmjs.org/istanbul-lib-source-maps/-/istanbul-lib-source-maps-4.0.1.tgz",
+      "integrity": "sha512-n3s8EwkdFIJCG3BPKBYvskgXGoy88ARzvegkitk60NxRdwltLOTaH7CUiMRXvwYorl0Q712iEjcWB+fK/MrWVw==",
       "dev": true,
       "requires": {
         "debug": "^4.1.1",
@@ -22959,9 +22563,9 @@
       }
     },
     "istanbul-reports": {
-      "version": "3.0.2",
-      "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.0.2.tgz",
-      "integrity": "sha512-9tZvz7AiR3PEDNGiV9vIouQ/EAcqMXFmkcA1CDFTwOB98OZVDL0PH9glHotf5Ugp6GCOTypfzGWI/OqjWNCRUw==",
+      "version": "3.1.7",
+      "resolved": "https://registry.npmjs.org/istanbul-reports/-/istanbul-reports-3.1.7.tgz",
+      "integrity": "sha512-BewmUXImeuRk2YY0PVbxgKAysvhRPUQE0h5QRM++nVWyubKGV0l8qQ5op8+B2DOmwSe63Jivj0BjkPQVf8fP5g==",
       "dev": true,
       "requires": {
         "html-escaper": "^2.0.0",
@@ -22998,9 +22602,9 @@
       }
     },
     "jasmine-core": {
-      "version": "4.6.0",
-      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.6.0.tgz",
-      "integrity": "sha512-O236+gd0ZXS8YAjFx8xKaJ94/erqUliEkJTDedyE7iHvv4ZVqi+q+8acJxu05/WJDKm512EUNn809In37nWlAQ==",
+      "version": "4.6.1",
+      "resolved": "https://registry.npmjs.org/jasmine-core/-/jasmine-core-4.6.1.tgz",
+      "integrity": "sha512-VYz/BjjmC3klLJlLwA4Kw8ytk0zDSmbbDLNs794VnWmkcCB7I9aAL/D48VNQtmITyPvea2C3jdUMfc3kAoy0PQ==",
       "dev": true
     },
     "jasmine-spec-reporter": {
@@ -23062,9 +22666,9 @@
       "dev": true
     },
     "jquery": {
-      "version": "3.6.0",
-      "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.6.0.tgz",
-      "integrity": "sha512-JVzAR/AjBvVt2BmYhxRCSYysDsPcssdmTFnzyLEts9qNwmjmu4JTAMYubEfwVOSwpQ1I1sKKFcxhZCI2buerfw=="
+      "version": "3.7.1",
+      "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.7.1.tgz",
+      "integrity": "sha512-m4avr8yL8kmFN8psrbFFFmB/If14iN5o9nw/NgnnM+kybDJpRsAynV2BsfpTYrTRysYUdADVD7CkUUizgkpLfg=="
     },
     "js-tokens": {
       "version": "4.0.0",
@@ -23089,9 +22693,9 @@
       "dev": true
     },
     "jsesc": {
-      "version": "2.5.2",
-      "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-2.5.2.tgz",
-      "integrity": "sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==",
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-3.1.0.tgz",
+      "integrity": "sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==",
       "dev": true
     },
     "json-logic-js": {
@@ -23112,9 +22716,9 @@
       "dev": true
     },
     "json-schema-traverse": {
-      "version": "0.4.1",
-      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
-      "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg=="
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
+      "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug=="
     },
     "json-stringify-safe": {
       "version": "5.0.1",
@@ -23210,9 +22814,9 @@
       "integrity": "sha512-UfpWE/VZn0iP50d8cz9NrZLM9lSWhcJ+0Gt/nm4by88UL+J1SiKN8/5dkjMmbEzwL2CAe+67GsegCbIKtbp75A=="
     },
     "karma": {
-      "version": "6.4.1",
-      "resolved": "https://registry.npmjs.org/karma/-/karma-6.4.1.tgz",
-      "integrity": "sha512-Cj57NKOskK7wtFWSlMvZf459iX+kpYIPXmkNUzP2WAFcA7nhr/ALn5R7sw3w+1udFDcpMx/tuB8d5amgm3ijaA==",
+      "version": "6.4.4",
+      "resolved": "https://registry.npmjs.org/karma/-/karma-6.4.4.tgz",
+      "integrity": "sha512-LrtUxbdvt1gOpo3gxG+VAJlJAEMhbWlM4YrFQgql98FwF7+K8K12LYO4hnDdUkNjeztYrOXEMqgTajSWgmtI/w==",
       "dev": true,
       "requires": {
         "@colors/colors": "1.5.0",
@@ -23234,38 +22838,13 @@
         "qjobs": "^1.2.0",
         "range-parser": "^1.2.1",
         "rimraf": "^3.0.2",
-        "socket.io": "^4.4.1",
+        "socket.io": "^4.7.2",
         "source-map": "^0.6.1",
         "tmp": "^0.2.1",
         "ua-parser-js": "^0.7.30",
         "yargs": "^16.1.1"
       },
       "dependencies": {
-        "glob": {
-          "version": "7.2.3",
-          "resolved": "https://registry.npmjs.org/glob/-/glob-7.2.3.tgz",
-          "integrity": "sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==",
-          "dev": true,
-          "requires": {
-            "fs.realpath": "^1.0.0",
-            "inflight": "^1.0.4",
-            "inherits": "2",
-            "minimatch": "^3.1.1",
-            "once": "^1.3.0",
-            "path-is-absolute": "^1.0.0"
-          },
-          "dependencies": {
-            "minimatch": {
-              "version": "3.1.2",
-              "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.1.2.tgz",
-              "integrity": "sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==",
-              "dev": true,
-              "requires": {
-                "brace-expansion": "^1.1.7"
-              }
-            }
-          }
-        },
         "mkdirp": {
           "version": "0.5.6",
           "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.6.tgz",
@@ -23282,20 +22861,17 @@
           "dev": true
         },
         "tmp": {
-          "version": "0.2.1",
-          "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz",
-          "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==",
-          "dev": true,
-          "requires": {
-            "rimraf": "^3.0.0"
-          }
+          "version": "0.2.3",
+          "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.3.tgz",
+          "integrity": "sha512-nZD7m9iCPC5g0pYmcaxogYKggSfLsdxl8of3Q/oIbqCqLLIO9IAF0GWjX1z9NZRHPiXv8Wex4yDCaZsgEw0Y8w==",
+          "dev": true
         }
       }
     },
     "karma-chrome-launcher": {
-      "version": "3.1.0",
-      "resolved": "https://registry.npmjs.org/karma-chrome-launcher/-/karma-chrome-launcher-3.1.0.tgz",
-      "integrity": "sha512-3dPs/n7vgz1rxxtynpzZTvb9y/GIaW8xjAwcIGttLbycqoFtI7yo1NGnQi6oFTherRE+GIhCAHZC4vEqWGhNvg==",
+      "version": "3.2.0",
+      "resolved": "https://registry.npmjs.org/karma-chrome-launcher/-/karma-chrome-launcher-3.2.0.tgz",
+      "integrity": "sha512-rE9RkUPI7I9mAxByQWkGJFXfFD6lE4gC5nPuZdobf/QdTEJI6EU4yIay/cfU/xV4ZxlM5JiTv7zWYgA64NpS5Q==",
       "dev": true,
       "requires": {
         "which": "^1.2.1"
@@ -23311,23 +22887,23 @@
       }
     },
     "karma-coverage": {
-      "version": "2.0.3",
-      "resolved": "https://registry.npmjs.org/karma-coverage/-/karma-coverage-2.0.3.tgz",
-      "integrity": "sha512-atDvLQqvPcLxhED0cmXYdsPMCQuh6Asa9FMZW1bhNqlVEhJoB9qyZ2BY1gu7D/rr5GLGb5QzYO4siQskxaWP/g==",
+      "version": "2.2.1",
+      "resolved": "https://registry.npmjs.org/karma-coverage/-/karma-coverage-2.2.1.tgz",
+      "integrity": "sha512-yj7hbequkQP2qOSb20GuNSIyE//PgJWHwC2IydLE6XRtsnaflv+/OSGNssPjobYUlhVVagy99TQpqUt3vAUG7A==",
       "dev": true,
       "requires": {
-        "istanbul-lib-coverage": "^3.0.0",
-        "istanbul-lib-instrument": "^4.0.1",
+        "istanbul-lib-coverage": "^3.2.0",
+        "istanbul-lib-instrument": "^5.1.0",
         "istanbul-lib-report": "^3.0.0",
-        "istanbul-lib-source-maps": "^4.0.0",
-        "istanbul-reports": "^3.0.0",
+        "istanbul-lib-source-maps": "^4.0.1",
+        "istanbul-reports": "^3.0.5",
         "minimatch": "^3.0.4"
       }
     },
     "karma-jasmine": {
-      "version": "4.0.1",
-      "resolved": "https://registry.npmjs.org/karma-jasmine/-/karma-jasmine-4.0.1.tgz",
-      "integrity": "sha512-h8XDAhTiZjJKzfkoO1laMH+zfNlra+dEQHUAjpn5JV1zCPtOIVWGQjLBrqhnzQa/hrU2XrZwSyBa6XjEBzfXzw==",
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/karma-jasmine/-/karma-jasmine-4.0.2.tgz",
+      "integrity": "sha512-ggi84RMNQffSDmWSyyt4zxzh2CQGwsxvYYsprgyR1j8ikzIduEdOlcLvXjZGwXG/0j41KUXOWsUCBfbEHPWP9g==",
       "dev": true,
       "requires": {
         "jasmine-core": "^3.6.0"
@@ -23627,6 +23203,7 @@
       "version": "6.0.0",
       "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz",
       "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==",
+      "dev": true,
       "requires": {
         "yallist": "^4.0.0"
       }
@@ -24891,9 +24468,9 @@
       "integrity": "sha512-zaOq3YvcOYytbAmKv3zYc+0VNS9Wg5d37dfxZnveKBFPr7vEIwfV5ydrpiouTft8MVW6qNjfkaQphHSnvgQbpQ=="
     },
     "primeicons": {
-      "version": "6.0.1",
-      "resolved": "https://registry.npmjs.org/primeicons/-/primeicons-6.0.1.tgz",
-      "integrity": "sha512-KDeO94CbWI4pKsPnYpA1FPjo79EsY9I+M8ywoPBSf9XMXoe/0crjbUK7jcQEDHuc0ZMRIZsxH3TYLv4TUtHmAA=="
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/primeicons/-/primeicons-7.0.0.tgz",
+      "integrity": "sha512-jK3Et9UzwzTsd6tzl2RmwrVY/b8raJ3QZLzoDACj+oTJ0oX7L9Hy+XnVwgo4QVKlKpnP/Ur13SXV/pVh4LzaDw=="
     },
     "primeng": {
       "version": "17.18.15",
@@ -25175,7 +24752,8 @@
     "punycode": {
       "version": "2.3.1",
       "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz",
-      "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg=="
+      "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==",
+      "dev": true
     },
     "puppeteer": {
       "version": "1.20.0",
@@ -25537,8 +25115,7 @@
     "require-from-string": {
       "version": "2.0.2",
       "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz",
-      "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==",
-      "dev": true
+      "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw=="
     },
     "require-main-filename": {
       "version": "2.0.0",
@@ -25689,9 +25266,9 @@
       }
     },
     "rxjs": {
-      "version": "7.8.1",
-      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
-      "integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
+      "version": "7.8.2",
+      "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.2.tgz",
+      "integrity": "sha512-dhKf903U/PQZY6boNNtAGdWbG85WAbjT/1xYoZIC7FAY0yWapOBQVsVrDl58W86//e1VpMNBtRV4MaXfdMySFA==",
       "requires": {
         "tslib": "^2.1.0"
       }
@@ -25785,18 +25362,6 @@
         "ajv-keywords": "^5.1.0"
       },
       "dependencies": {
-        "ajv": {
-          "version": "8.17.1",
-          "resolved": "https://registry.npmjs.org/ajv/-/ajv-8.17.1.tgz",
-          "integrity": "sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==",
-          "dev": true,
-          "requires": {
-            "fast-deep-equal": "^3.1.3",
-            "fast-uri": "^3.0.1",
-            "json-schema-traverse": "^1.0.0",
-            "require-from-string": "^2.0.2"
-          }
-        },
         "ajv-keywords": {
           "version": "5.1.0",
           "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-5.1.0.tgz",
@@ -25805,12 +25370,6 @@
           "requires": {
             "fast-deep-equal": "^3.1.3"
           }
-        },
-        "json-schema-traverse": {
-          "version": "1.0.0",
-          "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz",
-          "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==",
-          "dev": true
         }
       }
     },
@@ -25863,12 +25422,9 @@
       }
     },
     "semver": {
-      "version": "7.5.4",
-      "resolved": "https://registry.npmjs.org/semver/-/semver-7.5.4.tgz",
-      "integrity": "sha512-1bCSESV6Pv+i21Hvpxp3Dx+pSD8lIPt8uVjRrxAUt/nbswYc+tK6Y2btiULjd4+fnq15PX+nqQDC7Oft7WkwcA==",
-      "requires": {
-        "lru-cache": "^6.0.0"
-      }
+      "version": "7.7.1",
+      "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.1.tgz",
+      "integrity": "sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA=="
     },
     "semver-dsl": {
       "version": "1.0.1",
@@ -26929,16 +26485,10 @@
       "integrity": "sha512-veRf7dawaj9xaWEu9HoTVn5Pggtc/qj+kqTOFvNiN1l0YdxwC1kvel57UCjThjGa3BHBihE8/UJAHI+uQHmd/g==",
       "dev": true
     },
-    "undici": {
-      "version": "6.11.1",
-      "resolved": "https://registry.npmjs.org/undici/-/undici-6.11.1.tgz",
-      "integrity": "sha512-KyhzaLJnV1qa3BSHdj4AZ2ndqI0QWPxYzaIOio0WzcEJB9gvuysprJSLtpvc2D9mhR9jPDUk7xlJlZbH2KR5iw==",
-      "dev": true
-    },
     "undici-types": {
-      "version": "6.20.0",
-      "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.20.0.tgz",
-      "integrity": "sha512-Ny6QZ2Nju20vw1SRHe3d9jVu6gJ+4e3+MMpqu7pqE5HT6WsTSlce++GQmK5UXS8mzV8DSYHrQH+Xrf2jVcuKNg==",
+      "version": "6.21.0",
+      "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.21.0.tgz",
+      "integrity": "sha512-iwDZqg0QAGrg9Rav5H4n0M64c3mkR59cJ6wQp+7C4nI0gsmExaedaYLNO44eT4AtBBwjbTiGPMlt2Md0T9H9JQ==",
       "dev": true,
       "optional": true,
       "peer": true
@@ -26997,6 +26547,7 @@
       "version": "4.4.1",
       "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz",
       "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==",
+      "dev": true,
       "requires": {
         "punycode": "^2.1.0"
       }
@@ -27231,6 +26782,24 @@
         "webpack-sources": "^3.2.3"
       },
       "dependencies": {
+        "ajv": {
+          "version": "6.12.6",
+          "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz",
+          "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==",
+          "dev": true,
+          "requires": {
+            "fast-deep-equal": "^3.1.1",
+            "fast-json-stable-stringify": "^2.0.0",
+            "json-schema-traverse": "^0.4.1",
+            "uri-js": "^4.2.2"
+          }
+        },
+        "json-schema-traverse": {
+          "version": "0.4.1",
+          "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz",
+          "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==",
+          "dev": true
+        },
         "schema-utils": {
           "version": "3.3.0",
           "resolved": "https://registry.npmjs.org/schema-utils/-/schema-utils-3.3.0.tgz",
@@ -27508,7 +27077,8 @@
     "yallist": {
       "version": "4.0.0",
       "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz",
-      "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A=="
+      "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==",
+      "dev": true
     },
     "yargs": {
       "version": "16.2.0",
diff --git a/package.json b/package.json
index 6c76618594cd9546a117d73864d93c6fccfd124d..6b64b51760053ce0aef49fe87fe6bab107b9d996 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
 {
   "name": "nmaas-portal",
-  "version": "1.7.0",
+  "version": "1.7.1",
   "license": "Apache 2.0",
   "angular-cli": {},
   "scripts": {
@@ -28,24 +28,25 @@
     "@formio/angular": "7.0.0",
     "@formio/js": "^5.0.0",
     "@ngx-translate/core": "^14.0.0",
-    "@ngx-translate/http-loader": "^7.0.0",
+    "@ngx-translate/http-loader": "^16.0.0",
     "@types/semver": "^7.3.8",
     "@types/zxcvbn": "^4.4.1",
     "@zxcvbn-ts/core": "^3.0.0",
     "@zxcvbn-ts/language-en": "^3.0.0",
-    "ajv": "^6.12.6",
+    "ajv": "^8.0.0",
     "angular-password-strength-meter": "^11.0.0",
     "bootstrap": "^3.4.1",
+    "chart.js": "^4.4.8",
     "document-register-element": "^1.14.10",
     "jquery": "^3.6.0",
     "lodash": "^4.17.21",
     "ng-event-source": "^1.0.14",
-    "ng-recaptcha": "^13.0.0",
+    "ng-recaptcha": "^13.2.1",
     "ng-terminal": "^6.3.0",
     "ngx-pagination": "^6.0.3",
     "ngx-webstorage-service": "^5.0.0",
     "primeflex": "^3.3.1",
-    "primeicons": "^6.0.1",
+    "primeicons": "^7.0.0",
     "primeng": "^17.18.15",
     "rxjs": "^7.8.1",
     "semver": "^7.5.4",
@@ -58,14 +59,14 @@
     "@angular-devkit/build-angular": "^17.3.11",
     "@angular/cli": "^17.3.11",
     "@angular/compiler-cli": "^17.3.12",
-    "@types/jasmine": "~3.6.0",
+    "@types/jasmine": "~5.1.0",
     "@types/node": "^12.20.13",
     "codelyzer": "^6.0.0",
     "intl": "^1.2.5",
     "jasmine-core": "~4.6.0",
     "jasmine-spec-reporter": "~5.0.0",
     "karma": "^6.3.14",
-    "karma-chrome-launcher": "~3.1.0",
+    "karma-chrome-launcher": "~3.2.0",
     "karma-cli": "^1.0.1",
     "karma-coverage": "^2.0.3",
     "karma-jasmine": "~4.0.0",
diff --git a/renovate.json b/renovate.json
new file mode 100644
index 0000000000000000000000000000000000000000..fd6683814e88163cfbff70a4a77a9a2d2f88e454
--- /dev/null
+++ b/renovate.json
@@ -0,0 +1,7 @@
+{
+  "$schema": "https://docs.renovatebot.com/renovate-schema.json",
+  "extends": [
+    "config:recommended"
+  ],
+  "separateMinorPatch": true
+}
diff --git a/src/app/app.component.css b/src/app/app.component.css
index 48e17db39d06b20dd9d84fc11e0a2a89c75b53dc..035dee4e90e9ec4bc20dd27e9817e86ba1045d3d 100644
--- a/src/app/app.component.css
+++ b/src/app/app.component.css
@@ -14,34 +14,46 @@ body{
     flex-direction: row;
 }
 
+.flex-container-column {
+    flex: 1;
+    height:100vh;
+    display: flex;
+    flex-direction: column;
+}
+
 .flex-spacer {
-    /*flex: 1 0 auto;*/
-    /* width: 100%;
-    height: 100%; */
+    flex: 1 0 auto;
+    height: 100%
 }
 
 .logged-out-layout {
     display: flex;
     flex-direction: column;
     min-height: 100vh;
-  }
-  .logged-in-layout {
+}
+.logged-in-layout {
     display: flex;
     flex-direction: row;
     min-height: 100vh;
-  }
-  .content-area {
+}
+.content-area {
     flex: 1;
     padding: 1rem;
-  }
+    display: flex;
+    flex-direction: column;
+    min-height: calc(100vh - 150px);
+}
 
-  .side-menu {
-    width: var(--left-panel-width);
-    background-color: var(--menu-color);
-    color: var(--l-text-color);
-    height: 100vh ;
-    position: fixed;
-    top: 0;
-    left: 0;
-    padding: 1rem;
-  }
+.router-outlet {
+    flex: 1; /* Wypełnia dostępną przestrzeń */
+}
+
+.side-menu {
+    /*background-color: var(--menu-color);*/
+    /*color: var(--l-text-color);*/
+    /*height: 100vh ;*/
+    /*position: fixed;*/
+    /*top: 0;*/
+    /*left: 0;*/
+    /*padding: 1rem;*/
+}
diff --git a/src/app/app.component.html b/src/app/app.component.html
index 1717bc47861bbb0dc21e1b0b92f916fe445f7d05..479de55ee239bb09c3c58c025f65c0eef14ed746 100644
--- a/src/app/app.component.html
+++ b/src/app/app.component.html
@@ -1,8 +1,8 @@
 <div *ngIf="!isLoggedIn" class="flex-container"> <!---  -->
     <app-navbar ></app-navbar>
     <router-outlet></router-outlet>
-    <!-- <div class="flex-spacer"></div>
-    <nmaas-footer></nmaas-footer> -->
+    <div class="flex-spacer"></div>
+    <nmaas-footer></nmaas-footer>
 
 </div>
 
@@ -10,15 +10,16 @@
     <div class="side-menu">
         <app-left-menu [style]="{'display': 'flex', 'height': '100%'}"></app-left-menu>
     </div>
-    <div class="flex-spacer">
-      
-    </div>
 
-    <div class="content-area" [style]="{'margin-left': 'var(--left-panel-width)'}">
-        <router-outlet></router-outlet>
+    <div class="flex flex-column"  [style]="{'margin-left': 'var(--left-panel-width)', 'width': 'calc(100vw - var(--left-panel-width))'}">
+        <div class="content-area">
+            <router-outlet></router-outlet>
+        </div>
+
+        <nmaas-footer></nmaas-footer>
     </div>
-    <!-- <div class="flex-spacer"></div>
-    <nmaas-footer></nmaas-footer> -->
+
+
 </div>
 
 <app-toast-container aria-live="polite" aria-atomic="true"></app-toast-container>
diff --git a/src/app/app.component.spec.ts b/src/app/app.component.spec.ts
index 9ed907e1a0d0bc44573f38ccdf7dc472151253d7..67ac91ebe50e5c5f3f2cfe3b28052b2120ca3e51 100644
--- a/src/app/app.component.spec.ts
+++ b/src/app/app.component.spec.ts
@@ -1,12 +1,10 @@
 /* tslint:disable:no-unused-variable */
 
-import { TestBed, waitForAsync } from '@angular/core/testing';
-import { AppComponent } from './app.component';
-import { RouterTestingModule} from '@angular/router/testing';
+import {TestBed, waitForAsync} from '@angular/core/testing';
+import {AppComponent} from './app.component';
+import {RouterTestingModule} from '@angular/router/testing';
 import {AppConfigService, ConfigurationService} from './service';
-import {HttpClient, HttpHandler} from '@angular/common/http';
-import {TranslateService, TranslateModule, TranslateLoader, MissingTranslationHandler} from '@ngx-translate/core';
-import {TranslateFakeLoader} from '@ngx-translate/core';
+import {MissingTranslationHandler, TranslateFakeLoader, TranslateLoader, TranslateModule, TranslateService} from '@ngx-translate/core';
 import {Observable, of} from 'rxjs';
 import {Configuration} from './model/configuration';
 import {CustomMissingTranslationService} from './i18n/custommissingtranslation.service';
@@ -18,82 +16,111 @@ import { LeftMenuComponent } from './shared/left-menu/left-menu.component';
 import { ToastContainerComponent } from './shared/toast-container/toast-container.component';
 import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
 import { MessageService } from 'primeng/api';
+import {HttpClientTestingModule} from '@angular/common/http/testing';
 
 class MockConfigurationService {
-  protected uri: string;
+    protected uri: string;
 
-  constructor() {
-    this.uri = 'http://localhost/api';
-  }
+    constructor() {
+        this.uri = 'http://localhost/api';
+    }
 
-  public getApiUrl(): string {
-    return 'http://localhost/api';
-  }
+    public getApiUrl(): string {
+        return 'http://localhost/api';
+    }
 
-  public getConfiguration(): Observable<Configuration> {
-    return of<Configuration>();
-  }
+    public getConfiguration(): Observable<Configuration> {
+        return of<Configuration>();
+    }
 
-  public updateConfiguration(configuration: Configuration): Observable<any> {
-    return of<Configuration>();
-  }
+    public updateConfiguration(configuration: Configuration): Observable<any> {
+        return of<Configuration>();
+    }
 }
 
+class MockAppConfigService {
+    config: any;
+  
+    constructor() { }
+  
+    public load() {
+    }
+  
+    public getApiUrl(): string {
+      return '';
+    }
+  
+    public getNmaasGlobalDomainId(): number {
+      return 0;
+    }
+  
+    public getHttpTimeout(): number {
+      return 10000;
+    }
+  
+    public getShowGitInfo(): boolean {
+      return false;
+    }
+  
+    public getShowChangelog(): boolean {
+      return false;
+    }
+  }
+
 class MockServiceUnavailableService {
-  public isServiceAvailable: boolean;
+    public isServiceAvailable: boolean;
 
-  constructor() {
-    this.isServiceAvailable = true;
-  }
+    constructor() {
+        this.isServiceAvailable = true;
+    }
 }
 
 describe('App: NmaasPortal', () => {
-  beforeEach(() => {
-    TestBed.configureTestingModule({
-      declarations: [
-        AppComponent,
-        LeftMenuComponent,
-        ToastContainerComponent
-      ],
-        imports: [
-            RouterTestingModule,
-            TranslateModule.forRoot({
-                missingTranslationHandler: {provide: MissingTranslationHandler, useClass: CustomMissingTranslationService},
-                loader: {
-                    provide: TranslateLoader,
-                    useClass: TranslateFakeLoader
-                }
-            }),
-            JwtModule.forRoot({
-                config: {
-                    tokenGetter: () => {
-                        return '';
+    beforeEach(() => {
+        TestBed.configureTestingModule({
+            declarations: [
+                AppComponent,
+                LeftMenuComponent,
+                ToastContainerComponent
+            ],
+            imports: [
+                HttpClientTestingModule,
+                RouterTestingModule,
+                TranslateModule.forRoot({
+                    missingTranslationHandler: {provide: MissingTranslationHandler, useClass: CustomMissingTranslationService},
+                    loader: {
+                        provide: TranslateLoader,
+                        useClass: TranslateFakeLoader
                     }
-                }
-            }),
-          SharedModule
-        ],
-        providers: [
-            {provide: AppConfigService, useClass: MockConfigurationService},
-            HttpClient,
-            HttpHandler,
-            ConfigurationService,
-            TranslateService,
-            AuthService,
-            JwtHelperService,
+                }),
+                JwtModule.forRoot({
+                    config: {
+                        tokenGetter: () => {
+                            return '';
+                        }
+                    }
+                }),
+                SharedModule
+            ],
+            providers: [
+                {provide: AppConfigService, useClass: MockAppConfigService},
+                {provide: ConfigurationService, useClass: MockConfigurationService},
+                TranslateService,
+                AuthService,
+                JwtHelperService,
             MessageService,
-            {provide: ServiceUnavailableService, useClass: MockServiceUnavailableService}
+                {provide: ServiceUnavailableService, useClass: MockServiceUnavailableService}
         ],
         schemas: [
                       CUSTOM_ELEMENTS_SCHEMA,
                       NO_ERRORS_SCHEMA
-                  ]
+                      ]
+        });
     });
-  });
 
-  it('should create the app', waitForAsync(() => {
-    const fixture = TestBed.createComponent(AppComponent);
-    const app = fixture.debugElement.componentInstance;
-    expect(app).toBeTruthy();
-  }));
+    it('should create the app', waitForAsync(() => {
+        const fixture = TestBed.createComponent(AppComponent);
+        const app = fixture.debugElement.componentInstance;
+        expect(app).toBeTruthy();
+    }));
 });
diff --git a/src/app/app.module.ts b/src/app/app.module.ts
index 3a3ca3e05f970ad267c7e7ca5f10de457a406718..be39d339e116fb2a4cf03099c6c8666ea24ace06 100644
--- a/src/app/app.module.ts
+++ b/src/app/app.module.ts
@@ -32,6 +32,8 @@ import { MessageService } from 'primeng/api';
 import { ToastModule } from 'primeng/toast';
 import {SplitButtonModule} from 'primeng/splitbutton';
 import {MenuModule} from 'primeng/menu';
+import { AdminLeftMenuComponent } from './shared/admin-left-menu/admin-left-menu.component';
+import {AccordionModule} from 'primeng/accordion';
 
 export function appConfigFactory(config: AppConfigService) {
     return function create() {
@@ -59,7 +61,8 @@ export const jwtOptionsFactory = (appConfig: AppConfigService) => ({
     declarations: [
         AppComponent,
         LeftMenuComponent,
-        ToastContainerComponent
+        ToastContainerComponent,
+        AdminLeftMenuComponent
     ],
     imports: [
         BrowserModule,
@@ -90,6 +93,7 @@ export const jwtOptionsFactory = (appConfig: AppConfigService) => ({
         ToastModule,
         SplitButtonModule,
         MenuModule,
+        AccordionModule,
     ],
     providers: [
         AuthGuard,
diff --git a/src/app/app.routes.ts b/src/app/app.routes.ts
index 610c10ccf5c6a61d2610e4be2b3fdefe9e51fcde..31a968fec3b241c1d54e3257898a92a6e781fe71 100644
--- a/src/app/app.routes.ts
+++ b/src/app/app.routes.ts
@@ -6,6 +6,7 @@ import { WelcomeRoutes } from './welcome/welcome.routes';
 import {ServiceUnavailableRoutes} from './service-unavailable/service-unavailable.routes';
 import {PageNotFoundComponent} from './shared/page-not-found/page-not-found.component';
 import {LoginSuccessComponent} from './auth/login-success/login-success.component';
+import {LinkAccountComponent} from './welcome/link-account/link-account.component';
 
 const appRoutes: Routes = [
     ...WelcomeRoutes,
@@ -13,6 +14,7 @@ const appRoutes: Routes = [
     ...ServiceUnavailableRoutes,
     { path: 'notfound', component: PageNotFoundComponent },
     { path: 'login-success', component: LoginSuccessComponent },
+    { path: 'login-linking', component: LinkAccountComponent},
     { path: '**', redirectTo: '/welcome' },
 
 ];
diff --git a/src/app/appmarket/admin/clusters/clusters.module.ts b/src/app/appmarket/admin/clusters/clusters.module.ts
index c5137d01d8dd76c55e3ca77fda8f4fe5178ea2ce..fc03ca25144830a738d453913d47046effd941cb 100644
--- a/src/app/appmarket/admin/clusters/clusters.module.ts
+++ b/src/app/appmarket/admin/clusters/clusters.module.ts
@@ -7,10 +7,20 @@ import {NgModule} from "@angular/core";
 import {SharedModule} from "../../../shared/shared.module";
 import {ClusterDetailsComponent} from "./details/clusterdetails.component";
 import {ClusterService} from "../../../service/cluster.service";
+import { ClusterManagerDetailsComponent } from "../../../shared/admin/clusters/managerdetails/managerdetails.component";
+import { ClusterManagerComponent } from "../../../shared/admin/clusters/manager/manager.component";
+import { TableModule } from 'primeng/table';
+import { FileUploadModule } from 'primeng/fileupload';
+import { TranslateModule } from "@ngx-translate/core";
+import { TooltipModule } from 'primeng/tooltip';
+
+
 
 @NgModule({
     declarations: [
         ClusterDetailsComponent,
+        ClusterManagerDetailsComponent,
+        ClusterManagerComponent
     ],
     imports: [
         CommonModule,
@@ -19,9 +29,16 @@ import {ClusterService} from "../../../service/cluster.service";
         SharedModule,
         AuthModule,
         PipesModule,
+        TableModule,
+        FileUploadModule,
+         TranslateModule.forChild(),
+         TooltipModule
     ],
     exports: [
-        ClusterDetailsComponent
+        ClusterDetailsComponent,
+        ClusterManagerDetailsComponent,
+        ClusterManagerComponent
+
     ],
     providers: [
         ClusterService,
diff --git a/src/app/appmarket/admin/clusters/clusters.routes.ts b/src/app/appmarket/admin/clusters/clusters.routes.ts
index 4bfe2d9af597abd5daf68e0e66f31d816c92083e..9d6894ae8926e9cc19faf0e48cce1bc1d9a4e20b 100644
--- a/src/app/appmarket/admin/clusters/clusters.routes.ts
+++ b/src/app/appmarket/admin/clusters/clusters.routes.ts
@@ -3,10 +3,16 @@ import {ClusterDetailsComponent} from './index';
 import {AuthGuard} from '../../../auth/auth.guard';
 import {RoleGuard} from '../../../auth/role.guard';
 import {ComponentMode} from '../../../shared/common/componentmode';
+import { ClusterManagerComponent } from '../../../shared/admin/clusters/manager/manager.component';
+import { ClusterManagerDetailsComponent } from '../../../shared/admin/clusters/managerdetails/managerdetails.component';
 
 export const ClustersRoutes: Route[] = [
-    { path: 'admin/clusters', component: ClusterDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+    { path: 'clusters', component: ClusterDetailsComponent, canActivate: [AuthGuard, RoleGuard],
         data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}},
-    { path: 'admin/clusters/view', component: ClusterDetailsComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}}
+    { path: 'clusters/view', component: ClusterDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}},
+    { path: 'manage/clusters', component: ClusterManagerComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}},
+    { path: 'manage/clusters/:id', component: ClusterManagerDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {mode: ComponentMode.EDIT, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}},
 ];
diff --git a/src/app/appmarket/admin/clusters/details/clusterdetails.component.html b/src/app/appmarket/admin/clusters/details/clusterdetails.component.html
index b5730cb4b9e56571b219092a7e57e10fe0a5bc8e..464ced99150a4f51d3e6e2fb7f4aece24ad04137 100644
--- a/src/app/appmarket/admin/clusters/details/clusterdetails.component.html
+++ b/src/app/appmarket/admin/clusters/details/clusterdetails.component.html
@@ -1 +1 @@
-<nmaas-clusterdetails class="col-sm-12 col-sm-12 col-md-12" [cluster]="cluster" [error]="error" [mode]="getCurrentMode()" [allowedModes]="[ComponentMode.VIEW, ComponentMode.CREATE]" (onSave)="onSave($event)" (onDelete)="onDelete($event)"></nmaas-clusterdetails>
+<nmaas-clusterdetails class="" [cluster]="cluster" [error]="error" [mode]="getCurrentMode()" [allowedModes]="[ComponentMode.VIEW, ComponentMode.CREATE]"></nmaas-clusterdetails>
diff --git a/src/app/appmarket/admin/clusters/details/clusterdetails.component.ts b/src/app/appmarket/admin/clusters/details/clusterdetails.component.ts
index 248a6943e8c8662468fd62f1dad8c0833908ba1d..d9990a60a4ed7bf7effaebbf62dce13b1bcd63c4 100644
--- a/src/app/appmarket/admin/clusters/details/clusterdetails.component.ts
+++ b/src/app/appmarket/admin/clusters/details/clusterdetails.component.ts
@@ -29,21 +29,4 @@ export class ClusterDetailsComponent extends BaseComponent implements OnInit {
         });
     }
 
-    public onSave($event) {
-        const upCluster: Cluster = $event;
-        if (!upCluster) {
-            return;
-        }
-        if (this.isInMode(ComponentMode.CREATE)) {
-            this.clusterService.add(upCluster)
-                .subscribe(() => this.router.navigateByUrl('/admin/clusters'), err => this.error = err.message);
-        } else {
-            this.clusterService.update(upCluster)
-                .subscribe(() => this.router.navigateByUrl('/admin/clusters'), err => this.error = err.message);
-        }
-    }
-
-    public onDelete($event): void {
-        this.clusterService.remove($event).subscribe(() => this.router.navigate(['/admin/clusters/']));
-    }
 }
diff --git a/src/app/appmarket/admin/configuration/configuration.routes.ts b/src/app/appmarket/admin/configuration/configuration.routes.ts
index 3d232bc59f5f9a1407e2e5237807268e7d989421..adde5168ce4badc1f068931ff7978c8122ecdbbf 100644
--- a/src/app/appmarket/admin/configuration/configuration.routes.ts
+++ b/src/app/appmarket/admin/configuration/configuration.routes.ts
@@ -4,6 +4,6 @@ import {RoleGuard} from "../../../auth/role.guard";
 import {ConfigurationDetailsComponent} from "./index";
 
 export const ConfigurationRoutes: Route[] = [
-    {path: 'admin/configuration', component: ConfigurationDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+    {path: 'configuration', component: ConfigurationDetailsComponent, canActivate: [AuthGuard, RoleGuard],
         data:{roles: ['ROLE_SYSTEM_ADMIN']} }
 ];
diff --git a/src/app/appmarket/admin/configuration/details/configurationdetails.component.html b/src/app/appmarket/admin/configuration/details/configurationdetails.component.html
index de8a5d141eabd06407384500438ac27cf15ed1a3..120f90dc214c1069294c29a1ea17b387dc260d4a 100644
--- a/src/app/appmarket/admin/configuration/details/configurationdetails.component.html
+++ b/src/app/appmarket/admin/configuration/details/configurationdetails.component.html
@@ -1,6 +1,6 @@
-<div class="col-sm-12 col-sm-12 col-md-12" >
-    <div class="panel panel-default">
-        <div class="panel-heading">{{ 'PORTAL_CONFIGURATION.TITLE' | translate }}</div>
+<div class="" >
+    <div class="background-section">
+        <h4 style="font-size:15px; font-weight: bold">{{ 'PORTAL_CONFIGURATION.TITLE' | translate }}</h4>
         <div class="panel-body">
             <form (submit)="save()" class="form-horizontal" #configurationForm="ngForm" *ngIf="this.configuration">
                 <div class="form-group">
@@ -87,59 +87,85 @@
                                [(ngModel)]="this.configuration.registrationDomainSelectionEnabled">
                     </div>
                 </div>
-
                 <div class="form-group">
-                    <label for="bulkDomainsAllowForSsoAccounts"
-                           class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DOMAINS_ALLOW_FOR_SSO_ACCOUNTS' | translate}}</label>
+                    <label for="deploymentPrefix"
+                           class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.DEPLOYMENT_PREFIX' | translate}}</label>
                     <div class="col-sm-9 pd-top-7">
-                        <input type="checkbox" id="bulkDomainsAllowForSsoAccounts" name="bulkDomainsAllowForSsoAccounts"
-                               [(ngModel)]="this.configuration.bulkDomainsAllowForSsoAccounts"
-                               [checked]="this.configuration.bulkDomainsAllowForSsoAccounts === true">
+                        <div class="input-width">
+                            <input class="form-control" type="text" id="deploymentPrefix" name="deploymentPrefix"
+                                   [(ngModel)]="this.configuration.deploymentPrefix">
+                        </div>
+
                     </div>
                 </div>
 
-                <div class="form-group">
-                    <label for="bulkDomainsSendEmailForNewAccounts"
-                           class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DOMAINS_SEND_EMAIL_FOR_NEW_ACCOUNTS' | translate}}</label>
-                    <div class="col-sm-9 pd-top-7">
-                        <input type="checkbox" id="bulkDomainsSendEmailForNewAccounts" name="bulkDomainsSendEmailForNewAccounts"
-                               [(ngModel)]="this.configuration.bulkDomainsSendEmailForNewAccounts"
-                               [checked]="this.configuration.bulkDomainsSendEmailForNewAccounts === true">
+                <div class="panel-default panel-heading">Bulk settings</div>
+                <div class="panel-body">
+
+                    <div class="form-group">
+                        <label for="bulkDomainsAllowForSsoAccounts"
+                               class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DOMAINS_ALLOW_FOR_SSO_ACCOUNTS' | translate}}</label>
+                        <div class="col-sm-9 pd-top-7">
+                            <input type="checkbox" id="bulkDomainsAllowForSsoAccounts" name="bulkDomainsAllowForSsoAccounts"
+                                   [(ngModel)]="this.configuration.bulkDomainsAllowForSsoAccounts"
+                                   [checked]="this.configuration.bulkDomainsAllowForSsoAccounts === true">
+                        </div>
                     </div>
-                </div>
 
-                <div class="form-group">
-                    <label for="bulkDeploymentJobCron"
-                           class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_CRON' | translate}}</label>
-                    <div class="col-sm-9 pd-top-7 ">
-                        <div class="input-width">
-                            <input class="form-control" type="text" id="bulkDeploymentJobCron" name="bulkDeploymentJobCron"
-                            [(ngModel)]="this.configuration.bulkDeploymentJobCron">
+                    <div class="form-group">
+                        <label for="bulkDomainsSendEmailForNewAccounts"
+                               class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DOMAINS_SEND_EMAIL_FOR_NEW_ACCOUNTS' | translate}}</label>
+                        <div class="col-sm-9 pd-top-7">
+                            <input type="checkbox" id="bulkDomainsSendEmailForNewAccounts" name="bulkDomainsSendEmailForNewAccounts"
+                                   [(ngModel)]="this.configuration.bulkDomainsSendEmailForNewAccounts"
+                                   [checked]="this.configuration.bulkDomainsSendEmailForNewAccounts === true">
                         </div>
-                        
                     </div>
-                </div>
 
-                <div class="form-group">
-                    <label for="parallelDeploymentsLimit"
-                           class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_LIMIT' | translate}}</label>
-                    <div class="col-sm-9 pd-top-7">
-                        <div class="input-width">
-                            <input class="form-control" type="number" id="parallelDeploymentsLimit" name="parallelDeploymentsLimit"
-                            [(ngModel)]="this.configuration.parallelDeploymentsLimit">
+                    <div class="form-group">
+                        <label for="bulkDeploymentJobCron"
+                               class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_CRON' | translate}}</label>
+                        <div class="col-sm-9 pd-top-7 ">
+                            <div class="input-width">
+                                <input class="form-control" type="text" id="bulkDeploymentJobCron" name="bulkDeploymentJobCron"
+                                [(ngModel)]="this.configuration.bulkDeploymentJobCron">
+                            </div>
+
                         </div>
-                    
                     </div>
-                </div>
-                <div class="form-group">
-                    <label for="bulkDeploymentQueueRefresh"
-                           class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_QUEUE_REFRESH' | translate}}</label>
-                    <div class="col-sm-9 pd-top-7">
-                        <div class="input-width">
-                            <input class="form-control" type="number" id="bulkDeploymentQueueRefresh" name="bulkDeploymentQueueRefresh"
-                            [(ngModel)]="this.configuration.bulkDeploymentQueueRefresh">
+
+                    <div class="form-group">
+                        <label for="parallelDeploymentsLimit"
+                               class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_LIMIT' | translate}}</label>
+                        <div class="col-sm-9 pd-top-7">
+                            <div class="input-width">
+                                <input class="form-control" type="number" id="parallelDeploymentsLimit" name="parallelDeploymentsLimit"
+                                [(ngModel)]="this.configuration.parallelDeploymentsLimit">
+                            </div>
+
+                        </div>
+                    </div>
+                    <div class="form-group">
+                        <label for="bulkDeploymentQueueRefresh"
+                               class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_QUEUE_REFRESH' | translate}}</label>
+                        <div class="col-sm-9 pd-top-7">
+                            <div class="input-width">
+                                <input class="form-control" type="number" id="bulkDeploymentQueueRefresh" name="bulkDeploymentQueueRefresh"
+                                [(ngModel)]="this.configuration.bulkDeploymentQueueRefresh">
+                            </div>
+
+                        </div>
+                    </div>
+                    <div class="form-group">
+                        <label for="bulkDeploymentTimeThreshold"
+                               class="col-sm-3 control-label">{{'PORTAL_CONFIGURATION.BULK_DEPLOYMENT_THRESHOLD' | translate}}</label>
+                        <div class="col-sm-9 pd-top-7">
+                            <div class="input-width">
+                                <input class="form-control" type="number" id="bulkDeploymentTimeThreshold" name="bulkDeploymentTimeThreshold"
+                                [(ngModel)]="this.configuration.bulkDeploymentTimeThreshold">
+                            </div>
+
                         </div>
-                    
                     </div>
                 </div>
                 <div class="flex justify-content-end">
diff --git a/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.css b/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.css
index 76a9184a9116d73518d2bd3b9db0239df54da9cb..ef5401480eb1663ac2c9dec13c5a1014d6ea0a61 100644
--- a/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.css
+++ b/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.css
@@ -13,6 +13,6 @@ tr.clickable {
     cursor: pointer;
 }
 
-.dropdown:hover .dropdown-menu {
-    display: block;
-}
+/*.dropdown:hover .dropdown-menu {*/
+/*    display: block;*/
+/*}*/
diff --git a/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.html b/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.html
index fb9fcc5dce55c757cd218532db961cea45ee2c53..12bab7e9b17986da97dca30fc7dfda12de7c6acc 100644
--- a/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.html
+++ b/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.html
@@ -1,40 +1,40 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm-10 col-md-offset-1 col-md-10">
-  <h3>{{'LANGUAGE_MANAGEMENT.TITLE' | translate }}</h3>
-  <hr>
-  <table class="table table-hover table-condensed" aria-describedby="Language list table">
-    <thead>
-      <tr>
-        <th scope="col">&nbsp;</th>
-        <th scope="col">{{'LANGUAGE_MANAGEMENT.LANGUAGE' | translate }}</th>
-        <th scope="col">&nbsp;</th>
-      </tr>
-    </thead>
+<div class="">
+  <h4 class="header">{{'LANGUAGE_MANAGEMENT.TITLE' | translate }}</h4>
+  <div class="background-section">
+    <p-table [value]="languages" class="p-datatable-hover p-datatable-sm" [responsive]="true">
+      <ng-template pTemplate="header">
+        <tr>
+          <th></th>
+          <th>{{'LANGUAGE_MANAGEMENT.LANGUAGE' | translate }}</th>
+          <th></th>
+        </tr>
+      </ng-template>
 
-    <tbody>
-      <ng-template ngFor let-lang [ngForOf]="languages" let-i="index">
-        <tr class="clickable" [routerLink]="['/admin/languages/' + lang.language]">
-          <td><img alt="language" src="assets/images/country/{{lang.language}}_circle.png" style="height: 22px;"></td>
-          <td>{{'LANGUAGE.' + lang.language.toUpperCase() + '_LABEL' | translate}}</td>
+      <ng-template pTemplate="body" let-lang>
+        <tr class="clickable" >
+          <td [routerLink]="['/admin/languages/' + lang.language]">
+            <img alt="language" src="assets/images/country/{{lang.language}}_circle.png" style="height: 22px;">
+          </td>
+          <td [routerLink]="['/admin/languages/' + lang.language]">{{'LANGUAGE.' + lang.language.toUpperCase() + '_LABEL' | translate}}</td>
           <td class="text-right">
             <span class="dropdown">
-              <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
-                    data-toggle="dropdown" href="#" role="button">
-                <em class="fas fa-cog icon-black icon-bigger"></em>
+              <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
               </a>
               <ul class="dropdown-menu pull-right-drop">
                 <li>
                   <a [routerLink]="['/admin/languages/' + lang.language]">
-					{{ 'LANGUAGE_MANAGEMENT.EDIT_BUTTON' | translate }}
+                    {{ 'LANGUAGE_MANAGEMENT.EDIT_BUTTON' | translate }}
                   </a>
                 </li>
                 <li>
                   <a *ngIf="lang.enabled" (click)="changeLanguageState(lang)">
-					{{ 'LANGUAGE_MANAGEMENT.LANGUAGE_DISABLED' | translate }}
+                    {{ 'LANGUAGE_MANAGEMENT.LANGUAGE_DISABLED' | translate }}
                   </a>
                 </li>
                 <li>
                   <a *ngIf="!lang.enabled" (click)="changeLanguageState(lang)">
-					{{ 'LANGUAGE_MANAGEMENT.LANGUAGE_ENABLED' | translate }}
+                    {{ 'LANGUAGE_MANAGEMENT.LANGUAGE_ENABLED' | translate }}
                   </a>
                 </li>
               </ul>
@@ -42,8 +42,9 @@
           </td>
         </tr>
       </ng-template>
-    </tbody>
-  </table>
+    </p-table>
+  </div>
+
 </div>
 
 <nmaas-modal (click)="modal.hide()">
diff --git a/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.spec.ts b/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.spec.ts
index d3b5af459a7e540f00cb8a5af733f244aad46240..c444bc324042ff3be92876785d98b41622fad058 100644
--- a/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.spec.ts
+++ b/src/app/appmarket/admin/languagemanagement/languagelist/languagelist.component.spec.ts
@@ -8,6 +8,7 @@ import {InternationalizationService} from '../../../../service/internationalizat
 import {AppConfigService} from '../../../../service';
 import {of} from 'rxjs';
 import {ModalComponent} from '../../../../shared/modal';
+import {CUSTOM_ELEMENTS_SCHEMA} from '@angular/core';
 
 describe('LanguagelistComponent', () => {
     let component: LanguageListComponent;
@@ -35,7 +36,8 @@ describe('LanguagelistComponent', () => {
                     }
                 },
                 {provide: AppConfigService, useValue: {}}
-            ]
+            ],
+            schemas: [CUSTOM_ELEMENTS_SCHEMA]
         })
             .compileComponents();
     }));
diff --git a/src/app/appmarket/admin/languagemanagement/languagemanagement.module.ts b/src/app/appmarket/admin/languagemanagement/languagemanagement.module.ts
index 1fb084a507599dfa164511b46d80f94853a41fee..801e94f4dbc50cfa8eece97b8abea1c35f436ee2 100644
--- a/src/app/appmarket/admin/languagemanagement/languagemanagement.module.ts
+++ b/src/app/appmarket/admin/languagemanagement/languagemanagement.module.ts
@@ -8,17 +8,19 @@ import {TranslateModule} from '@ngx-translate/core';
 import {SharedModule} from '../../../shared';
 import {FormsModule} from '@angular/forms';
 import {InputSwitchModule} from 'primeng/inputswitch';
+import {TableModule} from 'primeng/table';
 
 @NgModule({
   declarations: [LanguageListComponent, LanguageDetailsComponent],
-  imports: [
-    CommonModule,
-    FormsModule,
-    InputSwitchModule,
-    RouterModule,
-    SharedModule,
-    TranslateModule.forChild()
-  ],
+    imports: [
+        CommonModule,
+        FormsModule,
+        InputSwitchModule,
+        RouterModule,
+        SharedModule,
+        TranslateModule.forChild(),
+        TableModule
+    ],
   providers: [InternationalizationService]
 })
 export class LanguageManagementModule { }
diff --git a/src/app/appmarket/admin/languagemanagement/languagemanagement.routes.ts b/src/app/appmarket/admin/languagemanagement/languagemanagement.routes.ts
index dcc2b8c840b7a220ef228fa3c9b5105fde2f714d..6586b88743e1b3164e96e5ba749cd6ca2ef045ce 100644
--- a/src/app/appmarket/admin/languagemanagement/languagemanagement.routes.ts
+++ b/src/app/appmarket/admin/languagemanagement/languagemanagement.routes.ts
@@ -5,6 +5,6 @@ import {AuthGuard} from "../../../auth/auth.guard";
 import {RoleGuard} from "../../../auth/role.guard";
 
 export const LanguageManagementRoutes: Route[] = [
-    {path: 'admin/languages', component: LanguageListComponent, canActivate: [AuthGuard, RoleGuard], data:{ roles: 'ROLE_SYSTEM_ADMIN'}},
-    {path: 'admin/languages/:id', component: LanguageDetailsComponent, canActivate: [AuthGuard, RoleGuard], data: { roles: 'ROLE_SYSTEM_ADMIN'}}
+    {path: 'languages', component: LanguageListComponent, canActivate: [AuthGuard, RoleGuard], data:{ roles: 'ROLE_SYSTEM_ADMIN'}},
+    {path: 'languages/:id', component: LanguageDetailsComponent, canActivate: [AuthGuard, RoleGuard], data: { roles: 'ROLE_SYSTEM_ADMIN'}}
 ];
\ No newline at end of file
diff --git a/src/app/appmarket/admin/monitor/list/monitor-list.component.html b/src/app/appmarket/admin/monitor/list/monitor-list.component.html
index d762b99e4772dd1b0b8e7f24401d5914d3dd2f1f..cdb2ce67972016f5020c03ec64f06851d24309e5 100644
--- a/src/app/appmarket/admin/monitor/list/monitor-list.component.html
+++ b/src/app/appmarket/admin/monitor/list/monitor-list.component.html
@@ -1,36 +1,36 @@
-<div class="col-sm-12 col-sm-12 col-md-12">
-    <h3>{{ 'MONITOR.TITLE' | translate }}</h3>
-    <br>
-    <table class="table table-hover table-condensed" aria-describedby="Service status table">
-        <thead>
-        <tr>
-            <th scope="col">{{ 'MONITOR.SERVICE_NAME' | translate }}</th>
-            <th scope="col">{{ 'MONITOR.LAST_CHECK' | translate }}</th>
-            <th scope="col">{{ 'MONITOR.LAST_SUCCESS' | translate }}</th>
-            <th scope="col">{{ 'MONITOR.CHECK_INTERVAL' | translate }}</th>
-            <th scope="col">&nbsp;</th>
-        </tr>
-        </thead>
+<div class="">
+    <h4 class="header">{{ 'MONITOR.TITLE' | translate }}</h4>
+    <div class="background-section">
+        <table class="table table-hover table-condensed" aria-describedby="Service status table">
+            <thead>
+            <tr>
+                <th scope="col">{{ 'MONITOR.SERVICE_NAME' | translate }}</th>
+                <th scope="col">{{ 'MONITOR.LAST_CHECK' | translate }}</th>
+                <th scope="col">{{ 'MONITOR.LAST_SUCCESS' | translate }}</th>
+                <th scope="col">{{ 'MONITOR.CHECK_INTERVAL' | translate }}</th>
+                <th scope="col">&nbsp;</th>
+            </tr>
+            </thead>
 
-        <tbody>
-        <ng-template ngFor let-entry [ngForOf]="monitorEntries">
-            <tr class="clickable" [routerLink]="['view/', entry.serviceName.toString()]"
-                [ngClass]="{'entry-unknown': entry.status === null || entry.status === undefined,
+            <tbody>
+            <ng-template ngFor let-entry [ngForOf]="monitorEntries">
+                <tr class="clickable" [routerLink]="['view/', entry.serviceName.toString()]"
+                    [ngClass]="{'entry-unknown': entry.status === null || entry.status === undefined,
                     'entry-deactivated': !entry.active,
                     'entry-success': entry.status.toString() === 'SUCCESS',
                     'entry-failure': entry.status.toString() === 'FAILURE'}">
 
-                <td>{{services[entry.serviceName]}}</td>
-                <td>
-                    <span *ngIf="entry.lastCheck">{{entry.lastCheck | date:'medium'}}</span>
-                    <span *ngIf="!entry.lastCheck">---</span>
-                </td>
-                <td>
-                    <span *ngIf="entry.lastSuccess">{{entry.lastSuccess | date:'medium'}}</span>
-                    <span *ngIf="!entry.lastSuccess">---</span>
-                </td>
-                <td>{{getIntervalCheck(entry.checkInterval, entry.timeFormat)}}</td>
-                <td>
+                    <td>{{services[entry.serviceName]}}</td>
+                    <td>
+                        <span *ngIf="entry.lastCheck">{{entry.lastCheck | date:'medium'}}</span>
+                        <span *ngIf="!entry.lastCheck">---</span>
+                    </td>
+                    <td>
+                        <span *ngIf="entry.lastSuccess">{{entry.lastSuccess | date:'medium'}}</span>
+                        <span *ngIf="!entry.lastSuccess">---</span>
+                    </td>
+                    <td>{{getIntervalCheck(entry.checkInterval, entry.timeFormat)}}</td>
+                    <td>
                         <span class="dropdown">
                             <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false"
                                aria-haspopup="true"
@@ -51,9 +51,10 @@
                                 </li>
                             </ul>
 					    </span>
-                </td>
-            </tr>
-        </ng-template>
-        </tbody>
-    </table>
+                    </td>
+                </tr>
+            </ng-template>
+            </tbody>
+        </table>
+    </div>
 </div>
diff --git a/src/app/appmarket/admin/monitor/monitor.routes.ts b/src/app/appmarket/admin/monitor/monitor.routes.ts
index b91a355cc48de6fb9712241163d8601e10e42283..2ae94cfbf60f50dc7f18bd5232772a60edd764dc 100644
--- a/src/app/appmarket/admin/monitor/monitor.routes.ts
+++ b/src/app/appmarket/admin/monitor/monitor.routes.ts
@@ -6,11 +6,11 @@ import {MonitorListComponent} from './list/monitor-list.component';
 import {ComponentMode} from '../../../shared';
 
 export const MonitorRoutes: Route[] = [
-    {path: 'admin/monitor', component: MonitorListComponent, canActivate: [AuthGuard, RoleGuard],
+    {path: 'monitor', component: MonitorListComponent, canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}},
-    {path: 'admin/monitor/edit/:name', component: MonitorDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+    {path: 'monitor/edit/:name', component: MonitorDetailsComponent, canActivate: [AuthGuard, RoleGuard],
         data: {mode: ComponentMode.EDIT, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}},
-    {path: 'admin/monitor/view/:name', component: MonitorDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+    {path: 'monitor/view/:name', component: MonitorDetailsComponent, canActivate: [AuthGuard, RoleGuard],
         data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}}
 ];
 
diff --git a/src/app/appmarket/appdetails/appdetails.component.html b/src/app/appmarket/appdetails/appdetails.component.html
index 7db442fe15ab9b6a711759732ed1056378587362..7caaea2e74a14291fecff80651685535df415117 100644
--- a/src/app/appmarket/appdetails/appdetails.component.html
+++ b/src/app/appmarket/appdetails/appdetails.component.html
@@ -10,14 +10,17 @@
 				<h3 style="margin:0 20px;">{{app?.name}}</h3>
 			</div>
 			<div class="" *ngIf="app && domain" style="display:flex; align-items: center">
-				<div *ngIf="!subscribed && isSubscriptionAllowed()" class="btn-group pull-right"
+				<div *ngIf="!subscribed && isSubscriptionAllowed()" class="pull-right"
 					 pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_SUBSCRIBE' | translate}}" tooltipPosition="bottom" [showDelay]="50" [tooltipDisabled]="defaultTooltipDisabled">
-					<button class="btn btn-primary" [disabled]="!active || !isApplicationEnabledInDomain()" (click)="subscribe()">{{'APPLICATIONS.SUBSCRIBE_BUTTON' | translate}}</button>
+					<button class="btn btn-primary m-1" [disabled]="!active || !isApplicationEnabledInDomain()" (click)="subscribe()">{{'APPLICATIONS.SUBSCRIBE_BUTTON' | translate}}</button>
+					<button class="btn btn-primary m-1"[routerLink]="['/admin/apps/bulks']">Bulk deployments</button>
 				</div>
+
 				<div *ngIf="subscribed" class=" pull-right" >
 					<div class="btn no-padding" pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_DEPLOY' | translate}}" tooltipPosition="bottom" [showDelay]="50" [tooltipDisabled]="defaultTooltipDisabled">
 						<button *ngIf="isSubscriptionAllowed()" class="btn btn-danger m-1" (click)="unsubscribe()">{{'APPLICATIONS.UNSUBSCRIBE_BUTTON' | translate}}</button>
 					</div>
+					<button class="btn btn-primary m-1" [routerLink]="['/admin/apps/bulks']">Bulk deployments</button>
 					<button *ngIf="isSubscriptionAllowed()" class="btn btn-primary m-1" [disabled]="!isApplicationEnabledInDomain()" (click)="appInstallModal.show()">{{'APPLICATIONS.DEPLOY_BUTTON' | translate}}</button>
 				</div>
 
@@ -58,7 +61,7 @@
 			<div class="" *ngIf="versionVisible">
 				<div class="" *ngIf="activeVersions">
 					<a *ngFor="let version of activeVersions" class="tag-button">
-						v.{{version}}
+						v{{version}}
 					</a>
 				</div>
 			</div>
@@ -81,7 +84,7 @@
 		</div>
 		<div style="padding-top:50px">
 			<p style="font-weight: bold" *ngIf="numberOfScreenshots > 0">{{'SCREENSHOTS.HEADER' | translate}}</p>
-			<screenshots (numberOfScreenshots)="screenshots($event)" [pathUrl]="'/apps/' + appId + '/screenshots'"></screenshots>
+			<screenshots style="display: flex" (numberOfScreenshots)="screenshots($event)" [pathUrl]="'/apps/' + appId + '/screenshots'"></screenshots>
 		</div>
 	</div>
 
diff --git a/src/app/appmarket/appdetails/appdetails.component.ts b/src/app/appmarket/appdetails/appdetails.component.ts
index e5518794a0850eb436fcafbe67025c1e78c33d75..cb156314c0447fa5f6e4530551266420d105368f 100644
--- a/src/app/appmarket/appdetails/appdetails.component.ts
+++ b/src/app/appmarket/appdetails/appdetails.component.ts
@@ -146,7 +146,8 @@ export class AppDetailsComponent implements OnInit {
         }
 
         return this.authService.hasRole(Role[Role.ROLE_SYSTEM_ADMIN])
-            || this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_DOMAIN_ADMIN]);
+            || this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_DOMAIN_ADMIN])
+            || this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_GROUP_DOMAIN_ADMIN]);
     }
 
     public isApplicationEnabledInDomain(): boolean {
diff --git a/src/app/appmarket/appinstance/appinstance.module.ts b/src/app/appmarket/appinstance/appinstance.module.ts
index 4fe735db92c8eeb7995b5811b5bad2d6d9adc515..bc7d02664d02586552884f6722dc9727463396a2 100644
--- a/src/app/appmarket/appinstance/appinstance.module.ts
+++ b/src/app/appmarket/appinstance/appinstance.module.ts
@@ -38,6 +38,7 @@ import {FormioAppConfig, FormioModule} from '@formio/angular';
 import {SelectButtonModule} from 'primeng/selectbutton';
 import {CheckboxModule} from 'primeng/checkbox';
 import {TableModule} from 'primeng/table';
+import {ProgressBarModule} from 'primeng/progressbar';
 
 @NgModule({
   declarations: [
@@ -78,6 +79,7 @@ import {TableModule} from 'primeng/table';
         CheckboxModule,
         SelectButtonModule,
         TableModule,
+        ProgressBarModule,
     ],
   exports: [
     AppInstanceComponent,
diff --git a/src/app/appmarket/appinstance/appinstance/appinstance.component.css b/src/app/appmarket/appinstance/appinstance/appinstance.component.css
index 96f3d93cb7b3cb432509395a983316d14c8ba532..3fe8d07992c63f0ea74cc5d8d25653db29998897 100644
--- a/src/app/appmarket/appinstance/appinstance/appinstance.component.css
+++ b/src/app/appmarket/appinstance/appinstance/appinstance.component.css
@@ -23,22 +23,26 @@
 
 .other-states{
     padding:15px;
-    margin-bottom:20px;
+    margin:50px 0;
     border-bottom: 1px solid lightgray;
     border-top: 1px solid lightgray;
     text-align: center;
     color: #337ab7;
+    background-image: none;
+    width:100%;
+    background: transparent;
 }
 
 .alert-danger{
     padding:15px;
-    margin-bottom:20px;
+    margin:50px 0;
     text-align: center;
     border-bottom: 1px solid #a94442;
     border-top: 1px solid #a94442;
     border-radius: 0;
-    background-color: #FFFFFF;
     background-image: none;
+    width:100%;
+    background: transparent;
 }
 
 .h-100 {
@@ -81,3 +85,6 @@
 :host ::ng-deep.p-dropdown-panel .p-dropdown-items {
     max-height: 150px;
 }
+:host ::ng-deep .dropdown-menu>li>a:focus, .dropdown-menu>li>a:hover{
+    background: var(--user-button-background-hover)
+}
diff --git a/src/app/appmarket/appinstance/appinstance/appinstance.component.html b/src/app/appmarket/appinstance/appinstance/appinstance.component.html
index 330151db9ebe9fe0c3741dec40f339e289153372..9ad4da9d993d742d8c3d061ce577ee84d3739b34 100644
--- a/src/app/appmarket/appinstance/appinstance/appinstance.component.html
+++ b/src/app/appmarket/appinstance/appinstance/appinstance.component.html
@@ -1,73 +1,61 @@
-<div class="container" *ngIf="appInstance">
-    <div class="row">
-        <!-- App logo -->
-        <div class="col-xs-4 col-sm-3 col-md-3 col-lg-2">
-            <div class="thumbnail" *ngIf="app">
-                <img alt="App logo"
-                     [src]="(appImagesService.getAppLogoUrl(app?.applicationBase.id) | secure) || 'assets/images/app-logo-example.png'"/>
-            </div>
-            <div class="thumbnail" *ngIf="!app">
-                <img alt="App logo" src="assets/images/app-logo-example.png"/>
-            </div>
-        </div>
-        <!-- App information-->
-        <div class="col-xs-8 col-sm-9 col-md-9 col-lg-10">
-            <div class="row flex-stretch">
-                <div class="col-xs-12 col-sm-6 col-md-6 col-lg-6">
-                    <h2 style="margin-bottom: 4px;">{{appInstance?.name}} ({{app?.applicationBase.name}})</h2>
-                    <rate *ngIf="app?.applicationBase.id" [showVotes]="true" [short]="true"
-                          [pathUrl]="getPathUrl(app?.applicationBase.id)"></rate>
-                    <div class="text-muted" style="font-size: small;">
-                        {{app?.application.version ? 'v.' + app?.application.version : 'None'}}
-                        |
-                        <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
-                              tooltipPosition="bottom" [showDelay]="50"
-                              [tooltipDisabled]="!!app?.applicationBase.licenseUrl">
-							<a class="{{app?.applicationBase.licenseUrl ? '' : 'disabled-url'}}"
-                               [href]="app?.applicationBase.licenseUrl"
-                               target="_blank">{{app?.applicationBase.license || 'License'}}</a>
-						</span>
-                        |
-                        <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
-                              tooltipPosition="bottom" [showDelay]="50"
-                              [tooltipDisabled]="!!app?.applicationBase.wwwUrl">
-							<a class="{{app?.applicationBase.wwwUrl ? '' : 'disabled-url'}}"
-                               [href]="app?.applicationBase.wwwUrl">WWW</a>
-						</span>
-                        |
-                        <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
-                              tooltipPosition="bottom" [showDelay]="50"
-                              [tooltipDisabled]="!!app?.applicationBase.sourceUrl">
-							<a class="{{app?.applicationBase.sourceUrl ? '' : 'disabled-url'}}"
-                               [href]="app?.applicationBase.sourceUrl"
-                               target="_blank">{{'APP_INSTANCE.SOURCE' | translate}}</a>
-						</span>
-                        |
-                        <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
-                              tooltipPosition="bottom" [showDelay]="50"
-                              [tooltipDisabled]="!!app?.applicationBase.issuesUrl">
-							<a class="{{app?.applicationBase.issuesUrl ? '' : 'disabled-url'}}"
-                               [href]="app?.applicationBase.issuesUrl"
-                               target="_blank">{{'APP_INSTANCE.ISSUES' | translate}}</a>
-						</span>
-                    </div>
+<div class="" *ngIf="appInstance">
+    <div class="background-section">
+        <div style=" display: flex; flex-direction: row; justify-content: space-between; padding-bottom: 50px">
+            <div style="display: flex; align-items: center;">
+                <div class="" *ngIf="app">
+                    <img alt="App logo"
+                         [src]="(appImagesService.getAppLogoUrl(app?.applicationBase.id) | secure) || 'assets/images/app-logo-example.png'" height="90px"/>
                 </div>
-                <div class="col-xs-12 col-sm-6 col-md-6 col-lg-6 container-bottom-right">
-                    <h3><em style="color: #337ab7;">{{ translateState(appInstanceStatus?.state) }}</em></h3>
+                <div class="" *ngIf="!app">
+                    <img alt="App logo" src="assets/images/app-logo-example.png" height="90px"/>
                 </div>
+                <h2 style="margin:0 20px;">{{appInstance?.name}} ({{app?.applicationBase.name}})</h2>
             </div>
-            <hr>
-            <div class="row">
-                <!-- Tags -->
-                <div class="col-xs-12 col-sm-6 col-md-6 col-lg-6" *ngIf="app?.applicationBase.tags">
+            <h3><em style="color: #337ab7;">{{ translateState(appInstanceStatus?.state) }}</em></h3>
+        </div>
+        <div style=" display: flex; flex-direction: row; justify-content: space-between;">
+            <div class="" style="display: flex;flex-direction: column;">
+                <div class="text-muted mt-2" style="font-size: small;">
+                    {{app?.application.version ? 'v.' + app?.application.version : 'None'}}
+                    |
+                    <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
+                          tooltipPosition="bottom" [showDelay]="50"
+                          [tooltipDisabled]="!!app?.applicationBase.licenseUrl">
+				    <a class="{{app?.applicationBase.licenseUrl ? '' : 'disabled-url'}}"
+                       [href]="app?.applicationBase.licenseUrl"
+                       target="_blank">{{app?.applicationBase.license || 'License'}}</a>
+				</span>
+                    |
+                    <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
+                          tooltipPosition="bottom" [showDelay]="50"
+                          [tooltipDisabled]="!!app?.applicationBase.wwwUrl">
+				    <a class="{{app?.applicationBase.wwwUrl ? '' : 'disabled-url'}}"
+                       [href]="app?.applicationBase.wwwUrl">WWW</a>
+				</span>
+                    |
+                    <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
+                          tooltipPosition="bottom" [showDelay]="50"
+                          [tooltipDisabled]="!!app?.applicationBase.sourceUrl">
+				    <a class="{{app?.applicationBase.sourceUrl ? '' : 'disabled-url'}}"
+                       [href]="app?.applicationBase.sourceUrl"
+                       target="_blank">{{'APP_INSTANCE.SOURCE' | translate}}</a>
+				</span>
+                    |
+                    <span pTooltip="{{'APPLICATIONS.TOOLTIP_MESSAGE_NOT_AVAILABLE' | translate}}"
+                          tooltipPosition="bottom" [showDelay]="50"
+                          [tooltipDisabled]="!!app?.applicationBase.issuesUrl">
+				    <a class="{{app?.applicationBase.issuesUrl ? '' : 'disabled-url'}}"
+                       [href]="app?.applicationBase.issuesUrl"
+                       target="_blank">{{'APP_INSTANCE.ISSUES' | translate}}</a>
+				</span>
+                </div>
+                <div class="" *ngIf="app?.applicationBase.tags">
                     <a *ngFor="let tag of app.applicationBase.tags" class="tag-button">
                         {{tag.name | titlecase}}
                     </a>
                 </div>
-
-                <!-- Deployment buttons -->
-
-                <!-- if application is still being deployed -->
+            </div>
+            <div>
                 <div class=" pull-right"
                      *ngIf="getStateAsEnum(appInstanceStatus?.state) != AppInstanceState.FAILURE
                          && getStateAsEnum(appInstanceStatus?.state) != AppInstanceState.RUNNING
@@ -86,7 +74,7 @@
                 <div *ngIf="appInstance && (
                      getStateAsEnum(appInstanceStatus?.state) == AppInstanceState.RUNNING ||
                      getStateAsEnum(appInstanceStatus?.state) == AppInstanceState.FAILURE)"
-                     class="col-xs-12 col-sm-6 col-md-6 col-lg-6">
+                     class="col-xs-12 col-sm-12 col-md-12 col-lg-12">
                     <div class="btn-group pull-right">
                         <button type="button" class="btn btn-primary dropdown-toggle" data-toggle="dropdown"
                                 aria-haspopup="true" aria-expanded="false">
@@ -95,7 +83,7 @@
                         <ul class="dropdown-menu">
                             <ng-container *ngIf="getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.RUNNING">
                                 <li>
-                                    <a role="button" (click)="this.accessMethodsModal.show()">
+                                    <a role="button" (click)="openAccessMethodsModal()">
                                         {{'APP_INSTANCE.APP_ACCESS_METHODS' | translate}}
                                     </a>
                                 </li>
@@ -162,9 +150,8 @@
                                         {{'APP_INSTANCE.VIEW_LOGS' | translate}}
                                     </a>
                                 </li>
-                                <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN']"
-                                    style="background-color: #ff0000;">
-                                    <a role="button" (click)="this.undeployModal.show()" style="color: #ffffff;">
+                                <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN']">
+                                    <a role="button" (click)="this.undeployModal.show()" style="color: var(--danger-button-color)">
                                         {{'APP_INSTANCE.UNDEPLOY_BUTTON' | translate}}
                                     </a>
                                 </li>
@@ -187,7 +174,7 @@
                                     </a>
                                 </li>
                                 <li>
-                                    <a role="button" style="color: red"
+                                    <a role="button" style="color: var(--danger-button-color)"
                                        *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN']"
                                        (click)="removeConfirm.show()">{{'APP_INSTANCE.REMOVE_BUTTON' | translate}}
                                     </a>
@@ -199,6 +186,83 @@
             </div>
         </div>
     </div>
+    <div class="background-section">
+        <!-- Installation step description text -->
+        <div id="app-progress-info" style="font-size: 16px;" class="">
+            <div id="app-progress-info-sub alert"
+                 [ngClass]="{
+				 'alert-danger': getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.FAILURE || getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.UNKNOWN,
+				 'other-states': getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.FAILURE && getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.UNKNOWN }"
+                 class="">
+                <div *ngIf="getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.FAILURE" class="info-container">
+                    <span class="glyphicon glyphicon-exclamation-sign info-icon" aria-hidden="true"></span>
+                    <span [innerHTML]="'APP_INSTANCE.INSTALLATION_PROGRESS.DEFAULT_ERROR_MESSAGE' | translate"></span>
+                </div>
+                <div *ngIf="getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.FAILURE && getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.UNKNOWN"
+                     class="info-container">
+                    <span class="glyphicon glyphicon-info-sign info-icon" aria-hidden="true"></span>
+                    <span [innerHTML]="'APP_INSTANCE.USER_FRIENDLY.' + getStateAsString(appInstanceStatus?.state) | translate"></span>
+                </div>
+            </div>
+        </div>
+
+        <!-- Progress bar -->
+        <div class=''>
+            <h3 style="margin-bottom: 30px">{{'APP_INSTANCE.INSTALLATION_PROGRESS.HEADER' | translate}}</h3>
+
+
+            <div id="app-prop" class="col-xs-12 col-sm-12 col-md-12 col-lg-12" style="overflow-x: auto;">
+                <nmaas-appinstanceprogress [stages]='getStages()'
+                                           [activeState]="getStateAsEnum(appInstanceStatus?.state)"></nmaas-appinstanceprogress>
+            </div>
+        </div>
+
+
+        <!-- Show additional information checkbox -->
+        <div class="" >
+            <label style="margin-top: 40px">
+                {{ 'APP_INSTANCE.ADDITIONAL_INFO' | translate}}
+                <input type="checkbox" [(ngModel)]="showAppInstanceHistory" (change)="showHistory()">
+            </label>
+        </div>
+
+        <!-- App Instance State History table -->
+        <div class="" *ngIf="this.showAppInstanceHistory && this.appInstanceStateHistory">
+            <h3>{{'APP_INSTANCE.DEPLOYMENT_HISTORY.HEADER' | translate}}</h3>
+            <hr>
+            <table class="table table-hover table-condensed" aria-describedby="App instance deployment history table">
+                <thead>
+                <tr>
+                    <th scope="col">{{'APP_INSTANCE.DEPLOYMENT_HISTORY.TIMESTAMP' | translate}}</th>
+                    <th scope="col">{{'APP_INSTANCE.DEPLOYMENT_HISTORY.STATE_TRANSITIONS' | translate}}</th>
+                    <th scope="col">&nbsp;</th>
+                </tr>
+                </thead>
+                <tbody>
+                <ng-template ngFor let-history
+                             [ngForOf]="this.appInstanceStateHistory | paginate: { itemsPerPage: maxItemsOnPage, currentPage: pageNumber, id: p_first }"
+                             let-isLast="last">
+                    <tr>
+                        <td>{{history.timestamp | localDate:'medium' }}</td>
+                        <td *ngIf="history.previousState !== null">
+                            {{history.previousState | translate }}
+                            <span class="glyphicon glyphicon-arrow-right"
+                                  style="padding-left: 5px;padding-right: 5px"></span>
+                            {{history.currentState | translate }}
+                        </td>
+                        <td *ngIf="history.previousState === null">{{history.currentState | translate }}</td>
+                    </tr>
+                </ng-template>
+                </tbody>
+            </table>
+            <pagination-controls class="text-right" (pageChange)="pageNumber = $event" id="{{ p_first }}"
+                                 previousLabel="{{ 'PAGINATION.PREVIOUS' | translate }}"
+                                 nextLabel="{{ 'PAGINATION.NEXT' | translate }}"
+                                 screenReaderPaginationLabel="{{ 'PAGINATION.SCREEN_READER.PAGINATION' | translate }}"
+                                 screenReaderPageLabel="{{ 'PAGINATION.SCREEN_READER.PAGE' | translate }}"
+                                 screenReaderCurrentLabel="{{ 'PAGINATION.SCREEN_READER.CURRENT' | translate }}"></pagination-controls>
+        </div>
+    </div>
 
     <!-- Undeploy modal-->
     <nmaas-modal styleModal="warning" #undeployModal>
@@ -211,10 +275,10 @@
             </div>
         </div>
         <div class="nmaas-modal-footer">
-            <button type="button" class="btn btn-danger"
-                    (click)="this.undeploy()">{{'UNDEPLOY_MODAL.YES_BUTTON' | translate}}</button>
             <button type="button" class="btn btn-primary"
                     (click)="this.undeployModal.hide()">{{'UNDEPLOY_MODAL.CANCEL_BUTTON' | translate}}</button>
+            <button type="button" class="btn btn-danger"
+                    (click)="this.undeploy()">{{'UNDEPLOY_MODAL.YES_BUTTON' | translate}}</button>
         </div>
     </nmaas-modal>
 
@@ -238,11 +302,11 @@
             </div>
         </div>
         <div class="nmaas-modal-footer">
+            <button type="button" class="btn btn-secondary"
+                    (click)="this.manualUpdateModal.hide()">{{'UNDEPLOY_MODAL.CANCEL_BUTTON' | translate}}</button>
             <button type="button" class="btn btn-primary "
                     [disabled]="appVersions.length === 0 || selectedVersion === ''"
                     (click)="this.manualUpdateVersion()">{{'APP_INSTANCES.MANUAL_UPDATE.YES_BUTTON' | translate}}</button>
-            <button type="button" class="btn btn-secondary"
-                    (click)="this.manualUpdateModal.hide()">{{'UNDEPLOY_MODAL.CANCEL_BUTTON' | translate}}</button>
         </div>
     </nmaas-modal>
 
@@ -301,82 +365,6 @@
         </div>
     </nmaas-modal>
 
-    <!-- Installation step description text -->
-    <div id="app-progress-info" style="font-size: 16px;" class="col-xs-12">
-        <div id="app-progress-info-sub alert"
-             [ngClass]="{
-				 'alert-danger': getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.FAILURE || getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.UNKNOWN,
-				 'other-states': getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.FAILURE && getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.UNKNOWN }"
-             class="col-xs-offset-1 col-xs-10">
-            <div *ngIf="getStateAsEnum(appInstanceStatus?.state) === AppInstanceState.FAILURE" class="info-container">
-                <span class="glyphicon glyphicon-exclamation-sign info-icon" aria-hidden="true"></span>
-                <span [innerHTML]="'APP_INSTANCE.INSTALLATION_PROGRESS.DEFAULT_ERROR_MESSAGE' | translate"></span>
-            </div>
-            <div *ngIf="getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.FAILURE && getStateAsEnum(appInstanceStatus?.state) !== AppInstanceState.UNKNOWN"
-                 class="info-container">
-                <span class="glyphicon glyphicon-info-sign info-icon" aria-hidden="true"></span>
-                <span [innerHTML]="'APP_INSTANCE.USER_FRIENDLY.' + getStateAsString(appInstanceStatus?.state) | translate"></span>
-            </div>
-        </div>
-    </div>
-
-    <!-- Progress bar -->
-    <div class='row'>
-        <h3>{{'APP_INSTANCE.INSTALLATION_PROGRESS.HEADER' | translate}}</h3>
-        <hr>
-
-        <div id="app-prop" class="col-xs-12 col-sm-12 col-md-12 col-lg-12" style="overflow-x: auto;">
-            <nmaas-appinstanceprogress [stages]='getStages()'
-                                       [activeState]="getStateAsEnum(appInstanceStatus?.state)"></nmaas-appinstanceprogress>
-        </div>
-    </div>
-    <hr>
-
-    <!-- Show additional information checkbox -->
-    <div class="row">
-        <label>
-            {{ 'APP_INSTANCE.ADDITIONAL_INFO' | translate}}
-            <input type="checkbox" [(ngModel)]="showAppInstanceHistory" (change)="showHistory()">
-        </label>
-    </div>
-
-    <!-- App Instance State History table -->
-    <div class="row" *ngIf="this.showAppInstanceHistory && this.appInstanceStateHistory">
-        <h3>{{'APP_INSTANCE.DEPLOYMENT_HISTORY.HEADER' | translate}}</h3>
-        <hr>
-        <table class="table table-hover table-condensed" aria-describedby="App instance deployment history table">
-            <thead>
-            <tr>
-                <th scope="col">{{'APP_INSTANCE.DEPLOYMENT_HISTORY.TIMESTAMP' | translate}}</th>
-                <th scope="col">{{'APP_INSTANCE.DEPLOYMENT_HISTORY.STATE_TRANSITIONS' | translate}}</th>
-                <th scope="col">&nbsp;</th>
-            </tr>
-            </thead>
-            <tbody>
-            <ng-template ngFor let-history
-                         [ngForOf]="this.appInstanceStateHistory | paginate: { itemsPerPage: maxItemsOnPage, currentPage: pageNumber, id: p_first }"
-                         let-isLast="last">
-                <tr>
-                    <td>{{history.timestamp | localDate:'medium' }}</td>
-                    <td *ngIf="history.previousState !== null">
-                        {{history.previousState | translate }}
-                        <span class="glyphicon glyphicon-arrow-right"
-                              style="padding-left: 5px;padding-right: 5px"></span>
-                        {{history.currentState | translate }}
-                    </td>
-                    <td *ngIf="history.previousState === null">{{history.currentState | translate }}</td>
-                </tr>
-            </ng-template>
-            </tbody>
-        </table>
-        <pagination-controls class="text-right" (pageChange)="pageNumber = $event" id="{{ p_first }}"
-                             previousLabel="{{ 'PAGINATION.PREVIOUS' | translate }}"
-                             nextLabel="{{ 'PAGINATION.NEXT' | translate }}"
-                             screenReaderPaginationLabel="{{ 'PAGINATION.SCREEN_READER.PAGINATION' | translate }}"
-                             screenReaderPageLabel="{{ 'PAGINATION.SCREEN_READER.PAGE' | translate }}"
-                             screenReaderCurrentLabel="{{ 'PAGINATION.SCREEN_READER.CURRENT' | translate }}"></pagination-controls>
-    </div>
-
     <!-- apply config modal -->
     <nmaas-modal styleModal="info" #applyConfig>
         <div class="nmaas-modal-header">
@@ -414,10 +402,11 @@
             {{'REDEPLOY_MODAL.BODY' | translate}}
         </div>
         <div class="nmaas-modal-footer">
-            <button type="button" class="btn btn-primary"
-                    (click)="redeploy(); redeployConfirm.hide()">{{'REDEPLOY_MODAL.OK_BUTTON' | translate}}</button>
             <button type="button" class="btn btn-secondary"
                     (click)="redeployConfirm.hide()">{{'REDEPLOY_MODAL.CANCEL_BUTTON' | translate}}</button>
+            <button type="button" class="btn btn-primary"
+                    (click)="redeploy(); redeployConfirm.hide()">{{'REDEPLOY_MODAL.OK_BUTTON' | translate}}</button>
+
         </div>
     </nmaas-modal>
 
@@ -430,10 +419,10 @@
             {{'REMOVE_MODAL.BODY' | translate}}
         </div>
         <div class="nmaas-modal-footer">
-            <button type="button" class="btn btn-primary"
-                    (click)="removalFailedInstance(); removeConfirm.hide()">{{'REMOVE_MODAL.OK_BUTTON' | translate}}</button>
             <button type="button" class="btn btn-secondary"
                     (click)="removeConfirm.hide()">{{'REMOVE_MODAL.CANCEL_BUTTON' | translate}}</button>
+            <button type="button" class="btn btn-primary"
+                    (click)="removalFailedInstance(); removeConfirm.hide()">{{'REMOVE_MODAL.OK_BUTTON' | translate}}</button>
         </div>
     </nmaas-modal>
 
@@ -446,10 +435,10 @@
             <div [innerHTML]="'ENABLE_AUTO_UPGRADES_MODAL.BODY' | translate"></div>
         </div>
         <div class="nmaas-modal-footer">
-            <button type="button" class="btn btn-primary"
-                    (click)="enableAutoUpgrades(); enableAutoUpgradesConfirm.hide()">{{'ENABLE_AUTO_UPGRADES_MODAL.OK_BUTTON' | translate}}</button>
             <button type="button" class="btn btn-secondary"
                     (click)="enableAutoUpgradesConfirm.hide()">{{'ENABLE_AUTO_UPGRADES_MODAL.CANCEL_BUTTON' | translate}}</button>
+            <button type="button" class="btn btn-primary"
+                    (click)="enableAutoUpgrades(); enableAutoUpgradesConfirm.hide()">{{'ENABLE_AUTO_UPGRADES_MODAL.OK_BUTTON' | translate}}</button>
         </div>
     </nmaas-modal>
 
@@ -462,10 +451,10 @@
             <div [innerHTML]="'DISABLE_AUTO_UPGRADES_MODAL.BODY' | translate"></div>
         </div>
         <div class="nmaas-modal-footer">
-            <button type="button" class="btn btn-primary"
-                    (click)="disableAutoUpgrades(); disableAutoUpgradesConfirm.hide()">{{'DISABLE_AUTO_UPGRADES_MODAL.OK_BUTTON' | translate}}</button>
             <button type="button" class="btn btn-secondary"
                     (click)="disableAutoUpgradesConfirm.hide()">{{'DISABLE_AUTO_UPGRADES_MODAL.CANCEL_BUTTON' | translate}}</button>
+            <button type="button" class="btn btn-primary"
+                    (click)="disableAutoUpgrades(); disableAutoUpgradesConfirm.hide()">{{'DISABLE_AUTO_UPGRADES_MODAL.OK_BUTTON' | translate}}</button>
         </div>
     </nmaas-modal>
 
diff --git a/src/app/appmarket/appinstance/appinstance/appinstance.component.spec.ts b/src/app/appmarket/appinstance/appinstance/appinstance.component.spec.ts
index 449459e4f4b881d437f763ae6433b6b45ad4b7b7..89a7c18a4588f435c824b0041fc9a844f1874499 100644
--- a/src/app/appmarket/appinstance/appinstance/appinstance.component.spec.ts
+++ b/src/app/appmarket/appinstance/appinstance/appinstance.component.spec.ts
@@ -159,6 +159,7 @@ describe('Component: AppInstance', () => {
         domainDcnDetails: null,
         domainTechDetails: null,
         groups: [],
+        clusters: [],
         applicationStatePerDomain: [
             {
                 applicationBaseId: 2,
@@ -186,6 +187,7 @@ describe('Component: AppInstance', () => {
         createdAt: new Date(),
         descriptiveDeploymentId: 'test-oxidized-48',
         domainId: 4,
+        domainName: "Test Domain",
         id: 1,
         internalId: 'eccbaf70-7fdd-401a-bb3e-b8659bcfbdff',
         name: 'oxi-virt-1',
diff --git a/src/app/appmarket/appinstance/appinstance/appinstance.component.ts b/src/app/appmarket/appinstance/appinstance/appinstance.component.ts
index c4ce87cd4c01e91f4f95949c30428da0c5ec570d..543a563ff26a4089231b8e225fbcc4512120f17c 100644
--- a/src/app/appmarket/appinstance/appinstance/appinstance.component.ts
+++ b/src/app/appmarket/appinstance/appinstance/appinstance.component.ts
@@ -164,8 +164,6 @@ export class AppInstanceComponent implements OnInit, OnDestroy {
                     this.configurationTemplate = this.getTemplate(appInstance.configWizardTemplate.template);
                     this.app = appInstance.application;
 
-                    this.updateAppInstancePodNames();
-
                     this.submission.data.configuration = JSON.parse(appInstance.configuration);
 
                     if (this.appInstance.configUpdateWizardTemplate != null) {
@@ -645,4 +643,13 @@ export class AppInstanceComponent implements OnInit, OnDestroy {
     }
 
 
+    public openAccessMethodsModal(): void {
+        this.appInstanceService.getDeploymentParameters(this.appInstanceId).subscribe(
+            deployParams => {
+                this.deployParametersSubject.next(deployParams)
+                this.accessMethodsModal.show()   ;
+    })
+      
+    }
+
 }
diff --git a/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.css b/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.css
index 0253fa70fbc1fcf20b1873fbd2d8360ddaa3309a..a1f3548446b32f144eaa14a1c003ce1a2b358506 100644
--- a/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.css
+++ b/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.css
@@ -25,7 +25,7 @@
     height: 20px;
 }
 
-tr.clickable {
+.clickable {
     cursor: pointer;
 }
 
@@ -39,52 +39,7 @@ label{
     margin-bottom: 0;
     font-weight: unset;
 }
-:host ::ng-deep .p-datatable .p-datatable-thead > tr > th{
-    border: 1px solid #E0E2E5;
-    border-width: 0 0 1px 0;
-}
-:host ::ng-deep .p-datatable .p-datatable-tbody > tr > td {
-    text-align: left;
-    border: 1px solid #E0E2E5;
-    border-width: 0 0 1px 0;
-    padding: 1rem 1rem;
-}
-:host ::ng-deep .p-datatable .p-paginator-bottom{
-    height: 40px;
-    background: transparent;
-    border: none;
-    margin-top:10px;
-}
-:host ::ng-deep .p-datatable .p-datatable-tbody > tr{
-    background: transparent;
-}
-
-:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page{
-    transition: unset;
-    border-radius: 50%;
-    min-width:3.5rem;
-    height:3.5rem;
-    margin:0 5px;
-    font-size: 14px;
-}
 
-:host ::ng-deep .p-paginator-element{
-    border-radius:50%;
-    margin:0 5px;
-    min-width:3.5rem;
-    height:3.5rem;
-    font-size: 14px;
-}
-:host ::ng-deep .p-paginator .p-dropdown{
-    height:3rem;
-}
-:host ::ng-deep .p-paginator-icon{
-    height: 1.5rem;
-    width: 1.5rem;
-}
-:host ::ng-deep .p-paginator .p-dropdown .p-dropdown-label{
-    padding-right: 10px;
-}
 ::ng-deep.p-selectbutton .p-button.p-highlight{
     background: var(--primary-button-color) !important;
     border-color: var(--primary-button-color);
@@ -100,3 +55,36 @@ label{
     border-color: var(--primary-button-color);
     color: var(--background);
 }
+:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page.p-highlight{
+    background: var(--user-button-background-hover);
+}
+:host ::ng-deep .p-button.p-button-icon-only{
+    width: unset;
+}
+::ng-deep .running .p-progressbar .p-progressbar-value {
+    background: #EBBD59;
+}
+.running{
+    color: #EBBD59;
+    font-weight: bold;
+}
+::ng-deep .failure .p-progressbar .p-progressbar-value{
+    background: #AA0404;
+}
+.failure{
+    color: #AA0404;
+    font-weight: bold;
+}
+::ng-deep .done .p-progressbar .p-progressbar-value{
+    background: #136214;
+}
+.done{
+    color: #136214;
+    font-weight: bold;
+}
+::ng-deep .p-progressbar .p-progressbar-label{
+    display: none;
+}
+p-selectbutton{
+    width: max-content;
+}
diff --git a/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.html b/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.html
index 2713e4d1baf36a9ca2ba56cc5eee3e7a089dcf68..7af02f7f4a03f7036cea696cf1beb791583dcfca 100644
--- a/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.html
+++ b/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.html
@@ -1,28 +1,37 @@
-<div style="display: flex; align-items: center; justify-content: space-between; margin-top:20px">
+<div style="display: flex; align-items: flex-start; justify-content: space-between; margin-top:20px">
     <div style="display:flex; align-items: center;">
-        <input pInputText name="search" id="search" placeholder="Search" type="text" [(ngModel)]="searchValue">
-        <div style="margin-left:20px">
+        <span class="p-input-icon-right">
+            <i class="pi pi-search" style="font-size: 13px; top: 16px; margin-right: 5px;"></i>
+             <input pInputText class="form-control" name="search" id="search" placeholder="Search" type="text" [(ngModel)]="searchValue">
+        </span>
+        <div style="display: flex; margin: 0 20px">
+            <p-checkbox id="show_my" inputId="show_my" binary="true" [(ngModel)]="showAll" (onChange)="onSelectionChange()"  [ngModelOptions]="{standalone: true}" ngDefaultControl></p-checkbox>
+            <label for="show_my" style="text-wrap: nowrap">Show all instances</label>
+        </div>
+        <div style="display: flex">
             <p-checkbox *domainRoles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR'];domainId:domainId"
                         id="show_visible" inputId="show_visible" binary="true" [(ngModel)]="undeployedVisible" [ngModelOptions]="{standalone: true}"></p-checkbox>
-            <label for="show_visible" *domainRoles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR'];domainId:domainId">{{'APP_INSTANCES.UNDEPLOYED_VISIBLE' | translate}}</label>
+            <label for="show_visible" style="text-wrap: nowrap" *domainRoles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR'];domainId:domainId">{{'APP_INSTANCES.UNDEPLOYED_VISIBLE' | translate}}</label>
         </div>
     </div>
     <div class="" style="display: inline-flex; align-items: center">
-        <label class="mr-3" for="selectionType">{{ 'APP_INSTANCES.SHOW' | translate }}: </label>
         <p-selectButton
                 id="selectionType"
-                [options]="selectionOptions"
-                [(ngModel)]="listSelection"
+                [options]="viewOptions"
+                [(ngModel)]="selectedOption"
                 [ngModelOptions]="{standalone: true}"
-                (ngModelChange)="onSelectionChange($event)"
                 optionLabel="label"
                 optionValue="value"
-                ngDefaultControl/>
+                ngDefaultControl>
+            <ng-template let-item pTemplate>
+                <i style="font-size: 14px; padding: 0 10px" [class]="item.icon"></i>
+            </ng-template>
+        </p-selectButton>
     </div>
 </div>
 
 <h4 style="margin-top:40px; font-weight: bold" *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']">{{ 'APP_INSTANCES.DEPLOYED' | translate }}</h4>
-<div class="background-section" style="margin-top:30px">
+<div *ngIf="selectedOption === 'list'" class="background-section" style="margin-top:30px">
     <p-table [value]="appDeployedInstances | async | searchAppInstance: searchValue"
              [paginator]="true"
              [rows]="maxItemsOnPage"
@@ -51,7 +60,7 @@
                 <td>{{ appInstance?.applicationName }}</td>
                 <td>{{ appInstance?.applicationVersion }}</td>
                 <td *ngIf="domainId === undefined || domainId === domainService.getGlobalDomainId()">
-                    {{ getDomainNameById(appInstance?.domainId) }}
+                    {{ appInstance?.domainName }}
                 </td>
                 <td>{{ appInstance?.owner?.username }}</td>
                 <td>{{ appInstance?.createdAt | localDate:'dd-MM-yyyy HH:mm' }}</td>
@@ -66,9 +75,52 @@
     </p-table>
 </div>
 
+<div *ngIf="selectedOption === 'cards'" class="grid col-12">
+    <div class="col-lg-4 col-md-6 col-sm-6 col-xs-12"  *ngFor="let appInstance of appDeployedInstances | async | searchAppInstance: searchValue">
+        <div class="background-section" [ngClass]="{'clickable': !userHasGuestRoleInCurrentDomain()}"
+             [routerLink]="userHasGuestRoleInCurrentDomain() ? [] : [appInstance.id]" >
+            <div  style="display:flex; justify-content: space-between; margin-bottom: 30px">
+                <div>
+                    <p>{{appInstance?.name}}</p>
+                    <p>{{ appInstance?.applicationName }}</p>
+                </div>
+                <div>
+                    <div class="" *ngIf="appInstance?.application">
+                        <img alt="App logo"
+                             [src]="(appImagesService.getAppLogoUrl(appInstance?.application.applicationBase.id) | secure) || 'assets/images/app-logo-example.png'" height="50px"/>
+                    </div>
+                    <div class="" *ngIf="!appInstance?.application">
+                        <img alt="App logo" src="assets/images/app-logo-example.png" height="50px"/>
+                    </div>
+                </div>
+            </div>
+            <div  *ngIf="getStateAsEnum(appInstance?.state) == AppInstanceState.FAILURE ||
+                    getStateAsEnum(appInstance?.state) == AppInstanceState.REMOVED">
+                <p class="failure">{{ translateState(appInstance?.state) }}</p>
+                <p-progressBar class="failure" [value]="100" [style]="{'height': '6px'}"></p-progressBar>
+            </div>
+            <div  *ngIf="getStateAsEnum(appInstance?.state) == AppInstanceState.RUNNING ||
+                    getStateAsEnum(appInstance?.state) == AppInstanceState.DEPLOYING ||
+                    getStateAsEnum(appInstance?.state) == AppInstanceState.CONFIGURATION_AWAITING ||
+                    getStateAsEnum(appInstance?.state) == AppInstanceState.CONNECTING">
+                <p class="running">{{ translateState(appInstance?.state) }}</p>
+                <p-progressBar class="running" mode="indeterminate" [style]="{'height': '6px'}"></p-progressBar>
+            </div>
+            <div  *ngIf="getStateAsEnum(appInstance?.state) == AppInstanceState.DONE ||
+                    getStateAsEnum(appInstance?.state) == AppInstanceState.RUNNING ">
+                <p class="done">{{ translateState(appInstance?.state) }}</p>
+                <p-progressBar class="done" [value]="100" [style]="{'height': '6px'}"></p-progressBar>
+            </div>
+
+
+        </div>
+    </div>
+
+</div>
+
 <div style="margin-top:40px"  *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']">
-    <h4 style="margin-top:40px; font-weight: bold" *ngIf="undeployedVisible">{{ 'APP_INSTANCES.UNDEPLOYED' | translate }}</h4>
-    <div style="margin-top:30px" *ngIf="undeployedVisible" class="background-section">
+    <h4 class="header" *ngIf="undeployedVisible">{{ 'APP_INSTANCES.UNDEPLOYED' | translate }}</h4>
+    <div style="margin-top:30px" *ngIf="undeployedVisible && selectedOption === 'list'" class="background-section">
         <p-table [value]="appUndeployedInstances | async | paginate: { itemsPerPage: maxItemsOnPageSec, currentPage: secondPageNumber, id: p_second }"
                  [paginator]="true"
                  [rows]="maxItemsOnPageSec"
@@ -91,7 +143,7 @@
                     <td>{{ appInstance?.name }}</td>
                     <td>{{ appInstance?.applicationName }}</td>
                     <td *ngIf="domainId === undefined || domainId === domainService.getGlobalDomainId()">
-                        {{ getDomainNameById(appInstance?.domainId) }}
+                        {{ appInstance?.domainName }}
                     </td>
                     <td>{{ appInstance?.owner?.username }}</td>
                     <td>{{ appInstance?.createdAt | localDate:'dd-MM-yyyy HH:mm' }}</td>
diff --git a/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.ts b/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.ts
index bf81b9835a99a41308b8073d3f2849cbed6d0073..6c09b32f86857764f1631aa41a5580bd094e2449 100644
--- a/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.ts
+++ b/src/app/appmarket/appinstance/appinstancelist/appinstancelist.component.ts
@@ -1,7 +1,7 @@
 import {Component, OnInit} from '@angular/core';
 
 import {AppInstance, AppInstanceState, parseAppInstanceState} from '../../../model';
-import {AppConfigService, AppInstanceService, CustomerSearchCriteria, DomainService} from '../../../service';
+import {AppConfigService, AppImagesService, AppInstanceService, CustomerSearchCriteria, DomainService} from '../../../service';
 import {AuthService} from '../../../auth/auth.service';
 import {UserDataService} from '../../../service/userdata.service';
 import {forkJoin, Observable, of} from 'rxjs';
@@ -23,6 +23,7 @@ export enum AppInstanceListSelection {
 export class AppInstanceListComponent implements OnInit {
 
     public undeployedVisible = false;
+    public showAll = false;
 
     private readonly item_number_key: string = 'item_number_per_page';
     private readonly list_selection_key: string = 'list_selection';
@@ -53,12 +54,13 @@ export class AppInstanceListComponent implements OnInit {
     public domainId = 0;
 
     public domains: Domain[] = [];
+    public viewOptions = [
+        {icon: 'pi pi-list', value: 'list'},
+        {icon: 'pi pi-th-large', value: 'cards'}
+    ];
+    public selectedOption = 'list';
 
     public searchValue = '';
-    public selectionOptions = [
-        { label: this.translateEnum(AppInstanceListSelection.ALL), value: AppInstanceListSelection.ALL },
-        { label: this.translateEnum(AppInstanceListSelection.MY), value: AppInstanceListSelection.MY },
-    ];
 
 
     constructor(private appInstanceService: AppInstanceService,
@@ -67,15 +69,13 @@ export class AppInstanceListComponent implements OnInit {
                 public authService: AuthService,
                 private appConfig: AppConfigService,
                 private translateService: TranslateService,
-                private sessionService: SessionService) {
+                private sessionService: SessionService,
+                public appImagesService: AppImagesService) {
 
     }
 
     ngOnInit() {
         this.sessionService.registerCulture(this.translateService.currentLang);
-        this.domainService.getAll().subscribe(result => {
-            this.domains.push(...result);
-        });
         const i = sessionStorage.getItem(this.item_number_key);
         if (i) {
             this.maxItemsOnPage = +i;
@@ -85,6 +85,7 @@ export class AppInstanceListComponent implements OnInit {
         const ls = AppInstanceListSelection[sessionStorage.getItem(this.list_selection_key)];
         if (ls !== undefined) {
             this.listSelection = ls;
+            this.showAll = ls === AppInstanceListSelection.ALL;
         }
         console.log(this.listSelection);
         this.userDataService.selectedDomainId.subscribe(domainId => {
@@ -97,49 +98,6 @@ export class AppInstanceListComponent implements OnInit {
 
             this.update(domainId)
         });
-        forkJoin({
-            all: this.translateService.get('ENUM.ALL'),
-            my: this.translateService.get('ENUM.MY')
-        }).subscribe(translations => {
-            this.selectionOptions = [
-                { label: translations.all, value: AppInstanceListSelection.ALL },
-                { label: translations.my, value: AppInstanceListSelection.MY },
-            ];
-        });
-
-
-        forkJoin({
-            all: this.translateService.get('ENUM.ALL'),
-            my: this.translateService.get('ENUM.MY')
-        }).subscribe(translations => {
-            this.selectionOptions = [
-                { label: translations.all, value: AppInstanceListSelection.ALL },
-                { label: translations.my, value: AppInstanceListSelection.MY },
-            ];
-        });
-
-    }
-
-    public getDomainNameById(id: number): string {
-        if (this.domains === undefined) {
-            return 'none';
-        }
-        return this.domains.find(value => value.id === id).name;
-    }
-
-    public translateEnum(value: AppInstanceListSelection): string {
-        let outValue = '';
-        if (value.toString() === 'ALL') {
-            this.translateService.get('ENUM.ALL').subscribe((res: string) => {
-                outValue = res;
-            })
-        }
-        if (value.toString() === 'MY') {
-            this.translateService.get('ENUM.MY').subscribe((res: string) => {
-                outValue = res;
-            })
-        }
-        return outValue;
     }
 
     public update(domainId: number): void {
@@ -165,7 +123,11 @@ export class AppInstanceListComponent implements OnInit {
             || this.authService.hasDomainRole(app.domainId, 'ROLE_USER');
     }
 
-    public onSelectionChange(event) {
+    public onSelectionChange() {
+        this.listSelection = this.showAll
+            ? AppInstanceListSelection.ALL
+            : AppInstanceListSelection.MY;
+
         sessionStorage.setItem(this.list_selection_key, AppInstanceListSelection[this.listSelection]);
         this.update(this.domainId);
     }
@@ -240,4 +202,8 @@ export class AppInstanceListComponent implements OnInit {
     public userHasGuestRoleInCurrentDomain(): boolean {
         return this.authService.hasDomainRole(this.domainId, 'ROLE_GUEST');
     }
+
+    public getStateAsEnum(state: string | AppInstanceState): AppInstanceState {
+        return typeof state === 'string' ? AppInstanceState[state] : state;
+    }
 }
diff --git a/src/app/appmarket/appinstance/modals/add-members-modal/add-members-modal.component.spec.ts b/src/app/appmarket/appinstance/modals/add-members-modal/add-members-modal.component.spec.ts
index 4a613f1394d03e28924f20c069a4f8c3e716cf28..0e2900d4ff0f8e9c11652b992abff6e0be6964e8 100644
--- a/src/app/appmarket/appinstance/modals/add-members-modal/add-members-modal.component.spec.ts
+++ b/src/app/appmarket/appinstance/modals/add-members-modal/add-members-modal.component.spec.ts
@@ -32,6 +32,7 @@ describe('AddMembersModalComponent', () => {
         createdAt: new Date(),
         descriptiveDeploymentId: 'test-oxidized-48',
         domainId: 4,
+        domainName: "Test Domain",
         id: 1,
         internalId: 'eccbaf70-7fdd-401a-bb3e-b8659bcfbdff',
         name: 'oxi-virt-1',
diff --git a/src/app/appmarket/applist/applist.component.html b/src/app/appmarket/applist/applist.component.html
index e39a6a560095b604441ce2ea47ba6c4ed49cbe32..4e46de83f11494f1d5ac48708eb7782aac7f1af4 100644
--- a/src/app/appmarket/applist/applist.component.html
+++ b/src/app/appmarket/applist/applist.component.html
@@ -1 +1 @@
-<nmaas-applications-view class="col-sm-12 col-sm-12 col-md-12" [domainId]="domainId" [appView]="appsView"></nmaas-applications-view>
+<nmaas-applications-view class="col-sm-12 col-sm-12 col-md-12" style="padding:0;" [domainId]="domainId" [appView]="appsView"></nmaas-applications-view>
diff --git a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.css b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..f2c387a9db7ec1e2c9aeefc41a92b4d6336c9fdb
--- /dev/null
+++ b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.css
@@ -0,0 +1,38 @@
+:host ::ng-deep input[type=file]{
+    display:none;
+}
+:host ::ng-deep  .p-button{
+    width: unset;
+    margin-right: 5px;
+    background: var(--primary-button-color);
+    color: var(--button-text-color);
+}
+:host ::ng-deep .p-button:hover{
+    background: var(--primary-button-hover);
+    border:none;
+}
+:host ::ng-deep .p-button-label{
+    font-weight: normal;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-buttonbar{
+    border: none;
+    background: transparent;
+    margin-bottom: 10px;
+    padding: 0;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-content{
+    border: none;
+    padding: 0;
+    border-radius: 3px;
+
+}
+:host ::ng-deep .p-fileupload-content .p-progressbar{
+    display: none;
+}
+textarea{
+    border-color: #ccc;
+}
+:host ::ng-deep .p-inputtext:enabled:focus{
+    box-shadow: none;
+    border-color: var(--l-text-color);
+}
diff --git a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.html b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.html
index 4fbade572a717bc1ceaa366511bc588551d6f8b7..ebd41c48dae2e11520b48a6727d77f2ad92d16f0 100644
--- a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.html
+++ b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.html
@@ -14,7 +14,7 @@
             <div style="margin-bottom: 10px">
                 {{ 'APPS_MANAGEMENT.ADD_JSON_TEXTAREA'| translate}}
             </div>
-            <textarea rows="10" cols="100" pInputTextarea [(ngModel)]="jsonText" (keyup)="this.JsonError = false; this.error = ''"></textarea>
+            <textarea pInputTextarea rows="10" cols="100" style="min-height: 200px; width: 100%" [autoResize]="true"  [(ngModel)]="jsonText" (keyup)="this.JsonError = false; this.error = ''"></textarea>
         </div>
         <div class="flex flex-row justify-content-center justify-content-center mt-2">
             <button *ngIf="jsonText.length >0" pButton class="btn btn-secondary"
diff --git a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.spec.ts b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.spec.ts
index e7ad001d3a837a971adbc8b9c1dc216762b20d64..061fc3dfa636a27175d86b3c25866756c197e669 100644
--- a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.spec.ts
+++ b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.spec.ts
@@ -1,34 +1,39 @@
 import { ComponentFixture, TestBed } from '@angular/core/testing';
-
 import { AppAddJsonAppComponent } from './app-add-json-app.component';
-import {HttpClientTestingModule, HttpTestingController} from '@angular/common/http/testing';
-import {RouterTestingModule} from '@angular/router/testing';
-import {TranslateFakeLoader, TranslateLoader, TranslateModule} from '@ngx-translate/core';
+import { ModalComponent } from '../../../shared';
+import { AppsService } from '../../../service';
+import { Router } from '@angular/router';
+import { of, throwError } from 'rxjs';
 import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+import { TranslateFakeLoader, TranslateLoader, TranslateModule } from '@ngx-translate/core';
 
 describe('AppAddJsonAppComponent', () => {
   let component: AppAddJsonAppComponent;
   let fixture: ComponentFixture<AppAddJsonAppComponent>;
+  let mockAppsService: jasmine.SpyObj<AppsService>;
+  let mockRouter: jasmine.SpyObj<Router>;
 
   beforeEach(async () => {
+    mockAppsService = jasmine.createSpyObj('AppsService', ['createApplicationDTO']);
+    mockRouter = jasmine.createSpyObj('Router', ['navigate']);
+
     await TestBed.configureTestingModule({
-      declarations: [ AppAddJsonAppComponent ],
+      declarations: [AppAddJsonAppComponent, ModalComponent],
       imports: [
-          HttpClientTestingModule,
-        RouterTestingModule,
-        TranslateModule.forRoot({
-          loader: {
-            provide: TranslateLoader,
-            useClass: TranslateFakeLoader
-          }
-        }),
+          TranslateModule.forRoot({
+                    loader: {
+                        provide: TranslateLoader,
+                        useClass: TranslateFakeLoader
+                    }
+                }),
       ],
-      schemas: [CUSTOM_ELEMENTS_SCHEMA,NO_ERRORS_SCHEMA],
-    })
-    .compileComponents();
-  });
+      providers: [
+        { provide: AppsService, useValue: mockAppsService },
+        { provide: Router, useValue: mockRouter }
+      ],
+      schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA]
+    }).compileComponents();
 
-  beforeEach(() => {
     fixture = TestBed.createComponent(AppAddJsonAppComponent);
     component = fixture.componentInstance;
     fixture.detectChanges();
@@ -37,4 +42,72 @@ describe('AppAddJsonAppComponent', () => {
   it('should create', () => {
     expect(component).toBeTruthy();
   });
+
+  it('should handle valid JSON upload', () => {
+    const mockFile = new Blob([JSON.stringify({ key: 'value' })], { type: 'application/json' });
+    const mockEvent = { files: [mockFile] };
+    mockAppsService.createApplicationDTO.and.returnValue(of({ id: '123' }));
+
+    spyOn(component, 'uploadHandler');
+    component.onUpload(mockEvent);
+
+    const fileReader = new FileReader();
+    fileReader.onload = () => {
+      expect(component.uploadHandler).toHaveBeenCalledWith({ id: '123' });
+    };
+  });
+
+  it('should handle invalid JSON upload', () => {
+    const mockFile = new Blob(['invalid json'], { type: 'application/json' });
+    const mockEvent = { files: [mockFile] };
+
+    component.onUpload(mockEvent);
+
+    const fileReader = new FileReader();
+    fileReader.onload = () => {
+      expect(component.JsonError).toBeTrue();
+    };
+  });
+
+  it('should handle valid JSON text submission', () => {
+    component.jsonText = JSON.stringify({ key: 'value' });
+    mockAppsService.createApplicationDTO.and.returnValue(of({ id: '123' }));
+
+    spyOn(component, 'uploadHandler');
+    component.sendJsonText();
+
+    expect(component.uploadHandler).toHaveBeenCalledWith({ id: '123' });
+  });
+
+  it('should handle invalid JSON text submission', () => {
+    component.jsonText = 'invalid json';
+
+    component.sendJsonText();
+
+    expect(component.JsonError).toBeTrue();
+  });
+
+  it('should handle error during JSON submission', () => {
+    component.jsonText = JSON.stringify({ key: 'value' });
+    mockAppsService.createApplicationDTO.and.returnValue(throwError({ message: 'Error occurred' }));
+
+    component.sendJsonText();
+
+    expect(component.error).toBe('Error occurred');
+  });
+
+  it('should navigate to app details on successful upload', () => {
+    const mockResult = { id: '123' };
+
+    component.uploadHandler(mockResult);
+
+    expect(mockRouter.navigate).toHaveBeenCalledWith(['apps', '123']);
+  });
+
+  it('should show modal', () => {
+    spyOn(component.modal, 'show');
+    component.show();
+
+    expect(component.modal.show).toHaveBeenCalled();
+  });
 });
diff --git a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.ts b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.ts
index e0d4bf65b773d08f3427a7c5fcec100a4a99d6d7..10e18dcfc0598fd779fe86dbd52a66e796f8bf94 100644
--- a/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.ts
+++ b/src/app/appmarket/appmanagement/app-add-json-app/app-add-json-app.component.ts
@@ -6,7 +6,7 @@ import {Router} from '@angular/router';
 @Component({
     selector: 'app-app-add-json-app',
     templateUrl: './app-add-json-app.component.html',
-    styleUrls: []
+    styleUrls: ['./app-add-json-app.component.css']
 })
 export class AppAddJsonAppComponent {
 
diff --git a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.css b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..f2c387a9db7ec1e2c9aeefc41a92b4d6336c9fdb
--- /dev/null
+++ b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.css
@@ -0,0 +1,38 @@
+:host ::ng-deep input[type=file]{
+    display:none;
+}
+:host ::ng-deep  .p-button{
+    width: unset;
+    margin-right: 5px;
+    background: var(--primary-button-color);
+    color: var(--button-text-color);
+}
+:host ::ng-deep .p-button:hover{
+    background: var(--primary-button-hover);
+    border:none;
+}
+:host ::ng-deep .p-button-label{
+    font-weight: normal;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-buttonbar{
+    border: none;
+    background: transparent;
+    margin-bottom: 10px;
+    padding: 0;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-content{
+    border: none;
+    padding: 0;
+    border-radius: 3px;
+
+}
+:host ::ng-deep .p-fileupload-content .p-progressbar{
+    display: none;
+}
+textarea{
+    border-color: #ccc;
+}
+:host ::ng-deep .p-inputtext:enabled:focus{
+    box-shadow: none;
+    border-color: var(--l-text-color);
+}
diff --git a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.html b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.html
index b1aebf85fa2ec769679f9d620222cb298756fc8c..658ebdfd794e2511480d2b3a613ca1ad9caf018d 100644
--- a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.html
+++ b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.html
@@ -14,7 +14,7 @@
             <div style="margin-bottom: 10px">
                 {{ 'APPS_MANAGEMENT.ADD_JSON_TEXTAREA'| translate}}
             </div>
-            <textarea rows="10" cols="100" pInputTextarea [(ngModel)]="jsonText" (keyup)="this.JsonError = false; this.error = ''"></textarea>
+            <textarea rows="10" cols="100" pInputTextarea style="min-height: 200px; width: 100%" [autoResize]="true" [(ngModel)]="jsonText" (keyup)="this.JsonError = false; this.error = ''"></textarea>
         </div>
         <div class="flex flex-row justify-content-center justify-content-center mt-2">
             <button *ngIf="jsonText.length >0" pButton class="btn btn-primary"
diff --git a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.spec.ts b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.spec.ts
index 958fb094e3a8d04e440656c3714c5f944b70a678..be45384e8dd010b6bf124400cb5be08d459cc57f 100644
--- a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.spec.ts
+++ b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.spec.ts
@@ -1,18 +1,26 @@
 import { ComponentFixture, TestBed } from '@angular/core/testing';
-
 import { AppAddJsonVersionAppComponent } from './app-add-json-version-app.component';
-import {HttpClientTestingModule} from '@angular/common/http/testing';
-import {RouterTestingModule} from '@angular/router/testing';
-import {TranslateFakeLoader, TranslateLoader, TranslateModule} from '@ngx-translate/core';
+import { AppsService } from '../../../service';
+import { Router } from '@angular/router';
+import { HttpClientTestingModule } from '@angular/common/http/testing';
+import { RouterTestingModule } from '@angular/router/testing';
+import { TranslateFakeLoader, TranslateLoader, TranslateModule } from '@ngx-translate/core';
 import { NO_ERRORS_SCHEMA } from '@angular/core';
+import { of, throwError } from 'rxjs';
+import { ModalComponent } from '../../../shared';
 
 describe('AppAddJsonVersionAppComponent', () => {
   let component: AppAddJsonVersionAppComponent;
   let fixture: ComponentFixture<AppAddJsonVersionAppComponent>;
+  let mockAppsService: jasmine.SpyObj<AppsService>;
+  let mockRouter: jasmine.SpyObj<Router>;
 
   beforeEach(async () => {
+    mockAppsService = jasmine.createSpyObj('AppsService', ['createApplication']);
+    mockRouter = jasmine.createSpyObj('Router', ['navigate']);
+
     await TestBed.configureTestingModule({
-      declarations: [ AppAddJsonVersionAppComponent ],
+      declarations: [AppAddJsonVersionAppComponent, ModalComponent],
       imports: [
         HttpClientTestingModule,
         RouterTestingModule,
@@ -23,9 +31,12 @@ describe('AppAddJsonVersionAppComponent', () => {
           }
         }),
       ],
+      providers: [
+        { provide: AppsService, useValue: mockAppsService },
+        { provide: Router, useValue: mockRouter }
+      ],
       schemas: [NO_ERRORS_SCHEMA],
-    })
-    .compileComponents();
+    }).compileComponents();
   });
 
   beforeEach(() => {
@@ -37,4 +48,55 @@ describe('AppAddJsonVersionAppComponent', () => {
   it('should create', () => {
     expect(component).toBeTruthy();
   });
+
+  it('should handle valid JSON version upload', () => {
+    const mockFile = new Blob([JSON.stringify({ version: '1.0.0' })], { type: 'application/json' });
+    const mockEvent = { files: [mockFile] };
+    mockAppsService.createApplication.and.returnValue(of({ id: '123' }));
+
+    component.onUpload(mockEvent);
+
+    const fileReader = new FileReader();
+    fileReader.onload = () => {
+      expect(mockAppsService.createApplication).toHaveBeenCalledWith(jasmine.objectContaining({ version: '1.0.0' }));
+    };
+    fileReader.readAsText(mockFile);
+  });
+
+  it('should call modal.hide on successful upload', () => {
+    spyOn(component.modal, 'hide');
+    const mockResult = { id: '123' };
+    component.handleUpload(mockResult);
+
+    expect(component.modal.hide).toHaveBeenCalled();
+  });
+
+
+  it('should handle valid JSON version text submission', () => {
+    component.jsonText = JSON.stringify({ version: '1.0.0' });
+    mockAppsService.createApplication.and.returnValue(of({ id: '123' }));
+
+    spyOn(component, 'handleUpload');
+    component.sendJsonText();
+
+    expect(component.handleUpload).toHaveBeenCalledWith({ id: '123' });
+  });
+
+  it('should handle invalid JSON version text submission', () => {
+    component.jsonText = 'invalid json';
+
+    component.sendJsonText();
+
+    expect(component.JsonError).toBeTrue();
+  });
+
+  it('should handle error during JSON version submission', () => {
+    component.jsonText = JSON.stringify({ version: '1.0.0' });
+    mockAppsService.createApplication.and.returnValue(throwError({ message: 'Error occurred' }));
+
+    component.sendJsonText();
+
+    expect(component.error).toBe('Error occurred');
+  });
+
 });
diff --git a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.ts b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.ts
index b72cade07a20a92d867071265e9642d8ce4aa6ee..12c2470341b84d814793fb754f9164ffeb2ca70d 100644
--- a/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.ts
+++ b/src/app/appmarket/appmanagement/app-add-json-version-app/app-add-json-version-app.component.ts
@@ -5,7 +5,7 @@ import {AppsService} from '../../../service';
 @Component({
     selector: 'app-app-add-json-version-app',
     templateUrl: './app-add-json-version-app.component.html',
-    styleUrls: []
+    styleUrls: ['app-add-json-version-app.component.css']
 })
 export class AppAddJsonVersionAppComponent {
 
@@ -73,7 +73,7 @@ export class AppAddJsonVersionAppComponent {
         this.modal.show();
     }
 
-    private handleUpload(result: any) {
+    public handleUpload(result: any) {
         console.log('uploaded', result);
         this.modal.hide();
         this.refresh.emit(true);
diff --git a/src/app/appmarket/appmanagement/app-change-owner-modal/app-change-owner-modal.component.html b/src/app/appmarket/appmanagement/app-change-owner-modal/app-change-owner-modal.component.html
index b9bdad7579139c2b35a093187883df888e18cd3f..8968f1e38a3745a3b76255014caab217d1dd8f06 100644
--- a/src/app/appmarket/appmanagement/app-change-owner-modal/app-change-owner-modal.component.html
+++ b/src/app/appmarket/appmanagement/app-change-owner-modal/app-change-owner-modal.component.html
@@ -18,12 +18,13 @@
         </div>
     </div>
     <div class="nmaas-modal-footer">
-        <button type="button" class="btn btn-primary" (click)="submit()" [disabled]="selectOwner.invalid">
-            {{'APPS_MANAGEMENT.CHANGE_OWNER_BUTTON' | translate}}
-        </button>
         <button type="button" class="btn btn-secondary" (click)="modal.hide()">
             {{'APP_CHANGE_STATE_MODAL.CANCEL_BUTTON' | translate}}
         </button>
+        <button type="button" class="btn btn-primary" (click)="submit()" [disabled]="selectOwner.invalid">
+            {{'APPS_MANAGEMENT.CHANGE_OWNER_BUTTON' | translate}}
+        </button>
+
     </div>
 </nmaas-modal>
 
diff --git a/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.html b/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.html
index 72fd4db5ee3d8ae828654970a253fc669cc7b7ca..3771d215733c6678848010cdfda44529fe087dd0 100644
--- a/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.html
+++ b/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.html
@@ -536,6 +536,7 @@
                             <form-builder *ngIf="formDisplayChange && applicationDTO.application.configWizardTemplate.template"
                                           [form]="applicationDTO.application.configWizardTemplate.template" (change)="setConfigTemplate($event)">
                             </form-builder>
+                           
                         </p-tabPanel>
 
                         <p-tabPanel header="{{'APPS_WIZARD.RAW_JSON' | translate}}">
diff --git a/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.ts b/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.ts
index e9e30b6449f6c4154ed1f3e679754a5d17c26636..90f3e447abb68f69f83746904b7a43dc3712885e 100644
--- a/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.ts
+++ b/src/app/appmarket/appmanagement/app-create-wizard/app-create-wizard.component.ts
@@ -1,4 +1,4 @@
-import {Component, OnInit, ViewChild, ViewEncapsulation} from '@angular/core';
+import {Component, OnDestroy, OnInit, ViewChild, ViewEncapsulation} from '@angular/core';
 import {ConfigWizardTemplate} from '../../../model';
 import {MenuItem, SelectItem} from 'primeng/api';
 import {AppImagesService, AppsService, TagService} from '../../../service';
@@ -29,7 +29,7 @@ import {ApplicationBase} from '../../../model/application-base';
     styleUrls: ['./app-create-wizard.component.css']
 })
 
-export class AppCreateWizardComponent extends BaseComponent implements OnInit {
+export class AppCreateWizardComponent extends BaseComponent implements OnInit, OnDestroy {
 
     @ViewChild(ModalComponent, {static: true})
     public modal: ModalComponent;
@@ -59,6 +59,9 @@ export class AppCreateWizardComponent extends BaseComponent implements OnInit {
     public languages: SelectItem[] = [];
     public formDisplayChange = true;
 
+    public template : any;
+    public translateUpdate: any;
+
     // properties for global parameters deploy validation
     // in future extensions pack this into single object
     public deployParamKeyValidator: ValidatorFn = noParameterTypeInControlValueValidator();
@@ -97,6 +100,7 @@ export class AppCreateWizardComponent extends BaseComponent implements OnInit {
         }));
         this.getParametersTypes().forEach(val => this.deployParameter.push({label: val.replace('_', ' '), value: val}));
         this.steps = this.getSteps();
+        this.updateStepsTranslation();
         this.route.params.subscribe(params => {
             if (params['id'] == null) {
                 this.createNewWizard();
@@ -120,6 +124,25 @@ export class AppCreateWizardComponent extends BaseComponent implements OnInit {
         });
     }
 
+    private updateStepsTranslation() {
+        this.translateUpdate = setInterval(() => {
+            if(this.translate.instant('APPS_WIZARD.GENERAL_INFO_STEP') !== null) {
+                this.steps = this.getSteps();
+                this.stopTranslationUpdate();
+            }
+        }, 200);
+    }
+
+    private stopTranslationUpdate() {
+        clearInterval(this.translateUpdate);
+        this.translateUpdate = null;
+    }
+
+    ngOnDestroy(): void {
+        clearInterval(this.translateUpdate);
+        this.translateUpdate = null;
+    }
+
     public getSteps(): any {
         if (this.isInMode(ComponentMode.CREATE)) {
             return [
@@ -206,7 +229,8 @@ export class AppCreateWizardComponent extends BaseComponent implements OnInit {
         this.configFileTemplates.push(new ConfigFileTemplate());
         this.applicationDTO.application.configWizardTemplate = new ConfigWizardTemplate();
         this.applicationDTO.application.configWizardTemplate.template = this.configTemplateService.getConfigTemplate();
-    }
+    };
+    
 
     public nextStep(): void {
         this.activeStepIndex += 1;
@@ -325,10 +349,15 @@ export class AppCreateWizardComponent extends BaseComponent implements OnInit {
     }
 
     public setConfigTemplate(event): void {
-        if (!this.applicationDTO.application.configWizardTemplate) {
-            this.applicationDTO.application.configWizardTemplate = new ConfigWizardTemplate();
+      console.log(event)
+        if(event.type === "addComponent" || event.type === "saveComponent") {
+            console.log(event);
+            this.template = event.form;
+            this.applicationDTO.application.configWizardTemplate.template = null;
+            this.applicationDTO.application.configWizardTemplate.template = Object.assign({}, this.template);
+            console.log('Wizard saved',this.applicationDTO.application.configWizardTemplate.template)
         }
-        this.applicationDTO.application.configWizardTemplate.template = event.form;
+       
     }
 
     public setUpdateConfigTemplate(event): void {
@@ -539,7 +568,7 @@ export class AppCreateWizardComponent extends BaseComponent implements OnInit {
         if (this.applicationDTO.application.appConfigurationSpec.configFileRepositoryRequired) {
             this.removeDefaultElement();
         } else {
-            this.addDefaultElement();
+            // this.addDefaultElement();
             this.removeElementsFromUpdateConfig();
         }
     }
diff --git a/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.css b/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.css
index 08d4bc6e817ee8bbdd9dcedfe621a9a439dc6709..83c4455b01ded2b71a8f81afc08872d537108a63 100644
--- a/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.css
+++ b/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.css
@@ -13,6 +13,7 @@
     margin-right: 5px;
 }
 
-.dropdown:hover .dropdown-menu {
-    display: block;
-}
+/*.dropdown:hover .dropdown-menu {*/
+/*    display: block;*/
+/*}*/
+
diff --git a/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.html b/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.html
index 19fca710ffd4222b0e182db1df8224394cd6eb49..8c62d32324d1e5e25b5cf52127828ae5af7c8353 100644
--- a/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.html
+++ b/src/app/appmarket/appmanagement/app-management-list/appmanagementlist.component.html
@@ -1,80 +1,99 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm 10 col-md-offset-1 col-md-10">
-  <h3>{{'APPS_MANAGEMENT.TITLE'| translate}}</h3>
-  <div style="display:flex; justify-content: space-between">
+<div class="">
+
+  <div style="display:flex; ">
+    <div style="margin-right:20px">
+      <span class="p-input-icon-right" style="width: 100%">
+        <i class="pi pi-search" style="font-size: 13px; top: 16px; margin-right: 5px;"></i>
+      <input pInputText id="searchText" type="text" class="form-control"  placeholder="Search" (keyup)="searchApp($event.target.value)">
+      </span>
+    </div>
     <div style="display:flex">
       <button [routerLink]="['/admin/apps/create']" class="btn btn-primary">{{ 'APPS_MANAGEMENT.ADD_BUTTON' | translate }}</button>
       <button (click)="appAddJson.show()" class="btn btn-primary" style="margin-left: 10px">{{ 'APPS_MANAGEMENT.ADD_BUTTON' | translate }} (JSON)</button>
     </div>
-    <div style="display: flex">
-      <input pInputText id="searchText" type="text"  placeholder="Search" (keyup)="searchApp($event.target.value)">
 
-    </div>
   </div>
+  <h4 class="header">{{'APPS_MANAGEMENT.TITLE'| translate}}</h4>
+  <div class="background-section">
+    <p-table [value]="apps" class="p-datatable-hover p-datatable-sm" [responsive]="true">
+      <ng-template pTemplate="header">
+        <tr>
+          <th></th>
+          <th pSortableColumn="name">
+            {{'APPS_MANAGEMENT.NAME' | translate}}
+            <p-sortIcon field="name"></p-sortIcon>
+          </th>
+          <th pSortableColumn="owner">
+            {{'APPS_MANAGEMENT.OWNER' | translate}}
+            <p-sortIcon field="owner"></p-sortIcon>
+          </th>
+          <th *ngIf="isAnySubtableVisible()">
+            {{'APPS_MANAGEMENT.VERSION' | translate}}
 
+          </th>
+          <th *ngIf="isAnySubtableVisible()">
+            {{'APPS_MANAGEMENT.STATE' | translate}}
+          </th>
+          <th></th>
+          <th></th>
+          <th></th>
+        </tr>
+      </ng-template>
 
-  <table class="table table-hover table-condensed" aria-describedby="Apps management table" style="margin-top:15px">
-    <thead>
-    <tr>
-      <th scope="col"></th>
-      <th scope="col">{{'APPS_MANAGEMENT.NAME' | translate}}</th>
-      <th scope="col">{{'APPS_MANAGEMENT.OWNER' | translate}}</th>
-      <th scope="col" *ngIf="isAnySubtableVisible()">{{'APPS_MANAGEMENT.VERSION' | translate}}</th>
-      <th scope="col" *ngIf="isAnySubtableVisible()">{{'APPS_MANAGEMENT.STATE' | translate}}</th>
-      <th scope="col"></th>
-    </tr>
-    </thead>
-
-    <tbody>
-    <ng-template ngFor let-app [ngForOf]="apps" let-i="index">
-      <tr class="table-row" (click)="clickTableRow(i)">
-        <td style="width: 5%" *ngIf="!versionRowVisible[i]"><span class="glyphicon glyphicon-chevron-right"></span></td>
-        <td style="width: 5%" *ngIf="versionRowVisible[i]"><span class="glyphicon glyphicon-chevron-down"></span></td>
-        <td style="width: 25%">{{app?.name}}</td>
-        <td style="width: 20%">{{app?.owner}}</td>
-        <td style="width: 15%"></td>
-        <td style="width: 15%"></td>
-        <td style="width: 20%" class="text-right">
-          <span class="dropdown">
-            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-              <li *roles="['ROLE_SYSTEM_ADMIN']">
-                <a (click)="appChangeOwnerModal.show(app)" >{{ 'APPS_MANAGEMENT.CHANGE_OWNER_BUTTON' | translate }}</a>
-              </li>
-              <li>
-                <a [routerLink]="['/admin/apps/create/version', app?.name]">{{ 'APPS_MANAGEMENT.ADD_NEW_VERSION_BUTTON' | translate }}</a>
-              </li>
-               <li>
-                <a (click)="appAddJsonVersion.show()" >{{ 'APPS_MANAGEMENT.ADD_NEW_VERSION_BUTTON' | translate }} (JSON)</a>
-              </li>
-              <li>
-                <a (click)="getApplicationInfoJSONWithBase(app?.id)"> {{'APPS_MANAGEMENT.EXPORT_JSON' | translate}}</a>
-              </li>
-              <li>
-                <a [routerLink]="['/admin/apps/edit', app?.id]">{{ 'APPS_MANAGEMENT.EDIT_BUTTON' | translate }}</a>
-              </li>
-              <li>
-                <a (click)="openRemovalModal(app)"> {{ 'APPS_MANAGEMENT.DELETE_BUTTON' | translate}}</a>
-              </li>
-            </ul>
-          </span>
-        </td>
-      </tr>
-      <ng-template ngFor let-version [ngForOf]="app.versions.sort(appVersionCompare)">
-        <tr *ngIf="versionRowVisible[i]" class="table-row" >
-          <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]"></td>
-          <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]"></td>
-          <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]"></td>
-          <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]">{{version.version}}</td>
-          <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]">{{"ENUM.STATE." + getStateAsString(version.state).toUpperCase() | translate }}</td>
+      <ng-template pTemplate="body" let-app let-i="rowIndex">
+        <tr>
+          <td *ngIf="!versionRowVisible[i]"  (click)="clickTableRow(i)">
+            <span class="pi pi-chevron-right"></span>
+          </td>
+          <td *ngIf="versionRowVisible[i]"  (click)="clickTableRow(i)">
+            <span class="pi pi-chevron-down"></span>
+          </td>
+          <td  (click)="clickTableRow(i)">{{app?.name}}</td>
+          <td  (click)="clickTableRow(i)">{{app?.owner}}</td>
+          <td></td>
+          <td></td>
           <td class="text-right">
-            <a [routerLink]="['/admin/apps/view', version?.appVersionId]">
-              <em class="far fa-eye icon-black icon-bigger"></em>
-            </a>
             <span class="dropdown">
+              <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
+              </a>
+              <ul class="dropdown-menu pull-right-drop">
+                <li *roles="['ROLE_SYSTEM_ADMIN']">
+                  <a (click)="appChangeOwnerModal.show(app)" >{{ 'APPS_MANAGEMENT.CHANGE_OWNER_BUTTON' | translate }}</a>
+                </li>
+                <li>
+                  <a [routerLink]="['/admin/apps/create/version', app?.name]">{{ 'APPS_MANAGEMENT.ADD_NEW_VERSION_BUTTON' | translate }}</a>
+                </li>
+                <li>
+                  <a (click)="appAddJsonVersion.show()" >{{ 'APPS_MANAGEMENT.ADD_NEW_VERSION_BUTTON' | translate }} (JSON)</a>
+                </li>
+                <li>
+                  <a (click)="getApplicationInfoJSONWithBase(app?.id)"> {{'APPS_MANAGEMENT.EXPORT_JSON' | translate}}</a>
+                </li>
+                <li>
+                  <a [routerLink]="['/admin/apps/edit', app?.id]">{{ 'APPS_MANAGEMENT.EDIT_BUTTON' | translate }}</a>
+                </li>
+                <li>
+                  <a (click)="openRemovalModal(app)"> {{ 'APPS_MANAGEMENT.DELETE_BUTTON' | translate}}</a>
+                </li>
+              </ul>
+            </span>
+          </td>
+        </tr>
+        <ng-container *ngIf="versionRowVisible[i]">
+          <tr *ngFor="let version of app.versions.sort(appVersionCompare)">
+            <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]"></td>
+            <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]"></td>
+            <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]"></td>
+            <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]">{{version.version}}</td>
+            <td [routerLink]="['/admin/apps/edit/version', version?.appVersionId]">{{"ENUM.STATE." + getStateAsString(version.state).toUpperCase() | translate }}</td>
+            <td class="text-right">
+              <a [routerLink]="['/admin/apps/view', version?.appVersionId]">
+                <em class="pi pi-eye" style="font-size: 1.8rem; color: var(--l-text-color); margin-right:10px"></em>
+              </a>
+              <span class="dropdown">
             <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
+              <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
             </a>
             <ul class="dropdown-menu pull-right-drop">
               <li *roles="['ROLE_SYSTEM_ADMIN']">
@@ -88,13 +107,12 @@
               </li>
             </ul>
           </span>
-          </td>
-        </tr>
+            </td>
+          </tr>
+        </ng-container>
       </ng-template>
-    </ng-template>
-    </tbody>
-  </table>
-
+    </p-table>
+  </div>
 </div>
 <app-appchangestatemodal [appName]="selectedAppName" [app]="selectedVersion"></app-appchangestatemodal>
 
diff --git a/src/app/appmarket/appmanagement/app-management.module.ts b/src/app/appmarket/appmanagement/app-management.module.ts
index ebaa7d15cc0cb276cc55ef0203201a683c594bdc..fa4470584c3485a0e65ed7be4eba85c84ecc76db 100644
--- a/src/app/appmarket/appmanagement/app-management.module.ts
+++ b/src/app/appmarket/appmanagement/app-management.module.ts
@@ -34,6 +34,7 @@ import {AppAddJsonAppComponent} from './app-add-json-app/app-add-json-app.compon
 import {InputTextareaModule} from 'primeng/inputtextarea';
 import {AppAddJsonVersionAppComponent} from './app-add-json-version-app/app-add-json-version-app.component';
 import {DomainsModule} from '../domains/domains.module';
+import {TableModule} from 'primeng/table';
 
 
 export function getJsonTemplates(config: ConfigTemplateService) {
@@ -83,7 +84,8 @@ export function formioAppConfigFactory(appConfig: AppConfigService) {
         TooltipModule,
         DropdownModule,
         InputTextareaModule,
-        DomainsModule
+        DomainsModule,
+        TableModule
     ],
     exports: [],
     providers: [
diff --git a/src/app/appmarket/appmanagement/app-management.routes.ts b/src/app/appmarket/appmanagement/app-management.routes.ts
index 3a38b22f99228ccae091e7ab302d6140d07ace95..8ef778a898b373941e2f6909a1dd2be0100dd534 100644
--- a/src/app/appmarket/appmanagement/app-management.routes.ts
+++ b/src/app/appmarket/appmanagement/app-management.routes.ts
@@ -15,48 +15,48 @@ import {AppsummaryComponent} from '../bulkDeployment/appDeployment/appsummary/ap
 
 export const AppManagementRoutes: Route[] = [
     {
-        path: 'admin/apps',
+        path: 'apps',
         component: AppManagementListComponent,
         canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER']}
     },
     {
-        path: 'admin/apps/create',
+        path: 'apps/create',
         component: AppCreateWizardComponent,
         canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER'], mode: ComponentMode.CREATE}
     },
     {
-        path: 'admin/apps/create/version/:name',
+        path: 'apps/create/version/:name',
         component: AppVersionCreateWizardComponent,
         canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER'], mode: ComponentMode.CREATE}
     },
     {
-        path: 'admin/apps/edit/:id',
+        path: 'apps/edit/:id',
         component: AppCreateWizardComponent,
         canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER'], mode: ComponentMode.EDIT}
     },
     {
-        path: 'admin/apps/edit/version/:id',
+        path: 'apps/edit/version/:id',
         component: AppVersionCreateWizardComponent,
         canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER'], mode: ComponentMode.EDIT}
     },
     {
-        path: 'admin/apps/view/:id',
+        path: 'apps/view/:id',
         component: AppPreviewComponent,
         canActivate: [AuthGuard, RoleGuard],
         data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER']}
     },
     {
-        path: 'admin/apps/bulks',
+        path: 'apps/bulks',
         component: BulkAppListComponent,
         canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}
+        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}
     },
-    { path: 'admin/apps/bulks/new',
+    { path: 'apps/bulks/new',
         component: AppnavigatorComponent,
         children: [
             {path: '', redirectTo: 'select', pathMatch: 'full'},
@@ -65,9 +65,9 @@ export const AppManagementRoutes: Route[] = [
             {path: 'summary', component: AppsummaryComponent}
         ]},
     {
-        path: 'admin/apps/bulks/:id',
+        path: 'apps/bulks/:id',
         component: BulkViewComponent,
         canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER' ]}
+        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER' ]}
     },
 ];
diff --git a/src/app/appmarket/appmanagement/app-version-create-wizard/app-version-create-wizard.component.ts b/src/app/appmarket/appmanagement/app-version-create-wizard/app-version-create-wizard.component.ts
index b964ab330bbac1b623b4390ecba870329d4b1e95..d4f6b6c6b18513c382a8d9605ca5a20a943246a5 100644
--- a/src/app/appmarket/appmanagement/app-version-create-wizard/app-version-create-wizard.component.ts
+++ b/src/app/appmarket/appmanagement/app-version-create-wizard/app-version-create-wizard.component.ts
@@ -1,25 +1,25 @@
-import {Component, OnInit, ViewChild} from '@angular/core';
-import {BaseComponent} from '../../../shared/common/basecomponent/base.component';
-import {ModalComponent} from '../../../shared';
-import {ConfigWizardTemplate} from '../../../model';
-import {ConfigFileTemplate} from '../../../model/configfiletemplate';
-import {AppImagesService, AppsService} from '../../../service';
-import {ActivatedRoute, Router} from '@angular/router';
-import {ConfigTemplateService} from '../../../service/configtemplate.service';
-import {ParameterType} from '../../../model/parametertype';
-import {KubernetesTemplate} from '../../../model/kubernetes-template';
-import {TranslateService} from '@ngx-translate/core';
-import {DomSanitizer} from '@angular/platform-browser';
-import {ApplicationState} from '../../../model/application-state';
-import {KubernetesChart} from '../../../model/kuberneteschart';
-import {AppStorageVolume} from '../../../model/app-storage-volume';
-import {parseServiceStorageVolumeType, ServiceStorageVolumeType} from '../../../model/service-storage-volume';
-import {AppAccessMethod} from '../../../model/app-access-method';
-import {parseServiceAccessMethodType, ServiceAccessMethodType} from '../../../model/service-access-method';
-import {AbstractControl, ValidatorFn} from '@angular/forms';
-import {MultiSelect} from 'primeng/multiselect';
-import {MenuItem, SelectItem} from 'primeng/api';
-import {ApplicationDTO} from '../../../model/application-dto';
+import { Component, OnDestroy, OnInit, ViewChild } from '@angular/core';
+import { BaseComponent } from '../../../shared/common/basecomponent/base.component';
+import { ModalComponent } from '../../../shared';
+import { ConfigWizardTemplate } from '../../../model';
+import { ConfigFileTemplate } from '../../../model/configfiletemplate';
+import { AppImagesService, AppsService } from '../../../service';
+import { ActivatedRoute, Router } from '@angular/router';
+import { ConfigTemplateService } from '../../../service/configtemplate.service';
+import { ParameterType } from '../../../model/parametertype';
+import { KubernetesTemplate } from '../../../model/kubernetes-template';
+import { TranslateService } from '@ngx-translate/core';
+import { DomSanitizer } from '@angular/platform-browser';
+import { ApplicationState } from '../../../model/application-state';
+import { KubernetesChart } from '../../../model/kuberneteschart';
+import { AppStorageVolume } from '../../../model/app-storage-volume';
+import { parseServiceStorageVolumeType, ServiceStorageVolumeType } from '../../../model/service-storage-volume';
+import { AppAccessMethod } from '../../../model/app-access-method';
+import { parseServiceAccessMethodType, ServiceAccessMethodType } from '../../../model/service-access-method';
+import { AbstractControl, ValidatorFn } from '@angular/forms';
+import { MultiSelect } from 'primeng/multiselect';
+import { MenuItem, SelectItem } from 'primeng/api';
+import { ApplicationDTO } from '../../../model/application-dto';
 import { ApplicationVersion } from '../../../model/application-version';
 import * as semver from 'semver';
 import { Application } from '../../../model/application';
@@ -34,7 +34,7 @@ export function noParameterTypeInControlValueValidator(): ValidatorFn {
         }
         const notValid = labels.filter(val => control.value.includes(val)).length === 0;
         console.log('checking: ', control.value, 'valid: ', !notValid);
-        return notValid ? {'noParameterTypeInControlValue': {value: control.value}} : null;
+        return notValid ? { 'noParameterTypeInControlValue': { value: control.value } } : null;
     };
 }
 
@@ -43,10 +43,10 @@ export function noParameterTypeInControlValueValidator(): ValidatorFn {
     templateUrl: './app-version-create-wizard.component.html',
     styleUrls: ['./app-version-create-wizard.component.css']
 })
-export class AppVersionCreateWizardComponent extends BaseComponent implements OnInit {
+export class AppVersionCreateWizardComponent extends BaseComponent implements OnInit, OnDestroy {
 
 
-    @ViewChild(ModalComponent, {static: true})
+    @ViewChild(ModalComponent, { static: true })
     public modal: ModalComponent;
 
     @ViewChild('tagsMultiSelect')
@@ -68,7 +68,9 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
     public logo: any[] = [];
     public screenshots: any[] = [];
     public applicationVersions: ApplicationVersion[] = [];
-    public selectedVersion : any ;
+    public selectedVersion: any;
+    public template: any;
+    public translateUpdate: any;
 
     // properties for global parameters deploy validation
     // in future extensions pack this into single object
@@ -83,12 +85,12 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
     };
 
     constructor(public appsService: AppsService,
-                public route: ActivatedRoute,
-                public translate: TranslateService,
-                public dom: DomSanitizer,
-                public configTemplateService: ConfigTemplateService,
-                public router: Router,
-                public appImagesService: AppImagesService) {
+        public route: ActivatedRoute,
+        public translate: TranslateService,
+        public dom: DomSanitizer,
+        public configTemplateService: ConfigTemplateService,
+        public router: Router,
+        public appImagesService: AppImagesService) {
         super();
     }
 
@@ -97,14 +99,21 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
         this.modal.setModalType('success');
         this.modal.setStatusOfIcons(false);
         this.mode = this.getMode(this.route);
-        this.getParametersTypes().forEach(val => this.deployParameter.push({label: val.replace('_', ' '), value: val}));
-        this.steps = [
-            {label: this.translate.instant('APPS_WIZARD.GENERAL_INFO_STEP')},
-            {label: this.translate.instant('APPS_WIZARD.BASIC_APP_INFO_STEP')},
-            {label: this.translate.instant('APPS_WIZARD.APP_DEPLOYMENT_SPEC_STEP')},
-            {label: this.translate.instant('APPS_WIZARD.CONFIG_TEMPLATES_STEP')},
-            {label: this.translate.instant('APPS_WIZARD.SHORT_REVIEW_STEP')}
-        ];
+        this.getParametersTypes().forEach(val => this.deployParameter.push({ label: val.replace('_', ' '), value: val }));
+        //trick to avoid using this.translate.onChange cuz its not working on current angular without changing language 
+        this.translateUpdate = setInterval(() => {
+            if(this.translate.instant('APPS_WIZARD.GENERAL_INFO_STEP') !== null) {
+                this.steps = [
+                    { label: this.translate.instant('APPS_WIZARD.GENERAL_INFO_STEP') },
+                    { label: this.translate.instant('APPS_WIZARD.BASIC_APP_INFO_STEP') },
+                    { label: this.translate.instant('APPS_WIZARD.APP_DEPLOYMENT_SPEC_STEP') },
+                    { label: this.translate.instant('APPS_WIZARD.CONFIG_TEMPLATES_STEP') },
+                    { label: this.translate.instant('APPS_WIZARD.SHORT_REVIEW_STEP') }
+                ];
+                this.stopTranslationUpdate();
+            }
+        }, 200);
+
         this.route.params.subscribe(params => {
             const appName = params['name']
             const appId = params['id']
@@ -137,6 +146,16 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
         });
     }
 
+    private stopTranslationUpdate() {
+        clearInterval(this.translateUpdate);
+        this.translateUpdate = null;
+    }
+
+    ngOnDestroy(): void {
+        clearInterval(this.translateUpdate);
+        this.translateUpdate = null;
+    }
+
     public appVersionCompare(a: ApplicationVersion, b: ApplicationVersion): number {
         // defaults version that cannot be parsed to `0.0.0`
         return semver.compare(semver.coerce(b.version) || '0.0.0', semver.coerce(a.version) || '0.0.0')
@@ -238,10 +257,13 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
     }
 
     public setConfigTemplate(event): void {
-        if (!this.applicationDTO.application.configWizardTemplate) {
-            this.applicationDTO.application.configWizardTemplate = new ConfigWizardTemplate();
+        if (event.type === "addComponent" || event.type === "saveComponent") {
+            console.log(event);
+            this.template = event.form;
+            this.applicationDTO.application.configWizardTemplate.template = null;
+            this.applicationDTO.application.configWizardTemplate.template = Object.assign({}, this.template);
+            console.log('Wizard saved', this.applicationDTO.application.configWizardTemplate.template)
         }
-        this.applicationDTO.application.configWizardTemplate.template = event.form;
     }
 
     public setUpdateConfigTemplate(event): void {
@@ -494,7 +516,7 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
     }
 
     private convertToProperImageFile(file: any) {
-        const result: any = new File([file], 'uploaded file', {type: file.type});
+        const result: any = new File([file], 'uploaded file', { type: file.type });
         result.objectURL = this.dom.bypassSecurityTrustUrl(URL.createObjectURL(result));
         return result;
     }
@@ -545,7 +567,7 @@ export class AppVersionCreateWizardComponent extends BaseComponent implements On
     }
 
     public onVersionSelect(event: any) {
-        console.log("Slected version ",event )
+        console.log("Slected version ", event)
         this.appsService.getApplication(event.value.appVersionId).subscribe(data => {
             console.log(data);
             this.applicationDTO.application = data;
diff --git a/src/app/appmarket/appmanagement/json-edit/json-edit.component.ts b/src/app/appmarket/appmanagement/json-edit/json-edit.component.ts
index e92e8eaf211d700684c6b23b62d3b405d147f609..0cbc671cfff9fc0fb5c8262285c57b1f0ae9b77a 100644
--- a/src/app/appmarket/appmanagement/json-edit/json-edit.component.ts
+++ b/src/app/appmarket/appmanagement/json-edit/json-edit.component.ts
@@ -28,7 +28,6 @@ export class JsonEditComponent {
 
   @Input()
   set object(obj: any) {
-    console.log('setting value')
     const contentString = JSON.stringify(obj, null, 2);
     if (this.content && contentString !== this.content.value) {
       this.content.setValue(contentString)
diff --git a/src/app/appmarket/appmarket.routes.ts b/src/app/appmarket/appmarket.routes.ts
index f1c40acf24a4f60353bf6c957a51de17a704ecd1..2d0196a195449dad55a32f1f6ed4a791b6a0b657 100644
--- a/src/app/appmarket/appmarket.routes.ts
+++ b/src/app/appmarket/appmarket.routes.ts
@@ -13,6 +13,8 @@ import {ConfigurationRoutes} from './admin/configuration/configuration.routes';
 import {MonitorRoutes} from './admin/monitor/monitor.routes';
 import {AppManagementRoutes} from './appmanagement/app-management.routes';
 import {LanguageManagementRoutes} from './admin/languagemanagement/languagemanagement.routes';
+import { AdminLeftMenuComponent } from '../shared/admin-left-menu/admin-left-menu.component';
+import { AdminDashboardComponent } from '../shared/admin-dashboard/admin-dashboard.component';
 
 export const AppMarketRoutes: Route[] = [
     {
@@ -23,15 +25,32 @@ export const AppMarketRoutes: Route[] = [
       children: [
         ...AppListRoutes,
         ...AppInstanceRoutes,
+          { path: 'apps/:id', component: AppDetailsComponent },
+
+      ]
+    },
+    {
+      path: 'admin',
+      component: AdminLeftMenuComponent,
+      canActivate: [AuthGuard],
+      canActivateChild: [AuthGuard],
+      children: [
+        {
+          path: '',
+          redirectTo: '/admin/dashboard',
+          pathMatch: 'full'
+        },
+        {
+          path: 'dashboard',
+          component: AdminDashboardComponent
+        },
         ...DomainsRoutes,
         ...UsersRoutes,
         ...ClustersRoutes,
-          ...ConfigurationRoutes,
-          ...MonitorRoutes,
-          ...AppManagementRoutes,
-          ...LanguageManagementRoutes,
-          { path: 'apps/:id', component: AppDetailsComponent },
-
+        ...ConfigurationRoutes,
+        ...MonitorRoutes,
+        ...AppManagementRoutes,
+        ...LanguageManagementRoutes,
       ]
     }
 ];
diff --git a/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.css b/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..f2c387a9db7ec1e2c9aeefc41a92b4d6336c9fdb
--- /dev/null
+++ b/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.css
@@ -0,0 +1,38 @@
+:host ::ng-deep input[type=file]{
+    display:none;
+}
+:host ::ng-deep  .p-button{
+    width: unset;
+    margin-right: 5px;
+    background: var(--primary-button-color);
+    color: var(--button-text-color);
+}
+:host ::ng-deep .p-button:hover{
+    background: var(--primary-button-hover);
+    border:none;
+}
+:host ::ng-deep .p-button-label{
+    font-weight: normal;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-buttonbar{
+    border: none;
+    background: transparent;
+    margin-bottom: 10px;
+    padding: 0;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-content{
+    border: none;
+    padding: 0;
+    border-radius: 3px;
+
+}
+:host ::ng-deep .p-fileupload-content .p-progressbar{
+    display: none;
+}
+textarea{
+    border-color: #ccc;
+}
+:host ::ng-deep .p-inputtext:enabled:focus{
+    box-shadow: none;
+    border-color: var(--l-text-color);
+}
diff --git a/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.html b/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.html
index 328d1af22da2d36c22a9624a6d9c57e56fa4e5d3..1385e9861fe9bd8022d8459450797eee0ea952f1 100644
--- a/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.html
+++ b/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.html
@@ -17,7 +17,7 @@
         <div style="margin-top: 1.5rem; margin-bottom: 1rem">
             <p>{{'BULK.APP.UPLOAD_TEXT' | translate}}</p>
         </div>
-        <textarea pInputTextarea [(ngModel)]="csvText" rows="10" cols="127" (keyup)="changeDetector = true"></textarea>
+        <textarea pInputTextarea [(ngModel)]="csvText" rows="10" cols="127" [autoResize]="true" (keyup)="changeDetector = true"></textarea>
     </div>
 
     <div *ngIf="errorMessage !== ''" style="margin-top: 1rem; display: flex; justify-content: start; color: indianred">
diff --git a/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.ts b/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.ts
index d718907e2389cbb9192bacddda36ad28e8733c32..015af6e6d18fc46553d4898a6e79e531d0f2c34e 100644
--- a/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.ts
+++ b/src/app/appmarket/bulkDeployment/appDeployment/appupload/appupload.component.ts
@@ -6,7 +6,7 @@ import {AppImagesService} from '../../../../service';
 @Component({
     selector: 'app-appupload',
     templateUrl: './appupload.component.html',
-    styleUrls: []
+    styleUrls: ['./appupload.component.css']
 })
 export class AppuploadComponent implements OnInit {
 
diff --git a/src/app/appmarket/bulkDeployment/appdeployment.service.ts b/src/app/appmarket/bulkDeployment/appdeployment.service.ts
index a44c0f9cc361bc8f12b247c5f9a1534fdbfe11f0..f660f0531c4ff76f1c92041d070d6205ced673fe 100644
--- a/src/app/appmarket/bulkDeployment/appdeployment.service.ts
+++ b/src/app/appmarket/bulkDeployment/appdeployment.service.ts
@@ -79,7 +79,7 @@ export class AppdeploymentService {
     }
 
     public getBulksDomainDeploymentsOwner(): Observable<BulkDeployment[]> {
-        return this.http.get<BulkDeployment[]>(this.getUrl() + 'domains/vl');
+        return this.http.get<BulkDeployment[]>(this.getUrl() + 'domains/group');
     }
 
     public getBulksAppDeployments(showDeleted: boolean = false): Observable<BulkDeployment[]> {
@@ -89,7 +89,7 @@ export class AppdeploymentService {
     }
 
     public getBulksAppDeploymentsOwner(): Observable<BulkDeployment[]> {
-        return this.http.get<BulkDeployment[]>(this.getUrl() + 'apps/vl');
+        return this.http.get<BulkDeployment[]>(this.getUrl() + 'apps/group');
     }
 
     public getBulkDeployment(id: number): Observable<BulkDeployment> {
diff --git a/src/app/appmarket/bulkDeployment/bulk-app-list/bulk-app-list.component.ts b/src/app/appmarket/bulkDeployment/bulk-app-list/bulk-app-list.component.ts
index 4a773179c64068601af012a9fe6506a818eecfbe..7b89c6899bce5d8dbe07c971fd8601093a27d2fc 100644
--- a/src/app/appmarket/bulkDeployment/bulk-app-list/bulk-app-list.component.ts
+++ b/src/app/appmarket/bulkDeployment/bulk-app-list/bulk-app-list.component.ts
@@ -24,7 +24,7 @@ export class BulkAppListComponent implements OnInit {
     }
 
     onRefresh(showDeleted = false) : void {
-        if (this.authService.getRoles().find(value => value === 'ROLE_VL_MANAGER') !== undefined) {
+        if (this.authService.getRoles().find(value => value === 'ROLE_GROUP_MANAGER') !== undefined) {
             this.deployService.getBulksAppDeploymentsOwner().subscribe(data => {
                 data = data.sort((a, b) => new Date(b.creationDate).getTime() - new Date(a.creationDate).getTime())
                 this.bulks = data
diff --git a/src/app/appmarket/bulkDeployment/bulk-domain-list/bulk-domain-list.component.ts b/src/app/appmarket/bulkDeployment/bulk-domain-list/bulk-domain-list.component.ts
index 696e86a9f8ccc30a4615d7e13af798cd423e4651..cfd2fe6751732bde31b6ef9e5553bb53b20e1a5f 100644
--- a/src/app/appmarket/bulkDeployment/bulk-domain-list/bulk-domain-list.component.ts
+++ b/src/app/appmarket/bulkDeployment/bulk-domain-list/bulk-domain-list.component.ts
@@ -20,7 +20,7 @@ export class BulkDomainListComponent implements OnInit {
     }
 
     ngOnInit(): void {
-        if (this.authService.getRoles().find(value => value === 'ROLE_VL_MANAGER') !== undefined) {
+        if (this.authService.getRoles().find(value => value === 'ROLE_GROUP_MANAGER') !== undefined) {
             this.deployService.getBulksDomainDeploymentsOwner().subscribe(data => {
                 data = data.sort((a, b) => new Date(b.creationDate).getTime() - new Date(a.creationDate).getTime())
                 this.bulks = data
diff --git a/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.css b/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.css
index 90bb2e521b576a5d1a687e77ce002fc4b7cded50..81faf4286ba49fea43ef151ccf0535977a655763 100644
--- a/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.css
+++ b/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.css
@@ -8,3 +8,4 @@
     margin-left: 5px;
     margin-right: 5px;
 }
+
diff --git a/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.html b/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.html
index 06d42a13307598d26cd863a2d5d086d6b4284510..77fa7865ee58f68e0d6d01784560d9c485f3aa1a 100644
--- a/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.html
+++ b/src/app/appmarket/bulkDeployment/bulk-list/bulk-list.component.html
@@ -1,156 +1,272 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm 10 col-md-offset-1 col-md-10">
-    <h3>{{header | translate}}</h3>
-    <div class="" style="display: flex; justify-content: space-between; margin-top: 10px;">
-        <div *ngIf="mode=== bulkTypeDomain">
+<div class="">
+    <div style="display:flex; ">
+        <div style="margin-right:20px">
+          <span class="p-input-icon-right" style="width: 100%">
+               <i class="pi pi-search" style="font-size: 13px; top: 16px; margin-right: 5px;"></i>
+              <input pInputText class="flex form-control" name="search" id="search" placeholder="Search" type="text"
+                     style="height: 34px" [(ngModel)]="searchValue">
+          </span>
+        </div>
+        <div *ngIf="mode=== bulkTypeDomain" style="margin-right: 10px">
             <button class="btn btn-primary" [routerLink]="['/admin/domains/bulks/new']">New deployment</button>
         </div>
-        <div *ngIf="mode=== bulkTypeApp">
+        <div *ngIf="mode=== bulkTypeApp" style="margin-right: 10px">
             <button class="btn btn-primary" [routerLink]="['/admin/apps/bulks/new']">New deployment</button>
         </div>
-        
-        <div class="flex">
-            <div  *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']"  class="flex align-items-center mr-6">
-        
-                <p-button 
-                    type="button" 
-                    class="mr-2" 
-                    (onClick)="sidebarVisible4 = true" 
+        <div  *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']"  class="flex align-items-center mr-6">
+            <p-button
+                    type="button"
+                    class=""
+                    (onClick)="sidebarVisible4 = true"
                     label="Deployments Queue"
                     severity="secondary"
-                     ></p-button>
-                <p-sidebar [(visible)]="sidebarVisible4" position="left" styleClass="w-30rem">
-                    <h3>Deployments Queue</h3>
-                    <div class="flex flex-column">
-                        <div class="flex grid">
-                            <label class="col-10" for="jobInQueue">Jobs in queue</label>
-                            <span class="col-2 " id="jobInQueue">{{queueDetails?.jobInQueue}}</span>
-                        </div>
-                        <div class="flex grid">
-                            <label class="col-10" for="jobInProcess">In progress</label>
-                            <span class="col-2 " id="jobInProcess">{{queueDetails?.jobInProcess}}</span>
-                        </div>
-                        <div class="flex grid">
-                            <label class="col-10" for="jobInProcessId">Current proccessing bulk id</label>
-                            <span class="col-2" id="jobInProcessId">{{queueDetails?.jobInProcessId}}</span>
-                        </div>
+            ></p-button>
+            <p-sidebar [(visible)]="sidebarVisible4" position="right" styleClass="w-30rem">
+                <h3>Deployments Queue</h3>
+                <div class="flex flex-column">
+                    <div class="flex grid">
+                        <label class="col-10" for="jobInQueue">Jobs in queue</label>
+                        <span class="col-2 " id="jobInQueue">{{queueDetails?.jobInQueue}}</span>
                     </div>
-                </p-sidebar>
-                
-            </div>
-            <div  *roles="['ROLE_SYSTEM_ADMIN']"  class="flex align-items-center mr-6 pt-2">
-                <label  *ngIf="mode=== bulkTypeApp" class="mr-2" for="showDeleted">Show all</label>
-                <p-inputSwitch  *ngIf="mode=== bulkTypeApp"  id="showDeleted" (onChange)="refreshBulks()" [(ngModel)]="showDeleted" ngDefaultControl/>
-            </div>
-            <div class="flex align-items-center mr-1">{{ 'BULK.LIST.PER_PAGE' | translate }}:</div>
-            <span id="selectionItems" class="dropdown"
-                  style="vertical-align: middle; display: inline-block; margin-right: 1rem;">
-        <button class="dropdown-toggle btn" data-toggle="dropdown" data-close-others="true">
-            {{maxItemsOnPage}}
-        </button>
-        <ul class="dropdown-menu">
-            <li *ngFor="let item of itemsPerPage" [ngClass]="{'active': maxItemsOnPage == item}">
-                <a (click)="setItems(item)">
-                    <span>{{item.toString()}}</span>
-                </a>
-            </li>
-        </ul>
-    </span>
-            <input pInputText class="flex" name="search" id="search" placeholder="Search" type="text"
-                   style="height: 34px" [(ngModel)]="searchValue">
+                    <div class="flex grid">
+                        <label class="col-10" for="jobInProcess">In progress</label>
+                        <span class="col-2 " id="jobInProcess">{{queueDetails?.jobInProcess}}</span>
+                    </div>
+                    <div class="flex grid">
+                        <label class="col-10" for="jobInProcessId">Current proccessing bulk id</label>
+                        <span class="col-2" id="jobInProcessId">{{queueDetails?.jobInProcessId}}</span>
+                    </div>
+                </div>
+            </p-sidebar>
+
+        </div>
+        <div  *roles="['ROLE_SYSTEM_ADMIN']"  class="flex align-items-center mr-6 pt-2">
+            <label  *ngIf="mode=== bulkTypeApp" class="mr-2" for="showDeleted">Show all</label>
+            <p-inputSwitch  *ngIf="mode=== bulkTypeApp"  id="showDeleted" (onChange)="refreshBulks()" [(ngModel)]="showDeleted" ngDefaultControl/>
         </div>
     </div>
-    <table *ngIf="mode === 'DOMAIN'" class="table table-hover table-condensed" style="margin-top: 3rem"
-           aria-describedby="Bulk deployment table" sortable-table (sorted)="onSort($event)">
-        <thead>
-        <tr>
-            <th scope="col" class="column-sortable" sortable-column="id">{{'BULK.LIST.ID' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="creator">{{'BULK.LIST.CREATOR' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="date">{{'BULK.LIST.CREATION_DATE' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="state">{{'BULK.LIST.STATE' | translate}}</th>
-            <th scope="col" ></th>
-        </tr>
-        </thead>
+    <h4 class="header">{{header | translate}}</h4>
+<!--    <div class="" style="display: flex; justify-content: space-between; margin-top: 10px;">-->
+<!--        <div class="flex">-->
+<!--            <div class="flex align-items-center mr-1">{{ 'BULK.LIST.PER_PAGE' | translate }}:</div>-->
+<!--            <span id="selectionItems" class="dropdown"-->
+<!--                  style="vertical-align: middle; display: inline-block; margin-right: 1rem;">-->
+<!--                <button class="dropdown-toggle btn" data-toggle="dropdown" data-close-others="true">-->
+<!--                        {{maxItemsOnPage}}-->
+<!--                </button>-->
+<!--                <ul class="dropdown-menu">-->
+<!--                    <li *ngFor="let item of itemsPerPage" [ngClass]="{'active': maxItemsOnPage == item}">-->
+<!--                        <a (click)="setItems(item)">-->
+<!--                            <span>{{item.toString()}}</span>-->
+<!--                        </a>-->
+<!--                    </li>-->
+<!--                </ul>-->
+<!--            </span>-->
 
-        <tbody>
-        <ng-template ngFor let-bulk [ngForOf]="bulks" let-i="index">
-            <tr class="table-row">
-                <td style="width: 10%">{{bulk?.id}}</td>
-                <td style="width: 25%">{{bulk?.creator.username}}</td>
-                <td style="width: 25%">{{bulk?.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>
-                <td style="width: 15%">{{'BULK.STATE.' + bulk?.state | translate}}</td>
-                <td style="width: 20%" class="text-right">
-                    <span class="dropdown">
-            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
-               data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-              <li *ngIf="mode === bulkTypeDomain">
-                <a [routerLink]="['/admin/domains/bulks/', bulk?.id]">{{ 'BULK.LIST.DETAILS' | translate }}</a>
-              </li>
-            </ul>
-          </span>
-                </td>
-            </tr>
-        </ng-template>
-        </tbody>
-    </table>
-    <table *ngIf="mode === 'APPLICATION'" class="table table-hover table-condensed" style="margin-top: 3rem"
-           aria-describedby="Bulk deployment table" sortable-table (sorted)="onSort($event)">
-        <thead>
-        <tr>
-            <th scope="col" class="column-sortable" sortable-column="id">{{'BULK.LIST.ID' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="creator">{{'BULK.LIST.CREATOR' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="app_name">{{'BULK.LIST.APP_NAME' | translate}}</th>
-            <th scope="col" class="column-sortable"
-                sortable-column="instance_no">{{'BULK.LIST.INSTANCE_NO' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="date"
-                sort-direction="desc">{{'BULK.LIST.CREATION_DATE' | translate}}</th>
-            <th scope="col" class="column-sortable" sortable-column="state">{{'BULK.LIST.STATE' | translate}}</th>
-            <th scope="col"></th>
-        </tr>
-        </thead>
+<!--        </div>-->
+<!--    </div>-->
+    <div *ngIf="mode === 'DOMAIN'" class="background-section">
+        <p-table *ngIf="mode === 'DOMAIN'" [value]="bulks" class="p-datatable-hover p-datatable-sm" [responsive]="true" (onSort)="onSort($event)">
+            <ng-template pTemplate="header">
+                <tr>
+                    <th pSortableColumn="id">{{'BULK.LIST.ID' | translate}}
+                        <p-sortIcon field="id"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="creator">{{'BULK.LIST.CREATOR' | translate}}
+                        <p-sortIcon field="creator"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="date">{{'BULK.LIST.CREATION_DATE' | translate}}
+                        <p-sortIcon field="date"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="state">{{'BULK.LIST.STATE' | translate}}
+                        <p-sortIcon field="state"></p-sortIcon>
+                    </th>
+                    <th></th>
+                </tr>
+            </ng-template>
 
-        <tbody>
-        <ng-template ngFor let-bulk
-                     [ngForOf]="bulks | searchBulk: searchValue: true | paginate: {itemsPerPage: maxItemsOnPage, currentPage: p}"
-                     let-i="index">
-            <tr class="table-row">
-                <td style="width: 5%">{{bulk?.id}}</td>
-                <td style="width: 15%">{{bulk?.creator.username}}</td>
-                <td style="width: 20%">{{getApplicationName(bulk?.details)}}</td>
-                <td style="width: 20%">{{getInstancesNumber(bulk?.details)}}</td>
-                <td style="width: 15%">{{bulk?.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>
-                <td style="width: 20%">{{'BULK.STATE.' + bulk?.state | translate}}</td>
-                <td style="width: 5%" class="text-right">
-                    <span class="dropdown">
-            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
-               data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-                <li *ngIf="mode === bulkTypeApp">
-                    <a [routerLink]="['/admin/apps/bulks/', bulk?.id]">{{ 'BULK.LIST.DETAILS' | translate }}</a>
-                </li>
-                <li *ngIf="mode === bulkTypeApp && bulk?.state !== 'REMOVED'">
-                    <a (click)="getAppBulkDetails(bulk?.id)"> {{"BULK.APP.DOWNLOAD_CSV" | translate}}</a>
-                </li>
-                <li *ngIf="mode === bulkTypeApp && !(bulk?.state === 'REMOVED' || bulk?.deleted )">
-                    <a (click)="modal.show(); removeBulkId=bulk?.id">{{ 'BULK.LIST.REMOVE' | translate }}</a>
-                </li>
-            </ul>
-          </span>
-                </td>
-            </tr>
-        </ng-template>
-        </tbody>
-    </table>
-    <pagination-controls class="text-right" (pageChange)="p = $event"
-                         previousLabel="{{ 'PAGINATION.PREVIOUS' | translate }}"
-                         nextLabel="{{ 'PAGINATION.NEXT' | translate }}"
-                         screenReaderPaginationLabel="{{ 'PAGINATION.SCREEN_READER.PAGINATION' | translate }}"
-                         screenReaderPageLabel="{{ 'PAGINATION.SCREEN_READER.PAGE' | translate }}"
-                         screenReaderCurrentLabel="{{ 'PAGINATION.SCREEN_READER.CURRENT' | translate }}"></pagination-controls>
+            <ng-template pTemplate="body" let-bulk>
+                <tr class="table-row">
+                    <td>{{bulk?.id}}</td>
+                    <td>{{bulk?.creator.username}}</td>
+                    <td>{{bulk?.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>
+                    <td>{{'BULK.STATE.' + bulk?.state | translate}}</td>
+                    <td class="text-right">
+                        <span class="dropdown">
+                          <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                            <em class="fas fa-cog icon-black icon-bigger"></em>
+                          </a>
+                          <ul class="dropdown-menu pull-right-drop">
+                            <li *ngIf="mode === bulkTypeDomain">
+                              <a [routerLink]="['/admin/domains/bulks/', bulk?.id]">{{ 'BULK.LIST.DETAILS' | translate }}</a>
+                            </li>
+                          </ul>
+                        </span>
+                    </td>
+                </tr>
+            </ng-template>
+        </p-table>
+
+
+<!--        <table *ngIf="mode === 'DOMAIN'" class="table table-hover table-condensed" style="margin-top: 3rem"-->
+<!--               aria-describedby="Bulk deployment table" sortable-table (sorted)="onSort($event)">-->
+<!--            <thead>-->
+<!--            <tr>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="id">{{'BULK.LIST.ID' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="creator">{{'BULK.LIST.CREATOR' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="date">{{'BULK.LIST.CREATION_DATE' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="state">{{'BULK.LIST.STATE' | translate}}</th>-->
+<!--                <th scope="col" ></th>-->
+<!--            </tr>-->
+<!--            </thead>-->
+
+<!--            <tbody>-->
+<!--            <ng-template ngFor let-bulk [ngForOf]="bulks" let-i="index">-->
+<!--                <tr class="table-row">-->
+<!--                    <td style="width: 10%">{{bulk?.id}}</td>-->
+<!--                    <td style="width: 25%">{{bulk?.creator.username}}</td>-->
+<!--                    <td style="width: 25%">{{bulk?.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>-->
+<!--                    <td style="width: 15%">{{'BULK.STATE.' + bulk?.state | translate}}</td>-->
+<!--                    <td style="width: 20%" class="text-right">-->
+<!--                    <span class="dropdown">-->
+<!--            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"-->
+<!--               data-toggle="dropdown" href="#" role="button">-->
+<!--              <em class="fas fa-cog icon-black icon-bigger"></em>-->
+<!--            </a>-->
+<!--            <ul class="dropdown-menu pull-right-drop">-->
+<!--              <li *ngIf="mode === bulkTypeDomain">-->
+<!--                <a [routerLink]="['/admin/domains/bulks/', bulk?.id]">{{ 'BULK.LIST.DETAILS' | translate }}</a>-->
+<!--              </li>-->
+<!--            </ul>-->
+<!--          </span>-->
+<!--                    </td>-->
+<!--                </tr>-->
+<!--            </ng-template>-->
+<!--            </tbody>-->
+<!--        </table>-->
+    </div>
+
+    <div *ngIf="mode === 'APPLICATION'" class="background-section">
+        <p-table *ngIf="mode === 'APPLICATION'" [value]="bulks | searchBulk: searchValue: true "
+                 class="p-datatable-hover p-datatable-sm"
+                 [responsive]="true"
+                 [paginator]="true"
+                 [rows]="maxItemsOnPage"
+                 [rowsPerPageOptions]="[15, 20, 25, 30, 50]"
+                 (onSort)="onSort($event)">
+            <ng-template pTemplate="header">
+                <tr>
+                    <th pSortableColumn="id">{{'BULK.LIST.ID' | translate}}
+                        <p-sortIcon field="id"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="creator">{{'BULK.LIST.CREATOR' | translate}}
+                        <p-sortIcon field="creator"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="app_name">{{'BULK.LIST.APP_NAME' | translate}}
+                        <p-sortIcon field="app_name"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="instance_no">{{'BULK.LIST.INSTANCE_NO' | translate}}
+                        <p-sortIcon field="instance_no"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="date" pSortOrder="-1">{{'BULK.LIST.CREATION_DATE' | translate}}
+                        <p-sortIcon field="date"></p-sortIcon>
+                    </th>
+                    <th pSortableColumn="state">{{'BULK.LIST.STATE' | translate}}
+                        <p-sortIcon field="state"></p-sortIcon>
+                    </th>
+                    <th></th>
+                </tr>
+            </ng-template>
+
+            <ng-template pTemplate="body" let-bulk>
+                <tr class="table-row">
+                    <td>{{bulk?.id}}</td>
+                    <td>{{bulk?.creator.username}}</td>
+                    <td>{{getApplicationName(bulk?.details)}}</td>
+                    <td>{{getInstancesNumber(bulk?.details)}}</td>
+                    <td>{{bulk?.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>
+                    <td>{{'BULK.STATE.' + bulk?.state | translate}}</td>
+                    <td class="text-right">
+                        <span class="dropdown">
+                          <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                            <em class="fas fa-cog icon-black icon-bigger"></em>
+                          </a>
+                          <ul class="dropdown-menu pull-right-drop">
+                            <li *ngIf="mode === bulkTypeApp">
+                              <a [routerLink]="['/admin/apps/bulks/', bulk?.id]">{{ 'BULK.LIST.DETAILS' | translate }}</a>
+                            </li>
+                            <li *ngIf="mode === bulkTypeApp && bulk?.state !== 'REMOVED'">
+                              <a (click)="getAppBulkDetails(bulk?.id)"> {{"BULK.APP.DOWNLOAD_CSV" | translate}}</a>
+                            </li>
+                            <li *ngIf="mode === bulkTypeApp && !(bulk?.state === 'REMOVED' || bulk?.deleted )">
+                              <a (click)="modal.show(); removeBulkId=bulk?.id">{{ 'BULK.LIST.REMOVE' | translate }}</a>
+                            </li>
+                          </ul>
+                        </span>
+                    </td>
+                </tr>
+            </ng-template>
+        </p-table>
+
+<!--        <table *ngIf="mode === 'APPLICATION'" class="table table-hover table-condensed" style="margin-top: 3rem"-->
+<!--               aria-describedby="Bulk deployment table" sortable-table (sorted)="onSort($event)">-->
+<!--            <thead>-->
+<!--            <tr>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="id">{{'BULK.LIST.ID' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="creator">{{'BULK.LIST.CREATOR' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="app_name">{{'BULK.LIST.APP_NAME' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable"-->
+<!--                    sortable-column="instance_no">{{'BULK.LIST.INSTANCE_NO' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="date"-->
+<!--                    sort-direction="desc">{{'BULK.LIST.CREATION_DATE' | translate}}</th>-->
+<!--                <th scope="col" class="column-sortable" sortable-column="state">{{'BULK.LIST.STATE' | translate}}</th>-->
+<!--                <th scope="col"></th>-->
+<!--            </tr>-->
+<!--            </thead>-->
+
+<!--            <tbody>-->
+<!--            <ng-template ngFor let-bulk-->
+<!--                         [ngForOf]="bulks | searchBulk: searchValue: true | paginate: {itemsPerPage: maxItemsOnPage, currentPage: p}"-->
+<!--                         let-i="index">-->
+<!--                <tr class="table-row">-->
+<!--                    <td style="width: 5%">{{bulk?.id}}</td>-->
+<!--                    <td style="width: 15%">{{bulk?.creator.username}}</td>-->
+<!--                    <td style="width: 20%">{{getApplicationName(bulk?.details)}}</td>-->
+<!--                    <td style="width: 20%">{{getInstancesNumber(bulk?.details)}}</td>-->
+<!--                    <td style="width: 15%">{{bulk?.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>-->
+<!--                    <td style="width: 20%">{{'BULK.STATE.' + bulk?.state | translate}}</td>-->
+<!--                    <td style="width: 5%" class="text-right">-->
+<!--                    <span class="dropdown">-->
+<!--            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"-->
+<!--               data-toggle="dropdown" href="#" role="button">-->
+<!--              <em class="fas fa-cog icon-black icon-bigger"></em>-->
+<!--            </a>-->
+<!--            <ul class="dropdown-menu pull-right-drop">-->
+<!--                <li *ngIf="mode === bulkTypeApp">-->
+<!--                    <a [routerLink]="['/admin/apps/bulks/', bulk?.id]">{{ 'BULK.LIST.DETAILS' | translate }}</a>-->
+<!--                </li>-->
+<!--                <li *ngIf="mode === bulkTypeApp && bulk?.state !== 'REMOVED'">-->
+<!--                    <a (click)="getAppBulkDetails(bulk?.id)"> {{"BULK.APP.DOWNLOAD_CSV" | translate}}</a>-->
+<!--                </li>-->
+<!--                <li *ngIf="mode === bulkTypeApp && !(bulk?.state === 'REMOVED' || bulk?.deleted )">-->
+<!--                    <a (click)="modal.show(); removeBulkId=bulk?.id">{{ 'BULK.LIST.REMOVE' | translate }}</a>-->
+<!--                </li>-->
+<!--            </ul>-->
+<!--          </span>-->
+<!--                    </td>-->
+<!--                </tr>-->
+<!--            </ng-template>-->
+<!--            </tbody>-->
+<!--        </table>-->
+
+    </div>
+
+<!--    <pagination-controls class="text-right" (pageChange)="p = $event"-->
+<!--                         previousLabel="{{ 'PAGINATION.PREVIOUS' | translate }}"-->
+<!--                         nextLabel="{{ 'PAGINATION.NEXT' | translate }}"-->
+<!--                         screenReaderPaginationLabel="{{ 'PAGINATION.SCREEN_READER.PAGINATION' | translate }}"-->
+<!--                         screenReaderPageLabel="{{ 'PAGINATION.SCREEN_READER.PAGE' | translate }}"-->
+<!--                         screenReaderCurrentLabel="{{ 'PAGINATION.SCREEN_READER.CURRENT' | translate }}"></pagination-controls>-->
 
 </div>
 
diff --git a/src/app/appmarket/bulkDeployment/bulk-view/bulk-view.component.html b/src/app/appmarket/bulkDeployment/bulk-view/bulk-view.component.html
index 9c870590051db4025f7b3d0dffbaeee499a71785..eabf5c0f2d06498168af5f2f5d6fe8efc599a9d5 100644
--- a/src/app/appmarket/bulkDeployment/bulk-view/bulk-view.component.html
+++ b/src/app/appmarket/bulkDeployment/bulk-view/bulk-view.component.html
@@ -1,285 +1,288 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm-10 col-md-offset-1 col-md-10">
-    <div *ngIf="bulk && bulkType === 'DOMAIN' ">
-        <h3>{{'BULK.DOMAIN.HEADER_VIEW' | translate}}</h3>
-        <div class="" style="padding-bottom: 5rem; margin-top: 3rem">
-            <label for="id" class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.ID' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="id" name="id" [disabled]="true"
-                       [(ngModel)]="bulk.id" #name="ngModel">
+<div class="">
+    <div class="background-section">
+        <div *ngIf="bulk && bulkType === 'DOMAIN' ">
+            <h3>{{'BULK.DOMAIN.HEADER_VIEW' | translate}}</h3>
+            <div class="" style="padding-bottom: 5rem; margin-top: 3rem">
+                <label for="id" class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.ID' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="id" name="id" [disabled]="true"
+                           [(ngModel)]="bulk.id" #name="ngModel">
+                </div>
             </div>
-        </div>
 
-        <div class="" style="padding-bottom: 5rem">
-            <label for="creator"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATOR' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="creator" name="creator" [disabled]="true"
-                       placeholder="{{bulk.creator.username}} ({{bulk.creator.firstname}} {{bulk.creator.lastname}})">
+            <div class="" style="padding-bottom: 5rem">
+                <label for="creator"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATOR' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="creator" name="creator" [disabled]="true"
+                           placeholder="{{bulk.creator.username}} ({{bulk.creator.firstname}} {{bulk.creator.lastname}})">
+                </div>
             </div>
-        </div>
 
-        <div class="" style="padding-bottom: 5rem">
-            <label for="date"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATION_DATE' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="date" name="date" [disabled]="true"
-                       placeholder="{{bulk.creationDate | date: 'dd-MM-yyyy HH:mm'}}">
+            <div class="" style="padding-bottom: 5rem">
+                <label for="date"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATION_DATE' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="date" name="date" [disabled]="true"
+                           placeholder="{{bulk.creationDate | date: 'dd-MM-yyyy HH:mm'}}">
+                </div>
             </div>
-        </div>
 
-        <div class="form-group" style="padding-bottom: 5rem">
-            <label for="state"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.STATE' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="state" name="state" [disabled]="true"
-                       placeholder="{{'BULK.STATE.' + bulk.state | translate}}">
+            <div class="form-group" style="padding-bottom: 5rem">
+                <label for="state"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.STATE' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="state" name="state" [disabled]="true"
+                           placeholder="{{'BULK.STATE.' + bulk.state | translate}}">
+                </div>
             </div>
-        </div>
-        <div class="panel panel-default" style="margin-top: 3rem">
-            <div class="panel-heading">
+            <div class="panel panel-default" style="margin-top: 3rem">
+                <div class="panel-heading">
 
-                <div style="display: flex; justify-content: start; align-items: center">
-                    <div>
-                        {{ 'BULK.DOMAIN.DEPLOYMENTS' | translate }}
+                    <div style="display: flex; justify-content: start; align-items: center">
+                        <div>
+                            {{ 'BULK.DOMAIN.DEPLOYMENTS' | translate }}
+                        </div>
                     </div>
                 </div>
-            </div>
-            <div class="panel-body">
-                <table class="table table-hover table-condensed" aria-describedby="Domains in Group table">
-                    <thead>
-                    <tr>
-                        <th scope="col">{{'BULK.LIST.STATE' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.CREATED' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.DOMAIN_ID' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.DOMAIN_NAME' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.DOMAIN_CODENAME' | translate}}</th>
-                        <th style="width: 5%" scope="col"></th>
-                    </tr>
-                    <ng-template ngFor let-response [ngForOf]="bulk.entries" let-i="index">
-                        <tr *ngIf="response.type === 'DOMAIN'" class="table-row">
-                            <td>{{'BULK.STATE.' + response.state | translate}}</td>
-                            <td>{{response.created}}</td>
-                            <td>{{getDomainId(response)}}</td>
-                            <td>{{getDomainName(response)}}</td>
-                            <td>{{getDomainCodeName(response)}}</td>
-                            <td style="width: 5%" class="text-right" *ngIf="bulk.state !== 'REMOVED'">
-                                <i *ngIf="response.type === 'DOMAIN'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/domains/view/', response?.details['domainId']]"></i>
-                                <i *ngIf="response.type === 'USER'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/users/view', response?.details['userId']]"></i>
-                    <!-- <span class="dropdown">
-            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
-               data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-              <li *ngIf="response.type === 'DOMAIN'">
-                <a [routerLink]="['/admin/domains/view/', response?.details['domainId']]">{{ 'BULK.LIST.MOVE_DOMAIN' | translate }}</a>
-              </li>
-                 <li *ngIf="response.type === 'USER'">
-                <a [routerLink]="['/admin/users/view', response?.details['userId']]">{{ 'BULK.LIST.MOVE_USER' | translate }}</a>
-              </li>
-            </ul>
-          </span> -->
-                            </td>
+                <div class="panel-body">
+                    <table class="table table-hover table-condensed" aria-describedby="Domains in Group table">
+                        <thead>
+                        <tr>
+                            <th scope="col">{{'BULK.LIST.STATE' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.CREATED' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.DOMAIN_ID' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.DOMAIN_NAME' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.DOMAIN_CODENAME' | translate}}</th>
+                            <th style="width: 5%" scope="col"></th>
                         </tr>
-                    </ng-template>
-                    </thead>
-                </table>
+                        <ng-template ngFor let-response [ngForOf]="bulk.entries" let-i="index">
+                            <tr *ngIf="response.type === 'DOMAIN'" class="table-row">
+                                <td>{{'BULK.STATE.' + response.state | translate}}</td>
+                                <td>{{response.created}}</td>
+                                <td>{{getDomainId(response)}}</td>
+                                <td>{{getDomainName(response)}}</td>
+                                <td>{{getDomainCodeName(response)}}</td>
+                                <td style="width: 5%" class="text-right" *ngIf="bulk.state !== 'REMOVED'">
+                                    <i *ngIf="response.type === 'DOMAIN'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/domains/view/', response?.details['domainId']]"></i>
+                                    <i *ngIf="response.type === 'USER'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/users/view', response?.details['userId']]"></i>
+                                    <!-- <span class="dropdown">
+                            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
+                               data-toggle="dropdown" href="#" role="button">
+                              <em class="fas fa-cog icon-black icon-bigger"></em>
+                            </a>
+                            <ul class="dropdown-menu pull-right-drop">
+                              <li *ngIf="response.type === 'DOMAIN'">
+                                <a [routerLink]="['/admin/domains/view/', response?.details['domainId']]">{{ 'BULK.LIST.MOVE_DOMAIN' | translate }}</a>
+                              </li>
+                                 <li *ngIf="response.type === 'USER'">
+                                <a [routerLink]="['/admin/users/view', response?.details['userId']]">{{ 'BULK.LIST.MOVE_USER' | translate }}</a>
+                              </li>
+                            </ul>
+                          </span> -->
+                                </td>
+                            </tr>
+                        </ng-template>
+                        </thead>
+                    </table>
 
+                </div>
             </div>
-        </div>
 
-        <div class="panel panel-default" style="margin-top: 3rem">
-            <div class="panel-heading">
+            <div class="panel panel-default" style="margin-top: 3rem">
+                <div class="panel-heading">
 
-                <div style="display: flex; justify-content: start; align-items: center">
-                    <div>
-                        {{'BULK.USER.DEPLOYMENTS' | translate }}
+                    <div style="display: flex; justify-content: start; align-items: center">
+                        <div>
+                            {{'BULK.USER.DEPLOYMENTS' | translate }}
+                        </div>
                     </div>
                 </div>
-            </div>
-            <div class="panel-body">
-                <table class="table table-hover table-condensed" aria-describedby="Domains in Group table">
-                    <thead>
-                    <tr>
-                        <th scope="col">{{'BULK.LIST.STATE' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.CREATED' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.USER_ID' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.USER_NAME' | translate}}</th>
-                        <th scope="col">{{'BULK.LIST.EMAIL' | translate}}</th>
-                        <th style="width: 5%" scope="col"></th>
-                    </tr>
-                    <ng-template ngFor let-response [ngForOf]="bulk.entries" let-i="index">
-                        <tr *ngIf="response.type === 'USER'" class="table-row">
-                            <td>{{'BULK.STATE.' + response.state | translate}}</td>
-                            <td>{{response.created}}</td>
-                            <td>{{getUserId(response)}}</td>
-                            <td>{{getUsername(response)}}</td>
-                            <td>{{getEmail(response)}}</td>
-                            <td style="width: 5%" class="text-right">
-                                <i *ngIf="response.type === 'DOMAIN'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/domains/view/', response?.details['domainId']]"></i>
-                                <i *ngIf="response.type === 'USER'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/users/view', response?.details['userId']]"></i>
-
-                    <!-- <span class="dropdown">
-            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
-               data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-                <li *ngIf="response.type === 'DOMAIN'">
-                <a [routerLink]="['/admin/domains/view/', response?.details['domainId']]">{{ 'BULK.LIST.MOVE_DOMAIN' | translate }}</a>
-              </li>
-                 <li *ngIf="response.type === 'USER'">
-                <a [routerLink]="['/admin/users/view', response?.details['userId']]">{{ 'BULK.LIST.MOVE_USER' | translate }}</a>
-              </li>
-            </ul>
-          </span> -->
-                            </td>
+                <div class="panel-body">
+                    <table class="table table-hover table-condensed" aria-describedby="Domains in Group table">
+                        <thead>
+                        <tr>
+                            <th scope="col">{{'BULK.LIST.STATE' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.CREATED' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.USER_ID' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.USER_NAME' | translate}}</th>
+                            <th scope="col">{{'BULK.LIST.EMAIL' | translate}}</th>
+                            <th style="width: 5%" scope="col"></th>
                         </tr>
-                    </ng-template>
-                    </thead>
-                </table>
+                        <ng-template ngFor let-response [ngForOf]="bulk.entries" let-i="index">
+                            <tr *ngIf="response.type === 'USER'" class="table-row">
+                                <td>{{'BULK.STATE.' + response.state | translate}}</td>
+                                <td>{{response.created}}</td>
+                                <td>{{getUserId(response)}}</td>
+                                <td>{{getUsername(response)}}</td>
+                                <td>{{getEmail(response)}}</td>
+                                <td style="width: 5%" class="text-right">
+                                    <i *ngIf="response.type === 'DOMAIN'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/domains/view/', response?.details['domainId']]"></i>
+                                    <i *ngIf="response.type === 'USER'" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/admin/users/view', response?.details['userId']]"></i>
 
-            </div>
-        </div>
+                                    <!-- <span class="dropdown">
+                            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
+                               data-toggle="dropdown" href="#" role="button">
+                              <em class="fas fa-cog icon-black icon-bigger"></em>
+                            </a>
+                            <ul class="dropdown-menu pull-right-drop">
+                                <li *ngIf="response.type === 'DOMAIN'">
+                                <a [routerLink]="['/admin/domains/view/', response?.details['domainId']]">{{ 'BULK.LIST.MOVE_DOMAIN' | translate }}</a>
+                              </li>
+                                 <li *ngIf="response.type === 'USER'">
+                                <a [routerLink]="['/admin/users/view', response?.details['userId']]">{{ 'BULK.LIST.MOVE_USER' | translate }}</a>
+                              </li>
+                            </ul>
+                          </span> -->
+                                </td>
+                            </tr>
+                        </ng-template>
+                        </thead>
+                    </table>
 
+                </div>
+            </div>
 
-    </div>
 
-    <div *ngIf="bulk && bulkType === 'APPLICATION' ">
-        <div class="flex justify-content-between">
-            <h3>{{'BULK.APP.VIEW_HEADER' | translate}}</h3>
-            <img alt="App logo" style="width: 50px"
-                             [src]="(appImagesService.getAppLogoUrl(bulk.details['appId']) | secure) || 'assets/images/app-logo-example.png'"/>
         </div>
-        
-        <div class="" style="padding-bottom: 5rem; margin-top: 3rem">
-            <label for="id" class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.ID' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="id" name="id" [disabled]="true"
-                       [(ngModel)]="bulk.id" #name="ngModel">
+
+        <div *ngIf="bulk && bulkType === 'APPLICATION' ">
+            <div class="flex justify-content-between">
+                <h3>{{'BULK.APP.VIEW_HEADER' | translate}}</h3>
+                <img alt="App logo" style="width: 50px"
+                     [src]="(appImagesService.getAppLogoUrl(bulk.details['appId']) | secure) || 'assets/images/app-logo-example.png'"/>
             </div>
-        </div>
 
-        <div class="" style="padding-bottom: 5rem;">
-            <label for="id" class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.APP_NAME' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="id" name="id" [disabled]="true"
-                       [(ngModel)]="bulk.details['appName']" #name="ngModel">
+            <div class="" style="padding-bottom: 5rem; margin-top: 3rem">
+                <label for="id" class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.ID' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="id" name="id" [disabled]="true"
+                           [(ngModel)]="bulk.id" #name="ngModel">
+                </div>
             </div>
-            
-        </div>
 
-        <div class="" style="padding-bottom: 5rem">
-            <label for="creator"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATOR' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="creator" name="creator" [disabled]="true"
-                       placeholder="{{bulk.creator.username}} ({{bulk.creator.firstname}} {{bulk.creator.lastname}})">
+            <div class="" style="padding-bottom: 5rem;">
+                <label for="id" class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.APP_NAME' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="id" name="id" [disabled]="true"
+                           [(ngModel)]="bulk.details['appName']" #name="ngModel">
+                </div>
+
             </div>
-        </div>
 
-        <div class="" style="padding-bottom: 5rem">
-            <label for="date"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATION_DATE' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="date" name="date" [disabled]="true"
-                       placeholder="{{bulk.creationDate | date: 'dd-MM-yyyy HH:mm'}}">
+            <div class="" style="padding-bottom: 5rem">
+                <label for="creator"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATOR' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="creator" name="creator" [disabled]="true"
+                           placeholder="{{bulk.creator.username}} ({{bulk.creator.firstname}} {{bulk.creator.lastname}})">
+                </div>
             </div>
-        </div>
 
-        <div class="" style="padding-bottom: 5rem">
-            <label for="state"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.STATE' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="state" name="state" [disabled]="true"
-                       placeholder="{{'BULK.STATE.' + bulk.state | translate}}">
+            <div class="" style="padding-bottom: 5rem">
+                <label for="date"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.CREATION_DATE' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="date" name="date" [disabled]="true"
+                           placeholder="{{bulk.creationDate | date: 'dd-MM-yyyy HH:mm'}}">
+                </div>
             </div>
-        </div>
 
-        <div class="" style="padding-bottom: 5rem">
-            <label for="completionDate"
-                   class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.COMPLETION_DATE' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" id="completionDate" name="completionDate" [disabled]="true"
-                       placeholder="{{completionDate}}">
+            <div class="" style="padding-bottom: 5rem">
+                <label for="state"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.STATE' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="state" name="state" [disabled]="true"
+                           placeholder="{{'BULK.STATE.' + bulk.state | translate}}">
+                </div>
+            </div>
+
+            <div class="" style="padding-bottom: 5rem">
+                <label for="completionDate"
+                       class="col-sm-2 control-label text-right mt-2">{{ 'BULK.LIST.COMPLETION_DATE' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control" id="completionDate" name="completionDate" [disabled]="true"
+                           placeholder="{{completionDate}}">
+                </div>
             </div>
-        </div>
 
-      
 
-        <div *ngIf="bulk.state !== 'REMOVED'" class="flex justify-content-end" style="padding-right: 1.5rem">
-            <button class="btn btn-primary mr-2" (click)="refreshStates()">{{'BULK.APP.REFRESH' | translate}}</button>
 
-            <button *ngIf="bulk.state !== 'FAILED'" class="btn btn-primary" (click)="getAppBulkDetails(this.bulkId)">{{'BULK.APP.DOWNLOAD_CSV' | translate}}</button>
-        </div>
-        <div class="mt-4">
-            <p-progressBar [mode]="progressBarMode"[value]="progressBarValue" id="progressBarr" [style]="{ height: '18px' }" [styleClass]="jobDone ? 'job-done-bar' : 'normal-bar'">
-                <ng-template pTemplate="content" let-value> 
-                    <span>{{queueDetails?.jobDone}} <span *ngIf="queueDetails?.jobDone !== bulk.entries.length">(+{{queueDetails?.jobInProcess}})</span> / {{bulk.entries.length}}</span>    
+            <div *ngIf="bulk.state !== 'REMOVED'" class="flex justify-content-end" style="padding-right: 1.5rem">
+                <button class="btn btn-primary mr-2" (click)="refreshStates()">{{'BULK.APP.REFRESH' | translate}}</button>
+
+                <button *ngIf="bulk.state !== 'FAILED'" class="btn btn-primary" (click)="getAppBulkDetails(this.bulkId)">{{'BULK.APP.DOWNLOAD_CSV' | translate}}</button>
+            </div>
+            <div class="mt-4">
+                <p-progressBar [mode]="progressBarMode"[value]="progressBarValue" id="progressBarr" [style]="{ height: '18px' }" [styleClass]="jobDone ? 'job-done-bar' : 'normal-bar'">
+                    <ng-template pTemplate="content" let-value>
+                        <span>{{queueDetails?.jobDone}} <span *ngIf="queueDetails?.jobDone !== bulk.entries.length">(+{{queueDetails?.jobInProcess}})</span> / {{bulk.entries.length}}</span>
                     </ng-template>
-            </p-progressBar>
+                </p-progressBar>
 
-        </div>
-        <div class="panel panel-default" style="margin-top: 1rem">
-            <div class="panel-heading">
+            </div>
+            <div class="panel panel-default" style="margin-top: 1rem">
+                <div class="panel-heading">
 
-                <div style="display: flex; justify-content: start; align-items: center">
-                    <div>
-                        {{ 'BULK.APP.DEPLOYMENTS' | translate }}
+                    <div style="display: flex; justify-content: start; align-items: center">
+                        <div>
+                            {{ 'BULK.APP.DEPLOYMENTS' | translate }}
+                        </div>
                     </div>
                 </div>
-            </div>
-            <div class="panel-body">
-
-        
-                <table class="table table-hover table-condensed" aria-describedby="Domains in Group table">
-                    <thead>
-                    <tr #column>
-                        <th scope="col">{{'BULK.LIST.STATE' | translate}}</th>
-                        <th scope="col">{{'BULK.APP.INSTANCE_ID' | translate}}</th>
-                        <th scope="col">{{'BULK.APP.INSTANCE_NAME' | translate}}</th>
-                        <th scope="col">{{'BULK.APP.DOMAIN' | translate}}</th>
-                        <th style="width: 5%" scope="col"></th>
-                    </tr>
-                    <ng-template ngFor let-response [ngForOf]="bulk.entries" let-i="index">
-                        <tr *ngIf="response.type === 'APPLICATION'" class="table-row">
-                            <td>{{'BULK.STATE.' + response.state | translate}}  <em
-                                    *ngIf="response.state == 'PROCESSING'"
-                                    class="pi pi-spin pi-spinner ml-1"
-                                    style="font-size: 1.4rem"></em>
-                                <em *ngIf="response.state == 'FAILED' && response?.details['appInstanceId'] === undefined" class="pi pi-info-circle"
-                                    style="font-size: 1.4rem"
-                                    pTooltip="{{response?.details['errorMessage']}}"
-                                    tooltipStyleClass="p-tooltip-width " [fitContent]="false"></em></td>
-                            <td>{{getAppInstanceId(response)}}</td>
-                            <td>{{getAppInstanceName(response)}}</td>
-                            <td>{{getDomainCodeName(response)}}</td>
-                            <td style="width: 5%" class="text-right"  >
-                                <i *ngIf="response?.details['appInstanceId'] !== undefined" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/instances/', response?.details['appInstanceId']]"></i>
-                    <!-- <span *ngIf="response?.details['appInstanceId'] !== undefined" class="dropdown">
-            <a  style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
-               data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-                 <li *ngIf="response.type === 'APPLICATION' && response?.details['appInstanceId'] !== undefined">
-                <a [routerLink]="['/instances/', response?.details['appInstanceId']]">{{ 'BULK.LIST.MOVE_APP' | translate }}</a>
-              </li>
-                 <li *ngIf="response.type === 'APPLICATION' && response.state !== 'COMPLETED'">
-                    <a>{{ 'BULK.APP.CHECK_STATE' | translate }}</a>
-                </li> 
-            </ul>
-          </span> -->
-                            </td>
+                <div class="panel-body">
+
+
+                    <table class="table table-hover table-condensed" aria-describedby="Domains in Group table">
+                        <thead>
+                        <tr #column>
+                            <th scope="col">{{'BULK.LIST.STATE' | translate}}</th>
+                            <th scope="col">{{'BULK.APP.INSTANCE_ID' | translate}}</th>
+                            <th scope="col">{{'BULK.APP.INSTANCE_NAME' | translate}}</th>
+                            <th scope="col">{{'BULK.APP.DOMAIN' | translate}}</th>
+                            <th style="width: 5%" scope="col"></th>
                         </tr>
-                    </ng-template>
-                    </thead>
-                </table>
+                        <ng-template ngFor let-response [ngForOf]="bulk.entries" let-i="index">
+                            <tr *ngIf="response.type === 'APPLICATION'" class="table-row">
+                                <td>{{'BULK.STATE.' + response.state | translate}}  <em
+                                        *ngIf="response.state == 'PROCESSING'"
+                                        class="pi pi-spin pi-spinner ml-1"
+                                        style="font-size: 1.4rem"></em>
+                                    <em *ngIf="response.state == 'FAILED' && response?.details['appInstanceId'] === undefined" class="pi pi-info-circle"
+                                        style="font-size: 1.4rem"
+                                        pTooltip="{{response?.details['errorMessage']}}"
+                                        tooltipStyleClass="p-tooltip-width " [fitContent]="false"></em></td>
+                                <td>{{getAppInstanceId(response)}}</td>
+                                <td>{{getAppInstanceName(response)}}</td>
+                                <td>{{getDomainCodeName(response)}}</td>
+                                <td style="width: 5%" class="text-right"  >
+                                    <i *ngIf="response?.details['appInstanceId'] !== undefined" class="pi pi-search" style="font-size: 1.8rem; cursor: pointer" [routerLink]="['/instances/', response?.details['appInstanceId']]"></i>
+                                    <!-- <span *ngIf="response?.details['appInstanceId'] !== undefined" class="dropdown">
+                            <a  style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true"
+                               data-toggle="dropdown" href="#" role="button">
+                              <em class="fas fa-cog icon-black icon-bigger"></em>
+                            </a>
+                            <ul class="dropdown-menu pull-right-drop">
+                                 <li *ngIf="response.type === 'APPLICATION' && response?.details['appInstanceId'] !== undefined">
+                                <a [routerLink]="['/instances/', response?.details['appInstanceId']]">{{ 'BULK.LIST.MOVE_APP' | translate }}</a>
+                              </li>
+                                 <li *ngIf="response.type === 'APPLICATION' && response.state !== 'COMPLETED'">
+                                    <a>{{ 'BULK.APP.CHECK_STATE' | translate }}</a>
+                                </li>
+                            </ul>
+                          </span> -->
+                                </td>
+                            </tr>
+                        </ng-template>
+                        </thead>
+                    </table>
 
+                </div>
             </div>
-        </div>
 
+        </div>
     </div>
 
 
+
 </div>
diff --git a/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.css b/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..f2c387a9db7ec1e2c9aeefc41a92b4d6336c9fdb
--- /dev/null
+++ b/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.css
@@ -0,0 +1,38 @@
+:host ::ng-deep input[type=file]{
+    display:none;
+}
+:host ::ng-deep  .p-button{
+    width: unset;
+    margin-right: 5px;
+    background: var(--primary-button-color);
+    color: var(--button-text-color);
+}
+:host ::ng-deep .p-button:hover{
+    background: var(--primary-button-hover);
+    border:none;
+}
+:host ::ng-deep .p-button-label{
+    font-weight: normal;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-buttonbar{
+    border: none;
+    background: transparent;
+    margin-bottom: 10px;
+    padding: 0;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-content{
+    border: none;
+    padding: 0;
+    border-radius: 3px;
+
+}
+:host ::ng-deep .p-fileupload-content .p-progressbar{
+    display: none;
+}
+textarea{
+    border-color: #ccc;
+}
+:host ::ng-deep .p-inputtext:enabled:focus{
+    box-shadow: none;
+    border-color: var(--l-text-color);
+}
diff --git a/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.html b/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.html
index 71d0eff138b7dc6da3d9f249f33ce97de8f63dc2..3a56ddc0d02e4864d2cd351ce33f7d06bdbbb772 100644
--- a/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.html
+++ b/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.html
@@ -1,28 +1,31 @@
-<div style="width: 80%; margin: auto; margin-top: 4rem;">
-    <div style="margin-bottom: 2rem">
-        <h2>{{'BULK.DOMAIN.NAVIGATION' | translate}}</h2>
-        <p class="mt-4">{{'BULK.DOMAIN.UPLOAD' | translate}}</p>
-    </div>
-    <p-fileUpload name="file[]" customUpload="true" (uploadHandler)="myUploader($event)" accept=".csv"
-                  multiple="false" uploadLabel="{{'BULK.BUTTON' | translate}}"></p-fileUpload>
+<div style="width: 100%; margin: auto; margin-top: 4rem;">
+    <h3>{{'BULK.DOMAIN.NAVIGATION' | translate}}</h3>
+    <div class="background-section">
+        <div style="margin-bottom: 2rem">
 
-    <div style="margin-top: 1.5rem; display: flex; justify-content: center; flex-direction: column">
-        <div style="margin-top: 1.5rem; margin-bottom: 1rem">
-            <p>{{'BULK.APP.UPLOAD_TEXT' | translate}}</p>
+            <p class="">{{'BULK.DOMAIN.UPLOAD' | translate}}</p>
         </div>
-        <textarea pInputTextarea [(ngModel)]="csvText" rows="10" cols="127" (keyup)="changeDetector = true"></textarea>
-    </div>
+        <p-fileUpload name="file[]" (uploadHandler)="myUploader($event)" accept=".csv"
+                      multiple="false" uploadLabel="{{'BULK.BUTTON' | translate}}" ></p-fileUpload>
 
-    <div *ngIf="errorMessage !== ''" style="margin-top: 1rem; display: flex; justify-content: start; color: indianred">
-        <p>{{errorMessage}}</p>
-    </div>
+        <div style="margin-top: 1.5rem; display: flex; justify-content: center; flex-direction: column">
+            <div style="margin-top: 1.5rem; margin-bottom: 1rem">
+                <p>{{'BULK.APP.UPLOAD_TEXT' | translate}}</p>
+            </div>
+            <textarea pInputTextarea [(ngModel)]="csvText" rows="10" cols="127" [autoResize]="true" (keyup)="changeDetector = true"></textarea>
+        </div>
 
-    <div  style="margin-top: 2rem; display: flex; justify-content: center;" >
+        <div *ngIf="errorMessage !== ''" style="margin-top: 1rem; display: flex; justify-content: start; color: indianred">
+            <p>{{errorMessage}}</p>
+        </div>
+
+        <div *ngIf="showProgressBar" style="margin-top: 20px;">
+            <p>{{ 'BULK.DOMAIN.DEPLOYMENT_IN_PROGRESS' | translate }}</p>
+            <p-progressBar mode="indeterminate" [style]="{height : '8px'}"></p-progressBar>
+        </div>
+    </div>
+    <div  style="margin-top: 2rem; display: flex; justify-content: end;" >
         <button class="btn btn-primary" (click)="uploadText(); this.errorMessage=''" [disabled]="csvText === '' || !changeDetector"> {{'BULK.UPLOAD_BUTTON' | translate}}</button>
     </div>
 
-    <div *ngIf="showProgressBar" style="margin-top: 20px;">
-        <p>{{ 'BULK.DOMAIN.DEPLOYMENT_IN_PROGRESS' | translate }}</p>
-        <p-progressBar mode="indeterminate" [style]="{height : '8px'}"></p-progressBar>
-    </div>
 </div>
diff --git a/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.ts b/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.ts
index 7919ba6ecd003708201643d666a6c445a99516ba..cc11875e86b51b7446c66f0834dd38d6c6c82893 100644
--- a/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.ts
+++ b/src/app/appmarket/bulkDeployment/domainDeployment/domainupload/domainupload.component.ts
@@ -7,7 +7,7 @@ import {DomainService} from '../../../../service';
 @Component({
     selector: 'app-domainupload',
     templateUrl: './domainupload.component.html',
-    styleUrls: []
+    styleUrls: ['./domainupload.component.css']
 })
 export class DomainuploadComponent {
 
diff --git a/src/app/appmarket/domains/domain-annotations/domain-annotations.component.html b/src/app/appmarket/domains/domain-annotations/domain-annotations.component.html
index b7a1c8994df0487f51786029da9a476fb7173f56..45ab00bcd295953589a3e5c2ddc03f9bc7d2b0aa 100644
--- a/src/app/appmarket/domains/domain-annotations/domain-annotations.component.html
+++ b/src/app/appmarket/domains/domain-annotations/domain-annotations.component.html
@@ -1,7 +1,7 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm-10 col-md-offset-1 col-md-10">
+<div class="">
     <h3> {{'DOMAINS.ANNOTATIONS.HEADER' | translate}}</h3>
     <p>{{'DOMAINS.ANNOTATIONS.SUBHEADER' | translate}} </p>
-    <div class="flex flex-grow-1 mt-6 col-sm-12" style="width: 100% !important;">
+    <div class="" style="width: 100% !important;">
         <app-domain-namespace-annotations [annotationRead]="annotations" [globalSettings]="true" (annotations)="handleAnnotationsUpdate($event)" 
         (trigerDelete)="handleDelete($event)" class="flex flex-grow-1"></app-domain-namespace-annotations>
     </div>
diff --git a/src/app/appmarket/domains/domain-group-view/domain-group-view.component.html b/src/app/appmarket/domains/domain-group-view/domain-group-view.component.html
index c42594752a704d430b01c6c597c099788a2ccb41..56d68346cc403a477bb1ce1a6a05d258bbaa0e54 100644
--- a/src/app/appmarket/domains/domain-group-view/domain-group-view.component.html
+++ b/src/app/appmarket/domains/domain-group-view/domain-group-view.component.html
@@ -1,40 +1,49 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm-10 col-md-offset-1 col-md-10">
-    <h3>{{ 'DOMAINS.LIST.GROUP' | translate }}</h3>
+<div class="">
+    <h4 class="header">{{ 'DOMAINS.LIST.GROUP' | translate }}</h4>
     <form *ngIf="domainGroup" (submit)="submit(false)" class="form-horizontal" #domainForm="ngForm">
-        <div class="form-group">
-            <label for="name" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.NAME' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control"  id="name" name="name"
-                       [(ngModel)]="domainGroup.name" #name="ngModel" required>
-                <div *ngIf="name.invalid && (name.dirty || name.touched)"
-                     class="alert alert-danger">
-                    <div *ngIf="name.errors.required">{{ 'DOMAIN_DETAILS.NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
+        <div class="background-section">
+            <div class="form-group">
+                <label for="name" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.NAME' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control"  id="name" name="name"
+                           [(ngModel)]="domainGroup.name" #name="ngModel" required>
+                    <div *ngIf="name.invalid && (name.dirty || name.touched)"
+                         class="alert alert-danger">
+                        <div *ngIf="name.errors.required">{{ 'DOMAIN_DETAILS.NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
+                    </div>
                 </div>
             </div>
-        </div>
 
-        <div class="form-group" *ngIf="!isInMode(ComponentMode.EDIT)">
-            <label for="codename" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.CODE_NAME' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control"  id="codename"
-                       name="codename" pattern="[a-zA-Z0-9-]*"
-                       [(ngModel)]="domainGroup.codename" #codename="ngModel" minlength="2" maxlength="20" required>
-                <div *ngIf="codename.invalid && (codename.dirty || codename.touched)"
-                     class="alert alert-danger">
+            <div class="form-group" *ngIf="!isInMode(ComponentMode.EDIT)">
+                <label for="codename" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.CODE_NAME' | translate }}</label>
+                <div class="col-sm-10">
+                    <input type="text" class="form-control"  id="codename"
+                           name="codename" pattern="[a-zA-Z0-9-]*"
+                           [(ngModel)]="domainGroup.codename" #codename="ngModel" minlength="2" maxlength="20" required>
+                    <div *ngIf="codename.invalid && (codename.dirty || codename.touched)"
+                         class="alert alert-danger">
 
-                    <div *ngIf="codename.errors.required">{{ 'DOMAIN_DETAILS.CODE_NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
-                    <div *ngIf="codename.errors.pattern">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_1' | translate }}</div>
-                    <div *ngIf="codename.errors.minlength || codename.errors.maxlength">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_2' | translate }}</div>
+                        <div *ngIf="codename.errors.required">{{ 'DOMAIN_DETAILS.CODE_NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
+                        <div *ngIf="codename.errors.pattern">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_1' | translate }}</div>
+                        <div *ngIf="codename.errors.minlength || codename.errors.maxlength">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_2' | translate }}</div>
 
+                    </div>
                 </div>
             </div>
         </div>
-        <div *ngIf="!this.addingMode" class="panel panel-default" style="margin-top: 3rem">
+
+        <div *ngIf="!this.addingMode" class="background-section" style="margin-top: 3rem">
             <div class="panel-heading">
 
-                <div style="display: flex; justify-content: start; align-items: center">
-                    <div>
+                <div style="display: flex; justify-content:space-between">
+                    <h4 style="font-size:15px; font-weight: bold">
                         {{ 'DOMAINS.GROUP.ACCESS_USER' | translate }}
+                    </h4>
+                    <div *roles="['ROLE_SYSTEM_ADMIN']" style="display: flex; justify-content: end">
+                        <button  type="button" class="btn btn-text" (click)="showModalUser()">{{'DOMAINS.GROUP.ADD_USERS' | translate}}</button>
+                    </div>
+                    <div *roles="['ROLE_VL_MANAGER']" style="display: flex; justify-content: end">
+                        <button  type="button" class="btn btn-warning" (click)="removeMyAccess()">{{'DOMAINS.GROUP.DELETE_MYSELF' | translate}}</button>
                     </div>
                 </div>
             </div>
@@ -42,7 +51,7 @@
                 <div *roles="['ROLE_SYSTEM_ADMIN']" style="display: flex; justify-content: end">
                     <button  type="button" class="btn btn-secondary" (click)="showModalUser()">{{'DOMAINS.GROUP.ADD_USERS' | translate}}</button>
                 </div>
-                <div *roles="['ROLE_VL_MANAGER']" style="display: flex; justify-content: end">
+                <div *roles="['ROLE_GROUP_MANAGER']" style="display: flex; justify-content: end">
                     <button  type="button" class="btn btn-warning" (click)="removeMyAccess()">{{'DOMAINS.GROUP.DELETE_MYSELF' | translate}}</button>
                 </div>
                 <table class="table table-hover table-condensed" aria-describedby="Domains in Group table" style="margin-top: 2rem">
@@ -211,8 +220,8 @@
         </table>
     </div>
     <div class="nmaas-modal-footer">
-        <button type="button" class="btn btn-primary" (click)="closeModal()" [disabled]="false">{{'DOMAINS.LIST.ADD' | translate}}</button>
         <button type="button" class="btn btn-secondary" (click)="modal.hide()">{{'APP_CHANGE_STATE_MODAL.CANCEL_BUTTON' | translate}}</button>
+        <button type="button" class="btn btn-primary" (click)="closeModal()" [disabled]="false">{{'DOMAINS.LIST.ADD' | translate}}</button>
     </div>
 </nmaas-modal>
 
@@ -258,7 +267,7 @@
         </table>
     </div>
     <div class="nmaas-modal-footer">
-        <button type="button" class="btn btn-primary" (click)="saveUsers()" [disabled]="false">{{'DOMAINS.GROUP.ADD_USERS' | translate}}</button>
         <button type="button" class="btn btn-secondary" (click)="closeModalUserAccess()">{{'APP_CHANGE_STATE_MODAL.CANCEL_BUTTON' | translate}}</button>
+        <button type="button" class="btn btn-primary" (click)="saveUsers()" [disabled]="false">{{'DOMAINS.GROUP.ADD_USERS' | translate}}</button>
     </div>
 </nmaas-modal>
diff --git a/src/app/appmarket/domains/domain-group-view/domain-group-view.component.spec.ts b/src/app/appmarket/domains/domain-group-view/domain-group-view.component.spec.ts
index 82d18dc612c8aeaee246b0f383482b4108fe5bdc..fa207e464e4238670e8196973654cbecb6738ce1 100644
--- a/src/app/appmarket/domains/domain-group-view/domain-group-view.component.spec.ts
+++ b/src/app/appmarket/domains/domain-group-view/domain-group-view.component.spec.ts
@@ -1,32 +1,68 @@
 import { ComponentFixture, TestBed } from '@angular/core/testing';
-
 import { DomainGroupViewComponent } from './domain-group-view.component';
-import {RouterTestingModule} from '@angular/router/testing';
-import {HttpClientTestingModule} from '@angular/common/http/testing';
-import {TranslateFakeLoader, TranslateLoader, TranslateModule} from '@ngx-translate/core';
-import {FormsModule, ReactiveFormsModule} from '@angular/forms';
-import {of} from 'rxjs';
-import createSpyObj = jasmine.createSpyObj;
-import {UserService} from '../../../service';
-import {AuthService} from '../../../auth/auth.service';
+import { RouterTestingModule } from '@angular/router/testing';
+import { HttpClientTestingModule } from '@angular/common/http/testing';
+import { TranslateFakeLoader, TranslateLoader, TranslateModule } from '@ngx-translate/core';
+import { FormsModule, ReactiveFormsModule } from '@angular/forms';
+import { of } from 'rxjs';
+import { DomainService, UserService } from '../../../service';
+import { AuthService } from '../../../auth/auth.service';
+import { ProfileService } from '../../../service/profile.service';
+import { ModalComponent } from '../../../shared';
 import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+import { DomainGroup } from '../../../model/domaingroup';
+import { Domain } from '../../../model/domain';
+import { User } from '../../../model/user';
+import { Role } from '../../../model/userrole';
+import { ActivatedRoute, Router } from '@angular/router';
+import { DomainApplicationStatePerDomain } from '../../../model/domainapplicationstateperdomain';
 
 describe('DomainGroupViewComponent', () => {
   let component: DomainGroupViewComponent;
   let fixture: ComponentFixture<DomainGroupViewComponent>;
+  let mockDomainService: jasmine.SpyObj<DomainService>;
+  let mockUserService: jasmine.SpyObj<UserService>;
+  let mockAuthService: jasmine.SpyObj<AuthService>;
+  let mockProfileService: jasmine.SpyObj<ProfileService>;
+  let mockModal: jasmine.SpyObj<ModalComponent>;
+  let mockActivatedRoute: any;
+    let mockRouter: jasmine.SpyObj<Router>;
+  
 
-  const userServiceSpy = createSpyObj('UserService', ['getAll'])
-  userServiceSpy.getAll.and.returnValue(of([]))
-
-  const authServiceSpy = createSpyObj('AuthService', ['hasRole', 'hasDomainRole', 'getRoles']);
-  authServiceSpy.hasRole.and.returnValue(true)
-  authServiceSpy.hasDomainRole.and.returnValue(true)
-  authServiceSpy.getRoles.and.returnValue([''])
+  beforeEach(async () => {
+    mockDomainService = jasmine.createSpyObj('DomainService', [
+      'getDomainGroup',
+      'createDomainGroup',
+      'updateDomainGroup',
+      'deleteDomainFromGroup',
+      'getAll', 
+      'addDomainsToGroup',
+      'updateDomainGroupManagers',
+      'getGlobalDomainId',
+    ]);
+    mockDomainService.getAll.and.returnValue(of([])); // Mock getAll to return an empty array
+    mockDomainService.getGlobalDomainId.and.returnValue(0); // Mock getGlobalDomainId
+    mockDomainService.getDomainGroup.and.returnValue(of({
+      id: 0,
+      name: '',
+      codename: '',
+      domains: [],
+      applicationStatePerDomain: [],
+      managers: []
+    } as DomainGroup)); // Mock getDomainGroup to return a valid DomainGroup object
 
+    mockUserService = jasmine.createSpyObj('UserService', ['getUserBySearchManagers']);
+    mockAuthService = jasmine.createSpyObj('AuthService', ['getUsername']);
+    mockRouter = jasmine.createSpyObj('Router', ['navigate']);
+    mockProfileService = jasmine.createSpyObj('ProfileService', ['getOne']);
+    mockModal = jasmine.createSpyObj('ModalComponent', ['show', 'hide']);
+    mockActivatedRoute = {
+      snapshot: { data: { mode: 'VIEW' } },
+      params: of({ id: 1 }) // Mock route parameters
+    };
 
-  beforeEach(async () => {
     await TestBed.configureTestingModule({
-      declarations: [ DomainGroupViewComponent ],
+      declarations: [DomainGroupViewComponent, ModalComponent],
       imports: [
         RouterTestingModule,
         HttpClientTestingModule,
@@ -35,26 +71,424 @@ describe('DomainGroupViewComponent', () => {
         TranslateModule.forRoot({
           loader: {
             provide: TranslateLoader,
-            useClass: TranslateFakeLoader
-          }
+            useClass: TranslateFakeLoader,
+          },
         }),
       ],
       providers: [
-        {provide: UserService, useValue: userServiceSpy},
-        {provide: AuthService, useValue: authServiceSpy},
+        { provide: DomainService, useValue: mockDomainService },
+        { provide: UserService, useValue: mockUserService },
+        { provide: AuthService, useValue: mockAuthService },
+        { provide: Router, useValue: mockRouter },
+        { provide: ProfileService, useValue: mockProfileService },
+        { provide: ActivatedRoute, useValue: mockActivatedRoute } // Provide mocked ActivatedRoute
       ],
       schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA],
-    })
-    .compileComponents();
+    }).compileComponents();
   });
 
   beforeEach(() => {
     fixture = TestBed.createComponent(DomainGroupViewComponent);
     component = fixture.componentInstance;
+    component.userAccessModal = mockModal; // Assign mocked user access modal
     fixture.detectChanges();
   });
 
   it('should create', () => {
     expect(component).toBeTruthy();
   });
+
+  it('should initialize and fetch domain group data based on route params', () => {
+    const mockDomainGroup: DomainGroup = {
+      id: 1,
+      name: 'Test Group',
+      codename: 'test-group',
+      domains: [],
+      applicationStatePerDomain: [],
+      managers: []
+    };
+    mockDomainService.getDomainGroup.and.returnValue(of(mockDomainGroup));
+
+    component.ngOnInit();
+
+    expect(mockDomainService.getDomainGroup).toHaveBeenCalledWith(1);
+    expect(component.domainGroup).toEqual(mockDomainGroup);
+  });
+
+  it('should initialize and fetch domain group data', () => {
+    const mockDomainGroup: DomainGroup = {
+      id: 1,
+      name: 'Test Group',
+      codename: 'test-group',
+      domains: [],
+      applicationStatePerDomain: [],
+      managers: []
+    };
+    mockDomainService.getDomainGroup.and.returnValue(of(mockDomainGroup));
+
+    component.domainGroupId = 1;
+    component.refresh();
+
+    expect(mockDomainService.getDomainGroup).toHaveBeenCalledWith(1);
+    expect(component.domainGroup).toEqual(mockDomainGroup);
+  });
+
+  it('should show modal and filter domains', () => {
+    component.domains = [{ id: 1 } as Domain, { id: 2 } as Domain];
+    component.domainGroup.domains = [{ id: 1 } as Domain];
+
+    spyOn(component.modal, 'show');
+
+    component.showModal();
+
+    expect(component.modal.show).toHaveBeenCalled();
+    expect(component.domains).toEqual([{ id: 2 } as Domain]);
+  });
+
+  it('should close modal and add domains to group', () => {
+    component.domainsToAdd = [{ id: 1 } as Domain];
+    mockDomainService.addDomainsToGroup.and.returnValue(of(null));
+    spyOn(component.modal, 'hide');
+
+    component.closeModal();
+
+    expect(mockDomainService.addDomainsToGroup).toHaveBeenCalledWith(component.domainGroup.codename, [1]);
+    expect(component.modal.hide).toHaveBeenCalled();
+  });
+
+  it('should delete a domain from the group', () => {
+    mockDomainService.deleteDomainFromGroup.and.returnValue(of(null));
+    spyOn(component, 'refresh');
+
+    component.domainGroup.id = 1;
+    component.deleteDomainFromGroup({ id: 2 } as Domain);
+
+    expect(mockDomainService.deleteDomainFromGroup).toHaveBeenCalledWith(1, 2);
+    expect(component.refresh).toHaveBeenCalled();
+  });
+
+  it('should search and filter users for adding', () => {
+    const mockUsers: User[] = [
+      {
+        id: 1,
+        username: 'user1',
+        enabled: true,
+        firstname: 'User',
+        lastname: 'One',
+        email: 'user1@example.com',
+        roles: [],
+        termsOfUseAccepted: true,
+        privacyPolicyAccepted: true,
+        ssoUser: false,
+        selectedLanguage: 'en',
+        defaultDomain: 1,
+        lastSuccessfulLoginDate: new Date(),
+        firstLoginDate: new Date(),
+        sshKeys: [],
+        hasSshKeys: false,
+        getRoles(): Role[] { return []; },
+        getDomainIds(): number[] {return [];},
+      },
+      {
+        id: 2,
+        username: 'user2',
+        enabled: true,
+        firstname: 'User',
+        lastname: 'Two',
+        email: 'user2@example.com',
+        roles: [],
+        termsOfUseAccepted: true,
+        privacyPolicyAccepted: true,
+        ssoUser: false,
+        selectedLanguage: 'en',
+        defaultDomain: 1,
+        lastSuccessfulLoginDate: new Date(),
+        firstLoginDate: new Date(),
+        sshKeys: [],
+        hasSshKeys: false,
+        getRoles(): Role[] { return []; },
+        getDomainIds(): number[] {return [];},
+      },
+    ];
+    mockUserService.getUserBySearchManagers.and.returnValue(of(mockUsers));
+    component.domainGroup.managers = [{ id: 1 } as User];
+
+    component.searchUsers('user');
+
+    expect(mockUserService.getUserBySearchManagers).toHaveBeenCalledWith('user');
+    expect(component.usersFound).toEqual([mockUsers[1]]);
+  });
+
+  it('should add a user to the group', () => {
+    const mockUser: User = {
+      id: 1,
+      username: 'user1',
+      enabled: true,
+      firstname: 'User',
+      lastname: 'One',
+      email: 'user1@example.com',
+      roles: [],
+      termsOfUseAccepted: true,
+      privacyPolicyAccepted: true,
+      ssoUser: false,
+      selectedLanguage: 'en',
+      defaultDomain: 1,
+      lastSuccessfulLoginDate: new Date(),
+      firstLoginDate: new Date(),
+      sshKeys: [],
+      hasSshKeys: false,
+      getRoles(): Role[] { return []; },
+      getDomainIds(): number[] { return []; },
+    };
+    component.usersToAdd = [];
+    component.usersFound = [mockUser];
+
+    component.addUser(mockUser);
+
+    expect(component.usersToAdd).toContain(jasmine.objectContaining({
+      id: mockUser.id,
+      username: mockUser.username,
+      firstname: mockUser.firstname,
+      lastname: mockUser.lastname
+    }));
+    expect(component.usersFound).not.toContain(mockUser);
+  });
+
+  it('should save users and update managers', () => {
+    const mockUser: User = {
+      id: 1,
+      username: 'user1',
+      enabled: true,
+      firstname: 'User',
+      lastname: 'One',
+      email: 'user1@example.com',
+      roles: [],
+      termsOfUseAccepted: true,
+      privacyPolicyAccepted: true,
+      ssoUser: false,
+      selectedLanguage: 'en',
+      defaultDomain: 1,
+      lastSuccessfulLoginDate: new Date(),
+      firstLoginDate: new Date(),
+      sshKeys: [],
+      hasSshKeys: false,
+      getRoles(): Role[] { return []; },
+      getDomainIds(): number[] {return [];},
+    };
+    component.usersToAdd = [mockUser];
+    component.domainGroup.managers = [];
+    mockDomainService.updateDomainGroupManagers.and.returnValue(of({
+      id: component.domainGroupId,
+      name: 'Test Group',
+      codename: 'test-group',
+      domains: [],
+      applicationStatePerDomain: [],
+      managers: [mockUser]
+    }));
+    spyOn(component.userAccessModal, 'hide');
+
+    component.saveUsers();
+
+    expect(mockDomainService.updateDomainGroupManagers).toHaveBeenCalledWith([mockUser], component.domainGroupId);
+    expect(component.userAccessModal.hide).toHaveBeenCalled();
+  });
+
+  it('should remove user access from the group', () => {
+    const mockUser: User = {
+      id: 1,
+      username: 'user1',
+      enabled: true,
+      firstname: 'User',
+      lastname: 'One',
+      email: 'user1@example.com',
+      roles: [],
+      termsOfUseAccepted: true,
+      privacyPolicyAccepted: true,
+      ssoUser: false,
+      selectedLanguage: 'en',
+      defaultDomain: 1,
+      lastSuccessfulLoginDate: new Date(),
+      firstLoginDate: new Date(),
+      sshKeys: [],
+      hasSshKeys: false,
+      getRoles(): Role[] { return []; },
+      getDomainIds(): number[] {return []},
+    };
+    component.domainGroup.managers = [mockUser];
+    mockDomainService.updateDomainGroupManagers.and.returnValue(of({
+      id: component.domainGroupId,
+      name: 'Test Group',
+      codename: 'test-group',
+      domains: [],
+      applicationStatePerDomain: [],
+      managers: []
+    }));
+
+    component.deleteUserAccess(mockUser);
+
+    expect(mockDomainService.updateDomainGroupManagers).toHaveBeenCalledWith([], component.domainGroupId);
+    expect(component.domainGroup.managers).toEqual([]);
+  });
+
+  it('should toggle all application states', () => {
+    const mockApplicationState: DomainApplicationStatePerDomain[] = [
+      { applicationBaseId: 1, applicationBaseName: 'App1', enabled: true, pvStorageSizeLimit: 100 },
+      { applicationBaseId: 2, applicationBaseName: 'App2', enabled: false, pvStorageSizeLimit: 200 }
+    ];
+    component.domainGroup.applicationStatePerDomain = mockApplicationState;
+
+    const mockElement = document.createElement('div');
+    mockElement.classList.add('show');
+    spyOn(document, 'querySelector').and.returnValue(mockElement);
+
+    component.toggleAll();
+
+    expect(mockElement.classList.contains('show')).toBeTruthy();
+  });
+
+  it('should sort applications by name', () => {
+    component.domainGroup.applicationStatePerDomain = [
+      { applicationBaseId: 3, applicationBaseName: 'Zebra', enabled: true, pvStorageSizeLimit: 300 },
+      { applicationBaseId: 1, applicationBaseName: 'Apple', enabled: true, pvStorageSizeLimit: 100 },
+      { applicationBaseId: 2, applicationBaseName: 'Mango', enabled: false, pvStorageSizeLimit: 200 }
+    ];
+
+    component.sortApplication();
+
+    expect(component.domainGroup.applicationStatePerDomain).toEqual([
+      { applicationBaseId: 1, applicationBaseName: 'Apple', enabled: true, pvStorageSizeLimit: 100 },
+      { applicationBaseId: 2, applicationBaseName: 'Mango', enabled: false, pvStorageSizeLimit: 200 },
+      { applicationBaseId: 3, applicationBaseName: 'Zebra', enabled: true, pvStorageSizeLimit: 300 }
+    ]);
+  });
+
+  it('should handle domain group creation', () => {
+    const mockOwner = { id: 1, username: 'owner' } as User;
+    const mockCreatedGroup = { id: 2, name: 'New Group' } as DomainGroup;
+    mockProfileService.getOne.and.returnValue(of(mockOwner));
+    mockDomainService.createDomainGroup.and.returnValue(of(mockCreatedGroup));
+
+    component.domainGroup = new DomainGroup();
+    component.submit();
+
+    expect(mockProfileService.getOne).toHaveBeenCalled();
+    expect(mockDomainService.createDomainGroup).toHaveBeenCalledWith(jasmine.objectContaining({
+      managers: [mockOwner]
+    }));
+    expect(mockRouter.navigate).toHaveBeenCalledWith(['/admin/domains/groups/', mockCreatedGroup.id]);
+  });
+
+  it('should handle domain group update', () => {
+    const mockUpdatedGroup = { id: 1, name: 'Updated Group' } as DomainGroup;
+    mockDomainService.updateDomainGroup.and.returnValue(of(mockUpdatedGroup));
+    spyOn(component, 'refresh');
+
+    component.domainGroup = mockUpdatedGroup;
+    component.domainGroupId = 1;
+    component.submit();
+
+    expect(mockDomainService.updateDomainGroup).toHaveBeenCalledWith(mockUpdatedGroup, 1);
+    expect(component.refresh).toHaveBeenCalled();
+  });
+
+  it('should handle domain group update and navigate away', () => {
+    const mockUpdatedGroup = { id: 1, name: 'Updated Group' } as DomainGroup;
+    mockDomainService.updateDomainGroup.and.returnValue(of(mockUpdatedGroup));
+
+    component.domainGroup = mockUpdatedGroup;
+    component.domainGroupId = 1;
+    component.submit(false);
+
+    expect(mockDomainService.updateDomainGroup).toHaveBeenCalledWith(mockUpdatedGroup, 1);
+    expect(mockRouter.navigate).toHaveBeenCalledWith(['/admin/domains/groups']);
+  });
+
+  it('should remove user from selected users to add', () => {
+    const mockUser: User = { id: 1, username: 'user1' } as User;
+    component.usersToAdd = [mockUser];
+
+    component.removeUserFromSelected(mockUser);
+
+    expect(component.usersToAdd).not.toContain(mockUser);
+  });
+
+  it('should close user access modal and reset users', () => {
+    spyOn(component.userAccessModal, 'hide');
+    component.usersToAdd = [{ id: 1, username: 'user1' } as User];
+    component.usersFound = [{ id: 2, username: 'user2' } as User];
+
+    component.closeModalUserAccess();
+
+    expect(component.userAccessModal.hide).toHaveBeenCalled();
+    expect(component.usersToAdd).toEqual([]);
+    expect(component.usersFound).toEqual([]);
+  });
+
+  it('should remove current user access and navigate away', () => {
+    const mockUsername = 'currentUser';
+    mockAuthService.getUsername.and.returnValue(mockUsername);
+    mockDomainService.updateDomainGroup.and.returnValue(of(null));
+
+    component.domainGroup.managers = [
+      {
+        id: 1,
+        username: 'currentUser',
+        enabled: true,
+        firstname: '',
+        lastname: '',
+        email: '',
+        roles: [],
+        termsOfUseAccepted: true,
+        privacyPolicyAccepted: true,
+        ssoUser: false,
+        selectedLanguage: 'en',
+        defaultDomain: 1,
+        lastSuccessfulLoginDate: new Date(),
+        firstLoginDate: new Date(),
+        sshKeys: [],
+        hasSshKeys: false,
+        getRoles(): Role[] { return []; },
+        getDomainIds(): number[] { return []; }
+      },
+      {
+        id: 2,
+        username: 'otherUser',
+        enabled: true,
+        firstname: '',
+        lastname: '',
+        email: '',
+        roles: [],
+        termsOfUseAccepted: true,
+        privacyPolicyAccepted: true,
+        ssoUser: false,
+        selectedLanguage: 'en',
+        defaultDomain: 1,
+        sshKeys: [],
+        hasSshKeys: false,
+      } as User
+    ];
+    component.domainGroupId = 1;
+
+    component.removeMyAccess();
+
+    expect(component.domainGroup.managers).toEqual([{
+      id: 2,
+      username: 'otherUser',
+      enabled: true,
+      firstname: '',
+      lastname: '',
+      email: '',
+      roles: [],
+      termsOfUseAccepted: true,
+      privacyPolicyAccepted: true,
+      ssoUser: false,
+      selectedLanguage: 'en',
+      defaultDomain: 1,
+  
+      sshKeys: [],
+      hasSshKeys: false,
+    } as User]);
+    expect(mockDomainService.updateDomainGroup).toHaveBeenCalledWith(component.domainGroup, 1);
+    expect(mockRouter.navigate).toHaveBeenCalledWith(['/admin/domains/groups']);
+  });
 });
diff --git a/src/app/appmarket/domains/domain-group-view/domain-group-view.component.ts b/src/app/appmarket/domains/domain-group-view/domain-group-view.component.ts
index 9d6a7fa59b5209a0bccc3d7987c14233089f0271..40016cb87969f989e696a01ab2b68dbf6ff4e6a0 100644
--- a/src/app/appmarket/domains/domain-group-view/domain-group-view.component.ts
+++ b/src/app/appmarket/domains/domain-group-view/domain-group-view.component.ts
@@ -117,6 +117,7 @@ export class DomainGroupViewComponent extends BaseComponent implements OnInit {
             this.refresh();
             this.domainsToAdd = [];
             this.refreshDomainForAdd();
+            
         });
         this.modal.hide();
     }
diff --git a/src/app/appmarket/domains/domain-groups/domain-groups.component.css b/src/app/appmarket/domains/domain-groups/domain-groups.component.css
index 7cc4c1ecabca30691fff692308eb4bbbd24dd7fe..e7436baab1c633ac509d2387be02c6255cfeea48 100644
--- a/src/app/appmarket/domains/domain-groups/domain-groups.component.css
+++ b/src/app/appmarket/domains/domain-groups/domain-groups.component.css
@@ -21,3 +21,64 @@
     margin-left: 5px;
     margin-right: 5px;
 }
+
+:host ::ng-deep .p-datatable .p-datatable-thead > tr > th{
+    border: 1px solid #E0E2E5;
+    background:transparent;
+    border-width: 0 0 1px 0;
+}
+:host ::ng-deep .p-datatable .p-datatable-tbody > tr > td {
+    text-align: left;
+    border: 1px solid #E0E2E5;
+    border-width: 0 0 1px 0;
+    padding: 1rem 1rem;
+}
+:host ::ng-deep .p-datatable .p-paginator-bottom{
+    height: 40px;
+    background: transparent;
+    border: none;
+    margin-top:10px;
+}
+:host ::ng-deep .p-datatable .p-datatable-tbody > tr{
+    background: transparent;
+}
+
+:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page{
+    transition: unset;
+    border-radius: 50%;
+    min-width:3.5rem;
+    height:3.5rem;
+    margin:0 5px;
+    font-size: 14px;
+}
+
+:host ::ng-deep .p-paginator-element{
+    border-radius:50%;
+    margin:0 5px;
+    min-width:3.5rem;
+    height:3.5rem;
+    font-size: 14px;
+}
+:host ::ng-deep .p-paginator .p-dropdown{
+    height:3rem;
+}
+:host ::ng-deep .p-paginator-icon{
+    height: 1.5rem;
+    width: 1.5rem;
+}
+:host ::ng-deep .p-paginator .p-dropdown .p-dropdown-label{
+    padding-right: 10px;
+}
+
+label{
+    padding-left:5px;
+    display: unset;
+    margin-bottom: 0;
+    font-weight: unset;
+}
+:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page.p-highlight{
+    background: var(--user-button-background-hover);
+}
+:host ::ng-deep .p-datatable>.p-datatable-wrapper {
+    overflow: visible;
+}
diff --git a/src/app/appmarket/domains/domain-groups/domain-groups.component.html b/src/app/appmarket/domains/domain-groups/domain-groups.component.html
index 53ae0e2083a29f2718b9b1cbd78c80e2039d1fe5..0e054bd69320aa30d884104e74f13f0865f7923e 100644
--- a/src/app/appmarket/domains/domain-groups/domain-groups.component.html
+++ b/src/app/appmarket/domains/domain-groups/domain-groups.component.html
@@ -1,50 +1,60 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm 10 col-md-offset-1 col-md-10">
-    <h3>{{'DOMAINS.LIST.GROUPS' | translate}}</h3>
-    <div class="flex space-between">
-        <div class="flex">
-            <a *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']" [routerLink]="['/admin/domains/groups/add']" class="btn btn-primary"
-               role="button">{{'DOMAINS.ADD_BUTTON' | translate}}</a>
-        </div>
-        <div class="flex">
-            <input pInputText class="flex" name="search" id="search" placeholder="Search" type="text" style="height: 34px" [(ngModel)]="searchValue">
-        </div>
+<div style="display: flex; align-items: center;  margin-top:20px">
+    <div style="margin-right:20px">
+        <span class="p-input-icon-right" style="width: 100%">
+     		 <i class="pi pi-search" style="font-size: 13px; top: 16px; margin-right: 5px;"></i>
+            <input pInputText class="flex form-control" name="search" id="search" placeholder="Search" type="text" style="height: 34px" [(ngModel)]="searchValue">
+        </span>
     </div>
-    <table class="table table-hover table-condensed" aria-describedby="Apps management table" style="margin-top: 20px;">
-        <thead>
-        <tr>
-            <th scope="col"></th>
-            <th scope="col">{{'APPS_MANAGEMENT.NAME' | translate}}</th>
-            <th scope="col">{{'DOMAINS.CODE_NAME' | translate}}</th>
-            <th scope="col">{{'DOMAINS.LIST.DOMAIN_NAME' | translate}}</th>
-            <th scope="col">{{'DOMAINS.LIST.DOMAIN_CODE_NAME' | translate}}</th>
-        </tr>
-        </thead>
-
-        <tbody>
-        <ng-template ngFor let-domainGroup [ngForOf]="groups | searchDomainGroup: searchValue" let-i="index">
-            <tr class="table-row" >
-                <td style="width: 5%" (click)="clickTableRow(i)" *ngIf="!domainsRowVisible[i]"><span class="glyphicon glyphicon-chevron-right"></span></td>
-                <td style="width: 5%" (click)="clickTableRow(i)" *ngIf="domainsRowVisible[i]"><span class="glyphicon glyphicon-chevron-down"></span></td>
+    <div class="flex" style="margin-right:20px">
+        <button *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']" [routerLink]="['/admin/domains/groups/add']" class="btn btn-primary"
+       role="button">{{'DOMAINS.ADD_BUTTON' | translate}}</button>
+    </div>
+</div>
+<h4 class="header">{{'DOMAINS.LIST.GROUPS' | translate}}</h4>
+
+<div class="background-section">
+
+    <p-table [value]="groups | searchDomainGroup: searchValue" [rowHover]="true">
+        <ng-template pTemplate="header">
+            <tr>
+                <th></th>
+                <th>{{'APPS_MANAGEMENT.NAME' | translate}}</th>
+                <th>{{'DOMAINS.CODE_NAME' | translate}}</th>
+                <th>{{'DOMAINS.LIST.DOMAIN_NAME' | translate}}</th>
+                <th>{{'DOMAINS.LIST.DOMAIN_CODE_NAME' | translate}}</th>
+                <th></th>
+            </tr>
+        </ng-template>
+
+        <ng-template pTemplate="body" let-domainGroup let-i="rowIndex">
+            <tr class="table-row">
+                <td style="width: 5%" (click)="clickTableRow(i)" *ngIf="!domainsRowVisible[i]">
+                    <span class="pi pi-chevron-right"></span>
+                </td>
+                <td style="width: 5%" (click)="clickTableRow(i)" *ngIf="domainsRowVisible[i]">
+                    <span class="pi pi-chevron-down"></span>
+                </td>
                 <td style="width: 25%" (click)="clickTableRow(i)">{{domainGroup?.name}}</td>
                 <td style="width: 20%" (click)="clickTableRow(i)">{{domainGroup?.codename}}</td>
                 <td style="width: 15%" (click)="clickTableRow(i)"></td>
                 <td style="width: 15%" (click)="clickTableRow(i)"></td>
                 <td style="width: 20%" class="text-right">
                     <span class="dropdown">
-            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
-              <em class="fas fa-cog icon-black icon-bigger"></em>
-            </a>
-            <ul class="dropdown-menu pull-right-drop">
-              <li>
-                <a [routerLink]="['/admin/domains/groups/', domainGroup?.id]">{{ 'APPS_MANAGEMENT.EDIT_BUTTON' | translate }}</a>
-              </li>
-                  <li>
-                <a (click)="deleteDomainGroup(domainGroup?.id)">{{ 'APP_INSTANCE.REMOVE_BUTTON' | translate }}</a>
-              </li>
-            </ul>
-          </span>
+                        <a style="display: inline-block" class="dropdown-toggle" aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                            <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
+                        </a>
+                        <ul class="dropdown-menu pull-right-drop">
+                            <li>
+                                <a [routerLink]="['/admin/domains/groups/', domainGroup?.id]">{{ 'APPS_MANAGEMENT.EDIT_BUTTON' | translate }}</a>
+                            </li>
+                            <li>
+                                <a (click)="deleteDomainGroup(domainGroup?.id)">{{ 'APP_INSTANCE.REMOVE_BUTTON' | translate }}</a>
+                            </li>
+                        </ul>
+                    </span>
                 </td>
             </tr>
+
             <ng-template ngFor let-domain [ngForOf]="domainGroup.domains">
                 <tr *ngIf="domainsRowVisible[i]" class="table-row pointer" [routerLink]="['/admin/domains/view/', domain.id]">
                     <td></td>
@@ -52,12 +62,62 @@
                     <td></td>
                     <td>{{domain.name}}</td>
                     <td>{{domain.codename}}</td>
-                    <td class="text-right">
-                    </td>
+                    <td class="text-right"></td>
                 </tr>
             </ng-template>
         </ng-template>
-        </tbody>
-    </table>
+    </p-table>
 </div>
 
+
+<!--    <table class="table table-hover table-condensed" aria-describedby="Apps management table" style="margin-top: 20px;">-->
+<!--        <thead>-->
+<!--        <tr>-->
+<!--            <th scope="col"></th>-->
+<!--            <th scope="col">{{'APPS_MANAGEMENT.NAME' | translate}}</th>-->
+<!--            <th scope="col">{{'DOMAINS.CODE_NAME' | translate}}</th>-->
+<!--            <th scope="col">{{'DOMAINS.LIST.DOMAIN_NAME' | translate}}</th>-->
+<!--            <th scope="col">{{'DOMAINS.LIST.DOMAIN_CODE_NAME' | translate}}</th>-->
+<!--        </tr>-->
+<!--        </thead>-->
+
+<!--        <tbody>-->
+<!--        <ng-template ngFor let-domainGroup [ngForOf]="groups | searchDomainGroup: searchValue" let-i="index">-->
+<!--            <tr class="table-row" >-->
+<!--                <td style="width: 5%" (click)="clickTableRow(i)" *ngIf="!domainsRowVisible[i]"><span class="glyphicon glyphicon-chevron-right"></span></td>-->
+<!--                <td style="width: 5%" (click)="clickTableRow(i)" *ngIf="domainsRowVisible[i]"><span class="glyphicon glyphicon-chevron-down"></span></td>-->
+<!--                <td style="width: 25%" (click)="clickTableRow(i)">{{domainGroup?.name}}</td>-->
+<!--                <td style="width: 20%" (click)="clickTableRow(i)">{{domainGroup?.codename}}</td>-->
+<!--                <td style="width: 15%" (click)="clickTableRow(i)"></td>-->
+<!--                <td style="width: 15%" (click)="clickTableRow(i)"></td>-->
+<!--                <td style="width: 20%" class="text-right">-->
+<!--                    <span class="dropdown">-->
+<!--            <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">-->
+<!--              <em class="fas fa-cog icon-black icon-bigger"></em>-->
+<!--            </a>-->
+<!--            <ul class="dropdown-menu pull-right-drop">-->
+<!--              <li>-->
+<!--                <a [routerLink]="['/admin/domains/groups/', domainGroup?.id]">{{ 'APPS_MANAGEMENT.EDIT_BUTTON' | translate }}</a>-->
+<!--              </li>-->
+<!--                  <li>-->
+<!--                <a (click)="deleteDomainGroup(domainGroup?.id)">{{ 'APP_INSTANCE.REMOVE_BUTTON' | translate }}</a>-->
+<!--              </li>-->
+<!--            </ul>-->
+<!--          </span>-->
+<!--                </td>-->
+<!--            </tr>-->
+<!--            <ng-template ngFor let-domain [ngForOf]="domainGroup.domains">-->
+<!--                <tr *ngIf="domainsRowVisible[i]" class="table-row pointer" [routerLink]="['/admin/domains/view/', domain.id]">-->
+<!--                    <td></td>-->
+<!--                    <td></td>-->
+<!--                    <td></td>-->
+<!--                    <td>{{domain.name}}</td>-->
+<!--                    <td>{{domain.codename}}</td>-->
+<!--                    <td class="text-right">-->
+<!--                    </td>-->
+<!--                </tr>-->
+<!--            </ng-template>-->
+<!--        </ng-template>-->
+<!--        </tbody>-->
+<!--    </table>-->
+
diff --git a/src/app/appmarket/domains/domain/domain.component.css b/src/app/appmarket/domains/domain/domain.component.css
index 2c587d11ef0fc19812ddea12ab21bb9029db6350..5bcb6ebc246def5aa232ad2b49d95b88155ff827 100644
--- a/src/app/appmarket/domains/domain/domain.component.css
+++ b/src/app/appmarket/domains/domain/domain.component.css
@@ -55,3 +55,8 @@ input.ng-dirty.ng-invalid {
 .no-padding-top {
     padding-top: 0!important;
 }
+.form-control[disabled], fieldset[disabled] .form-control{
+    background: transparent;
+    border:none;
+    box-shadow: none;
+}
diff --git a/src/app/appmarket/domains/domain/domain.component.html b/src/app/appmarket/domains/domain/domain.component.html
index 00208f2f896690b530f2229310fa7dd3b6c375dc..0963f7ae40c3656822bfd6c2d4fb6734d09292e3 100644
--- a/src/app/appmarket/domains/domain/domain.component.html
+++ b/src/app/appmarket/domains/domain/domain.component.html
@@ -1,108 +1,111 @@
-<div class="col-sm-12 col-sm-offset-1 col-sm-10 col-md-offset-1 col-md-10">
+<div class="">
 	<h3>{{ 'DOMAIN_DETAILS.TITLE' | translate }}</h3>
+
 	<form *ngIf="domain" (submit)="submit()" class="form-horizontal" #domainForm="ngForm">
-		<div class="form-group">
-			<label for="name" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.NAME' | translate }}</label>
-			<div class="col-sm-10">
-				<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW) || authService.hasRole('ROLE_OPERATOR')" id="name" name="name"
-					[(ngModel)]="domain.name" #name="ngModel" required>
-				<div *ngIf="name.invalid && (name.dirty || name.touched)"
-					class="alert alert-danger">
-					<div *ngIf="name.errors.required">{{ 'DOMAIN_DETAILS.NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
+		<div class="background-section">
+			<div class="form-group">
+				<label for="name" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.NAME' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW) || authService.hasRole('ROLE_OPERATOR')" id="name" name="name"
+						   [(ngModel)]="domain.name" #name="ngModel" required>
+					<div *ngIf="name.invalid && (name.dirty || name.touched)"
+						 class="alert alert-danger">
+						<div *ngIf="name.errors.required">{{ 'DOMAIN_DETAILS.NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
+					</div>
 				</div>
 			</div>
-		</div>
 
 
-		<div class="form-group" *ngIf="!isInMode(ComponentMode.EDIT)">
-			<label for="codename" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.CODE_NAME' | translate }}</label>
-			<div class="col-sm-10">
-				<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="codename"
-					name="codename" pattern="[a-z0-9-]*"
-					[(ngModel)]="domain.codename" #codename="ngModel" minlength="2" maxlength="12" required>
-				<div *ngIf="codename.invalid && (codename.dirty || codename.touched)"
-					class="alert alert-danger">
+			<div class="form-group" *ngIf="!isInMode(ComponentMode.EDIT)">
+				<label for="codename" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.CODE_NAME' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="codename"
+						   name="codename" pattern="[a-z0-9-]*"
+						   [(ngModel)]="domain.codename" #codename="ngModel" minlength="2" maxlength="12" required>
+					<div *ngIf="codename.invalid && (codename.dirty || codename.touched)"
+						 class="alert alert-danger">
 
-					<div *ngIf="codename.errors.required">{{ 'DOMAIN_DETAILS.CODE_NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
-					<div *ngIf="codename.errors.pattern">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_1' | translate }}</div>
-					<div *ngIf="codename.errors.minlength || codename.errors.maxlength">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_2' | translate }}</div>
+						<div *ngIf="codename.errors.required">{{ 'DOMAIN_DETAILS.CODE_NAME_IS_REQUIRED_MESSAGE' | translate }}</div>
+						<div *ngIf="codename.errors.pattern">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_1' | translate }}</div>
+						<div *ngIf="codename.errors.minlength || codename.errors.maxlength">{{ 'DOMAIN_DETAILS.CODE_NAME_PATTERN_MESSAGE_2' | translate }}</div>
 
+					</div>
 				</div>
 			</div>
-		</div>
 
-		<div class="form-group" *ngIf="!isInMode(ComponentMode.CREATE) && (authService.hasRole('ROLE_SYSTEM_ADMIN') || authService.hasRole('ROLE_OPERATOR'))">
-			<label class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.ID_IN_DB' | translate }}</label>
-			<div class="col-sm-10">
-				<p class="form-control-static">{{domain.id}}</p>
+			<div class="form-group" *ngIf="!isInMode(ComponentMode.CREATE) && (authService.hasRole('ROLE_SYSTEM_ADMIN') || authService.hasRole('ROLE_OPERATOR'))">
+				<label class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.ID_IN_DB' | translate }}</label>
+				<div class="col-sm-10">
+					<p class="form-control-static">{{domain.id}}</p>
+				</div>
+			</div>
+			<hr/>
+
+			<div class="form-group">
+				<label for="kubernetesNamespace" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.KUBERNETES_NAMESPACE' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="kubernetesNamespace" pattern="[a-z0-9-]*" maxlength="64" #namespace="ngModel"
+						   name="kubernetesNamespace" [(ngModel)]="domain.domainTechDetails.kubernetesNamespace" placeholder="{{'DOMAIN_DETAILS.KUBERNETES_NAMESPACE_PLACEHOLDER' | translate}}">
+					<div *ngIf="namespace.invalid && (namespace.dirty || namespace.touched)" class="alert alert-danger">
+						<div *ngIf="namespace.errors.pattern">{{ 'DOMAIN_DETAILS.NAMESPACE_PATTERN_VALIDATION_MESSAGE' | translate }}</div>
+						<div *ngIf="namespace.errors.maxlength">{{ 'DOMAIN_DETAILS.NAMESPACE_MAX_LENGTH_VALIDATION_MESSAGE' | translate }}</div>
+					</div>
+				</div>
 			</div>
-		</div>
-
-		<hr/>
 
-		<div class="form-group">
-			<label for="kubernetesNamespace" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.KUBERNETES_NAMESPACE' | translate }}</label>
-			<div class="col-sm-10">
-				<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="kubernetesNamespace" pattern="[a-z0-9-]*" maxlength="64" #namespace="ngModel"
-				name="kubernetesNamespace" [(ngModel)]="domain.domainTechDetails.kubernetesNamespace" placeholder="{{'DOMAIN_DETAILS.KUBERNETES_NAMESPACE_PLACEHOLDER' | translate}}">
-				<div *ngIf="namespace.invalid && (namespace.dirty || namespace.touched)" class="alert alert-danger">
-					<div *ngIf="namespace.errors.pattern">{{ 'DOMAIN_DETAILS.NAMESPACE_PATTERN_VALIDATION_MESSAGE' | translate }}</div>
-					<div *ngIf="namespace.errors.maxlength">{{ 'DOMAIN_DETAILS.NAMESPACE_MAX_LENGTH_VALIDATION_MESSAGE' | translate }}</div>
+			<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId()">
+				<label for="kubernetesStorageClass" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.KUBERNETES_STORAGE_CLASS' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="kubernetesStorageClass"
+						   name="kubernetesStorageClass" [(ngModel)]="domain.domainTechDetails.kubernetesStorageClass">
 				</div>
 			</div>
-		</div>
 
-        <div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId()">
-            <label for="kubernetesStorageClass" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.KUBERNETES_STORAGE_CLASS' | translate }}</label>
-            <div class="col-sm-10">
-                <input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="kubernetesStorageClass"
-                       name="kubernetesStorageClass" [(ngModel)]="domain.domainTechDetails.kubernetesStorageClass">
-            </div>
-        </div>
-
-		<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId()">
-			<label for="kubernetesIngressClass" class="col-sm-2 control-label">{{'DOMAIN_DETAILS.KUBERNETES_INGRESS_CLASS' | translate }}</label>
-			<div class="col-sm-10">
-				<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="kubernetesIngressClass"
-					   name="kubernetesIngressClass" [(ngModel)]="domain.domainTechDetails.kubernetesIngressClass">
+			<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId()">
+				<label for="kubernetesIngressClass" class="col-sm-2 control-label">{{'DOMAIN_DETAILS.KUBERNETES_INGRESS_CLASS' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="kubernetesIngressClass"
+						   name="kubernetesIngressClass" [(ngModel)]="domain.domainTechDetails.kubernetesIngressClass">
+				</div>
 			</div>
-		</div>
 
-		<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId()">
-			<label for="externalServiceDomain " class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.EXTERNAL_SERVICE_DOMAIN' | translate }}</label>
-			<div class="col-sm-10">
-				<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="externalServiceDomain "
-					   name="externalServiceDomain " [(ngModel)]="domain.domainTechDetails.externalServiceDomain">
+			<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId()">
+				<label for="externalServiceDomain " class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.EXTERNAL_SERVICE_DOMAIN' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="isInMode(ComponentMode.VIEW)" id="externalServiceDomain "
+						   name="externalServiceDomain " [(ngModel)]="domain.domainTechDetails.externalServiceDomain">
+				</div>
 			</div>
-		</div>
 
-		<div class="form-group" *ngIf="domain?.id !== domainService.getGlobalDomainId()">
-			<label class="col-sm-2 control-label text-right" for="dcnDeploymentType">{{'DOMAIN_DETAILS.DCN_DEPLOYMENT_TYPE' | translate }}</label>
-			<div class="col-sm-10">
-				<select class="form-control" id="dcnDeploymentType" name="dcnDeploymentType" [(ngModel)]="domain.domainDcnDetails.dcnDeploymentType" [disabled]="isInMode(ComponentMode.VIEW)" required>
-					<option *ngFor="let type of keys" [value]="type">{{type | titlecase}}</option>
-				</select>
+			<div class="form-group" *ngIf="domain?.id !== domainService.getGlobalDomainId()">
+				<label class="col-sm-2 control-label text-right" for="dcnDeploymentType">{{'DOMAIN_DETAILS.DCN_DEPLOYMENT_TYPE' | translate }}</label>
+				<div class="col-sm-10">
+					<select class="form-control" id="dcnDeploymentType" name="dcnDeploymentType" [(ngModel)]="domain.domainDcnDetails.dcnDeploymentType" [disabled]="isInMode(ComponentMode.VIEW)" required>
+						<option *ngFor="let type of keys" [value]="type">{{type | titlecase}}</option>
+					</select>
+				</div>
 			</div>
-		</div>
 
-		<div class="form-group" *ngIf="domain?.id !== domainService.getGlobalDomainId() && isInMode(ComponentMode.VIEW) && isManual()">
-			<label class="col-sm-2 control-label text-right" for="configured-status">{{ 'DOMAIN_DETAILS.DCN_STATUS' | translate }}</label>
-			<div class="col-sm-10" id="configured-status" style="padding-top: 6px;">
-				<p *ngIf="domain?.domainDcnDetails?.dcnConfigured">{{ 'DOMAIN_DETAILS.CONFIGURED_VIEW' | translate }}</p>
-				<p *ngIf="!domain?.domainDcnDetails?.dcnConfigured">{{ 'DOMAIN_DETAILS.NOT_CONFIGURED_VIEW' | translate }}</p>
+			<div class="form-group" *ngIf="domain?.id !== domainService.getGlobalDomainId() && isInMode(ComponentMode.VIEW) && isManual()">
+				<label class="col-sm-2 control-label text-right" for="configured-status">{{ 'DOMAIN_DETAILS.DCN_STATUS' | translate }}</label>
+				<div class="col-sm-10" id="configured-status" style="padding-top: 6px;">
+					<p *ngIf="domain?.domainDcnDetails?.dcnConfigured">{{ 'DOMAIN_DETAILS.CONFIGURED_VIEW' | translate }}</p>
+					<p *ngIf="!domain?.domainDcnDetails?.dcnConfigured">{{ 'DOMAIN_DETAILS.NOT_CONFIGURED_VIEW' | translate }}</p>
+				</div>
 			</div>
-		</div>
 
-		<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId() && !isInMode(ComponentMode.VIEW) && isManual()">
-			<label for="dcnConfigured" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.DCN_CONFIGURED' | translate }}</label>
-			<div class="col-sm-10">
-				<input type="checkbox" class="btn btn-default" [disabled]="isInMode(ComponentMode.VIEW)" id="dcnConfigured"
-				name="dcnConfigured" [(ngModel)]="domain.domainDcnDetails.dcnConfigured" (change)="changeDcnFieldUpdatedFlag()">
+			<div class="form-group" *ngIf="domain.id !== domainService.getGlobalDomainId() && !isInMode(ComponentMode.VIEW) && isManual()">
+				<label for="dcnConfigured" class="col-sm-2 control-label">{{ 'DOMAIN_DETAILS.DCN_CONFIGURED' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="checkbox" class="btn btn-default" [disabled]="isInMode(ComponentMode.VIEW)" id="dcnConfigured"
+						   name="dcnConfigured" [(ngModel)]="domain.domainDcnDetails.dcnConfigured" (change)="changeDcnFieldUpdatedFlag()">
+				</div>
 			</div>
 		</div>
 
-		<div class="panel panel-default" *ngIf="isInMode(ComponentMode.VIEW) && !authService.hasRole('ROLE_OPERATOR')">
-			<div class="panel-heading">{{ 'DOMAIN_DETAILS.DOMAIN_USERS' | translate }}</div>
+
+		<div class="background-section" *ngIf="isInMode(ComponentMode.VIEW) && !authService.hasRole('ROLE_OPERATOR')">
+			<h4 style="font-size:15px; font-weight: bold">{{ 'DOMAIN_DETAILS.DOMAIN_USERS' | translate }}</h4>
 			<div class="panel-body">
 				<table class="table table-hover table-condensed" aria-describedby="Domains details table">
 					<thead>
@@ -147,8 +150,8 @@
 		<app-domain-namespace-annotations [annotationRead]="annotations" (annotations)="handleAnnotationsChange($event)" (trigerDelete)="handleAnnotationDelete($event)"></app-domain-namespace-annotations>
 		</div>
 
-		<div *ngIf="isInMode(ComponentMode.VIEW)" class="panel panel-default">
-			<div class="panel-heading">{{ 'DOMAIN_DETAILS.APP_STATUS' | translate }}</div>
+		<div *ngIf="isInMode(ComponentMode.VIEW)" class="background-section">
+			<h4 style="font-size:15px; font-weight: bold">{{ 'DOMAIN_DETAILS.APP_STATUS' | translate }}</h4>
 			<div class="panel-body">
 				<table class="table table-hover table-condensed" aria-describedby="Domain details table">
 					<thead>
@@ -207,8 +210,8 @@
 			</div>
 		</div>
 
-		<div class="panel panel-default" *ngIf="displayCustomerNetworksSection && domain.id !== domainService.getGlobalDomainId()">
-			<div class="panel-heading">{{'DOMAIN_DETAILS.CUSTOMER_NETWORKS' | translate}}</div>
+		<div class="background-section" *ngIf="displayCustomerNetworksSection && domain.id !== domainService.getGlobalDomainId()">
+			<h4 style="font-size:15px; font-weight: bold">{{'DOMAIN_DETAILS.CUSTOMER_NETWORKS' | translate}}</h4>
 			<div class="panel-body">
 				<div class="text-center" *ngIf="isInMode(ComponentMode.VIEW) && domain.domainDcnDetails.customerNetworks.length == 0">
 					<h5>{{'DOMAIN_DETAILS.CUSTOMER_NETWORKS_EMPTY_LIST_MESSAGE' | translate}}</h5>
@@ -233,8 +236,8 @@
 
 
 
-		<div class="panel panel-default" *ngIf="isInMode(ComponentMode.VIEW) && !authService.hasRole('ROLE_OPERATOR')">
-			<div class="panel-heading">{{ 'DOMAINS.LIST.GROUP' | translate }}</div>
+		<div class="background-section" *ngIf="isInMode(ComponentMode.VIEW) && !authService.hasRole('ROLE_OPERATOR')">
+			<h4 style="font-size:15px; font-weight: bold">{{ 'DOMAINS.LIST.GROUP' | translate }}</h4>
 			<div class="panel-body">
 				<table class="table table-hover table-condensed" aria-describedby="Domain group list">
 					<thead>
@@ -255,11 +258,59 @@
 					</tbody>
 				</table>
 			</div>
+		</div>
+
+
+			<!-- CLUSTER CONFIGURATION READ ONLY PRESENTATION  -->
+		<div class="background-section" *ngIf="isInMode(ComponentMode.VIEW) && !authService.hasRole('ROLE_OPERATOR')">
+			<h4 style="font-size:15px; font-weight: bold">{{ 'CLUSTERS.CONFIGURATION' | translate  }}</h4>
+
+			<div class="form-group" *ngIf="domain.clusters.length >0">
+				<label for="clusterId" class="col-sm-2 control-label">{{ 'CLUSTERS.ID' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="true" id="clusterId "
+						   name="clusterId " [(ngModel)]="cluster.id">
+				</div>
+			</div>
+
+			<div class="form-group" *ngIf="domain.clusters.length >0">
+				<label for="clusterName" class="col-sm-2 control-label">{{ 'CLUSTERS.NAME' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="true" id="clusterName "
+						   name="clusterName " [(ngModel)]="cluster.name">
+				</div>
+			</div>
+
+			<div class="form-group" *ngIf="domain.clusters.length >0">
+				<label for="clusterCodeName" class="col-sm-2 control-label">{{ 'CLUSTERS.CODENAME' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="true" id="clusterCodeName "
+						   name="clusterCodeName " [(ngModel)]="cluster.codename">
+				</div>
+			</div>
+
+			<div class="form-group" *ngIf="domain.clusters.length >0">
+				<label for="clusterDescription" class="col-sm-2 control-label">{{ 'CLUSTERS.DESCRIPTION' | translate }}</label>
+				<div class="col-sm-10">
+					<input type="text" class="form-control" [disabled]="true" id="clusterDescription "
+						   name="clusterDescription " [(ngModel)]="cluster.description">
+				</div>
+			</div>
+
+
+
+
+
 		</div>
 
 		<div class="flex justify-content-end">
 			<button *ngIf="!isInMode(ComponentMode.VIEW)" type="submit" class="btn btn-primary" [disabled]="!domainForm.form.valid">{{ 'DOMAIN_DETAILS.SUBMIT_BUTTON' | translate }}</button>
 		</div>
+
+		<br *ngIf="errorMessage">
+      <div class="alert alert-danger text-left" *ngIf="errorMessage">
+        {{errorMessage}}
+      </div>
 	</form>
 </div>
 
diff --git a/src/app/appmarket/domains/domain/domain.component.ts b/src/app/appmarket/domains/domain/domain.component.ts
index eecd96f7840b8cacb482cbfaa219fc6cab1cdf15..b31df76200441f3eaaeb2f9a9dc7294991749ac7 100644
--- a/src/app/appmarket/domains/domain/domain.component.ts
+++ b/src/app/appmarket/domains/domain/domain.component.ts
@@ -9,13 +9,14 @@ import {User} from '../../../model';
 import {Observable, of} from 'rxjs';
 import {UserRole} from '../../../model/userrole';
 import {AuthService} from '../../../auth/auth.service';
-import {ModalComponent} from '../../../shared';
+import {ModalComponent} from '../../../shared'; 
 import {map, shareReplay, take} from 'rxjs/operators';
 import {DcnDeploymentType} from '../../../model/dcndeploymenttype';
 import {CustomerNetwork} from '../../../model/customernetwork';
 import {MinLengthDirective} from '../../../directive/min-length.directive';
 import {MaxLengthDirective} from '../../../directive/max-length.directive';
 import {DomainAnnotation} from '../../../model/domain-annotation';
+import { ClusterManager } from '../../../model/cluster-manager';
 
 
 @Component({
@@ -48,6 +49,10 @@ export class DomainComponent extends BaseComponent implements OnInit {
 
     public annotations : Observable<DomainAnnotation[]> = of([]);
 
+    public errorMessage = "";
+
+    public cluster: ClusterManager = new ClusterManager();
+
     constructor(public domainService: DomainService,
                 protected userService: UserService,
                 private router: Router,
@@ -70,6 +75,9 @@ export class DomainComponent extends BaseComponent implements OnInit {
                 this.domainService.getOne(this.domainId).subscribe(
                     (domain: Domain) => {
                         this.domain = domain;
+                        if(domain.clusters.length >0) {
+                            this.cluster = domain.clusters[0];
+                        }
                         this.domain.applicationStatePerDomain
                             .sort((a, b) => a.applicationBaseName.localeCompare(b.applicationBaseName))
                     },
@@ -103,7 +111,14 @@ export class DomainComponent extends BaseComponent implements OnInit {
         if (this.domainId !== undefined) {
             this.updateExistingDomain();
         } else {
-            this.domainService.add(this.domain).subscribe(() => this.router.navigate(['admin/domains/']));
+            this.domainService.add(this.domain).subscribe(() => {
+                this.router.navigate(['admin/domains/'])
+        }, err => {
+            console.error(err);
+            if(err.statusCode !== 409 && err?.message !== undefined) this.errorMessage = err.message;
+            else this.errorMessage = err;
+    
+        });
         }
         this.domainService.setUpdateRequiredFlag(true);
     }
diff --git a/src/app/appmarket/domains/domains.routes.ts b/src/app/appmarket/domains/domains.routes.ts
index 12fb5a90bfaa0a6e3363b6e89855cebc7bbc4f9f..65701e24f5b398eecaa6d87baf0bee021ffb024c 100644
--- a/src/app/appmarket/domains/domains.routes.ts
+++ b/src/app/appmarket/domains/domains.routes.ts
@@ -12,46 +12,46 @@ import { DomainAnnotationsComponent } from './domain-annotations/domain-annotati
 
 export const DomainsRoutes: Route[] = [
     {
-        path: 'admin/domains', component: DomainsListComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_DOMAIN_ADMIN', 'ROLE_OPERATOR', 'ROLE_VL_DOMAIN_ADMIN', 'ROLE_VL_MANAGER']}
+        path: 'domains', component: DomainsListComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_DOMAIN_ADMIN', 'ROLE_OPERATOR', 'ROLE_GROUP_DOMAIN_ADMIN', 'ROLE_GROUP_MANAGER']}
     },
     {
-        path: 'admin/domains/add', component: DomainComponent, canActivate: [AuthGuard, RoleGuard],
+        path: 'domains/add', component: DomainComponent, canActivate: [AuthGuard, RoleGuard],
         data: {mode: ComponentMode.CREATE, roles: ['ROLE_SYSTEM_ADMIN']}
     },
     {
-        path: 'admin/domains/annotations', component: DomainAnnotationsComponent, canActivate: [AuthGuard, RoleGuard],
+        path: 'domains/annotations', component: DomainAnnotationsComponent, canActivate: [AuthGuard, RoleGuard],
         data: {mode: ComponentMode.CREATE, roles: ['ROLE_SYSTEM_ADMIN']}
     },
     {
-        path: 'admin/domains/view/:id', component: DomainComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_DOMAIN_ADMIN', 'ROLE_OPERATOR', 'ROLE_VL_DOMAIN_ADMIN']}
+        path: 'domains/view/:id', component: DomainComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_DOMAIN_ADMIN', 'ROLE_OPERATOR', 'ROLE_GROUP_DOMAIN_ADMIN']}
     },
     {
-        path: 'admin/domains/edit/:id', component: DomainComponent, canActivate: [AuthGuard, RoleGuard],
+        path: 'domains/edit/:id', component: DomainComponent, canActivate: [AuthGuard, RoleGuard],
         data: {mode: ComponentMode.EDIT, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']}
     },
     {
-        path: 'admin/domains/groups', component: DomainGroupsComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}
+        path: 'domains/groups', component: DomainGroupsComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}
     },
     {
-        path: 'admin/domains/groups/add', component: DomainGroupViewComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {mode: ComponentMode.CREATE, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}
+        path: 'domains/groups/add', component: DomainGroupViewComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {mode: ComponentMode.CREATE, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}
     },
     {
-        path: 'admin/domains/groups/:id', component: DomainGroupViewComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}
+        path: 'domains/groups/:id', component: DomainGroupViewComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}
     },
     {
-        path: 'admin/domains/bulks/new', component: DomainuploadComponent,
-        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}},
+        path: 'domains/bulks/new', component: DomainuploadComponent,
+        data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}},
     {
-        path: 'admin/domains/bulks', component: BulkDomainListComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}
+        path: 'domains/bulks', component: BulkDomainListComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}
     },
     {
-        path: 'admin/domains/bulks/:id', component: BulkViewComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']}
+        path: 'domains/bulks/:id', component: BulkViewComponent, canActivate: [AuthGuard, RoleGuard],
+        data: {roles: ['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']}
     }
 ];
diff --git a/src/app/appmarket/domains/list/domainslist.component.css b/src/app/appmarket/domains/list/domainslist.component.css
index 4b35785d88db8ee0325b8ab438f15b17163535c1..f53cede1f87da0dc9913a49b194585761fc63a40 100644
--- a/src/app/appmarket/domains/list/domainslist.component.css
+++ b/src/app/appmarket/domains/list/domainslist.component.css
@@ -13,66 +13,18 @@ tr.clickable {
     cursor: pointer;
 }
 
-.dropdown:hover .dropdown-menu {
-    display: block;
-}
+/*.dropdown:hover .dropdown-menu {*/
+/*    display: block;*/
+/*}*/
 
 .space-between {
     display: flex;
     justify-content: space-between;
 }
-
-:host ::ng-deep .p-datatable .p-datatable-thead > tr > th{
-    border: 1px solid #E0E2E5;
-    background:transparent;
-    border-width: 0 0 1px 0;
-}
-:host ::ng-deep .p-datatable .p-datatable-tbody > tr > td {
-    text-align: left;
-    border: 1px solid #E0E2E5;
-    border-width: 0 0 1px 0;
-    padding: 1rem 1rem;
-}
-:host ::ng-deep .p-datatable .p-paginator-bottom{
-    height: 40px;
-    background: transparent;
-    border: none;
-    margin-top:10px;
-}
-:host ::ng-deep .p-datatable .p-datatable-tbody > tr{
-    background: transparent;
-}
-
-:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page{
-    transition: unset;
-    border-radius: 50%;
-    min-width:3.5rem;
-    height:3.5rem;
-    margin:0 5px;
-    font-size: 14px;
-}
-
-:host ::ng-deep .p-paginator-element{
-    border-radius:50%;
-    margin:0 5px;
-    min-width:3.5rem;
-    height:3.5rem;
-    font-size: 14px;
-}
-:host ::ng-deep .p-paginator .p-dropdown{
-    height:3rem;
-}
-:host ::ng-deep .p-paginator-icon{
-    height: 1.5rem;
-    width: 1.5rem;
-}
-:host ::ng-deep .p-paginator .p-dropdown .p-dropdown-label{
-    padding-right: 10px;
-}
-
 label{
     padding-left:5px;
     display: unset;
     margin-bottom: 0;
     font-weight: unset;
 }
+
diff --git a/src/app/appmarket/domains/list/domainslist.component.html b/src/app/appmarket/domains/list/domainslist.component.html
index 53b85f9f4ab3e1f11e921ba8274eddd9a5a249b1..5a279e5cd877cd3b2c0ba1978ecc8549aa6e3dd8 100644
--- a/src/app/appmarket/domains/list/domainslist.component.html
+++ b/src/app/appmarket/domains/list/domainslist.component.html
@@ -18,7 +18,7 @@
         <label for="showNotActive"> {{'DOMAINS.NOTACTIVE' | translate}}</label>
     </div>
 </div>
-    <h4 style="margin-top:40px; font-weight: bold">{{ 'DOMAINS.TITLE' | translate }}</h4>
+    <h4 class="header">{{ 'DOMAINS.TITLE' | translate }}</h4>
 
     <div class="background-section">
         <p-table [value]="domains | async | searchDomain: searchValue: showNotActive"
@@ -44,35 +44,33 @@
                 </tr>
             </ng-template>
             <ng-template pTemplate="body" let-domain>
-                <tr  [routerLink]="['view/', domain.id]" *ngIf="!domain.deleted">
-                    <td>{{domain?.codename}}</td>
+                <tr *ngIf="!domain.deleted">
+                    <td [routerLink]="['view/', domain.id]">{{domain?.codename}}</td>
                     <td>{{domain?.name}}</td>
                     <td>
                         <span class="glyphicon glyphicon-ok" *ngIf="domain?.active"></span>
                         <span class="glyphicon glyphicon-remove" *ngIf="!(domain?.active)"></span>
                     </td>
                     <td class="text-right">
-                <span class="dropdown">
-						<a style="display: inline-block; text-align:right" class="dropdown-toggle " aria-expanded="false"
-                           aria-haspopup="true"
-                           data-toggle="dropdown" href="#" role="button">
-							<em class="fas fa-cog icon-black icon-bigger"></em>
-						</a>
-						<ul class="dropdown-menu pull-right-drop" [appendTo]="'body'" >
-							<li><a [routerLink]="['view/', domain.id]" class="">
-								{{ 'DOMAINS.DETAILS_BUTTON' | translate }}</a>
-							</li>
-							<li><a *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']" [routerLink]="['edit/', domain.id]"
-                                   class="">{{ 'DOMAINS.EDIT_BUTTON' | translate }}</a>
-							</li>
-							<li><a *roles="['ROLE_SYSTEM_ADMIN']" (click)="$event.stopPropagation(); changeState(domain)"
-                                   class="">{{ getStateLabel(domain?.active) }}</a>
-							</li>
-							<li><a *roles="['ROLE_SYSTEM_ADMIN']" (click)="$event.stopPropagation(); openRemovalModal(domain)"
-                                   class="">{{ 'DOMAINS.DELETE_BUTTON' | translate }}</a>
-							</li>
-						</ul>
-					</span>
+                        <span class="dropdown">
+                                <a style="display: inline-block" class="dropdown-toggle" aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                                    <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
+                                </a>
+                                <ul class="dropdown-menu pull-right-drop" [appendTo]="'body'" >
+                                    <li><a [routerLink]="['view/', domain.id]" class="">
+                                        {{ 'DOMAINS.DETAILS_BUTTON' | translate }}</a>
+                                    </li>
+                                    <li><a *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']" [routerLink]="['edit/', domain.id]"
+                                           class="">{{ 'DOMAINS.EDIT_BUTTON' | translate }}</a>
+                                    </li>
+                                    <li><a *roles="['ROLE_SYSTEM_ADMIN']" (click)="$event.stopPropagation(); changeState(domain)"
+                                           class="">{{ getStateLabel(domain?.active) }}</a>
+                                    </li>
+                                    <li><a *roles="['ROLE_SYSTEM_ADMIN']" (click)="$event.stopPropagation(); openRemovalModal(domain)"
+                                           class="">{{ 'DOMAINS.DELETE_BUTTON' | translate }}</a>
+                                    </li>
+                                </ul>
+                        </span>
                     </td>
                 </tr>
             </ng-template>
diff --git a/src/app/appmarket/domains/list/domainslist.component.spec.ts b/src/app/appmarket/domains/list/domainslist.component.spec.ts
index d82cc80409c2a22df51857dfa53c48528ade455d..d4acc1fe17cb3df9bf196fae53136cff9b88de6d 100644
--- a/src/app/appmarket/domains/list/domainslist.component.spec.ts
+++ b/src/app/appmarket/domains/list/domainslist.component.spec.ts
@@ -19,7 +19,8 @@ describe('DomainslistComponent', () => {
         const authServiceSpy = createSpyObj('AuthService', ['hasRole']);
         authServiceSpy.hasRole.and.returnValue(true)
 
-        const domainServiceSpy = createSpyObj('DomainService', ['getGlobalDomainId', 'getAll'])
+        const domainServiceSpy = createSpyObj('DomainService', ['getGlobalDomainId', 'getAll', 'getAllBase']);
+        domainServiceSpy.getAllBase.and.returnValue(of([]))
         domainServiceSpy.getAll.and.returnValue(of([]))
         domainServiceSpy.getGlobalDomainId.and.returnValue(1)
 
diff --git a/src/app/appmarket/domains/list/domainslist.component.ts b/src/app/appmarket/domains/list/domainslist.component.ts
index 133d11d612c2f1f61336315499b654c48d2e0b5d..c86a3150db827baa4177c60f44e799babf1bee33 100644
--- a/src/app/appmarket/domains/list/domainslist.component.ts
+++ b/src/app/appmarket/domains/list/domainslist.component.ts
@@ -58,11 +58,11 @@ export class DomainsListComponent implements OnInit {
 
     protected getDomainsObservable(): Observable<Domain[]> {
         if (this.authService.hasRole(Role[Role.ROLE_SYSTEM_ADMIN]) || this.authService.hasRole(Role[Role.ROLE_OPERATOR])) {
-            return this.domainService.getAll().pipe(
+            return this.domainService.getAllBase().pipe(
                 map((domains) => domains.filter((domain) => domain.id !== this.domainService.getGlobalDomainId())));
         } else {
             return this.domainService.getMyDomains().pipe(
-                map((domains) => domains.filter((domain) => this.authService.hasDomainRole(domain.id, Role[Role.ROLE_DOMAIN_ADMIN]) || this.authService.hasDomainRole(domain.id, Role[Role.ROLE_VL_DOMAIN_ADMIN]))));
+                map((domains) => domains.filter((domain) => this.authService.hasDomainRole(domain.id, Role[Role.ROLE_DOMAIN_ADMIN]) || this.authService.hasDomainRole(domain.id, Role[Role.ROLE_GROUP_DOMAIN_ADMIN]))));
         }
     }
 
diff --git a/src/app/appmarket/users/list/userslist.component.html b/src/app/appmarket/users/list/userslist.component.html
index 6d9333ad9f77cb06d0cc389dc13401150af6c16e..b5540012889ac83ee00f113ef2a46c7e17626cf0 100644
--- a/src/app/appmarket/users/list/userslist.component.html
+++ b/src/app/appmarket/users/list/userslist.component.html
@@ -1,4 +1,4 @@
-<div class="col-sm-12" *ngIf="!domainMode" >
+<div class="" *ngIf="!domainMode" >
 	<div *roles="['ROLE_SYSTEM_ADMIN']" >
 		<nmaas-userslist *ngIf="!isInAddToDomainMode" [users]="allUsers" [allowedModes]="[ComponentMode.VIEW, ComponentMode.DELETE]"  (onUserRoleChange)="onUserRoleChange($event)"
 						 (onView)="onUserView($event)" (onModeChange)="onModeChange($event)" (onDelete)="onUserDelete($event)" (onRemoveFromDomain)="onRemoveRole($event)">
@@ -10,8 +10,8 @@
 
 </div>
 
-<div class="col-sm-12" *ngIf="domainMode">
-	<div *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_VL_MANAGER']">
+<div class="" *ngIf="domainMode">
+	<div *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_GROUP_MANAGER']">
 		<nmaas-userslist *ngIf="!isInAddToDomainMode" [users]="allUsers" [allowedModes]="[ComponentMode.VIEW, ComponentMode.DELETE]" [domainMode]="true" (onUserRoleChange)="onUserRoleChange($event)"
 						 (onView)="onUserView($event)" (onModeChange)="onModeChange($event)" (onDelete)="onUserDelete($event)" (onRemoveFromDomain)="onRemoveRole($event)">
 		</nmaas-userslist>
diff --git a/src/app/appmarket/users/list/userslist.component.ts b/src/app/appmarket/users/list/userslist.component.ts
index 3bb01ecd9dd280bf7bfc623d7a34e26f2d3e1727..dbcbc5545d6dd437cc30d86fa55c74823a1e8807 100644
--- a/src/app/appmarket/users/list/userslist.component.ts
+++ b/src/app/appmarket/users/list/userslist.component.ts
@@ -57,7 +57,7 @@ export class UsersListComponent implements OnInit {
             users = this.userService.getDomainUsersAsAdmin(this.domainId);
         } else if (this.authService.hasRole(Role[Role.ROLE_SYSTEM_ADMIN])) {
             users = this.userService.getAll(this.domainId);
-        } else if (this.domainId != null && (this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_DOMAIN_ADMIN]) || this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_VL_DOMAIN_ADMIN]))) {
+        } else if (this.domainId != null && (this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_DOMAIN_ADMIN]) || this.authService.hasDomainRole(this.domainId, Role[Role.ROLE_GROUP_DOMAIN_ADMIN]))) {
             this.domainMode = true;
             users = this.userService.getAll(this.domainId);
         } else {
diff --git a/src/app/appmarket/users/userdetails/userdetails.component.html b/src/app/appmarket/users/userdetails/userdetails.component.html
index f728a79ce158c48bcbe6db89c05d4452d03a47c3..64eeb8ac7800129a795c0e1648aded5819dadbc5 100644
--- a/src/app/appmarket/users/userdetails/userdetails.component.html
+++ b/src/app/appmarket/users/userdetails/userdetails.component.html
@@ -1,5 +1,5 @@
 <div class="col-sm-12 col-sm-12 col-md-12">
-	<div class="page-header">
+	<div class="">
 		<h3>
 			{{'USER_DETAILS.USER' | translate}} {{user?.username}}
 		</h3>
diff --git a/src/app/appmarket/users/users.routes.ts b/src/app/appmarket/users/users.routes.ts
index abe74e43673b587888d86cf984e1d54252e1e2fa..5c91077d5ce0107de3baff5206b3277b5f4401bd 100644
--- a/src/app/appmarket/users/users.routes.ts
+++ b/src/app/appmarket/users/users.routes.ts
@@ -5,10 +5,10 @@ import {RoleGuard} from '../../auth/role.guard';
 import {ComponentMode} from '../../shared/common/componentmode';
 
 export const UsersRoutes: Route[] = [
-    { path: 'admin/users', component: UsersListComponent, canActivate: [AuthGuard, RoleGuard],
+    { path: 'users', component: UsersListComponent, canActivate: [AuthGuard, RoleGuard],
                       data: {roles: ['ROLE_SYSTEM_ADMIN']}},
-    { path: 'admin/users/view/:id', component: UserDetailsComponent, canActivate: [AuthGuard, RoleGuard],
+    { path: 'users/view/:id', component: UserDetailsComponent, canActivate: [AuthGuard, RoleGuard],
                       data: {mode: ComponentMode.VIEW, roles: ['ROLE_SYSTEM_ADMIN']} },
     { path: 'domain/users', component: UsersListComponent, canActivate: [AuthGuard, RoleGuard],
-        data: {roles: ['ROLE_DOMAIN_ADMIN', 'ROLE_VL_MANAGER', 'ROLE_VL_MANAGER']}},
+        data: {roles: ['ROLE_DOMAIN_ADMIN', 'ROLE_GROUP_MANAGER']}},
 ];
diff --git a/src/app/auth/auth.guard.ts b/src/app/auth/auth.guard.ts
index 2fe88c217381e865b5ed27e7a814578d5c59aa32..f0c2074acada30084334a6ff28f2cd1b0686c995 100644
--- a/src/app/auth/auth.guard.ts
+++ b/src/app/auth/auth.guard.ts
@@ -4,7 +4,7 @@ import {AuthService} from './auth.service';
 import {ConfigurationService} from '../service';
 import { debounceTime } from 'rxjs';
 
-@Injectable()
+@Injectable()         
 export class AuthGuard  {
 
   constructor(private auth: AuthService, private router: Router, private maintenanceService: ConfigurationService) {}
@@ -12,13 +12,7 @@ export class AuthGuard  {
 
   public canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): boolean {
     if (this.auth.isLogged()) {
-      this.maintenanceService.getConfiguration().pipe(debounceTime(500)).subscribe(value => {
-         if (!this.auth.hasRole('ROLE_SYSTEM_ADMIN') && value.maintenance) {
-             this.auth.logout();
-             this.router.navigate(['/welcome/login']);
-             return false;
-         }
-      });
+    
       if(this.auth.hasRole('ROLE_INCOMPLETE') && route.url.toString() !== 'complete') {
           this.router.navigate(['/complete']);
           return false;
diff --git a/src/app/auth/auth.service.spec.ts b/src/app/auth/auth.service.spec.ts
index 6b0bb367feea3e0729c83c0209409e8d8d32dace..9e5569e278803124096a72dec6c7172feb75e927 100644
--- a/src/app/auth/auth.service.spec.ts
+++ b/src/app/auth/auth.service.spec.ts
@@ -1,16 +1,20 @@
 /* tslint:disable:no-unused-variable */
-import { TestBed, waitForAsync } from '@angular/core/testing';
+import {fakeAsync, TestBed, waitForAsync} from '@angular/core/testing';
 import {AuthService} from './auth.service';
-import {AppConfigService} from '../service';
+import {AppConfigService, ConfigurationService} from '../service';
 import {JwtHelperService} from '@auth0/angular-jwt';
-import {HttpClientTestingModule} from '@angular/common/http/testing';
-import {Role} from '../model/userrole';
+import {HttpClientTestingModule, HttpTestingController} from '@angular/common/http/testing';
+import {Role, UserRole} from '../model/userrole';
+import {ProfileService} from '../service/profile.service';
+import {Observable, of} from 'rxjs';
+import {Configuration} from '../model/configuration';
 
 describe('Service: Auth', () => {
     let authService: AuthService;
     let appConfigServiceSpy: jasmine.SpyObj<AppConfigService>;
     let jwtHelperServiceSpy: jasmine.SpyObj<JwtHelperService>;
-
+    let maintenanceServiceSpy: jasmine.SpyObj<ConfigurationService>;
+    let httpMock: HttpTestingController;
     let store: any = {};
 
     beforeEach(waitForAsync(() => {
@@ -18,34 +22,75 @@ describe('Service: Auth', () => {
             config: {
                 apiUrl: 'http://api.url',
                 tokenName: 'token',
-            }
+            },
+            getTestInstanceModalKey: () => 'testModalKey'
         };
-
         const jwtSpy = jasmine.createSpyObj('JwtHelperService', ['decodeToken', 'isTokenExpired']);
         jwtSpy.decodeToken.and.returnValue({
+            preferred_username: 'username',
             language: 'pl',
             sub: 'test-user',
-            scopes: [{authority: '1:' + Role[Role.ROLE_SYSTEM_ADMIN]}, {authority: '2:' + Role[Role.ROLE_USER]}]
+            global_role: ['ROLE_SYSTEM_ADMIN'],
+            roles: [`ROLE_USER`]
         });
         jwtSpy.isTokenExpired.and.callFake((arg: string): boolean => {
             return arg !== 'valid';
         });
 
+        maintenanceServiceSpy = jasmine.createSpyObj('maintenanceService', ['getConfiguration']);
+        maintenanceServiceSpy.getConfiguration.and.returnValue(of())
+
+        class MockConfigurationService {
+            protected uri: string;
+
+            constructor() {
+                this.uri = 'http://localhost/api';
+            }
+
+            public getApiUrl(): string {
+                return 'http://localhost/api';
+            }
+
+            public getConfiguration(): Observable<Configuration> {
+                return of<Configuration>();
+            }
+
+            public updateConfiguration(configuration: Configuration): Observable<any> {
+                return of<Configuration>();
+            }
+        }
+
+
+        const userRole = new UserRole();
+        userRole.role = Role.ROLE_SYSTEM_ADMIN;
+        userRole.domainName = 'test';
+        userRole.domainId = 1;
+        const userRole2 = new UserRole();
+        userRole2.role = Role.ROLE_USER;
+        userRole2.domainName = 'test2';
+        userRole2.domainId = 2;
+        const profileServiceStub = jasmine.createSpyObj('ProfileService', ['getRoles']);
+        profileServiceStub.getRoles.and.returnValue(of([userRole, userRole2]))
+
         TestBed.configureTestingModule({
             imports: [
-                HttpClientTestingModule
+                HttpClientTestingModule,
             ],
             providers: [
                 AuthService,
                 {provide: AppConfigService, useValue: appConfigServiceStub},
                 {provide: JwtHelperService, useValue: jwtSpy},
+                {provide: ProfileService, useValue: profileServiceStub},
+                {provide: ConfigurationService, useClass: MockConfigurationService}
             ],
         });
 
+        httpMock = TestBed.inject(HttpTestingController)
         authService = TestBed.get(AuthService);
+        authService.profile = [userRole, userRole2]
         appConfigServiceSpy = TestBed.get(AppConfigService);
         jwtHelperServiceSpy = TestBed.get(JwtHelperService);
-        // spyOn(appConfigServiceSpy, 'getTestInstanceModalKey').and.returnValue("test-instance-modal-key");
+        // maintenanceServiceSpy = TestBed.get(ConfigurationService);
 
         // local store mock
         store = {token: 'valid'};
@@ -61,6 +106,10 @@ describe('Service: Auth', () => {
         });
 
     }));
+    afterEach(() => {
+        httpMock.verify();
+        store = {};
+    });
 
     it('should create service', () => {
         expect(authService).toBeTruthy();
@@ -99,7 +148,7 @@ describe('Service: Auth', () => {
     });
 
     it('should return domains from roles', () => {
-        const result  = authService.getDomains();
+        const result = authService.getDomains();
         expect(result).toContain(1);
         expect(result).toContain(2);
         store = {token: null};
@@ -137,8 +186,11 @@ describe('Service: Auth', () => {
     });
 
     it('should remove token on logout', () => {
+        store['oidc-token'] = 'some-oidc-token';
         authService.logout();
         expect(store['token']).not.toBeDefined();
+        const req = httpMock.expectOne('http://api.url/oidc/logout/some-oidc-token');
+        req.flush({});
     });
 
     it('should be logged in when token is present and valid', () => {
@@ -154,4 +206,79 @@ describe('Service: Auth', () => {
         expect(r).toEqual(false);
     });
 
+    it('should store token and oidc token in localStorage', () => {
+        authService.storeToken('abc123');
+        expect(store['token']).toEqual('abc123');
+
+        authService.storeOidcToken('oidc456');
+        expect(store['oidc-token']).toEqual('oidc456');
+    });
+
+    it('should remove roles from localStorage', () => {
+        store['rolesToken'] = 'some_roles';
+        authService.removeRoles();
+        expect(store['rolesToken']).toBeUndefined();
+    });
+
+    it('should load and parse roles from localStorage', () => {
+        const roles = [{domainId: 1, role: Role.ROLE_USER, domainName: 'x'}];
+        store['rolesToken'] = JSON.stringify(roles);
+
+        const result = authService.loadRoles();
+        expect(result.length).toEqual(1);
+        expect(result[0].role).toEqual(Role.ROLE_USER);
+    });
+
+    it('should assign loaded roles to profile', () => {
+        const roles = [{domainId: 2, role: Role.ROLE_DOMAIN_ADMIN, domainName: 'x'}];
+        store['rolesToken'] = JSON.stringify(roles);
+        authService.loadAndSaveRoles();
+        expect(authService.profile[0].role).toEqual(Role.ROLE_DOMAIN_ADMIN);
+    });
+    it('should stringify and store roles', () => {
+        const roles = [new UserRole()];
+        roles[0].domainId = 1;
+        roles[0].role = Role.ROLE_USER;
+        roles[0].domainName = 'dom1';
+
+        authService.storeRoles(roles);
+        expect(store['rolesToken']).toContain('ROLE_USER');
+    });
+    it('should get global role from token', () => {
+        const result = authService.getGlobalRole();
+        expect(result).toContain('ROLE_SYSTEM_ADMIN');
+    });
+
+    it('should handle login error with catchError', waitForAsync(() => {
+        authService.login('user', 'pass').subscribe({
+            next: () => fail('Expected error'),
+            error: (err) => {
+                expect(err.status).toEqual(401);
+            }
+        });
+
+        const req = httpMock.expectOne('http://api.url/auth/basic/login');
+        req.flush({message: 'Invalid credentials'}, {status: 401, statusText: 'Unauthorized'});
+    }));
+
+    it('should return only uniqe domainids', () => {
+        (authService as any).profile = [
+            {domainId: 1}, {domainId: 2}, {domainId: 1}
+        ];
+        const ids = authService.getDomainIds();
+        expect(ids).toEqual([1, 2]);
+    });
+
+    it('getGlobalRole should return null when token is missing', () => {
+        delete store['token'];
+        expect(authService.getGlobalRole()).toBeNull();
+    });
+
+    it('getPreferredUsername should return preferred_username or null', () => {
+        const name = authService.getPreferredUsername();
+        expect(name).toBe('username');
+        delete store['token'];
+        expect(authService.getPreferredUsername()).toBeNull();
+    });
+
 });
diff --git a/src/app/auth/auth.service.ts b/src/app/auth/auth.service.ts
index ad7c6b8fcfa0166568751f3f9e1e3b4aa1a11938..2734f0b6b2f63738ed46639c80fbcfb10ff04aeb 100644
--- a/src/app/auth/auth.service.ts
+++ b/src/app/auth/auth.service.ts
@@ -1,17 +1,18 @@
-import {BehaviorSubject, Observable, Subject, throwError as observableThrowError} from 'rxjs';
+import {BehaviorSubject, Observable, of, Subject, throwError as observableThrowError} from 'rxjs';
 import {catchError, debounceTime, map} from 'rxjs/operators';
 import {Injectable} from '@angular/core';
-import {AppConfigService} from '../service';
+import {AppConfigService, ConfigurationService} from '../service';
 import {JwtHelperService} from '@auth0/angular-jwt';
 import {HttpClient, HttpHeaders} from '@angular/common/http';
-import {Authority} from '../model';
+import {ProfileService} from '../service/profile.service';
+import {Role, UserRole} from '../model/userrole';
 
-export class DomainRoles {
-    constructor(private domainId: number, private roles: string[] = []) {
-    }
 
-    public getDomainId(): number {
-        return this.domainId;
+export class DomainRoles {
+    constructor(
+        private domainId: number,
+        private roles: string[] = []
+    ) {
     }
 
     public getRoles(): string[] {
@@ -25,28 +26,132 @@ export class DomainRoles {
 
 @Injectable()
 export class AuthService {
+
+    private static REFRESH_TOKEN: string = 'refresh-token';
+    private static OIDC_TOKEN: string = 'oidc-token';
+
     public loginUsingSsoService: boolean;
 
     private readonly isLoggedInSubject: Subject<boolean> = new BehaviorSubject<boolean>(false);
+    public profile: UserRole[]
+
+    private rolesTabelName = 'rolesToken'
+
+    private refresh: any;
+
+    private maintenance: boolean = false;
 
 
     constructor(private http: HttpClient,
                 private appConfig: AppConfigService,
-                private jwtHelper: JwtHelperService) {
+                private jwtHelper: JwtHelperService,
+                private profileService: ProfileService,
+                private maintenanceService: ConfigurationService) {
+        this.loadAndSaveRoles();
+        this.loadUser()
+        this.getConfigurationToCheckMaintenance();
     }
-    //TODO make this static again and serive this feature in other way
+
+    public loadUser(): void {
+
+        this.profileService.getRoles().subscribe(roles => {
+            this.profile = roles
+            this.storeRoles(roles)
+        })
+    }
+
+    public refreshUserRoles(): void {
+        this.refresh = setInterval(() => {
+            if (this.isLogged()) {
+                this.refreshToken()
+                this.loadUser();
+            }
+        }, 60000);
+    }
+
+    private getConfigurationToCheckMaintenance() {
+        this.maintenanceService.getConfiguration().subscribe(value => {
+            if (value !== undefined && value !== null && value.maintenance) {
+                console.warn('Maintenance is on. Disabled login.')
+                this.isLoggedInSubject.next(false);
+                this.logout();
+                this.maintenance = true;
+                return false;
+            }
+        });
+    }
+
     public storeToken(token: string): void {
         localStorage.setItem(this.appConfig.config.tokenName, token);
     }
 
+    public storeRefreshToken(token: string): void {
+        localStorage.setItem(AuthService.REFRESH_TOKEN, token);
+    }
+
+    public storeOidcToken(token: string): void {
+        localStorage.setItem(AuthService.OIDC_TOKEN, token);
+    }
+
+    public refreshToken() {
+        return this.http.post<any>(this.appConfig.config.apiUrl + '/auth/basic/token', {
+            refreshToken: this.getRefreshToken()
+        }).subscribe(response => {
+            const token = response && response['token'];
+            const refreshToken = response && response[AuthService.REFRESH_TOKEN];
+            if (token) {
+                this.storeToken(token);
+            }
+            if (refreshToken) {
+                this.storeRefreshToken(refreshToken)
+            }
+        })
+
+    }
+
+    public storeRoles(roles: UserRole[]): void {
+        const rolesString = JSON.stringify(roles);
+        localStorage.setItem(this.rolesTabelName, rolesString);
+    }
+
+    public loadAndSaveRoles() {
+        this.profile = this.loadRoles();
+    }
+
+    public loadRoles(): UserRole[] {
+        const rolesString = localStorage.getItem(this.rolesTabelName);
+        if (!rolesString) {
+            return null;
+        }
+
+        const parsed = JSON.parse(rolesString);
+        return parsed.map((item: any) => Object.assign(new UserRole(), item));
+    }
+
+    public removeRoles(): void {
+        localStorage.removeItem(this.rolesTabelName)
+    }
+
     private getToken(): string {
         return localStorage.getItem(this.appConfig.config.tokenName)
     }
 
+    private getOidcToken(): string {
+        return localStorage.getItem(AuthService.OIDC_TOKEN)
+    }
+
+    private getRefreshToken(): string {
+        return localStorage.getItem(AuthService.REFRESH_TOKEN)
+    }
+
     private removeToken(): void {
         localStorage.removeItem(this.appConfig.config.tokenName);
     }
 
+    private removeOidcToken(): void {
+        localStorage.removeItem(AuthService.OIDC_TOKEN);
+    }
+
     public getSelectedLanguage(): string {
         if (localStorage.getItem('lang') != null) {
             return localStorage.getItem('lang')
@@ -59,62 +164,60 @@ export class AuthService {
         return (token ? this.jwtHelper.decodeToken(token).sub : null);
     }
 
-    public hasRole(name: string): boolean {
+    public getPreferredUsername(): string {
         const token = this.getToken();
-        const authorities: Authority[] = this.jwtHelper.decodeToken(token).scopes;
-        for (let i = 0; i < authorities.length; i++) {
-            if (authorities[i].authority.indexOf(name) > -1) {
+        return (token ? this.jwtHelper.decodeToken(token).preferred_username : null);
+    }
+
+    public hasRole(name: string): boolean {
+
+        const roles = this.getRoles()
+
+        for (const role of roles) {
+            if (role === name) {
                 return true;
             }
         }
         return false;
+
     }
 
     public hasDomainRole(domainId: number, name: string): boolean {
-        const token = this.getToken();
-        const authorities: Authority[] = this.jwtHelper.decodeToken(token).scopes;
-        for (let i = 0; i < authorities.length; i++) {
-            if (authorities[i].authority.indexOf(domainId + ':' + name) > -1) {
-                return true;
+        let result = false;
+        const domainRoles: Map<number, DomainRoles> = this.getDomainRoles();
+        for (const [mapDomainId, domainRolesValue] of domainRoles) {
+            if (mapDomainId === domainId) {
+                domainRolesValue.getRoles().forEach(role => {
+                    if (role === name) {
+                        result = true;
+                    }
+                })
             }
         }
-        return false;
+        return result;
     }
 
-    public getDomainRoles(): Map<number, DomainRoles> {
-        const drMap: Map<number, DomainRoles> = new Map<number, DomainRoles>();
-
+    public getGlobalRole(): string[] {
         const token = this.getToken();
         if (token == null) {
-            return drMap;
+            return null;
         }
+        return this.jwtHelper.decodeToken(token).global_role;
+    }
 
-        const authorities: Authority[] = this.jwtHelper.decodeToken(token).scopes;
-        if (authorities == null) {
-            return drMap;
-        }
+    public getDomainRoles(): Map<number, DomainRoles> {
+        const domainRolesMap: Map<number, DomainRoles> = new Map<number, DomainRoles>();
 
-        for (let index = 0; index < authorities.length; index++) {
-            if (authorities[index].authority === undefined) {
-                continue;
-            }
+        const domains: number[] = this.getDomains();
+        for (const domain of domains) {
+            const roles: string[] = this.profile
+                .filter(userRole => userRole.domainId === domain)
+                .map(userRole => Role[userRole.role])
 
-            const domainRole: string[] = authorities[index].authority.split(':', 2);
-            if (domainRole.length !== 2) {
-                continue;
-            }
-            const domainId: number = Number.parseInt(domainRole[0], 10);
-            const role: string = domainRole[1];
+            domainRolesMap.set(domain, new DomainRoles(domain, roles));
 
-            let dr: DomainRoles;
-            if (!drMap.has(domainId)) {
-                drMap.set(domainId, new DomainRoles(domainId, []));
-            }
-            dr = drMap.get(domainId);
-            dr.getRoles().push(role);
         }
-
-        return drMap;
+        return domainRolesMap;
     }
 
     public getRoles(): string[] {
@@ -124,56 +227,35 @@ export class AuthService {
         if (token == null) {
             return roles;
         }
+        const domainRoles: string[] = this.jwtHelper.decodeToken(token).roles;
+        const globalRole: string[] = this.jwtHelper.decodeToken(token).global_role;
 
-        const authorities: Authority[] = this.jwtHelper.decodeToken(token).scopes;
-        for (let index = 0; index < authorities.length; index++) {
-            if (authorities[index].authority === undefined) {
-                continue;
-            }
+        roles.push(globalRole[0]);
 
-            const domainRole: string[] = authorities[index].authority.split(':', 2);
-            if (domainRole.length !== 2) {
-                continue;
-            }
-            const role: string = domainRole[1];
-            if (roles.indexOf(role) === -1) {
-                roles.push(role);
-            }
+        for (const role of domainRoles) {
+
+            roles.push(role);
         }
+
         return roles;
     }
 
 
     public getDomains(): number[] {
-        const domains: number[] = [];
-
-        const token = this.getToken();
-        if (token == null) {
-            return domains;
-        }
-
-        const authorities: Authority[] = this.jwtHelper.decodeToken(token).scopes;
-
-        for (let index = 0; index < authorities.length; index++) {
-            if (authorities[index].authority === undefined) {
-                continue;
+        if (this.isLogged()) {
+            if (this.profile !== undefined && this.profile !== null) {
+                return this.getDomainIds();
+            } else {
+                return [];
             }
 
-            const domainIdStr: string[] = authorities[index].authority.split(':', 1);
-            if (domainIdStr.length === 0) {
-                continue;
-            }
-            const domainId: number = Number.parseInt(domainIdStr[0], 10);
-            if (domains.indexOf(domainId) === -1) {
-                domains.push(domainId);
-            }
         }
-        return domains;
+        return [];
+
     }
 
     public getDomainsWithRole(name: string): number[] {
         const domainsWithRole: number[] = [];
-
         const domains: number[] = this.getDomains();
         domains.forEach((domainId) => {
             if (this.hasDomainRole(domainId, name)) {
@@ -184,10 +266,60 @@ export class AuthService {
         return domainsWithRole;
     }
 
+    public oidcLinkingLogin(oidcToken: string,
+                            email: string,
+                            password: string,
+                            uuid: string,
+                            firstName: string,
+                            lastName: string) {
+        const headers = new HttpHeaders({'Content-Type': 'application/json', 'Accept': 'application/json'});
+
+        return this.http.post(this.appConfig.config.apiUrl + '/oidc/link',
+            JSON.stringify(
+                {
+                    'oidcToken': oidcToken,
+                    'email': email,
+                    'password': password,
+                    'uuid': uuid,
+                    'firstName': firstName,
+                    'lastName': lastName,
+                }
+            ),
+            {headers: headers}).pipe(
+            debounceTime(1000),
+            map((res: Response) => {
+                    const token = res && res['token'];
+                    const oidcToken = res && res['oidcToken'];
+                    if (token && oidcToken) {
+                        this.storeToken(token);
+                        this.storeOidcToken(oidcToken);
+                        this.loginUsingSsoService = false;
+                        this.isLoggedInSubject.next(true);
+                        this.profileService.getRoles().subscribe(profile => {
+                            this.profile = profile
+                            this.storeRoles(profile);
+                            return true;
+                        })
+                    } else {
+                        this.isLoggedInSubject.next(false);
+                        return false;
+                    }
+                }
+            ),
+        )
+    }
+
     public login(username: string, password: string): Observable<boolean> {
         // hack so test instance modal is shown onl after login
         localStorage.setItem(this.appConfig.getTestInstanceModalKey(), 'True');
 
+        if (this.maintenance) {
+            this.isLoggedInSubject.next(false);
+            console.warn('Maintenance is on. Disabled login.')
+            //add toast here
+            return of(false);
+        }
+
         const headers = new HttpHeaders({'Content-Type': 'application/json', 'Accept': 'application/json'});
         return this.http.post(this.appConfig.config.apiUrl + '/auth/basic/login',
             JSON.stringify({'username': username, 'password': password}), {headers: headers}).pipe(
@@ -196,9 +328,11 @@ export class AuthService {
                 console.debug('Login response: ' + response.statusText);
                 // login successful if there's a jwt token in the response
                 const token = response && response['token'];
-                if (token) {
+                const refreshToken = response && response[AuthService.REFRESH_TOKEN];
+                if (token && refreshToken) {
                     // set token property
                     this.storeToken(token);
+                    this.storeRefreshToken(refreshToken)
 
                     console.debug('AUTH | User: ' + this.getUsername());
                     console.debug('AUTH | Domains: ' + this.getDomains());
@@ -206,7 +340,11 @@ export class AuthService {
                     console.debug('AUTH | DomainRoles: ' + this.getDomainRoles());
                     this.loginUsingSsoService = false;
                     this.isLoggedInSubject.next(true);
-                    return true;
+                    this.profileService.getRoles().subscribe(profile => {
+                        this.profile = profile
+                        this.storeRoles(profile);
+                        return true;
+                    })
                 } else {
                     // return false to indicate failed login
                     this.isLoggedInSubject.next(false);
@@ -226,48 +364,33 @@ export class AuthService {
             }));
     }
 
-    public propagateSSOLogin(userid: string): Observable<boolean> {
-        console.debug('propagateSSOLogin');
-        console.debug('propagateSSOLogin ' + this.appConfig.config.apiUrl);
-        console.debug('propagateSSOLogin ' + this.appConfig.config.apiUrl + '/auth/sso/login');
-        console.debug('propagateSSOLogin ' + userid);
-        // hack so test instance modal is shown onl after login
-        localStorage.setItem(this.appConfig.getTestInstanceModalKey(), 'True');
-
-        const headers = new HttpHeaders({'Content-Type': 'application/json', 'Accept': 'application/json'});
-        return this.http.post(this.appConfig.config.apiUrl + '/auth/sso/login',
-            JSON.stringify({'userid': userid}), {headers: headers}).pipe(
-            debounceTime(10000),
-            map((response: Response) => {
-                console.debug('SSO login response: ' + response);
-                // login successful if there's a jwt token in the response
-                const token = response && response['token'];
+    public logout(): void {
+        const oidcToken = this.getOidcToken();
+        this.refresh = null;
+        if (oidcToken === null) {
+            this.removeToken();
+            this.isLoggedInSubject.next(false);
+            localStorage.removeItem('_expiredTime');
+        } else {
+            this.removeToken();
+            this.removeOidcToken();
+            this.isLoggedInSubject.next(false);
+            localStorage.removeItem('_expiredTime');
+            this.http.get(this.appConfig.config.apiUrl + '/oidc/logout/' + oidcToken).subscribe(() => {
+            })
+        }
+    }
 
-                if (token) {
-                    this.storeToken(token);
-                    console.debug('SSO AUTH | User: ' + this.getUsername());
-                    console.debug('SSO AUTH | Domains: ' + this.getDomains());
-                    console.debug('SSO AUTH | Roles: ' + this.getRoles());
-                    console.debug('SSO AUTH | DomainRoles: ' + this.getDomainRoles());
-                    this.loginUsingSsoService = true;
-                    this.isLoggedInSubject.next(true);
-                    return true;
-                } else {
-                    // return false to indicate failed login
-                    this.isLoggedInSubject.next(false);
-                    return false;
-                }
-            }),
-            catchError((error) => {
-                console.error('SSO login error: ' + error.error['message']);
-                return observableThrowError(error);
-            }));
+    public oidcLogout(oidcToken: string): void {
+        this.http.get(this.appConfig.config.apiUrl + '/oidc/logout/' + oidcToken).subscribe(() => {
+        })
     }
 
-    public logout(): void {
-        this.removeToken();
-        this.isLoggedInSubject.next(false);
-        localStorage.removeItem('_expiredTime');
+    get isLoggedIn$(): Observable<boolean> {
+        this.isLoggedInSubject.next(this.isLogged());
+        return this.isLoggedInSubject.pipe(
+            debounceTime(100), // use debounceTime to aggregate multiple emissions https://rxjs.dev/api/operators/debounceTime
+        );
     }
 
     public isLogged(): boolean {
@@ -278,11 +401,9 @@ export class AuthService {
         return (token ? !this.jwtHelper.isTokenExpired(token) : false);
     }
 
-    get isLoggedIn$(): Observable<boolean> {
-        this.isLoggedInSubject.next(this.isLogged());
-        return this.isLoggedInSubject.pipe(
-            debounceTime(100), // use debounceTime to aggregate multiple emissions https://rxjs.dev/api/operators/debounceTime
-        );
+
+    public getDomainIds(): number[] {
+        return Array.from(new Set(this.profile.map(ur => ur.domainId)));
     }
 
 }
diff --git a/src/app/auth/login-success/login-success.component.ts b/src/app/auth/login-success/login-success.component.ts
index 02d3386850147f1e758a80f4b435d973e5abb42f..f4f72dda8b1d19b812957eee50f7144afe815f74 100644
--- a/src/app/auth/login-success/login-success.component.ts
+++ b/src/app/auth/login-success/login-success.component.ts
@@ -17,11 +17,19 @@ export class LoginSuccessComponent implements OnInit {
     ngOnInit(): void {
         this.route.queryParams.subscribe(params => {
             const token = params['token'];
-            const refreshToken = params['refresh_token'];
+            const refreshToken = params['refresh-token'];
+            const oidcToken = params['oidc-token'];
             if (token) {
                 this.authService.storeToken(token);
             }
-            this.router.navigate(['/portal'])
+            if (oidcToken) {
+                this.authService.storeOidcToken(oidcToken);
+            }
+            if (refreshToken) {
+                this.authService.storeRefreshToken(refreshToken);
+            }
+            this.authService.loadUser();
+            this.router.navigate(['/'])
         })
 
     }
diff --git a/src/app/directive/roles-exluded.directive.ts b/src/app/directive/roles-exluded.directive.ts
new file mode 100644
index 0000000000000000000000000000000000000000..6b003ab52b1403e88a538ac016bc9e7cdde22636
--- /dev/null
+++ b/src/app/directive/roles-exluded.directive.ts
@@ -0,0 +1,30 @@
+import { Directive, Input, TemplateRef, ViewContainerRef } from '@angular/core';
+import { AuthService } from '../auth/auth.service';
+
+@Directive({
+  selector: '[rolesExcluded]'
+})
+export class RolesExcludedDirective {
+  private _excluded: Array<string> = [];
+
+  constructor(
+    private _templateRef: TemplateRef<any>,
+    private _viewContainer: ViewContainerRef,
+    private authService: AuthService
+  ) {}
+
+  @Input() set rolesExcluded(excludedRoles: Array<string>) {
+    this._excluded = excludedRoles;
+    this.updateState();
+  }
+
+  private updateState() {
+    this._viewContainer.clear();
+
+    const hasExcludedRole = this._excluded.some(role => this.authService.hasRole(role));
+    if (!hasExcludedRole) {
+      // If user has exluded role hide the element 
+      this._viewContainer.createEmbeddedView(this._templateRef);
+    } 
+  }
+}
\ No newline at end of file
diff --git a/src/app/directive/roles.directive.ts b/src/app/directive/roles.directive.ts
index 68f2e12346693fe23de1f14c4f90b100cfd8b095..c2155e3c2a02438a75fd56ae119b5a12c910b3d8 100644
--- a/src/app/directive/roles.directive.ts
+++ b/src/app/directive/roles.directive.ts
@@ -3,10 +3,7 @@ import {Directive, Input, TemplateRef, ViewContainerRef} from '@angular/core';
 
 class RoleState {
     public allowed: Array<string> = new Array<string>();
-    public excluded: Array<string> = new Array<string>()
 }
-
-
 @Directive({
     selector: '[roles]',
     inputs: ['roles']
@@ -15,8 +12,6 @@ export class RolesDirective {
 
     private _allowed: Array<string> = new Array<string>();
 
-    private _excluded: Array<string> = new Array<string>();
-
     constructor(private _templateRef: TemplateRef<any>,
                 private _viewContainer: ViewContainerRef,
                 private authService: AuthService) {
@@ -26,53 +21,18 @@ export class RolesDirective {
     @Input() set roles(allowedRoles: Array<string>) {
         this._allowed = allowedRoles;
         this.updateState({
-            allowed: this._allowed,
-            excluded: this._excluded
-        })
-    }
-
-    // Excluded roles have priority than allowed roles
-    // If user have excluded role template would not be shown
-
-    @Input() set rolesExcluded(excluded: Array<string>) {
-        this._excluded = excluded;
-        this.updateState({
-            allowed: this._allowed,
-            excluded: this._excluded
+            allowed: this._allowed
         })
     }
 
     updateState(state: RoleState) {
         this._viewContainer.clear();
-
-        let show: boolean = false;
-        let notAllowed: boolean = false;
-
-        const allowedRoles = state.allowed;
-
-        for (let exclude of state.excluded) {
-            if (this.authService.hasRole(exclude)) {
-                notAllowed = true;
-                break;
-            }
+    
+    
+        const hasAllowedRole = state.allowed.some(role => this.authService.hasRole(role));
+        if (hasAllowedRole) {
+            this._viewContainer.createEmbeddedView(this._templateRef);
         }
-        if (notAllowed) {
-            this._viewContainer.clear();
-        } else {
-            for (let allowedRole of allowedRoles) {
-                if (this.authService.hasRole(allowedRole)) {
-                    show = true;
-                    break;
-                }
-            }
-
-            if (show) {
-                this._viewContainer.createEmbeddedView(this._templateRef);
-            } else {
-                this._viewContainer.clear();
-            }
-        }
-
     }
 
 }
diff --git a/src/app/model/app-instance.ts b/src/app/model/app-instance.ts
index 76edca2f6b68caf22d2f7702e9a2eb6f06d5c237..27119dad519db59323259ae6544037dc14fcd478 100644
--- a/src/app/model/app-instance.ts
+++ b/src/app/model/app-instance.ts
@@ -28,6 +28,7 @@ export class AppInstance {
 
   public id: number = undefined;
   public domainId: number = undefined;
+  public domainName: string = undefined;
   public applicationId: number = undefined;
   public applicationName: string = undefined;
   public applicationVersion: string = undefined;
diff --git a/src/app/model/cluster-manager.ts b/src/app/model/cluster-manager.ts
new file mode 100644
index 0000000000000000000000000000000000000000..f37b9747cb8cc223d1ee1d4d8b5f142cf582b270
--- /dev/null
+++ b/src/app/model/cluster-manager.ts
@@ -0,0 +1,20 @@
+import { ClusterDeployment , ClusterExtNetwork, ClusterIngress} from './cluster'; 
+
+
+export class ClusterManager {
+    public id: number;
+    public name: string;
+    public codename: string;
+    public description: string;
+    public creationDate: Date;  
+    public modificationDate: Date;
+    public clusterConfigFile: string;
+    public pathConfigFile: string;
+    public ingress: ClusterIngress;
+    public deployment: ClusterDeployment;
+    public externalNetworks: ClusterExtNetwork[]
+    public domainNames: string[];
+    public state : string;
+    public currentStateSince: Date;
+    public contactEmail: string;
+}
\ No newline at end of file
diff --git a/src/app/model/cluster.ts b/src/app/model/cluster.ts
index c08513213109a0eb2c1ca9075c726a032130a468..3468c121486e3069ce8c2b0f69815eb1c9f3200f 100644
--- a/src/app/model/cluster.ts
+++ b/src/app/model/cluster.ts
@@ -2,7 +2,7 @@ export class ClusterInfo {
     public id: number;
 }
 
-class ClusterDeployment {
+export class ClusterDeployment {
     public smtpServerHostname: string="";
     public smtpServerPort: string="";
     public smtpServerUsername: string="";
@@ -24,7 +24,7 @@ export class ClusterExtNetwork {
     public id: number;
 }
 
-class ClusterIngress {
+export class ClusterIngress {
     public id: number;
     public controllerConfigOption: string;
     public controllerChartName: string;
diff --git a/src/app/model/configuration.ts b/src/app/model/configuration.ts
index 5bdb54fdace5d822fef1526fbfe092aa13117288..40896c07bfc2b1439633aef88f05cb1660beceec 100644
--- a/src/app/model/configuration.ts
+++ b/src/app/model/configuration.ts
@@ -12,4 +12,6 @@ export class Configuration {
     public bulkDeploymentJobCron: string;
     public parallelDeploymentsLimit: number;
     public bulkDeploymentQueueRefresh: number;
+    public deploymentPrefix: string;
+    public bulkDeploymentTimeThreshold: number;
 }
diff --git a/src/app/model/domain.ts b/src/app/model/domain.ts
index 524de2483f92a0f7a69036624fdc351665b535e1..04b91adb2465594e36ca2d13197445d6011c05ef 100644
--- a/src/app/model/domain.ts
+++ b/src/app/model/domain.ts
@@ -4,6 +4,7 @@ import {DomainApplicationStatePerDomain} from './domainapplicationstateperdomain
 import {DomainGroup} from './domaingroup';
 import {KeyValue} from './key-value';
 import { DomainAnnotation } from './domain-annotation';
+import { ClusterManager } from './cluster-manager';
 
 export class Domain {
   public id: number = undefined;
@@ -16,4 +17,5 @@ export class Domain {
   public groups: DomainGroup[] = [];
   public deleted: boolean;
   public annotations: DomainAnnotation[] = [];
+  public clusters: ClusterManager[] = [];
 }
diff --git a/src/app/model/userrole.ts b/src/app/model/userrole.ts
index ee06e84b3828a14565b91448cae2c595b73fda3a..acf7ac2f0228e50b8220b4e1812e47fd4377a473 100644
--- a/src/app/model/userrole.ts
+++ b/src/app/model/userrole.ts
@@ -1,14 +1,14 @@
 export enum Role {
-  ROLE_SYSTEM_ADMIN,
-  ROLE_DOMAIN_ADMIN,
-  ROLE_OPERATOR,
-  ROLE_TOOL_MANAGER,
-  ROLE_USER,
-  ROLE_GUEST,
-  ROLE_INCOMPLETE,
-  ROLE_NOT_ACCEPTED,
-  ROLE_VL_MANAGER,
-  ROLE_VL_DOMAIN_ADMIN
+  ROLE_SYSTEM_ADMIN = 'ROLE_SYSTEM_ADMIN',
+  ROLE_DOMAIN_ADMIN = 'ROLE_DOMAIN_ADMIN',
+  ROLE_OPERATOR = "ROLE_OPERATOR",
+  ROLE_TOOL_MANAGER = "ROLE_TOOL_MANAGER",
+  ROLE_USER = "ROLE_USER",
+  ROLE_GUEST = "ROLE_GUEST",
+  ROLE_INCOMPLETE = "ROLE_INCOMPLETE",
+  ROLE_NOT_ACCEPTED = "ROLE_NOT_ACCEPTED",
+  ROLE_GROUP_MANAGER = "ROLE_GROUP_MANAGER",
+  ROLE_GROUP_DOMAIN_ADMIN = "ROLE_GROUP_DOMAIN_ADMIN",
 }
 
 export function RoleAware(constructor: Function) {
diff --git a/src/app/service/appconfig.service.ts b/src/app/service/appconfig.service.ts
index e15d9b5c331c6cfdc8d7bf68ed9c24ec3d8bed3e..df61388c90ac79ee006e8922fb695a032bae7ed8 100644
--- a/src/app/service/appconfig.service.ts
+++ b/src/app/service/appconfig.service.ts
@@ -64,6 +64,7 @@ export class AppConfigService {
     }
 
     public getSiteKey(): string {
+        console.log("Site key:", this.config.captchaKey)
         if (this.config == null) {
             return '';
         }
diff --git a/src/app/service/cluster-manager.service.ts b/src/app/service/cluster-manager.service.ts
new file mode 100644
index 0000000000000000000000000000000000000000..a298dfe92ec77fd4fb80cdd8d4ecc6248b5f3c70
--- /dev/null
+++ b/src/app/service/cluster-manager.service.ts
@@ -0,0 +1,39 @@
+import { HttpClient } from "@angular/common/http";
+import { Injectable } from "@angular/core";
+import { AppConfigService } from "./appconfig.service";
+import { Observable } from "rxjs";
+import { ClusterManager } from "../model/cluster-manager";
+
+@Injectable({
+    providedIn: 'root',
+})
+export class ClusterManagerService {
+
+    protected url: string;
+
+
+    constructor(private http: HttpClient, 
+                private appConfig: AppConfigService) {
+            this.url = this.appConfig.getApiUrl() + '/management/cluster';
+    }
+
+    public sendCluster(file: File, view: ClusterManager): Observable<ClusterManager> {
+        const formParams = new FormData();
+        formParams.append('file', file);
+        formParams.append('data', new Blob([JSON.stringify(view)], { type: 'application/json' }));
+        return this.http.post<ClusterManager>(this.url, formParams);
+    }
+
+    public getAllClusters(): Observable<ClusterManager[]> {
+    return this.http.get<ClusterManager[]>(this.url + '/all');
+    }
+
+    public getClusterDetails(id: number): Observable<ClusterManager> {
+        return this.http.get<ClusterManager>(`${this.url}/${id}`);
+    }
+
+    public updateCluster(cluster: ClusterManager): Observable<ClusterManager> {
+        return this.http.put<ClusterManager>(`${this.url}/${cluster.id}`, cluster);
+    }
+
+}
\ No newline at end of file
diff --git a/src/app/service/cluster.service.ts b/src/app/service/cluster.service.ts
index dace40815e83787a5897843b9d7206c153ca2686..4830699766480719290f664be76a554b8c85725d 100644
--- a/src/app/service/cluster.service.ts
+++ b/src/app/service/cluster.service.ts
@@ -17,22 +17,11 @@ export class ClusterService extends GenericDataService {
     constructor(http: HttpClient, appConfig: AppConfigService) {
         super(http, appConfig);
 
-        this.url = this.appConfig.getApiUrl() + '/management/kubernetes/';
+        this.url = this.appConfig.getApiUrl() + '/management/kubernetes';
     }
 
     public getCluster(): Observable<Cluster> {
         return this.get<Cluster>(this.url);
     }
 
-    public add(cluster: Cluster): Observable<any> {
-        return this.post(this.url, cluster);
-    }
-
-    public update(cluster: Cluster): Observable<any> {
-        return this.put(this.url + cluster.id, cluster);
-    }
-
-    public remove(clusterId: number): Observable<any> {
-        return this.http.delete(this.url + clusterId);
-    }
 }
diff --git a/src/app/service/dashboard.service.spec.ts b/src/app/service/dashboard.service.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..24d7a1a55c4c188c015e11bf161b50823ba4ab3c
--- /dev/null
+++ b/src/app/service/dashboard.service.spec.ts
@@ -0,0 +1,42 @@
+import { TestBed, inject} from '@angular/core/testing';
+
+import { DashboardService } from './dashboard.service';
+import {HttpClient, HttpHandler} from '@angular/common/http';
+import {Observable, of} from 'rxjs';
+import {Configuration} from '../model/configuration';
+import {AppConfigService} from './appconfig.service';
+
+class MockConfigurationService{
+  protected uri:string;
+
+  constructor() {
+    this.uri = 'http://localhost/api';
+  }
+
+  public getApiUrl(): string {
+    return 'http://localhost/api';
+  }
+
+  public getConfiguration():Observable<Configuration>{
+    return of<Configuration>();
+  }
+
+  public updateConfiguration(configuration:Configuration):Observable<any>{
+    return of<Configuration>();
+  }
+}
+
+describe('DashboardService', () => {
+  let service: DashboardService;
+
+  beforeEach(() => {
+    TestBed.configureTestingModule({
+      providers: [DashboardService, HttpHandler, HttpClient, {provide: AppConfigService, useClass: MockConfigurationService}]
+    });
+    service = TestBed.inject(DashboardService);
+  });
+
+  it('should be created', inject([DashboardService], (service: DashboardService) =>{
+    expect(service).toBeTruthy();
+  }));
+});
diff --git a/src/app/service/dashboard.service.ts b/src/app/service/dashboard.service.ts
new file mode 100644
index 0000000000000000000000000000000000000000..eadf24747dfe0e98f2aca7dc637916e917fa4f03
--- /dev/null
+++ b/src/app/service/dashboard.service.ts
@@ -0,0 +1,22 @@
+import { Injectable } from '@angular/core';
+import {HttpClient} from '@angular/common/http';
+import {AppConfigService} from './appconfig.service';
+import {GenericDataService} from './genericdata.service';
+
+@Injectable({
+  providedIn: 'root'
+})
+export class DashboardService extends GenericDataService {
+
+  constructor(http: HttpClient, appConfig: AppConfigService) {
+    super(http, appConfig);
+  }
+
+  public getAdmin() {
+    return this.get(this.appConfig.getApiUrl() + '/dashboard/admin')
+  }
+
+  public getDomainAdmin(domainId?: number) {
+    return this.get(this.appConfig.getApiUrl() + '/dashboard/domain/' + domainId)
+  }
+}
diff --git a/src/app/service/domain.service.spec.ts b/src/app/service/domain.service.spec.ts
index 4ea9fa4e4fc2f5afff4f3674affb79ff7afbf19a..0efb7b70d3a410434874a88ace9f1f352b6c37e3 100644
--- a/src/app/service/domain.service.spec.ts
+++ b/src/app/service/domain.service.spec.ts
@@ -5,6 +5,8 @@ import {HttpClient, HttpHandler} from "@angular/common/http";
 import {AppConfigService} from "./appconfig.service";
 import {Observable, of} from "rxjs";
 import {Configuration} from "../model/configuration";
+import { HttpClientTestingModule, HttpTestingController } from '@angular/common/http/testing';
+import { Domain } from '../model/domain';
 
 class MockConfigurationService{
     protected uri:string;
@@ -26,14 +28,130 @@ class MockConfigurationService{
     }
 }
 
+
+
 describe('DomainService', () => {
+  let service: DomainService;
+  let httpMock: HttpTestingController;
+  let appConfigService: jasmine.SpyObj<AppConfigService>;
+  const mockApiUrl = 'http://localhost/api';
+
+  const mockDomain: Domain = {
+    id: 1,
+    name: 'Test Domain',
+    codename: 'test-domain',
+    active: true,
+    domainDcnDetails: {
+      id: 1,
+      domainCodename: 'test-domain',
+      dcnConfigured: false,
+      dcnDeploymentType: 'type',
+      customerNetworks: []
+    },
+    domainTechDetails: null,
+    applicationStatePerDomain: [],
+    groups: [],
+    deleted: false,
+    annotations: [],
+    clusters: [],
+  };
+
   beforeEach(() => {
+    const appConfigSpy = jasmine.createSpyObj('AppConfigService', ['getApiUrl', 'getNmaasGlobalDomainId', 'getHttpTimeout']);
+    appConfigSpy.getApiUrl.and.returnValue(mockApiUrl);
+    appConfigSpy.getNmaasGlobalDomainId.and.returnValue(1);
+    appConfigSpy.getHttpTimeout.and.returnValue(30000); // Dodano mock dla getHttpTimeout
+
     TestBed.configureTestingModule({
-      providers: [DomainService, HttpHandler, HttpClient, {provide: AppConfigService, useClass: MockConfigurationService}]
+      imports: [HttpClientTestingModule],
+      providers: [
+        DomainService, 
+        {provide: AppConfigService, useValue: appConfigSpy}]
     });
+
+    service = TestBed.inject(DomainService);
+  httpMock = TestBed.inject(HttpTestingController);
   });
+  
+
+
+  afterEach(() => {
+    httpMock.verify();
+  });
+
 
   it('should be created', inject([DomainService], (service: DomainService) => {
     expect(service).toBeTruthy();
   }));
+
+
+
+  it('should get global domain', () => {
+    service.getGlobalDomain().subscribe((domain) => {
+      expect(domain).toEqual(mockDomain);
+    });
+
+    const req = httpMock.expectOne(`${mockApiUrl}/domains/1`);
+    expect(req.request.method).toBe('GET');
+    req.flush(mockDomain);
+  });
+
+  it('should get all domains', () => {
+    const mockDomains: Domain[] = [mockDomain, { ...mockDomain, id: 2, name: 'Another Domain' }];
+
+    service.getAll().subscribe((domains) => {
+      expect(domains.length).toBe(2);
+      expect(domains).toEqual(mockDomains);
+    });
+
+    const req = httpMock.expectOne(`${mockApiUrl}/domains`);
+    expect(req.request.method).toBe('GET');
+    req.flush(mockDomains);
+  });
+
+  it('should add a new domain', () => {
+    const mockId= { id: 1 };
+
+    service.add(mockDomain).subscribe((id) => {
+      expect(id).toEqual(mockId);
+    });
+
+    const req = httpMock.expectOne(`${mockApiUrl}/domains`);
+    expect(req.request.method).toBe('POST');
+    expect(req.request.body).toEqual(mockDomain);
+    req.flush(mockId);
+  });
+
+  it('should update a domain', () => {
+    service.update(mockDomain).subscribe((response) => {
+      expect(response).toBeTruthy();
+    });
+
+    const req = httpMock.expectOne(`${mockApiUrl}/domains/1`);
+    expect(req.request.method).toBe('PUT');
+    expect(req.request.body).toEqual(mockDomain);
+    req.flush({});
+  });
+
+  it('should delete a domain', () => {
+    service.remove(1).subscribe((response) => {
+      expect(response).toBeTruthy();
+    });
+
+    const req = httpMock.expectOne(`${mockApiUrl}/domains/1`);
+    expect(req.request.method).toBe('DELETE');
+    req.flush({});
+  });
+
+
+  it('should update domain state', () => {
+    service.updateDomainState(mockDomain).subscribe((response) => {
+      expect(response).toBeTruthy();
+    });
+
+    const req = httpMock.expectOne(`${mockApiUrl}/domains/1/state?active=false`);
+    expect(req.request.method).toBe('PATCH');
+    req.flush({});
+  });
+
 });
diff --git a/src/app/service/domain.service.ts b/src/app/service/domain.service.ts
index 7ed0257a4aca76390edd525a84274cb6667c150d..7f6a3e2c51420794fc1317ac2e88ddabfdfdc7d8 100644
--- a/src/app/service/domain.service.ts
+++ b/src/app/service/domain.service.ts
@@ -19,12 +19,15 @@ export class DomainService extends GenericDataService {
 
   protected url: string;
 
+  protected urlGroups: string;
+
   private updateRequiredFlag: boolean;
 
   constructor(http: HttpClient, appConfig: AppConfigService) {
     super(http, appConfig);
     this.updateRequiredFlag = false;
     this.url = this.appConfig.getApiUrl() + '/domains';
+    this.urlGroups = this.appConfig.getApiUrl() + '/groups';
   }
 
   public getGlobalDomainId(): number {
@@ -39,6 +42,10 @@ export class DomainService extends GenericDataService {
     return this.get<Domain[]>(this.url);
   }
 
+  public getAllBase(): Observable<Domain[]> {
+    return this.get<Domain[]>(this.url + '/base');
+  }
+
   public getOne(domainId: number): Observable<Domain> {
     return this.get<Domain>(this.url + '/' + domainId);
   }
@@ -89,35 +96,35 @@ export class DomainService extends GenericDataService {
 
   // GROUPS
   public getAllDomainGroups(): Observable<DomainGroup[]> {
-    return this.get<DomainGroup[]>(this.url + '/group');
+    return this.get<DomainGroup[]>(this.urlGroups);
   }
 
   public getDomainGroup(domainGroupId: number): Observable<DomainGroup> {
-    return this.get<DomainGroup>(this.url + '/group/' + domainGroupId);
+    return this.get<DomainGroup>(this.urlGroups + '/' + domainGroupId);
   }
 
   public deleteDomainGroup(domainGroupId: number): Observable<void> {
-    return this.delete<void>(this.url + '/group/' + domainGroupId);
+    return this.delete<void>(this.urlGroups + '/' + domainGroupId);
   }
 
   public addDomainsToGroup(groupCodeName: string, domainIds: number[]): Observable<DomainGroup> {
-    return this.post(this.url + '/group/' + groupCodeName, domainIds);
+    return this.post(this.urlGroups + '/' + groupCodeName, domainIds);
   }
 
   public deleteDomainFromGroup(groupId: number, domainId: number): Observable<DomainGroup> {
-    return this.patch(this.url + '/group/' + groupId, domainId);
+    return this.patch(this.urlGroups + '/' + groupId, domainId);
   }
 
   public createDomainGroup(domainGroup: DomainGroup): Observable<Id> {
-    return this.post(this.url + '/group', domainGroup);
+    return this.post(this.urlGroups , domainGroup);
   }
 
   public updateDomainGroup(domainGroup: DomainGroup, id: number): Observable<Id> {
-    return this.put(this.url + '/group/' + id, domainGroup);
+    return this.put(this.urlGroups+ "/" + id, domainGroup);
   }
 
   public updateDomainGroupManagers(managers: User[], id: number): Observable<DomainGroup> {
-    return this.put(this.url + '/group/members/' + id, managers);
+    return this.put(this.urlGroups + '/' + id + "/members", managers);
   }
 
   public getAnnotations(): Observable<DomainAnnotation[]> {
diff --git a/src/app/service/profile.service.ts b/src/app/service/profile.service.ts
index 0c745763a950266d06cfa37e2f574eeb336a2cc8..ee77d26c2101c874456c1d6ebd1e868aa0cc68d7 100644
--- a/src/app/service/profile.service.ts
+++ b/src/app/service/profile.service.ts
@@ -4,6 +4,7 @@ import {AppConfigService} from './appconfig.service';
 import {Observable} from 'rxjs';
 import {User} from '../model';
 import {HttpClient} from '@angular/common/http';
+import { UserRole } from '../model/userrole';
 
 
 @Injectable({
@@ -19,6 +20,10 @@ export class ProfileService extends GenericDataService {
     return this.http.get<User>(this.getProfileUrl() + 'user')
   }
 
+  public getRoles(): Observable<UserRole[]> {
+    return this.http.get<UserRole[]>(this.getProfileUrl() + 'user/roles')
+  }
+
   protected getProfileUrl(): string {
       return this.appConfig.getApiUrl() + '/profile/'
   }
diff --git a/src/app/service/shell-client.service.ts b/src/app/service/shell-client.service.ts
index 7a1cb49aef95fb181afe999a4bfaa17bc8599141..7d920a07bae5f470a5fc97ea19b286993a4b1ecf 100644
--- a/src/app/service/shell-client.service.ts
+++ b/src/app/service/shell-client.service.ts
@@ -18,11 +18,11 @@ export class ShellClientService {
 
     public initConnection(id: number, pod: string): Observable<string> {
         // @ts-ignore
-        return this.http.post<string>(this.appConfig.getApiUrl() + '/shell/' + id + '/init/' + pod, {}, {responseType: 'text'});
+        return this.http.post<string>(this.appConfig.getApiUrl() + '/pods/shell/' + id + '/init/' + pod, {}, {responseType: 'text'});
     }
 
     public sendCommand(sessionId: string, command: Object = {}): Observable<any> {
-        return this.http.post(this.appConfig.getApiUrl() + '/shell/' + sessionId + '/command', command);
+        return this.http.post(this.appConfig.getApiUrl() + '/pods/shell/' + sessionId + '/command', command);
     }
 
     /**
@@ -30,7 +30,7 @@ export class ShellClientService {
      */
     public closeConnection(sessionId: string) {
         this.closeEventStream()
-        this.http.delete(this.appConfig.getApiUrl() + '/shell/' + sessionId).subscribe(
+        this.http.delete(this.appConfig.getApiUrl() + '/pods/shell/' + sessionId).subscribe(
             () => console.log('session completed: ', sessionId),
             error => console.error('error completing session', error))
     }
@@ -42,7 +42,7 @@ export class ShellClientService {
 
     public getServerSentEvent(sessionId: string): Observable<OnMessageEvent> {
         return new Observable<OnMessageEvent>(observableEvents => {
-            const events = this._sseService.getEventSource(this.appConfig.getApiUrl() + '/shell/' + sessionId);
+            const events = this._sseService.getEventSource(this.appConfig.getApiUrl() + '/pods/shell/' + sessionId);
 
             events.onopen = onopenEvent => {
                 this._zone.run(() => {
@@ -67,7 +67,7 @@ export class ShellClientService {
     }
 
     public getPossiblePods(id: number): Observable<PodInfo[]> {
-        return this.http.get<PodInfo[]>(this.appConfig.getApiUrl() + '/shell/' + id + '/podnames');
+        return this.http.get<PodInfo[]>(this.appConfig.getApiUrl() + '/pods/shell/' + id + '/podnames');
     }
 
 }
diff --git a/src/app/service/sso.service.spec.ts b/src/app/service/sso.service.spec.ts
deleted file mode 100644
index 447e1159701776ff09a20d63fefdee219f341f06..0000000000000000000000000000000000000000
--- a/src/app/service/sso.service.spec.ts
+++ /dev/null
@@ -1,39 +0,0 @@
-import { TestBed, inject } from '@angular/core/testing';
-
-import { SSOService } from './sso.service';
-import {Observable, of} from 'rxjs';
-import {Configuration} from '../model/configuration';
-import {HttpClient, HttpHandler} from '@angular/common/http';
-import {AppConfigService} from './appconfig.service';
-
-class MockConfigurationService {
-    protected uri: string;
-
-    constructor() {
-        this.uri = 'http://localhost/api';
-    }
-
-    public getApiUrl(): string {
-        return 'http://localhost/api';
-    }
-
-    public getConfiguration(): Observable<Configuration> {
-        return of<Configuration>();
-    }
-
-    public updateConfiguration(configuration: Configuration): Observable<any> {
-        return of<Configuration>();
-    }
-}
-
-describe('SSOService', () => {
-  beforeEach(() => {
-    TestBed.configureTestingModule({
-      providers: [SSOService, HttpHandler, HttpClient, {provide: AppConfigService, useClass: MockConfigurationService}]
-    });
-  });
-
-  it('should be created', inject([SSOService], (service: SSOService) => {
-    expect(service).toBeTruthy();
-  }));
-});
diff --git a/src/app/service/sso.service.ts b/src/app/service/sso.service.ts
deleted file mode 100644
index c3ff73bfa55445414fc44f6c923af9607c6dc61b..0000000000000000000000000000000000000000
--- a/src/app/service/sso.service.ts
+++ /dev/null
@@ -1,22 +0,0 @@
-import { Injectable } from '@angular/core';
-import {GenericDataService} from './genericdata.service';
-import {HttpClient} from '@angular/common/http';
-import {AppConfigService} from './appconfig.service';
-import {Observable} from 'rxjs';
-import {SSOConfig} from '../model/sso';
-
-@Injectable()
-export class SSOService extends GenericDataService {
-
-  protected url: string;
-
-  constructor(http: HttpClient, appConfig: AppConfigService) {
-    super(http, appConfig);
-    this.url = this.appConfig.getApiUrl() + '/auth/sso';
-  }
-
-  public getOne(): Observable<SSOConfig> {
-    return this.get<SSOConfig>(this.url);
-  }
-
-}
diff --git a/src/app/service/user.service.ts b/src/app/service/user.service.ts
index e139180f752173a84594c97211e16e8ddb17ae96..8393eb431889e4f88d5c70304a12104b3a1634d7 100644
--- a/src/app/service/user.service.ts
+++ b/src/app/service/user.service.ts
@@ -20,7 +20,7 @@ export class UserService extends GenericDataService {
 
     public getAll(domainId?: number): Observable<User[]> {
         return this.get<User[]>(domainId === undefined || domainId === this.domainService.getGlobalDomainId() ?
-            this.getUsersUrlWithoutDash() : this.getDomainUsersUrl(domainId));
+            this.getUsersUrlWithoutDash() : this.getDomainUsersUrlWithoutDash(domainId));
     }
 
     public getOne(userId: number, domainId?: number): Observable<User> {
@@ -96,12 +96,16 @@ export class UserService extends GenericDataService {
         return this.appConfig.getApiUrl() + '/domains/' + domainId + '/users/';
     }
 
+    protected getDomainUsersUrlWithoutDash(domainId: number): string {
+        return this.appConfig.getApiUrl() + '/domains/' + domainId + '/users';
+    }
+
     public getDomainUsersAsAdmin(domainId: number): Observable<User[]> {
         return this.get<User[]>(this.appConfig.getApiUrl() + '/domains/' + domainId + '/users/admin');
     }
 
     protected getUserAcceptanceUrl(): string {
-        return this.appConfig.getApiUrl() + '/users/terms/';
+        return this.appConfig.getApiUrl() + '/users/terms';
     }
 
     protected getEnableOrDisableUsersUrl(userId: number, enabled: boolean): string {
diff --git a/src/app/shared/about/about.component.html b/src/app/shared/about/about.component.html
index df6d0eb479e590e7436abc90906638ecbe4fb3d0..93662491047eb9332ea1a61af958ffacc4007969 100644
--- a/src/app/shared/about/about.component.html
+++ b/src/app/shared/about/about.component.html
@@ -1,4 +1,4 @@
-<div class="col-md-offset-1 col-md-10 col-lg-offset-1 col-lg-10 row position" style="padding-bottom: 80px; padding-top: 80px;">
+<div class=" row position" style="margin:40px">
     <div class="col-md-6">
         <div class="" style="padding-bottom: 15px;">
             <h2>{{ 'ABOUT.CHANGELOG_TITLE' | translate }}</h2>
@@ -26,12 +26,12 @@
                                 <p class="form-control-static">{{gitInfo?.commitName}}</p>
                             </div>
                         </div>
-                        <div class="row">
-                            <label class="control-label col-sm-2">{{'GIT_INFO.BRANCH_NAME' | translate}}:</label>
-                            <div class="col-sm-10">
-                                <p class="form-control-static">{{gitInfo?.branchName}}</p>
-                            </div>
-                        </div>
+<!--                        <div class="row">-->
+<!--                            <label class="control-label col-sm-2">{{'GIT_INFO.BRANCH_NAME' | translate}}:</label>-->
+<!--                            <div class="col-sm-10">-->
+<!--                                <p class="form-control-static">{{gitInfo?.branchName}}</p>-->
+<!--                            </div>-->
+<!--                        </div>-->
                     </div>
                 </form>
             </div>
diff --git a/src/app/shared/admin-dashboard/admin-dashboard.component.css b/src/app/shared/admin-dashboard/admin-dashboard.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..fdab80cb4c0d886552fe88c52387d4e9616f0493
--- /dev/null
+++ b/src/app/shared/admin-dashboard/admin-dashboard.component.css
@@ -0,0 +1,69 @@
+td{
+    padding: 10px;
+    background: transparent;
+}
+th{
+    padding: 10px;
+}
+:host ::ng-deep .p-datatable .p-datatable-thead > tr > th{
+    border: 1px solid #E0E2E5;
+    background:transparent;
+    border-width: 0 0 1px 0;
+}
+:host ::ng-deep .p-datatable .p-datatable-tbody > tr > td {
+    text-align: left;
+    border: 1px solid #E0E2E5;
+    border-width: 0 0 1px 0;
+    padding: 1rem 1rem;
+}
+:host ::ng-deep .p-datatable .p-datatable-tbody > tr{
+    background: transparent;
+}
+:host ::ng-deep .p-datatable .p-paginator-bottom{
+    height: 40px;
+    background: transparent;
+    border: none;
+    margin-top:10px;
+}
+:host ::ng-deep .p-datatable .p-datatable-tbody > tr{
+    background: transparent;
+}
+
+:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page{
+    transition: unset;
+    border-radius: 50%;
+    min-width:3.5rem;
+    height:3.5rem;
+    margin:0 5px;
+    font-size: 14px;
+}
+
+:host ::ng-deep .p-paginator-element{
+    border-radius:50%;
+    margin:0 5px;
+    min-width:3.5rem;
+    height:3.5rem;
+    font-size: 14px;
+}
+:host ::ng-deep .p-paginator-icon{
+    height: 1.5rem;
+    width: 1.5rem;
+}
+:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page.p-highlight{
+    background: var(--user-button-background-hover);
+}
+:host ::ng-deep .p-datatable-wrapper {
+    max-height: 50vh
+}
+:host ::ng-deep .p-datatable.p-datatable-scrollable > .p-datatable-wrapper > .p-datatable-table > .p-datatable-thead, .p-datatable.p-datatable-scrollable > .p-datatable-wrapper > .p-datatable-table > .p-datatable-tfoot, .p-datatable.p-datatable-scrollable > .p-datatable-wrapper > .p-scroller-viewport > .p-scroller > .p-datatable-table > .p-datatable-thead, .p-datatable.p-datatable-scrollable > .p-datatable-wrapper > .p-scroller-viewport > .p-scroller > .p-datatable-table > .p-datatable-tfoot{
+    background: var(--app-background-color);
+}
+.width-50  {
+    width: 49%
+}
+@media screen and (max-width: 1390px){
+    .width-50 {
+        width:100%
+    }
+}
+
diff --git a/src/app/shared/admin-dashboard/admin-dashboard.component.html b/src/app/shared/admin-dashboard/admin-dashboard.component.html
new file mode 100644
index 0000000000000000000000000000000000000000..b5e72786990f7cd04b73149b71c0554f90c99594
--- /dev/null
+++ b/src/app/shared/admin-dashboard/admin-dashboard.component.html
@@ -0,0 +1,112 @@
+<div  *roles="['ROLE_SYSTEM_ADMIN']">
+    <div style="display: flex; flex-direction:column">
+        <div style="display: flex; flex-wrap: wrap;">
+            <div class="background-section" style="flex: 1 1 30%; margin-right: 20px">
+                <h5 style="font-weight: bold">Current number of user </h5>
+                <h1 style="font-weight: bold">{{ adminData.userCount}}</h1>
+            </div>
+            <div class="background-section" style="flex: 1 1 30%; margin-right: 20px">
+                <h5 style="font-weight: bold">Current number of domains </h5>
+                <h1 style="font-weight: bold">{{ adminData.domainsCount}}</h1>
+            </div>
+            <div class="background-section" style="flex: 1 1 30% ;">
+                <h5 style="font-weight: bold">Current number of deployed applications </h5>
+                <h1 style="font-weight: bold">{{ adminData.instanceCount}}</h1>
+            </div>
+        </div>
+        <div class="grid" style="display: flex; justify-content: space-between;">
+            <div class="background-section width-50 " style="margin-right: 20px">
+                <h5 style="font-weight: bold">Application deployments in the last week</h5>
+                <p-table [value]="instanceCountInPeriodDetails"   [scrollable]="true" [style]="{'width': '100%', 'max-height': '50vh'}">
+                    <ng-template pTemplate="header">
+                        <tr>
+                            <th></th>
+                            <th>Name</th>
+                            <th>Version</th>
+                            <th>Domain</th>
+                        </tr>
+                    </ng-template>
+                    <ng-template pTemplate="body" let-instance>
+                        <tr>
+                            <td><img style="height: 40px" src="../../../assets/images/app-logo-example.png"/></td>
+                            <td>{{instance.applicationName}}</td>
+                            <td>{{instance.applicationVersion}}</td>
+                            <td>{{instance.domainName}}</td>
+                        </tr>
+                    </ng-template>
+                </p-table>
+            </div>
+            <div class="width-50" >
+                <div class="background-section" style="">
+                    <h5 style="font-weight: bold">Most popular applications</h5>
+                    <p-chart type="bar" [data]="popularAppsChartData" [options]="basicOptions" width="100%" height="50vh" />
+                </div>
+            </div>
+        </div>
+    </div>
+</div>
+<div *roles="['ROLE_DOMAIN_ADMIN','ROLE_SYSTEM_ADMIN']">
+    <div *ngIf="domainId !== 1">
+        <div style="display: flex">
+            <div class="background-section" style="flex: 1 1 50%; margin-right: 20px">
+                <h5 style="font-weight: bold">Last login to the domain </h5>
+                <p-table [value]="domainAdminData?.userLogins | keyvalue">
+                    <ng-template pTemplate="header">
+                        <tr>
+                            <th>User</th>
+                            <th>Last login</th>
+                        </tr>
+                    </ng-template>
+                    <ng-template pTemplate="body" let-login>
+                        <tr>
+                            <td>{{ login.key }}</td>
+                            <td>{{ formatDate(login.value) }}</td>
+                        </tr>
+                    </ng-template>
+                </p-table>
+            </div>
+            <div class="background-section" style="flex: 1 1 50%;">
+                <h5 style="font-weight: bold">Number of deployed applications per user </h5>
+                <p-table [value]="domainAdminData?.applicationDeployed | keyvalue">
+                    <ng-template pTemplate="header">
+                        <tr>
+                            <th>User</th>
+                            <th>Deployment</th>
+                        </tr>
+                    </ng-template>
+                    <ng-template pTemplate="body" let-deployment>
+                        <tr>
+                            <td>{{ deployment.key }}</td>
+                            <td>{{ deployment.value }}</td>
+                        </tr>
+                    </ng-template>
+                </p-table>
+            </div>
+        </div>
+        <div class="background-section" style="">
+            <h5 style="font-weight: bold">Application status</h5>
+            <p-table [value]="applicationUpgradeStatus"  [paginator]="true" [rows]="4" [scrollable]="true" [style]="{'width': '100%'}">
+                <ng-template pTemplate="header">
+                    <tr>
+                        <th></th>
+                        <th>Name</th>
+                        <th>Id</th>
+                        <th>Instance name</th>
+                        <th>Version</th>
+                        <th>Need upgrade</th>
+                    </tr>
+                </ng-template>
+                <ng-template pTemplate="body" let-app>
+                    <tr>
+                        <td><img style="height: 40px" src="../../../assets/images/app-logo-example.png"/></td>
+                        <td>{{app.appName}}</td>
+                        <td>{{app.appId}}</td>
+                        <td>{{app.instanceName}}</td>
+                        <td>{{app.appVersion}}</td>
+                        <td>{{app.upgradePossible}}</td>
+                    </tr>
+                </ng-template>
+            </p-table>
+        </div>
+    </div>
+</div>
diff --git a/src/app/shared/admin-dashboard/admin-dashboard.component.spec.ts b/src/app/shared/admin-dashboard/admin-dashboard.component.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..1877b765c09ce11d4eb5b6db1900c7627f0837b2
--- /dev/null
+++ b/src/app/shared/admin-dashboard/admin-dashboard.component.spec.ts
@@ -0,0 +1,67 @@
+import { ComponentFixture, TestBed } from '@angular/core/testing';
+import { of } from 'rxjs';
+import { AdminDashboardComponent } from './admin-dashboard.component';
+import { DashboardService } from '../../service/dashboard.service';
+import { UserDataService } from '../../service/userdata.service';
+import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+
+describe('AdminDashboardComponent', () => {
+  let component: AdminDashboardComponent;
+  let fixture: ComponentFixture<AdminDashboardComponent>;
+  let mockDashboardService: jasmine.SpyObj<DashboardService>;
+  let mockUserDataService: jasmine.SpyObj<UserDataService>;
+
+  beforeEach(async () => {
+    mockDashboardService = jasmine.createSpyObj('DashboardService', ['getAdmin', 'getDomainAdmin']);
+    mockUserDataService = jasmine.createSpyObj('UserDataService', ['selectedDomainId']);
+    mockUserDataService.selectedDomainId = of(123); // Replace 'test-domain-id' with a numeric value
+    mockDashboardService.getAdmin.and.returnValue(of({ 
+      popularApps: { App1: 10, App2: 20 },
+      instanceCountInPeriodDetails: []
+    }));
+    mockDashboardService.getDomainAdmin.and.returnValue(of({
+      applicationUpgradeStatus: []
+    }));
+
+    await TestBed.configureTestingModule({
+      declarations: [AdminDashboardComponent],
+      providers: [
+        { provide: DashboardService, useValue: mockDashboardService },
+        { provide: UserDataService, useValue: mockUserDataService }
+      ],
+      schemas: [NO_ERRORS_SCHEMA, CUSTOM_ELEMENTS_SCHEMA] // Add this to allow unknown properties
+    }).compileComponents();
+
+    fixture = TestBed.createComponent(AdminDashboardComponent);
+    component = fixture.componentInstance;
+    fixture.detectChanges();
+  });
+
+  it('should create', () => {
+    expect(component).toBeTruthy();
+  });
+
+  it('should initialize with admin data and chart data', () => {
+    expect(component.adminData).toBeDefined();
+    expect(component.popularAppsChartData).toBeDefined();
+    expect(component.instanceCountInPeriodDetails).toEqual([]);
+  });
+
+  it('should subscribe to selectedDomainId and fetch domain admin data', () => {
+    expect(component.domainId).toBe(123);
+    expect(component.domainAdminData).toBeDefined();
+    expect(component.applicationUpgradeStatus).toEqual([]);
+  });
+
+  it('should format date correctly', () => {
+    const date = '2023-01-01T00:00:00Z';
+    const formattedDate = component.formatDate(date);
+    expect(formattedDate).toBe(new Date(date).toLocaleString());
+  });
+
+  it('should call chartData method and populate chart data', () => {
+    component.chartData();
+    expect(component.popularAppsChartData.labels).toEqual(['App1', 'App2']);
+    expect(component.popularAppsChartData.datasets[0].data).toEqual([10, 20]);
+  });
+});
diff --git a/src/app/shared/admin-dashboard/admin-dashboard.component.ts b/src/app/shared/admin-dashboard/admin-dashboard.component.ts
new file mode 100644
index 0000000000000000000000000000000000000000..3ae9e16672ced2b5176ef5633728141465828473
--- /dev/null
+++ b/src/app/shared/admin-dashboard/admin-dashboard.component.ts
@@ -0,0 +1,106 @@
+import { Component } from '@angular/core';
+import {DashboardService} from '../../service/dashboard.service';
+import {UserDataService} from '../../service/userdata.service';
+
+@Component({
+  selector: 'app-admin-dashboard',
+  templateUrl: './admin-dashboard.component.html',
+  styleUrl: './admin-dashboard.component.css'
+})
+export class AdminDashboardComponent {
+  popularAppsChartData: any;
+
+  basicOptions: any;
+  adminData: any;
+  domainAdminData: any;
+  instanceCountInPeriodDetails: any[] = [];
+  applicationUpgradeStatus: any[] = [];
+  domainId;
+
+  constructor(protected dashboardService: DashboardService,
+              private userDataService: UserDataService) {
+  }
+
+
+  ngOnInit() {
+    this.userDataService.selectedDomainId.subscribe((domainId) => {
+          this.domainId = domainId
+          this.getDomainAdmin()
+    });
+    this.dashboardService.getAdmin().subscribe(
+        (response) => {
+          this.adminData = response;
+          this.chartData();
+          this.instanceCountInPeriodDetails = this.adminData.instanceCountInPeriodDetails;
+        }
+    )
+    const documentStyle = getComputedStyle(document.documentElement);
+    const textColor = documentStyle.getPropertyValue('--text-color');
+    const textColorSecondary = documentStyle.getPropertyValue('--text-color-secondary');
+    const surfaceBorder = documentStyle.getPropertyValue('--surface-border');
+
+
+    this.basicOptions = {
+      plugins: {
+        legend: {
+          labels: {
+            color: textColor
+          }
+        }
+      },
+      scales: {
+        y: {
+          beginAtZero: true,
+          ticks: {
+            color: textColorSecondary,
+            callback: function(value) {
+              return Number(value).toFixed(0);
+            }
+          },
+          grid: {
+            color: surfaceBorder,
+            drawBorder: false
+          }
+        },
+        x: {
+          ticks: {
+            color: textColorSecondary
+          },
+          grid: {
+            color: surfaceBorder,
+            drawBorder: false
+          }
+        }
+      }
+    };
+  }
+
+  chartData() {
+    const appNames = Object.keys(this.adminData.popularApps);
+    const appValues = Object.values(this.adminData.popularApps);
+
+    this.popularAppsChartData = {
+      labels: appNames,
+      datasets: [
+        {
+          label: 'Count of deployments',
+          data: appValues,
+          borderColor: '#42A5F5',
+          backgroundColor: ['rgba(66, 165, 245, 0.2)', 'rgba(255, 208, 208, 0.7)', 'rgba(115, 104, 193, 0.7)', 'rgba(255, 193, 130, 0.7)', 'rgba(140, 193, 104, 0.7)'],
+          fill: true
+        }
+      ]
+    };
+  }
+  formatDate(date: any): string {
+    return new Date(date).toLocaleString();
+  }
+  getDomainAdmin() {
+    this.dashboardService.getDomainAdmin(this.domainId).subscribe(
+        (response) => {
+          this.domainAdminData = response;
+          this.applicationUpgradeStatus  = this.domainAdminData.applicationUpgradeStatus;
+        }
+    )
+  }
+}
diff --git a/src/app/shared/admin-left-menu/admin-left-menu.component.css b/src/app/shared/admin-left-menu/admin-left-menu.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..afd8e55a067061f61d251e45aee4ab6787b740e5
--- /dev/null
+++ b/src/app/shared/admin-left-menu/admin-left-menu.component.css
@@ -0,0 +1,62 @@
+.menu {
+    background-color: var(--menu-color);
+    color: var(--l-text-color);
+    /*height: calc(100vh - 2rem);*/
+    /*position: static;*/
+    /*top: 0;*/
+    /*left: 0;*/
+    display: flex;
+    flex-direction: column;
+    padding: 1rem;
+  }
+  .menu ul {
+    list-style: none;
+    padding: 0;
+  }
+  .menu li {
+      padding: 10px 10px;
+      margin: 0.5rem 0;
+      border-radius: 4px;
+  }
+.menu li:hover {
+    padding: 10px 5px;
+    background: var(--background);
+    border-left: 5px solid var(--menu-pink)
+}
+.menu li.active{
+    padding: 10px 5px;
+}
+.menu li.active:hover{
+    padding: 10px 5px;
+}
+.active{
+    padding: 10px 5px;
+    background: white;
+    border-left: 5px solid var(--menu-pink)
+}
+  .menu a {
+    color: var(--l-text-color);
+    text-decoration: none;
+  }
+:host ::ng-deep .p-button{
+    padding: 8px 10px;
+    width:100%;
+    background: var(--user-button-background);
+    border: none;
+}
+:host ::ng-deep .p-button:hover{
+    background: var(--user-button-background-hover)
+}
+:host ::ng-deep .p-menu.p-menu-overlay{
+    position: static;
+    width:100%;
+    margin-bottom:5px;
+    border:none;
+}
+:host ::ng-deep .p-menu .p-menuitem > .p-menuitem-content .p-menuitem-link  {
+    text-decoration: none;
+    padding: 1.3rem;
+}
+:host ::ng-deep .p-menu .p-menuitem:not(.p-highlight):not(.p-disabled) > .p-menuitem-content:hover{
+    background:var(--user-button-background-hover);
+}
diff --git a/src/app/shared/admin-left-menu/admin-left-menu.component.html b/src/app/shared/admin-left-menu/admin-left-menu.component.html
new file mode 100644
index 0000000000000000000000000000000000000000..5f787a0b75252eaf9cf74e511a8df9c4bca5f8bc
--- /dev/null
+++ b/src/app/shared/admin-left-menu/admin-left-menu.component.html
@@ -0,0 +1,54 @@
+<!-- <div class="flex flex-column justify-content-between ">
+    <div class="menu flex">
+        <div>
+            <img src="../../../assets/images/logo-small.png" width="250px">
+        </div>
+        <div style="margin-top: 30px">
+            <nmaas-domain-filter class="drop-domain"></nmaas-domain-filter>
+        </div>
+        <ul  style="margin-top: 30px">
+            <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/dashboard']">
+                    <i class="pi pi-chart-bar" style="margin-right:10px; font-size: 15px"></i>Dashboard</a>
+            </li>
+            <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_VL_MANAGER', 'ROLE_VL_DOMAIN_ADMIN']"
+                [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/domains']">
+                    <i class="pi pi-server" style="margin-right:10px; font-size: 15px"></i>{{ 'NAVBAR.DOMAINS' | translate }}</a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/users']">
+                    <i class="pi pi-users" style="margin-right:10px; font-size: 15px"></i>{{ 'NAVBAR.USERS' | translate }}</a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/']">
+                    <i class="pi pi-th-large" style="margin-right:10px; font-size: 15px"></i>Catalog</a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/configuration']">
+                    <i class="pi pi-cog" style="margin-right:10px; font-size: 15px"></i>Settings</a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/languages']">
+                    <i class="pi pi-tags" style="margin-right:10px; font-size: 15px"></i>{{'NAVBAR.LANGUAGES' | translate }}</a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/monitor']">
+                    <i class="pi pi-chart-line" style="margin-right:10px; font-size: 15px"></i>{{ 'NAVBAR.MONITOR' | translate }}</a>
+            </li>
+
+        </ul>
+    </div>
+    <div class="menu flex">
+        <p-menu  #menu [model]="items" [popup]="true" class="test" />
+        <p-button *ngIf="!toggleAdmin" (onClick)="menu.toggle($event)" class="user-button"><i class="pi pi-user" style="font-size: 13px; margin-right:10px"></i> User</p-button>
+        <p-button *ngIf="!toggleAdmin" style="margin-top:10px"><i class="pi pi-sign-in" style="margin-right:10px; font-size: 15px"></i>Go to admin panel</p-button>
+        <p-button *ngIf="toggleAdmin"  style="margin-top:10px"><i class="pi pi-sign-in" style="margin-right:10px; font-size: 15px"></i>Go to user panel</p-button>
+    </div>
+</div> -->
+
+<div style="margin:40px">
+    <router-outlet></router-outlet>
+</div>
+
+  
diff --git a/src/app/shared/admin-left-menu/admin-left-menu.component.spec.ts b/src/app/shared/admin-left-menu/admin-left-menu.component.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..a1b9df7593065ac1bf629c4f81b7406a23fbbae7
--- /dev/null
+++ b/src/app/shared/admin-left-menu/admin-left-menu.component.spec.ts
@@ -0,0 +1,30 @@
+import { ComponentFixture, TestBed } from '@angular/core/testing';
+
+import { AdminLeftMenuComponent } from './admin-left-menu.component';
+import { MessageService } from 'primeng/api';
+import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+
+describe('AdminLeftMenuComponent', () => {
+  let component: AdminLeftMenuComponent;
+  let fixture: ComponentFixture<AdminLeftMenuComponent>;
+
+  beforeEach(async () => {
+    await TestBed.configureTestingModule({
+      declarations: [AdminLeftMenuComponent],
+      providers: [MessageService],
+      schemas: [
+                            CUSTOM_ELEMENTS_SCHEMA,
+                            NO_ERRORS_SCHEMA
+                        ]
+    })
+    .compileComponents();
+    
+    fixture = TestBed.createComponent(AdminLeftMenuComponent);
+    component = fixture.componentInstance;
+    fixture.detectChanges();
+  });
+
+  it('should create', () => {
+    expect(component).toBeTruthy();
+  });
+});
diff --git a/src/app/shared/admin-left-menu/admin-left-menu.component.ts b/src/app/shared/admin-left-menu/admin-left-menu.component.ts
new file mode 100644
index 0000000000000000000000000000000000000000..b14f03859bb36cb68b2030ef212d7b15cfcfe7dd
--- /dev/null
+++ b/src/app/shared/admin-left-menu/admin-left-menu.component.ts
@@ -0,0 +1,16 @@
+import { Component } from '@angular/core';
+import { MenuItem } from 'primeng/api';
+import { ToastContainerComponent } from '../toast-container/toast-container.component';
+import { Router } from '@angular/router';
+
+@Component({
+  selector: 'app-admin-left-menu',
+  templateUrl: './admin-left-menu.component.html',
+  styleUrl: './admin-left-menu.component.css'
+})
+export class AdminLeftMenuComponent {
+
+    constructor() {
+    }
+
+}
diff --git a/src/app/shared/admin/clusters/details/clusterdetails.component.html b/src/app/shared/admin/clusters/details/clusterdetails.component.html
index 8d086868fe9beadb049eb635e58a6153ec82e304..2b5781131cc346714da10005bda01870e480bddc 100644
--- a/src/app/shared/admin/clusters/details/clusterdetails.component.html
+++ b/src/app/shared/admin/clusters/details/clusterdetails.component.html
@@ -1,9 +1,10 @@
-<div class="panel panel-default">
-    <div class="panel-heading">{{ 'CLUSTERS.TITLE' | translate }}</div>
+<div class="background-section">
+    <h4 style="font-size:15px; font-weight: bold">{{ 'CLUSTERS.TITLE' | translate }}</h4>
     <div class="panel-body">
         <form *ngIf="cluster" (submit)="submit()" class="form-horizontal" #clusterForm="ngForm">
-            <div class="panel-default panel-heading">{{ 'CLUSTERS.INGRESS' | translate }}</div>
+            <div class="panel-default panel-heading">{{ 'CLUSTERS.INGRESS' | translate }} </div>
             <div class="panel-body">
+               
                 <div class="form-group">
                     <label for="ingresscontrollerconfigoption" class="col-sm-2 control-label">{{ 'CLUSTERS.CONTROLLER_CONFIG_OPTION' | translate }}</label>
                     <div class="col-sm-10">
@@ -243,9 +244,10 @@
             <div *ngIf="this.error" class="alert alert-danger">
                 <p>{{this.error}}</p>
             </div>
-
-            <button *ngIf="!isInMode(ComponentMode.VIEW)" [disabled]="!clusterForm.form.valid" type="submit"
-                    class="btn btn-primary">{{ 'CLUSTERS.SUBMIT_BUTTON' | translate }}</button>
+            <div class="flex justify-content-end">
+                <button *ngIf="!isInMode(ComponentMode.VIEW)" [disabled]="!clusterForm.form.valid" type="submit"
+                        class="btn btn-primary">{{ 'CLUSTERS.SUBMIT_BUTTON' | translate }}</button>
+            </div>
         </form>
     </div>
 </div>
diff --git a/src/app/shared/admin/clusters/details/clusterdetails.component.spec.ts b/src/app/shared/admin/clusters/details/clusterdetails.component.spec.ts
index 327d8c58004c56f36a2be8389fcb5be0e57e1c5f..b253949bbfdf2e2825951a1c9c53f7ea43dc7806 100644
--- a/src/app/shared/admin/clusters/details/clusterdetails.component.spec.ts
+++ b/src/app/shared/admin/clusters/details/clusterdetails.component.spec.ts
@@ -5,12 +5,18 @@ import {FormsModule} from '@angular/forms';
 import {RouterTestingModule} from '@angular/router/testing';
 import {MissingTranslationHandler, TranslateFakeLoader, TranslateLoader, TranslateModule} from '@ngx-translate/core';
 import {CustomMissingTranslationService} from '../../../../i18n/custommissingtranslation.service';
+import { ClusterManagerService } from '../../../../service/cluster-manager.service';
 
 describe('ClusterDetailsComponent', () => {
     let component: ClusterDetailsComponent;
     let fixture: ComponentFixture<ClusterDetailsComponent>;
+    let clusterService: jasmine.SpyObj<ClusterManagerService>;
+
 
     beforeEach(waitForAsync(() => {
+
+        const clusterServiceSpy = jasmine.createSpyObj('ClusterManagerService', ['sendCluster']);
+
         TestBed.configureTestingModule({
             declarations: [ ClusterDetailsComponent ],
             imports: [
@@ -22,9 +28,14 @@ describe('ClusterDetailsComponent', () => {
                         provide: TranslateLoader,
                         useClass: TranslateFakeLoader
                     }
-                })]
+                })],
+                providers: [
+                    { provide: ClusterManagerService, useValue: clusterServiceSpy } ]
         })
             .compileComponents();
+
+            clusterService = TestBed.inject(ClusterManagerService) as jasmine.SpyObj<ClusterManagerService>;
+
     }));
 
     beforeEach(() => {
diff --git a/src/app/shared/admin/clusters/details/clusterdetails.component.ts b/src/app/shared/admin/clusters/details/clusterdetails.component.ts
index 34a96c5caa337ec592690b03f488d06115dc6014..f59594415860614d488b0e3e5a60c940b7e40272 100644
--- a/src/app/shared/admin/clusters/details/clusterdetails.component.ts
+++ b/src/app/shared/admin/clusters/details/clusterdetails.component.ts
@@ -6,6 +6,8 @@ import {
     IngressResourceConfigOption,
     NamespaceConfigOption
 } from '../../../../model/cluster';
+import { ClusterManager } from '../../../../model/cluster-manager';
+import { ClusterManagerService } from '../../../../service/cluster-manager.service';
 import {BaseComponent} from '../../../common/basecomponent/base.component';
 import {Component, EventEmitter, Input, Output} from '@angular/core';
 import {Router} from '@angular/router';
@@ -37,11 +39,23 @@ export class ClusterDetailsComponent extends BaseComponent {
     @Output()
     public onDelete: EventEmitter<string> = new EventEmitter<string>();
 
-    constructor(private router: Router) {
+    constructor(private router: Router, private clusterService: ClusterManagerService) {
         super();
         this.initializeMaps();
     }
 
+    public sendCluster(event: any) {
+    console.log(event);
+    const file = event.files[0];
+    const view = new ClusterManager();
+    view.name = "test"
+    view.description="testest"
+    this.clusterService.sendCluster(file, view).subscribe(result => { 
+        console.log(result);
+    }
+    )
+    }
+
     public submit(): void {
         this.onSave.emit(this.cluster);
     }
diff --git a/src/app/shared/admin/clusters/manager/manager.component.css b/src/app/shared/admin/clusters/manager/manager.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..00fa651ed9049179e0c2b26eb4f142fb21b00d92
--- /dev/null
+++ b/src/app/shared/admin/clusters/manager/manager.component.css
@@ -0,0 +1,44 @@
+label{
+    padding-left:5px;
+    display: unset;
+    margin-bottom: 0;
+    font-weight: unset;
+}
+:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page.p-highlight{
+    background: var(--user-button-background-hover);
+}
+:host ::ng-deep .p-datatable>.p-datatable-wrapper {
+    overflow: visible;
+}
+
+:host ::ng-deep input[type=file]{
+    display:none;
+}
+:host ::ng-deep  .p-button{
+    width: unset;
+    margin-right: 5px;
+    background: var(--primary-button-color);
+    color: var(--button-text-color);
+}
+:host ::ng-deep .p-button:hover{
+    background: var(--primary-button-hover);
+    border:none;
+}
+:host ::ng-deep .p-button-label{
+    font-weight: normal;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-buttonbar{
+    border: none;
+    background: transparent;
+    margin-bottom: 10px;
+    padding: 0;
+}
+:host ::ng-deep .p-fileupload .p-fileupload-content{
+    border: none;
+    padding: 0;
+    border-radius: 3px;
+
+}
+:host ::ng-deep .p-fileupload-content .p-progressbar{
+    display: none;
+}
diff --git a/src/app/shared/admin/clusters/manager/manager.component.html b/src/app/shared/admin/clusters/manager/manager.component.html
new file mode 100644
index 0000000000000000000000000000000000000000..cf693202ea648e7e341fc231b6df0e9becbdfcce
--- /dev/null
+++ b/src/app/shared/admin/clusters/manager/manager.component.html
@@ -0,0 +1,115 @@
+<div style="display: flex; align-items: center;  margin-top:20px">
+    <div style="margin-right:20px">
+        <div >
+            <button class="btn btn-primary" (click)="openModal()">New Cluster</button>
+        </div>
+    </div>
+    <div class="flex" style="margin-right:20px">
+        
+    </div>
+</div>
+
+    <h4 class="header">{{ 'CLUSTERS.CONFIGURATION' | translate }}</h4>
+    
+<div class="background-section">
+    <p-table
+    [value]="clusters"
+    [paginator]="true"
+    [rows]="maxItemsOnPage"
+    [rowsPerPageOptions]="[15, 20, 25, 30, 50]"
+    [responsiveLayout]="'scroll'">
+        <ng-template pTemplate="header">
+            <tr>
+                <th  pSortableColumn="id" id="id"> {{ 'CLUSTERS.ID' | translate }}
+                    <p-sortIcon field="id"></p-sortIcon>
+                </th>
+                <th pSortableColumn="name" id="name"> {{ 'CLUSTERS.NAME' | translate }}
+                    <p-sortIcon field="name"></p-sortIcon>
+                </th>
+                <th pSortableColumn="codename" id="codename"> {{ 'CLUSTERS.CODENAME' | translate }}
+                    <p-sortIcon field="codename"></p-sortIcon>
+                </th>
+                <th pSortableColumn="state" id="state"> {{ 'CLUSTERS.STATE' | translate }}
+                    <p-sortIcon field="state"></p-sortIcon>
+                </th>
+                <th pSortableColumn="creationDate" id="creationDate"> {{ 'CLUSTERS.CREATION_DATE' | translate }}
+                    <p-sortIcon field="creationDate"></p-sortIcon>
+                </th>
+                <th pSortableColumn="modificationDate" id="modificationDate"> {{ 'CLUSTERS.MODIFICATION_DATE' | translate }}
+                    <p-sortIcon field="modificationDate"></p-sortIcon>
+                </th>
+                <th></th>
+            </tr>
+        </ng-template>
+        <ng-template pTemplate="body" let-cluster>
+            <tr>
+                <td  [routerLink]="[cluster.id]">{{cluster.id}}</td>
+                <td>{{cluster.name}}</td>
+                <td>{{cluster.codename}}</td>
+                <td>{{('CLUSTERS.'+cluster.state.toString().toUpperCase() ) | translate}}</td>
+                <td>{{cluster.creationDate | date: 'dd-MM-yyyy HH:mm'}}</td>
+                <td>{{cluster.modificationDate | date: 'dd-MM-yyyy HH:mm'}}</td>
+                <td class="text-right">
+                    <span class="dropdown">
+                            <a style="display: inline-block" class="dropdown-toggle" aria-expanded="false" aria-haspopup="true" data-toggle="dropdown" href="#" role="button">
+                                <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
+                            </a>
+                            <ul class="dropdown-menu pull-right-drop" >
+                                <li><a [routerLink]="[ cluster.id]" class="">
+                                    {{ 'CLUSTERS.DETAILS' | translate }}</a>
+                                </li>
+                            </ul>
+                    </span>
+                </td>
+            </tr>
+        </ng-template>
+    </p-table>
+
+</div>
+
+
+<nmaas-modal >
+    <div class="nmaas-modal-header">{{'CLUSTERS.CONNECT_CLUSTER' | translate}}</div>
+    <div class="nmaas-modal-body">
+        <div class="flex flex-column">
+            <div class="mt-4">
+                <label for="name">{{'CLUSTERS.NAME' | translate}}</label>
+                <input id="name" type="text" class="form-control" [(ngModel)]="addedCluster.name" [ngModelOptions]="{standalone: true}">
+            </div>
+
+            <div class="mt-4">
+                <label for="desc">{{'CLUSTERS.DESCRIPTION' | translate}}</label>
+                <input id="desc" type="text" class="form-control" [(ngModel)]="addedCluster.description" [ngModelOptions]="{standalone: true}">
+            </div>
+            <div class="mt-4">
+                <label for="contactEmail">{{'CLUSTERS.CONTACT_MAIL' | translate}}</label>
+                <input id="contactEmail" type="text" class="form-control" [(ngModel)]="addedCluster.contactEmail" [ngModelOptions]="{standalone: true}">
+            </div>
+
+
+            <div class="mt-4">
+                <label for="name">{{'CLUSTERS.DOMAIN' | translate}}</label>
+                <select id="domain" #domainSelect class="form-control" (change)="onDomainSelection(domainSelect.value)">
+                    <option *ngFor="let domain of domains" [value]="domain.name"
+                        >{{domain.name}}
+                    </option>
+                </select>            
+            </div>
+
+
+            <div class="card flex justify-content-center mt-4" >
+                <p-fileUpload name="json" (onUpload)="saveFile($event)" customUpload="true" [draggable]="true"  pTooltip="Upload file is required before save" 
+             (uploadHandler)="saveFile($event)" [multiple]="false" accept=".yaml" maxFileSize="1000000">
+         
+                </p-fileUpload>
+            </div>
+            </div>
+    </div>
+    <div class="nmaas-modal-footer">
+      <button type="button" class="btn btn-primary" [disabled]="updatedFile === null || addedCluster?.name === null || addedCluster?.description === null"(click)="closeModalAndSaveCluster()" 
+      pTooltip="Upload file is required before save" showDelay="2000" >{{'CLUSTERS.SAVE' | translate}}</button>
+      <button type="button" class="btn btn-secondary"
+                    (click)="this.modal.hide()">{{'UNDEPLOY_MODAL.CANCEL_BUTTON' | translate}}</button>
+    
+    </div>
+  </nmaas-modal>
diff --git a/src/app/shared/admin/clusters/manager/manager.component.spec.ts b/src/app/shared/admin/clusters/manager/manager.component.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..a0d38438323ff1ce2d736bdc4df03ba3f6460054
--- /dev/null
+++ b/src/app/shared/admin/clusters/manager/manager.component.spec.ts
@@ -0,0 +1,146 @@
+import { ComponentFixture, TestBed } from '@angular/core/testing';
+import { HttpClientTestingModule } from '@angular/common/http/testing';
+import { ClusterManagerComponent } from './manager.component';
+import { ClusterManagerService } from '../../../../service/cluster-manager.service';
+import { of } from 'rxjs';
+import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+import { TranslateFakeLoader, TranslateLoader, TranslateModule } from '@ngx-translate/core';
+import { ClusterManager } from '../../../../model/cluster-manager';
+import { ModalComponent } from '../../../modal';
+
+describe('ClusterManagerComponent', () => {
+  let component: ClusterManagerComponent;
+  let fixture: ComponentFixture<ClusterManagerComponent>;
+  let clusterService: jasmine.SpyObj<ClusterManagerService>;
+  let mockClusters: any[];
+  let mockModal: jasmine.SpyObj<ModalComponent>;
+
+
+  beforeEach(async () => {
+    const clusterServiceSpy = jasmine.createSpyObj('ClusterManagerService', ['getAllClusters', 'sendCluster']);
+    const mockModalSpy = jasmine.createSpyObj('ModalComponent', ['hide']);
+    mockModalSpy.hide.and.returnValue(null);
+
+    mockClusters = [
+      {
+        id: 1,
+        name: 'Cluster A',
+        codename: 'CodeA',
+        creationDate: new Date('2025-01-01'),
+        modificationDate: new Date('2025-02-01'),
+        pathConfigFile: '/path/to/configA.yaml',
+        description: 'Description A',
+        clusterConfigFile: 'ConfigA',
+        ingress: {
+          id: 1,
+          controllerConfigOption: 'OptionA',
+          controllerChartName: 'ChartA',
+          controllerChartArchive: 'ArchiveA',
+          resourceConfigOption: 'ResourceA',
+          externalServiceDomain: 'domainA.com',
+          tlsSupported: true,
+          supportedIngressClass: 'ClassA',
+          certificateConfigOption: 'CertOptionA',
+          issuerOrWildcardName: 'WildcardA',
+          ingressPerDomain: false,
+          publicIngressClass: 'PublicClassA',
+          publicServiceDomain: 'public.domainA.com'
+        },
+        deployment: {
+          smtpServerHostname: 'smtp.domainA.com',
+          smtpServerPort: '587',
+          smtpServerUsername: 'userA',
+          smtpServerPassword: 'passwordA',
+          defaultNamespace: 'namespaceA',
+          defaultStorageClass: 'storageClassA',
+          id: 1,
+          namespaceConfigOption: 'OptionA',
+          forceDedicatedWorkers: true
+        },
+        externalNetworks: [
+          {
+            assigned: true,
+            assignedSince: '2025-01-01',
+            assignedTo: 'UserA',
+            externalIp: '192.168.1.1',
+            externalNetwork: 'NetworkA',
+            externalNetworkMaskLength: 24,
+            id: 1
+          }
+        ]
+      },
+      {
+        id: 2,
+        name: 'Cluster B',
+        codename: 'CodeB',
+        creationDate: new Date('2025-01-15'),
+        modificationDate: new Date('2025-02-15'),
+        pathConfigFile: '/path/to/configB.yaml',
+        description: 'Description B',
+        clusterConfigFile: 'ConfigB',
+        ingress: 'IngressB',
+        deployment: 'DeploymentB',
+        externalNetworks: []
+      }
+    ];
+
+    clusterServiceSpy.getAllClusters.and.returnValue(of(mockClusters));
+
+    await TestBed.configureTestingModule({
+      declarations: [ClusterManagerComponent],
+      imports: [HttpClientTestingModule,
+        TranslateModule.forRoot({
+                            loader: {
+                                provide: TranslateLoader,
+                                useClass: TranslateFakeLoader
+                            }
+                        }),
+      ],
+      providers: [
+        { provide: ClusterManagerService, useValue: clusterServiceSpy }
+      ],
+       schemas: [NO_ERRORS_SCHEMA, CUSTOM_ELEMENTS_SCHEMA],
+    }).compileComponents();
+
+    fixture = TestBed.createComponent(ClusterManagerComponent);
+    component = fixture.componentInstance;
+    component.modal = mockModalSpy;
+    clusterService = TestBed.inject(ClusterManagerService) as jasmine.SpyObj<ClusterManagerService>;
+    fixture.detectChanges();
+  });
+
+  it('should create the component', () => {
+    expect(component).toBeTruthy();
+  });
+
+  it('should call getAllClusters on initialization', () => {
+    component.getAllClusters();
+    expect(clusterService.getAllClusters).toHaveBeenCalled();
+    expect(component.clusters).toEqual(mockClusters);
+  });
+
+  it('should call saveFile and store the uploaded file', () => {
+    const mockFile = new File(['test content'], 'test.yaml', { type: 'application/x-yaml' });
+    const mockEvent = { files: [mockFile] };
+
+    component.saveFile(mockEvent);
+
+    expect(component.updatedFile).toBe(mockFile);
+    expect(component.updatedFile.name).toBe('test.yaml');
+  });
+
+  it('should call closeModalAndSaveCluster and reset state after saving', () => {
+    const mockFile = new File(['test content'], 'test.yaml', { type: 'application/x-yaml' });
+    // const mockCluster = { id: 3, name: 'Cluster C', codename: 'CodeC' };
+    component.updatedFile = mockFile;
+    component.addedCluster = mockClusters[0];
+
+    clusterService.sendCluster.and.returnValue(of(mockClusters[0]));
+
+    component.closeModalAndSaveCluster();
+
+    expect(clusterService.sendCluster).toHaveBeenCalledWith(mockFile, mockClusters[0]);
+    // expect(component.updatedFile).toBeNull();
+    // expect(component.addedCluster).toEqual(new ClusterManager());
+  });
+});
\ No newline at end of file
diff --git a/src/app/shared/admin/clusters/manager/manager.component.ts b/src/app/shared/admin/clusters/manager/manager.component.ts
new file mode 100644
index 0000000000000000000000000000000000000000..2e9df32629c98c7ed0181231b3fe064f3da72753
--- /dev/null
+++ b/src/app/shared/admin/clusters/manager/manager.component.ts
@@ -0,0 +1,77 @@
+import { Component, ViewChild } from '@angular/core';
+import { ClusterManagerService } from '../../../../service/cluster-manager.service';
+import { ClusterManager } from '../../../../model/cluster-manager';
+import { ModalComponent } from '../../../modal';
+import { DomainService } from '../../../../service';
+
+@Component({
+  selector: 'app-manager',
+  templateUrl: './manager.component.html',
+  styleUrl: './manager.component.css'
+})
+export class ClusterManagerComponent {
+
+  public clusters: ClusterManager[] = [];
+
+  public addedCluster: ClusterManager = new ClusterManager();
+  public updatedFile : File = null;
+  public maxItemsOnPage = 15;
+
+  public domains = [];
+
+    @ViewChild(ModalComponent, { static: true })
+    public modal: ModalComponent;
+
+  constructor(private clusterService: ClusterManagerService,
+              private domainService: DomainService
+  ) {
+    this.getAllClusters();
+    this.domainService.getAllBase().subscribe(result => {
+      this.domains = result.filter(d => d.id !== this.domainService.getGlobalDomainId());
+    });
+  }
+
+ public saveFile(event: any) {
+    console.log(event);
+    this.updatedFile =event.files[0];     
+    }
+
+public getAllClusters() {
+    this.clusterService.getAllClusters().subscribe(result => { 
+          console.log(result);
+            this.clusters = result;
+        })
+      }
+
+public closeModalAndSaveCluster() {
+  this.clusterService.sendCluster(this.updatedFile, this.addedCluster).subscribe(result => { 
+    console.log(result);
+    this.getAllClusters();
+    this.modal.hide();
+    this.updatedFile = null;
+    this.addedCluster = new ClusterManager();
+  }, error => {
+    console.error(error);
+    
+  }
+)
+}
+
+
+public onDomainSelection(event: any) {
+
+    console.log(event);
+    this.addedCluster.domainNames = [event]
+  
+}
+
+public openModal() {
+  if(this.domains.length > 0) {
+    this.addedCluster.domainNames = [this.domains[0].name];
+  }
+  this.modal.show();
+}
+
+
+
+}
diff --git a/src/app/shared/admin/clusters/managerdetails/managerdetails.component.css b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/src/app/shared/admin/clusters/managerdetails/managerdetails.component.html b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.html
new file mode 100644
index 0000000000000000000000000000000000000000..9f7c872af6f0fe143d19d6bf09102cd51986309c
--- /dev/null
+++ b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.html
@@ -0,0 +1,377 @@
+<div class="">
+    <div class="background-section">  
+    <h4 style="font-size:15px; font-weight: bold">{{ 'CLUSTERS.TITLE_GENERAL' | translate }}</h4>
+
+    <div class="panel-body">
+        <form *ngIf="cluster" (submit)="submit()" class="form-horizontal" #clusterFormGeneral="ngForm">
+            <div class="panel-default panel-heading">{{ 'CLUSTERS.GENERAL' | translate }} </div>
+            <div class="panel-body">
+               
+                <div class="form-group">
+                    <label for="clusterId" class="col-sm-2 control-label">{{ 'CLUSTERS.ID' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="clusterId" name="clusterId"
+                                   [(ngModel)]="cluster.id" [disabled]="true">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="clusterName" class="col-sm-2 control-label">{{ 'CLUSTERS.NAME' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="clusterName" name="clusterName"
+                                   [(ngModel)]="cluster.name" [disabled]="false">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="ClusterCodeName" class="col-sm-2 control-label">{{ 'CLUSTERS.CODENAME' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="ClusterCodeName" name="ClusterCodeName"
+                                   [(ngModel)]="cluster.codename" [disabled]="false">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="clusterDescription" class="col-sm-2 control-label">{{ 'CLUSTERS.DESCRIPTION' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="clusterDescription" name="clusterDescription"
+                                   [(ngModel)]="cluster.description" [disabled]="false">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="clusterCreationDate" class="col-sm-2 control-label">{{ 'CLUSTERS.DOMAIN' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <select id="domain" #domainSelect class="form-control" (change)="onDomainSelection(domainSelect.value)">
+                                <option *ngFor="let domain of domains" [selected]="cluster.domainNames[0] === domain.name" [value]="domain.name"
+                                    >{{domain.name}}
+                                </option>
+                            </select>         
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="state" class="col-sm-2 control-label">{{ 'CLUSTERS.STATE' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="state" name="state"
+                                   placeholder="{{'CLUSTERS.' + cluster.state.toString().toUpperCase()| translate}}" [disabled]="true">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="state" class="col-sm-2 control-label">{{ 'CLUSTERS.STATE_SINCE' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="state" name="state"
+                                   [ngModel]="formatDate(cluster.currentStateSince)" [disabled]="true">
+                        </div>
+                    </div>
+                </div>
+
+
+                <div class="form-group">
+                    <label for="clusterCreationDate" class="col-sm-2 control-label">{{ 'CLUSTERS.CREATION_DATE' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="clusterCreationDate" name="clusterCreationDate"
+                                   [ngModel]="formatDate(cluster.creationDate)" [disabled]="true">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="clusterModificationnDate" class="col-sm-2 control-label">{{ 'CLUSTERS.MODIFICATION_DATE' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="clusterModificationnDate" name="clusterModificationnDate"
+                                   [ngModel]="formatDate(cluster.modificationDate) " [disabled]="true">
+                        </div>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="clusterPathConfigFile" class="col-sm-2 control-label">{{ 'CLUSTERS.PATH_TO_CONFIG' | translate }}</label>
+                    <div class="col-sm-10">
+                        <div class="col-sm-10">
+                            <input type="text" class="form-control" id="clusterPathConfigFile" name="clusterPathConfigFile"
+                                   [(ngModel)]="cluster.pathConfigFile" [disabled]="true">
+                        </div>
+                    </div>
+                </div>
+
+            </div>
+        </form>
+    </div>
+</div>
+</div>
+
+<div class="">
+    <div class="background-section">  
+    <h4 style="font-size:15px; font-weight: bold">{{ 'CLUSTERS.TITLE' | translate }}</h4>
+    <div class="panel-body">
+        <form *ngIf="cluster" (submit)="submit()" class="form-horizontal" #clusterForm="ngForm">
+            <div class="panel-default panel-heading">{{ 'CLUSTERS.INGRESS' | translate }} </div>
+            <div class="panel-body">
+               
+                <div class="form-group">
+                    <label for="ingresscontrollerconfigoption" class="col-sm-2 control-label">{{ 'CLUSTERS.CONTROLLER_CONFIG_OPTION' | translate }}</label>
+                    <div class="col-sm-10" *ngIf="controllerConfigOption">
+                        <select class="form-control" id="ingresscontrollerconfigoption" name="ingresscontrollerconfigoption"
+                                [(ngModel)]="cluster.ingress.controllerConfigOption" [disabled]="" required>
+                            <option *ngFor="let configOption of getKeys(controllerConfigOption)" [value]="controllerConfigOption.get(configOption)">{{configOption}}</option>
+                        </select>
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="suportedingressclass" class="col-sm-2 control-label">{{ 'CLUSTERS.SUPPORTED_INGRESS_CLASS' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="suportedingressclass" name="suportedingressclass"
+                               [(ngModel)]="cluster.ingress.supportedIngressClass" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="publicingressclass" class="col-sm-2 control-label">{{ 'CLUSTERS.PUBLIC_INGRESS_CLASS' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="publicingressclass" name="publicingressclass"
+                               [(ngModel)]="cluster.ingress.publicIngressClass" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingresscontrollerchartname" class="col-sm-2 control-label">{{ 'CLUSTERS.CONTROLLER_CHART_NAME' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="ingresscontrollerchartname" name="ingresscontrollerchartname"
+                               [(ngModel)]="cluster.ingress.controllerChartName" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingresscontrollerchartarchive" class="col-sm-2 control-label">{{ 'CLUSTERS.CONTROLLER_CHART_ARCHIVE' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="ingresscontrollerchartarchive" name="ingresscontrollerchartarchive"
+                               [(ngModel)]="cluster.ingress.controllerChartArchive" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingressresourceconfigoption" class="col-sm-2 control-label">{{ 'CLUSTERS.RESOURCE_CONFIG_OPTION' | translate }}</label>
+                    <div class="col-sm-10">
+                        <select class="form-control" id="ingressresourceconfigoption" name="ingressresourceconfigoption"
+                                [(ngModel)]="cluster.ingress.resourceConfigOption" [disabled]="" required>
+                            <option *ngFor="let configOption of getKeys(resourceConfigOption)" [value]="resourceConfigOption.get(configOption)">{{configOption}}</option>
+                        </select>
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingressexternalservicedomain" class="col-sm-2 control-label">{{ 'CLUSTERS.EXTERNAL_SERVICE_DOMAIN' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="ingressexternalservicedomain" name="ingressexternalservicedomain"
+                               [(ngModel)]="cluster.ingress.externalServiceDomain" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingresspublicservicedomain" class="col-sm-2 control-label">{{ 'CLUSTERS.PUBLIC_SERVICE_DOMAIN' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="ingresspublicservicedomain" name="ingresspublicservicedomain"
+                               [(ngModel)]="cluster.ingress.publicServiceDomain" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingresstlssupported" class="col-sm-2 control-label">{{ 'CLUSTERS.TLS_SUPPORTED' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="checkbox" id="ingresstlssupported" name="ingresstlssupported"
+                               [(ngModel)]="cluster.ingress.tlsSupported" [checked]="cluster.ingress.tlsSupported == true" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group" *ngIf="cluster.ingress.tlsSupported">
+                    <label for="ingresscertificateconfigoption" class="col-sm-2 control-label">{{ 'CLUSTERS.INGRESS_CERTIFICATE_CONFIG_OPTION' | translate }}</label>
+                    <div class="col-sm-10">
+                        <select class="form-control" id="ingresscertificateconfigoption" name="ingresscertificateconfigoption"
+                        [(ngModel)]="cluster.ingress.certificateConfigOption" [disabled]="" required>
+                        <option *ngFor="let configOption of getKeys(certificateConfigOption)" [value]="certificateConfigOption.get(configOption)">{{configOption}}</option>
+                        </select>
+                    </div>
+                </div>
+                <div class="form-group" *ngIf="cluster.ingress.tlsSupported">
+                    <label for="ingressissuerorwildcardname" class="col-sm-2 control-label">{{ 'CLUSTERS.INGRESS_ISSUER_OR_WILDCARD_NAME' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="ingressissuerorwildcardname" name="ingressissuerorwildcardname"
+                               [(ngModel)]="cluster.ingress.issuerOrWildcardName" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="ingressperdomain" class="col-sm-2 control-label">{{ 'CLUSTERS.INGRESS_PER_DOMAIN' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="checkbox" id="ingressperdomain" name="ingressperdomain"
+                               [(ngModel)]="cluster.ingress.ingressPerDomain" [checked]="cluster.ingress.ingressPerDomain == true" [disabled]="">
+                    </div>
+                </div>
+            </div>
+
+            <div class="panel-default panel-heading">{{ 'CLUSTERS.DEPLOYMENT' | translate }}</div>
+            <div class="panel-body">
+                <div class="form-group">
+                    <label for="deploymentnamespaceconfigoption" class="col-sm-2 control-label">{{ 'CLUSTERS.NAMESPACE_CONFIG_OPTION' | translate }}</label>
+                    <div class="col-sm-10" *ngIf="controllerConfigOption">
+                        <select class="form-control" id="deploymentnamespaceconfigoption" name="deploymentnamespaceconfigoption"
+                                [(ngModel)]="cluster.deployment.namespaceConfigOption" [disabled]="" required>
+                            <option *ngFor="let configOption of getKeys(namespaceConfigOption)" [value]="namespaceConfigOption.get(configOption)">{{configOption}}</option>
+                        </select>
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="deploymentdefaultnamespace" class="col-sm-2 control-label">{{ 'CLUSTERS.DEFAULT_NAMESPACE' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="deploymentdefaultnamespace" name="deploymentdefaultnamespace" #namespace="ngModel" pattern="[a-z-]*" maxlength="64"
+                               [(ngModel)]="cluster.deployment.defaultNamespace" [disabled]="">
+                        <div *ngIf="namespace.invalid && (namespace.dirty || namespace.touched)" class="alert alert-danger">
+                            <div *ngIf="namespace.errors.pattern">{{ 'CLUSTERS.NAMESPACE_PATTERN_VALIDATION_MESSAGE' | translate }}</div>
+                            <div *ngIf="namespace.errors.maxlength">{{ 'CLUSTERS.NAMESPACE_MAX_LENGTH_VALIDATION_MESSAGE' | translate }}</div>
+                        </div>
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="deploymentdefaultstorageclass" class="col-sm-2 control-label">{{ 'CLUSTERS.DEFAULT_STORAGE_CLASS' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="deploymentdefaultstorageclass" name="deploymentdefaultstorageclass"
+                               [(ngModel)]="cluster.deployment.defaultStorageClass" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="forceDedicatedWorkers" class="col-sm-2 control-label">{{ 'CLUSTERS.FORCE_DEDICATED_WORKERS' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="checkbox" id="forceDedicatedWorkers" name="forceDedicatedWorkers"
+                               [(ngModel)]="cluster.deployment.forceDedicatedWorkers" [checked]="cluster.deployment.forceDedicatedWorkers == true" [disabled]="isInMode(ComponentMode.VIEW)">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="smtpServerHostname" class="col-sm-2 control-label">{{ 'CLUSTERS.SMTP_SERVER_HOSTNAME' | translate }}: </label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="smtpServerHostname" name="smtpServerHostname"
+                               [(ngModel)]="cluster.deployment.smtpServerHostname" [disabled]="" required #smtpServerHostname="ngModel">
+                        <div class="alert alert-danger" *ngIf="smtpServerHostname.invalid && (smtpServerHostname.dirty || smtpServerHostname.touched)">
+                            <div *ngIf="smtpServerHostname.errors.required">SMTP server hostname is required</div>
+                        </div>
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="smtpServerPort" class="col-sm-2 control-label">{{ 'CLUSTERS.SMTP_SERVER_PORT' | translate }}: </label>
+                    <div class="col-sm-10">
+                        <input type="number" class="form-control no-spin" id="smtpServerPort" name="smtpServerPort"
+                               [(ngModel)]="cluster.deployment.smtpServerPort" [disabled]="" required #smtpServerPort="ngModel">
+                        <div class="alert alert-danger" *ngIf="smtpServerPort.invalid && (smtpServerPort.dirty || smtpServerPort.touched)">
+                            <div *ngIf="smtpServerPort.errors.required">SMTP server port is required</div>
+                        </div>
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="smtpServerUsername" class="col-sm-2 control-label">{{ 'CLUSTERS.SMTP_SERVER_USERNAME' | translate }}: </label>
+                    <div class="col-sm-10">
+                        <input type="text" class="form-control" id="smtpServerUsername" name="smtpServerUsername"
+                               [(ngModel)]="cluster.deployment.smtpServerUsername" [disabled]="">
+                    </div>
+                </div>
+                <div class="form-group">
+                    <label for="smtpServerPass" class="col-sm-2 control-label">{{ 'CLUSTERS.SMTP_SERVER_PASSWORD' | translate }}: </label>
+                    <div class="col-sm-10">
+                        <input type="password" class="form-control" id="smtpServerPass" name="smtpServerPass"
+                               [(ngModel)]="cluster.deployment.smtpServerPassword" [disabled]="">
+                    </div>
+                </div>
+            </div>
+
+            <!-- Hide external networks section -->
+            <div [hidden]="true" class="panel-default panel-heading">{{ 'CLUSTERS.EXTERNAL_NETWORKS' | translate }}</div>
+            <div [hidden]="true" class="panel-body">
+                <table class="table table-hover table-condensed" aria-describedby="Clusters details table">
+                    <thead>
+                    <tr>
+                        <th scope="col">{{ 'CLUSTERS.ADDRESS' | translate }}</th>
+                        <th scope="col">{{ 'CLUSTERS.NETWORK' | translate }}</th>
+                        <th scope="col">{{ 'CLUSTERS.NETMASK_LENGTH' | translate }}</th>
+                        <th scope="col">{{ 'CLUSTERS.ASSIGNED' | translate }}</th>
+                        <th scope="col">{{ 'CLUSTERS.ASSIGNED_SINCE' | translate }}</th>
+                        <th scope="col">{{ 'CLUSTERS.ASSIGNED_TO' | translate }}</th>
+                        <th scope="col">&nbsp;</th>
+                    </tr>
+                    </thead>
+                    <tbody>
+                    <ng-template ngFor let-extnetwork [ngForOf]="cluster.externalNetworks" let-i="index" [ngForTrackBy]="">
+                        <tr>
+                            <td>
+                                <input type="text" class="form-control" [name]="'extnetextip'+i"
+                                       [(ngModel)]="extnetwork.externalIp" [disabled]="" required pattern="[0-9.]*" #ip="ngModel">
+                                <div class="alert alert-danger" *ngIf="ip.invalid && (ip.dirty || ip.touched)">
+                                    <div *ngIf="ip.errors.required">{{ 'CLUSTERS.IP_REQUIRED_MESSAGE' | translate }}</div>
+                                    <div *ngIf="ip.errors.pattern">{{ 'CLUSTERS.IP_VALIDATION_MESSAGE' | translate }}</div>
+                                </div>
+                            </td>
+                            <td>
+                                <input type="text" class="form-control" [name]="'extnetextnet'+i"
+                                       [(ngModel)]="extnetwork.externalNetwork" [disabled]="" required pattern="[0-9.]*" #network="ngModel">
+                                <div class="alert alert-danger" *ngIf="network.invalid && (network.dirty || network.touched)">
+                                    <div *ngIf="network.errors.required">{{ 'CLUSTERS.NETWORK_REQUIRED_MESSAGE' | translate }}</div>
+                                    <div *ngIf="network.errors.pattern">{{ 'CLUSTERS.NETWORK_ADDRESS_VALIDATION_MESSAGE' | translate }}</div>
+                                </div>
+                            </td>
+                            <td>
+                                <input type="text" class="form-control" [name]="'extnetmask'+i"
+                                       [(ngModel)]="extnetwork.externalNetworkMaskLength" [disabled]="" min="0" max="32" #mask="ngModel">
+                                <div class="alert alert-danger" *ngIf="mask.invalid && (mask.dirty || mask.touched)">
+                                    <div *ngIf="mask.errors.min || mask.errors.max">{{ 'CLUSTERS.MASK_VALIDATION_MESSAGE' | translate }}</div>
+                                </div>
+                            </td>
+                            <td>
+                                <input type="checkbox" [name]="'extnetassigned'+i"
+                                       [(ngModel)]="extnetwork.assigned" [checked]="extnetwork.assigned == true" [disabled]="">
+                            </td>
+                            <td>
+                                <input type="text" class="form-control" [name]="'extnetassince'+i"
+                                       [(ngModel)]="extnetwork.assignedSince" [disabled]=" !extnetwork.assigned">
+                            </td>
+                            <td>
+                                <input type="text" class="form-control" [name]="'extnetassto'+i"
+                                       [(ngModel)]="extnetwork.assignedTo" [disabled]=" !extnetwork.assigned">
+                            </td>
+                            <td class="text-right">
+                                <button *ngIf="" type="button" class="btn btn-sm btn-danger"
+                                        (click)="removeNetwork(extnetwork.id)">{{ 'CLUSTERS.REMOVE_BUTTON' | translate }}
+                                </button>
+                            </td>
+                        </tr>
+                    </ng-template>
+                    <tr *ngIf="">
+                        <td></td><td></td><td></td><td></td><td></td><td></td>
+                        <td>
+                            <button type="button" class="btn btn-sm btn-secondary"
+                                    (click)="addNetwork()">{{ 'CLUSTERS.ADD_BUTTON' | translate }}
+                            </button>
+                        </td>
+                    </tr>
+                    </tbody>
+                </table>
+            </div>
+
+            <div *ngIf="this.error" class="alert alert-danger">
+                <p>{{this.error}}</p>
+            </div>
+
+            <div class="flex justify-content-end">
+                <button [disabled]="!clusterForm.form.valid" type="submit" class="btn btn-primary"
+                        type="submit">{{ 'PORTAL_CONFIGURATION.SUBMIT_BUTTON' | translate }}</button>
+            </div>
+            <!-- <button 
+                    class="btn btn-primary">{{ 'CLUSTERS.SUBMIT_BUTTON' | translate }}</button> -->
+        </form>
+    </div>
+</div>
+</div>
diff --git a/src/app/shared/admin/clusters/managerdetails/managerdetails.component.spec.ts b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..b9b928804c25a5b8ba4817fc5bab13369cef47cf
--- /dev/null
+++ b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.spec.ts
@@ -0,0 +1,196 @@
+import { ComponentFixture, TestBed, waitForAsync } from '@angular/core/testing';
+import { ClusterManagerDetailsComponent } from './managerdetails.component';
+import { ClusterManagerService } from '../../../../service/cluster-manager.service';
+import { ActivatedRoute, Router } from '@angular/router';
+import { CommonModule, DatePipe } from '@angular/common';
+import { of } from 'rxjs';
+import { ClusterManager } from '../../../../model/cluster-manager';
+import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+import { TranslateFakeLoader, TranslateLoader, TranslateModule } from '@ngx-translate/core';
+import { FormsModule } from '@angular/forms';
+import { IngressCertificateConfigOption, IngressControllerConfigOption, IngressResourceConfigOption, NamespaceConfigOption } from '../../../../model/cluster';
+import { HttpClientTestingModule } from '@angular/common/http/testing';
+
+describe('ClusterManagerDetailsComponent', () => {
+  let component: ClusterManagerDetailsComponent;
+  let fixture: ComponentFixture<ClusterManagerDetailsComponent>;
+  let clusterService: jasmine.SpyObj<ClusterManagerService>;
+  let mockRouter: jasmine.SpyObj<Router>;
+  let mockActivatedRoute: any;
+
+  const mockCluster: ClusterManager = {
+    id: 1,
+    name: 'Test Cluster',
+    state: "UP",
+    currentStateSince: new Date('2025-01-01'),
+      contactEmail: "test@test.test",
+    description: 'Test Description',
+    externalNetworks: [],
+    creationDate: new Date('2025-01-01'),
+    modificationDate: new Date('2025-02-01'),
+    codename: 'test-cluster',
+    pathConfigFile: '/path/to/config.yaml',
+    clusterConfigFile: 'Config',
+    domainNames: ["test"],
+    ingress: {
+        id: 1,
+        controllerConfigOption: IngressControllerConfigOption.USE_EXISTING,
+        controllerChartName: 'nginx-ingress',
+        controllerChartArchive: 'nginx-ingress-1.0.0.tgz',
+        resourceConfigOption: IngressResourceConfigOption.DEPLOY_FROM_CHART,
+        externalServiceDomain: 'example.com',
+        tlsSupported: true,
+        supportedIngressClass: 'nginx',
+        certificateConfigOption: IngressCertificateConfigOption.USE_LETSENCRYPT,
+        issuerOrWildcardName: 'letsencrypt',
+        ingressPerDomain: false,
+        publicIngressClass: 'nginx-public',
+        publicServiceDomain: 'public.example.com'
+      },
+      deployment: {
+        id: 1,
+        smtpServerHostname: 'smtp.example.com',
+        smtpServerPort: '587',
+        smtpServerUsername: 'user@example.com',
+        smtpServerPassword: 'password',
+        defaultNamespace: 'default',
+        defaultStorageClass: 'standard',
+        namespaceConfigOption: NamespaceConfigOption.USE_DEFAULT_NAMESPACE,
+        forceDedicatedWorkers: false
+      }
+  };
+
+  beforeEach(waitForAsync(() => {
+    const clusterServiceSpy = jasmine.createSpyObj('ClusterManagerService', ['getClusterDetails', 'sendCluster', 'updateCluster']);
+    const routerSpy = jasmine.createSpyObj('Router', ['navigate']);
+    mockActivatedRoute = {
+      params: of({ id: 1 })
+    };
+
+    
+
+    TestBed.configureTestingModule({
+      declarations: [ClusterManagerDetailsComponent],
+      imports: [FormsModule,
+                CommonModule,
+                HttpClientTestingModule,
+                      TranslateModule.forRoot({
+                          loader: {
+                              provide: TranslateLoader,
+                              useClass: TranslateFakeLoader
+                          }
+                      }),
+                  ],
+      providers: [
+        { provide: ClusterManagerService, useValue: clusterServiceSpy },
+        { provide: Router, useValue: routerSpy },
+        { provide: ActivatedRoute, useValue: mockActivatedRoute },
+        DatePipe
+      ],
+      schemas: [NO_ERRORS_SCHEMA, CUSTOM_ELEMENTS_SCHEMA]
+    }).compileComponents();
+
+    clusterService = TestBed.inject(ClusterManagerService) as jasmine.SpyObj<ClusterManagerService>;
+    mockRouter = TestBed.inject(Router) as jasmine.SpyObj<Router>;
+  }));
+
+  beforeEach(() => {
+    fixture = TestBed.createComponent(ClusterManagerDetailsComponent);
+    component = fixture.componentInstance;
+
+    component.controllerConfigOption = new Map<string, IngressControllerConfigOption>();
+    component.resourceConfigOption = new Map<string, IngressResourceConfigOption>();
+    component.namespaceConfigOption = new Map<string, NamespaceConfigOption>();
+    component.certificateConfigOption = new Map<string, IngressCertificateConfigOption>();
+  
+
+    clusterService.getClusterDetails.and.returnValue(of(mockCluster));
+    fixture.detectChanges();
+  });
+
+  it('should create the component', () => {
+    expect(component).toBeTruthy();
+  });
+
+  it('should initialize and fetch cluster details', () => {
+    expect(clusterService.getClusterDetails).toHaveBeenCalledWith(1);
+    expect(component.cluster).toEqual(mockCluster);
+  });
+
+  it('should add a new network', () => {
+    component.cluster = { ...mockCluster, externalNetworks: [] };
+    component.addNetwork();
+    expect(component.cluster.externalNetworks.length).toBe(1);
+  });
+
+  it('should remove a network by id', () => {
+    component.cluster = {
+      ...mockCluster,
+      externalNetworks: [{
+          id: 1,
+          assigned: false,
+          assignedSince: '',
+          assignedTo: '',
+          externalIp: '',
+          externalNetwork: '',
+          externalNetworkMaskLength: 0
+      }, {
+          id: 2,
+          assigned: false,
+          assignedSince: '',
+          assignedTo: '',
+          externalIp: '',
+          externalNetwork: '',
+          externalNetworkMaskLength: 0
+      }]
+    };
+    component.removeNetwork(1);
+    expect(component.cluster.externalNetworks.length).toBe(1);
+    expect(component.cluster.externalNetworks[0].id).toBe(2);
+  });
+
+  it('should format date correctly', () => {
+    const date = new Date('2025-01-01T12:00:00');
+    const formattedDate = component.formatDate(date);
+    expect(formattedDate).toBe('01-01-2025 12:00');
+  });
+
+  it('should submit updated cluster', () => {
+    const updatedCluster = { ...mockCluster, name: 'Updated Cluster' };
+    clusterService.updateCluster.and.returnValue(of(updatedCluster));
+
+    component.cluster = mockCluster;
+    component.submit();
+
+    expect(clusterService.updateCluster).toHaveBeenCalledWith(mockCluster);
+    expect(component.cluster).toEqual(updatedCluster);
+  });
+
+  it('should send cluster with file', () => {
+    const mockFile = new File(['test content'], 'test.yaml', { type: 'application/x-yaml' });
+    const mockEvent = { files: [mockFile] };
+    const mockResponse: ClusterManager = {
+      id: 1,
+      name: 'Test Cluster',
+      state:"UP",
+      currentStateSince: new Date('2025-01-01'),
+      contactEmail: "test@test.test",
+      description: 'Test Description',
+      externalNetworks: [],
+      creationDate: new Date('2025-01-01'),
+      modificationDate: new Date('2025-02-01'),
+      codename: 'test-cluster',
+      pathConfigFile: '/path/to/config.yaml',
+      clusterConfigFile: 'Config',
+      ingress: null,
+      deployment: null,
+      domainNames: ["test"]
+    };
+
+    clusterService.sendCluster.and.returnValue(of(mockResponse));
+
+    component.sendCluster(mockEvent);
+
+    expect(clusterService.sendCluster).toHaveBeenCalledWith(mockFile, jasmine.any(ClusterManager));
+  });
+});
\ No newline at end of file
diff --git a/src/app/shared/admin/clusters/managerdetails/managerdetails.component.ts b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.ts
new file mode 100644
index 0000000000000000000000000000000000000000..1f275e021482b68feb11db39c7a9709ea70cda5b
--- /dev/null
+++ b/src/app/shared/admin/clusters/managerdetails/managerdetails.component.ts
@@ -0,0 +1,118 @@
+import { Component, OnInit } from '@angular/core';
+import { ClusterManagerService } from '../../../../service/cluster-manager.service';
+import { ClusterManager } from '../../../../model/cluster-manager';
+import { ActivatedRoute, Router } from '@angular/router';
+import { BaseComponent } from '../../../common/basecomponent/base.component';
+import { ClusterExtNetwork, IngressCertificateConfigOption, IngressControllerConfigOption, IngressResourceConfigOption, NamespaceConfigOption } from '../../../../model/cluster';
+import { DatePipe } from '@angular/common';
+import { DomainService } from '../../../../service';
+
+@Component({
+  selector: 'app-manager-details',
+  templateUrl: './managerdetails.component.html',
+  styleUrl: './managerdetails.component.css'
+})
+export class ClusterManagerDetailsComponent extends BaseComponent implements OnInit  {
+
+  public cluster: ClusterManager ;
+  public cluterId;
+  public error = "";
+
+  public domains = [];
+
+
+    controllerConfigOption: Map<string, IngressControllerConfigOption> = new Map<string, IngressControllerConfigOption>();
+
+    resourceConfigOption: Map<string, IngressResourceConfigOption> = new Map<string, IngressResourceConfigOption>();
+
+    namespaceConfigOption: Map<string, NamespaceConfigOption> = new Map<string, NamespaceConfigOption>();
+
+    certificateConfigOption: Map<string, IngressCertificateConfigOption> = new Map<string, IngressCertificateConfigOption>();
+
+
+  constructor(private clusterService: ClusterManagerService,
+                    public router: Router,
+                    private route: ActivatedRoute,
+                    private datePipe: DatePipe,
+                    private domainService: DomainService
+                    
+  ) {
+    super();
+    this.initializeMaps();
+  }
+
+  public ngOnInit() {
+    this.domainService.getAllBase().subscribe(result => this.domains = result);
+
+    this.route.params.subscribe(params => {
+        this.cluterId = +params['id'];
+
+        this.clusterService.getClusterDetails(this.cluterId).subscribe(result => {
+          console.log(result);
+          this.cluster = result;
+        } )
+    })
+  }
+
+ public sendCluster(event: any) {
+    console.log(event);
+    const file = event.files[0];
+    const view = new ClusterManager();
+    view.name = "test"
+    view.description="testest"
+    this.clusterService.sendCluster(file, view).subscribe(result => { 
+        console.log(result);
+    }
+    )
+    }
+
+    private initializeMaps() {
+        this.resourceConfigOption.set('Do nothing', IngressResourceConfigOption.NOT_USED);
+        this.resourceConfigOption.set('Deploy new resource from the definition in the application chart', IngressResourceConfigOption.DEPLOY_FROM_CHART);
+        this.controllerConfigOption.set('Use existing', IngressControllerConfigOption.USE_EXISTING);
+        this.controllerConfigOption.set('Deploy new controller from chart repository', IngressControllerConfigOption.DEPLOY_NEW_FROM_REPO);
+        this.controllerConfigOption.set('Deploy new controller from local chart archive', IngressControllerConfigOption.DEPLOY_NEW_FROM_ARCHIVE);
+        this.namespaceConfigOption.set('Use default namespace', NamespaceConfigOption.USE_DEFAULT_NAMESPACE);
+        this.namespaceConfigOption.set('Use domain namespace', NamespaceConfigOption.USE_DOMAIN_NAMESPACE);
+        this.namespaceConfigOption.set('Create namespace', NamespaceConfigOption.CREATE_NAMESPACE);
+        this.certificateConfigOption.set('Use my own wildcard certificate', IngressCertificateConfigOption.USE_WILDCARD);
+        this.certificateConfigOption.set('Generate LetsEncrypt certificates automatically', IngressCertificateConfigOption.USE_LETSENCRYPT);
+    }
+
+    public getKeys(map) {
+        return Array.from(map.keys());
+    }
+
+    public removeNetwork(id) {
+            this.cluster.externalNetworks.splice(
+                this.cluster.externalNetworks.findIndex(
+                    function (i) {
+                        return i.id = id;
+                    }), 1);
+    }
+    
+    public addNetwork() {
+            const newobj: ClusterExtNetwork = new ClusterExtNetwork();
+            this.cluster.externalNetworks.push(newobj);
+    }
+
+    public formatDate(date: Date) {
+        return  this.datePipe.transform(date, 'dd-MM-yyyy HH:mm');
+    }
+
+    public submit(): void {
+        console.log(this.cluster);
+        this.clusterService.updateCluster(this.cluster).subscribe(result => {
+            console.log(result);
+            this.cluster = result;
+        });
+    }
+
+    public onDomainSelection(event: any) {
+
+      console.log(event);
+      this.cluster.domainNames = [event]
+    
+  }
+
+}
diff --git a/src/app/shared/applications/applications.component.html b/src/app/shared/applications/applications.component.html
index 533fc8862b187fa46f722615edd9a63f1560082d..840b0e5448d17aa65e8bb0445b661d5992a57484 100644
--- a/src/app/shared/applications/applications.component.html
+++ b/src/app/shared/applications/applications.component.html
@@ -16,6 +16,16 @@
 			</select>
 		</div>
 	</div>
+	<div  class="col-xs-12 col-sm-12 col-md-4 col-lg-3" style="padding: 8px 15px; display: flex">
+		<p-checkbox
+				inputId="subscribed"
+				binary="true"
+				[(ngModel)]="showSubscribed"
+				[ngModelOptions]="{standalone: true}"
+				id="subscribed"
+				ngDefaultControl/>
+		<label style="margin: 0; padding-left: 5px; font-weight: unset; text-wrap: nowrap" for="subscribed">Show subscribed only</label>
+	</div>
 <!--	<div class="col-xs-12 col-sm-2 col-md-2 col-lg-2">-->
 <!--		<div class="btn-toolbar" role="toolbar">-->
 <!--			<div class="btn-group pull-right">-->
@@ -31,4 +41,4 @@
 </div>
 <hr>
 
-<nmaas-applist [appView]="appView" [listType]="selectedListType" [applications]="applications" [selected]="selected" [domainId]="domainId" [domain]="domain"></nmaas-applist>
+<nmaas-applist [appView]="appView" [listType]="selectedListType" [showSubscribed]="showSubscribed" [applications]="applications" [selected]="selected" [domainId]="domainId" [domain]="domain"></nmaas-applist>
diff --git a/src/app/shared/applications/applications.component.spec.ts b/src/app/shared/applications/applications.component.spec.ts
index d45f571f8995d6bb44529fd4672c7173b6bf67e7..296500a694818afb5a8b519a9638002e64ebc1fd 100644
--- a/src/app/shared/applications/applications.component.spec.ts
+++ b/src/app/shared/applications/applications.component.spec.ts
@@ -18,6 +18,7 @@ import {of} from 'rxjs';
 import {AppInstallModalComponent} from '../modal/appinstall';
 import {ModalComponent} from '../modal';
 import {Domain} from '../../model/domain';
+import {CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA} from '@angular/core';
 
 describe('ApplicationsComponent', () => {
   let component: ApplicationsViewComponent;
@@ -52,7 +53,8 @@ describe('ApplicationsComponent', () => {
               }
           }),
       ],
-      providers: [AppsService, AppSubscriptionsService, UserDataService, AppConfigService, TagService, DomainService, AppInstanceService]
+      providers: [AppsService, AppSubscriptionsService, UserDataService, AppConfigService, TagService, DomainService, AppInstanceService],
+        schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA]
     })
     .compileComponents();
   }));
diff --git a/src/app/shared/applications/applications.component.ts b/src/app/shared/applications/applications.component.ts
index 03a1b40421b93fceead7206aefb4d2e6c9ffcace..0c5ca512ab2e7d7b9d2e5d763290d15628ed62e1 100644
--- a/src/app/shared/applications/applications.component.ts
+++ b/src/app/shared/applications/applications.component.ts
@@ -60,6 +60,7 @@ export class ApplicationsViewComponent implements OnInit, OnChanges {
     public sortMode = 'NAME';
 
     private popStats: any = {};
+    public showSubscribed = false;
 
     constructor(private appsService: AppsService,
                 private appSubsService: AppSubscriptionsService,
@@ -76,7 +77,6 @@ export class ApplicationsViewComponent implements OnInit, OnChanges {
                 this.popStats = data;
             }
         )
-
     }
 
     ngOnChanges(changes: SimpleChanges) {
diff --git a/src/app/shared/applications/list/applist.component.html b/src/app/shared/applications/list/applist.component.html
index 4d0aafd6788ff2fa08c866c1756e6428e56e3c09..62290e16b297d01e643bf0bc1c05fc4642aa2f8f 100644
--- a/src/app/shared/applications/list/applist.component.html
+++ b/src/app/shared/applications/list/applist.component.html
@@ -3,7 +3,7 @@
 	<div *ngIf="listType === ListType.GRID" class="tab-pane fade in"
 		[class.active]="listType === ListType.GRID" id="tab-grid">
 		<div class="row auto-clear">
-			<nmaas-applist-element *ngFor="let app of applications | async" [app]="app" [domainId]="domainId" [selected]="(selected | async)?.has(app.id)" [domain]="domainObject" ></nmaas-applist-element>
+			<nmaas-applist-element *ngFor="let app of applications | async" [app]="app" [showSubscribed]="showSubscribed" [domainId]="domainId" [selected]="(selected | async)?.has(app.id)" [domain]="domainObject" ></nmaas-applist-element>
 		</div>
 	</div>
 	<div *ngIf="listType === ListType.TABLE" class="tab-pane fade in"
diff --git a/src/app/shared/applications/list/applist.component.ts b/src/app/shared/applications/list/applist.component.ts
index 7d8cccabdb8b86d45bdf78ea3825e755ba2f84ea..eef0d2b72ac4589058931269fbdff4cb1a565ea7 100644
--- a/src/app/shared/applications/list/applist.component.ts
+++ b/src/app/shared/applications/list/applist.component.ts
@@ -42,9 +42,13 @@ export class AppListComponent implements OnInit, OnChanges {
     @Input()
     public domain: Observable<Domain>;
 
+    @Input()
+    public showSubscribed: boolean;
+
     public domainObject: Domain = undefined;
 
 
+
     constructor(private appSubscriptionService: AppSubscriptionsService,
                 private userDataService: UserDataService,
                 private appConfig: AppConfigService,
diff --git a/src/app/shared/applications/list/element/appelement.component.html b/src/app/shared/applications/list/element/appelement.component.html
index 8bb64633ab90a936f0d0cd4a8448f38db892a069..0a4686b1dd0589b99b239b9987108fd2f48de632 100644
--- a/src/app/shared/applications/list/element/appelement.component.html
+++ b/src/app/shared/applications/list/element/appelement.component.html
@@ -1,5 +1,23 @@
 
-<div *ngIf="app && showAppInList" class="col-xs-12 col-sm-12 col-md-6 col-lg-4 col-xl-3">
+<div *ngIf="app && showAppInList && !showSubscribed" class="col-xs-12 col-sm-12 col-md-6 col-lg-4 col-xl-3">
+	<div class="app-card clickable-tail"  [routerLink]="['/apps', app.id]">
+		<div class = "element-container">
+			<div [class.subscribed]="selected">
+				<i [class.pi]="selected" [class.pi-star-fill]="selected" [class.star]="selected"></i>
+			</div>
+			<div class="image-container-outer">
+				<img class="center center-block image-container" alt="App logo" [src]="appImagesService.getAppLogoUrl(app?.id) | secure"
+					 onError="this.src='assets/images/app-logo-example.png';"  />
+			</div>
+			<div class="text-center description-container">
+				<h3 class="app-name">{{app?.name}}</h3>
+				<div class="text-two-lines">{{getDescription()?.briefDescription}}</div>
+			</div>
+		</div>
+	</div>
+</div>
+
+<div *ngIf="selected && showAppInList && showSubscribed" class="col-xs-12 col-sm-12 col-md-6 col-lg-4 col-xl-3">
 	<div class="app-card clickable-tail"  [routerLink]="['/apps', app.id]">
 		<div class = "element-container">
 			<div [class.subscribed]="selected">
diff --git a/src/app/shared/applications/list/element/appelement.component.ts b/src/app/shared/applications/list/element/appelement.component.ts
index 434d17c702c85570022e2b406c17281a856e9960..d18b0371caf3129e34fd486cb02436f80b85b0e3 100644
--- a/src/app/shared/applications/list/element/appelement.component.ts
+++ b/src/app/shared/applications/list/element/appelement.component.ts
@@ -40,6 +40,9 @@ export class AppElementComponent implements OnInit, OnChanges {
     @Input()
     public domain: Domain;
 
+    @Input()
+    public showSubscribed: boolean;
+
     @ViewChild(AppInstallModalComponent)
     public readonly modal: AppInstallModalComponent;
 
diff --git a/src/app/shared/common/domainfilter/domainfilter.component.html b/src/app/shared/common/domainfilter/domainfilter.component.html
index b7fe493cd5b083b6be70c23477a0e53e06cb4c94..a307df6d8ce63368b3b289c83c0cdccf9a2b0e4d 100644
--- a/src/app/shared/common/domainfilter/domainfilter.component.html
+++ b/src/app/shared/common/domainfilter/domainfilter.component.html
@@ -20,11 +20,13 @@
 		optionLabel="name"
 		[filter]="false"
 		[filterPlaceholder]="'SEARCH' | translate"
-		(onChange)="changeDomain($event.value.id, $event.value.name)">
+		(onChange)="changeDomain($event.value.id, $event.value.name)"
+		appendTo="body">
 
 	<ng-template pTemplate="selectedItem" let-item>
     <span style="color: #414F6B;">
-      {{ "FILTER.DOMAIN" | translate }}: {{ item?.name }}
+<!--      {{ "FILTER.DOMAIN" | translate }}: -->
+		{{ item?.name }}
     </span>
 	</ng-template>
 
diff --git a/src/app/shared/common/domainfilter/domainfilter.component.spec.ts b/src/app/shared/common/domainfilter/domainfilter.component.spec.ts
index 1dfabffcdf0244881d130a98c96a00ae59ebc875..4f293574d7139510c4f2b6c61f7c8e53c94578e4 100644
--- a/src/app/shared/common/domainfilter/domainfilter.component.spec.ts
+++ b/src/app/shared/common/domainfilter/domainfilter.component.spec.ts
@@ -28,6 +28,7 @@ describe('DomainFilterComponent', () => {
         applicationStatePerDomain: [],
         groups: [],
         annotations: [],
+        clusters: [],
     }
 
     const domain1: Domain = {
@@ -41,6 +42,7 @@ describe('DomainFilterComponent', () => {
         applicationStatePerDomain: [],
         groups: [],
         annotations: [],
+        clusters: [],
     };
 
     const domain2: Domain = {
@@ -54,6 +56,7 @@ describe('DomainFilterComponent', () => {
         applicationStatePerDomain: [],
         groups: [],
         annotations: [],
+        clusters: [],
     };
 
     beforeEach(waitForAsync(() => {
diff --git a/src/app/shared/common/domainfilter/domainfilter.component.ts b/src/app/shared/common/domainfilter/domainfilter.component.ts
index 426978d47713b97d1e8a8f1c019d4c1ea738d4a7..57723deda8e95bddd8f115b8ca89e7f32fdeb62a 100644
--- a/src/app/shared/common/domainfilter/domainfilter.component.ts
+++ b/src/app/shared/common/domainfilter/domainfilter.component.ts
@@ -74,7 +74,7 @@ export class DomainFilterComponent implements OnInit {
 
     public updateDomains(): void {
         if (this.authService.hasRole('ROLE_SYSTEM_ADMIN')) {
-            this.domains = this.domainService.getAll();
+            this.domains = this.domainService.getAllBase();
         } else {
             this.domains = this.domainService.getMyDomains();
             const globalDomainId = this.domainService.getGlobalDomainId();
@@ -109,6 +109,7 @@ export class DomainFilterComponent implements OnInit {
 
     private sortDomains(): void {
         const globalDomainId = this.domainService.getGlobalDomainId();
+        console.log(this.domains);
         this.domains = this.domains.pipe(
             map(
                 domains => {
@@ -126,10 +127,13 @@ export class DomainFilterComponent implements OnInit {
                         domains.unshift(defaultDomain)
                     }
                     this.domainsLocal = domains;
+                    this.filteredDomainsSub.next(this.domainsLocal);
                     return domains
                 }
             )
         )
+        console.log(this.domainsLocal);
+        
     }
 
     public changeDomain(domainId: number, domainName: string) {
diff --git a/src/app/shared/contact/contact.component.ts b/src/app/shared/contact/contact.component.ts
index 732955b972b12bf62d045cb8aa57edfbc34ba737..2ccb5d3e20301d266483167f47290518c7b79a2b 100644
--- a/src/app/shared/contact/contact.component.ts
+++ b/src/app/shared/contact/contact.component.ts
@@ -125,8 +125,11 @@ export class ContactComponent implements OnInit {
     private sendMail(data: any): Observable<void> {
         // submit captcha request
         return this.recaptchaV3Service.execute('contactForm').pipe(
-            catchError(_ => of('')), // in case of captcha error return empty token
+            catchError(error => {
+                console.error(error);
+                return of(error)}), // in case of captcha error return empty token
             map((token) => {
+                console.log(token)
                 const result = {token, mail: new Mail()} // create mail object
                 result.mail.otherAttributes = data; // set properties and mail attributes
                 result.mail.otherAttributes.subType = this.formType.key;
diff --git a/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.css b/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.css
index f28c0dc3b4b161c71b93acbce3445f3e467cb425..1ffc9808117f220b152d39a389897a633805cf4c 100644
--- a/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.css
+++ b/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.css
@@ -1,3 +1,4 @@
 .border-red {
     border: 1px solid red;
 }
+
diff --git a/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.html b/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.html
index 826defac24c854dbfe46797077b2e1331ea1dc36..b710e9074aaa9c5bfd6b9d37c19c7ffa2f5566f8 100644
--- a/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.html
+++ b/src/app/shared/domain-namespace-annotations/domain-namespace-annotations.component.html
@@ -1,14 +1,15 @@
-<div class="panel panel-default" style="width: 100% !important;" >
+<div class="background-section" style="width: 100% !important;" >
     <div class="panel-heading">
-        <div style="display: flex; justify-content: start; align-items: center">
-            <div>
+        <div style="display: flex; justify-content:space-between">
+            <h4 style="font-size:15px; font-weight: bold">
                 {{'DOMAINS.ANNOTATIONS.CREATION' | translate}}
-            </div>
+            </h4>
+            <button type="button" class="btn btn-text" (click)="addAnnotation()">{{'DOMAINS.ANNOTATIONS.ADD'| translate}}</button>
         </div>
     </div>
     <div class="panel-body">
         <div  style="display: flex; justify-content: end">
-            <button type="button" class="btn btn-primary" (click)="addAnnotation()">{{'DOMAINS.ANNOTATIONS.ADD'| translate}}</button>
+
         </div>
         <div class="grid flex flex-grow-1">
             <div class="col-4">
@@ -63,8 +64,8 @@
 
     </div>
     <div class="nmaas-modal-footer">
-        <button type="button" class="btn btn-primary" (click)="closeModal()" [disabled]="isKeyNotUniqueAdd(newAnnotations) || !isKeyPatternCorrect">{{'DOMAINS.ADD_BUTTON' | translate}}</button>
         <button type="button" class="btn btn-secondary" (click)="modal.hide()">{{'APP_CHANGE_STATE_MODAL.CANCEL_BUTTON' | translate}}</button>
+        <button type="button" class="btn btn-primary" (click)="closeModal()" [disabled]="isKeyNotUniqueAdd(newAnnotations) || !isKeyPatternCorrect">{{'DOMAINS.ADD_BUTTON' | translate}}</button>
     </div>
 </nmaas-modal>
 
@@ -94,7 +95,7 @@
 
     </div>
     <div class="nmaas-modal-footer">
-        <button type="button" class="btn btn-primary" (click)="closeModalEdit()" [disabled]="isEditAnnotationCorrect(editAnnotation) || !isKeyPatternCorrect">{{'DOMAINS.EDIT_BUTTON' | translate}}</button>
         <button type="button" class="btn btn-secondary" (click)="editModal.hide()">{{'APP_CHANGE_STATE_MODAL.CANCEL_BUTTON' | translate}}</button>
+        <button type="button" class="btn btn-primary" (click)="closeModalEdit()" [disabled]="isEditAnnotationCorrect(editAnnotation) || !isKeyPatternCorrect">{{'DOMAINS.EDIT_BUTTON' | translate}}</button>
     </div>
 </nmaas-modal>
diff --git a/src/app/shared/footer/footer.component.css b/src/app/shared/footer/footer.component.css
index 1d1b633e0b99bf386b188289e88d4fa62337f785..d1bab419a3afca8ce4d51a601485adb82bfaed8d 100644
--- a/src/app/shared/footer/footer.component.css
+++ b/src/app/shared/footer/footer.component.css
@@ -1,8 +1,10 @@
 footer {
   flex-shrink: 0;
-  padding-bottom: 15px;
+  padding-bottom: 0px;
   padding-top: 15px;
-  background-color: #e7e7e7;
+  background-color: var(--menu-color);
+  display:flex;
+  /* margin-left: -1rem; */
 }
 
 /*explicit text alignment for chrome*/
@@ -17,9 +19,9 @@ a:link{
   text-decoration: underline;
 }
 
-a:hover {
-  font-weight: 600;
-}
+/*a:hover {*/
+/*  font-weight: 600;*/
+/*}*/
 
 .img-footer{
   max-height: 34px;
@@ -86,6 +88,6 @@ a:hover {
   flex-direction: row;
 }
 .container-width {
-  width: 85vw;
+  width: calc(100vw - var(--left-panel-width));
   margin: auto;
 }
diff --git a/src/app/shared/footer/footer.component.html b/src/app/shared/footer/footer.component.html
index bbce48b72740f03e6b38520708430af57b838036..e39c025be237c2abd69a09b6811a31051f220a54 100644
--- a/src/app/shared/footer/footer.component.html
+++ b/src/app/shared/footer/footer.component.html
@@ -1,29 +1,34 @@
 <footer class="footer col-xs-12" id="global-footer">
 	<div class="container-width">
-		<div class="row row-center">
-			<div class="col-sm-2">
-				<!-- nmaas Logo optionally -->
-                <a href="https://www.geant.org/">
-                    <img alt="Geant Logo" src="/assets/images/geant-logo.png"  width="200" class="image-link"/>
-                </a>
-			</div>
-            <div class="col-sm-3">
-                    <img alt="EU flag" src="/assets/images/cofunded.png" width="200" style="padding-top: 15px; "/>
-			</div>
-			<div class="col-sm-2 col-sm-offset-5">
-                <p>
-                    <a *ngIf="landingProfile === 'VNOC'" href="https://docs.nmaas.eu/use-cases/virtual-noc/vnoc-introduction/">Documentation</a>
-                    <a *ngIf="landingProfile !== 'VNOC'" href="https://docs.nmaas.eu/use-cases/virtual-lab/vlab-introduction/">Documentation</a>
-                </p>
-                <p><a routerLink="/privacy">{{ 'FOOTER.NOTICE' | translate }}</a></p>
-                <p><a routerLink="/aup">{{ 'FOOTER.AUP' | translate }}</a></p>
-                <p><a routerLink="/about">{{ 'FOOTER.CONTACT' | translate }}</a></p>
+		<div class="" style="display: flex; justify-content: space-between">
+            <div style="width:50%; display: flex">
+                <div class="" style="margin-right: 20px">
+                    <!-- nmaas Logo optionally -->
+                    <a href="https://www.geant.org/">
+                        <img alt="GÉANT Logo" src="/assets/images/geant-logo.png"  width="100" class="image-link"/>
+                    </a>
+                </div>
+                <div class="">
+                    <img alt="EU flag" src="/assets/images/cofunded.png" width="180" style="padding-top: 5px; "/>
+                </div>
+            </div>
+			<div class="" style="display: flex; width: 50%; justify-content: end; margin-right: 50px">
+                <div style="margin-right: 30px">
+                    <p>
+                        <a *ngIf="landingProfile === 'VNOC'" href="https://docs.nmaas.eu/use-cases/virtual-noc/vnoc-introduction/">Documentation</a>
+                        <a *ngIf="landingProfile !== 'VNOC'" href="https://docs.nmaas.eu/use-cases/virtual-lab/vlab-introduction/">Documentation</a>
+                    </p>
+                    <p><a routerLink="/about">{{ 'FOOTER.CONTACT' | translate }}</a></p>
+                </div>
+                <div>
+                    <p><a routerLink="/privacy">{{ 'FOOTER.NOTICE' | translate }}</a></p>
+                    <p><a routerLink="/aup">{{ 'FOOTER.AUP' | translate }}</a></p>
+                </div>
 			</div>
 		</div>
-
-        <div class="row">
-            <div class="col-xs-10">
-            </div>
+<!--        <div class="row">-->
+<!--            <div class="col-xs-10">-->
+<!--            </div>-->
 <!--            <div class="col-xs-2">-->
 <!--                <div>-->
 <!--                    <a class="footer-light footer-move-top" (click)="this.moveToTop();">-->
@@ -31,7 +36,6 @@
 <!--                    </a>-->
 <!--                </div>-->
 <!--            </div>-->
-        </div>
-
+<!--        </div>-->
 	</div>
 </footer>
diff --git a/src/app/shared/left-menu/left-menu.component.css b/src/app/shared/left-menu/left-menu.component.css
index afd8e55a067061f61d251e45aee4ab6787b740e5..4ae8e6cfc231bdce82773cef601b773e09fe7be0 100644
--- a/src/app/shared/left-menu/left-menu.component.css
+++ b/src/app/shared/left-menu/left-menu.component.css
@@ -8,16 +8,17 @@
     display: flex;
     flex-direction: column;
     padding: 1rem;
-  }
-  .menu ul {
+}
+.menu ul {
     list-style: none;
     padding: 0;
-  }
-  .menu li {
-      padding: 10px 10px;
-      margin: 0.5rem 0;
-      border-radius: 4px;
-  }
+}
+.menu li {
+    padding: 10px 10px;
+    margin: 0.5rem 0;
+    border-radius: 4px;
+}
+
 .menu li:hover {
     padding: 10px 5px;
     background: var(--background);
@@ -29,15 +30,18 @@
 .menu li.active:hover{
     padding: 10px 5px;
 }
+.collapsed{
+    /*width:40px;*/
+}
 .active{
     padding: 10px 5px;
     background: white;
     border-left: 5px solid var(--menu-pink)
 }
-  .menu a {
+.menu a {
     color: var(--l-text-color);
     text-decoration: none;
-  }
+}
 :host ::ng-deep .p-button{
     padding: 8px 10px;
     width:100%;
@@ -60,3 +64,46 @@
 :host ::ng-deep .p-menu .p-menuitem:not(.p-highlight):not(.p-disabled) > .p-menuitem-content:hover{
     background:var(--user-button-background-hover);
 }
+:host ::ng-deep .p-accordion .p-accordion-header .p-accordion-header-link{
+    display:flex;
+    flex-direction: row-reverse;
+    justify-content: space-between;
+    border:none;
+}
+:host ::ng-deep a {
+    font-weight: normal;
+    color: var(--l-text-color)
+}
+:host ::ng-deep a:hover {
+    text-decoration:none;
+    color: var(--l-text-color);
+    outline:none;
+}
+:host ::ng-deep a:focus{
+    outline: none;
+    text-decoration: none;
+}
+:host ::ng-deep .p-accordion .p-accordion-content{
+    background: transparent;
+    border: none;
+}
+
+.toggle-button{
+    width: 30px;
+    height:30px;
+    background: var(--menu-color);
+    box-shadow: 0 0 3px rgba(0, 0, 0, 0.15);
+    border-radius: 50px;
+    position: absolute;
+    left: 284px;
+    display: flex;
+    align-items: center;
+    justify-content: center;
+}
+
+.collapsed-user{
+    width: 130px;
+}
+::ng-deep app-modal-notification-send {
+
+}
diff --git a/src/app/shared/left-menu/left-menu.component.html b/src/app/shared/left-menu/left-menu.component.html
index ad8ae052055756b291a667dcd50382ccc53e3e8f..38d7687035637e3d3ee3cc8913e63affe9d93231 100644
--- a/src/app/shared/left-menu/left-menu.component.html
+++ b/src/app/shared/left-menu/left-menu.component.html
@@ -1,58 +1,175 @@
-<div class="flex flex-column justify-content-between ">
+<div class="flex flex-column justify-content-between menu-tr" [ngStyle]="{'width': isCollapsed ? '100px' : '300px'}" style="background: var(--menu-color); height: 100%; position: fixed;">
     <div class="menu flex">
-        <div>
-            <img src="../../../assets/images/logo-small.png" width="250px">
+        <div style="display: flex; align-items: center">
+            <div class="logo-container">
+                <img *ngIf="!isCollapsed" class="logo" src="../../../assets/images/logo-small.png" width="250px">
+                <img *ngIf="isCollapsed"  class="logo" src="../../../assets/images/nmaas-cloud.png" width="50px">
+            </div>
+            <div class="toggle-button" (click)="toggleMenu()" [ngStyle]="{'left': isCollapsed ? '85px' : '284px'}">
+                <i style="font-size: 1.8rem" class="pi pi-angle-left"></i>
+            </div>
         </div>
         <div style="margin-top: 30px">
             <nmaas-domain-filter class="drop-domain"></nmaas-domain-filter>
         </div>
-        <ul *ngIf="!toggleAdmin" style="margin-top: 30px">
-          <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
-              <a  style="display: flex; align-items: center;" [routerLink]="['/']">
-                  <i class="pi pi-th-large" style="margin-right:10px; font-size: 15px"></i>Applications</a>
-          </li>
-          <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
-              <a href="#" style="display: flex; align-items: center;" [routerLink]="['/instances']">
-                  <i class="pi pi-server" style="margin-right:10px; font-size: 15px"></i>Instances</a>
-          </li>
+        <ul *ngIf="!toggleAdmin" style="margin-top: 30px" >
+            <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a  style="display: flex; align-items: center;" [routerLink]="['/']">
+                    <i class="pi pi-th-large" style="margin-right:10px; font-size: 18px" title="Application"></i>
+                    <span *ngIf="!isCollapsed">
+                      Applications
+                  </span>
+                </a>
+            </li>
+            <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a href="#" style="display: flex; align-items: center;" [routerLink]="['/instances']">
+                    <i class="pi pi-server" style="margin-right:10px; font-size: 18px" title=" Instances"></i>
+                    <span *ngIf="!isCollapsed">
+                      Instances
+                  </span>
+                </a>
+            </li>
         </ul>
         <ul *ngIf="toggleAdmin" style="margin-top: 30px">
-            <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
-                <a  style="display: flex; align-items: center;" [routerLink]="['/dashboard']">
-                    <i class="pi pi-chart-bar" style="margin-right:10px; font-size: 15px"></i>Dashboard</a>
+            <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a  style="display: flex; align-items: center;" [routerLink]="['admin/dashboard']">
+                    <i class="pi pi-chart-bar" style="margin-right:10px; font-size: 18px" title="Dashboard"></i>
+                    <span *ngIf="!isCollapsed">
+                        Dashboard
+                    </span>
+                </a>
             </li>
-            <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_VL_MANAGER', 'ROLE_VL_DOMAIN_ADMIN']"
-                [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
-                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/domains']">
-                    <i class="pi pi-server" style="margin-right:10px; font-size: 15px"></i>{{ 'NAVBAR.DOMAINS' | translate }}</a>
+            <p-accordion>
+                <p-accordionTab *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_GROUP_MANAGER', 'ROLE_GROUP_DOMAIN_ADMIN']">
+                    <ng-template pTemplate="header">
+                        <div>
+                            <i class="pi pi-server" style="margin-right:10px; font-size: 18px" title="{{ 'NAVBAR.DOMAINS' | translate }}"></i>
+                            <span *ngIf="!isCollapsed">
+                                 {{ 'NAVBAR.DOMAINS' | translate }}
+                            </span>
+                        </div>
+                    </ng-template>
+                    <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_GROUP_MANAGER', 'ROLE_GROUP_DOMAIN_ADMIN']"
+                        [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}" >
+                        <a  style="display: flex; align-items: center;" [routerLink]="['/admin/domains']">
+                            <i class="pi pi-list" style="margin-right:10px; font-size: 18px" title="List"></i>
+                            <span *ngIf="!isCollapsed">
+                                List
+                            </span>
+                        </a>
+                    </li>
+                    <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']"
+                        [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                        <a  style="display: flex; align-items: center;" [routerLink]="['/admin/domains/groups']">
+                            <i class="pi pi-table" style="margin-right:10px; font-size: 18px" title="Group"></i>
+                            <span *ngIf="!isCollapsed">
+                                Group
+                            </span>
+                        </a>
+                    </li>
+                    <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']"
+                        [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                        <a  style="display: flex; align-items: center;" [routerLink]="['/admin/domains/bulks']">
+                            <i class="pi pi-sitemap" style="margin-right:10px; font-size: 18px" title="Bulk deployments"></i>
+                            <span *ngIf="!isCollapsed">
+                                 Bulk deployments
+                            </span>
+                        </a>
+                    </li>
+                </p-accordionTab>
+            </p-accordion>
+            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/apps/bulks']">
+                    <i class="pi pi-box" style="margin-right:10px; font-size: 18px" title="{{ 'BULK.APP.HEADER' | translate }}"></i>
+                    <span *ngIf="!isCollapsed">
+                       {{ 'BULK.APP.HEADER' | translate }}
+                    </span>
+                </a>
             </li>
-            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
                 <a  style="display: flex; align-items: center;" [routerLink]="['/admin/users']">
-                    <i class="pi pi-users" style="margin-right:10px; font-size: 15px"></i>{{ 'NAVBAR.USERS' | translate }}</a>
+                    <i class="pi pi-users" style="margin-right:10px; font-size: 18px" title="{{ 'NAVBAR.USERS' | translate }}"></i>
+                    <span *ngIf="!isCollapsed">
+                        {{ 'NAVBAR.USERS' | translate }}
+                    </span>
+                </a>
             </li>
-            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
-                <a  style="display: flex; align-items: center;" [routerLink]="['/']">
-                    <i class="pi pi-th-large" style="margin-right:10px; font-size: 15px"></i>Catalog</a>
+            <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_GROUP_DOMAIN_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/domain/users']">
+                    <i class="pi pi-users" style="margin-right:10px; font-size: 18px" title="{{ 'NAVBAR.DOMAIN_USERS' | translate }}"></i>
+                    <span *ngIf="!isCollapsed">
+                        {{ 'NAVBAR.DOMAIN_USERS' | translate  }}
+                    </span>
+                </a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/apps']">
+                    <i class="pi pi-th-large" style="margin-right:10px; font-size: 18px" title="Catalog"></i>
+                    <span *ngIf="!isCollapsed">
+                        Catalog
+                    </span>
+                </a>
             </li>
-            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
                 <a  style="display: flex; align-items: center;" [routerLink]="['/admin/configuration']">
-                    <i class="pi pi-cog" style="margin-right:10px; font-size: 15px"></i>Settings</a>
+                    <i class="pi pi-cog" style="margin-right:10px; font-size: 18px" title="Settings"></i>
+                    <span *ngIf="!isCollapsed">
+                       Settings
+                    </span>
+                </a>
             </li>
-            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
+                <a  style="display: flex; align-items: center;" [routerLink]="['/admin/manage/clusters']">
+                    <i class="pi pi-cog" style="margin-right:10px; font-size: 18px"></i>
+                    <span *ngIf="!isCollapsed">
+                        {{ 'CLUSTERS.CONFIGURATION' | translate }}
+                    </span>
+                </a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
                 <a  style="display: flex; align-items: center;" [routerLink]="['/admin/languages']">
-                    <i class="pi pi-tags" style="margin-right:10px; font-size: 15px"></i>{{'NAVBAR.LANGUAGES' | translate }}</a>
+                    <i class="pi pi-tags" style="margin-right:10px; font-size: 18px" title=" {{'NAVBAR.LANGUAGES' | translate }}"></i>
+                    <span *ngIf="!isCollapsed">
+                        {{'NAVBAR.LANGUAGES' | translate }}
+                    </span>
+                </a>
             </li>
-            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" >
+            <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR']" [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']" [ngClass]="{'collapsed': isCollapsed}">
                 <a  style="display: flex; align-items: center;" [routerLink]="['/admin/monitor']">
-                    <i class="pi pi-chart-line" style="margin-right:10px; font-size: 15px"></i>{{ 'NAVBAR.MONITOR' | translate }}</a>
+                    <i class="pi pi-chart-line" style="margin-right:10px; font-size: 18px" title="{{ 'NAVBAR.MONITOR' | translate }}"></i>
+                    <span *ngIf="!isCollapsed">
+                        {{ 'NAVBAR.MONITOR' | translate }}
+                    </span>
+                </a>
+            </li>
+            <li *roles="['ROLE_SYSTEM_ADMIN']" (click)="showNotificationModal()" [ngClass]="{'collapsed': isCollapsed}">
+                <i class="pi pi-send" style="margin-right:10px; font-size: 18px" title="{{ 'NAVBAR.ALL_USERS' | translate }}"></i>
+                <span *ngIf="!isCollapsed">{{ 'NAVBAR.ALL_USERS' | translate }}</span>
             </li>
 
         </ul>
     </div>
     <div class="menu flex">
-        <p-menu  #menu [model]="items" [popup]="true" class="test" />
-        <p-button *ngIf="!toggleAdmin" (onClick)="menu.toggle($event)" class="user-button"><i class="pi pi-user" style="font-size: 13px; margin-right:10px"></i> User</p-button>
-        <p-button *ngIf="!toggleAdmin" (onClick)="adminPanel()" style="margin-top:10px"><i class="pi pi-sign-in" style="margin-right:10px; font-size: 15px"></i>Go to admin panel</p-button>
-        <p-button *ngIf="toggleAdmin" (onClick)="adminPanel()" style="margin-top:10px"><i class="pi pi-sign-in" style="margin-right:10px; font-size: 15px"></i>Go to user panel</p-button>
+        <p-menu  #menu [model]="items" [popup]="true" class="test" [ngClass]="{'collapsed-user': isCollapsed}"/>
+        <p-button  (onClick)="menu.toggle($event)" class="user-button"><i class="pi pi-user" style="font-size: 18px; margin-right:10px"[ngClass]="{'collapsed': isCollapsed}" title="User"></i>
+            <span *ngIf="!isCollapsed">
+                User
+            </span>
+        </p-button>
+        <div style="margin-top:10px" [routerLink]="['admin/dashboard']">
+            <p-button *ngIf="!toggleAdmin" (onClick)="adminPanel()" ><i class="pi pi-sign-in" style="margin-right:10px; font-size: 18px"[ngClass]="{'collapsed': isCollapsed}" title=" Go to admin panel"></i>
+                <span *ngIf="!isCollapsed">
+                      Admin panel
+                </span>
+            </p-button>
+        </div>
+        <div [routerLink]="['/']"  >
+            <p-button *ngIf="toggleAdmin" (onClick)="adminPanel()" ><i class="pi pi-sign-in" style="margin-right:10px; font-size: 18px"[ngClass]="{'collapsed': isCollapsed}" title="Go to user panel"></i>
+                <span *ngIf="!isCollapsed">
+                        User panel
+                </span>
+            </p-button>
+        </div>
     </div>
 </div>
+<app-modal-notification-send></app-modal-notification-send>
diff --git a/src/app/shared/left-menu/left-menu.component.spec.ts b/src/app/shared/left-menu/left-menu.component.spec.ts
index 320e5ed342b010cabd35a5156b469321d75f65f5..b1c9a408ff29d9de9477256c88225cbe5ad1bfd8 100644
--- a/src/app/shared/left-menu/left-menu.component.spec.ts
+++ b/src/app/shared/left-menu/left-menu.component.spec.ts
@@ -1,30 +1,81 @@
-// import { ComponentFixture, TestBed } from '@angular/core/testing';
-
-// import { LeftMenuComponent } from './left-menu.component';
-// import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
-// import { MessageService } from 'primeng/api';
-
-// describe('LeftMenuComponent', () => {
-//   let component: LeftMenuComponent;
-//   let fixture: ComponentFixture<LeftMenuComponent>;
-
-//   beforeEach(async () => {
-//     await TestBed.configureTestingModule({
-//       imports: [LeftMenuComponent],
-//       providers: [MessageService], 
-//       schemas: [
-//               CUSTOM_ELEMENTS_SCHEMA,
-//               NO_ERRORS_SCHEMA
-//           ]
-//     })
-//     .compileComponents();
-    
-//     fixture = TestBed.createComponent(LeftMenuComponent);
-//     component = fixture.componentInstance;
-//     fixture.detectChanges();
-//   });
-
-//   it('should create', () => {
-//     expect(component).toBeTruthy();
-//   });
-// });
+import { ComponentFixture, TestBed } from '@angular/core/testing';
+import { LeftMenuComponent } from './left-menu.component';
+import { Router, NavigationEnd, ActivatedRoute } from '@angular/router';
+import { ToastContainerComponent } from '../toast-container/toast-container.component';
+import { CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
+import { of, Subject } from 'rxjs';
+
+describe('LeftMenuComponent', () => {
+  let component: LeftMenuComponent;
+  let fixture: ComponentFixture<LeftMenuComponent>;
+  let mockRouter: any;
+  let mockToast: jasmine.SpyObj<ToastContainerComponent>;
+  let routerEventsSubject: Subject<any>;
+  let mockActivatedRoute: any;
+
+  beforeEach(async () => {
+    routerEventsSubject = new Subject();
+    mockRouter = {
+      events: routerEventsSubject.asObservable(),
+      navigate: jasmine.createSpy('navigate')
+    };
+    mockToast = jasmine.createSpyObj('ToastContainerComponent', ['show']);
+    mockActivatedRoute = {
+      snapshot: { params: {}, queryParams: {} }
+    };
+
+    await TestBed.configureTestingModule({
+      declarations: [LeftMenuComponent],
+      providers: [
+        { provide: Router, useValue: mockRouter },
+        { provide: ToastContainerComponent, useValue: mockToast },
+        { provide: ActivatedRoute, useValue: mockActivatedRoute }
+      ],
+      schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA]
+    }).compileComponents();
+
+    fixture = TestBed.createComponent(LeftMenuComponent);
+    component = fixture.componentInstance;
+    fixture.detectChanges();
+  });
+
+  it('should create', () => {
+    expect(component).toBeTruthy();
+  });
+
+  it('should initialize menu items and collapsed state', () => {
+    expect(component.items.length).toBeGreaterThan(0);
+    expect(component.isCollapsed).toBeFalse();
+  });
+
+  it('should update currentUrl and toggleAdmin on NavigationEnd event', () => {
+    const testUrl = '/admin/dashboard';
+    routerEventsSubject.next(new NavigationEnd(1, testUrl, testUrl));
+    expect(component.currentUrl).toBe(testUrl);
+    expect(component.toggleAdmin).toBeTrue();
+  });
+
+  it('should toggle menu collapsed state and update CSS variable', () => {
+    component.toggleMenu();
+    expect(component.isCollapsed).toBeTrue();
+    expect(sessionStorage.getItem('menuCollapsed')).toBe('true');
+
+    component.toggleMenu();
+    expect(component.isCollapsed).toBeFalse();
+    expect(sessionStorage.getItem('menuCollapsed')).toBe('false');
+  });
+
+  it('should show toast message', () => {
+    component.showToastTest();
+    expect(mockToast.show).toHaveBeenCalledWith('Test test', jasmine.anything(), 'HEADER');
+  });
+
+  it('should toggle admin panel visibility', () => {
+    component.toggleAdmin = false;
+    component.adminPanel();
+    expect(component.toggleAdmin).toBeTrue();
+
+    component.adminPanel();
+    expect(component.toggleAdmin).toBeFalse();
+  });
+});
diff --git a/src/app/shared/left-menu/left-menu.component.ts b/src/app/shared/left-menu/left-menu.component.ts
index 064c24b730830328829606ca4485edd794cc1434..84ae20e7257e52be870f5f64f9edda7fbc7362c6 100644
--- a/src/app/shared/left-menu/left-menu.component.ts
+++ b/src/app/shared/left-menu/left-menu.component.ts
@@ -1,7 +1,8 @@
-import { Component, OnInit } from '@angular/core';
+import {Component, OnInit, ViewChild} from '@angular/core';
 import { ToastContainerComponent, ToastMode } from '../toast-container/toast-container.component';
-import {Router} from '@angular/router';
+import {ActivatedRoute, NavigationEnd, Router} from '@angular/router';
 import {MenuItem} from 'primeng/api';
+import {ModalNotificationSendComponent} from '../modal/modal-notification-send/modal-notification-send.component';
 
 @Component({
   selector: 'app-left-menu',
@@ -9,11 +10,17 @@ import {MenuItem} from 'primeng/api';
   styleUrl: './left-menu.component.css'
 })
 export class LeftMenuComponent  implements OnInit {
+  @ViewChild(ModalNotificationSendComponent, {static: true})
+  public notificationModal;
+
   items: MenuItem[];
   toggleAdmin = false;
+  currentUrl : string ;
+  isCollapsed = false;
 
   constructor(private toast: ToastContainerComponent,
-              public router: Router) {
+              public router: Router,
+              private readonly activeRoute: ActivatedRoute,) {
     this.items = [
       {
         label: 'Profile',
@@ -28,10 +35,23 @@ export class LeftMenuComponent  implements OnInit {
         routerLink: ['/logout']
       }
     ]
+    const storedState = sessionStorage.getItem('menuCollapsed');
+    this.isCollapsed = storedState === 'true';
   }
 
   public ngOnInit(): void {
-      console.log("test left menu ")
+    this.router.events.subscribe(event => {
+      if (event instanceof NavigationEnd) {
+        this.currentUrl = event.urlAfterRedirects;
+        console.log('Aktualny URL:', this.currentUrl);
+        if(this.currentUrl.includes('admin')) {
+          this.toggleAdmin = true;
+        }
+      }
+    })
+    console.log("test left menu ")
+    const newWidth = this.isCollapsed ? '100px' : '300px';
+    document.documentElement.style.setProperty('--left-panel-width', newWidth);
   }
 
   public showToastTest() {
@@ -40,5 +60,14 @@ export class LeftMenuComponent  implements OnInit {
   adminPanel() {
     this.toggleAdmin = !this.toggleAdmin;
   }
+  toggleMenu() {
+    this.isCollapsed = !this.isCollapsed;
+    const newWidth = this.isCollapsed ? '100px' : '300px';
+    document.documentElement.style.setProperty('--left-panel-width', newWidth);
+    sessionStorage.setItem('menuCollapsed', this.isCollapsed.toString());
+  }
+  public showNotificationModal(): void {
+    this.notificationModal.show();
+  }
 
 }
diff --git a/src/app/shared/modal/appinstall/appinstallmodal.component.spec.ts b/src/app/shared/modal/appinstall/appinstallmodal.component.spec.ts
index 38b1ba8fd6fb049ce222eccb9fa86a4552792944..859826d73ed6c3685ef23a0b2868f692c0ec0f3f 100644
--- a/src/app/shared/modal/appinstall/appinstallmodal.component.spec.ts
+++ b/src/app/shared/modal/appinstall/appinstallmodal.component.spec.ts
@@ -47,6 +47,7 @@ describe('AppInstallmodalComponent', () => {
         applicationStatePerDomain: [],
         groups: [],
         annotations: [],
+        clusters: [],
     }
 
     beforeEach(waitForAsync(() => {
diff --git a/src/app/shared/modal/modal-notification-send/modal-notification-send.component.html b/src/app/shared/modal/modal-notification-send/modal-notification-send.component.html
index 435992b9e9b3e71156a5ded7e6ca4008a93fd501..4b2cbdcdab4c8f136b1224cc865065dc43c96642 100644
--- a/src/app/shared/modal/modal-notification-send/modal-notification-send.component.html
+++ b/src/app/shared/modal/modal-notification-send/modal-notification-send.component.html
@@ -13,7 +13,7 @@
       </form>
   </div>
     <div class="nmaas-modal-footer">
+        <button type="button" (click)="modal.hide()" class="btn btn-secondary text-center">{{'MESSAGE_MODAL.DISMISS' | translate}}</button>
       <button type="submit" class="btn btn-primary text-center" [disabled]="!f.valid" form="notification-form">{{'MESSAGE_MODAL.CONFIRM' | translate}}</button>
-      <button type="button" (click)="modal.hide()" class="btn btn-secondary text-center">{{'MESSAGE_MODAL.DISMISS' | translate}}</button>
     </div>
 </nmaas-modal>
diff --git a/src/app/shared/navbar/navbar.component.css b/src/app/shared/navbar/navbar.component.css
index 5978cfb11627290845a547fca380052b4cb72606..55bdd7192499c31c22991e19beac919fb0bbf82d 100644
--- a/src/app/shared/navbar/navbar.component.css
+++ b/src/app/shared/navbar/navbar.component.css
@@ -26,11 +26,6 @@
 .lang-circle-icon{
   height: 26px;
 }
-.navbar-left{
-  padding-top: 6px;
-  display: flex;
-  align-items: center;
-}
 .navbar-right{
   display:flex;
   align-items: center;
@@ -48,7 +43,6 @@
   }
   .navbar-left,.navbar-right {
     float: none !important;
-    display:block;
   }
   .navbar-toggle {
     display: block;
@@ -203,18 +197,16 @@
   color: #414F6B;
 }
 .navbar-default .navbar-nav>li>a{
-  color: #414F6B;
-  padding:10px;
+  color: #6D788E;
 }
 .navbar-default .navbar-nav>.active>a{
   border-radius: 5px;
   color: #142548;
- padding:10px;
+  /*font-weight: bold;*/
   background-color: #D1D1D1;
 }
 .navbar-default .navbar-nav>.open>a{
   border-radius: 5px;
   color: #142548;
-  padding:10px;
   background-color: #D1D1D1;
 }
diff --git a/src/app/shared/navbar/navbar.component.html b/src/app/shared/navbar/navbar.component.html
index b75127c4b75f76f275941006c1910aa93457bac3..123273f20eedc423a1110af5d56a3c2a4cfabb81 100644
--- a/src/app/shared/navbar/navbar.component.html
+++ b/src/app/shared/navbar/navbar.component.html
@@ -1,7 +1,8 @@
 <nav class="navbar navbar-default" id="navbar" role="navigation" style="margin:0">
     <div class="container-fluid">
         <div class="navbar-header">
-            <a routerLink="/"><img alt="Geant" src="assets/images/logo-small.png" style="margin: 8px; padding:4px; height:35px"></a>
+            <a routerLink="/"><img alt="GÉANT" src="assets/images/logo-small.png"
+                                   style="margin: 8px; padding:4px; height:35px"></a>
             <button class="navbar-toggle" data-target="#navbarCollapse" data-toggle="collapse" type="button">
                 <span class="sr-only">Toggle Navigation</span>
                 <em class="fas fa-bars"></em>
@@ -20,22 +21,22 @@
             </ul>
             <ul *ngIf="authService.isLogged()" class="nav navbar-nav navbar-right">
                 <li *ngIf="showClock" class="">
-                    <div class="navbar-logout">{{'NAVBAR.EXPIRED_TIME' | translate}}: {{time}}</div>
+                    <div class="navbar-logout">{{ 'NAVBAR.EXPIRED_TIME' | translate }}: {{ time }}</div>
                 </li>
                 <li *ngIf="showClock" class="divider-vertical"></li>
                 <li *ngIf="checkUserRole()" class="drop-domain">
                     <nmaas-domain-filter class="drop-domain"></nmaas-domain-filter>
                 </li>
-                <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']" class="divider-vertical"></li>
-                <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']" [routerLinkActiveOptions]="{exact:true}"
+                <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']" class="divider-vertical"></li>
+                <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']" [routerLinkActiveOptions]="{exact:true}"
                     [routerLinkActive]="['active']" class="dropdown">
                     <a aria-expanded="false" aria-haspopup="true" class="dropdown-toggle" data-toggle="dropdown"
-                       role="button">{{'NAVBAR.ADVANCED' | translate}}<strong class="caret"></strong></a>
+                       role="button">{{ 'NAVBAR.ADVANCED' | translate }}<strong class="caret"></strong></a>
                     <ul class="dropdown-menu">
-                        <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']">
+                        <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']">
                             <a [routerLink]="['/admin/domains/bulks']">{{ 'BULK.DOMAIN.HEADER' | translate }}</a>
                         </li>
-                        <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']">
+                        <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']">
                             <a [routerLink]="['/admin/apps/bulks']">{{ 'BULK.APP.HEADER' | translate }}</a>
                         </li>
                     </ul>
@@ -44,15 +45,15 @@
                 <li *roles="['ROLE_SYSTEM_ADMIN']" [routerLinkActiveOptions]="{exact:true}"
                     [routerLinkActive]="['active']" class="dropdown">
                     <a aria-expanded="false" aria-haspopup="true" class="dropdown-toggle" data-toggle="dropdown"
-                       role="button">{{'NAVBAR.NOTIFICATION' | translate}}<strong class="caret"></strong></a>
+                       role="button">{{ 'NAVBAR.NOTIFICATION' | translate }}<strong class="caret"></strong></a>
                     <ul class="dropdown-menu">
                         <li *roles="['ROLE_SYSTEM_ADMIN']">
-                            <span (click)="showNotificationModal()">{{'NAVBAR.ALL_USERS' | translate}}</span>
+                            <span (click)="showNotificationModal()">{{ 'NAVBAR.ALL_USERS' | translate }}</span>
                         </li>
                     </ul>
                 </li>
                 <li *roles="['ROLE_SYSTEM_ADMIN']" class="divider-vertical"></li>
-                <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_DOMAIN_ADMIN', 'ROLE_TOOL_MANAGER', 'ROLE_VL_MANAGER']"
+                <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_DOMAIN_ADMIN', 'ROLE_TOOL_MANAGER', 'ROLE_GROUP_MANAGER']"
                     [routerLinkActiveOptions]="{exact:true}"
                     [routerLinkActive]="['active']" class="dropdown">
                     <a aria-expanded="false" aria-haspopup="true" class="dropdown-toggle" data-toggle="dropdown"
@@ -61,25 +62,33 @@
                         <li *roles="['ROLE_SYSTEM_ADMIN']"><a
                                 [routerLink]="['/admin/configuration']">{{ 'NAVBAR.SETTINGS' | translate }}</a>
                         </li>
+                        <li *roles="['ROLE_SYSTEM_ADMIN']"><a
+                            [routerLink]="['/admin/manage/clusters']">{{ 'CLUSTERS.CONFIGURATION' | translate }}</a>
+                    </li>
 
                         <li *roles="['ROLE_SYSTEM_ADMIN']" class="dropdown-divider"></li>
                         <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_TOOL_MANAGER']"><a
                                 [routerLink]="['/admin/apps']">{{ 'NAVBAR.MARKET' | translate }}</a>
                         </li>
-                        <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_VL_MANAGER', 'ROLE_VL_DOMAIN_ADMIN']"><a
-                                [routerLink]="['/admin/domains']">{{ 'NAVBAR.DOMAINS' | translate }}</a>
+                        <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_SYSTEM_ADMIN', 'ROLE_OPERATOR', 'ROLE_GROUP_MANAGER', 'ROLE_GROUP_DOMAIN_ADMIN']">
+                            <a
+                                    [routerLink]="['/admin/domains']">{{ 'NAVBAR.DOMAINS' | translate }}</a>
                         </li>
-                        <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_VL_MANAGER']">
+                        <li *roles="['ROLE_SYSTEM_ADMIN', 'ROLE_GROUP_MANAGER']">
                             <a [routerLink]="['/admin/domains/groups']">{{ 'NAVBAR.DOMAIN_GROUPS' | translate }}</a>
                         </li>
                         <li *roles="['ROLE_SYSTEM_ADMIN']"><a
                                 [routerLink]="['/admin/users']">{{ 'NAVBAR.USERS' | translate }}</a>
                         </li>
-                        <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_VL_DOMAIN_ADMIN']"><a
-                                [routerLink]="['/domain/users']">{{ 'NAVBAR.DOMAIN_USERS' | translate }}</a>
+                        
+                        <li *roles="['ROLE_DOMAIN_ADMIN', 'ROLE_GROUP_DOMAIN_ADMIN']">
+                                <a *rolesExcluded="['ROLE_SYSTEM_ADMIN']"
+                                    [routerLink]="['/domain/users']">{{ 'NAVBAR.DOMAIN_USERS' | translate }}</a>
+                           
                         </li>
+                    
                         <li *roles="['ROLE_SYSTEM_ADMIN']"><a
-                                [routerLink]="['/admin/languages']">{{'NAVBAR.LANGUAGES' | translate }}</a>
+                                [routerLink]="['/admin/languages']">{{ 'NAVBAR.LANGUAGES' | translate }}</a>
                         </li>
 
                         <li *roles="['ROLE_SYSTEM_ADMIN']" class="dropdown-divider"></li>
@@ -94,7 +103,7 @@
                     <a aria-expanded="false" aria-haspopup="true" class="dropdown-toggle"
                        data-toggle="dropdown" href="#" role="button">
                         <span class="glyphicon glyphicon-user"></span>
-                        {{authService.getUsername()}} <strong class="caret"></strong></a>
+                        {{ authService.getPreferredUsername() }} <strong class="caret"></strong></a>
                     <ul class="dropdown-menu">
                         <li [routerLinkActiveOptions]="{exact:true}" [routerLinkActive]="['active']"><a
                                 [routerLink]="['/profile']">{{ 'NAVBAR.PROFILE' | translate }}</a></li>
@@ -108,12 +117,16 @@
 
             <ul *ngIf="!authService.isLogged()" class="nav navbar-nav pull-right-lg" id="navbar-main-not-logged">
                 <li>
-                    <button *ngIf="router.url == '/welcome' || router.url.startsWith('/welcome/login') || router.url == '/welcome/registration'" data-parent="#accordion"
-                            class="btn navbar-btn accordion-group" data-target="#login-panel" data-toggle="collapse" [routerLink]="['welcome/login']">
+                    <button *ngIf="router.url == '/welcome' || router.url.startsWith('/welcome/login') || router.url == '/welcome/registration'"
+                            data-parent="#accordion"
+                            class="btn navbar-btn accordion-group" data-target="#login-panel" data-toggle="collapse"
+                            [routerLink]="['welcome/login']">
                         {{ 'WELCOME.LOGIN' | translate }}
                     </button>
-                    <button *ngIf="router.url == '/welcome' || router.url.startsWith('/welcome/login') || router.url == '/welcome/registration'" data-parent="#accordion"
-                            class="btn navbar-btn accordion-group" data-target="#register-panel" data-toggle="collapse" [routerLink]="['welcome/registration']">
+                    <button *ngIf="router.url == '/welcome' || router.url.startsWith('/welcome/login') || router.url == '/welcome/registration'"
+                            data-parent="#accordion"
+                            class="btn navbar-btn accordion-group" data-target="#register-panel" data-toggle="collapse"
+                            [routerLink]="['welcome/registration']">
                         {{ 'WELCOME.REGISTER' | translate }}
                     </button>
                 </li>
@@ -136,7 +149,7 @@
                             <a (click)="useLanguage(lang)">
                                 <img alt="lang flag" class="lang-circle-icon"
                                      src="assets/images/country/{{lang}}_circle.png"/>
-                                <span>{{lang.toUpperCase()}}</span>
+                                <span>{{ lang.toUpperCase() }}</span>
                             </a>
                         </li>
                     </ul>
diff --git a/src/app/shared/navbar/navbar.component.spec.ts b/src/app/shared/navbar/navbar.component.spec.ts
index 7f81b7e65f719b681db4b423c85550e84c0a7e0d..fe0dc2256e63c906623f7fd69c28c13ff2513064 100644
--- a/src/app/shared/navbar/navbar.component.spec.ts
+++ b/src/app/shared/navbar/navbar.component.spec.ts
@@ -49,11 +49,12 @@ describe('NavbarComponent_Shared', () => {
         const mockLanguageService = jasmine.createSpyObj(['getEnabledLanguages', 'shouldUpdate']);
         mockLanguageService.getEnabledLanguages.and.returnValue(of(['en', 'fr', 'pl']));
         mockLanguageService.shouldUpdate.and.returnValue(false);
-        const mockAuthService = jasmine.createSpyObj(['isLogged', 'hasRole', 'getDomains', 'getRoles']);
+        const mockAuthService = jasmine.createSpyObj(['isLogged', 'hasRole', 'getDomains', 'getRoles', 'loadUser', 'refreshUserRoles']);
         mockAuthService.isLogged.and.returnValue(false);
         mockAuthService.hasRole.and.returnValue(false);
         mockAuthService.getDomains.and.returnValue([]);
         mockAuthService.getRoles.and.returnValue([]);
+        mockAuthService.refreshUserRoles.and.returnValue();
         const mockUserDataService = jasmine.createSpyObj(['selectedDomainId'])
         mockUserDataService.selectedDomainId.and.returnValue(1)
 
diff --git a/src/app/shared/navbar/navbar.component.ts b/src/app/shared/navbar/navbar.component.ts
index 394fcdfe84fa6c6fb988684ebc71df8b9a90ff0e..ee1d343013ae4f642475899fd2a5d4d329e45d19 100644
--- a/src/app/shared/navbar/navbar.component.ts
+++ b/src/app/shared/navbar/navbar.component.ts
@@ -56,15 +56,15 @@ export class NavbarComponent implements OnInit {
     ngOnInit() {
         this.isServiceAvailable = this.serviceAvailability.isServiceAvailable;
         this.getSupportedLanguages();
+        this.authService.refreshUserRoles();
         if (this.authService.isLogged()) {
-            if (this.authService.hasRole('ROLE_SYSTEM_ADMIN')) {
                 this.refresh = interval(5000).subscribe(next => {
                     if (this.languageService.shouldUpdate()) {
                         this.getSupportedLanguages();
                         this.languageService.setUpdateRequiredFlag(false);
                     }
                 });
-            }
+            // }
         }
         this.intervalId = setInterval(() => {
             if (this.authService.isLogged()) {
@@ -88,10 +88,12 @@ export class NavbarComponent implements OnInit {
     }
 
     public checkUserRole(): boolean {
-        return this.authService.getDomains().filter(value => value !== this.domainService.getGlobalDomainId()).length > 0
+        if (this.authService.isLogged()) {
+            return this.authService.getDomains().filter(value => value !== this.domainService.getGlobalDomainId()).length > 0
             || this.authService.getRoles().filter(value => value !== 'ROLE_INCOMPLETE')
                 .filter(value => value !== 'ROLE_GUEST')
                 .length > 0;
+        }
     }
 
     public showNotificationModal(): void {
@@ -99,7 +101,7 @@ export class NavbarComponent implements OnInit {
     }
 
     public isOnlyGuestInGlobalDomain(): boolean {
-        const globalDomainRoles = this.authService.getDomainRoles().get(this.domainService.getGlobalDomainId()).getRoles()
+        const globalDomainRoles = this.authService.getGlobalRole()
         return globalDomainRoles  // does have any role in global domain (not undefined)
             && globalDomainRoles.length === 1  // only one role in global domain
             && globalDomainRoles[0] === 'ROLE_GUEST'  // this single role is ROLE_GUEST
diff --git a/src/app/shared/shared.module.ts b/src/app/shared/shared.module.ts
index b1f373c8a0f49f624fa8e4628df4e5888f290e8c..20ffb98d661d7af399933fb60a6111bbcaf9bf74 100644
--- a/src/app/shared/shared.module.ts
+++ b/src/app/shared/shared.module.ts
@@ -1,6 +1,6 @@
 import {DefaultLogo} from '../directive/defaultlogo.directive';
 import {RolesDirective} from '../directive/roles.directive';
-import {NgModule} from '@angular/core';
+import {CUSTOM_ELEMENTS_SCHEMA, NgModule, NO_ERRORS_SCHEMA} from '@angular/core';
 import {FormsModule, ReactiveFormsModule} from '@angular/forms';
 import {CommonModule, DatePipe} from '@angular/common';
 
@@ -37,7 +37,7 @@ import {PasswordStrengthMeterComponent} from 'angular-password-strength-meter';
 import {AboutComponent} from './about/about.component';
 import {ChangelogComponent} from './changelog/changelog.component';
 import {NotificationService} from '../service/notification.service';
-import {RECAPTCHA_V3_SITE_KEY, RecaptchaV3Module} from 'ng-recaptcha';
+import {RECAPTCHA_V3_SITE_KEY, RecaptchaModule, RecaptchaV3Module} from 'ng-recaptcha';
 import {SingleCommentComponent} from './comments/single-comment/single-comment.component';
 import {TranslateStateModule} from './translate-state/translate-state.module';
 import {MinLengthDirective} from '../directive/min-length.directive';
@@ -63,6 +63,17 @@ import { provideZxvbnServiceForPSM  } from 'angular-password-strength-meter/zxcv
 import { AccessTokensComponent } from './users/access-token/access-tokens.component';
 import { LeftMenuComponent } from './left-menu/left-menu.component';
 import {TableModule} from 'primeng/table';
+import { AdminDashboardComponent } from './admin-dashboard/admin-dashboard.component';
+import {CheckboxModule} from 'primeng/checkbox';
+import { InputGroupModule } from 'primeng/inputgroup';
+import { InputGroupAddonModule } from 'primeng/inputgroupaddon';
+import { ButtonModule } from 'primeng/button';
+import { BrowserModule } from '@angular/platform-browser';
+import {ChartModule} from 'primeng/chart';
+import { RolesExcludedDirective } from '../directive/roles-exluded.directive';
+import { FileUploadModule } from 'primeng/fileupload';
+
+
 
 
 @NgModule({
@@ -73,7 +84,6 @@ import {TableModule} from 'primeng/table';
         ServicesModule,
         RouterModule,
         ReactiveFormsModule,
-        RecaptchaV3Module,
         PasswordStrengthMeterComponent,
         TranslateModule.forChild(),
         NgxPaginationModule,
@@ -83,6 +93,15 @@ import {TableModule} from 'primeng/table';
         InputTextModule,
         FormioModule,
         TableModule,
+        CheckboxModule,
+        InputGroupModule,
+        InputGroupAddonModule,
+        ButtonModule,
+        RecaptchaV3Module,
+        ButtonModule,
+        ChartModule,
+        FileUploadModule,
+        TableModule
     ],
     declarations: [
         RateComponent,
@@ -99,6 +118,7 @@ import {TableModule} from 'primeng/table';
         NavbarComponent,
         DefaultLogo,
         RolesDirective,
+        RolesExcludedDirective,
         MinLengthDirective,
         MaxLengthDirective,
         SearchComponent,
@@ -128,7 +148,8 @@ import {TableModule} from 'primeng/table';
         PreferencesComponent,
         SortableHeaderDirective,
         DomainNamespaceAnnotationsComponent,
-        AccessTokensComponent
+        AccessTokensComponent,
+        AdminDashboardComponent,
     ],
     providers: [
         PasswordValidator,
@@ -175,13 +196,16 @@ import {TableModule} from 'primeng/table';
         ModalTestInstanceComponent,
         ModalNotificationSendComponent,
         DomainRolesDirective,
+        RolesExcludedDirective,
         SshKeysComponent,
         ModalProvideSshKeyComponent,
         PreferencesComponent,
         SortableHeaderDirective,
         DomainNamespaceAnnotationsComponent,
         AccessTokensComponent
-    ]
+    ],
+     schemas: [NO_ERRORS_SCHEMA, CUSTOM_ELEMENTS_SCHEMA]
+
 })
 export class SharedModule {
 }
diff --git a/src/app/shared/users/access-token/access-tokens.component.html b/src/app/shared/users/access-token/access-tokens.component.html
index e58fa61efbc62b07e6e9692877deb12fc3288b4c..81bd13e6bfcca04309f38b2a289c687c08046962 100644
--- a/src/app/shared/users/access-token/access-tokens.component.html
+++ b/src/app/shared/users/access-token/access-tokens.component.html
@@ -1,27 +1,29 @@
-<div style="margin-bottom: 15px;" class="panel panel-default">
-    <div class="panel-heading">{{'TOKENS.HEADER' | translate}}</div>
+<div style="padding-bottom: 15px;" class="background-section">
+    <div style="display: flex; justify-content:space-between">
+        <h4 style="font-size:15px; font-weight: bold">{{'TOKENS.HEADER' | translate}}</h4>
+        <button type="button" class="btn btn-text"
+                (click)="modal.show()">{{'TOKENS.NEW_TOKEN' | translate}}</button>
+    </div>
     <div class="panel-body">
         <table class="table table-hover" aria-describedby="User access tokens table">
             <thead>
             <tr>
                 <th scope="col">{{'TOKENS.TABLE.ID' | translate}}</th>
                 <th scope="col">{{'TOKENS.TABLE.NAME' | translate}}</th>
-                <th scope="col">{{'TOKENS.TABLE.VALUE' | translate}}</th>
                 <th scope="col">{{'TOKENS.TABLE.VALID' | translate}}</th>
                 <th scope="col">{{'TOKENS.TABLE.ACTIONS' | translate}}</th>
             </tr>
             </thead>
             <tbody>
             <tr *ngFor="let token of tokensList">
-                <td>{{token.id}}</td>
-                <td>{{token.name}}</td>
-                <td>{{token.tokenValue}}</td>
-                <td>{{token.valid}}</td>
-                <td *ngIf="token.valid">
+                <td style="width: 25%;">{{token.id}}</td>
+                <td style="width: 25%;">{{token.name}}</td>
+                <td style="width: 25%;">{{token.valid}}</td>
+                <td style="width: 25%;" *ngIf="token.valid">
                     <button type="button" class="btn btn-danger"
                             (click)="invalidate(token.id)">{{'TOKENS.BUTTON_INVALIDATE' | translate}}</button>
                 </td>
-                <td *ngIf="!token.valid">
+                <td style="width: 25%;" *ngIf="!token.valid">
                     <button type="button" class="btn btn-danger"
                             (click)="deleteToken(token.id)">{{'TOKENS.BUTTON_DELETE' | translate}}</button>
                 </td>
@@ -31,18 +33,14 @@
             </tr>
             </tbody>
         </table>
-        <div>
-            <button type="button" class="btn btn-success"
-                    (click)="modal.show()">{{'TOKENS.NEW_TOKEN' | translate}}</button>
 
-        </div>
     </div>
 </div>
 
 <nmaas-modal styleModal="info">
     <div class="nmaas-modal-header">{{'TOKENS.MODAL.HEADER' | translate}}</div>
     <div class="nmaas-modal-body" style="height: 60%; max-height: 80vh;overflow-y: auto;">
-        <form [formGroup]="requestForm" (ngSubmit)="createNewToken()">
+        <form *ngIf="!showCopyToken" [formGroup]="requestForm" (ngSubmit)="createNewToken()">
             <div class="form-group">
                 <label class="control-label" for="new-token-name">
                     {{'TOKENS.MODAL.NAME' | translate}}:
@@ -56,11 +54,29 @@
                 <div *ngIf="name.errors.notUnique">{{name.errors.message}}</div>
 
             </div>
-            <input type="submit" class="btn btn-success" value="{{'SSH_KEYS.MODAL.BUTTON_ADD' | translate}}"
-                   [disabled]="!requestForm.valid">
-            <button type="button" class="btn btn-primary pull-right"
-                    (click)="modal.hide()">{{'SSH_KEYS.MODAL.BUTTON_CANCEL' | translate}}</button>
+            <div style="display: flex; justify-content: flex-end">
+                <button type="button" class="btn btn-secondary mr-2"
+                        (click)="modal.hide()">{{'SSH_KEYS.MODAL.BUTTON_CANCEL' | translate}}</button>
+                <input type="submit" class="btn btn-primary" value="{{'SSH_KEYS.MODAL.BUTTON_ADD' | translate}}"
+                       [disabled]="!requestForm.valid">
+            </div>
+
+
 
         </form>
+        <div *ngIf="showCopyToken">
+                <span class="text-bold">
+                    {{"TOKENS.MODAL.TOKEN_COPY" | translate}}
+                </span>
+                <div>
+                    <p-inputGroup>
+                        <input pInputText [(ngModel)]="newToken.tokenValue"  readonly="true"  placeholder="Token to copy" />
+                        <button class="btn btn-secondary" type="button" (click)="copyToClipboard()">{{"TOKENS.MODAL.COPY" | translate}}</button>
+                    </p-inputGroup>
+                </div>
+                <div class="mt-6 flex ">
+                    <button class="btn btn-primary" type="button"  (click)="ConfirmAndClose()"  >{{"TOKENS.MODAL.TOKEN_SAVED" | translate}}</button>
+                </div>
+        </div>
     </div>
-</nmaas-modal>
\ No newline at end of file
+</nmaas-modal>
diff --git a/src/app/shared/users/access-token/access-tokens.component.ts b/src/app/shared/users/access-token/access-tokens.component.ts
index c901eb760d28787fd0d3209eaf474a858ec8f588..d3123d0cb97493131055103be59bf0058edb79c9 100644
--- a/src/app/shared/users/access-token/access-tokens.component.ts
+++ b/src/app/shared/users/access-token/access-tokens.component.ts
@@ -20,6 +20,9 @@ export class AccessTokensComponent implements OnInit {
 
     public newTokenName = '';
 
+    public showCopyToken = false;
+    public newToken :AccessToken;
+
     @ViewChild(ModalComponent, {static: true})
     public readonly modal: ModalComponent;
 
@@ -61,9 +64,9 @@ export class AccessTokensComponent implements OnInit {
     public createNewToken() {
         this.tokenService.createToken(this.requestForm.value.name.trim()).subscribe({
             next: val => {
-                this.tokensList.push(val)
                 this.requestForm.reset();
-                this.modal.hide();
+                this.showCopyToken = true;
+                this.newToken = val;
             },
             error: err => {
                 console.warn(err.error)
@@ -73,6 +76,24 @@ export class AccessTokensComponent implements OnInit {
         })
     }
 
+    public copyToClipboard() {
+        if (this.newToken.tokenValue) {
+            navigator.clipboard.writeText(this.newToken.tokenValue).then(() => {
+                console.log('Copied to clipbord');
+            }, (err) => {
+                console.error('Some errors accoured: ', err);
+            });
+        }
+    }
+
+    public ConfirmAndClose() {
+        this.showCopyToken = false;
+        this.newToken = null;
+        this.getData();
+        this.modal.hide();
+       
+    }
+
     get name() {
         return this.requestForm.get('name');
     }
diff --git a/src/app/shared/users/list/userslist.component.css b/src/app/shared/users/list/userslist.component.css
index 293357ddfa9e87687990d062df9f777337186781..018a8b04f96d66b5a17cad0ef9d105004dc2ad50 100644
--- a/src/app/shared/users/list/userslist.component.css
+++ b/src/app/shared/users/list/userslist.component.css
@@ -13,9 +13,9 @@ tr.clickable {
     cursor: pointer;
 }
 
-.dropdown:hover .dropdown-menu {
-    display: block;
-}
+/*.dropdown:hover .dropdown-menu {*/
+/*    display: block;*/
+/*}*/
 
 .align-vertically {
     display: flex;
@@ -32,50 +32,4 @@ li::marker {
     content: '';
     font-size: 0em;
 }
-:host ::ng-deep .p-datatable .p-datatable-thead > tr > th{
-    border: 1px solid #E0E2E5;
-    background:transparent;
-    border-width: 0 0 1px 0;
-}
-:host ::ng-deep .p-datatable .p-datatable-tbody > tr > td {
-    text-align: left;
-    border: 1px solid #E0E2E5;
-    border-width: 0 0 1px 0;
-    padding: 1rem 1rem;
-}
-:host ::ng-deep .p-datatable .p-paginator-bottom{
-    height: 40px;
-    background: transparent;
-    border: none;
-    margin-top:10px;
-}
-:host ::ng-deep .p-datatable .p-datatable-tbody > tr{
-    background: transparent;
-}
 
-:host ::ng-deep .p-paginator .p-paginator-pages .p-paginator-page{
-    transition: unset;
-    border-radius: 50%;
-    min-width:3.5rem;
-    height:3.5rem;
-    margin:0 5px;
-    font-size: 14px;
-}
-
-:host ::ng-deep .p-paginator-element{
-    border-radius:50%;
-    margin:0 5px;
-    min-width:3.5rem;
-    height:3.5rem;
-    font-size: 14px;
-}
-:host ::ng-deep .p-paginator .p-dropdown{
-    height:3rem;
-}
-:host ::ng-deep .p-paginator-icon{
-    height: 1.5rem;
-    width: 1.5rem;
-}
-:host ::ng-deep .p-paginator .p-dropdown .p-dropdown-label{
-    padding-right: 10px;
-}
diff --git a/src/app/shared/users/list/userslist.component.html b/src/app/shared/users/list/userslist.component.html
index 1f8eb8717e6f04680a4850b9492365035b303f3c..39d46e17d1dd501a7dc60d261a9cf9338ce8aa36 100644
--- a/src/app/shared/users/list/userslist.component.html
+++ b/src/app/shared/users/list/userslist.component.html
@@ -1,4 +1,31 @@
- <div class="" style="display: flex">
+<!-- <div class="col-sm-12 col-sm-10  col-md-12">
+    <h3>
+        {{ 'USERS.TITLE' | translate }}</h3>
+    <div class="flex space-between">
+        <div class="flex">
+            <button *ngIf="authService.hasDomainRole(domainId, 'ROLE_DOMAIN_ADMIN') || authService.hasDomainRole(domainId, 'ROLE_GROUP_DOMAIN_ADMIN')"
+                    class="btn btn-primary" (click)="changeMode()">
+                <span *ngIf="isModeAllowed(ComponentMode.DELETE)">{{'USERS.ADD_TO_DOMAIN_BUTTON' | translate}}</span>
+                <span *ngIf="isModeAllowed(ComponentMode.EDIT)">{{'USERS.GO_BACK_BUTTON' | translate}}</span>
+            </button>
+        </div>
+        <div class="" style="display: flex">
+            <div *ngIf="isModeAllowed(ComponentMode.DELETE)" class="flex ">
+                <span class="mt-2 pr-1">{{ 'USERS.ITEMS_PER_PAGE' | translate }}:</span>
+                <span id="selectionItems" class="dropdown"
+                      style="vertical-align: middle; display: inline-block; margin-right: 1rem;">
+        <button class="dropdown-toggle btn" data-toggle="dropdown" data-close-others="true">
+            {{maxItemsOnPage}}
+        </button>
+        <ul class="dropdown-menu">
+            <li *ngFor="let item of itemsPerPage" [ngClass]="{'active': maxItemsOnPage == item}">
+                <a (click)="setItems(item)">
+                    <span>{{item.toString()}}</span>
+                </a>
+            </li>
+        </ul>
+    </span>
+            </div>
 <!--            <div *ngIf="isModeAllowed(ComponentMode.DELETE)" class="flex ">-->
 <!--                <span class="mt-2 pr-1">{{ 'USERS.ITEMS_PER_PAGE' | translate }}:</span>-->
 <!--                <span id="selectionItems" class="dropdown"-->
@@ -15,6 +42,8 @@
 <!--                    </ul>-->
 <!--                </span>-->
 <!--            </div>-->
+<div class="" style="display: flex">
+
             <div *ngIf="isModeAllowed(ComponentMode.EDIT)"
                  style="margin-right: 15px; padding-top: 5px;"> {{'USERS.SEARCH' | translate}}</div>
 
@@ -29,43 +58,63 @@
                        class="form-control" (keyup)="onSearch($event.target.value)">
                 </span>
             </div>
-            <button *ngIf="authService.hasDomainRole(domainId, 'ROLE_DOMAIN_ADMIN') || authService.hasDomainRole(domainId, 'ROLE_VL_DOMAIN_ADMIN')"
+            <button *ngIf="authService.hasDomainRole(domainId, 'ROLE_DOMAIN_ADMIN') || authService.hasDomainRole(domainId, 'ROLE_GROUP_DOMAIN_ADMIN')"
                     class="btn btn-primary" (click)="changeMode()">
                 <span *ngIf="isModeAllowed(ComponentMode.DELETE)" >{{'USERS.ADD_TO_DOMAIN_BUTTON' | translate}}</span>
                 <span *ngIf="isModeAllowed(ComponentMode.EDIT)">{{'USERS.GO_BACK_BUTTON' | translate}}</span>
             </button>
  </div>
 
-    <h4 style="margin-top:40px; font-weight: bold"> {{ 'USERS.TITLE' | translate }}</h4>
+    <h4 class="header"> {{ 'USERS.TITLE' | translate }}</h4>
     <div class="background-section">
         <p-table #dt [value]="displayUsers" [paginator]="true" [rows]="maxItemsOnPage"
                  [rowsPerPageOptions]="[15, 20, 25, 30, 50]" >
             <ng-template pTemplate="header">
                 <tr>
-                    <th scope="col" class="column-sortable" sortable-column="username"
-                        sort-direction="asc">{{ 'USERS.USER_NAME' | translate }}</th>
-                    <th scope="col" class="column-sortable" sortable-column="lastname">{{'USERS.NAME' | translate}}</th>
-                    <th *ngIf="!domainMode" scope="col" class="column-sortable"
-                        sortable-column="email">{{'USERS.EMAIL' | translate}}</th>
-                    <th scope="col" class="column-sortable" sortable-column="domains"
-                        *ngIf="domainId === domainService.getGlobalDomainId()">{{ 'USERS.DOMAINS' | translate }}</th>
-                    <th scope="col" class="column-sortable" sortable-column="globalRole"
-                        *ngIf="domainId === domainService.getGlobalDomainId()">{{ 'USERS.GLOBAL_ROLE' | translate }}</th>
-                    <th scope="col" class="column-sortable" sortable-column="roles"
-                        *ngIf="domainId !== domainService.getGlobalDomainId() && !isModeAllowed(ComponentMode.EDIT)">{{ 'USERS.ROLES' | translate }}</th>
-                    <th scope="col" class="column-sortable" *ngIf="!isModeAllowed(ComponentMode.EDIT) && !domainMode"
-                        sortable-column="firstLoginDate">{{ 'USERS.FIRST_LOGIN' | translate }}</th>
-                    <th scope="col" class="column-sortable" *ngIf="!isModeAllowed(ComponentMode.EDIT) && !domainMode"
-                        sortable-column="lastSuccessfulLoginDate">{{ 'USERS.LAST_SUCCESSFUL_LOGIN' | translate }}</th>
-                    <th scope="col" class="column-sortable" sortable-column="enabled">{{ 'USERS.ENABLED' | translate }}</th>
+                    <th scope="col" class="column-sortable" pSortableColumn="username">
+                        {{ 'USERS.USER_NAME' | translate }}
+                        <p-sortIcon field="username"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" pSortableColumn="lastname">
+                        {{'USERS.NAME' | translate}}
+                        <p-sortIcon field="lastname"></p-sortIcon>
+                    </th>
+                    <th *ngIf="!domainMode" scope="col" class="column-sortable" pSortableColumn="email">
+                        {{'USERS.EMAIL' | translate}}
+                        <p-sortIcon field="email"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" pSortableColumn="domains" *ngIf="domainId === domainService.getGlobalDomainId()">
+                        {{ 'USERS.DOMAINS' | translate }}
+                        <p-sortIcon field="domains"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" pSortableColumn="globalRole" *ngIf="domainId === domainService.getGlobalDomainId()">
+                        {{ 'USERS.GLOBAL_ROLE' | translate }}
+                        <p-sortIcon field="globalRole"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" pSortableColumn="roles" *ngIf="domainId !== domainService.getGlobalDomainId() && !isModeAllowed(ComponentMode.EDIT)">
+                        {{ 'USERS.ROLES' | translate }}
+                        <p-sortIcon field="roles"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" *ngIf="!isModeAllowed(ComponentMode.EDIT) && !domainMode" pSortableColumn="firstLoginDate">
+                        {{ 'USERS.FIRST_LOGIN' | translate }}
+                        <p-sortIcon field="firstLoginDate"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" *ngIf="!isModeAllowed(ComponentMode.EDIT) && !domainMode" pSortableColumn="lastSuccessfulLoginDate">
+                        {{ 'USERS.LAST_SUCCESSFUL_LOGIN' | translate }}
+                        <p-sortIcon field="lastSuccessfulLoginDate"></p-sortIcon>
+                    </th>
+                    <th scope="col" class="column-sortable" pSortableColumn="enabled">
+                        {{ 'USERS.ENABLED' | translate }}
+                        <p-sortIcon field="enabled"></p-sortIcon>
+                    </th>
                     <th *ngIf="!isModeAllowed(ComponentMode.EDIT)" scope="col">&nbsp;</th>
                     <th *ngIf="isModeAllowed(ComponentMode.EDIT)" scope="col">&nbsp;</th>
                 </tr>
             </ng-template>
 
             <ng-template pTemplate="body" let-user>
-                <tr (click)="view(user.id)">
-                    <td>{{ user.username }}</td>
+                <tr>
+                    <td (click)="view(user.id)">{{ user.username }}</td>
                     <td>{{(user.firstname || '') + ' ' + (user.lastname || '')}}</td>
                     <td *ngIf="!domainMode">{{user.email}}</td>
                     <td *ngIf="domainId === domainService.getGlobalDomainId()">
@@ -88,7 +137,7 @@
                                          <strong class="caret"></strong>
                                         </span>
                                     </a>
-                                    <ul class="dropdown-menu">
+                                    <ul class="dropdown-menu"  style="left: 0; right:unset;">
                                         <li *ngFor="let role of getAllowedRoles()">
                                             <a (click)="changeUserRole(user,domainId, {value:role})">{{"ENUM.USER_ROLES." + Role[role].toUpperCase() | translate}}</a>
                                         </li>
@@ -121,7 +170,7 @@
                             <a style="display: inline-block" class="dropdown-toggle " aria-expanded="false"
                                aria-haspopup="true"
                                data-toggle="dropdown" href="#" role="button">
-                                <em class="fas fa-cog icon-black icon-bigger"></em>
+                                <em class="pi pi-cog" style="font-size: 1.8rem; color: var(--l-text-color)"></em>
                             </a>
                             <ul class="dropdown-menu pull-right-drop">
                                 <li *ngIf="isModeAllowed(ComponentMode.VIEW)">
diff --git a/src/app/shared/users/list/userslist.component.ts b/src/app/shared/users/list/userslist.component.ts
index 7394575d57a4f6d527893ff57c82ad1d4d71b007..1ae3116b57b2d986b67eaaef9d6ca6a47f96d777 100644
--- a/src/app/shared/users/list/userslist.component.ts
+++ b/src/app/shared/users/list/userslist.component.ts
@@ -101,11 +101,20 @@ export class UsersListComponent extends BaseComponent implements OnInit, OnChang
     }
 
     public getAllDomain() {
-        this.domainService.getAll().subscribe(domains => {
-            domains.forEach(domain => {
-                this.domainCache.setData(domain.id, domain)
+        if(this.domainMode) {
+            this.domainService.getMyDomains().subscribe(domains => {
+                domains.forEach(domain => { 
+                    this.domainCache.setData(domain.id, domain)
+                }
+            ) })
+        } else {
+            this.domainService.getAll().subscribe(domains => {
+                domains.forEach(domain => {
+                    this.domainCache.setData(domain.id, domain)
+                })
             })
-        })
+        }
+       
     }
 
     public getDomainName(domainId: number): Observable<string> {
diff --git a/src/app/shared/users/new-ssh-key/new-ssh-key.component.html b/src/app/shared/users/new-ssh-key/new-ssh-key.component.html
index d94339f5b282e7632f47b819c9eaf7e2a317b056..176ebdef2d70761f3ffeb7a3d6cfb241e931cb90 100644
--- a/src/app/shared/users/new-ssh-key/new-ssh-key.component.html
+++ b/src/app/shared/users/new-ssh-key/new-ssh-key.component.html
@@ -26,9 +26,10 @@
           <div *ngIf="key.errors.required">{{'SSH_KEYS.MODAL.ERROR.KEY_REQUIRED' | translate}}</div>
           <div *ngIf="key.errors.pattern">{{'SSH_KEYS.MODAL.ERROR.KEY_PATTERN' | translate}}</div>
         </div>
-
-        <input type="submit" style="border-radius: 4px" class="btn btn-primary" value="{{'SSH_KEYS.MODAL.BUTTON_ADD' | translate}}" [disabled]="!requestForm.valid">
-        <button type="button" class="btn btn-secondary pull-right" (click)="modal.hide()">{{'SSH_KEYS.MODAL.BUTTON_CANCEL' | translate}}</button>
+        <div style="display: flex; justify-content: flex-end">
+          <button type="button" class="btn btn-secondary mr-2" (click)="modal.hide()">{{'SSH_KEYS.MODAL.BUTTON_CANCEL' | translate}}</button>
+          <input type="submit" style="border-radius: 4px" class="btn btn-primary" value="{{'SSH_KEYS.MODAL.BUTTON_ADD' | translate}}" [disabled]="!requestForm.valid">
+        </div>
 
       </form>
       <div *ngIf="error" class="alert alert-danger">
diff --git a/src/app/shared/users/privileges/userprivileges.component.ts b/src/app/shared/users/privileges/userprivileges.component.ts
index a79b06dc31f7548cedea9b393c72cc847efbe11c..5c7e8d99875729dbfc43be8c7bab9b8e6920bd83 100644
--- a/src/app/shared/users/privileges/userprivileges.component.ts
+++ b/src/app/shared/users/privileges/userprivileges.component.ts
@@ -57,7 +57,7 @@ export class UserPrivilegesComponent extends BaseComponent implements OnInit {
         if (this.authService.hasRole(Role[Role.ROLE_SYSTEM_ADMIN]) &&
             Number(this.newPrivilegeForm.get('domainId').value) === this.domainService.getGlobalDomainId()) {
             // admin (global) role set
-            roles = [Role.ROLE_OPERATOR, Role.ROLE_TOOL_MANAGER, Role.ROLE_SYSTEM_ADMIN, Role.ROLE_VL_MANAGER];
+            roles = [Role.ROLE_OPERATOR, Role.ROLE_TOOL_MANAGER, Role.ROLE_SYSTEM_ADMIN, Role.ROLE_GROUP_MANAGER];
             roles = this.filterRoles(roles, this.newPrivilegeForm.get('domainId').value);
         } else if (this.newPrivilegeForm.get('domainId').value != null) {
             // default (domain) role set
diff --git a/src/app/shared/users/ssh-keys/ssh-keys.component.html b/src/app/shared/users/ssh-keys/ssh-keys.component.html
index e9025bddb5cd7796a569b04f68bb8cd26b94c772..7cc7808076580c866bce02ff27d905eafb96c18b 100644
--- a/src/app/shared/users/ssh-keys/ssh-keys.component.html
+++ b/src/app/shared/users/ssh-keys/ssh-keys.component.html
@@ -1,9 +1,11 @@
-<div style="margin-bottom: 15px;" class="panel panel-default">
-    <div class="panel-heading">{{'SSH_KEYS.HEADER' | translate}}</div>
+<div style="padding-bottom: 15px;" class="background-section">
+
+    <div style="display: flex; justify-content:space-between">
+        <h4 style="font-size:15px; font-weight: bold" >{{'SSH_KEYS.HEADER' | translate}}</h4>
+        <app-new-ssh-key [userMode]="userMode" [userId]="userId" (out)="getData()"></app-new-ssh-key>
+    </div>
     <div class="panel-body">
-        <div class="flex justify-content-end mb-4">
-            <app-new-ssh-key [userMode]="userMode" [userId]="userId" (out)="getData()"></app-new-ssh-key>
-        </div>
+
         <table class="table table-hover" aria-describedby="User ssh keys table">
             <thead>
             <tr>
diff --git a/src/app/welcome/complete/complete.component.html b/src/app/welcome/complete/complete.component.html
index 46cef36fa39df40e49ed75893af4cca1c04f3485..64acd24a4363e8f96d10fafc70258bc9b3eaea3c 100644
--- a/src/app/welcome/complete/complete.component.html
+++ b/src/app/welcome/complete/complete.component.html
@@ -6,7 +6,7 @@
                     <div class="row">
                         <div class="col-xs-3"></div>
                         <div class="text-center col-xs-6">
-                            <img alt="Geant logo" src="assets/images/geant-logo-small.png">
+                            <img alt="GÉANT logo" src="assets/images/geant-logo-small.png">
                         </div>
                         <div class="dropdown text-right drop-lang-div col-xs-3">
                             <a style="display: inline-block" class="dropdown-toggle" aria-expanded="false" aria-haspopup="true"
diff --git a/src/app/welcome/link-account/link-account.component.css b/src/app/welcome/link-account/link-account.component.css
new file mode 100644
index 0000000000000000000000000000000000000000..8b137891791fe96927ad78e64b0aad7bded08bdc
--- /dev/null
+++ b/src/app/welcome/link-account/link-account.component.css
@@ -0,0 +1 @@
+
diff --git a/src/app/welcome/link-account/link-account.component.html b/src/app/welcome/link-account/link-account.component.html
new file mode 100644
index 0000000000000000000000000000000000000000..2d75205238a0c5f83811c5aa3ebcb229b4d79d89
--- /dev/null
+++ b/src/app/welcome/link-account/link-account.component.html
@@ -0,0 +1,51 @@
+<div style="display: flex; justify-content: center;">
+    <div style="
+margin-top: 50px;
+ width: 60%
+" class="panel panel-default">
+        <div class="panel-heading">{{ 'ACCOUNT_LINKING.HEADER' | translate }}</div>
+        <div class="panel-body">
+            <form *ngIf="user"
+                  class="form-horizontal" #userDetailsForm="ngForm">
+                <div>
+                    <p>
+                        {{ 'ACCOUNT_LINKING.INFO' | translate }}
+                    </p>
+                </div>
+                <div class="form-group">
+                    <label class="col-sm-2 control-label">{{ 'USER_DETAILS.FIRST_NAME' | translate }}</label>
+                    <div class="col-sm-10">
+                        <p class="form-control-static">{{ user.firstname }}</p>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label class="col-sm-2 control-label">{{ 'USER_DETAILS.LAST_NAME' | translate }}</label>
+                    <div class="col-sm-10">
+                        <p class="form-control-static">{{ user.lastname }}</p>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label class="col-sm-2 control-label">{{ 'USER_DETAILS.EMAIL' | translate }}</label>
+                    <div class="col-sm-10">
+                        <p class="form-control-static">{{ user.email }}</p>
+                    </div>
+                </div>
+
+                <div class="form-group">
+                    <label for="password" class="col-sm-2 control-label">{{ 'PASSWORD.PASSWORD' | translate }}</label>
+                    <div class="col-sm-10">
+                        <input type="password" class="form-control" id="password"
+                               name="password" [(ngModel)]="password">
+                    </div>
+                </div>
+                <button type="submit" class="btn btn-primary"
+                        (click)="submit()">{{ 'ACCOUNT_LINKING.CONFIRM' | translate }}
+                </button>
+                <div *ngIf="error" class="alert alert-danger" style="margin-top: 20px">{{error}}</div>
+            </form>
+            <br>
+        </div>
+    </div>
+</div>
diff --git a/src/app/welcome/link-account/link-account.component.spec.ts b/src/app/welcome/link-account/link-account.component.spec.ts
new file mode 100644
index 0000000000000000000000000000000000000000..0b0a9f98c9b851dbd8f044e900df4b02595ca2ca
--- /dev/null
+++ b/src/app/welcome/link-account/link-account.component.spec.ts
@@ -0,0 +1,57 @@
+import {ComponentFixture, TestBed} from '@angular/core/testing';
+
+import {LinkAccountComponent} from './link-account.component';
+import {ActivatedRoute} from '@angular/router';
+import {of} from 'rxjs';
+import {AuthService} from '../../auth/auth.service';
+import {TranslateFakeLoader, TranslateLoader, TranslateModule} from '@ngx-translate/core';
+
+describe('LinkAccountComponent', () => {
+    let component: LinkAccountComponent;
+    let fixture: ComponentFixture<LinkAccountComponent>;
+
+    beforeEach(async () => {
+        await TestBed.configureTestingModule({
+            declarations: [LinkAccountComponent],
+            imports: [TranslateModule.forRoot({
+                loader: {
+                    provide: TranslateLoader,
+                    useClass: TranslateFakeLoader
+                }
+            })],
+            providers: [
+                {
+                    provide: ActivatedRoute,
+                    useValue: {
+                        queryParams: of({
+                            oidc_token: 'mocked.jwt.token'
+                        }),
+                        snapshot: {
+                            paramMap: {
+                                get: () => null
+                            }
+                        }
+                    }
+                },
+                {
+                    provide: AuthService,
+                    useValue: {
+                        isLogged: () => true,
+                        oidcLogout: jasmine.createSpy('oidcLogout'),
+                        oidcLinkingLogin: jasmine.createSpy('oidcLinkingLogin').and.returnValue(of({}))
+                    }
+                },
+
+            ]
+        })
+            .compileComponents();
+
+        fixture = TestBed.createComponent(LinkAccountComponent);
+        component = fixture.componentInstance;
+        fixture.detectChanges();
+    });
+
+    it('should create', () => {
+        expect(component).toBeTruthy();
+    });
+});
diff --git a/src/app/welcome/link-account/link-account.component.ts b/src/app/welcome/link-account/link-account.component.ts
new file mode 100644
index 0000000000000000000000000000000000000000..79b4133b77ec780ae9ab540481f9e87e4693d84d
--- /dev/null
+++ b/src/app/welcome/link-account/link-account.component.ts
@@ -0,0 +1,84 @@
+import {Component, OnDestroy, OnInit} from '@angular/core';
+import {User} from '../../model';
+import {ActivatedRoute, Router} from '@angular/router';
+import jwtDecode from 'jwt-decode';
+import {AuthService} from '../../auth/auth.service';
+import {TranslateService} from '@ngx-translate/core';
+
+
+@Component({
+    selector: 'app-link-account',
+    templateUrl: './link-account.component.html',
+    styleUrl: './link-account.component.css'
+})
+export class LinkAccountComponent implements OnInit, OnDestroy {
+    public user: User;
+    private token: string;
+    public password: string;
+    public error: string;
+
+    constructor(
+        private readonly route: ActivatedRoute,
+        private readonly authService: AuthService,
+        private readonly router: Router,
+        private translate: TranslateService,
+    ) {
+    }
+
+    ngOnDestroy() {
+        if (!this.authService.isLogged()) {
+            this.authService.oidcLogout(this.token)
+        }
+    }
+
+    ngOnInit() {
+        this.route.queryParams.subscribe(param => {
+            this.token = param['oidc-token'];
+            const decoded: TokenPayload = jwtDecode<TokenPayload>(this.token);
+            this.user = new User();
+            this.user.username = decoded.sub;
+            this.user.firstname = decoded.given_name;
+            this.user.lastname = decoded.family_name;
+            this.user.email = decoded.email;
+        })
+
+    }
+
+    public submit(): void {
+        this.authService.oidcLinkingLogin(
+            this.token,
+            this.user.email,
+            this.password,
+            this.user.username,
+            this.user.firstname,
+            this.user.lastname,
+        ).subscribe(
+            () => {
+                this.router.navigate(['/']);
+            },
+            err => {
+                this.error = this.translate.instant(this.getMessage(err));
+            }
+        )
+    }
+    private getMessage(err: any): string {
+        switch (err['status']) {
+            case 401:
+                return 'LOGIN.LOGIN_FAILURE_MESSAGE';
+            case 406:
+                return 'LOGIN.APPLICATION_UNDER_MAINTENANCE_MESSAGE';
+            case 409:
+                return 'GENERIC_MESSAGE.UNAVAILABLE_MESSAGE';
+            default:
+                return 'GENERIC_MESSAGE.UNAVAILABLE_MESSAGE';
+        }
+    }
+}
+
+
+interface TokenPayload {
+    sub: string;
+    email: string;
+    given_name: string;
+    family_name: string;
+}
diff --git a/src/app/welcome/login/login.component.html b/src/app/welcome/login/login.component.html
index 7fd223061e3430e40066581208df5f152c1d463a..af758ef732c5a46c8e251d7f66b454f6ae62ec88 100644
--- a/src/app/welcome/login/login.component.html
+++ b/src/app/welcome/login/login.component.html
@@ -26,7 +26,8 @@
     </fieldset>
 </form>
 <div class="form-group">
-    <button type="submit" (click)="triggerOIDC()" class="btn btn-primary btn-block">
+    <button type="submit" (click)="triggerOIDC()" class="btn btn-primary btn-block"
+            [disabled]="!this.configuration?.ssoLoginAllowed || loading || ssoLoading">
         {{ 'LOGIN.LOGIN_WITH' | translate }}
     </button>
     <img alt="sso" *ngIf="ssoLoading" src="data:"/>
diff --git a/src/app/welcome/login/login.component.spec.ts b/src/app/welcome/login/login.component.spec.ts
index 35e39bc620879877c64f1d11636786124b0439f8..f5ebbcf5ea4bef842108fda08b35ae7bdc1dd7d4 100644
--- a/src/app/welcome/login/login.component.spec.ts
+++ b/src/app/welcome/login/login.component.spec.ts
@@ -7,7 +7,6 @@ import {TranslateFakeLoader, TranslateLoader, TranslateModule} from '@ngx-transl
 import {ModalComponent} from '../../shared/modal';
 import {AuthService} from '../../auth/auth.service';
 import {ConfigurationService, UserService} from '../../service';
-import {SSOService} from '../../service/sso.service';
 import createSpyObj = jasmine.createSpyObj;
 import {of} from 'rxjs';
 import { HttpClientTestingModule } from '@angular/common/http/testing';
@@ -40,7 +39,6 @@ describe('Component: Login', () => {
             providers: [
                 {provide: AuthService, useValue: {}},
                 {provide: ConfigurationService, useValue: configServiceSpy},
-                {provide: SSOService, useValue: {}},
                 {provide: UserService, useValue: {}},
             ],
         }).compileComponents();
diff --git a/src/app/welcome/login/login.component.ts b/src/app/welcome/login/login.component.ts
index dbfcc78194a47a0585edbfd2d35d4b8ee52d32ff..0a4481b66e12318164be2249a30b512a6dfcf0c9 100644
--- a/src/app/welcome/login/login.component.ts
+++ b/src/app/welcome/login/login.component.ts
@@ -4,7 +4,6 @@ import {Router} from '@angular/router';
 import {AuthService} from '../../auth/auth.service';
 import {AppConfigService, ConfigurationService, UserService} from '../../service';
 import {Configuration} from '../../model/configuration';
-import {SSOService} from '../../service/sso.service';
 import {SSOConfig} from '../../model/sso';
 import {UntypedFormBuilder, UntypedFormGroup, Validators} from '@angular/forms';
 import {ModalComponent} from '../../shared/modal';
@@ -34,7 +33,6 @@ export class LoginComponent implements OnInit {
     constructor(private router: Router,
                 private auth: AuthService,
                 private configService: ConfigurationService,
-                private ssoService: SSOService,
                 private fb: UntypedFormBuilder,
                 private userService: UserService,
                 private translate: TranslateService,
@@ -47,12 +45,6 @@ export class LoginComponent implements OnInit {
     ngOnInit() {
         this.configService.getConfiguration().subscribe(config => {
             this.configuration = config;
-            if (config.ssoLoginAllowed) {
-                this.ssoService.getOne().subscribe(sso => {
-                    this.ssoConfig = sso;
-                    this.checkSSO();
-                });
-            }
         });
     }
 
@@ -72,42 +64,13 @@ export class LoginComponent implements OnInit {
         );
     }
 
+    // only for use in linking accounts
     public triggerOIDC() {
-        window.location.href = this.appConfig.getOidcUrl();
-    }
-
-    public checkSSO() {
-        const params = this.router.parseUrl(this.router.url).queryParams;
-
-        if ('ssoUserId' in params) {
-            // Got auth data, send to api
-            this.ssoLoading = true;
-            this.ssoError = '';
-            this.auth.propagateSSOLogin(params.ssoUserId).subscribe(
-                result => {
-                    if (result === true) {
-                        this.ssoLoading = false;
-                        this.translate.setDefaultLang(this.auth.getSelectedLanguage());
-                        this.translate.use(this.auth.getSelectedLanguage());
-                        this.router.navigate(['/']);
-                    } else {
-                        this.ssoError = 'Failed to propagate SSO user id';
-                        this.ssoLoading = false;
-                    }
-                },
-                err => {
-                    this.ssoError = this.translate.instant(this.getMessage(err));
-                    this.ssoLoading = false;
-                }
-            );
+        if (!this.configuration.maintenance) {
+            window.location.href = this.appConfig.getOidcUrl();
         }
     }
 
-    public triggerSSO() {
-        const url = window.location.href.replace(/ssoUserId=.+/, '');
-        window.location.href = this.ssoConfig.loginUrl + '?return=' + url;
-    }
-
     public sendResetNotification() {
         if (this.resetPasswordForm.valid) {
             this.userService.resetPasswordNotification(this.resetPasswordForm.controls['email'].value).subscribe(
diff --git a/src/app/welcome/logout/logout.component.spec.ts b/src/app/welcome/logout/logout.component.spec.ts
index e2e7d4c106d3cb949a4e25bd17b26566d346b828..8db6bfeb9cc5fdfee95e2aea5e4e64266bb7f9db 100644
--- a/src/app/welcome/logout/logout.component.spec.ts
+++ b/src/app/welcome/logout/logout.component.spec.ts
@@ -6,7 +6,6 @@ import createSpyObj = jasmine.createSpyObj;
 import {of} from 'rxjs';
 import {AuthService} from '../../auth/auth.service';
 import {ConfigurationService} from '../../service';
-import {SSOService} from '../../service/sso.service';
 
 describe('LogoutComponent', () => {
     let component: LogoutComponent;
@@ -29,7 +28,6 @@ describe('LogoutComponent', () => {
             providers: [
                 {provide: AuthService, useValue: authServiceSpy},
                 {provide: ConfigurationService, useValue: configServiceSpy},
-                {provide: SSOService, useValue: {}}
             ]
         })
             .compileComponents();
diff --git a/src/app/welcome/logout/logout.component.ts b/src/app/welcome/logout/logout.component.ts
index fb9c9e8263c2d0187a1cbcb3dd76bcee4bd1e3b1..4eaaa50f7df58c9ae99dccb68665c21597a652c5 100644
--- a/src/app/welcome/logout/logout.component.ts
+++ b/src/app/welcome/logout/logout.component.ts
@@ -3,7 +3,6 @@ import { Component, OnInit } from '@angular/core';
 import { Router } from '@angular/router';
 import { AuthService } from '../../auth/auth.service';
 import {ConfigurationService} from '../../service';
-import {SSOService} from '../../service/sso.service';
 
 
 @Component({
@@ -15,21 +14,12 @@ export class LogoutComponent implements OnInit {
 
   constructor(private router: Router,
               private auth: AuthService,
-              private configService: ConfigurationService,
-              private ssoService: SSOService) { }
+              private configService: ConfigurationService) { }
 
   ngOnInit() {
       this.auth.logout();
       this.configService.getConfiguration().subscribe(config => {
-          if (config.ssoLoginAllowed && this.auth.loginUsingSsoService) {
-              const url = window.location.origin;
-              this.ssoService.getOne().subscribe(sso => {
-                  // Shibboleth SP uses parameter 'target' instead of 'return'
-                  window.location.href = sso.logoutUrl + '?return=' + url;
-              });
-          } else {
               this.router.navigate(['/welcome']);
-          }
       });
   }
 
diff --git a/src/app/welcome/passwordreset/password-reset.component.html b/src/app/welcome/passwordreset/password-reset.component.html
index c62301d65a9f27622c178c45b8c299fa04ca760a..8c60eb985068cb262ef92924dabd30b0ca432958 100644
--- a/src/app/welcome/passwordreset/password-reset.component.html
+++ b/src/app/welcome/passwordreset/password-reset.component.html
@@ -4,7 +4,7 @@
       <div class="panel panel-default login-vertical-offset">
         <div class="panel-heading">
           <div class="text-center">
-            <img alt="Geant logo" src="assets/images/geant-logo-small.png">
+            <img alt="GÉANT logo" src="assets/images/geant-logo-small.png">
           </div>
         </div>
         <div class="panel-body" *ngIf="user">
diff --git a/src/app/welcome/passwordreset/password-reset.component.ts b/src/app/welcome/passwordreset/password-reset.component.ts
index 3694303c9c9f26926dba0b28bdb272d824c56160..755353da38a280b7147aab06bece2072de01f587 100644
--- a/src/app/welcome/passwordreset/password-reset.component.ts
+++ b/src/app/welcome/passwordreset/password-reset.component.ts
@@ -58,8 +58,11 @@ export class PasswordResetComponent implements OnInit {
     public resetPassword() {
         if (this.form.valid) {
             this.recaptchaV3Service.execute('password_reset').pipe(
-                catchError(_ => of('')), // in case of captcha error return empty token
+                catchError(error => {
+                    console.error(error);
+                    return of(error)}), // in case of captcha error return empty tokenin case of captcha error return empty token
             ).subscribe((captchaToken) => {
+                console.log(captchaToken)
                 this.showLoading = true;
                 this.passwordReset.password = this.form.controls['newPassword'].value;
                 this.passwordReset.token = this.token;
diff --git a/src/app/welcome/terms-acceptance/terms-acceptance.component.html b/src/app/welcome/terms-acceptance/terms-acceptance.component.html
index ce70113e91c73008691ffb22a2181a56b6a206c0..3605f9376128d984c7d9a38596cbdb918d9373bd 100644
--- a/src/app/welcome/terms-acceptance/terms-acceptance.component.html
+++ b/src/app/welcome/terms-acceptance/terms-acceptance.component.html
@@ -2,7 +2,7 @@
   <div class="row panel panel-default login-vertical-offset col-lg-offset-4 col-lg-4 col-md-4 col-md-offset-4 col-sm-6 col-sm-offset-3 col-xs-12">
     <div class="panel-heading">
       <div class="text-center">
-        <img alt="Geant logo" src="assets/images/geant-logo-small.png">
+        <img alt="GÉANT logo" src="assets/images/geant-logo-small.png">
       </div>
     </div>
     <div class="panel-body">
@@ -47,4 +47,4 @@
   </div>
 </nmaas-modal>
 <modal-info-terms></modal-info-terms>
-<modal-info-policy></modal-info-policy>
\ No newline at end of file
+<modal-info-policy></modal-info-policy>
diff --git a/src/app/welcome/welcome.module.ts b/src/app/welcome/welcome.module.ts
index 1e0ecde52c243ae5ed4004c6dce60bbe39f8c075..e212c4f059d959724211aa423e911d38b087f067 100644
--- a/src/app/welcome/welcome.module.ts
+++ b/src/app/welcome/welcome.module.ts
@@ -17,43 +17,44 @@ import {CompleteComponent} from './complete/complete.component';
 import {ContentDisplayService} from '../service/content-display.service';
 import {TermsAcceptanceComponent} from './terms-acceptance/terms-acceptance.component';
 import {TranslateModule} from '@ngx-translate/core';
-import {SSOService} from '../service/sso.service';
 import {PasswordResetComponent} from './passwordreset/password-reset.component';
 import {PasswordStrengthMeterComponent} from 'angular-password-strength-meter';
 import {PolicySubpageComponent} from './policy-subpage/policy-subpage.component';
+import {LinkAccountComponent} from './link-account/link-account.component';
 
 @NgModule({
-  declarations: [
-    WelcomeComponent,
-    LoginComponent,
-    LogoutComponent,
-    RegistrationComponent,
-    ProfileComponent,
-    CompleteComponent,
-    TermsAcceptanceComponent,
-    PasswordResetComponent,
-    PolicySubpageComponent
-  ],
-  imports: [
-    FormsModule,
-    ReactiveFormsModule,
-    CommonModule,
-    RouterModule,
-    SharedModule,
-    PipesModule,
-    AppMarketModule,
-    PasswordStrengthMeterComponent,
-    TranslateModule.forChild()
-  ],
-  exports: [
-    WelcomeComponent
-  ],
-  providers: [
-    RegistrationService,
-    UserService,
-    ChangelogService,
-    ContentDisplayService,
-    SSOService
-  ]
+    declarations: [
+        WelcomeComponent,
+        LoginComponent,
+        LogoutComponent,
+        RegistrationComponent,
+        ProfileComponent,
+        CompleteComponent,
+        TermsAcceptanceComponent,
+        PasswordResetComponent,
+        PolicySubpageComponent,
+        LinkAccountComponent
+    ],
+    imports: [
+        FormsModule,
+        ReactiveFormsModule,
+        CommonModule,
+        RouterModule,
+        SharedModule,
+        PipesModule,
+        AppMarketModule,
+        PasswordStrengthMeterComponent,
+        TranslateModule.forChild()
+    ],
+    exports: [
+        WelcomeComponent
+    ],
+    providers: [
+        RegistrationService,
+        UserService,
+        ChangelogService,
+        ContentDisplayService
+    ]
 })
-export class WelcomeModule {}
+export class WelcomeModule {
+}
diff --git a/src/assets/formio/config-template.json b/src/assets/formio/config-template.json
index 4f01f8c274ec539a2bf97f85f4d91142e72a2bb8..fe79f6dc84e9f22f76f9de4c119e722d51c99ebe 100644
--- a/src/assets/formio/config-template.json
+++ b/src/assets/formio/config-template.json
@@ -15,14 +15,7 @@
               "input": true,
               "tab": 0,
               "key": "configuration",
-              "components": [
-                {
-                  "type": "htmlelement",
-                  "input": false,
-                  "content": "<p>All required configuration should be applied using graphical interface</p>",
-                  "tab": 0
-                }
-              ]
+              "components": []
             }
           ]
         },
diff --git a/src/assets/images/nmaas-cloud.png b/src/assets/images/nmaas-cloud.png
new file mode 100644
index 0000000000000000000000000000000000000000..2790aa3f466f627706c59bdf8ecb8ad0e1f6499b
Binary files /dev/null and b/src/assets/images/nmaas-cloud.png differ
diff --git a/src/styles.css b/src/styles.css
index f96544036e2898e50df0f2e2b5111db494c2cd40..b467c8f239634fbb7639cfd5035144c2ca746c71 100644
--- a/src/styles.css
+++ b/src/styles.css
@@ -79,6 +79,10 @@
     margin:20px 0;
     padding:30px;
 }
+.header{
+    margin-top:40px;
+    font-weight: bold
+}
 .card {
     position: relative;
     display: -webkit-box;
@@ -165,3 +169,74 @@
     background: var(--primary-text-button-background-hover);
     color: var(--primary-text-button-text-hover)
 }
+
+.dropdown-menu{
+    right: 0;
+    left:unset;
+}
+
+.text-bold {
+    font-weight: 700;;
+}
+
+
+body .p-datatable .p-datatable-thead > tr > th{
+    border: 1px solid #E0E2E5;
+    background:transparent;
+    border-width: 0 0 1px 0;
+}
+body .p-datatable .p-datatable-tbody > tr > td {
+    text-align: left;
+    border: 1px solid #E0E2E5;
+    border-width: 0 0 1px 0;
+    padding: 1rem 1rem;
+}
+body .p-datatable .p-paginator-bottom{
+    height: 40px;
+    background: transparent;
+    border: none;
+    margin-top:10px;
+}
+body .p-datatable .p-datatable-tbody > tr{
+    background: transparent;
+}
+
+body .p-paginator .p-paginator-pages .p-paginator-page{
+    transition: unset;
+    border-radius: 50%;
+    min-width:3.5rem;
+    height:3.5rem;
+    margin:0 5px;
+    font-size: 14px;
+}
+
+body .p-paginator-element{
+    border-radius:50%;
+    margin:0 5px;
+    min-width:3.5rem;
+    height:3.5rem;
+    font-size: 14px;
+}
+body .p-paginator .p-dropdown{
+    height:3rem;
+}
+body .p-paginator-icon{
+    height: 1.5rem;
+    width: 1.5rem;
+}
+body .p-paginator .p-dropdown .p-dropdown-label{
+    padding-right: 10px;
+}
+
+body .p-paginator .p-paginator-pages .p-paginator-page.p-highlight{
+    background: var(--user-button-background-hover);
+}
+body .p-datatable>.p-datatable-wrapper {
+    overflow: visible;
+}
+body .p-datatable .p-sortable-column.p-highlight{
+    color: var(--primary-button-color);
+}
+body .p-datatable .p-sortable-column.p-highlight .p-sortable-column-icon{
+    color:var(--primary-button-color);
+}
diff --git a/ws/run_ws.sh b/ws/run_ws.sh
deleted file mode 100644
index 8763a587feed5aac2fcb74b297ebaed9481b0859..0000000000000000000000000000000000000000
--- a/ws/run_ws.sh
+++ /dev/null
@@ -1,7 +0,0 @@
-#!/bin/sh
-
-echo "Downloading WhiteSource agent..."
-curl -LJO https://github.com/whitesource/unified-agent-distribution/releases/latest/download/wss-unified-agent.jar
-
-echo "Running WhiteSource scan..."
-java -jar wss-unified-agent.jar -userKey ${USER_KEY} -apiKey ${API_KEY} -projectVersion ${PROJECT_VERSION} -projectToken ${PROJECT_TOKEN} -productVersion ${PRODUCT_VERSION} -productToken ${PRODUCT_TOKEN} -c ws.config -d ../
\ No newline at end of file