asd123a20 3 anos atrás
commit
d44f9d7911
100 arquivos alterados com 65144 adições e 0 exclusões
  1. 3 0
      admin-code/.browserslistrc
  2. 5 0
      admin-code/.editorconfig
  3. 2 0
      admin-code/.env
  4. 1 0
      admin-code/.eslintignore
  5. 23 0
      admin-code/.eslintrc.js
  6. 23 0
      admin-code/.gitignore
  7. 24 0
      admin-code/README.md
  8. 5 0
      admin-code/babel.config.js
  9. 12586 0
      admin-code/package-lock.json
  10. 35 0
      admin-code/package.json
  11. BIN
      admin-code/public/favicon.ico
  12. 17 0
      admin-code/public/index.html
  13. 24 0
      admin-code/src/App.vue
  14. BIN
      admin-code/src/assets/logo.png
  15. 48 0
      admin-code/src/main.js
  16. 3 0
      admin-code/src/public-path.js
  17. 10 0
      admin-code/src/router/index.js
  18. 84 0
      admin-code/src/store/index.js
  19. 193 0
      admin-code/src/views/Home.vue
  20. 32 0
      admin-code/vue.config.js
  21. 3 0
      admin-column/.browserslistrc
  22. 5 0
      admin-column/.editorconfig
  23. 2 0
      admin-column/.env
  24. 1 0
      admin-column/.eslintignore
  25. 23 0
      admin-column/.eslintrc.js
  26. 23 0
      admin-column/.gitignore
  27. 24 0
      admin-column/README.md
  28. 5 0
      admin-column/babel.config.js
  29. 12565 0
      admin-column/package-lock.json
  30. 35 0
      admin-column/package.json
  31. BIN
      admin-column/public/favicon.ico
  32. 17 0
      admin-column/public/index.html
  33. 24 0
      admin-column/src/App.vue
  34. BIN
      admin-column/src/assets/logo.png
  35. 48 0
      admin-column/src/main.js
  36. 3 0
      admin-column/src/public-path.js
  37. 11 0
      admin-column/src/router/index.js
  38. 48 0
      admin-column/src/store/index.js
  39. 110 0
      admin-column/src/views/home.vue
  40. 31 0
      admin-column/vue.config.js
  41. 3 0
      admin-content/.browserslistrc
  42. 5 0
      admin-content/.editorconfig
  43. 2 0
      admin-content/.env
  44. 1 0
      admin-content/.eslintignore
  45. 23 0
      admin-content/.eslintrc.js
  46. 23 0
      admin-content/.gitignore
  47. 24 0
      admin-content/README.md
  48. 5 0
      admin-content/babel.config.js
  49. 12565 0
      admin-content/package-lock.json
  50. 35 0
      admin-content/package.json
  51. BIN
      admin-content/public/favicon.ico
  52. 17 0
      admin-content/public/index.html
  53. 24 0
      admin-content/src/App.vue
  54. BIN
      admin-content/src/assets/logo.png
  55. 48 0
      admin-content/src/main.js
  56. 3 0
      admin-content/src/public-path.js
  57. 11 0
      admin-content/src/router/index.js
  58. 48 0
      admin-content/src/store/index.js
  59. 110 0
      admin-content/src/views/home.vue
  60. 31 0
      admin-content/vue.config.js
  61. 3 0
      admin-files/.browserslistrc
  62. 5 0
      admin-files/.editorconfig
  63. 17 0
      admin-files/.eslintrc.js
  64. 23 0
      admin-files/.gitignore
  65. 24 0
      admin-files/README.md
  66. 5 0
      admin-files/babel.config.js
  67. 12553 0
      admin-files/package-lock.json
  68. 34 0
      admin-files/package.json
  69. BIN
      admin-files/public/favicon.ico
  70. 17 0
      admin-files/public/index.html
  71. 10 0
      admin-files/src/App.vue
  72. BIN
      admin-files/src/assets/logo.png
  73. 41 0
      admin-files/src/main.js
  74. 3 0
      admin-files/src/public-path.js
  75. 9 0
      admin-files/src/router/index.js
  76. 15 0
      admin-files/src/store/index.js
  77. 14 0
      admin-files/src/views/Home.vue
  78. 17 0
      admin-files/vue.config.js
  79. 3 0
      admin-frame/.browserslistrc
  80. 5 0
      admin-frame/.editorconfig
  81. 14 0
      admin-frame/.env
  82. 24 0
      admin-frame/.eslintrc.js
  83. 23 0
      admin-frame/.gitignore
  84. 27 0
      admin-frame/README.md
  85. 5 0
      admin-frame/babel.config.js
  86. 71 0
      admin-frame/lib/apps.js
  87. 49 0
      admin-frame/lib/axios.js
  88. 9 0
      admin-frame/lib/dict.js
  89. 11 0
      admin-frame/lib/qiankun.js
  90. 17 0
      admin-frame/lib/resChange.js
  91. 26 0
      admin-frame/lib/tree.js
  92. 42 0
      admin-frame/mock/menu.js
  93. 12673 0
      admin-frame/package-lock.json
  94. 39 0
      admin-frame/package.json
  95. BIN
      admin-frame/public/favicon.ico
  96. 17 0
      admin-frame/public/index.html
  97. 225 0
      admin-frame/src/App.vue
  98. BIN
      admin-frame/src/assets/bg2.jpg
  99. BIN
      admin-frame/src/assets/code.png
  100. 0 0
      admin-frame/src/assets/home.png

+ 3 - 0
admin-code/.browserslistrc

@@ -0,0 +1,3 @@
+> 1%
+last 2 versions
+not dead

+ 5 - 0
admin-code/.editorconfig

@@ -0,0 +1,5 @@
+[*.{js,jsx,ts,tsx,vue}]
+indent_style = space
+indent_size = 2
+trim_trailing_whitespace = true
+insert_final_newline = true

+ 2 - 0
admin-code/.env

@@ -0,0 +1,2 @@
+# 窗口使用弹出还是抽屉 (dialog And drawer)
+VUE_APP_WINDOW=dialog

+ 1 - 0
admin-code/.eslintignore

@@ -0,0 +1 @@
+public-path.js

+ 23 - 0
admin-code/.eslintrc.js

@@ -0,0 +1,23 @@
+module.exports = {
+  root: true,
+  env: {
+    node: true
+  },
+  extends: [
+    'plugin:vue/essential',
+    '@vue/standard'
+  ],
+  parserOptions: {
+    parser: 'babel-eslint'
+  },
+  rules: {
+    'no-console': 0,
+    'no-debugger': 0,
+    'comma-dangle': [2, 'never'],
+    'no-extra-parens': 2,
+    'no-extra-semi': 2,
+    semi: [2, 'always'],
+    'space-before-function-paren': [0, 'always'],
+    eqeqeq: 0
+  }
+};

+ 23 - 0
admin-code/.gitignore

@@ -0,0 +1,23 @@
+.DS_Store
+node_modules
+/dist
+
+
+# local env files
+.env.local
+.env.*.local
+
+# Log files
+npm-debug.log*
+yarn-debug.log*
+yarn-error.log*
+pnpm-debug.log*
+
+# Editor directories and files
+.idea
+.vscode
+*.suo
+*.ntvs*
+*.njsproj
+*.sln
+*.sw?

+ 24 - 0
admin-code/README.md

@@ -0,0 +1,24 @@
+# admin-code
+
+## Project setup
+```
+npm install
+```
+
+### Compiles and hot-reloads for development
+```
+npm run serve
+```
+
+### Compiles and minifies for production
+```
+npm run build
+```
+
+### Lints and fixes files
+```
+npm run lint
+```
+
+### Customize configuration
+See [Configuration Reference](https://cli.vuejs.org/config/).

+ 5 - 0
admin-code/babel.config.js

@@ -0,0 +1,5 @@
+module.exports = {
+  presets: [
+    '@vue/cli-plugin-babel/preset'
+  ]
+};

Diferenças do arquivo suprimidas por serem muito extensas
+ 12586 - 0
admin-code/package-lock.json


+ 35 - 0
admin-code/package.json

@@ -0,0 +1,35 @@
+{
+  "name": "admin-code",
+  "version": "0.1.0",
+  "private": true,
+  "scripts": {
+    "serve": "vue-cli-service serve",
+    "build": "vue-cli-service build",
+    "lint": "vue-cli-service lint"
+  },
+  "dependencies": {
+    "core-js": "^3.6.5",
+    "element-ui": "^2.15.6",
+    "vue": "^2.6.11",
+    "vue-router": "^3.2.0",
+    "vuex": "^3.4.0"
+  },
+  "devDependencies": {
+    "@vue/cli-plugin-babel": "~4.5.0",
+    "@vue/cli-plugin-eslint": "~4.5.0",
+    "@vue/cli-plugin-router": "~4.5.0",
+    "@vue/cli-plugin-vuex": "~4.5.0",
+    "@vue/cli-service": "~4.5.0",
+    "@vue/eslint-config-standard": "^5.1.2",
+    "babel-eslint": "^10.1.0",
+    "eslint": "^6.7.2",
+    "eslint-plugin-import": "^2.20.2",
+    "eslint-plugin-node": "^11.1.0",
+    "eslint-plugin-promise": "^4.2.1",
+    "eslint-plugin-standard": "^4.0.0",
+    "eslint-plugin-vue": "^6.2.2",
+    "sass": "^1.45.1",
+    "sass-loader": "^10.0.0",
+    "vue-template-compiler": "^2.6.11"
+  }
+}

BIN
admin-code/public/favicon.ico


+ 17 - 0
admin-code/public/index.html

@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html lang="">
+  <head>
+    <meta charset="utf-8">
+    <meta http-equiv="X-UA-Compatible" content="IE=edge">
+    <meta name="viewport" content="width=device-width,initial-scale=1.0">
+    <link rel="icon" href="<%= BASE_URL %>favicon.ico">
+    <title><%= htmlWebpackPlugin.options.title %></title>
+  </head>
+  <body>
+    <noscript>
+      <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
+    </noscript>
+    <div id="app"></div>
+    <!-- built files will be auto injected -->
+  </body>
+</html>

+ 24 - 0
admin-code/src/App.vue

@@ -0,0 +1,24 @@
+<template>
+  <div id="app">
+    <router-view></router-view>
+  </div>
+</template>
+
+<script>
+export default {
+  components: {},
+  computed: {},
+  data() {
+    return {};
+  },
+  mounted() {},
+  methods: {}
+};
+</script>
+
+<style lang="scss" scoped>
+#app {
+  width: 100%;
+  height: 100%;
+}
+</style>

