Explorar el Código

新增 settings, License Manage, ProductManagement, Device Manage,页面

lisiyan hace 2 años
padre
commit
c621927d63

+ 1 - 0
.eslintrc.cjs

@@ -112,5 +112,6 @@ module.exports = {
     "vue/space-infix-ops": "error",
     "vue/space-unary-ops": ["error", { words: true, nonwords: false }],
     "vue/template-curly-spacing": "error",
+    "vue/no-reserved-component-names": "off"
   },
 };

+ 5 - 0
.prettierrc.json

@@ -0,0 +1,5 @@
+{
+    "singleQuote": true,
+    "semi": false,
+    "trailingComma": "none"
+}

+ 2 - 0
package.json

@@ -12,10 +12,12 @@
   },
   "dependencies": {
     "axios": "^1.2.1",
+    "crypto-js": "^4.1.1",
     "element-ui": "^2.15.12",
     "pinia": "^2.0.16",
     "sass": "^1.57.1",
     "vue": "^2.7.7",
+    "vue-cookies": "^1.8.2",
     "vue-router": "^3.5.4"
   },
   "devDependencies": {

+ 273 - 300
pnpm-lock.yaml

@@ -7,6 +7,7 @@ specifiers:
   '@vue/eslint-config-prettier': ^7.0.0
   '@vue/test-utils': ^1.3.0
   axios: ^1.2.1
+  crypto-js: ^4.1.1
   cypress: ^10.3.0
   element-ui: ^2.15.12
   eslint: ^8.5.0
@@ -23,16 +24,19 @@ specifiers:
   vite-plugin-windicss: ^1.8.10
   vitest: ^0.18.1
   vue: ^2.7.7
+  vue-cookies: ^1.8.2
   vue-router: ^3.5.4
   vue-template-compiler: ^2.7.7
   windicss: ^3.5.6
 
 dependencies:
   axios: registry.npmmirror.com/axios/1.2.1
+  crypto-js: 4.1.1
   element-ui: registry.npmmirror.com/element-ui/2.15.12_vue@2.7.14
   pinia: registry.npmmirror.com/pinia/2.0.28_vue@2.7.14
   sass: registry.npmmirror.com/sass/1.57.1
   vue: registry.npmmirror.com/vue/2.7.14
+  vue-cookies: 1.8.2
   vue-router: registry.npmmirror.com/vue-router/3.6.5_vue@2.7.14
 
 devDependencies:
@@ -58,6 +62,245 @@ devDependencies:
 
 packages:
 
+  /@colors/colors/1.5.0:
+    resolution: {integrity: sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==}
+    engines: {node: '>=0.1.90'}
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /@esbuild/android-arm/0.15.18:
+    resolution: {integrity: sha512-5GT+kcs2WVGjVs7+boataCkO5Fg0y4kCjzkB5bAip7H4jfnOS3dA6KPiww9W1OEKTKeAcUVhdZGvgI65OXmUnw==}
+    engines: {node: '>=12'}
+    cpu: [arm]
+    os: [android]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /@esbuild/linux-loong64/0.15.18:
+    resolution: {integrity: sha512-L4jVKS82XVhw2nvzLg/19ClLWg0y27ulRwuP7lcyL6AbUWB5aPglXY3M21mauDQMDfRLs8cQmeT03r/+X3cZYQ==}
+    engines: {node: '>=12'}
+    cpu: [loong64]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /@types/yauzl/2.10.0:
+    resolution: {integrity: sha512-Cn6WYCm0tXv8p6k+A8PvbDG763EDpBoTzHdA+Q/MF6H3sapGjCm9NzoaJncJS9tUKSuCoDs9XHxYYsQDgxR6kw==}
+    requiresBuild: true
+    dependencies:
+      '@types/node': registry.npmmirror.com/@types/node/14.18.36
+    dev: true
+    optional: true
+
+  /crypto-js/4.1.1:
+    resolution: {integrity: sha512-o2JlM7ydqd3Qk9CA0L4NL6mTzU2sdx96a+oOfPu8Mkl/PK51vSyoi8/rQ8NknZtk44vq15lmhAj9CIAGwgeWKw==}
+    dev: false
+
+  /esbuild-android-64/0.15.18:
+    resolution: {integrity: sha512-wnpt3OXRhcjfIDSZu9bnzT4/TNTDsOUvip0foZOUBG7QbSt//w3QV4FInVJxNhKc/ErhUxc5z4QjHtMi7/TbgA==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [android]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-android-arm64/0.15.18:
+    resolution: {integrity: sha512-G4xu89B8FCzav9XU8EjsXacCKSG2FT7wW9J6hOc18soEHJdtWu03L3TQDGf0geNxfLTtxENKBzMSq9LlbjS8OQ==}
+    engines: {node: '>=12'}
+    cpu: [arm64]
+    os: [android]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-darwin-64/0.15.18:
+    resolution: {integrity: sha512-2WAvs95uPnVJPuYKP0Eqx+Dl/jaYseZEUUT1sjg97TJa4oBtbAKnPnl3b5M9l51/nbx7+QAEtuummJZW0sBEmg==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [darwin]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-darwin-arm64/0.15.18:
+    resolution: {integrity: sha512-tKPSxcTJ5OmNb1btVikATJ8NftlyNlc8BVNtyT/UAr62JFOhwHlnoPrhYWz09akBLHI9nElFVfWSTSRsrZiDUA==}
+    engines: {node: '>=12'}
+    cpu: [arm64]
+    os: [darwin]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-freebsd-64/0.15.18:
+    resolution: {integrity: sha512-TT3uBUxkteAjR1QbsmvSsjpKjOX6UkCstr8nMr+q7zi3NuZ1oIpa8U41Y8I8dJH2fJgdC3Dj3CXO5biLQpfdZA==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [freebsd]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-freebsd-arm64/0.15.18:
+    resolution: {integrity: sha512-R/oVr+X3Tkh+S0+tL41wRMbdWtpWB8hEAMsOXDumSSa6qJR89U0S/PpLXrGF7Wk/JykfpWNokERUpCeHDl47wA==}
+    engines: {node: '>=12'}
+    cpu: [arm64]
+    os: [freebsd]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-32/0.15.18:
+    resolution: {integrity: sha512-lphF3HiCSYtaa9p1DtXndiQEeQDKPl9eN/XNoBf2amEghugNuqXNZA/ZovthNE2aa4EN43WroO0B85xVSjYkbg==}
+    engines: {node: '>=12'}
+    cpu: [ia32]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-64/0.15.18:
+    resolution: {integrity: sha512-hNSeP97IviD7oxLKFuii5sDPJ+QHeiFTFLoLm7NZQligur8poNOWGIgpQ7Qf8Balb69hptMZzyOBIPtY09GZYw==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-arm/0.15.18:
+    resolution: {integrity: sha512-UH779gstRblS4aoS2qpMl3wjg7U0j+ygu3GjIeTonCcN79ZvpPee12Qun3vcdxX+37O5LFxz39XeW2I9bybMVA==}
+    engines: {node: '>=12'}
+    cpu: [arm]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-arm64/0.15.18:
+    resolution: {integrity: sha512-54qr8kg/6ilcxd+0V3h9rjT4qmjc0CccMVWrjOEM/pEcUzt8X62HfBSeZfT2ECpM7104mk4yfQXkosY8Quptug==}
+    engines: {node: '>=12'}
+    cpu: [arm64]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-mips64le/0.15.18:
+    resolution: {integrity: sha512-Mk6Ppwzzz3YbMl/ZZL2P0q1tnYqh/trYZ1VfNP47C31yT0K8t9s7Z077QrDA/guU60tGNp2GOwCQnp+DYv7bxQ==}
+    engines: {node: '>=12'}
+    cpu: [mips64el]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-ppc64le/0.15.18:
+    resolution: {integrity: sha512-b0XkN4pL9WUulPTa/VKHx2wLCgvIAbgwABGnKMY19WhKZPT+8BxhZdqz6EgkqCLld7X5qiCY2F/bfpUUlnFZ9w==}
+    engines: {node: '>=12'}
+    cpu: [ppc64]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-riscv64/0.15.18:
+    resolution: {integrity: sha512-ba2COaoF5wL6VLZWn04k+ACZjZ6NYniMSQStodFKH/Pu6RxzQqzsmjR1t9QC89VYJxBeyVPTaHuBMCejl3O/xg==}
+    engines: {node: '>=12'}
+    cpu: [riscv64]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-linux-s390x/0.15.18:
+    resolution: {integrity: sha512-VbpGuXEl5FCs1wDVp93O8UIzl3ZrglgnSQ+Hu79g7hZu6te6/YHgVJxCM2SqfIila0J3k0csfnf8VD2W7u2kzQ==}
+    engines: {node: '>=12'}
+    cpu: [s390x]
+    os: [linux]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-netbsd-64/0.15.18:
+    resolution: {integrity: sha512-98ukeCdvdX7wr1vUYQzKo4kQ0N2p27H7I11maINv73fVEXt2kyh4K4m9f35U1K43Xc2QGXlzAw0K9yoU7JUjOg==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [netbsd]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-openbsd-64/0.15.18:
+    resolution: {integrity: sha512-yK5NCcH31Uae076AyQAXeJzt/vxIo9+omZRKj1pauhk3ITuADzuOx5N2fdHrAKPxN+zH3w96uFKlY7yIn490xQ==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [openbsd]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-sunos-64/0.15.18:
+    resolution: {integrity: sha512-On22LLFlBeLNj/YF3FT+cXcyKPEI263nflYlAhz5crxtp3yRG1Ugfr7ITyxmCmjm4vbN/dGrb/B7w7U8yJR9yw==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [sunos]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-windows-32/0.15.18:
+    resolution: {integrity: sha512-o+eyLu2MjVny/nt+E0uPnBxYuJHBvho8vWsC2lV61A7wwTWC3jkN2w36jtA+yv1UgYkHRihPuQsL23hsCYGcOQ==}
+    engines: {node: '>=12'}
+    cpu: [ia32]
+    os: [win32]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-windows-64/0.15.18:
+    resolution: {integrity: sha512-qinug1iTTaIIrCorAUjR0fcBk24fjzEedFYhhispP8Oc7SFvs+XeW3YpAKiKp8dRpizl4YYAhxMjlftAMJiaUw==}
+    engines: {node: '>=12'}
+    cpu: [x64]
+    os: [win32]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /esbuild-windows-arm64/0.15.18:
+    resolution: {integrity: sha512-q9bsYzegpZcLziq0zgUi5KqGVtfhjxGbnksaBFYmWLxeV/S1fK4OLdq2DFYnXcLMjlZw2L0jLsk1eGoB522WXQ==}
+    engines: {node: '>=12'}
+    cpu: [arm64]
+    os: [win32]
+    requiresBuild: true
+    dev: true
+    optional: true
+
+  /fsevents/2.3.2:
+    resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==}
+    engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0}
+    os: [darwin]
+    requiresBuild: true
+    optional: true
+
+  /graceful-fs/4.2.10:
+    resolution: {integrity: sha512-9ByhssR2fPVsNZj478qUUbKfmL0+t5BDVyjShtyZZLiK7ZDAArFFfopyOTj0M05wE2tJPisA4iTnnXl2YoPvOA==}
+    dev: true
+    optional: true
+
+  /source-map/0.6.1:
+    resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==}
+    engines: {node: '>=0.10.0'}
+    dev: true
+    optional: true
+
+  /vue-cookies/1.8.2:
+    resolution: {integrity: sha512-+NfoC5l+7ybuVwpnqsf52qndnoYMjEb4EFhX4/j9RzzQP00dNzuJELsWuW2p8omNUzNlSgWGVyyWoOeJr347tw==}
+    dev: false
+
   registry.npmmirror.com/@antfu/utils/0.7.2:
     resolution: {integrity: sha512-vy9fM3pIxZmX07dL+VX1aZe7ynZ+YyB0jY+jE6r3hOK6GNY2t6W8rzpFC4tgpbXUYABkFQwgJq2XYXlxbXAI0g==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@antfu/utils/-/utils-0.7.2.tgz}
     name: '@antfu/utils'
@@ -102,15 +345,6 @@ packages:
       '@babel/helper-validator-identifier': registry.npmmirror.com/@babel/helper-validator-identifier/7.19.1
       to-fast-properties: registry.npmmirror.com/to-fast-properties/2.0.0
 
-  registry.npmmirror.com/@colors/colors/1.5.0:
-    resolution: {integrity: sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@colors/colors/-/colors-1.5.0.tgz}
-    name: '@colors/colors'
-    version: 1.5.0
-    engines: {node: '>=0.1.90'}
-    requiresBuild: true
-    dev: true
-    optional: true
-
   registry.npmmirror.com/@cypress/request/2.88.10:
     resolution: {integrity: sha512-Zp7F+R93N0yZyG34GutyTNr+okam7s/Fzc1+i3kcqOP8vk6OuajuE9qZJ6Rs+10/1JFtXFYMdyarnU1rZuJesg==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@cypress/request/-/request-2.88.10.tgz}
     name: '@cypress/request'
@@ -149,28 +383,6 @@ packages:
       - supports-color
     dev: true
 
-  registry.npmmirror.com/@esbuild/android-arm/0.15.18:
-    resolution: {integrity: sha512-5GT+kcs2WVGjVs7+boataCkO5Fg0y4kCjzkB5bAip7H4jfnOS3dA6KPiww9W1OEKTKeAcUVhdZGvgI65OXmUnw==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@esbuild/android-arm/-/android-arm-0.15.18.tgz}
-    name: '@esbuild/android-arm'
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm]
-    os: [android]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/@esbuild/linux-loong64/0.15.18:
-    resolution: {integrity: sha512-L4jVKS82XVhw2nvzLg/19ClLWg0y27ulRwuP7lcyL6AbUWB5aPglXY3M21mauDQMDfRLs8cQmeT03r/+X3cZYQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@esbuild/linux-loong64/-/linux-loong64-0.15.18.tgz}
-    name: '@esbuild/linux-loong64'
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [loong64]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
   registry.npmmirror.com/@eslint/eslintrc/1.4.0:
     resolution: {integrity: sha512-7yfvXy6MWLgWSFsLhz5yH3iQ52St8cdUY6FoGieKkRDVxuxmrNuUetIuu6cmjNWwniUHiWXjxCr5tTXDrbYS5A==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@eslint/eslintrc/-/eslintrc-1.4.0.tgz}
     name: '@eslint/eslintrc'
@@ -408,16 +620,6 @@ packages:
     version: 2.3.3
     dev: true
 
-  registry.npmmirror.com/@types/yauzl/2.10.0:
-    resolution: {integrity: sha512-Cn6WYCm0tXv8p6k+A8PvbDG763EDpBoTzHdA+Q/MF6H3sapGjCm9NzoaJncJS9tUKSuCoDs9XHxYYsQDgxR6kw==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@types/yauzl/-/yauzl-2.10.0.tgz}
-    name: '@types/yauzl'
-    version: 2.10.0
-    requiresBuild: true
-    dependencies:
-      '@types/node': registry.npmmirror.com/@types/node/14.18.36
-    dev: true
-    optional: true
-
   registry.npmmirror.com/@vitejs/plugin-legacy/2.3.1_terser@5.16.1+vite@3.2.5:
     resolution: {integrity: sha512-J5KaGBlSt2tEYPVjM/C8dA6DkRzkFkbPe+Xb4IX5G+XOV5OGbVAfkMjKywdrkO3gGynO8S98i71Lmsff4cWkCQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/@vitejs/plugin-legacy/-/plugin-legacy-2.3.1.tgz}
     id: registry.npmmirror.com/@vitejs/plugin-legacy/2.3.1
@@ -929,7 +1131,7 @@ packages:
       normalize-path: registry.npmmirror.com/normalize-path/3.0.0
       readdirp: registry.npmmirror.com/readdirp/3.6.0
     optionalDependencies:
-      fsevents: registry.npmmirror.com/fsevents/2.3.2
+      fsevents: 2.3.2
 
   registry.npmmirror.com/ci-info/3.7.0:
     resolution: {integrity: sha512-2CpRNYmImPx+RXKLq6jko/L07phmS9I02TyqkcNU20GCF/GgaWvc58hPtjxDX8lPpkdwc9sNh72V9k00S7ezog==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/ci-info/-/ci-info-3.7.0.tgz}
@@ -962,7 +1164,7 @@ packages:
     dependencies:
       string-width: registry.npmmirror.com/string-width/4.2.3
     optionalDependencies:
-      '@colors/colors': registry.npmmirror.com/@colors/colors/1.5.0
+      '@colors/colors': 1.5.0
     dev: true
 
   registry.npmmirror.com/cli-truncate/2.1.0:
@@ -1377,226 +1579,6 @@ packages:
     engines: {node: '>=0.12'}
     dev: true
 
-  registry.npmmirror.com/esbuild-android-64/0.15.18:
-    resolution: {integrity: sha512-wnpt3OXRhcjfIDSZu9bnzT4/TNTDsOUvip0foZOUBG7QbSt//w3QV4FInVJxNhKc/ErhUxc5z4QjHtMi7/TbgA==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-android-64/-/esbuild-android-64-0.15.18.tgz}
-    name: esbuild-android-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [android]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-android-arm64/0.15.18:
-    resolution: {integrity: sha512-G4xu89B8FCzav9XU8EjsXacCKSG2FT7wW9J6hOc18soEHJdtWu03L3TQDGf0geNxfLTtxENKBzMSq9LlbjS8OQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-android-arm64/-/esbuild-android-arm64-0.15.18.tgz}
-    name: esbuild-android-arm64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm64]
-    os: [android]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-darwin-64/0.15.18:
-    resolution: {integrity: sha512-2WAvs95uPnVJPuYKP0Eqx+Dl/jaYseZEUUT1sjg97TJa4oBtbAKnPnl3b5M9l51/nbx7+QAEtuummJZW0sBEmg==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-darwin-64/-/esbuild-darwin-64-0.15.18.tgz}
-    name: esbuild-darwin-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [darwin]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-darwin-arm64/0.15.18:
-    resolution: {integrity: sha512-tKPSxcTJ5OmNb1btVikATJ8NftlyNlc8BVNtyT/UAr62JFOhwHlnoPrhYWz09akBLHI9nElFVfWSTSRsrZiDUA==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-darwin-arm64/-/esbuild-darwin-arm64-0.15.18.tgz}
-    name: esbuild-darwin-arm64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm64]
-    os: [darwin]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-freebsd-64/0.15.18:
-    resolution: {integrity: sha512-TT3uBUxkteAjR1QbsmvSsjpKjOX6UkCstr8nMr+q7zi3NuZ1oIpa8U41Y8I8dJH2fJgdC3Dj3CXO5biLQpfdZA==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-freebsd-64/-/esbuild-freebsd-64-0.15.18.tgz}
-    name: esbuild-freebsd-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [freebsd]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-freebsd-arm64/0.15.18:
-    resolution: {integrity: sha512-R/oVr+X3Tkh+S0+tL41wRMbdWtpWB8hEAMsOXDumSSa6qJR89U0S/PpLXrGF7Wk/JykfpWNokERUpCeHDl47wA==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-freebsd-arm64/-/esbuild-freebsd-arm64-0.15.18.tgz}
-    name: esbuild-freebsd-arm64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm64]
-    os: [freebsd]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-32/0.15.18:
-    resolution: {integrity: sha512-lphF3HiCSYtaa9p1DtXndiQEeQDKPl9eN/XNoBf2amEghugNuqXNZA/ZovthNE2aa4EN43WroO0B85xVSjYkbg==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-32/-/esbuild-linux-32-0.15.18.tgz}
-    name: esbuild-linux-32
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [ia32]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-64/0.15.18:
-    resolution: {integrity: sha512-hNSeP97IviD7oxLKFuii5sDPJ+QHeiFTFLoLm7NZQligur8poNOWGIgpQ7Qf8Balb69hptMZzyOBIPtY09GZYw==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-64/-/esbuild-linux-64-0.15.18.tgz}
-    name: esbuild-linux-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-arm/0.15.18:
-    resolution: {integrity: sha512-UH779gstRblS4aoS2qpMl3wjg7U0j+ygu3GjIeTonCcN79ZvpPee12Qun3vcdxX+37O5LFxz39XeW2I9bybMVA==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-arm/-/esbuild-linux-arm-0.15.18.tgz}
-    name: esbuild-linux-arm
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-arm64/0.15.18:
-    resolution: {integrity: sha512-54qr8kg/6ilcxd+0V3h9rjT4qmjc0CccMVWrjOEM/pEcUzt8X62HfBSeZfT2ECpM7104mk4yfQXkosY8Quptug==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-arm64/-/esbuild-linux-arm64-0.15.18.tgz}
-    name: esbuild-linux-arm64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm64]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-mips64le/0.15.18:
-    resolution: {integrity: sha512-Mk6Ppwzzz3YbMl/ZZL2P0q1tnYqh/trYZ1VfNP47C31yT0K8t9s7Z077QrDA/guU60tGNp2GOwCQnp+DYv7bxQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-mips64le/-/esbuild-linux-mips64le-0.15.18.tgz}
-    name: esbuild-linux-mips64le
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [mips64el]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-ppc64le/0.15.18:
-    resolution: {integrity: sha512-b0XkN4pL9WUulPTa/VKHx2wLCgvIAbgwABGnKMY19WhKZPT+8BxhZdqz6EgkqCLld7X5qiCY2F/bfpUUlnFZ9w==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-ppc64le/-/esbuild-linux-ppc64le-0.15.18.tgz}
-    name: esbuild-linux-ppc64le
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [ppc64]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-riscv64/0.15.18:
-    resolution: {integrity: sha512-ba2COaoF5wL6VLZWn04k+ACZjZ6NYniMSQStodFKH/Pu6RxzQqzsmjR1t9QC89VYJxBeyVPTaHuBMCejl3O/xg==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-riscv64/-/esbuild-linux-riscv64-0.15.18.tgz}
-    name: esbuild-linux-riscv64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [riscv64]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-linux-s390x/0.15.18:
-    resolution: {integrity: sha512-VbpGuXEl5FCs1wDVp93O8UIzl3ZrglgnSQ+Hu79g7hZu6te6/YHgVJxCM2SqfIila0J3k0csfnf8VD2W7u2kzQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-linux-s390x/-/esbuild-linux-s390x-0.15.18.tgz}
-    name: esbuild-linux-s390x
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [s390x]
-    os: [linux]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-netbsd-64/0.15.18:
-    resolution: {integrity: sha512-98ukeCdvdX7wr1vUYQzKo4kQ0N2p27H7I11maINv73fVEXt2kyh4K4m9f35U1K43Xc2QGXlzAw0K9yoU7JUjOg==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-netbsd-64/-/esbuild-netbsd-64-0.15.18.tgz}
-    name: esbuild-netbsd-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [netbsd]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-openbsd-64/0.15.18:
-    resolution: {integrity: sha512-yK5NCcH31Uae076AyQAXeJzt/vxIo9+omZRKj1pauhk3ITuADzuOx5N2fdHrAKPxN+zH3w96uFKlY7yIn490xQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-openbsd-64/-/esbuild-openbsd-64-0.15.18.tgz}
-    name: esbuild-openbsd-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [openbsd]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-sunos-64/0.15.18:
-    resolution: {integrity: sha512-On22LLFlBeLNj/YF3FT+cXcyKPEI263nflYlAhz5crxtp3yRG1Ugfr7ITyxmCmjm4vbN/dGrb/B7w7U8yJR9yw==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-sunos-64/-/esbuild-sunos-64-0.15.18.tgz}
-    name: esbuild-sunos-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [sunos]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-windows-32/0.15.18:
-    resolution: {integrity: sha512-o+eyLu2MjVny/nt+E0uPnBxYuJHBvho8vWsC2lV61A7wwTWC3jkN2w36jtA+yv1UgYkHRihPuQsL23hsCYGcOQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-windows-32/-/esbuild-windows-32-0.15.18.tgz}
-    name: esbuild-windows-32
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [ia32]
-    os: [win32]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-windows-64/0.15.18:
-    resolution: {integrity: sha512-qinug1iTTaIIrCorAUjR0fcBk24fjzEedFYhhispP8Oc7SFvs+XeW3YpAKiKp8dRpizl4YYAhxMjlftAMJiaUw==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-windows-64/-/esbuild-windows-64-0.15.18.tgz}
-    name: esbuild-windows-64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [x64]
-    os: [win32]
-    requiresBuild: true
-    dev: true
-    optional: true
-
-  registry.npmmirror.com/esbuild-windows-arm64/0.15.18:
-    resolution: {integrity: sha512-q9bsYzegpZcLziq0zgUi5KqGVtfhjxGbnksaBFYmWLxeV/S1fK4OLdq2DFYnXcLMjlZw2L0jLsk1eGoB522WXQ==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild-windows-arm64/-/esbuild-windows-arm64-0.15.18.tgz}
-    name: esbuild-windows-arm64
-    version: 0.15.18
-    engines: {node: '>=12'}
-    cpu: [arm64]
-    os: [win32]
-    requiresBuild: true
-    dev: true
-    optional: true
-
   registry.npmmirror.com/esbuild/0.15.18:
     resolution: {integrity: sha512-x/R72SmW3sSFRm5zrrIjAhCeQSAWoni3CmHEqfQrZIQTM3lVCdehdwuIqaOtfC2slvpdlLa62GYoN8SxT23m6Q==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/esbuild/-/esbuild-0.15.18.tgz}
     name: esbuild
@@ -1605,28 +1587,28 @@ packages:
     hasBin: true
     requiresBuild: true
     optionalDependencies:
-      '@esbuild/android-arm': registry.npmmirror.com/@esbuild/android-arm/0.15.18
-      '@esbuild/linux-loong64': registry.npmmirror.com/@esbuild/linux-loong64/0.15.18
-      esbuild-android-64: registry.npmmirror.com/esbuild-android-64/0.15.18
-      esbuild-android-arm64: registry.npmmirror.com/esbuild-android-arm64/0.15.18
-      esbuild-darwin-64: registry.npmmirror.com/esbuild-darwin-64/0.15.18
-      esbuild-darwin-arm64: registry.npmmirror.com/esbuild-darwin-arm64/0.15.18
-      esbuild-freebsd-64: registry.npmmirror.com/esbuild-freebsd-64/0.15.18
-      esbuild-freebsd-arm64: registry.npmmirror.com/esbuild-freebsd-arm64/0.15.18
-      esbuild-linux-32: registry.npmmirror.com/esbuild-linux-32/0.15.18
-      esbuild-linux-64: registry.npmmirror.com/esbuild-linux-64/0.15.18
-      esbuild-linux-arm: registry.npmmirror.com/esbuild-linux-arm/0.15.18
-      esbuild-linux-arm64: registry.npmmirror.com/esbuild-linux-arm64/0.15.18
-      esbuild-linux-mips64le: registry.npmmirror.com/esbuild-linux-mips64le/0.15.18
-      esbuild-linux-ppc64le: registry.npmmirror.com/esbuild-linux-ppc64le/0.15.18
-      esbuild-linux-riscv64: registry.npmmirror.com/esbuild-linux-riscv64/0.15.18
-      esbuild-linux-s390x: registry.npmmirror.com/esbuild-linux-s390x/0.15.18
-      esbuild-netbsd-64: registry.npmmirror.com/esbuild-netbsd-64/0.15.18
-      esbuild-openbsd-64: registry.npmmirror.com/esbuild-openbsd-64/0.15.18
-      esbuild-sunos-64: registry.npmmirror.com/esbuild-sunos-64/0.15.18
-      esbuild-windows-32: registry.npmmirror.com/esbuild-windows-32/0.15.18
-      esbuild-windows-64: registry.npmmirror.com/esbuild-windows-64/0.15.18
-      esbuild-windows-arm64: registry.npmmirror.com/esbuild-windows-arm64/0.15.18
+      '@esbuild/android-arm': 0.15.18
+      '@esbuild/linux-loong64': 0.15.18
+      esbuild-android-64: 0.15.18
+      esbuild-android-arm64: 0.15.18
+      esbuild-darwin-64: 0.15.18
+      esbuild-darwin-arm64: 0.15.18
+      esbuild-freebsd-64: 0.15.18
+      esbuild-freebsd-arm64: 0.15.18
+      esbuild-linux-32: 0.15.18
+      esbuild-linux-64: 0.15.18
+      esbuild-linux-arm: 0.15.18
+      esbuild-linux-arm64: 0.15.18
+      esbuild-linux-mips64le: 0.15.18
+      esbuild-linux-ppc64le: 0.15.18
+      esbuild-linux-riscv64: 0.15.18
+      esbuild-linux-s390x: 0.15.18
+      esbuild-netbsd-64: 0.15.18
+      esbuild-openbsd-64: 0.15.18
+      esbuild-sunos-64: 0.15.18
+      esbuild-windows-32: 0.15.18
+      esbuild-windows-64: 0.15.18
+      esbuild-windows-arm64: 0.15.18
     dev: true
 
   registry.npmmirror.com/escape-string-regexp/1.0.5:
@@ -1655,7 +1637,7 @@ packages:
       esutils: registry.npmmirror.com/esutils/2.0.3
       optionator: registry.npmmirror.com/optionator/0.8.3
     optionalDependencies:
-      source-map: registry.npmmirror.com/source-map/0.6.1
+      source-map: 0.6.1
     dev: true
 
   registry.npmmirror.com/eslint-config-prettier/8.5.0_eslint@8.30.0:
@@ -1957,7 +1939,7 @@ packages:
       get-stream: registry.npmmirror.com/get-stream/5.2.0
       yauzl: registry.npmmirror.com/yauzl/2.10.0
     optionalDependencies:
-      '@types/yauzl': registry.npmmirror.com/@types/yauzl/2.10.0
+      '@types/yauzl': 2.10.0
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -2136,15 +2118,6 @@ packages:
     version: 1.0.0
     dev: true
 
-  registry.npmmirror.com/fsevents/2.3.2:
-    resolution: {integrity: sha512-xiqMQR4xAeHTuB9uWm+fFRcIOgKBMiOBP+eXiyT7jsgVCq1bkVygt00oASowB7EdtpOHaaPgKt812P9ab+DDKA==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/fsevents/-/fsevents-2.3.2.tgz}
-    name: fsevents
-    version: 2.3.2
-    engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0}
-    os: [darwin]
-    requiresBuild: true
-    optional: true
-
   registry.npmmirror.com/function-bind/1.1.1:
     resolution: {integrity: sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==, registry: http://registry.npm.taobao.org/, tarball: https://registry.npmmirror.com/function-bind/-/function-bind-1.1.1.tgz}
     name: function-bind
@@ -2684,7 +2657,7 @@ packages:
     dependencies:
       universalify: registry.npmmirror.com/universalify/2.0.0
     optionalDependencies:
-      graceful-fs: registry.npmmirror.com/graceful-fs/4.2.10
+      graceful-fs: 4.2.10
     dev: true
 
   registry.npmmirror.com/jsprim/2.0.2:
@@ -3441,7 +3414,7 @@ packages:
     engines: {node: '>=10.0.0'}
     hasBin: true
     optionalDependencies:
-      fsevents: registry.npmmirror.com/fsevents/2.3.2
+      fsevents: 2.3.2
     dev: true
 
   registry.npmmirror.com/run-parallel/1.2.0:
@@ -4006,7 +3979,7 @@ packages:
       sass: registry.npmmirror.com/sass/1.57.1
       terser: registry.npmmirror.com/terser/5.16.1
     optionalDependencies:
-      fsevents: registry.npmmirror.com/fsevents/2.3.2
+      fsevents: 2.3.2
     dev: true
 
   registry.npmmirror.com/vite/3.2.5_zxbrnrc4iyldik6mikh3pswz4i:
@@ -4045,7 +4018,7 @@ packages:
       sass: registry.npmmirror.com/sass/1.57.1
       terser: registry.npmmirror.com/terser/5.16.1
     optionalDependencies:
-      fsevents: registry.npmmirror.com/fsevents/2.3.2
+      fsevents: 2.3.2
     dev: true
 
   registry.npmmirror.com/vitest/0.18.1_m56nrrnamstgopt75m5z676faa:

+ 9 - 2
src/App.vue

@@ -1,11 +1,18 @@
-<script setup>
+<script>
 import Aside from '@/components/Aside.vue'
+
+export default {
+  name:'app',
+  components:{
+    Aside
+  },
+}
 </script>
 
 <template>
   <div id="app">
     <el-container>
-      <el-aside width="260px"><Aside /></el-aside>
+      <el-aside width="260px"  v-if="$route.fullPath !== '/login' && $route.fullPath !== '/create' && $route.fullPath !== '/forgotpassword'"><Aside /></el-aside>
       <el-main><router-view /></el-main>
     </el-container>
   </div>

+ 29 - 5
src/components/Aside.vue

@@ -1,4 +1,5 @@
-<script setup>
+<script>
+import { onMounted, ref } from "vue"
 import Dashboard from '@/components/icon/menu_dashboard.vue'
 import Product from '@/components/icon/menu_product.vue'
 import Team from '@/components/icon/menu_team.vue'
@@ -6,6 +7,29 @@ import License from '@/components/icon/menu_license.vue'
 import Device from '@/components/icon/menu_device.vue'
 import Settings from '@/components/icon/menu_setting.vue'
 import Support from '@/components/icon/menu_support.vue'
+import { Aside } from 'element-ui'
+export default {
+  name:'Aside',
+  components:{
+    Dashboard,
+    Product,
+    Team,
+    License,
+    Device,
+    Settings,
+    Support
+  },
+  data(){
+    return{
+      path:''
+    }
+  },
+  watch:{
+    path(value){
+      this.path = this.$route.path
+    }
+  }
+}
 </script>
 
 <template>
@@ -18,12 +42,12 @@ import Support from '@/components/icon/menu_support.vue'
       </div>
       <div class="type">Super admin / Team admin</div>
     </div>
-    <el-menu default-active="/dashboard" active-text-color="#1460F3" text-color="#232A40" router>
+    <el-menu :default-active="path" active-text-color="#1460F3" text-color="#232A40" router>
       <el-menu-item index="/dashboard">
         <Dashboard />
         <span>Dashboard</span>
       </el-menu-item>
-      <el-menu-item index="/product">
+      <el-menu-item index="/productManagement">
         <Product />
         <span>Product Management</span>
       </el-menu-item>
@@ -41,8 +65,8 @@ import Support from '@/components/icon/menu_support.vue'
           <License />
           <span>License Management</span>
         </template>
-        <el-menu-item index="4-1">Manage License</el-menu-item>
-        <el-menu-item index="4-2">Assign License</el-menu-item>
+        <el-menu-item index="/licenseManage">Manage License</el-menu-item>
+        <el-menu-item index="/assignlicense">Assign License</el-menu-item>
         <el-menu-item index="4-3">Volume Cancel</el-menu-item> 
       </el-submenu>
       <el-menu-item index="/device">

La diferencia del archivo ha sido suprimido porque es demasiado grande
+ 5 - 0
src/components/icon/download.vue


+ 7 - 0
src/components/icon/eye_colse.vue

@@ -0,0 +1,7 @@
+<template>
+    <svg width="14" height="14" viewBox="0 0 14 14" fill="none" xmlns="http://www.w3.org/2000/svg">
+        <path d="M2.87529 5.25C1.81967 6.125 1.16675 7 1.16675 7C1.16675 7 3.77842 10.5 7.00008 10.5C7.39964 10.5 7.7898 10.4462 8.16675 10.3519M5.84269 3.64583C6.21678 3.55297 6.60382 3.5 7.00008 3.5C10.2217 3.5 12.8334 7 12.8334 7C12.8334 7 12.1805 7.875 11.1249 8.75" stroke="#666666" stroke-linecap="round" stroke-linejoin="round"/>
+        <path d="M5.92506 6.0145C5.68703 6.27402 5.54175 6.62003 5.54175 6.99995C5.54175 7.80536 6.19467 8.45828 7.00008 8.45828C7.39754 8.45828 7.75786 8.29927 8.02091 8.0414" stroke="#666666" stroke-linecap="round" stroke-linejoin="round"/>
+        <path d="M12.25 12.25L1.75 1.75" stroke="#666666" stroke-linecap="round" stroke-linejoin="round"/>
+    </svg>
+</template>

+ 6 - 0
src/components/icon/eye_open.vue

@@ -0,0 +1,6 @@
+<template>
+    <svg width="14" height="14" viewBox="0 0 14 14" fill="none" xmlns="http://www.w3.org/2000/svg">
+        <path d="M7.00002 10.5C10.2217 10.5 12.8334 7 12.8334 7C12.8334 7 10.2217 3.5 7.00002 3.5C3.77836 3.5 1.16669 7 1.16669 7C1.16669 7 3.77836 10.5 7.00002 10.5Z" stroke="#666666" stroke-linejoin="round"/>
+        <path d="M7.00002 8.45833C7.80543 8.45833 8.45835 7.80541 8.45835 7C8.45835 6.19459 7.80543 5.54166 7.00002 5.54166C6.19461 5.54166 5.54169 6.19459 5.54169 7C5.54169 7.80541 6.19461 8.45833 7.00002 8.45833Z" stroke="#666666" stroke-linejoin="round"/>
+    </svg>
+</template>

+ 6 - 0
src/components/icon/search.vue

@@ -0,0 +1,6 @@
+<template>
+    <svg width="12" height="12" viewBox="0 0 12 12" fill="none" xmlns="http://www.w3.org/2000/svg">
+        <circle cx="5" cy="5" r="3.5" stroke="#808185"/>
+        <path d="M7.5 7.5L10 10" stroke="#808185" stroke-linecap="round"/>
+    </svg>
+</template>

+ 7 - 0
src/components/icon/warning.vue

@@ -0,0 +1,7 @@
+<template>
+    <svg width="48" height="48" viewBox="0 0 48 48" fill="none" xmlns="http://www.w3.org/2000/svg">
+        <rect width="48" height="48" rx="24" fill="#FFAE49"/>
+        <rect x="21" y="7" width="6" height="24" rx="3" fill="white"/>
+        <rect x="21" y="35" width="6" height="6" rx="3" fill="white"/>
+    </svg>
+</template>

+ 9 - 0
src/components/tooltip.vue

@@ -0,0 +1,9 @@
+<script>
+export default {
+    
+}
+</script>
+
+<template>
+    
+</template>

+ 29 - 0
src/crypto/crypto.js

@@ -0,0 +1,29 @@
+// crypto.js文件内容
+import CryptoJS from 'crypto-js'
+export default { // 加密
+  /**
+   * @description: 加密
+   * @param {*} word
+   * @param {*} keyStr
+   */
+  set (word) {
+    var keyStr = 'abcdef0123456789' // 16位的密钥,自己定义,和下面的密钥要相同
+    var srcs = CryptoJS.enc.Utf8.parse(word) // 字符串到数组转换,解析明文
+    var key = CryptoJS.enc.Utf8.parse(keyStr) // 字符串到数组转换,解析秘钥
+    // mode:加密方式;padding:填充方式;iv便宜向量(可选)
+    var encrypted = CryptoJS.AES.encrypt(srcs, key, { mode: CryptoJS.mode.ECB, padding: CryptoJS.pad.Pkcs7 })
+    return encrypted.toString() // 加密后的结果是对象,要转换为文本
+  },
+
+  /**
+   * @description: 解密
+   * @param {*} word
+   * @param {*} keyStr
+   */
+  get (word) {
+    var keyStr = 'abcdef0123456789'
+    var key = CryptoJS.enc.Utf8.parse(keyStr) // 字符串到数组转换
+    var decrypt = CryptoJS.AES.decrypt(word, key, { mode: CryptoJS.mode.ECB, padding: CryptoJS.pad.Pkcs7 })
+    return CryptoJS.enc.Utf8.stringify(decrypt).toString() // 数组到字符串转换
+  }
+}

+ 3 - 0
src/main.js

@@ -10,6 +10,9 @@ import 'virtual:windi.css'
 import ElementUI from 'element-ui'
 import 'element-ui/lib/theme-chalk/index.css'
 import '@/assets/style/element-variables.scss'
+// 配置cookie
+import cookies from 'vue-cookies'
+Vue.prototype.$cookies = cookies
 
 Vue.use(ElementUI)
 

+ 20 - 0
src/router/index.js

@@ -42,6 +42,26 @@ const router = new VueRouter({
       name: "settings",
       component: () => import("../views/Settings.vue"),
     },
+    {
+      path: "/device",
+      name: "device",
+      component: () => import("../views/Device.vue"),
+    },
+    {
+      path: "/licenseManage",
+      name: "licenseManage",
+      component: () => import("../views/LicenseManage.vue"),
+    },
+    {
+      path: "/assignlicense",
+      name: "assignlicense",
+      component: () => import("../views/Assignlicense.vue"),
+    },
+    {
+      path: "/productManagement",
+      name: "productManagement",
+      component: () => import("../views/ProductManagement.vue"),
+    },
   ],
 })
 