BIN
admin-code/src/assets/logo.png


+ 48 - 0
admin-code/src/main.js

@@ -0,0 +1,48 @@
+import Vue from 'vue';
+import App from './App.vue';
+import VueRouter from 'vue-router';
+import routes from './router';
+import store from './store';
+import ElementUI from 'element-ui';
+import 'element-ui/lib/theme-chalk/index.css';
+import './public-path.js';
+import dict from '@lib/dict.js';
+import tree from '@lib/tree.js';
+import resChange from '@lib/resChange.js';
+Vue.config.productionTip = false;
+Vue.use(VueRouter);
+Vue.use(ElementUI);
+Vue.use(dict);
+Vue.use(tree);
+Vue.use(resChange);
+let router = null;
+let instance = null;
+function render (props = {}) {
+  const { container } = props;
+  router = new VueRouter({
+    base: window.__POWERED_BY_QIANKUN__ ? '/admin/code/' : '/',
+    mode: 'history',
+    routes
+  });
+  instance = new Vue({
+    router,
+    store,
+    render: (h) => h(App)
+  }).$mount(container ? container.querySelector('#app') : '#app');
+}
+
+// 独立运行时
+if (!window.__POWERED_BY_QIANKUN__) {
+  render();
+}
+
+export async function bootstrap () {}
+export async function mount (props) {
+  render(props);
+}
+export async function unmount () {
+  instance.$destroy();
+  instance.$el.innerHTML = '';
+  instance = null;
+  router = null;
+}

+ 3 - 0
admin-code/src/public-path.js

@@ -0,0 +1,3 @@
+if (window.__POWERED_BY_QIANKUN__) {
+  __webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__;
+}

+ 10 - 0
admin-code/src/router/index.js

@@ -0,0 +1,10 @@
+import home from '../views/Home.vue';
+const routes = [
+  {
+    path: '/home',
+    name: 'home',
+    component: home
+  }
+];
+
+export default routes;

+ 84 - 0
admin-code/src/store/index.js

@@ -0,0 +1,84 @@
+import Vue from 'vue';
+import Vuex from 'vuex';
+import $axios from '@lib/axios.js';
+Vue.use(Vuex);
+const api = {
+  typeCreate: '/api/code/type/create',
+  typeUpdate: '/api/code/type/update',
+  typeDelete: '/api/code/type/delete',
+  typeQuery: '/api/code/type/query',
+  codeCreate: '/api/code/dictionary/create',
+  codeUpdate: '/api/code/dictionary/update',
+  codeDelete: '/api/code/dictionary/delete',
+  codeQuery: '/api/code/dictionary/query'
+};
+
+const state = () => ({
+  dict: {
+    status: [
+      { code: '0', name: '正常' },
+      { code: '1', name: '注销' }
+    ]
+  },
+  typeList: [],
+  typeTotal: 0,
+  codeList: [],
+  codeTotal: 0
+});
+
+const actions = {
+  async typeQuery({ commit }) {
+    const res = await $axios.get(api.typeQuery);
+    commit('typeQuery', res);
+    return res;
+  },
+  async typeCreate({ commit }, payload) {
+    const res = await $axios.post(api.typeCreate, payload);
+    return res;
+  },
+  async typeUpdate({ commit }, payload) {
+    payload = { ...payload, id: payload._id };
+    const res = await $axios.post(api.typeUpdate, payload);
+    return res;
+  },
+  async typeDelete({ commit }, { id }) {
+    const res = await $axios.delete(`${api.typeDelete}/${id}`);
+    return res;
+  },
+  async codeQuery({ commit }, { filter, paging } = {}) {
+    const res = await $axios.get(api.codeQuery, { ...filter, skip: paging.page, limit: paging.size });
+    commit('codeQuery', res);
+    return res;
+  },
+  async codeCreate({ commit }, payload) {
+    const res = await $axios.post(api.codeCreate, payload);
+    return res;
+  },
+  async codeUpdate({ commit }, payload) {
+    payload = { ...payload, id: payload._id };
+    const res = await $axios.post(api.codeUpdate, payload);
+    return res;
+  },
+  async codeDelete({ commit }, { id }) {
+    const res = await $axios.delete(`${api.codeDelete}/${id}`);
+    return res;
+  }
+};
+
+const mutations = {
+  typeQuery(state, payload) {
+    state.typeList = payload.data;
+    state.typeTotal = payload.total;
+  },
+  codeQuery(state, payload) {
+    state.codeList = payload.data;
+    state.codeTotal = payload.total;
+  }
+};
+
+export default new Vuex.Store({
+  state,
+  mutations,
+  actions,
+  modules: {}
+});

+ 193 - 0
admin-code/src/views/Home.vue

@@ -0,0 +1,193 @@
+<template>
+  <div class="code-home">
+    <el-card class="box-card-left">
+      <div slot="header">
+        <span>字典类别</span>
+        <el-tooltip effect="dark" content="添加类型" placement="top-start">
+          <el-button style="float: right; padding: 3px 0" icon="el-icon-plus" type="text" @click="treeTypeAdd"></el-button>
+        </el-tooltip>
+      </div>
+      <deepTree :operation="true" @edit="treeEdit" @remove="treeRemove" @nodeClick="treeClick" class="deepTree" :data="treeList"></deepTree>
+    </el-card>
+    <el-card class="box-card">
+      <div slot="header" class="clearfix">
+        <span>数据字典</span>
+        <el-button style="float: right; padding: 3px 0" type="text" @click="filterAdd">添加字典</el-button>
+      </div>
+      <filterList ref="filterList" :tableData="tableData" :filed="filed" @edit="filtereEdit" @delete="filterDelete" @query="filterQuery" :total="codeTotal"></filterList>
+    </el-card>
+    <dialogAndDrawer :title="title" :visibleSync="visibleSync" v-if="visibleSync" @close="visibleSync = false">
+      <template v-slot:windowMain>
+        <formData :filed="formfiled" :data="formdata" :rules="formrules" @save="formSave"></formData>
+      </template>
+    </dialogAndDrawer>
+  </div>
+</template>
+
+<script>
+import filterList from '@components/filterList/index.vue';
+import deepTree from '@components/deepTree.vue';
+import dialogAndDrawer from '@components/dialogAndDrawer.vue';
+import formData from '@components/formData/index.vue';
+import { mapState, mapActions } from 'vuex';
+export default {
+  name: 'Home',
+  components: {
+    filterList,
+    deepTree,
+    dialogAndDrawer,
+    formData
+  },
+  computed: {
+    ...mapState({ tableData: 'codeList', treeList: 'typeList', codeTotal: 'codeTotal', typeTotal: 'typeTotal' })
+  },
+  data() {
+    return {
+      type: null,
+      title: '',
+      visibleSync: false,
+      formdata: {},
+      formrules: {},
+      formfiled: [
+        { label: '名称', name: 'name' },
+        { label: '编码', name: 'code' }
+      ],
+      filed: [
+        { label: '类型', name: 'parentCode' },
+        { label: '名称', name: 'name', filter: true },
+        { label: '编码', name: 'code', filter: true }
+      ]
+    };
+  },
+  mounted() {
+    this.treeQuery();
+  },
+  methods: {
+    ...mapActions(['typeQuery', 'typeCreate', 'typeUpdate', 'typeDelete', 'codeQuery', 'codeCreate', 'codeUpdate', 'codeDelete']),
+    // filter
+    // 添加
+    filterAdd() {
+      if (this.type == null) {
+        this.$message.warning('请先选择类别');
+        return;
+      }
+      this.formdata = {};
+      this.title = '添加字典';
+      this.visibleSync = true;
+    },
+    // 修改
+    filtereEdit(e) {
+      this.formdata = e;
+      this.title = '修改字典';
+      this.visibleSync = true;
+    },
+    // 删除
+    async filterDelete(e) {
+      const res = await this.codeDelete({ id: e?._id });
+      this.$resChange(res, '删除成功');
+      this.filterQuery();
+    },
+    // 查询
+    async filterQuery({ filter = {}, paging = { page: 0, size: 10 } } = {}) {
+      if (this.type == null) {
+        this.$message.error('请先选择类别');
+        return;
+      }
+      filter.parentCode = this.type;
+      await this.codeQuery({ filter, paging });
+    },
+    // tree
+    // 查询
+    async treeQuery(e) {
+      await this.typeQuery({ filter: {} });
+    },
+    // 添加
+    treeTypeAdd() {
+      this.type = null;
+      this.formdata = {};
+      this.title = '添加类别';
+      this.visibleSync = true;
+    },
+    // 修改
+    treeEdit(e) {
+      this.type = null;
+      this.formdata = e;
+      this.title = '修改类别';
+      this.visibleSync = true;
+    },
+    // 删除
+    async treeRemove(e) {
+      this.type = null;
+      const res = await this.typeDelete({ id: e?._id });
+      this.$resChange(res, '删除成功');
+      this.treeQuery();
+    },
+    // 选择
+    treeClick(e) {
+      this.type = e.data.code;
+      this.filterQuery();
+    },
+    // 表单保存
+    async formSave(e) {
+      if (e.isRevise && e?.isRevise == false) {
+        this.$message.warning('未作修改');
+        return;
+      }
+      this.$delete(e, 'isRevise');
+      let res, msg;
+      if (this.type !== null) {
+        // 字典
+        this.$set(e, 'parentCode', this.type);
+        if (e._id) {
+          // 字典修改
+          res = await this.codeUpdate(e);
+          msg = '字典修改成功';
+        } else {
+          // 字典添加
+          res = await this.codeCreate(e);
+          msg = '字典添加成功';
+        }
+      } else {
+        // 字典类别
+        if (e._id) {
+          // 类别修改
+          res = await this.typeUpdate(e);
+          msg = '类别修改成功';
+        } else {
+          // 类别添加
+          res = await this.typeCreate(e);
+          msg = '类别添加成功';
+        }
+      }
+      this.$resChange(res, msg);
+      this.treeQuery();
+      this.filterQuery();
+      this.visibleSync = false;
+    }
+  }
+};
+</script>
+<style lang="scss">
+.code-home {
+  width: 100%;
+  height: 100%;
+  display: flex;
+  .box-card {
+    width: 84%;
+    height: 100%;
+  }
+  .box-card-left {
+    width: 15%;
+    height: 100%;
+    .el-card__body {
+      height: 88%;
+      .deepTree {
+        width: 100%;
+        height: 100%;
+        overflow-y: auto;
+      }
+    }
+  }
+}
+
+</style>

+ 32 - 0
admin-code/vue.config.js

@@ -0,0 +1,32 @@
+const path = require('path');
+const frameSrc = path.resolve(__dirname, '../admin-frame');
+const packageName = require('./package.json').name;
+console.log(path.join(frameSrc));
+module.exports = {
+  devServer: {
+    port: 3001,
+    headers: {
+      'Access-Control-Allow-Origin': '*'
+    },
+    proxy: {
+      '/api/': {
+        target: 'http://192.168.0.45:18090'
+        // target: 'http://127.0.0.1:18090'
+      }
+    }
+  },
+  configureWebpack: {
+    output: {
+      library: `${packageName}-[name]`,
+      libraryTarget: 'umd',
+      jsonpFunction: `webpackJsonp_${packageName}`
+    },
+    resolve: {
+      alias: {
+        '@components': path.join(frameSrc, '/src/components'),
+        '@style': path.join(frameSrc, '/style'),
+        '@lib': path.join(frameSrc, '/lib')
+      }
+    }
+  }
+};

+ 3 - 0
admin-column/.browserslistrc

@@ -0,0 +1,3 @@
+> 1%
+last 2 versions
+not dead

+ 5 - 0
admin-column/.editorconfig

@@ -0,0 +1,5 @@
+[*.{js,jsx,ts,tsx,vue}]
+indent_style = space
+indent_size = 2
+trim_trailing_whitespace = true
+insert_final_newline = true

+ 2 - 0
admin-column/.env

@@ -0,0 +1,2 @@
+# 窗口使用弹出还是抽屉 (dialog And drawer)
+VUE_APP_WINDOW=dialog

+ 1 - 0
admin-column/.eslintignore

@@ -0,0 +1 @@
+public-path.js

+ 23 - 0
admin-column/.eslintrc.js

@@ -0,0 +1,23 @@
+module.exports = {
+  root: true,
+  env: {
+    node: true
+  },
+  extends: [
+    'plugin:vue/essential',
+    '@vue/standard'
+  ],
+  parserOptions: {
+    parser: 'babel-eslint'
+  },
+  rules: {
+    'no-console': 0,
+    'no-debugger': 0,
+    'comma-dangle': [2, 'never'],
+    'no-extra-parens': 2,
+    'no-extra-semi': 2,
+    semi: [2, 'always'],
+    'space-before-function-paren': [0, 'always'],
+    eqeqeq: 0
+  }
+};

+ 23 - 0
admin-column/.gitignore

@@ -0,0 +1,23 @@
+.DS_Store
+node_modules
+/dist
+
+
+# local env files
+.env.local
+.env.*.local
+
+# Log files
+npm-debug.log*
+yarn-debug.log*
+yarn-error.log*
+pnpm-debug.log*
+
+# Editor directories and files
+.idea
+.vscode
+*.suo
+*.ntvs*
+*.njsproj
+*.sln
+*.sw?

+ 24 - 0
admin-column/README.md

@@ -0,0 +1,24 @@
+# admin-role
+
+## Project setup
+```
+npm install
+```
+
+### Compiles and hot-reloads for development
+```
+npm run serve
+```
+
+### Compiles and minifies for production
+```
+npm run build
+```
+
+### Lints and fixes files
+```
+npm run lint
+```
+
+### Customize configuration
+See [Configuration Reference](https://cli.vuejs.org/config/).

+ 5 - 0
admin-column/babel.config.js

@@ -0,0 +1,5 @@
+module.exports = {
+  presets: [
+    '@vue/cli-plugin-babel/preset'
+  ]
+};

Diferenças do arquivo suprimidas por serem muito extensas
+ 12565 - 0
admin-column/package-lock.json


+ 35 - 0
admin-column/package.json

@@ -0,0 +1,35 @@
+{
+  "name": "admin-column",
+  "version": "0.1.0",
+  "private": true,
+  "scripts": {
+    "serve": "vue-cli-service serve",
+    "build": "vue-cli-service build",
+    "lint": "vue-cli-service lint"
+  },
+  "dependencies": {
+    "core-js": "^3.6.5",
+    "element-ui": "^2.15.6",
+    "sass": "^1.48.0",
+    "sass-loader": "^10.0.0",
+    "vue": "^2.6.11",
+    "vue-router": "^3.2.0",
+    "vuex": "^3.4.0"
+  },
+  "devDependencies": {
+    "@vue/cli-plugin-babel": "~4.5.0",
+    "@vue/cli-plugin-eslint": "~4.5.0",
+    "@vue/cli-plugin-router": "~4.5.0",
+    "@vue/cli-plugin-vuex": "~4.5.0",
+    "@vue/cli-service": "~4.5.0",
+    "@vue/eslint-config-standard": "^5.1.2",
+    "babel-eslint": "^10.1.0",
+    "eslint": "^6.7.2",
+    "eslint-plugin-import": "^2.20.2",
+    "eslint-plugin-node": "^11.1.0",
+    "eslint-plugin-promise": "^4.2.1",
+    "eslint-plugin-standard": "^4.0.0",
+    "eslint-plugin-vue": "^6.2.2",
+    "vue-template-compiler": "^2.6.11"
+  }
+}

BIN
admin-column/public/favicon.ico


+ 17 - 0
admin-column/public/index.html

@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html lang="">
+  <head>
+    <meta charset="utf-8">
+    <meta http-equiv="X-UA-Compatible" content="IE=edge">
+    <meta name="viewport" content="width=device-width,initial-scale=1.0">
+    <link rel="icon" href="<%= BASE_URL %>favicon.ico">
+    <title><%= htmlWebpackPlugin.options.title %></title>
+  </head>
+  <body>
+    <noscript>
+      <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
+    </noscript>
+    <div id="app"></div>
+    <!-- built files will be auto injected -->
+  </body>
+</html>

+ 24 - 0
admin-column/src/App.vue

@@ -0,0 +1,24 @@
+<template>
+  <div id="app">
+    <router-view></router-view>
+  </div>
+</template>
+
+<script>
+export default {
+  components: {},
+  computed: {},
+  data() {
+    return {};
+  },
+  mounted() {},
+  methods: {}
+};
+</script>
+
+<style lang="scss" scoped>
+#app {
+  width: 100%;
+  height: 100%;
+}
+</style>

BIN
admin-column/src/assets/logo.png


+ 48 - 0
admin-column/src/main.js

@@ -0,0 +1,48 @@
+import Vue from 'vue';
+import App from './App.vue';
+import VueRouter from 'vue-router';
+import routes from './router';
+import store from './store';
+import ElementUI from 'element-ui';
+import 'element-ui/lib/theme-chalk/index.css';
+import './public-path.js';
+import dict from '@lib/dict.js';
+import tree from '@lib/tree.js';
+import resChange from '@lib/resChange.js';
+Vue.config.productionTip = false;
+Vue.use(VueRouter);
+Vue.use(ElementUI);
+Vue.use(dict);
+Vue.use(tree);
+Vue.use(resChange);
+let router = null;
+let instance = null;
+function render (props = {}) {
+  const { container } = props;
+  router = new VueRouter({
+    base: window.__POWERED_BY_QIANKUN__ ? '/admin/column/' : '/',
+    mode: 'history',
+    routes
+  });
+  instance = new Vue({
+    router,
+    store,
+    render: (h) => h(App)
+  }).$mount(container ? container.querySelector('#app') : '#app');
+}
+
+// 独立运行时
+if (!window.__POWERED_BY_QIANKUN__) {
+  render();
+}
+
+export async function bootstrap () {}
+export async function mount (props) {
+  render(props);
+}
+export async function unmount () {
+  instance.$destroy();
+  instance.$el.innerHTML = '';
+  instance = null;
+  router = null;
+}