+ 3 - 6
src/stores/counter.js

@@ -1,16 +1,13 @@
 import { defineStore } from "pinia"
 
 export const useCounterStore = defineStore({
-  id: "counter",
   state: () => ({
-    counter: 0,
+    
   }),
   getters: {
-    doubleCount: (state) => state.counter * 2,
+    
   },
   actions: {
-    increment() {
-      this.counter++
-    },
+    
   },
 })

+ 281 - 0
src/views/Assignlicense.vue

@@ -0,0 +1,281 @@
+<script>
+import { post, put } from '../../utils/request'
+import { country } from '../../utils/country.js'
+
+export default {
+  data() {
+    return {
+      active: 0
+    }
+  },
+  methods: {},
+  mounted() {}
+}
+</script>
+
+<template>
+  <div>
+    <h1 class="text-28px leading-40px mb-15px font-700">Assign License</h1>
+    <div class="flex">
+      <span
+        class="
+          flex
+          justify-center
+          bg-[#C6C9CC]
+          rounded-t-8px
+          items-center
+          font-bold
+          w-200px
+          h-32px
+          hand
+        "
+        @click="active = 0"
+        :class="active === 0 ? 'active' : ''"
+        >Single License</span
+      >
+      <span
+        class="
+          flex
+          justify-center
+          bg-[#C6C9CC]
+          rounded-t-8px
+          items-center
+          font-bold
+          w-200px
+          h-32px
+          ml-8px
+          hand
+        "
+        @click="active = 1"
+        :class="active === 1 ? 'active' : ''"
+        >Team License</span
+      >
+    </div>
+    <div class="bg-[#fff] card">
+      <el-form
+        label-position="top"
+        label-width="100px"
+        class="p-40px"
+        v-show="active === 0"
+      >
+        <el-form-item prop="userName" class="required">
+          <span slot="label" class="label"
+            >Team<span class="text-[#FF5054]">*</span></span
+          >
+          <el-select
+            v-model="value1"
+            multiple
+            placeholder="Product Designer"
+            class="w-600px"
+          >
+            <el-option
+              v-for="item in options"
+              :key="item.value"
+              :label="item.label"
+              :value="item.value"
+            >
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item prop="email" class="w-600px required">
+          <span slot="label" class="label"
+            >Email<span class="text-[#FF5054]">*</span></span
+          >
+          <el-select
+            v-model="value1"
+            multiple
+            placeholder="Please select"
+            class="w-600px"
+          >
+            <el-option
+              v-for="item in options"
+              :key="item.value"
+              :label="item.label"
+              :value="item.value"
+            >
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item>
+          <span slot="label" class="label"
+            >Product<span class="text-[#FF5054]">*</span></span
+          >
+          <el-select
+            v-model="value1"
+            multiple
+            placeholder="Please select"
+            class="w-600px"
+          >
+            <el-option
+              v-for="item in options"
+              :key="item.value"
+              :label="item.label"
+              :value="item.value"
+            >
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item>
+          <button
+            type="button"
+            @click="changeInfo()"
+            class="
+              w-168px
+              h-48px
+              border-1px border-[#1460F3]
+              text-[#1460F3]
+              rounded-8px
+              font-bold
+              hover:opacity-80
+            "
+          >
+            Cancel
+          </button>
+          <button
+            type="button"
+            @click="changeInfo()"
+            class="
+              w-168px
+              h-48px
+              ml-16px
+              bg-[#1460F3]
+              text-[#fff]
+              rounded-8px
+              font-bold
+              hover:opacity-80
+            "
+          >
+            Assign
+          </button>
+        </el-form-item>
+      </el-form>
+      <el-form
+        label-position="top"
+        label-width="100px"
+        inline-message
+        class="p-40px"
+        v-show="active === 1"
+      >
+        <el-form-item prop="userName" class="required">
+          <span slot="label" class="label"
+            >Team<span class="text-[#FF5054]">*</span></span
+          >
+          <el-select
+            v-model="value1"
+            multiple
+            placeholder="Product Designer"
+            class="w-600px"
+          >
+            <el-option
+              v-for="item in options"
+              :key="item.value"
+              :label="item.label"
+              :value="item.value"
+            >
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item>
+          <span slot="label" class="label"
+            >Product<span class="text-[#FF5054]">*</span></span
+          >
+          <el-select
+            v-model="value1"
+            multiple
+            placeholder="Please select"
+            class="w-600px"
+          >
+            <el-option
+              v-for="item in options"
+              :key="item.value"
+              :label="item.label"
+              :value="item.value"
+            >
+            </el-option>
+          </el-select>
+        </el-form-item>
+        <el-form-item>
+          <button
+            type="button"
+            @click="changeInfo()"
+            class="
+              w-168px
+              h-48px
+              border-1px border-[#1460F3]
+              text-[#1460F3]
+              rounded-8px
+              font-bold
+              hover:opacity-80
+            "
+          >
+            Cancel
+          </button>
+          <button
+            type="button"
+            @click="changeInfo()"
+            class="
+              w-168px
+              h-48px
+              ml-16px
+              bg-[#1460F3]
+              text-[#fff]
+              rounded-8px
+              font-bold
+              hover:opacity-80
+            "
+          >
+            Assign
+          </button>
+        </el-form-item>
+      </el-form>
+    </div>
+  </div>
+</template>
+
+<style lang="scss" scoped>
+.hand {
+  cursor: pointer;
+}
+.el-form-item::v-deep label {
+  color: #232a40 !important;
+}
+.active {
+  color: #1460f3;
+  background-color: #fff;
+}
+.card {
+  border-radius: 8px;
+  border-top-left-radius: 0px;
+}
+.el-input::v-deep input {
+  border: 0px !important;
+  border-bottom: 1px solid #d9d9d9 !important;
+  border-radius: 6px !important;
+}
+.username::v-deep input {
+  border-radius: 0px !important;
+}
+.email::v-deep input {
+  border: 0px !important;
+}
+.required::v-deep label::before {
+  display: none;
+}
+.el-form-item::v-deep label {
+  font-weight: 700;
+  padding: 0;
+  margin-left: 8px;
+}
+.el-select-dropdown::v-deep .popper__arrow {
+  display: none;
+}
+</style>
+
+<style lang="scss">
+.popper__arrow {
+  display: none !important;
+}
+.el-select-dropdown {
+  margin-top: 0 !important;
+}
+</style>

+ 8 - 2
src/views/Create.vue

@@ -43,6 +43,11 @@ export default {
       },
     }
   },
+  methods:{
+    createAccount(){
+      console.log(this.ruleForm)
+    }
+  }
 }
 </script>
 
@@ -106,7 +111,7 @@ export default {
             </el-input><img src="@/assets/images/warning.png" alt="" class="w-14px h-14px hidden">
           </div>
         </el-form-item>
-        <select name="" id="" class="w-full h-40px mt-4px border-1px border-[#D9D9D9] rounded-6px text-[#808185]">
+        <select name="" id="" class="flex w-full !h-40px mt-4px border-1px border-[#D9D9D9] rounded-6px text-[#808185]">
           <option value="" selected>Select Industry</option>
         </select>
         <el-form-item prop="company" class="mt-4px">
@@ -139,7 +144,8 @@ export default {
             Back
           </button>
           <button
-            @click="submit()"
+            type="button"
+            @click="createAccount()"
             class="
               w-170px
               h-48px

+ 243 - 0
src/views/Device.vue

@@ -0,0 +1,243 @@
+<script setup>
+import { onMounted, ref } from 'vue'
+import Download from '@/components/icon/download.vue'
+import Warning from '@/components/icon/warning.vue'
+import Search from '@/components/icon/search.vue'
+import { get } from '../../utils/request'
+
+const currentPage = ref(1)
+const size = ref(5)
+const search = ref('')
+const tableData = ref([])
+const dialogVisible = ref(false)
+const cancelEmail = ref('')
+const cancelUniqueSn = ref('')
+onMounted(() => {
+  let pageText = document.getElementsByClassName('el-pagination__jump')[0]
+  if (pageText) {
+    pageText.childNodes[0].nodeValue = '跳至'
+  }
+  get(
+    'http://81.68.234.235:8032/pdf-tech/vppDevice/page?page=' +
+      currentPage.value +
+      '&' +
+      'pageSize=' +
+      size.value
+  ).then((res) => {
+    tableData.value = res.data.result.list
+  })
+})
+//打开对话框
+const handleClick = (val) => {
+  dialogVisible.value = true
+  cancelEmail.value = val.email
+  cancelUniqueSn.value = val.uniqueSn
+}
+const handleSizeChange = (value) => {
+  size.value = value
+}
+const handleCurrentChange = () => {
+  console.log(`当前页`)
+}
+</script>
+
+<template>
+  <div class="flex flex-col items-center">
+    <div class="w-full">
+      <h1 class="leading-40px">Device Management</h1>
+      <div
+        class="
+          mt-36px
+          mb-16px
+          leading-20px
+          text-16px
+          font-bold
+          flex
+          justify-between
+        "
+      >
+        <span>Content</span>
+        <span
+          class="
+            flex
+            justify-center
+            items-center
+            rounded-4px
+            min-w-28px min-h-28px
+            bg-[#fff]
+          "
+          ><Download
+        /></span>
+      </div>
+      <div class="flex bg-[#fff] pt-32px px-24px rounded-t-8px w-full">
+        <select name="" id="" class="w-140px">
+          <option value="" selected>Product</option>
+        </select>
+        <select name="" id="" class="w-140px ml-16px">
+          <option value="" selected>Staus</option>
+        </select>
+        <select name="" id="" class="w-140px ml-16px">
+          <option value="" selected>Team</option>
+        </select>
+        <div class="relative">
+          <el-input
+            v-model="search"
+            size="mini"
+            class="!w-316px ml-16px input-with-select"
+            placeholder="Search User Name / Email / UUID"
+          >
+          </el-input>
+          <button class="absolute top-8px right-8px"><Search /></button>
+        </div>
+        <button
+          class="
+            w-70px
+            h-28px
+            border-1px border-[#1460F3]
+            rounded-4px
+            ml-16px
+            text-[#1460F3]
+          "
+        >
+          Confirm
+        </button>
+      </div>
+      <el-table :data="tableData" class="px-24px rounded-b-8px !w-full">
+        <el-table-column prop="productName" label="Product"> </el-table-column>
+        <el-table-column prop="memberName" label="User Name"> </el-table-column>
+        <el-table-column prop="email" label="Email" width="130">
+        </el-table-column>
+        <el-table-column prop="teamName" label="Team"> </el-table-column>
+        <el-table-column prop="uniqueSn" label="UUID"> </el-table-column>
+        <el-table-column prop="status" label="Status"> </el-table-column>
+        <el-table-column prop="activeDate" label="Activated Date">
+        </el-table-column>
+        <el-table-column prop="expireDate" label="Expire Data">
+        </el-table-column>
+        <el-table-column prop="canceledDate" label="Canceled Date">
+        </el-table-column>
+        <el-table-column prop="operate" label="Operate">
+          <template slot-scope="scope">
+            <button
+              @click="handleClick(scope.row)"
+              type="text"
+              class="
+                w-60px
+                h-20px
+                rounded-4px
+                border-1px border-[#1460F3]
+                text-[#1460F3]
+                leading-12px
+              "
+            >
+              Cancel
+            </button>
+            <el-dialog :visible.sync="dialogVisible" width="376">
+              <Warning />
+              <span class="mt-16px">Sure unactive the device?</span>
+              <p class="leading-24px text-16px text-[#232A40] font-bold">
+                {{ cancelEmail }}
+              </p>
+              <span
+                class="
+                  leading-24px
+                  w-175px
+                  text-[#232A40]
+                  flex
+                  justify-center
+                  text-center text-16px
+                  font-bold
+                "
+                >{{ cancelUniqueSn }}</span
+              >
+              <span slot="footer" class="dialog-footer">
+                <el-button @click="dialogVisible = false">No</el-button>
+                <el-button type="primary" @click="dialogVisible = false">
+                  Yes
+                </el-button>
+              </span>
+            </el-dialog>
+          </template>
+        </el-table-column>
+      </el-table>
+      <el-pagination
+        @size-change="handleSizeChange"
+        @current-change="handleCurrentChange"
+        :current-page.sync="currentPage"
+        :page-sizes="[5, 10, 20]"
+        :page-size="size"
+        :background="true"
+        layout="sizes, prev, pager, next, jumper"
+        :total="tableData.length"
+        class="px-24px !rounded-0 rounded-b-8px mt-20px flex justify-end"
+      >
+      </el-pagination>
+    </div>
+  </div>
+</template>
+
+<style lang="scss" scoped>
+.el-table__header-wrapper::v-deep .el-table__header {
+  display: flex;
+  width: 1100px !important;
+}
+.el-table__header {
+  display: flex;
+  width: 1100px !important;
+}
+.el-pagination::v-deep button {
+  color: #232a40;
+  background-color: #e7eaee !important;
+}
+.el-pagination::v-deep ul > li {
+  color: #232a40;
+  border-radius: 4px;
+  margin-left: 6px;
+  font-weight: normal !important;
+  min-width: 24px !important;
+  height: 24px !important;
+  background-color: #fff;
+}
+.el-pagination::v-deep ul > .active {
+  color: #232a40 !important;
+  background-color: #c6c9cc !important;
+}
+.el-table::v-deep thead {
+  color: #000 !important;
+}
+</style>
+
+<style lang="scss">
+.el-dialog {
+  width: 376px;
+  height: 264px;
+  box-shadow: none;
+  border-radius: 8px;
+}
+.el-dialog > .el-dialog__body {
+  display: flex;
+  flex-direction: column;
+  justify-content: center;
+  align-items: center;
+  padding: 0 0 20px;
+}
+.el-dialog > .el-dialog__footer {
+  padding: 0 20px 20px;
+  span {
+    display: flex;
+    justify-content: center;
+    width: 100%;
+    .el-button--default {
+      border-color: #1460f3;
+      color: #1460f3;
+    }
+    .el-button {
+      width: 132px;
+      height: 32px;
+      display: flex;
+      align-items: center;
+      justify-content: center;
+    }
+  }
+}
+</style>

+ 287 - 0
src/views/LicenseManage.vue

@@ -0,0 +1,287 @@
+<script setup>
+import { onMounted, ref } from 'vue'
+import Download from '@/components/icon/download.vue'
+import Warning from '@/components/icon/warning.vue'
+import Search from '@/components/icon/search.vue'
+import { get } from '../../utils/request'
+
+const currentPage = ref(1)
+const size = ref(5)
+const search = ref('')
+const tableData = ref([])
+const dialogVisible = ref(false)
+const cancelEmail = ref('')
+onMounted(() => {
+  let pageText = document.getElementsByClassName('el-pagination__jump')[0]
+  if (pageText) {
+    pageText.childNodes[0].nodeValue = '跳至'
+  }
+  //获取分页数据
+  get(
+    'http://81.68.234.235:8032/pdf-tech/vppLicenseCode/page?' +
+      currentPage.value +
+      '&' +
+      'pageSize=' +
+      size.value
+  ).then((res) => {
+    console.log(res.data.result)
+    tableData.value = res.data.result.list
+  })
+})
+//打开对话框
+const handleClick = (val) => {
+  dialogVisible.value = true
+  cancelEmail.value = val.email
+}
+//切换每页条数
+const handleSizeChange = () => {
+  console.log(`每页条`)
+}
+//切换分页
+const handleCurrentChange = () => {
+  console.log(`当前页:`)
+}
+//按产品筛选
+const product = (val) => {
+  console.log(`当前页:`)
+}
+//按分配筛选
+const assigned = (val) => {
+  console.log(`当前页:`)
+}
+//按团队筛选
+const team = (val) => {
+  console.log(`当前页:`)
+}
+</script>
+
+<template>
+  <div class="flex flex-col items-center">
+    <div class="w-full">
+      <h1 class="leading-40px">Device Management</h1>
+      <div
+        class="
+          mt-36px
+          mb-16px
+          leading-20px
+          text-16px
+          font-bold
+          flex
+          justify-between
+        "
+      >
+        <span>Content</span>
+        <div class="flex">
+          <span
+            class="
+              flex
+              justify-center
+              items-center
+              rounded-4px
+              min-w-28px min-h-28px
+              bg-[#fff]
+            "
+          >
+            <Download />
+          </span>
+          <button
+            class="
+              bg-[#1460F3]
+              h-28px
+              w-111px
+              text-14px
+              ml-12px
+              rounded-4px
+              text-[#fff]
+            "
+          >
+            Assign License
+          </button>
+          <button
+            class="
+              bg-[#1460F3]
+              h-28px
+              w-111px
+              text-14px
+              ml-12px
+              rounded-4px
+              text-[#fff]
+            "
+          >
+            Volume Cancel
+          </button>
+        </div>
+      </div>
+      <div class="flex bg-[#fff] pt-32px px-24px rounded-t-8px w-full">
+        <select class="w-140px" @change="product()">
+          <option value="" selected>Product</option>
+        </select>
+        <select class="w-140px ml-16px" @change="assigned()">
+          <option value="" selected>Assigned</option>
+        </select>
+        <select class="w-140px ml-16px" @change="team()">
+          <option value="" selected>Team</option>
+        </select>
+        <div class="relative">
+          <el-input
+            v-model="search"
+            size="mini"
+            class="!w-316px ml-16px input-with-select"
+            placeholder="Search User Name / Email / License Code"
+          >
+          </el-input>
+          <button class="absolute top-8px right-8px"><Search /></button>
+        </div>
+        <button
+          class="
+            w-70px
+            h-28px
+            border-1px border-[#1460F3]
+            rounded-4px
+            ml-16px
+            text-[#1460F3]
+          "
+        >
+          Confirm
+        </button>
+      </div>
+      <el-table :data="tableData" class="px-24px rounded-b-8px w-full">
+        <el-table-column prop="productName" label="Product">
+        </el-table-column>
+        <el-table-column prop="userName" label="User Name">
+        </el-table-column>
+        <el-table-column prop="email" label="Email">
+        </el-table-column>
+        <el-table-column prop="teamName" label="Team">
+        </el-table-column>
+        <el-table-column prop="cdkey" label="License Code">
+        </el-table-column>
+        <el-table-column prop="validFlag" label="Status">
+        </el-table-column>
+        <el-table-column prop="updatedAt" label="Operated Date">
+        </el-table-column>
+        <el-table-column prop="endDate" label="Expire Data">
+        </el-table-column>
+        <el-table-column prop="operate" label="Operate">
+          <template slot-scope="scope">
+            <button
+              @click="handleClick(scope.row)"
+              type="text"
+              class="
+                w-60px
+                h-20px
+                rounded-4px
+                border-1px border-[#1460F3]
+                text-[#1460F3]
+                leading-12px
+              "
+            >
+              Cancel
+            </button>
+            <el-dialog
+              title=""
+              :visible.sync="dialogVisible"
+              width="376"
+              @close="dialogClose"
+            >
+              <Warning />
+              <p class="mt-16px">Sure cancel the license?</p>
+              <p>Product:<span class="text-16px font-bold">{{ cancelEmail }}</span></p>
+              <span slot="footer" class="dialog-footer">
+                <el-button @click="dialogVisible = false">No</el-button>
+                <el-button type="primary" @click="dialogVisible = false">
+                  Yes
+                </el-button>
+              </span>
+            </el-dialog>
+          </template>
+        </el-table-column>
+      </el-table>
+      <el-pagination
+        @size-change="handleSizeChange"
+        @current-change="handleCurrentChange"
+        :current-page.sync="currentPage"
+        :page-sizes="[5, 10, 20]"
+        :page-size="size"
+        :background="true"
+        layout="sizes, prev, pager, next, jumper"
+        :total="tableData.length"
+        class="
+          px-24px
+          !rounded-0
+          rounded-b-8px
+          mt-20px
+          flex
+          justify-end
+        "
+      >
+      </el-pagination>
+    </div>
+  </div>
+</template>
+
+<style lang="scss" scoped>
+.el-table__header-wrapper::v-deep .el-table__header {
+  display: flex;
+  width: 1100px !important;
+}
+.el-table__header {
+  display: flex;
+  width: 1100px !important;
+}
+.el-pagination::v-deep button {
+  color: #232a40;
+  background-color: #e7eaee !important;
+}
+.el-pagination::v-deep ul > li {
+  color: #232a40;
+  border-radius: 4px;
+  margin-left: 6px;
+  font-weight: normal !important;
+  min-width: 24px !important;
+  height: 24px !important;
+  background-color: #fff;
+}
+.el-pagination::v-deep ul > .active {
+  color: #232a40 !important;
+  background-color: #c6c9cc !important;
+}
+.el-table::v-deep thead {
+  color: #000 !important;
+}
+</style>
+
+<style lang="scss">
+.el-dialog {
+  width: 376px;
+  height: 214px;
+  box-shadow: none;
+  border-radius: 8px;
+}
+.el-dialog > .el-dialog__body {
+  display: flex;
+  flex-direction: column;
+  justify-content: center;
+  align-items: center;
+  padding: 0 0 20px;
+}
+.el-dialog > .el-dialog__footer {
+  padding: 0 20px 20px;
+  span {
+    display: flex;
+    justify-content: center;
+    width: 100%;
+    .el-button--default {
+      border-color: #1460f3;
+      color: #1460f3;
+    }
+    .el-button {
+      width: 132px;
+      height: 32px;
+      display: flex;
+      align-items: center;
+      justify-content: center;
+    }
+  }
+}
+</style>

+ 156 - 41
src/views/Login.vue

@@ -1,40 +1,113 @@
 <script>
+import { post, get } from '../../utils/request'
+import crypto from '@/crypto/crypto'
+import Eyecolse from '@/components/icon/eye_colse.vue'
+import Eyeopen from '@/components/icon/eye_open.vue'
+
 export default {
+  components: { Eyecolse, Eyeopen },
   data() {
     return {
+      empty: true,
+      passwordType: false,
+      remenber: false,
       ruleForm: {
-        email: "",
-        password: "",
+        email: '',
+        password: ''
       },
       rules: {
         email: [
           {
             required: true,
-            message: "Email Address is required",
-            trigger: [""],
+            message: 'Email Address is required',
+            trigger: ['']
           },
           {
-            type: "email",
-            message: "Please enter a valid Email Address",
-            trigger: [""],
-          },
+            type: 'email',
+            message: 'Please enter a valid Email Address',
+            trigger: ['']
+          }
         ],
         password: [
-          { required: true, message: "Password is required", trigger: [""] },
-        ],
-      },
+          { required: true, message: 'Password is required', trigger: [''] }
+        ]
+      }
     }
   },
-  components: {},
+  mounted () {
+    this.isdisable()
+    const isRemenber = localStorage.getItem('isRemenber')
+    if (isRemenber) {
+      this.ruleForm.email = localStorage.getItem('username') || ''
+      this.ruleForm.password = crypto.get(localStorage.getItem('password')) || ''
+      this.remenber = true
+    }
+  },
+  methods: {
+    submit() {
+      this.$refs['ruleForm'].validate((valid) => {
+        if (valid) {
+          var formdata = new FormData()
+          formdata.append('username', this.ruleForm.email)
+          formdata.append('password', this.ruleForm.password)
+          post('http://81.68.234.235:8032/pdf-tech/login', formdata).then(
+            (res) => {
+              if (res.data.code === 200 && res.data.msg === '获取授权码成功') {
+                get(
+                  'http://81.68.234.235:8032/pdf-tech/auth/getToken?code=' +
+                    res.data.result
+                ).then((res) => {
+                  this.$cookies.set('accessToken',res.data.result.accessToken)
+                  this.$router.push('/dashboard')
+                })
+                localStorage.setItem('username', this.ruleForm.email)
+                const SECRET_PWD = crypto.set(this.ruleForm.password) // 加密
+                localStorage.setItem('password', SECRET_PWD)
+                if (this.remenber) {
+                  localStorage.setItem('isRemenber', 'true')
+                } else {
+                  localStorage.removeItem('isRemenber')
+                }
+              } else if (
+                res.data.code === 306 &&
+                res.data.msg === '账号或者密码错误'
+              ) {
+                this.$message.error({
+                  message: 'Please Check your password'
+                })
+              } else if (
+                res.data.code === 302 &&
+                res.data.msg === 'Please Create your Account first'
+              ) {
+                this.$message.error({
+                  message: 'Please Create your Account first'
+                })
+              }
+            }
+          )
+        } else {
+          console.log('error submit!!')
+          return false
+        }
+      })
+    },
+    isdisable() {
+      if (
+        this.ruleForm.email.trim() !== '' ||
+        this.ruleForm.password.trim() !== ''
+      ) {
+        this.empty = false
+      } else {
+        this.empty = true
+      }
+    }
+  }
 }
 </script>
 
-
 <template>
-  <div
-    class="bg w-1440px h-900px flex justify-center items-center m-auto"
-  >
-    <div class="w-404px h-auto rounded-8px p-24px bg-[#fff] loginBox">
+  <div class="bg flex justify-center items-center m-auto">
+    <div class="w-404px h-auto rounded-8px p-24px bg-[#fff] loginBox mt-278px">
       <h1 class="text-24px font-bold mb-24px">Sign in</h1>
       <el-form
         :model="ruleForm"
@@ -47,46 +120,69 @@ export default {
         <el-form-item prop="email">
           <div style="display: flex">
             <el-input
-              v-model.trim="ruleForm.email"
-              clearable
+              v-model="ruleForm.email"
+              @input="isdisable()"
               placeholder="Email address"
-            >
-            </el-input><img src="@/assets/images/warning.png" alt="" class="w-14px h-14px hidden">
+            />
+            <img
+              src="@/assets/images/warning.png"
+              alt=""
+              class="w-14px h-14px hidden"
+            />
           </div>
         </el-form-item>
         <el-form-item prop="password">
           <div style="display: flex">
             <el-input
-              v-model.trim="ruleForm.email"
-              clearable
+              v-model="ruleForm.password"
               placeholder="Password"
+              @input="isdisable()"
+              :type="passwordType ? '' : 'password'"
             >
-            </el-input><img src="@/assets/images/warning.png" alt="" class="w-14px h-14px hidden">
+            </el-input>
+            <span
+              v-show="ruleForm.password !== ''"
+              class="show-password"
+              :class="passwordType ? 'eye-open' : 'eye-close'"
+              @click="passwordType = !passwordType"
+            >
+              <Eyeopen v-show="passwordType" />
+              <Eyecolse v-show="!passwordType" />
+            </span>
+            <img
+              src="@/assets/images/warning.png"
+              alt=""
+              class="w-14px h-14px hidden"
+            />
           </div>
         </el-form-item>
         <el-form-item>
           <div class="flex justify-between !text-12px">
-            <el-checkbox label="Keep me logged in" name="type"></el-checkbox>
-            <router-link to="/forgotpassword" class="text-[#1460F3]">Forgot Password?</router-link>
+            <el-checkbox
+              label="Keep me logged in"
+              name="type"
+              v-model="remenber"
+            ></el-checkbox>
+            <router-link to="/forgotpassword" class="text-[#1460F3]">
+              Forgot Password?
+            </router-link>
           </div>
         </el-form-item>
         <el-form-item>
           <button
+            :disabled="empty"
+            type="button"
             @click="submit()"
-            class="
-              w-full
-              h-48px
-              bg-[#1460F3]
-              text-[#fff]
-              rounded-8px
-              hover:opacity-80
-            "
+            :class="empty ? 'opacity-20' : 'hover:opacity-80'"
+            class="w-full h-48px bg-[#1460F3] text-[#fff] rounded-8px"
           >
             sign in
           </button>
         </el-form-item>
         <div class="flex justify-end">
-          <span class="text-12px text-[#1460F3]">Create account</span>
+          <router-link to="/create" class="text-12px text-[#1460F3]">
+            Create account
+          </router-link>
         </div>
       </el-form>
     </div>
@@ -95,18 +191,37 @@ export default {
 
 <style lang="scss" scoped>
 .bg {
-  background: #E7EAEE;
-  background-image: url("@/assets/images/background.png");
+  background: #e7eaee;
+  background-image: url('@/assets/images/background.png');
+  background-repeat: no-repeat;
 }
 .loginBox {
   box-shadow: 0px 0px 12px rgba(35, 97, 169, 0.05);
 }
-.el-input::v-deep input{
-  border:0px !important;
-  border-bottom: 1px solid #D9D9D9 !important;
+.el-input::v-deep input {
+  border: 0px !important;
+  border-bottom: 1px solid #d9d9d9 !important;
   border-radius: 0 !important;
 }
-.is-error{
+.is-error {
   display: block;
 }
+.show-password {
+  display: inline-block;
+  position: absolute;
+  right: 13px;
+  top: 13px;
+  width: 14px;
+  height: 14px;
+  cursor: pointer;
+}
+</style>
+
+<style lang="scss">
+.el-message--error {
+  border-color: #ff5054 !important;
+  height: 36px;
+  min-width: auto !important;
+  padding: 12px !important;
+}
 </style>

+ 183 - 0
src/views/ProductManagement.vue

@@ -0,0 +1,183 @@
+<script setup>
+import { onMounted, ref } from 'vue'
+import Download from '@/components/icon/download.vue'
+import Warning from '@/components/icon/warning.vue'
+import Search from '@/components/icon/search.vue'
+import { get } from '../../utils/request'
+
+const currentPage = ref(1)
+const size = ref(5)
+const search = ref('')
+const tableData = ref([])
+const dialogVisible = ref(false)
+const cancelEmail = ref('')
+const cancelUniqueSn = ref('')
+onMounted(() => {
+  let pageText = document.getElementsByClassName('el-pagination__jump')[0]
+  if (pageText) {
+    pageText.childNodes[0].nodeValue = '跳至'
+  }
+  var formdata = new FormData()
+  formdata.append('code', '')
+  formdata.append('page', currentPage.value)
+  formdata.append('pageSize', size.value)
+  get('http://81.68.234.235:8032/pdf-tech/vppOrderDetail/pageByCompany',formdata).then(
+    (res) => {
+      tableData.value = res.data.result.list
+    }
+  )
+})
+//打开对话框
+const handleClick = (val) => {
+  dialogVisible.value = true
+  cancelEmail.value = val.email
+  cancelUniqueSn.value = val.uniqueSn
+}
+const handleSizeChange = (value) => {
+  size.value = value
+}
+const handleCurrentChange = () => {
+  console.log(`当前页`)
+}
+</script>
+
+<template>
+  <div class="flex flex-col items-center">
+    <div class="w-full">
+      <h1 class="leading-40px">Product Management</h1>
+      <div
+        class="
+          mt-36px
+          mb-16px
+          leading-20px
+          text-16px
+          font-bold
+          flex
+          justify-between
+        "
+      >
+        <span>Content</span>
+        <span
+          class="
+            flex
+            justify-center
+            items-center
+            rounded-4px
+            min-w-28px min-h-28px
+            bg-[#fff]
+          "
+          ><Download
+        /></span>
+      </div>
+      <div class="flex bg-[#fff] pt-32px px-24px rounded-t-8px w-full">
+        <select name="" id="" class="w-140px">
+          <option value="" selected>Product</option>
+        </select>
+        <select name="" id="" class="w-140px ml-16px">
+          <option value="" selected>Plan</option>
+        </select>
+        <button
+          class="
+            w-70px
+            h-28px
+            border-1px border-[#1460F3]
+            rounded-4px
+            ml-16px
+            text-[#1460F3]
+          "
+        >
+          Confirm
+        </button>
+      </div>
+      <el-table :data="tableData" class="px-24px rounded-b-8px !w-full">
+        <el-table-column prop="name" label="Product"> </el-table-column>
+        <el-table-column prop="memberName" label="Plan"> </el-table-column>
+        <el-table-column prop="quantity" label="Total amount"> </el-table-column>
+        <el-table-column prop="price" label="Purchase Price">
+        </el-table-column>
+        <el-table-column prop="createdAt" label="Purchase date">
+        </el-table-column>
+        <el-table-column prop="expirationAt" label="Expiration Date">
+        </el-table-column>
+      </el-table>
+      <el-pagination
+        @size-change="handleSizeChange"
+        @current-change="handleCurrentChange"
+        :current-page.sync="currentPage"
+        :page-sizes="[5, 10, 20]"
+        :page-size="size"
+        :background="true"
+        layout="sizes, prev, pager, next, jumper"
+        :total="tableData.length"
+        class="px-24px !rounded-0 rounded-b-8px mt-20px flex justify-end"
+      >
+      </el-pagination>
+    </div>
+  </div>
+</template>
+
+<style lang="scss" scoped>
+.el-table__header-wrapper::v-deep .el-table__header {
+  display: flex;
+  width: 1100px !important;
+}
+.el-table__header {
+  display: flex;
+  width: 1100px !important;
+}
+.el-pagination::v-deep button {
+  color: #232a40;
+  background-color: #e7eaee !important;
+}
+.el-pagination::v-deep ul > li {
+  color: #232a40;
+  border-radius: 4px;
+  margin-left: 6px;
+  font-weight: normal !important;
+  min-width: 24px !important;
+  height: 24px !important;
+  background-color: #fff;
+}
+.el-pagination::v-deep ul > .active {
+  color: #232a40 !important;
+  background-color: #c6c9cc !important;
+}
+.el-table::v-deep thead {
+  color: #000 !important;
+}
+</style>
+
+<style lang="scss">
+.el-dialog {
+  width: 376px;
+  height: 264px;
+  box-shadow: none;
+  border-radius: 8px;
+}
+.el-dialog > .el-dialog__body {
+  display: flex;
+  flex-direction: column;
+  justify-content: center;
+  align-items: center;
+  padding: 0 0 20px;
+}
+.el-dialog > .el-dialog__footer {
+  padding: 0 20px 20px;
+  span {
+    display: flex;
+    justify-content: center;
+    width: 100%;
+    .el-button--default {
+      border-color: #1460f3;
+      color: #1460f3;
+    }
+    .el-button {
+      width: 132px;
+      height: 32px;
+      display: flex;
+      align-items: center;
+      justify-content: center;
+    }
+  }
+}
+</style>

+ 154 - 46
src/views/Settings.vue

@@ -1,51 +1,125 @@
 <script>
+import { post, put } from '../../utils/request'
+import { country } from '../../utils/country.js'
+
 export default {
   data() {
     return {
-      active: 1,
+      active: 0,
+      country: [],
       ruleForm: {
-        userName: "",
-        email: "",
-        area: "",
+        userName: '',
+        email: '',
+        area: ''
       },
       rules: {
         userName: [
-          { required: true, message: "User name is required", trigger: [""] },
+          { required: true, message: 'User name is required', trigger: [''] }
         ],
         email: [
           {
             required: true,
-            message: "Email Address is required",
-            trigger: [""],
+            message: 'Email Address is required',
+            trigger: ['']
           },
           {
-            type: "email",
-            message: "Please enter a valid Email Address",
-            trigger: [""],
-          },
-        ],
-        area: [
-          { required: true, message: "Area is required", trigger: [""] },
+            type: 'email',
+            message: 'Please enter a valid Email Address',
+            trigger: ['']
+          }
         ],
+        area: [{ required: true, message: 'Area is required', trigger: [''] }]
       },
       ruleFormPass: {
-        oldPassword: "",
-        newPassword: "",
-        confirmPassword: "",
+        oldPassword: '',
+        newPassword: '',
+        confirmPassword: ''
       },
       rulesPass: {
         oldPassword: [
-          { required: true, message: "Old password is required", trigger: [""] },
+          { required: true, message: 'Old password is required', trigger: [''] }
         ],
         newPassword: [
-          { required: true, message: "New password is required", trigger: [""] },
+          { required: true, message: 'New password is required', trigger: [''] }
         ],
         confirmPassword: [
-          { required: true, message: "Confirm password is required", trigger: [""] },
-        ],
-      },
+          {
+            required: true,
+            message: 'Confirm password is required',
+            trigger: ['']
+          }
+        ]
+      }
     }
   },
+  methods: {
+    changePassword() {
+      this.$refs['ruleFormPass'].validate((valid) => {
+        if (valid) {
+          post('http://81.68.234.235:8032/pdf-tech/vppMember/updatePassword', {
+            password: this.ruleFormPass.oldPassword,
+            newPassword: this.ruleFormPass.newPassword,
+            newPasswordConfirm: this.ruleFormPass.confirmPassword
+          }).then((res) => {
+            console.log(res)
+            // if (res.data.code === 200 && res.data.msg === '获取授权码成功') {
+            // } else if (
+            //   res.data.code === 306 &&
+            //   res.data.msg === '账号或者密码错误'
+            // ) {
+            //   this.$message.error({
+            //     message: 'Please Check your password'
+            //   })
+            // } else if (
+            //   res.data.code === 302 &&
+            //   res.data.msg === 'Please Create your Account first'
+            // ) {
+            //   this.$message.error({
+            //     message: 'Please Create your Account first'
+            //   })
+            // }
+          })
+        } else {
+          console.log('error submit!!')
+          return false
+        }
+      })
+    },
+    changeInfo() {
+      this.$refs['ruleForm'].validate((valid) => {
+        if (valid) {
+          put('http://81.68.234.235:8032/pdf-tech/vppSet/setGeneral', {
+            userName: this.ruleForm.userName,
+            area: this.ruleForm.userName
+          }).then((res) => {
+            console.log(res)
+            // if (res.data.code === 200 && res.data.msg === '获取授权码成功') {
+            // } else if (
+            //   res.data.code === 306 &&
+            //   res.data.msg === '账号或者密码错误'
+            // ) {
+            //   this.$message.error({
+            //     message: 'Please Check your password'
+            //   })
+            // } else if (
+            //   res.data.code === 302 &&
+            //   res.data.msg === 'Please Create your Account first'
+            // ) {
+            //   this.$message.error({
+            //     message: 'Please Create your Account first'
+            //   })
+            // }
+          })
+        } else {
+          console.log('error submit!!')
+          return false
+        }
+      })
+    }
+  },
+  mounted() {
+    this.country = country()
+  }
 }
 </script>
 
@@ -63,7 +137,9 @@ export default {
           font-bold
           w-200px
           h-32px
+          hand
         "
+        @click="active = 0"
         :class="active === 0 ? 'active' : ''"
         >General</span
       >
@@ -78,7 +154,9 @@ export default {
           w-200px
           h-32px
           ml-8px
+          hand
         "
+        @click="active = 1"
         :class="active === 1 ? 'active' : ''"
         >Security</span
       >
@@ -94,11 +172,11 @@ export default {
         class="p-40px"
         v-show="active === 0"
       >
-        <el-form-item label="User Name" prop="email" class="required">
+        <el-form-item label="User Name" prop="userName">
           <div style="display: flex">
             <el-input
               v-model.trim="ruleForm.userName"
-              clearable
+              class="username"
               placeholder="User Name"
             >
             </el-input
@@ -109,12 +187,11 @@ export default {
             />
           </div>
         </el-form-item>
-        <el-form-item label="Email" prop="email" class="w-600px required">
+        <el-form-item label="Email" prop="email" class="w-600px">
           <div style="display: flex">
             <el-input
               v-model.trim="ruleForm.email"
               class="email"
-              clearable
               disabled
               placeholder="Email address confirmation"
             >
@@ -127,13 +204,21 @@ export default {
           </div>
         </el-form-item>
         <el-form-item label="Area">
-        <select name="" id="" class="flex w-600px !h-40px required">
+          <select v-model="ruleForm.area" class="flex w-600px !h-40px">
             <option value="" selected>Choose your Area</option>
-        </select>
+            <option
+              v-for="(item, index) in country"
+              :key="index"
+              :value="item.name"
+            >
+              {{ item.name }}
+            </option>
+          </select>
         </el-form-item>
         <el-form-item>
           <button
-            @click="submit()"
+            type="button"
+            @click="changeInfo()"
             class="
               w-168px
               h-48px
@@ -150,7 +235,7 @@ export default {
       </el-form>
       <el-form
         :model="ruleFormPass"
-        ref="ruleForm"
+        ref="ruleFormPass"
         :rules="rulesPass"
         label-position="top"
         label-width="100px"
@@ -158,11 +243,14 @@ export default {
         class="p-40px"
         v-show="active === 1"
       >
-        <el-form-item label="Old Password" prop="oldPassword">
+        <el-form-item prop="oldPassword">
+          <span slot="label" class="font-bold"
+            >Old Password<span class="text-[#FF5054]">*</span></span
+          >
           <div style="display: flex">
             <el-input
-              v-model.trim="ruleForm.email"
-              clearable
+              type="password"
+              v-model.trim="ruleFormPass.oldPassword"
               placeholder="Old Password"
             >
             </el-input
@@ -173,11 +261,14 @@ export default {
             />
           </div>
         </el-form-item>
-        <el-form-item label="New Password" prop="newPassword">
+        <el-form-item prop="newPassword">
+          <span slot="label" class="font-bold"
+            >New Password<span class="text-[#FF5054]">*</span></span
+          >
           <div style="display: flex">
             <el-input
-              v-model.trim="ruleForm.newPassword"
-              clearable
+              type="password"
+              v-model.trim="ruleFormPass.newPassword"
               placeholder="New Password"
             >
             </el-input
@@ -188,11 +279,14 @@ export default {
             />
           </div>
         </el-form-item>
-        <el-form-item label="Confirm Password" prop="confirmPassword">
+        <el-form-item prop="confirmPassword">
+          <span slot="label" class="font-bold"
+            >Confirm Password<span class="text-[#FF5054]">*</span></span
+          >
           <div style="display: flex">
             <el-input
-              v-model.trim="ruleForm.confirmPassword"
-              clearable
+              type="password"
+              v-model.trim="ruleFormPass.confirmPassword"
               placeholder="Confirm Password"
             >
             </el-input
@@ -203,10 +297,15 @@ export default {
             />
           </div>
         </el-form-item>
-        <router-link to="/forgotpassword" class="flex ml-8px leading-20px mb-10px text-[#1460F3]">Forgot Password?</router-link>
+        <router-link
+          to="/forgotpassword"
+          class="flex ml-8px leading-20px mb-10px text-[#1460F3]"
+          >Forgot Password?</router-link
+        >
         <el-form-item>
           <button
-            @click="submit()"
+            type="button"
+            @click="changePassword()"
             class="
               w-168px
               h-48px
@@ -226,23 +325,32 @@ export default {
 </template>
 
 <style lang="scss" scoped>
+.hand {
+  cursor: pointer;
+}
+.el-form-item::v-deep label {
+  color: #232a40 !important;
+}
 .active {
   color: #1460f3;
   background-color: #fff;
 }
-.card{
-    border-radius: 8px;
-    border-top-left-radius: 0px;
+.card {
+  border-radius: 8px;
+  border-top-left-radius: 0px;
 }
 .el-input::v-deep input {
   border: 0px !important;
   border-bottom: 1px solid #d9d9d9 !important;
-  border-radius: 0 !important;
+  border-radius: 6px !important;
+}
+.username::v-deep input {
+  border-radius: 0px !important;
 }
 .email::v-deep input {
   border: 0px !important;
 }
-.required::v-deep label::before {
+.el-form-item::v-deep label::before {
   display: none;
 }
 .el-form-item::v-deep label {

+ 250 - 0
utils/country.js

@@ -0,0 +1,250 @@
+export function country() {
+    var country =
+        [
+            { name: "Afghanistan", code: "AF" },
+            { name: "Åland Islands", code: "AX" },
+            { name: "Albania", code: "AL" },
+            { name: "Algeria", code: "DZ" },
+            { name: "American Samoa", code: "AS" },
+            { name: "Andorra", code: "AD" },
+            { name: "Angola", code: "AO" },
+            { name: "Anguilla", code: "AI" },
+            { name: "Antarctica", code: "AQ" },
+            { name: "Antigua and Barbuda", code: "AG" },
+            { name: "Argentina", code: "AR" },
+            { name: "Armenia", code: "AM" },
+            { name: "Aruba", code: "AW" },
+            { name: "Australia", code: "AU" },
+            { name: "Austria", code: "AT" },
+            { name: "Azerbaijan", code: "AZ" },
+            { name: "Bahamas", code: "BS" },
+            { name: "Bahrain", code: "BH" },
+            { name: "Bangladesh", code: "BD" },
+            { name: "Barbados", code: "BB" },
+            { name: "Belarus", code: "BY" },
+            { name: "Belgium", code: "BE" },
+            { name: "Belize", code: "BZ" },
+            { name: "Benin", code: "BJ" },
+            { name: "Bermuda", code: "BM " },
+            { name: "Bhutan", code: "BT" },
+            { name: "Bolivia", code: "BO" },
+            { name: "Bosnia and Herzegovina", code: "BA" },
+            { name: "Botswana", code: "BW" },
+            { name: "Bouvet Island", code: "BV" },
+            { name: "Brazil", code: "BR" },
+            { name: "British Indian Ocean Territory", code: "IO" },
+            { name: "Brunei Darussalam", code: "BN" },
+            { name: "Bulgaria", code: "BG" },
+            { name: "Burkina Faso", code: "BF" },
+            { name: "Burundi", code: "BI" },
+            { name: "Cambodia", code: "KH" },
+            { name: "Cameroon", code: "CM" },
+            { name: "Canada", code: "CA" },
+            { name: "Cape Verde", code: "CV" },
+            { name: "Cayman Islands", code: "KY" },
+            { name: "Central African Republic", code: "CF" },
+            { name: "Chad", code: "TD" },
+            { name: "Chile", code: "CL" },
+            { name: "China", code: "CN" },
+            { name: "Christmas Island", code: "CX" },
+            { name: "Cocos (Keeling) Islands", code: "CC" },
+            { name: "Colombia", code: "CO" },
+            { name: "Comoros", code: "KM" },
+            { name: "Congo", code: "CG" },
+            { name: "Congo, The Democratic Republic of the", code: "CD" },
+            { name: "Cook Islands", code: "CK" },
+            { name: "Costa Rica", code: "CR" },
+            { name: 'Cote D"Ivoire', code: "CI" },
+            { name: "Croatia", code: "HR" },
+            { name: "Cuba", code: "CU" },
+            { name: "Cyprus", code: "CY" },
+            { name: "Czech Republic", code: "CZ" },
+            { name: "Denmark", code: "DK" },
+            { name: "Djibouti", code: "DJ" },
+            { name: "Dominica", code: "DM" },
+            { name: "Dominican Republic", code: "DO" },
+            { name: "Ecuador", code: "EC" },
+            { name: "Egypt", code: "EG" },
+            { name: "El Salvador", code: "SV" },
+            { name: "Equatorial Guinea", code: "GQ" },
+            { name: "Eritrea", code: "ER" },
+            { name: "Estonia", code: "EE" },
+            { name: "Ethiopia", code: "ET" },
+            { name: "Falkland Islands (Malvinas)", code: "FK" },
+            { name: "Faroe Islands", code: "FO" },
+            { name: "Fiji", code: "FJ" },
+            { name: "Finland", code: "FI" },
+            { name: "France", code: "FR" },
+            { name: "French Guiana", code: "GF" },
+            { name: "French Polynesia", code: "PF" },
+            { name: "French Southern Territories", code: "TF" },
+            { name: "Gabon", code: "GA" },
+            { name: "Gambia", code: "GM" },
+            { name: "Georgia", code: "GE" },
+            { name: "Germany", code: "DE" },
+            { name: "Ghana", code: "GH" },
+            { name: "Gibraltar", code: "GI" },
+            { name: "Greece", code: "GR" },
+            { name: "Greenland", code: "GL" },
+            { name: "Grenada", code: "GD" },
+            { name: "Guadeloupe", code: "GP" },
+            { name: "Guam", code: "GU" },
+            { name: "Guatemala", code: "GT" },
+            { name: "Guernsey", code: "GG" },
+            { name: "Guinea", code: "GN" },
+            { name: "Guinea-Bissau", code: "GW" },
+            { name: "Guyana", code: "GY" },
+            { name: "Haiti", code: "HT" },
+            { name: "Heard Island and Mcdonald Islands", code: "HM" },
+            { name: "Holy See (Vatican City State)", code: "VA" },
+            { name: "Honduras", code: "HN" },
+            { name: "Hong Kong, Province of China", code: "HK" },
+            { name: "Hungary", code: "HU" },
+            { name: "Iceland", code: "IS" },
+            { name: "India", code: "IN" },
+            { name: "Indonesia", code: "ID" },
+            { name: "Iran, Islamic Republic Of", code: "IR" },
+            { name: "Iraq", code: "IQ" },
+            { name: "Ireland", code: "IE" },
+            { name: "Isle of Man", code: "IM" },
+            { name: "Israel", code: "IL" },
+            { name: "Italy", code: "IT" },
+            { name: "Jamaica", code: "JM" },
+            { name: "Japan", code: "JP" },
+            { name: "Jersey", code: "JE" },
+            { name: "Jordan", code: "JO" },
+            { name: "Kazakhstan", code: "KZ" },
+            { name: "Kenya", code: "KE" },
+            { name: "Kiribati", code: "KI" },
+            { name: 'Korea, Democratic People"S Republic of', code: "KP" },
+            { name: "Korea, Republic of", code: "KR" },
+            { name: "Kuwait", code: "KW" },
+            { name: "Kyrgyzstan", code: "KG" },
+            { name: 'Lao People"S Democratic Republic', code: "LA" },
+            { name: "Latvia", code: "LV" },
+            { name: "Lebanon", code: "LB" },
+            { name: "Lesotho", code: "LS" },
+            { name: "Liberia", code: "LR" },
+            { name: "Libyan Arab Jamahiriya", code: "LY" },
+            { name: "Liechtenstein", code: "LI" },
+            { name: "Lithuania", code: "LT" },
+            { name: "Luxembourg", code: "LU" },
+            { name: "Macao, Province of China", code: "MO" },
+            { name: "Macedonia, The Former Yugoslav Republic of", code: "MK" },
+            { name: "Madagascar", code: "MG" },
+            { name: "Malawi", code: "MW" },
+            { name: "Malaysia", code: "MY" },
+            { name: "Maldives", code: "MV" },
+            { name: "Mali", code: "ML" },
+            { name: "Malta", code: "MT" },
+            { name: "Marshall Islands", code: "MH" },
+            { name: "Martinique", code: "MQ" },
+            { name: "Mauritania", code: "MR" },
+            { name: "Mauritius", code: "MU" },
+            { name: "Mayotte", code: "YT" },
+            { name: "Mexico", code: "MX" },
+            { name: "Micronesia, Federated States of", code: "FM" },
+            { name: "Moldova, Republic of", code: "MD" },
+            { name: "Monaco", code: "MC" },
+            { name: "Mongolia", code: "MN" },
+            { name: "Montserrat", code: "MS" },
+            { name: "Morocco", code: "MA" },
+            { name: "Mozambique", code: "MZ" },
+            { name: "Myanmar", code: "MM" },
+            { name: "Namibia", code: "NA" },
+            { name: "Nauru", code: "NR" },
+            { name: "Nepal", code: "NP" },
+            { name: "Netherlands", code: "NL" },
+            { name: "Netherlands Antilles", code: "AN" },
+            { name: "New Caledonia", code: "NC" },
+            { name: "New Zealand", code: "NZ" },
+            { name: "Nicaragua", code: "NI" },
+            { name: "Niger", code: "NE" },
+            { name: "Nigeria", code: "NG" },
+            { name: "Niue", code: "NU" },
+            { name: "Norfolk Island", code: "NF" },
+            { name: "Northern Mariana Islands", code: "MP" },
+            { name: "Norway", code: "NO" },
+            { name: "Oman", code: "OM" },
+            { name: "Pakistan", code: "PK" },
+            { name: "Palau", code: "PW" },
+            { name: "Palestinian Territory, Occupied", code: "PS" },
+            { name: "Panama", code: "PA" },
+            { name: "Papua New Guinea", code: "PG" },
+            { name: "Paraguay", code: "PY" },
+            { name: "Peru", code: "PE" },
+            { name: "Philippines", code: "PH" },
+            { name: "Pitcairn", code: "PN" },
+            { name: "Poland", code: "PL" },
+            { name: "Portugal", code: "PT" },
+            { name: "Puerto Rico", code: "PR" },
+            { name: "Qatar", code: "QA" },
+            { name: "Reunion", code: "RE" },
+            { name: "Romania", code: "RO" },
+            { name: "Russian Federation", code: "RU" },
+            { name: "RWANDA", code: "RW" },
+            { name: "Saint Helena", code: "SH" },
+            { name: "Saint Kitts and Nevis", code: "KN" },
+            { name: "Saint Lucia", code: "LC" },
+            { name: "Saint Pierre and Miquelon", code: "PM" },
+            { name: "Saint Vincent and the Grenadines", code: "VC" },
+            { name: "Samoa", code: "WS" },
+            { name: "San Marino", code: "SM" },
+            { name: "Sao Tome and Principe", code: "ST" },
+            { name: "Saudi Arabia", code: "SA" },
+            { name: "Senegal", code: "SN" },
+            { name: "Serbia", code: "RS" },
+            { name: "Montenegro", code: "ME" },
+            { name: "Seychelles", code: "SC" },
+            { name: "Sierra Leone", code: "SL" },
+            { name: "Singapore", code: "SG" },
+            { name: "Slovakia", code: "SK" },
+            { name: "Slovenia", code: "SI" },
+            { name: "Solomon Islands", code: "SB" },
+            { name: "Somalia", code: "SO" },
+            { name: "South Africa", code: "ZA" },
+            { name: "South Georgia and the South Sandwich Islands", code: "GS" },
+            { name: "Spain", code: "ES" },
+            { name: "Sri Lanka", code: "LK" },
+            { name: "Sudan", code: "SD" },
+            { name: "Suriname", code: "SR" },
+            { name: "Svalbard and Jan Mayen", code: "SJ" },
+            { name: "Swaziland", code: "SZ" },
+            { name: "Sweden", code: "SE" },
+            { name: "Switzerland", code: "CH" },
+            { name: "Syrian Arab Republic", code: "SY" },
+            { name: "Taiwan, Province of China", code: "TW" },
+            { name: "Tajikistan", code: "TJ" },
+            { name: "Tanzania, United Republic of", code: "TZ" },
+            { name: "Thailand", code: "TH" },
+            { name: "Timor-Leste", code: "TL" },
+            { name: "Togo", code: "TG" },
+            { name: "Tokelau", code: "TK" },
+            { name: "Tonga", code: "TO" },
+            { name: "Trinidad and Tobago", code: "TT" },
+            { name: "Tunisia", code: "TN" },
+            { name: "Turkey", code: "TR" },
+            { name: "Turkmenistan", code: "TM" },
+            { name: "Turks and Caicos Islands", code: "TC" },
+            { name: "Tuvalu", code: "TV" },
+            { name: "Uganda", code: "UG" },
+            { name: "Ukraine", code: "UA" },
+            { name: "United Arab Emirates", code: "AE" },
+            { name: "United Kingdom", code: "GB" },
+            { name: "United States", code: "US" },
+            { name: "United States Minor Outlying Islands", code: "UM" },
+            { name: "Uruguay", code: "UY" },
+            { name: "Uzbekistan", code: "UZ" },
+            { name: "Vanuatu", code: "VU" },
+            { name: "Venezuela", code: "VE" },
+            { name: "Viet Nam", code: "VN" },
+            { name: "Virgin Islands, British", code: "VG" },
+            { name: "Virgin Islands, U.S.", code: "VI" },
+            { name: "Wallis and Futuna", code: "WF" },
+            { name: "Western Sahara", code: "EH" },
+            { name: "Yemen", code: "YE" },
+            { name: "Zambia", code: "ZM" },
+            { name: "Zimbabwe", code: "ZW" }
+        ]
+        return country
+} 

+ 3 - 1
utils/request.js

@@ -1,10 +1,12 @@
 import axios from 'axios';
 
+const token = $cookies.get('accessToken')
+axios.defaults.headers['authorization'] = `Bearer ${token}`;
 // 创建请求实例
 const instance = axios.create({
   baseURL: '/api',
   // 指定请求超时的毫秒数
-  timeout: 1000,
+  timeout: 10000,
   // 表示跨域请求时是否需要使用凭证
   withCredentials: false,
 });