+ 3 - 0
admin-column/src/public-path.js

@@ -0,0 +1,3 @@
+if (window.__POWERED_BY_QIANKUN__) {
+  __webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__;
+}

+ 11 - 0
admin-column/src/router/index.js

@@ -0,0 +1,11 @@
+import home from '../views/home.vue';
+
+const routes = [
+  {
+    path: '/home',
+    name: 'home',
+    component: home
+  }
+];
+
+export default routes;

+ 48 - 0
admin-column/src/store/index.js

@@ -0,0 +1,48 @@
+import Vue from 'vue';
+import Vuex from 'vuex';
+import $axios from '@lib/axios.js';
+const api = {
+  columnCreate: '/api/cms/column/create',
+  columnUpdate: '/api/cms/column/update',
+  columnDelete: '/api/cms/column/delete',
+  columnQuery: '/api/cms/column/query'
+};
+Vue.use(Vuex);
+const state = () => ({
+  Total: 0,
+  columnList: []
+});
+
+const actions = {
+  async columnCreate ({ commit }, payload) {
+    const res = await $axios.post(api.columnCreate, payload);
+    return res;
+  },
+  async columnUpdate ({ commit }, payload) {
+    const res = await $axios.post(api.columnUpdate, { ...payload, id: payload._id });
+    return res;
+  },
+  async columnDelete ({ commit }, { id }) {
+    const res = await $axios.delete(`${api.columnDelete}/${id}`);
+    return res;
+  },
+  async columnQuery ({ commit }, { filter, paging } = {}) {
+    const res = await $axios.get(api.columnQuery, { ...filter, skip: paging.page, limit: paging.size });
+    commit('columnQuery', res);
+    return res;
+  }
+};
+
+const mutations = {
+  columnQuery(state, payload) {
+    state.columnList = payload.data;
+    state.Total = payload.total;
+  }
+};
+
+export default new Vuex.Store({
+  state,
+  actions,
+  mutations,
+  modules: {}
+});

+ 110 - 0
admin-column/src/views/home.vue

@@ -0,0 +1,110 @@
+<template>
+  <div class="box">
+    <el-card class="box-card">
+      <div slot="header" class="clearfix">
+        <span>栏目管理</span>
+        <el-button style="float: right; padding: 3px 0" type="text" @click="addcolumn">添加栏目</el-button>
+      </div>
+      <div class="main">
+        <filterList ref="filterList" :tableData="columnList" :filed="filed" @edit="filtereEdit" @delete="filterDelete" @query="filterQuery" :total="Total"></filterList>
+      </div>
+    </el-card>
+    <dialogAndDrawer :width="'35%'" :title="title" :visibleSync="visibleSync" v-if="visibleSync" @close="visibleSync = false">
+      <template v-slot:windowMain>
+        <formData :filed="formfiled" :data="formdata" :rules="formrules" @save="formSave"></formData>
+      </template>
+    </dialogAndDrawer>
+  </div>
+</template>
+<script>
+import filterList from '@components/filterList/index.vue';
+import dialogAndDrawer from '@components/dialogAndDrawer.vue';
+import formData from '@components/formData/index.vue';
+import { mapState, mapActions } from 'vuex';
+export default {
+  components: {
+    filterList,
+    dialogAndDrawer,
+    formData
+  },
+  data() {
+    return {
+      title: '',
+      visibleSync: false,
+      filed: [
+        { name: 'name', label: '名称', filter: true },
+        { name: 'code', label: '编码', filter: true }
+      ],
+      formdata: {},
+      formfiled: [
+        { name: 'name', label: '名称' },
+        { name: 'code', label: '编码' }
+      ],
+      formrules: {}
+    };
+  },
+  computed: {
+    ...mapState(['columnList', 'Total'])
+  },
+  async mounted() {
+    await this.filterQuery();
+  },
+  methods: {
+    ...mapActions(['columnQuery', 'columnCreate', 'columnUpdate', 'columnDelete', 'columnQuery', 'queryBind', 'batchUnBind', 'batchBind']),
+    // 添加
+    addcolumn () {
+      this.formdata = {};
+      this.title = '添加栏目';
+      this.visibleSync = true;
+    },
+    // 修改
+    filtereEdit (e) {
+      this.formdata = e;
+      this.title = '修改栏目';
+      this.visibleSync = true;
+    },
+    // 删除
+    async filterDelete (e) {
+      const res = await this.columnDelete({ id: e?._id });
+      this.$resChange(res, '删除成功');
+      this.filterQuery();
+    },
+    // 查询
+    async filterQuery ({ filter = {}, paging = { page: 0, size: 10 } } = {}) {
+      await this.columnQuery({ filter, paging });
+    },
+    // 表单保存
+    async formSave (e) {
+      if (e.isRevise && e?.isRevise == false) {
+        this.$message.warning('未作修改');
+        return;
+      }
+      this.$delete(e, 'isRevise');
+      let res, msg;
+      // 修改
+      if (e._id) {
+        res = await this.columnUpdate(e);
+        msg = '栏目修改成功';
+      } else {
+        res = await this.columnCreate(e);
+        msg = '栏目修改成功';
+      }
+      this.$resChange(res, msg);
+      this.filterQuery();
+      this.visibleSync = false;
+    }
+  }
+};
+</script>
+<style lang="scss" scoped>
+.box {
+  width: 100%;
+  height: 100%;
+  .box-card {
+    height: 100%;
+    .el-card__body {
+      height: 100%;
+    }
+  }
+}
+</style>

+ 31 - 0
admin-column/vue.config.js

@@ -0,0 +1,31 @@
+const path = require('path');
+const frameSrc = path.resolve(__dirname, '../admin-frame');
+const packageName = require('./package.json').name;
+module.exports = {
+  devServer: {
+    port: 3006,
+    headers: {
+      'Access-Control-Allow-Origin': '*'
+    },
+    proxy: {
+      '/api/': {
+        target: 'http://192.168.0.45:18090'
+        // target: 'http://127.0.0.1:18090'
+      }
+    }
+  },
+  configureWebpack: {
+    output: {
+      library: `${packageName}-[name]`,
+      libraryTarget: 'umd',
+      jsonpFunction: `webpackJsonp_${packageName}`
+    },
+    resolve: {
+      alias: {
+        '@components': path.join(frameSrc, '/src/components'),
+        '@style': path.join(frameSrc, '/style'),
+        '@lib': path.join(frameSrc, '/lib')
+      }
+    }
+  }
+};

+ 3 - 0
admin-content/.browserslistrc

@@ -0,0 +1,3 @@
+> 1%
+last 2 versions
+not dead

+ 5 - 0
admin-content/.editorconfig

@@ -0,0 +1,5 @@
+[*.{js,jsx,ts,tsx,vue}]
+indent_style = space
+indent_size = 2
+trim_trailing_whitespace = true
+insert_final_newline = true

+ 2 - 0
admin-content/.env

@@ -0,0 +1,2 @@
+# 窗口使用弹出还是抽屉 (dialog And drawer)
+VUE_APP_WINDOW=dialog

+ 1 - 0
admin-content/.eslintignore

@@ -0,0 +1 @@
+public-path.js

+ 23 - 0
admin-content/.eslintrc.js

@@ -0,0 +1,23 @@
+module.exports = {
+  root: true,
+  env: {
+    node: true
+  },
+  extends: [
+    'plugin:vue/essential',
+    '@vue/standard'
+  ],
+  parserOptions: {
+    parser: 'babel-eslint'
+  },
+  rules: {
+    'no-console': 0,
+    'no-debugger': 0,
+    'comma-dangle': [2, 'never'],
+    'no-extra-parens': 2,
+    'no-extra-semi': 2,
+    semi: [2, 'always'],
+    'space-before-function-paren': [0, 'always'],
+    eqeqeq: 0
+  }
+};

+ 23 - 0
admin-content/.gitignore

@@ -0,0 +1,23 @@
+.DS_Store
+node_modules
+/dist
+
+
+# local env files
+.env.local
+.env.*.local
+
+# Log files
+npm-debug.log*
+yarn-debug.log*
+yarn-error.log*
+pnpm-debug.log*
+
+# Editor directories and files
+.idea
+.vscode
+*.suo
+*.ntvs*
+*.njsproj
+*.sln
+*.sw?

+ 24 - 0
admin-content/README.md

@@ -0,0 +1,24 @@
+# admin-role
+
+## Project setup
+```
+npm install
+```
+
+### Compiles and hot-reloads for development
+```
+npm run serve
+```
+
+### Compiles and minifies for production
+```
+npm run build
+```
+
+### Lints and fixes files
+```
+npm run lint
+```
+
+### Customize configuration
+See [Configuration Reference](https://cli.vuejs.org/config/).

+ 5 - 0
admin-content/babel.config.js

@@ -0,0 +1,5 @@
+module.exports = {
+  presets: [
+    '@vue/cli-plugin-babel/preset'
+  ]
+};

Diferenças do arquivo suprimidas por serem muito extensas
+ 12565 - 0
admin-content/package-lock.json


+ 35 - 0
admin-content/package.json

@@ -0,0 +1,35 @@
+{
+  "name": "admin-contents",
+  "version": "0.1.0",
+  "private": true,
+  "scripts": {
+    "serve": "vue-cli-service serve",
+    "build": "vue-cli-service build",
+    "lint": "vue-cli-service lint"
+  },
+  "dependencies": {
+    "core-js": "^3.6.5",
+    "element-ui": "^2.15.6",
+    "sass": "^1.48.0",
+    "sass-loader": "^10.0.0",
+    "vue": "^2.6.11",
+    "vue-router": "^3.2.0",
+    "vuex": "^3.4.0"
+  },
+  "devDependencies": {
+    "@vue/cli-plugin-babel": "~4.5.0",
+    "@vue/cli-plugin-eslint": "~4.5.0",
+    "@vue/cli-plugin-router": "~4.5.0",
+    "@vue/cli-plugin-vuex": "~4.5.0",
+    "@vue/cli-service": "~4.5.0",
+    "@vue/eslint-config-standard": "^5.1.2",
+    "babel-eslint": "^10.1.0",
+    "eslint": "^6.7.2",
+    "eslint-plugin-import": "^2.20.2",
+    "eslint-plugin-node": "^11.1.0",
+    "eslint-plugin-promise": "^4.2.1",
+    "eslint-plugin-standard": "^4.0.0",
+    "eslint-plugin-vue": "^6.2.2",
+    "vue-template-compiler": "^2.6.11"
+  }
+}

BIN
admin-content/public/favicon.ico


+ 17 - 0
admin-content/public/index.html

@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html lang="">
+  <head>
+    <meta charset="utf-8">
+    <meta http-equiv="X-UA-Compatible" content="IE=edge">
+    <meta name="viewport" content="width=device-width,initial-scale=1.0">
+    <link rel="icon" href="<%= BASE_URL %>favicon.ico">
+    <title><%= htmlWebpackPlugin.options.title %></title>
+  </head>
+  <body>
+    <noscript>
+      <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
+    </noscript>
+    <div id="app"></div>
+    <!-- built files will be auto injected -->
+  </body>
+</html>

+ 24 - 0
admin-content/src/App.vue

@@ -0,0 +1,24 @@
+<template>
+  <div id="app">
+    <router-view></router-view>
+  </div>
+</template>
+
+<script>
+export default {
+  components: {},
+  computed: {},
+  data() {
+    return {};
+  },
+  mounted() {},
+  methods: {}
+};
+</script>
+
+<style lang="scss" scoped>
+#app {
+  width: 100%;
+  height: 100%;
+}
+</style>

BIN
admin-content/src/assets/logo.png


+ 48 - 0
admin-content/src/main.js

@@ -0,0 +1,48 @@
+import Vue from 'vue';
+import App from './App.vue';
+import VueRouter from 'vue-router';
+import routes from './router';
+import store from './store';
+import ElementUI from 'element-ui';
+import 'element-ui/lib/theme-chalk/index.css';
+import './public-path.js';
+import dict from '@lib/dict.js';
+import tree from '@lib/tree.js';
+import resChange from '@lib/resChange.js';
+Vue.config.productionTip = false;
+Vue.use(VueRouter);
+Vue.use(ElementUI);
+Vue.use(dict);
+Vue.use(tree);
+Vue.use(resChange);
+let router = null;
+let instance = null;
+function render (props = {}) {
+  const { container } = props;
+  router = new VueRouter({
+    base: window.__POWERED_BY_QIANKUN__ ? '/admin/contents/' : '/',
+    mode: 'history',
+    routes
+  });
+  instance = new Vue({
+    router,
+    store,
+    render: (h) => h(App)
+  }).$mount(container ? container.querySelector('#app') : '#app');
+}
+
+// 独立运行时
+if (!window.__POWERED_BY_QIANKUN__) {
+  render();
+}
+
+export async function bootstrap () {}
+export async function mount (props) {
+  render(props);
+}
+export async function unmount () {
+  instance.$destroy();
+  instance.$el.innerHTML = '';
+  instance = null;
+  router = null;
+}

+ 3 - 0
admin-content/src/public-path.js

@@ -0,0 +1,3 @@
+if (window.__POWERED_BY_QIANKUN__) {
+  __webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__;
+}

+ 11 - 0
admin-content/src/router/index.js

@@ -0,0 +1,11 @@
+import home from '../views/home.vue';
+
+const routes = [
+  {
+    path: '/home',
+    name: 'home',
+    component: home
+  }
+];
+
+export default routes;

+ 48 - 0
admin-content/src/store/index.js

@@ -0,0 +1,48 @@
+import Vue from 'vue';
+import Vuex from 'vuex';
+import $axios from '@lib/axios.js';
+const api = {
+  contentsCreate: '/api/cms/contents/create',
+  contentsUpdate: '/api/cms/contents/update',
+  contentsDelete: '/api/cms/contents/delete',
+  contentsQuery: '/api/cms/contents/query'
+};
+Vue.use(Vuex);
+const state = () => ({
+  Total: 0,
+  contentsList: []
+});
+
+const actions = {
+  async contentsCreate ({ commit }, payload) {
+    const res = await $axios.post(api.contentsCreate, payload);
+    return res;
+  },
+  async contentsUpdate ({ commit }, payload) {
+    const res = await $axios.post(api.contentsUpdate, { ...payload, id: payload._id });
+    return res;
+  },
+  async contentsDelete ({ commit }, { id }) {
+    const res = await $axios.delete(`${api.contentsDelete}/${id}`);
+    return res;
+  },
+  async contentsQuery ({ commit }, { filter, paging } = {}) {
+    const res = await $axios.get(api.contentsQuery, { ...filter, skip: paging.page, limit: paging.size });
+    commit('contentsQuery', res);
+    return res;
+  }
+};
+
+const mutations = {
+  contentsQuery(state, payload) {
+    state.contentsList = payload.data;
+    state.Total = payload.total;
+  }
+};
+
+export default new Vuex.Store({
+  state,
+  actions,
+  mutations,
+  modules: {}
+});

+ 110 - 0
admin-content/src/views/home.vue

@@ -0,0 +1,110 @@
+<template>
+  <div class="box">
+    <el-card class="box-card">
+      <div slot="header" class="clearfix">
+        <span>文章管理</span>
+        <el-button style="float: right; padding: 3px 0" type="text" @click="addcontents">添加文章</el-button>
+      </div>
+      <div class="main">
+        <filterList ref="filterList" :tableData="contentsList" :filed="filed" @edit="filtereEdit" @delete="filterDelete" @query="filterQuery" :total="Total"></filterList>
+      </div>
+    </el-card>
+    <dialogAndDrawer :width="'35%'" :title="title" :visibleSync="visibleSync" v-if="visibleSync" @close="visibleSync = false">
+      <template v-slot:windowMain>
+        <formData :filed="formfiled" :data="formdata" :rules="formrules" @save="formSave"></formData>
+      </template>
+    </dialogAndDrawer>
+  </div>
+</template>
+<script>
+import filterList from '@components/filterList/index.vue';
+import dialogAndDrawer from '@components/dialogAndDrawer.vue';
+import formData from '@components/formData/index.vue';
+import { mapState, mapActions } from 'vuex';
+export default {
+  components: {
+    filterList,
+    dialogAndDrawer,
+    formData
+  },
+  data() {
+    return {
+      title: '',
+      visibleSync: false,
+      filed: [
+        { name: 'name', label: '名称', filter: true },
+        { name: 'code', label: '编码', filter: true }
+      ],
+      formdata: {},
+      formfiled: [
+        { name: 'name', label: '名称' },
+        { name: 'code', label: '编码' }
+      ],
+      formrules: {}
+    };
+  },
+  computed: {
+    ...mapState(['contentsList', 'Total'])
+  },
+  async mounted() {
+    await this.filterQuery();
+  },
+  methods: {
+    ...mapActions(['contentsQuery', 'contentsCreate', 'contentsUpdate', 'contentsDelete', 'contentsQuery', 'queryBind', 'batchUnBind', 'batchBind']),
+    // 添加
+    addcontents () {
+      this.formdata = {};
+      this.title = '添加文章';
+      this.visibleSync = true;
+    },
+    // 修改
+    filtereEdit (e) {
+      this.formdata = e;
+      this.title = '修改文章';
+      this.visibleSync = true;
+    },
+    // 删除
+    async filterDelete (e) {
+      const res = await this.contentsDelete({ id: e?._id });
+      this.$resChange(res, '删除成功');
+      this.filterQuery();
+    },
+    // 查询
+    async filterQuery ({ filter = {}, paging = { page: 0, size: 10 } } = {}) {
+      await this.contentsQuery({ filter, paging });
+    },
+    // 表单保存
+    async formSave (e) {
+      if (e.isRevise && e?.isRevise == false) {
+        this.$message.warning('未作修改');
+        return;
+      }
+      this.$delete(e, 'isRevise');
+      let res, msg;
+      // 修改
+      if (e._id) {
+        res = await this.contentsUpdate(e);
+        msg = '文章修改成功';
+      } else {
+        res = await this.contentsCreate(e);
+        msg = '文章修改成功';
+      }
+      this.$resChange(res, msg);
+      this.filterQuery();
+      this.visibleSync = false;
+    }
+  }
+};
+</script>
+<style lang="scss" scoped>
+.box {
+  width: 100%;
+  height: 100%;
+  .box-card {
+    height: 100%;
+    .el-card__body {
+      height: 100%;
+    }
+  }
+}
+</style>

+ 31 - 0
admin-content/vue.config.js

@@ -0,0 +1,31 @@
+const path = require('path');
+const frameSrc = path.resolve(__dirname, '../admin-frame');
+const packageName = require('./package.json').name;
+module.exports = {
+  devServer: {
+    port: 3007,
+    headers: {
+      'Access-Control-Allow-Origin': '*'
+    },
+    proxy: {
+      '/api/': {
+        target: 'http://192.168.0.45:18090'
+        // target: 'http://127.0.0.1:18090'
+      }
+    }
+  },
+  configureWebpack: {
+    output: {
+      library: `${packageName}-[name]`,
+      libraryTarget: 'umd',
+      jsonpFunction: `webpackJsonp_${packageName}`
+    },
+    resolve: {
+      alias: {
+        '@components': path.join(frameSrc, '/src/components'),
+        '@style': path.join(frameSrc, '/style'),
+        '@lib': path.join(frameSrc, '/lib')
+      }
+    }
+  }
+};

+ 3 - 0
admin-files/.browserslistrc

@@ -0,0 +1,3 @@
+> 1%
+last 2 versions
+not dead

+ 5 - 0
admin-files/.editorconfig

@@ -0,0 +1,5 @@
+[*.{js,jsx,ts,tsx,vue}]
+indent_style = space
+indent_size = 2
+trim_trailing_whitespace = true
+insert_final_newline = true

+ 17 - 0
admin-files/.eslintrc.js

@@ -0,0 +1,17 @@
+module.exports = {
+  root: true,
+  env: {
+    node: true
+  },
+  extends: [
+    'plugin:vue/essential',
+    '@vue/standard'
+  ],
+  parserOptions: {
+    parser: 'babel-eslint'
+  },
+  rules: {
+    'no-console': process.env.NODE_ENV === 'production' ? 'warn' : 'off',
+    'no-debugger': process.env.NODE_ENV === 'production' ? 'warn' : 'off'
+  }
+}

+ 23 - 0
admin-files/.gitignore

@@ -0,0 +1,23 @@
+.DS_Store
+node_modules
+/dist
+
+
+# local env files
+.env.local
+.env.*.local
+
+# Log files
+npm-debug.log*
+yarn-debug.log*
+yarn-error.log*
+pnpm-debug.log*
+
+# Editor directories and files
+.idea
+.vscode
+*.suo
+*.ntvs*
+*.njsproj
+*.sln
+*.sw?

+ 24 - 0
admin-files/README.md

@@ -0,0 +1,24 @@
+# admin-code
+
+## Project setup
+```
+npm install
+```
+
+### Compiles and hot-reloads for development
+```
+npm run serve
+```
+
+### Compiles and minifies for production
+```
+npm run build
+```
+
+### Lints and fixes files
+```
+npm run lint
+```
+
+### Customize configuration
+See [Configuration Reference](https://cli.vuejs.org/config/).

+ 5 - 0
admin-files/babel.config.js

@@ -0,0 +1,5 @@
+module.exports = {
+  presets: [
+    '@vue/cli-plugin-babel/preset'
+  ]
+}

Diferenças do arquivo suprimidas por serem muito extensas
+ 12553 - 0
admin-files/package-lock.json


+ 34 - 0
admin-files/package.json

@@ -0,0 +1,34 @@
+{
+  "name": "admin-files",
+  "version": "0.1.0",
+  "private": true,
+  "scripts": {
+    "serve": "vue-cli-service serve",
+    "build": "vue-cli-service build",
+    "lint": "vue-cli-service lint"
+  },
+  "dependencies": {
+    "core-js": "^3.6.5",
+    "vue": "^2.6.11",
+    "vue-router": "^3.2.0",
+    "vuex": "^3.4.0"
+  },
+  "devDependencies": {
+    "@vue/cli-plugin-babel": "~4.5.0",
+    "@vue/cli-plugin-eslint": "~4.5.0",
+    "@vue/cli-plugin-router": "~4.5.0",
+    "@vue/cli-plugin-vuex": "~4.5.0",
+    "@vue/cli-service": "~4.5.0",
+    "@vue/eslint-config-standard": "^5.1.2",
+    "babel-eslint": "^10.1.0",
+    "eslint": "^6.7.2",
+    "eslint-plugin-import": "^2.20.2",
+    "eslint-plugin-node": "^11.1.0",
+    "eslint-plugin-promise": "^4.2.1",
+    "eslint-plugin-standard": "^4.0.0",
+    "eslint-plugin-vue": "^6.2.2",
+    "less": "^3.0.4",
+    "less-loader": "^5.0.0",
+    "vue-template-compiler": "^2.6.11"
+  }
+}

BIN
admin-files/public/favicon.ico


+ 17 - 0
admin-files/public/index.html

@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html lang="">
+  <head>
+    <meta charset="utf-8">
+    <meta http-equiv="X-UA-Compatible" content="IE=edge">
+    <meta name="viewport" content="width=device-width,initial-scale=1.0">
+    <link rel="icon" href="<%= BASE_URL %>favicon.ico">
+    <title><%= htmlWebpackPlugin.options.title %></title>
+  </head>
+  <body>
+    <noscript>
+      <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
+    </noscript>
+    <div id="app"></div>
+    <!-- built files will be auto injected -->
+  </body>
+</html>

+ 10 - 0
admin-files/src/App.vue

@@ -0,0 +1,10 @@
+<template>
+  <div id="app">
+    <div id="nav">
+      456
+    </div>
+    <!-- <router-view></router-view> -->
+  </div>
+</template>
+
+<style lang="less"></style>

BIN
admin-files/src/assets/logo.png


+ 41 - 0
admin-files/src/main.js

@@ -0,0 +1,41 @@
+import Vue from 'vue'
+import App from './App.vue'
+import VueRouter from 'vue-router'
+import routes from './router'
+import store from './store'
+Vue.config.productionTip = false
+
+let router = null
+let instance = null
+function render (props = {}) {
+  const { container } = props
+  router = new VueRouter({
+    base: window.__POWERED_BY_QIANKUN__ ? '/admin-files/' : '/',
+    mode: 'history',
+    routes
+  })
+  instance = new Vue({
+    router,
+    store,
+    render: (h) => h(App)
+  }).$mount(container ? container.querySelector('#app') : '#app')
+}
+
+// 独立运行时
+if (!window.__POWERED_BY_QIANKUN__) {
+  render()
+}
+
+export async function bootstrap () {
+  console.log('[vue] vue app bootstraped')
+}
+export async function mount (props) {
+  console.log('[vue] props from main framework', props)
+  render(props)
+}
+export async function unmount () {
+  instance.$destroy()
+  instance.$el.innerHTML = ''
+  instance = null
+  router = null
+}

+ 3 - 0
admin-files/src/public-path.js

@@ -0,0 +1,3 @@
+if (window.__POWERED_BY_QIANKUN__) {
+__webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__;
+}

+ 9 - 0
admin-files/src/router/index.js

@@ -0,0 +1,9 @@
+const routes = [
+  {
+    path: '/',
+    name: 'Home',
+    component: () => import(/* webpackChunkName: "about" */ '../views/Home.vue')
+  }
+]
+
+export default routes

+ 15 - 0
admin-files/src/store/index.js

@@ -0,0 +1,15 @@
+import Vue from 'vue'
+import Vuex from 'vuex'
+
+Vue.use(Vuex)
+
+export default new Vuex.Store({
+  state: {
+  },
+  mutations: {
+  },
+  actions: {
+  },
+  modules: {
+  }
+})

+ 14 - 0
admin-files/src/views/Home.vue

@@ -0,0 +1,14 @@
+<template>
+  <div class="home">
+    <img alt="Vue logo" src="../assets/logo.png">
+    files
+  </div>
+</template>
+
+<script>
+
+export default {
+  name: 'files',
+  components: {}
+}
+</script>

+ 17 - 0
admin-files/vue.config.js

@@ -0,0 +1,17 @@
+const packageName = require('./package.json').name
+
+module.exports = {
+  devServer: {
+    port: 3002,
+    headers: {
+      'Access-Control-Allow-Origin': '*'
+    }
+  },
+  configureWebpack: {
+    output: {
+      library: `${packageName}-[name]`,
+      libraryTarget: 'umd',
+      jsonpFunction: `webpackJsonp_${packageName}`
+    }
+  }
+}

+ 3 - 0
admin-frame/.browserslistrc

@@ -0,0 +1,3 @@
+> 1%
+last 2 versions
+not dead

+ 5 - 0
admin-frame/.editorconfig

@@ -0,0 +1,5 @@
+[*.{js,jsx,ts,tsx,vue}]
+indent_style = space
+indent_size = 2
+trim_trailing_whitespace = true
+insert_final_newline = true

+ 14 - 0
admin-frame/.env

@@ -0,0 +1,14 @@
+# 设置是否使用tab选项卡
+VUE_APP_TABS=true
+# tabs 卡片类型 (card, border-card)
+VUE_APP_TABS_CARD=card
+# 设置头部使用高的还是矮的 (max, min )
+VUE_APP_HEADER=min
+# 首页标题
+VUE_APP_HOME_TITLE=测试信息管理系统
+# 首页描述
+VUE_APP_HOME_DESCRIDE=基于内容管理、系统管理、预约管理、订单管理等功能的优秀网站管理系统。
+# 窗口使用弹出还是抽屉 (dialog And drawer)
+VUE_APP_WINDOW=dialog
+# 文件上传地址 (app = 各模块自行配置名称)
+VUE_APP_FILE_UPLOAD=/api/files/frame/upload

+ 24 - 0
admin-frame/.eslintrc.js

@@ -0,0 +1,24 @@
+module.exports = {
+  root: true,
+  env: {
+    node: true
+  },
+  extends: [
+    'plugin:vue/essential',
+    '@vue/standard'
+  ],
+  parserOptions: {
+    parser: 'babel-eslint'
+  },
+  rules: {
+    'no-console': 0,
+    'no-debugger': 0,
+    'comma-dangle': [2, 'never'],
+    'no-extra-parens': 2,
+    'no-extra-semi': 2,
+    semi: [2, 'always'],
+    'space-before-function-paren': [0, 'always'],
+    eqeqeq: 0,
+    'no-eval': [0, { allowIndirect: true }]
+  }
+};

+ 23 - 0
admin-frame/.gitignore

@@ -0,0 +1,23 @@
+.DS_Store
+node_modules
+/dist
+
+
+# local env files
+.env.local
+.env.*.local
+
+# Log files
+npm-debug.log*
+yarn-debug.log*
+yarn-error.log*
+pnpm-debug.log*
+
+# Editor directories and files
+.idea
+.vscode
+*.suo
+*.ntvs*
+*.njsproj
+*.sln
+*.sw?

+ 27 - 0
admin-frame/README.md

@@ -0,0 +1,27 @@
+# admin-frame
+
+## Project setup
+```
+npm install
+```
+
+### Compiles and hot-reloads for development
+```
+npm run serve
+```
+
+### Compiles and minifies for production
+```
+npm run build
+```
+
+### Lints and fixes files
+```
+npm run lint
+```
+
+### Customize configuration
+See [Configuration Reference](https://cli.vuejs.org/config/).
+
+### qiankun渲染注意事项
+渲染子应用ID不能嵌套到路由内或者不能在组件内,存在以上情况会找不到ID

+ 5 - 0
admin-frame/babel.config.js

@@ -0,0 +1,5 @@
+module.exports = {
+  presets: [
+    '@vue/cli-plugin-babel/preset'
+  ]
+};

+ 71 - 0
admin-frame/lib/apps.js

@@ -0,0 +1,71 @@
+// .env配置
+const config = {
+  tabs: eval(process.env.VUE_APP_TABS ?? false)
+};
+export default [
+  {
+    // 子应用名称
+    name: 'admin-code',
+    // 子应用入口
+    entry: '//localhost:3001',
+    // 子应用渲染ID
+    container: config.tabs ? '#code' : '#content',
+    // 路由匹配规则
+    activeRule: '/admin/code'
+  },
+  // {
+  //   name: 'admin-files',
+  //   entry: '//localhost:3002',
+  //   container: config.tabs ? '#files' : '#content',
+  //   activeRule: '/admin/files'
+  // },
+  {
+    name: 'admin-user',
+    entry: '//localhost:3003',
+    container: config.tabs ? '#adminUser' : '#content',
+    activeRule: '/admin/adminUser'
+  },
+  {
+    name: 'admin-role',
+    entry: '//localhost:3004',
+    container: config.tabs ? '#role' : '#content',
+    activeRule: '/admin/role'
+  },
+  // 内容管理
+  {
+    name: 'admin-menus',
+    entry: '//localhost:3005',
+    container: config.tabs ? '#menus' : '#content',
+    activeRule: '/admin/menus'
+  },
+  {
+    name: 'admin-column',
+    entry: '//localhost:3006',
+    container: config.tabs ? '#column' : '#content',
+    activeRule: '/admin/column'
+  },
+  {
+    name: 'admin-contents',
+    entry: '//localhost:3007',
+    container: config.tabs ? '#contents' : '#content',
+    activeRule: '/admin/contents'
+  },
+  {
+    name: 'admin-pages',
+    entry: '//localhost:3008',
+    container: config.tabs ? '#pages' : '#content',
+    activeRule: '/admin/pages'
+  },
+  {
+    name: 'admin-imgNews',
+    entry: '//localhost:3009',
+    container: config.tabs ? '#imgNews' : '#content',
+    activeRule: '/admin/imgNews'
+  },
+  {
+    name: 'admin-toConfig',
+    entry: '//localhost:3010',
+    container: config.tabs ? '#toConfig' : '#content',
+    activeRule: '/admin/toConfig'
+  }
+];

+ 49 - 0
admin-frame/lib/axios.js

@@ -0,0 +1,49 @@
+import axios from 'axios';
+import router from '../src/router/index';
+// 添加请求拦截器
+axios.interceptors.request.use(function (config) {
+  const token = sessionStorage.getItem('token');
+  if (token) config.headers.authorization = token;
+  return config;
+}, function (error) {
+  // 对请求错误做些什么
+  return Promise.reject(error);
+});
+
+// 添加响应拦截器
+axios.interceptors.response.use(function (response) {
+  if (response.status == 401) {
+    // 返回登录处理
+    sessionStorage.removeItem('token');
+    router.replace('/frame/login');
+  }
+  if (response.status == 500) {
+    // 错误处理
+    response.data.data = { errcode: -1001, errmsg: '服务器错误' };
+  }
+  return response.data;
+}, function (error) {
+  // 对响应错误做点什么
+  return Promise.reject(error);
+});
+
+// 私有方法
+const request = async ({ url, method, params, data, headers }) => {
+  return await axios.request({ url, method, params, data, headers });
+};
+
+// 定义类
+class Point {
+  get(url, params, headers) {
+    return request({ url, params, headers });
+  }
+
+  post(url, data, params, headers) {
+    return request({ url, method: 'post', data, params, headers });
+  }
+
+  delete(url, params, headers) {
+    return request({ url, method: 'delete', params, headers });
+  }
+}
+export default new Point();

+ 9 - 0
admin-frame/lib/dict.js

@@ -0,0 +1,9 @@
+const dict = {
+  install (vue) {
+    vue.prototype.$dict = function (item) {
+      const dict = this.$store.state.dict;
+      return dict[item];
+    };
+  }
+};
+export default dict;

+ 11 - 0
admin-frame/lib/qiankun.js

@@ -0,0 +1,11 @@
+import { registerMicroApps, start } from 'qiankun';
+import apps from './apps';
+// .env配置
+const config = {
+  tabs: eval(process.env.VUE_APP_TABS ?? false)
+};
+const qiankunInit = () => {
+  registerMicroApps(apps);
+  start({ singular: !config.tabs, sandbox: true });
+};
+export default qiankunInit;

+ 17 - 0
admin-frame/lib/resChange.js

@@ -0,0 +1,17 @@
+const resChange = {
+  install (vue) {
+    vue.prototype.$resChange = function (data, msg) {
+      if (data.errcode !== 0) {
+        this.$message.error(data.errmsg);
+        return;
+      }
+      if (data.errcode == 0 || !data.errcode) {
+        this.$message({
+          message: msg,
+          type: 'success'
+        });
+      }
+    };
+  }
+};
+export default resChange;

+ 26 - 0
admin-frame/lib/tree.js

@@ -0,0 +1,26 @@
+// 树状结构构建插件
+const tree = {
+  install (Vue) {
+    Vue.prototype.$tree = function(options) {
+      // 子级菜单构建函数
+      const children = items => {
+        /*
+        * 根据items.code与所有菜单parentCode比较
+        * 如果相等所有菜单当前项就是子级菜单
+        * 同时调用当前函数创建多级菜单
+        */
+        const childrenList = options.filter(j => items.code == j.parentCode).map(e => children(e));
+        // 如果当前子菜单项存在 就添加children属性
+        if (childrenList.length > 0) {
+          return { ...items, children: childrenList };
+        }
+        // 不存在就不添加
+        return { ...items };
+      };
+      // 过滤一级菜单并添加子级菜单
+      const list = options.filter(e => e.parentCode == null || e.parentCode == '').map(e => children(e));
+      return list;
+    };
+  }
+};
+export default tree;

+ 42 - 0
admin-frame/mock/menu.js

@@ -0,0 +1,42 @@
+export default [
+  {
+    module: 'frame',
+    path: '/frame/home',
+    title: '首页',
+    code: 'frameHome',
+    parentCode: null,
+    icon: 'el-icon-star-on'
+  },
+  {
+    module: 'gaf',
+    path: '',
+    title: '系统管理',
+    code: 'gaf',
+    parentCode: null,
+    icon: 'el-icon-star-on'
+  },
+  {
+    module: 'code',
+    path: '/code/home',
+    title: '字典管理',
+    code: 'code',
+    parentCode: 'gaf',
+    icon: 'el-icon-star-on'
+  },
+  {
+    module: 'adminUser',
+    path: '/adminUser/home',
+    title: '系统用户',
+    code: 'adminUser',
+    parentCode: 'gaf',
+    icon: 'el-icon-star-on'
+  },
+  {
+    module: 'role',
+    path: '/role/home',
+    title: '系统角色',
+    code: 'role',
+    parentCode: 'gaf',
+    icon: 'el-icon-star-on'
+  }
+];

Diferenças do arquivo suprimidas por serem muito extensas
+ 12673 - 0
admin-frame/package-lock.json


+ 39 - 0
admin-frame/package.json

@@ -0,0 +1,39 @@
+{
+  "name": "admin-frame",
+  "version": "0.1.0",
+  "private": true,
+  "scripts": {
+    "serve": "vue-cli-service serve",
+    "build": "vue-cli-service build",
+    "lint": "vue-cli-service lint"
+  },
+  "dependencies": {
+    "axios": "^0.24.0",
+    "core-js": "^3.6.5",
+    "element-ui": "^2.15.6",
+    "qiankun": "^2.6.0",
+    "uuid": "^8.3.2",
+    "vue": "^2.6.11",
+    "vue-router": "^3.2.0",
+    "vuex": "^3.4.0",
+    "wangeditor": "^4.7.11"
+  },
+  "devDependencies": {
+    "@vue/cli-plugin-babel": "~4.5.0",
+    "@vue/cli-plugin-eslint": "~4.5.0",
+    "@vue/cli-plugin-router": "~4.5.0",
+    "@vue/cli-plugin-vuex": "~4.5.0",
+    "@vue/cli-service": "~4.5.0",
+    "@vue/eslint-config-standard": "^5.1.2",
+    "babel-eslint": "^10.1.0",
+    "eslint": "^6.7.2",
+    "eslint-plugin-import": "^2.20.2",
+    "eslint-plugin-node": "^11.1.0",
+    "eslint-plugin-promise": "^4.2.1",
+    "eslint-plugin-standard": "^4.0.0",
+    "eslint-plugin-vue": "^6.2.2",
+    "sass": "^1.45.0",
+    "sass-loader": "^10.0.0",
+    "vue-template-compiler": "^2.6.11"
+  }
+}

BIN
admin-frame/public/favicon.ico


+ 17 - 0
admin-frame/public/index.html

@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html lang="">
+  <head>
+    <meta charset="utf-8">
+    <meta http-equiv="X-UA-Compatible" content="IE=edge">
+    <meta name="viewport" content="width=device-width,initial-scale=1.0">
+    <link rel="icon" href="<%= BASE_URL %>favicon.ico">
+    <title><%= htmlWebpackPlugin.options.title %></title>
+  </head>
+  <body>
+    <noscript>
+      <strong>We're sorry but <%= htmlWebpackPlugin.options.title %> doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
+    </noscript>
+    <div id="app"></div>
+    <!-- built files will be auto injected -->
+  </body>
+</html>

+ 225 - 0
admin-frame/src/App.vue

@@ -0,0 +1,225 @@
+<template>
+  <div id="app">
+    <router-view v-if="$route.path == '/frame/login'"></router-view>
+    <div v-else class="main">
+      <div class="left" :style="{ 'width': is_collapse.leftWidth }">
+        <logo :isCollapse="isCollapse" class="logo" :style="{ 'height': computedHeigth.headerHeigth }"></logo>
+        <menus ref="menus" :menuList="menuList" :isCollapse="isCollapse" class="menu" :style="{ 'height': computedHeigth.menuHeigth }" @menuSelect="menuSelect"></menus>
+      </div>
+      <div class="right" :style="{ 'width': is_collapse.rightWidth }">
+        <headers class="header" :style="{ 'height': computedHeigth.headerHeigth }" @isCollapseChage="isCollapse = $event"></headers>
+        <!-- 非标签页时使用 -->
+        <breadcrumb v-if="!config.tabs" :menuList="menuList" :home="frameTabs"></breadcrumb>
+        <!-- 标签页 -->
+        <el-tabs v-if="config.tabs" class="tabBox" :style="{ 'height': computedHeigth.contentHeigth }" v-model="editableTabsValue" :type="config.tabs_card" @tab-remove="removeTab" @tab-click="clickTab">
+          <el-tab-pane
+            v-for="item in frameTabs"
+            :key="item.code"
+            :label="item.title"
+            :name="item.code"
+          >
+            <router-view></router-view>
+          </el-tab-pane>
+          <el-tab-pane
+            closable
+            v-for="item in editableTabs"
+            :key="item.code"
+            :label="item.title"
+            :name="item.code"
+          >
+            <template v-if="editableTabsValue == item.code">
+              <div :id="item.module" class="content"></div>
+            </template>
+          </el-tab-pane>
+        </el-tabs>
+        <!-- 非标签页时使用 -->
+        <router-view v-if="is_frame && !config.tabs"></router-view>
+        <div v-show="!is_frame" v-if="!config.tabs" id="content" class="content"></div>
+      </div>
+    </div>
+  </div>
+</template>
+
+<script>
+/* 此处进行菜单数据模拟,正式调试后删除 */
+// import menuList from '@mock/menu.js';
+/* 调试结束符号 */
+import style from '@style/index.module.scss';
+import headers from '@components/header';
+import menus from '@components/menu';
+import logo from '@components/header/logo';
+import breadcrumb from '@components/header/breadcrumb';
+import { mapState, mapActions } from 'vuex';
+// .env配置
+const config = {
+  tabs: eval(process.env.VUE_APP_TABS ?? false),
+  headerHeigth: process.env.VUE_APP_HEADER,
+  tabs_card: process.env.VUE_APP_TABS_CARD
+};
+export default {
+  components: {
+    headers,
+    menus,
+    logo,
+    breadcrumb
+  },
+  computed: {
+    ...mapState(['menuList']),
+    // 切换路由或dom对象计算属性 如果当前选项包含frame 使用路由 否则 使用dom
+    is_frame() {
+      return this.editableTabsValue.includes('frame');
+    },
+    // 切换菜单宽度计算属性
+    is_collapse() {
+      return { leftWidth: this.isCollapse ? style.minLeftWidth : style.maxLeftWidth, rightWidth: this.isCollapse ? style.maxRightWidth : style.minRightWidth };
+    },
+    // 切换header高度 与 menu高度
+    computedHeigth() {
+      if (config.headerHeigth == 'max') {
+        return { headerHeigth: style.maxHeaderHeigth, menuHeigth: style.minMenuHeigth, contentHeigth: style.minContentHeigth };
+      }
+      return { headerHeigth: style.minHeaderHeigth, menuHeigth: style.maxMenuHeigth, contentHeigth: style.maxContentHeigth };
+    }
+  },
+  data() {
+    return {
+      // .env配置
+      config,
+      // 折叠收起菜单
+      isCollapse: false,
+      // tabs当前选项
+      editableTabsValue: '',
+      // 默认不可关闭页面数组
+      frameTabs: [
+        { module: 'frame', path: '/frame/home', title: '首页', code: 'frameHome', parentCode: null }
+      ],
+      // 可关闭页面数组
+      editableTabs: []
+    };
+  },
+  async mounted() {
+    if (sessionStorage.userInfo) {
+      const { id } = JSON.parse(sessionStorage.userInfo);
+      await this.queryUserMenu({ userId: id });
+    }
+    if (this.$route.path !== '/frame/login') this.menuInit();
+  },
+  methods: {
+    ...mapActions(['queryUserMenu']),
+    // 初始化菜单点击
+    menuInit() {
+      // 获取当前选中tab 没有默认设置Home页
+      this.editableTabsValue = sessionStorage.getItem('tabs') ?? 'frameHome';
+      // 调用菜单点击函数
+      this.$refs.menus.menuSelect(this.editableTabsValue);
+    },
+    // 菜单选择函数
+    menuSelect(e) {
+      // 赋值当前选项
+      this.editableTabsValue = e.code;
+      // 不是子应用向选项组添加当前选项
+      if (!this.is_frame && !this.editableTabs.includes(e)) {
+        this.editableTabs.push(e);
+      }
+      this.clickTab(e);
+    },
+    // tab点击函数
+    clickTab (e) {
+      // 解决点击tab标签是导航不跟随切换问题
+      if (this.$refs.menus.defaultActiveItem !== this.editableTabsValue) {
+        this.$refs.menus.menuSelect(this.editableTabsValue);
+      }
+      // 解决tab标签实例不存在code属性
+      if (!e.code) e.code = e.name;
+      // 存储 sessionStorage
+      sessionStorage.setItem('tabs', e.code);
+      let item;
+      // 判断是不是子应用
+      if (!this.is_frame) {
+        item = this.editableTabs.find(i => i.code == e.code);
+      } else {
+        item = this.frameTabs.find(i => i.code == e.code);
+      }
+      // 如果是当前路由,直接返回
+      if (item.path == this.$route.path) return;
+      // 路由跳转
+      this.$router.push(item.path);
+    },
+    // 移除tab标签函数
+    removeTab (index) {
+      // 删除当前选项
+      this.editableTabs = this.editableTabs.filter(e => e.code !== index);
+      // 删除后选择打开的最后一项 或 首页
+      this.editableTabsValue = this.editableTabs[this.editableTabs.length - 1]?.code ?? 'frameHome';
+      this.$refs.menus.menuSelect(this.editableTabsValue);
+    }
+  },
+  watch: {
+    $route(to) {
+      if (this.$route.path == '/') this.$router.go(0);
+    }
+  }
+};
+</script>
+
+<style lang="scss">
+@import '@style/index.scss';
+body {
+  margin: 0;
+  padding: 0;
+}
+#app {
+  width: 100vw;
+  height: 100vh;
+  .main {
+    display: flex;
+    overflow: hidden;
+    width: 100%;
+    height: 100%;
+    .left {
+      height: 100vh;
+      .logo {
+        width: 100%;
+        background: $menuBackgroundColor;
+      }
+      .menu {
+        width: 100%;
+      }
+    }
+    .right {
+      height: 100%;
+      .header {
+        height: 10vh;
+      }
+      .tabBox {
+        width: 100%;
+        .el-tabs__header {
+          margin: 0;
+        }
+        .el-tabs__content {
+          width: 100%;
+          height: 97%;
+          .el-tab-pane {
+            width: 100%;
+            height: 100%;
+          }
+        }
+        .content {
+          height: 100%;
+          width: 100%;
+          > div {
+            height: 98%;
+          }
+        }
+      }
+      #content {
+        height: 100%;
+        width: 100%;
+        > div {
+          height: 98%;
+        }
+      }
+    }
+  }
+}
+</style>

BIN
admin-frame/src/assets/bg2.jpg


BIN
admin-frame/src/assets/code.png


+ 0 - 0
admin-frame/src/assets/home.png


Alguns arquivos não foram mostrados porque muitos arquivos mudaram nesse diff