Compare commits

...

2 Commits

Author SHA1 Message Date
HINOTOR ff2699b6b7 src
2 years ago
HINOTOR 453f34870a src
2 years ago

@ -1,2 +0,0 @@
> 1%
last 2 versions

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

@ -1,19 +0,0 @@
module.exports = {
root: true,
env: {
node: true
},
'extends': [
'plugin:vue/essential',
'@vue/standard'
],
rules: {
'no-console': process.env.NODE_ENV === 'production' ? 'error' : 'off',
'no-debugger': process.env.NODE_ENV === 'production' ? 'error' : 'off',
"space-before-function-paren": 0,
"indent": [2, 4]
},
parserOptions: {
parser: 'babel-eslint'
}
}

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

@ -1,5 +0,0 @@
{
"tabWidth": 4,
"singleQuote":true,
"semi":false
}

@ -1,3 +0,0 @@
module.exports = {
presets: ['@vue/app']
}

@ -1,22 +0,0 @@
module.exports = {
moduleFileExtensions: ['js', 'jsx', 'json', 'vue'],
transform: {
'^.+\\.vue$': 'vue-jest',
'.+\\.(css|styl|less|sass|scss|svg|png|jpg|ttf|woff|woff2)$':
'jest-transform-stub',
'^.+\\.jsx?$': 'babel-jest'
},
transformIgnorePatterns: ['/node_modules/'],
moduleNameMapper: {
'^@/(.*)$': '<rootDir>/src/$1'
},
snapshotSerializers: ['jest-serializer-vue'],
testMatch: [
'**/tests/unit/**/*.spec.(js|jsx|ts|tsx)|**/__tests__/*.(js|jsx|ts|tsx)'
],
testURL: 'http://localhost/',
watchPlugins: [
'jest-watch-typeahead/filename',
'jest-watch-typeahead/testname'
]
}

File diff suppressed because it is too large Load Diff

@ -1,49 +0,0 @@
{
"name": "vue-admin-permission",
"version": "0.1.0",
"private": true,
"author": "Hui <543245444@qq.com>",
"scripts": {
"serve": "vue-cli-service serve",
"serve:randy": "cross-env API_TYPE=randy vue-cli-service serve",
"serve:peter": "cross-env API_TYPE=peter vue-cli-service serve",
"build": "vue-cli-service build",
"analyze": "vue-cli-service build",
"lint": "vue-cli-service lint",
"test:unit": "vue-cli-service test:unit",
"dll": "webpack -p --progress --config ./webpack.dll.conf.js"
},
"dependencies": {
"axios": "^0.19.0",
"core-js": "^2.6.5",
"element-ui": "^2.9.2",
"moment": "^2.24.0",
"vue": "^2.6.10",
"vue-router": "^3.0.3",
"vuex": "^3.0.1"
},
"devDependencies": {
"@vue/cli-plugin-babel": "^3.8.0",
"@vue/cli-plugin-eslint": "^3.8.0",
"@vue/cli-plugin-unit-jest": "^3.8.0",
"@vue/cli-service": "^3.8.0",
"@vue/eslint-config-standard": "^4.0.0",
"@vue/test-utils": "1.0.0-beta.29",
"add-asset-html-webpack-plugin": "^3.1.3",
"babel-core": "7.0.0-bridge.0",
"babel-eslint": "^10.0.1",
"babel-jest": "^23.6.0",
"clean-webpack-plugin": "^1.0.1",
"compression-webpack-plugin": "^3.0.0",
"cross-env": "^5.2.0",
"eslint": "^5.16.0",
"eslint-plugin-vue": "^5.0.0",
"qiniu-webpack-plugin": "^0.4.2",
"sass": "^1.18.0",
"sass-loader": "^7.1.0",
"svg-sprite-loader": "^3.9.2",
"vue-template-compiler": "^2.6.10",
"webpack-bundle-analyzer": "^2.13.1",
"webpack-cli": "^3.2.3"
}
}

@ -1,5 +0,0 @@
module.exports = {
plugins: {
autoprefixer: {}
}
}

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.2 KiB

@ -1,24 +0,0 @@
<!DOCTYPE html>
<html lang="en">
<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>loveRandy</title>
</head>
<body>
<noscript>
<strong>We're sorry but vue-admin doesn't work properly without JavaScript enabled. Please enable it to continue.</strong>
</noscript>
<div id="app"></div>
<!-- built files will be auto injected -->
<div class="ajax-loading" id="ajaxLoading" style="display: none;">
<div class="overlay"></div>
<div class="loading">
<img src="https://media.number-7.cn/ebike-h5/static/images/common/loading.gif" alt="">
<span>加载中,请稍后...</span>
</div>
</div>
</body>
</html>

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

@ -1,20 +0,0 @@
<template>
<div id="app">
<router-view />
</div>
</template>
<script>
export default {
name: 'App'
}
</script>
<style lang="scss">
#app {
height: 100%;
> div {
height: 100%;
}
}
</style>

@ -1,29 +0,0 @@
import axios from '@/config/httpConfig'
export function fetchPermission() {
return axios.get('/user/info')
}
// 获取用户列表
export function getUserList() {
return axios.get('/user/list')
}
// 获取角色列表
export function getRoleList() {
return axios.get('/role/list')
}
// 获取所有权限
export function getAllPermissiion() {
return axios.get('/permission/all')
}
// 获取一级权限列表
export function getFirstLevel() {
return axios.get('/permission/resource')
}
// 获取次级权限列表
export function getNextLevel(id) {
return axios.get(`/permission/level?id=${id}`)
}
export function login(data) {
return axios.post('/user/login', data)
}

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

@ -1,45 +0,0 @@
<template>
<svg
:class="svgClass"
aria-hidden="true"
>
<use :xlink:href="iconName"></use>
</svg>
</template>
<script>
export default {
name: 'svg-icon',
props: {
iconClass: {
type: String,
required: true
},
className: {
type: String
}
},
computed: {
iconName() {
return `#icon-${this.iconClass}`
},
svgClass() {
if (this.className) {
return 'svg-icon ' + this.className
} else {
return 'svg-icon'
}
}
}
}
</script>
<style scoped>
.svg-icon {
width: 1em;
height: 1em;
vertical-align: -0.15em;
fill: currentColor;
overflow: hidden;
}
</style>

@ -1,63 +0,0 @@
<template>
<div class='menu-container'>
<template v-for='v in menuList'>
<el-submenu
:index='v.name'
v-if='v.children&&v.children.length>0'
:key='v.name'
>
<template slot='title'>
<!-- <i
class='iconfont'
:class='v.meta.icon'
></i> -->
<svg-icon v-if="v.meta&&v.meta.icon" :icon-class="v.meta.icon"></svg-icon>
<span>{{v.meta.name}}</span>
</template>
<el-menu-item-group>
<my-nav :menuList='v.children'></my-nav>
</el-menu-item-group>
</el-submenu>
<el-menu-item
:key='v.name'
:index='v.name'
@click='gotoRoute(v.name)'
v-else
>
<!-- <i
class='iconfont'
:class='v.meta.icon'
></i> -->
<svg-icon v-if="v.meta&&v.meta.icon" :icon-class="v.meta.icon"></svg-icon>
<span slot='title'>{{v.meta.name}}</span>
</el-menu-item>
</template>
</div>
</template>
<script>
export default {
name: 'my-nav',
props: {
menuList: {
type: Array,
default: () => {
return []
}
}
},
methods: {
gotoRoute(name) {
this.$router.push({ name })
}
}
}
</script>
<style lang='scss'>
.menu-container {
.svg-icon{
margin-right:10px;
}
}
</style>

@ -1,2 +0,0 @@
const baseUrl = process.env.NODE_ENV === 'production' ? '/' : '/api'
export default baseUrl

@ -1,133 +0,0 @@
import axios from 'axios'
import store from '@/store/index.js'
import baseURL from './baseUrl'
import { Message } from 'element-ui'
const http = {}
var instance = axios.create({
timeout: 5000,
baseURL,
validateStatus(status) {
switch (status) {
case 400:
Message.error('请求出错')
break
case 401:
Message.warning({
message: '授权失败,请重新登录'
})
store.commit('LOGIN_OUT')
setTimeout(() => {
window.location.reload()
}, 1000)
return
case 403:
Message.warning({
message: '拒绝访问'
})
break
case 404:
Message.warning({
message: '请求错误,未找到该资源'
})
break
case 500:
Message.warning({
message: '服务端错误'
})
break
}
return status >= 200 && status < 300
}
})
// 添加请求拦截器
instance.interceptors.request.use(
function(config) {
// 请求头添加token
if (store.state.UserToken) {
config.headers.Authorization = `Bearer ${store.state.UserToken}`
}
return config
},
function(error) {
return Promise.reject(error)
}
)
// 响应拦截器即异常处理
instance.interceptors.response.use(
response => {
return response.data
},
err => {
if (err && err.response) {
} else {
err.message = '连接服务器失败'
}
// Message.error({
// message: err.message
// })
return Promise.reject(err.response)
}
)
http.get = function(url, options) {
let loading
if (!options || options.isShowLoading !== false) {
loading = document.getElementById('ajaxLoading')
loading.style.display = 'block'
}
return new Promise((resolve, reject) => {
instance
.get(url, options)
.then(response => {
if (!options || options.isShowLoading !== false) {
loading = document.getElementById('ajaxLoading')
loading.style.display = 'none'
}
if (response.code === 1) {
resolve(response.data)
} else {
Message.error({
message: response.msg
})
reject(response.msg)
}
})
.catch(e => {
console.log(e)
})
})
}
http.post = function(url, data, options) {
let loading
if (!options || options.isShowLoading !== false) {
loading = document.getElementById('ajaxLoading')
loading.style.display = 'block'
}
return new Promise((resolve, reject) => {
instance
.post(url, data, options)
.then(response => {
if (!options || options.isShowLoading !== false) {
loading = document.getElementById('ajaxLoading')
loading.style.display = 'none'
}
if (response.code === 1) {
resolve(response.data)
} else {
Message.error({
message: response.msg
})
reject(response.message)
}
})
.catch(e => {
console.log(e)
})
})
}
export default http

@ -1,19 +0,0 @@
function formatNumber(n) {
const str = n.toString()
return str[1] ? str : `0${str}`
}
export function formatTime(date) {
const year = date.getFullYear()
const month = date.getMonth() + 1
const day = date.getDate()
const hour = date.getHours()
const minute = date.getMinutes()
const second = date.getSeconds()
const t1 = [year, month, day].map(formatNumber).join('/')
const t2 = [hour, minute, second].map(formatNumber).join(':')
return `${t1} ${t2}`
}

@ -1,10 +0,0 @@
import Vue from 'vue'
import SvgIcon from '@/components/SvgIcon'// svg组件
// register globally
Vue.component('svg-icon', SvgIcon)
const requireAll = requireContext => requireContext.keys().map(requireContext)
const req = require.context('./svg', false, /\.svg$/)
// console.log(req)
requireAll(req)

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1511504199105" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1815" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M770.56 460.8h250.88C998.4 220.16 803.84 25.6 563.2 2.56v250.88c104.96 20.48 186.88 102.4 207.36 207.36z m0 0M460.8 253.44V2.56C220.16 25.6 25.6 220.16 2.56 460.8h250.88c20.48-104.96 102.4-186.88 207.36-207.36z m0 0M563.2 770.56v250.88c243.2-23.04 435.2-217.6 460.8-460.8H773.12C750.08 668.16 668.16 750.08 563.2 770.56z m0 0M253.44 563.2H2.56c23.04 243.2 217.6 435.2 460.8 460.8V773.12C355.84 750.08 273.92 668.16 253.44 563.2z m0 0" fill="" p-id="1816"></path></svg>

Before

Width:  |  Height:  |  Size: 852 B

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1503993826520" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="7878" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M941.677063 391.710356c9.337669-14.005992 6.224772-32.68133-6.224772-43.575447-14.005992-10.894118-32.68133-7.78122-43.575447 6.224771-1.556449 1.556449-174.300768 205.426673-379.727441 205.426673-199.200878 0-379.727441-205.426673-381.28389-206.982098-10.894118-12.450567-31.124881-14.005992-43.575448-3.112898-12.450567 10.894118-14.005992 31.124881-3.112897 43.575448 3.112897 4.668323 40.46255 46.687322 99.600439 93.375667l-79.369676 82.48155c-12.450567 12.450567-10.894118 32.68133 1.556449 43.575448 3.112897 6.224772 10.894118 9.337669 18.675338 9.337669 7.78122 0 15.562441-3.112897 21.787213-9.337669l85.594447-88.706321c40.46255 28.013007 88.706321 54.469566 141.619438 73.14388L340.959485 707.631586c-4.668323 17.118889 4.669346 34.237779 21.787213 38.906101h9.337669c14.005992 0 26.456558-9.337669 29.568432-23.343661l32.68133-110.494556c24.90011 4.668323 51.356668 7.78122 77.813227 7.78122s52.913117-3.112897 77.813227-7.78122l32.68133 108.938108c3.112897 14.005992 17.118889 23.343661 29.569456 23.343661 3.112897 0 6.224772 0 7.78122-1.556449 17.118889-4.669346 26.456558-21.787212 21.788236-38.906102l-32.68133-108.938108c52.913117-18.675338 101.156888-45.131897 141.619438-73.14388l84.037998 87.150896c6.224772 6.224772 14.005992 9.337669 21.787212 9.337669 7.78122 0 15.562441-3.112897 21.787212-9.337669 12.450567-12.450567 12.450567-31.124881 1.556449-43.575448l-79.369675-82.48155c63.808258-46.688345 101.158934-91.820242 101.158934-91.820242z" p-id="7879"></path></svg>

Before

Width:  |  Height:  |  Size: 1.8 KiB

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1511504319223" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="3230" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M942.827259 80.3367c-11.42419-11.406794-26.41051-17.117866-41.377386-17.117866-14.985296 0-29.952172 5.711072-41.358967 17.117866L719.392444 221.014696l-19.441794 19.441794L681.577187 258.832 569.516971 370.909611 375.99749 564.411697l0 0.019443 0 84.372619 81.145112 0 0.010233 0 95.418186-95.435583 213.398228-213.400275 3.14155-3.14155-0.019443 0 9.979282-9.977235 0 0L942.827259 163.073052C965.697129 140.259464 965.697129 103.186104 942.827259 80.3367z" p-id="3231"></path><path d="M793.542234 367.521444 580.14196 580.939115 484.72582 676.376745 473.299583 687.800935 457.152834 687.800935 375.99749 687.800935 337.000314 687.800935 337.000314 648.803759 337.000314 564.411697 337.000314 548.264948 348.424504 536.838711 541.943986 343.338672 654.004201 231.259014 665.428392 219.834824 64.020082 219.834824 64.020082 960.781166 804.966425 960.781166 804.966425 356.116697 796.607036 364.475062Z" p-id="3232"></path></svg>

Before

Width:  |  Height:  |  Size: 1.3 KiB

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1529559567446" class="icon" style="" viewBox="0 0 1167 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1767" xmlns:xlink="http://www.w3.org/1999/xlink" width="227.9296875" height="200"><defs><style type="text/css"></style></defs><path d="M0.015952 74.459413A2.286 2.286 1440 1 0 145.85218 74.459413 2.286 2.286 1440 1 0 0.015952 74.459413zM291.720312 1.525347 1166.801488 1.525347 1166.801488 147.361574 291.720312 147.361574zM291.720312 366.163773A2.286 2.286 1440 1 0 437.55654 366.163773 2.286 2.286 1440 1 0 291.720312 366.163773zM583.424672 293.229707 1166.801488 293.229707 1166.801488 439.065934 583.424672 439.065934zM291.720312 949.540588A2.286 2.286 1440 1 0 437.55654 949.540588 2.286 2.286 1440 1 0 291.720312 949.540588zM583.424672 876.638427 1166.801488 876.638427 1166.801488 1022.474654 583.424672 1022.474654zM583.424672 657.836228A2.286 2.286 1440 1 0 729.2609 657.836228 2.286 2.286 1440 1 0 583.424672 657.836228zM875.129032 584.934067 1166.801488 584.934067 1166.801488 730.770294 875.129032 730.770294z" p-id="1768"></path></svg>

Before

Width:  |  Height:  |  Size: 1.2 KiB

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1503994678729" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="9229" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M780.8 354.579692 665.6 354.579692 665.6 311.689846c0-72.310154-19.849846-193.299692-153.6-193.299692-138.870154 0-153.6 135.049846-153.6 193.299692l0 42.889846L243.2 354.579692 243.2 311.689846C243.2 122.249846 348.790154 0 512 0s268.8 122.249846 268.8 311.689846L780.8 354.579692zM588.8 669.420308C588.8 625.900308 554.220308 590.769231 512 590.769231s-76.8 35.131077-76.8 78.651077c0 29.459692 15.399385 54.468923 38.439385 67.820308l0 89.639385c0 21.740308 17.250462 39.699692 38.4 39.699692s38.4-17.959385 38.4-39.699692l0-89.639385C573.44 723.889231 588.8 698.88 588.8 669.420308zM896 512l0 393.609846c0 65.260308-51.869538 118.390154-115.2 118.390154L243.2 1024c-63.291077 0-115.2-53.129846-115.2-118.390154L128 512c0-65.220923 51.869538-118.390154 115.2-118.390154l537.6 0C844.130462 393.609846 896 446.779077 896 512z" p-id="9230"></path></svg>

Before

Width:  |  Height:  |  Size: 1.2 KiB

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1511504440567" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="5070" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M568.6 0h454.9v454.9H568.6V0z m0 568.6h454.9v454.9H568.6V568.6zM0 568.6h454.9v454.9H0V568.6zM0 0h454.9v454.9H0V0z" fill="" p-id="5071"></path></svg>

Before

Width:  |  Height:  |  Size: 532 B

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1511512690058" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="3507" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M1013.703 693.345c6.865 6.865 10.297 14.874 10.297 24.027l0 205.944c0 9.916-3.432 18.115-10.297 24.599-6.865 6.483-15.255 9.725-25.171 9.725L782.588 957.64c-9.153 0-17.162-3.242-24.027-9.725-6.865-6.483-10.297-14.683-10.297-24.599L748.264 717.372c0-6.102 1.526-11.823 4.577-17.162s7.246-9.534 12.586-12.586 11.06-4.577 17.162-4.577l77.801 0L860.39 546.896c0-4.577-1.144-8.772-3.432-12.586s-5.339-6.865-9.153-9.153-8.009-3.432-12.585-3.432L543.464 521.725l0 161.323 77.801 0c9.153 0 17.162 3.432 24.027 10.297s10.297 14.874 10.297 24.027l0 205.944c0 6.102-1.526 11.823-4.577 17.162s-7.246 9.534-12.585 12.585-11.06 4.577-17.162 4.577L415.321 957.64c-6.102 0-11.823-1.526-17.162-4.577s-9.725-7.246-13.158-12.585-5.149-11.06-5.149-17.162L379.852 717.372c0-9.153 3.432-17.162 10.297-24.027s15.255-10.297 25.171-10.297l76.657 0L491.977 521.725 188.782 521.725c-7.628 0-13.92 2.479-18.878 7.437-4.958 4.958-7.437 10.869-7.437 17.734l0 136.152 77.801 0c9.916 0 18.115 3.432 24.599 10.297s9.725 14.874 9.725 24.027l0 205.944c0 9.916-3.242 18.115-9.725 24.599-6.483 6.483-14.683 9.725-24.599 9.725L34.324 957.64c-3.814 0-7.437-0.572-10.869-1.716-3.432-1.144-6.483-2.67-9.153-4.577-2.67-1.907-5.149-4.386-7.437-7.437-2.288-3.051-4.004-6.293-5.149-9.725C0.572 930.753 0 927.13 0 923.316L0 717.372c0-3.051 0.381-6.102 1.144-9.153s1.907-5.721 3.432-8.009 3.432-4.577 5.721-6.865 4.577-4.195 6.865-5.721 4.958-2.67 8.009-3.432 6.102-1.144 9.153-1.144l77.801 0L112.125 495.41c0-6.865 2.479-12.776 7.437-17.734s10.869-7.437 17.734-7.437l354.682 0L491.978 342.096l-76.657 0c-9.916 0-18.306-3.432-25.171-10.297s-10.297-14.874-10.297-24.027L379.853 101.828c0-9.916 3.432-18.306 10.297-25.171s15.255-10.297 25.171-10.297l205.944 0c6.102 0 11.823 1.716 17.162 5.149 5.339 3.432 9.534 7.818 12.585 13.158 3.051 5.339 4.577 11.06 4.577 17.162l0 205.944c0 9.153-3.432 17.162-10.297 24.027s-14.874 10.297-24.027 10.297l-77.801 0 0 128.143L885.56 470.24c7.628 0 13.92 2.479 18.878 7.437s7.437 10.869 7.437 17.734l0 187.638 76.657 0C998.448 683.048 1006.838 686.48 1013.703 693.345z" p-id="3508"></path></svg>

Before

Width:  |  Height:  |  Size: 2.4 KiB

@ -1 +0,0 @@
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1503993891882" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="7986" xmlns:xlink="http://www.w3.org/1999/xlink" width="64" height="64"><defs><style type="text/css"></style></defs><path d="M504.951 511.98c93.49 0 169.28-74.002 169.28-165.26 0-91.276-75.79-165.248-169.28-165.248-93.486 0-169.287 73.972-169.279 165.248-0.001 91.258 75.793 165.26 169.28 165.26z m77.6 55.098H441.466c-120.767 0-218.678 95.564-218.678 213.45V794.3c0 48.183 97.911 48.229 218.678 48.229H582.55c120.754 0 218.66-1.78 218.66-48.229v-13.77c0-117.887-97.898-213.45-218.66-213.45z" p-id="7987"></path></svg>

Before

Width:  |  Height:  |  Size: 777 B

@ -1,58 +0,0 @@
import Vue from 'vue'
import App from '@/App'
import store from '@/store/index'
import router from '@/router/index'
import ElementUI from 'element-ui'
import 'element-ui/lib/theme-chalk/index.css'
import './styles/index.scss'
import axios from './config/httpConfig'
import * as globalFilter from './filters/filters'
import '@/icons'
Vue.prototype.$http = axios
for (var key in globalFilter) {
Vue.filter(key, globalFilter[key])
}
Vue.use(ElementUI)
Vue.config.productionTip = false
router.beforeEach((to, from, next) => {
if (!store.state.UserToken) {
if (to.matched.length > 0 && !to.matched.some(record => record.meta.requiresAuth)) {
next()
} else {
next({ path: '/login' })
}
} else {
if (!store.state.permission.permissionList) {
store.dispatch('permission/FETCH_PERMISSION').then(() => {
next({ path: to.path })
})
} else {
if (to.path !== '/login') {
next()
} else {
next(from.fullPath)
}
}
}
})
router.afterEach((to, from, next) => {
var routerList = to.matched
store.commit('setCrumbList', routerList)
store.commit('permission/SET_CURRENT_MENU', to.name)
})
/* eslint-disable no-new */
new Vue({
el: '#app',
router,
store,
render: h => h(App)
})

@ -1,220 +0,0 @@
<template>
<div style="background:#f0f2f5;margin-top: -20px;height:100%;">
<div class="wscn-http404">
<div class="pic-404"></div>
<div class="bullshit">
<div class="bullshit__headline">{{ message }}</div>
<div class="bullshit__info">对不起你没有权限</div>
<a @click="backToHome" class="bullshit__return-home">返回首页</a>
</div>
</div>
</div>
</template>
<script>
export default {
name: 'page401',
data() {
return {}
},
methods: {
backToHome() {
this.$router.push('/')
}
},
computed: {
message() {
return '对不起,你没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限没有权限'
}
}
}
</script>
<style rel="stylesheet/scss" lang="scss" scoped>
.wscn-http404 {
position: relative;
width: 1200px;
margin: 20px auto 60px;
padding: 0 100px;
overflow: hidden;
.pic-404 {
position: relative;
float: left;
width: 600px;
padding: 150px 0;
overflow: hidden;
&__parent {
width: 100%;
}
&__child {
position: absolute;
&.left {
width: 80px;
top: 17px;
left: 220px;
opacity: 0;
animation-name: cloudLeft;
animation-duration: 2s;
animation-timing-function: linear;
animation-fill-mode: forwards;
animation-delay: 1s;
}
&.mid {
width: 46px;
top: 10px;
left: 420px;
opacity: 0;
animation-name: cloudMid;
animation-duration: 2s;
animation-timing-function: linear;
animation-fill-mode: forwards;
animation-delay: 1.2s;
}
&.right {
width: 62px;
top: 100px;
left: 500px;
opacity: 0;
animation-name: cloudRight;
animation-duration: 2s;
animation-timing-function: linear;
animation-fill-mode: forwards;
animation-delay: 1s;
}
@keyframes cloudLeft {
0% {
top: 17px;
left: 220px;
opacity: 0;
}
20% {
top: 33px;
left: 188px;
opacity: 1;
}
80% {
top: 81px;
left: 92px;
opacity: 1;
}
100% {
top: 97px;
left: 60px;
opacity: 0;
}
}
@keyframes cloudMid {
0% {
top: 10px;
left: 420px;
opacity: 0;
}
20% {
top: 40px;
left: 360px;
opacity: 1;
}
70% {
top: 130px;
left: 180px;
opacity: 1;
}
100% {
top: 160px;
left: 120px;
opacity: 0;
}
}
@keyframes cloudRight {
0% {
top: 100px;
left: 500px;
opacity: 0;
}
20% {
top: 120px;
left: 460px;
opacity: 1;
}
80% {
top: 180px;
left: 340px;
opacity: 1;
}
100% {
top: 200px;
left: 300px;
opacity: 0;
}
}
}
}
.bullshit {
position: relative;
float: left;
width: 300px;
padding: 150px 0;
overflow: hidden;
&__oops {
font-size: 32px;
font-weight: bold;
line-height: 40px;
color: #1482f0;
opacity: 0;
margin-bottom: 20px;
animation-name: slideUp;
animation-duration: 0.5s;
animation-fill-mode: forwards;
}
&__headline {
font-size: 20px;
line-height: 24px;
color: #1482f0;
opacity: 0;
margin-bottom: 10px;
animation-name: slideUp;
animation-duration: 0.5s;
animation-delay: 0.1s;
animation-fill-mode: forwards;
}
&__info {
font-size: 13px;
line-height: 21px;
color: grey;
opacity: 0;
margin-bottom: 30px;
animation-name: slideUp;
animation-duration: 0.5s;
animation-delay: 0.2s;
animation-fill-mode: forwards;
}
&__return-home {
display: block;
float: left;
width: 110px;
height: 36px;
background: #1482f0;
border-radius: 100px;
text-align: center;
color: #ffffff;
opacity: 0;
font-size: 14px;
line-height: 36px;
cursor: pointer;
animation-name: slideUp;
animation-duration: 0.5s;
animation-delay: 0.3s;
animation-fill-mode: forwards;
}
@keyframes slideUp {
0% {
transform: translateY(60px);
opacity: 0;
}
100% {
transform: translateY(0);
opacity: 1;
}
}
}
}
</style>

@ -1,220 +0,0 @@
<template>
<div style="background:#f0f2f5;margin-top: -20px;height:100%;">
<div class="wscn-http404">
<div class="pic-404"></div>
<div class="bullshit">
<div class="bullshit__headline">{{ message }}</div>
<div class="bullshit__info">请检查您输入的网址是否正确</div>
<a @click="backToHome" class="bullshit__return-home">返回首页</a>
</div>
</div>
</div>
</template>
<script>
export default {
name: 'page404',
data() {
return {}
},
methods: {
backToHome() {
this.$router.push('/')
}
},
computed: {
message() {
return '找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面找不到页面'
}
}
}
</script>
<style rel="stylesheet/scss" lang="scss" scoped>
.wscn-http404 {
position: relative;
width: 1200px;
margin: 20px auto 60px;
padding: 0 100px;
overflow: hidden;
.pic-404 {
position: relative;
float: left;
width: 600px;
padding: 150px 0;
overflow: hidden;
&__parent {
width: 100%;
}
&__child {
position: absolute;
&.left {
width: 80px;
top: 17px;
left: 220px;
opacity: 0;
animation-name: cloudLeft;
animation-duration: 2s;
animation-timing-function: linear;
animation-fill-mode: forwards;
animation-delay: 1s;
}
&.mid {
width: 46px;
top: 10px;
left: 420px;
opacity: 0;
animation-name: cloudMid;
animation-duration: 2s;
animation-timing-function: linear;
animation-fill-mode: forwards;
animation-delay: 1.2s;
}
&.right {
width: 62px;
top: 100px;
left: 500px;
opacity: 0;
animation-name: cloudRight;
animation-duration: 2s;
animation-timing-function: linear;
animation-fill-mode: forwards;
animation-delay: 1s;
}
@keyframes cloudLeft {
0% {
top: 17px;
left: 220px;
opacity: 0;
}
20% {
top: 33px;
left: 188px;
opacity: 1;
}
80% {
top: 81px;
left: 92px;
opacity: 1;
}
100% {
top: 97px;
left: 60px;
opacity: 0;
}
}
@keyframes cloudMid {
0% {
top: 10px;
left: 420px;
opacity: 0;
}
20% {
top: 40px;
left: 360px;
opacity: 1;
}
70% {
top: 130px;
left: 180px;
opacity: 1;
}
100% {
top: 160px;
left: 120px;
opacity: 0;
}
}
@keyframes cloudRight {
0% {
top: 100px;
left: 500px;
opacity: 0;
}
20% {
top: 120px;
left: 460px;
opacity: 1;
}
80% {
top: 180px;
left: 340px;
opacity: 1;
}
100% {
top: 200px;
left: 300px;
opacity: 0;
}
}
}
}
.bullshit {
position: relative;
float: left;
width: 300px;
padding: 150px 0;
overflow: hidden;
&__oops {
font-size: 32px;
font-weight: bold;
line-height: 40px;
color: #1482f0;
opacity: 0;
margin-bottom: 20px;
animation-name: slideUp;
animation-duration: 0.5s;
animation-fill-mode: forwards;
}
&__headline {
font-size: 20px;
line-height: 24px;
color: #1482f0;
opacity: 0;
margin-bottom: 10px;
animation-name: slideUp;
animation-duration: 0.5s;
animation-delay: 0.1s;
animation-fill-mode: forwards;
}
&__info {
font-size: 13px;
line-height: 21px;
color: grey;
opacity: 0;
margin-bottom: 30px;
animation-name: slideUp;
animation-duration: 0.5s;
animation-delay: 0.2s;
animation-fill-mode: forwards;
}
&__return-home {
display: block;
float: left;
width: 110px;
height: 36px;
background: #1482f0;
border-radius: 100px;
text-align: center;
color: #ffffff;
opacity: 0;
font-size: 14px;
line-height: 36px;
cursor: pointer;
animation-name: slideUp;
animation-duration: 0.5s;
animation-delay: 0.3s;
animation-fill-mode: forwards;
}
@keyframes slideUp {
0% {
transform: translateY(60px);
opacity: 0;
}
100% {
transform: translateY(0);
opacity: 1;
}
}
}
}
</style>

@ -1,35 +0,0 @@
<template>
<div>
<el-progress
type="circle"
:percentage="0"
></el-progress>
<el-progress
type="circle"
:percentage="25"
></el-progress>
<el-progress
type="circle"
:percentage="100"
status="success"
></el-progress>
<el-progress
type="circle"
:percentage="70"
status="warning"
></el-progress>
<el-progress
type="circle"
:percentage="50"
status="exception"
></el-progress>
</div>
</template>
<script>
export default {
data() {
return {}
}
}
</script>

@ -1,22 +0,0 @@
<template>
<div class="demo-image__placeholder">
<div class="block">
<el-image :src="src">
<div slot="placeholder" class="image-slot">
加载中<span class="dot">...</span>
</div>
</el-image>
</div>
</div>
</template>
<script>
export default {
data() {
return {
src:
'https://cube.elemecdn.com/6/94/4d3ea53c084bad6931a56d5158a48jpeg.jpeg'
}
}
}
</script>

@ -1,16 +0,0 @@
<template>
<div>
<router-view></router-view>
</div>
</template>
<script>
export default {
data() {
return {}
},
mounted() {
}
}
</script>

@ -1,13 +0,0 @@
<template>
<div>
<p>home</p>
</div>
</template>
<script>
export default {
data() {
return {}
}
}
</script>

@ -1,13 +0,0 @@
<template>
<div>
one
</div>
</template>
<script>
export default {
data() {
return {}
}
}
</script>

@ -1,22 +0,0 @@
<template>
<div class="demo-image__placeholder">
<div class="block">
<el-image :src="src">
<div slot="placeholder" class="image-slot">
加载中<span class="dot">...</span>
</div>
</el-image>
</div>
</div>
</template>
<script>
export default {
data() {
return {
src:
'https://cube.elemecdn.com/6/94/4d3ea53c084bad6931a56d5158a48jpeg.jpeg'
}
}
}
</script>

@ -1,22 +0,0 @@
<template>
<div>
<router-view></router-view>
<TotalStatus/>
</div>
</template>
<script>
import TotalStatus from './component/total-status'
export default {
data() {
return {}
},
mounted() {
},
components: {
TotalStatus
}
}
</script>

@ -1,15 +0,0 @@
<template>
<router-view class="content"></router-view>
</template>
<script>
export default {
data() {
return {}
}
}
</script>
<style lang="scss" scoped>
</style>

@ -1,25 +0,0 @@
<template>
<div class="main-container">
<TopAside/>
<Content/>
</div>
</template>
<script>
import TopAside from './top-aside'
import Content from './content'
import { mapState } from 'vuex'
export default {
data() {
return {}
},
computed: {
...mapState(['isSidebarNavCollapse'])
},
components: {
TopAside,
Content
}
}
</script>

@ -1,185 +0,0 @@
<template>
<aside class="aside__top">
<span
class="iconfont icon-nav toggleNavCollapse"
:class="{active:isSidebarNavCollapse}"
@click="toggleNavCollapse"
>
</span>
<el-breadcrumb separator="/">
<transition-group name="breadcrumb">
<!-- 防止面包屑导航出现 首页/首页 v-if="route.name!='home'" -->
<template v-for="(route,i) in crumbList">
<el-breadcrumb-item
:key="route.name"
:to="{name:route.name}"
v-if="route.name!='home' && route.meta.name!='首页'"
:class="{'is-last-link':i==crumbList.length-1}"
>
{{route.meta.name}}
</el-breadcrumb-item>
</template>
</transition-group>
</el-breadcrumb>
<div class="aside__top--right">
<div class="user-msg">
<img class="user-img" :src="avatar" alt="">
<span class="user-name">{{account}}</span>
<el-dropdown trigger="click" placement="top">
<span class="el-dropdown-link">
<i class="el-icon-arrow-down el-icon--right"></i>
</span>
<el-dropdown-menu slot="dropdown">
<el-dropdown-item>个人中心</el-dropdown-item>
<el-dropdown-item>修改密码</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</div>
<div class="quit-system" @click="loginOut">
<span class="iconfont icon-quit"></span>
</div>
</div>
</aside>
</template>
<script>
import { mapState } from 'vuex'
export default {
data() {
return {}
},
computed: {
...mapState(['isSidebarNavCollapse', 'crumbList']),
...mapState('permission', ['avatar', 'account'])
},
methods: {
toggleNavCollapse() {
this.$store.commit('toggleNavCollapse')
},
loginOut() {
this.$store.commit('LOGIN_OUT')
/* 防止切换角色时addRoutes重复添加路由导致出现警告 */
window.location.reload()
}
}
}
</script>
<style lang="scss" scoped>
.aside__top {
border-bottom: 1px solid #e5e5e5;
height: 50px;
line-height: 50px;
position: fixed;
left: 200px;
top: 0;
right: 0;
background: #fff;
z-index: 1000;
transition: left 0.25s;
.toggleNavCollapse {
display: inline-block;
margin-left: 8px;
padding: 0 10px;
font-size: 26px;
vertical-align: middle;
color: #333;
cursor: pointer;
transition: all 0.5s;
&.active {
transform: rotate(90deg);
}
}
.aside__top--right {
position: absolute;
right: 10px;
top: -1px;
bottom: 0px;
> div {
position: relative;
display: inline-block;
text-align: center;
vertical-align: middle;
margin-left: 10px;
padding: 0 15px;
cursor: pointer;
&:hover::after {
transform-origin: 0 0;
transform: scaleX(1);
}
&:first-child:before {
border: none;
}
&::after {
content: '';
position: absolute;
left: 0;
bottom: 0;
width: 100%;
height: 2px;
background: #ef4747;
transform: scaleX(0);
transform-origin: right 0;
transition: transform 0.5s;
}
&::before {
content: '';
position: absolute;
height: 20px;
top: 50%;
left: -8px;
margin-top: -10px;
border-left: 1px solid #ccc;
}
&.email {
i {
position: absolute;
left: 18px;
top: -12px;
border-radius: 20px;
background: red;
color: #fff;
text-align: center;
font-size: 12px;
line-height: 1.5;
min-width: 20px;
min-height: 20px;
}
}
&.user-msg {
.user-img {
width: 34px;
height: 34px;
border-radius: 50%;
vertical-align: middle;
}
.user-name {
color: #758eb5;
padding: 0 4px;
}
}
.iconfont {
position: relative;
font-size: 24px;
color: #758eb5;
}
}
}
}
.breadcrumb-enter,
.breadcrumb-leave-active {
opacity: 0;
transform: translateX(20px);
}
.breadcrumb-enter-active,
.breadcrumb-leave-active {
transition: all 0.6s;
}
.breadcrumb-leave-active {
position: absolute;
}
</style>

@ -1,32 +0,0 @@
<template>
<el-menu
:collapse="isSidebarNavCollapse"
background-color="#304156"
text-color="#eee"
active-text-color="#4dbcff"
:default-active="currentMenu"
>
<DynamicMenu :menuList="sidebarMenu"></DynamicMenu>
</el-menu>
</template>
<script>
import DynamicMenu from '@/components/dynamic-menu'
import { mapState } from 'vuex'
export default {
data() {
return {
isCollapse: true
}
},
computed: {
...mapState(['isSidebarNavCollapse']),
...mapState('permission', ['sidebarMenu', 'currentMenu'])
},
methods: {},
components: {
DynamicMenu
}
}
</script>

@ -1,28 +0,0 @@
<template>
<div :class="{navCollapsed:isSidebarNavCollapse}">
<sidebarNav class="sidebar"/>
<mainContent/>
</div>
</template>
<script>
import sidebarNav from './component/sidebar-nav'
import mainContent from './component/main-content/index'
import { mapState } from 'vuex'
export default {
data() {
return {}
},
computed: {
...mapState(['isSidebarNavCollapse'])
},
components: {
sidebarNav,
mainContent
}
}
</script>
<style lang="scss" scoped>
</style>

@ -1,182 +0,0 @@
<template>
<div class="login-container">
<el-form class="login-form" autoComplete="on" :model="loginForm" :rules="loginRules" ref="loginForm" label-position="left">
<h3 class="title">后台管理系统</h3>
<el-form-item prop="username">
<span class="svg-container svg-container_login">
<svg-icon icon-class="user" />
</span>
<el-input name="username" type="text" v-model="loginForm.username" autoComplete="on" placeholder="username" />
</el-form-item>
<el-form-item prop="password">
<span class="svg-container">
<svg-icon icon-class="password"></svg-icon>
</span>
<el-input name="password" :type="pwdType" @keyup.enter.native="login" v-model="loginForm.password" autoComplete="on"
placeholder="password"></el-input>
<span class="show-pwd" @click="showPwd"><svg-icon icon-class="eye" /></span>
</el-form-item>
<el-form-item>
<el-button type="primary" style="width:100%;" :loading="loading" @click.native.prevent="login">
Sign in
</el-button>
</el-form-item>
<div class="tips">用户为admin的时候能够看到所有的权限列表其余账号只能看到部分</div>
</el-form>
</div>
</template>
<script>
import { login } from '@/api/permission'
export default {
data() {
const validateUsername = (rule, value, callback) => {
if (value.length < 5) {
callback(new Error('请输入正确的用户名'))
} else {
callback()
}
}
const validatePass = (rule, value, callback) => {
if (value.length < 5) {
callback(new Error('密码不能小于5位'))
} else {
callback()
}
}
return {
loginForm: {
username: 'admin',
password: '123456'
},
loginRules: {
username: [
{
required: true,
trigger: 'blur',
validator: validateUsername
}
],
password: [
{ required: true, trigger: 'blur', validator: validatePass }
]
},
loading: false,
pwdType: 'password'
}
},
methods: {
showPwd() {
if (this.pwdType === 'password') {
this.pwdType = ''
} else {
this.pwdType = 'password'
}
},
async login() {
try {
let data = await login(this.loginForm)
let token = data.token
this.$store.commit('LOGIN_IN', token)
this.$router.replace('/')
} catch (e) {
console.log(e)
}
}
}
}
</script>
<style rel="stylesheet/scss" lang="scss">
$bg: #2d3a4b;
$light_gray: #eee;
/* reset element-ui css */
.login-container {
.el-input {
display: inline-block;
height: 47px;
width: 90%;
input {
background: transparent;
border: 0px;
-webkit-appearance: none;
border-radius: 0px;
padding: 12px 5px 12px 15px;
color: $light_gray;
height: 47px;
&:-webkit-autofill {
-webkit-box-shadow: 0 0 0px 1000px $bg inset !important;
-webkit-text-fill-color: #fff !important;
}
}
}
.el-form-item {
border: 1px solid rgba(255, 255, 255, 0.1);
background: rgba(0, 0, 0, 0.1);
border-radius: 5px;
color: #454545;
}
}
</style>
<style rel="stylesheet/scss" lang="scss" scoped>
$bg: #2d3a4b;
$dark_gray: #889aa4;
$light_gray: #eee;
.login-container {
position: fixed;
height: 100%;
width: 100%;
background-color: $bg;
.login-form {
position: absolute;
left: 0;
right: 0;
width: 520px;
padding: 35px 35px 15px 35px;
margin: 120px auto;
}
.tips {
font-size: 14px;
color: #fff;
margin-bottom: 10px;
span {
&:first-of-type {
margin-right: 16px;
}
}
}
.svg-container {
padding: 6px 5px 6px 15px;
color: $dark_gray;
vertical-align: middle;
width: 30px;
display: inline-block;
&_login {
font-size: 20px;
}
}
.title {
font-size: 26px;
font-weight: 400;
color: $light_gray;
margin: 0px auto 40px auto;
text-align: center;
font-weight: bold;
}
.show-pwd {
position: absolute;
right: 10px;
top: 7px;
font-size: 16px;
color: $dark_gray;
cursor: pointer;
user-select: none;
}
.fontcontainer{
color:#889aa4;
padding-left:10px;
}
}
</style>

@ -1,16 +0,0 @@
<template>
<div>
<router-view></router-view>
</div>
</template>
<script>
export default {
data() {
return {}
},
mounted() {
}
}
</script>

@ -1,28 +0,0 @@
<template>
<div class="demo-image__lazy">
<el-image
v-for="url in urls"
:key="url"
:src="url"
lazy
></el-image>
</div>
</template>
<script>
export default {
data() {
return {
urls: [
'https://fuss10.elemecdn.com/a/3f/3302e58f9a181d2509f3dc0fa68b0jpeg.jpeg',
'https://fuss10.elemecdn.com/1/34/19aa98b1fcb2781c4fba33d850549jpeg.jpeg',
'https://fuss10.elemecdn.com/0/6f/e35ff375812e6b0020b6b4e8f9583jpeg.jpeg',
'https://fuss10.elemecdn.com/9/bb/e27858e973f5d7d3904835f46abbdjpeg.jpeg',
'https://fuss10.elemecdn.com/d/e6/c4d93a3805b3ce3f323f7974e6f78jpeg.jpeg',
'https://fuss10.elemecdn.com/3/28/bbf893f792f03a54408b3b7a7ebf0jpeg.jpeg',
'https://fuss10.elemecdn.com/2/11/6535bcfb26e4c79b48ddde44f4b6fjpeg.jpeg'
]
}
}
}
</script>

@ -1,13 +0,0 @@
<template>
<div>
<router-view></router-view>
</div>
</template>
<script>
export default {
data() {
return {}
}
}
</script>

@ -1,50 +0,0 @@
<template>
<el-collapse
v-model="activeNames"
@change="handleChange"
>
<el-collapse-item
title="一致性 Consistency"
name="1"
>
<div>与现实生活一致与现实生活的流程逻辑保持一致遵循用户习惯的语言和概念</div>
<div>在界面中一致所有的元素和结构需保持一致比如设计样式图标和文本元素的位置等</div>
</el-collapse-item>
<el-collapse-item
title="反馈 Feedback"
name="2"
>
<div>控制反馈通过界面样式和交互动效让用户可以清晰的感知自己的操作</div>
<div>页面反馈操作后通过页面元素的变化清晰地展现当前状态</div>
</el-collapse-item>
<el-collapse-item
title="效率 Efficiency"
name="3"
>
<div>简化流程设计简洁直观的操作流程</div>
<div>清晰明确语言表达清晰且表意明确让用户快速理解进而作出决策</div>
<div>帮助用户识别界面简单直白让用户快速识别而非回忆减少用户记忆负担</div>
</el-collapse-item>
<el-collapse-item
title="可控 Controllability"
name="4"
>
<div>用户决策根据场景可给予用户操作建议或安全提示但不能代替用户进行决策</div>
<div>结果可控用户可以自由的进行操作包括撤销回退和终止当前操作等</div>
</el-collapse-item>
</el-collapse>
</template>
<script>
export default {
data() {
return {
activeNames: ['1']
}
},
methods: {
handleChange(val) {
}
}
}
</script>

@ -1,37 +0,0 @@
<template>
<ul
class="infinite-list"
v-infinite-scroll="load"
>
<template v-for="(i,key) in count">
<li
:key="key"
class="infinite-list-item"
>{{ i }}</li>
</template>
</ul>
</template>
<script>
export default {
data() {
return {
count: 0
}
},
methods: {
load() {
this.count += 2
}
}
}
</script>
<style scope>
.infinite-list li{
background:#f0f1f2;
line-height:40px;
margin-bottom:10px;
text-align: center;
}
</style>

@ -1,40 +0,0 @@
<template>
<el-card class="box-card">
<div
slot="header"
class="clearfix"
>
<span>卡片名称</span>
<el-button
style="float: right; padding: 3px 0"
type="text"
>操作按钮</el-button>
</div>
<div
v-for="o in 4"
:key="o"
class="text item"
>
{{'列表内容 ' + o }}
</div>
</el-card>
</template>
<style>
.text {
font-size: 14px;
}
.item {
margin-bottom: 18px;
}
.clearfix:before,
.clearfix:after {
display: table;
content: '';
}
.clearfix:after {
clear: both;
}
</style>

@ -1,16 +0,0 @@
<template>
<div>
<router-view></router-view>
</div>
</template>
<script>
export default {
data() {
return {}
},
mounted() {
}
}
</script>

@ -1,444 +0,0 @@
<template lang="html">
<el-card class="box-card">
<div>
<div style="margin-bottom:10px;">
<el-button type="success" icon="el-icon-plus" size="small" @click="handleNewCategory(1,0)"></el-button>
</div>
<el-table
v-loading="loading"
:data="list"
highlight-current-row
border
size="small">
<el-table-column
label="分类名称"
align="left"
>
<template slot-scope="scope">
<a :style="`margin-left: ${(scope.row.categoryLevel - 1) * 20}px`" class="category-row">
<i class="block-icon" v-if="scope.row.categoryLevel<3" :class="[expandData[scope.row.id] ? 'el-icon-minus' : 'el-icon-plus']" @click="toggleExpend(scope.row)"></i>
<span v-if="scope.row.categoryLevel>=3" style="margin-left: 20px"></span>
<span class="category-name">{{scope.row.categoryLevel}}&emsp;{{ scope.row.permissionName }}
<i class="el-icon-edit" @click="showEdit(scope.row)"></i>
</span>
</a>
</template>
</el-table-column>
<el-table-column
label="操作"
width="350"
>
<template slot-scope="scope">
<div>
<el-button
size="small"
v-if="scope.row.permissionLevel<3"
@click="handleNewCategory(scope.row.permissionLevel+1,scope.row.id)"
>添加子分类</el-button>
</div>
</template>
</el-table-column>
</el-table>
<!-- 编辑类目弹窗 -->
<el-dialog
title="编辑类目"
:visible.sync="visible"
width="30%">
<el-form label-width="100px">
<el-row>
<el-col :span="24" >
<el-form-item label="权限名称">
<el-input v-model="editBuild.permissionName"></el-input>
</el-form-item>
<el-form-item label="权限代码">
<el-input :disabled="true" v-model="editBuild.permissionCode"></el-input>
</el-form-item>
<el-form-item label="模块名">
<el-input v-model="editBuild.module"></el-input>
</el-form-item>
</el-col>
</el-row>
</el-form>
<span slot="footer" class="dialog-footer">
<el-button @click="visible = false"> </el-button>
<el-button type="primary" @click="update"> </el-button>
</span>
</el-dialog>
<!-- 新增类目弹窗 -->
<el-dialog
title="新增类目"
:visible.sync="newVisible"
width="50%">
<el-form label-width="100px">
<el-row>
<el-col :span="24" >
<el-form-item label="权限名称">
<el-input v-model="firstBuild.permissionName"></el-input>
</el-form-item>
<el-form-item label="权限代码">
<el-input v-model="firstBuild.permissionCode"></el-input>
</el-form-item>
<el-form-item label="模块名">
<el-input v-model="firstBuild.module"></el-input>
</el-form-item>
</el-col>
</el-row>
</el-form>
<span slot="footer" class="dialog-footer">
<el-button @click="cancelNewCategory"> </el-button>
<el-button type="primary" @click="setNewCategory"> </el-button>
</span>
</el-dialog>
</div>
</el-card>
</template>
<script>
import { getFirstLevel, getNextLevel } from '@/api/permission'
export default {
name: 'coolefyCategory',
data() {
return {
firstBuild: {
permissionName: '',
module: '',
permissionCode: ''
},
editBuild: {
permissionName: '',
module: '',
permissionCode: ''
},
loading: false,
visible: false,
newVisible: false,
secondVisible: false,
thirdVisible: false,
totalRecord: 100,
checked: false,
indeterminate: false,
data: [],
list: [],
expandData: {},
checkedData: {},
indeterminateData: {},
searchData: {
pageSize: 10,
pageNumber: 1,
operateType: '',
startDate: '',
endDate: ''
},
currentRow: '',
form: {
parentId: '',
id: '',
cnCategoryName: '',
sort: '',
categoryImg: ''
},
cnCategoryName: '',
cnCategoryNameTwo: '',
levelOne: {},
//
newCategoryType: '',
parentId: 0,
isContact: false,
dialogVisible: false,
putawayName: '',
putawayCategoryId: '',
categoryData: { categoryId: '', categoryTreePath: '' },
categoryList: [], //
pageNumber: 1,
notPutVisible: false,
webCategoryId: '',
webPutaway: [],
notBelongWeb: [],
newPutawayWeb: [],
putawayCategoryName: '',
//
isTranslate: false,
translateVisible: false,
translateCncnCategoryName: '',
formLabelWidth: '100px',
isEdit: true,
webArr: []
}
},
mounted() {
this.search()
},
methods: {
handleNewCategory(type, id) {
this.newVisible = true
this.newCategoryType = type
if (id) {
this.parentId = id
} else {
this.parentId = 0
}
},
setNewCategory() {
//
var formData = new URLSearchParams()
for (var key in this.firstBuild) {
if (!this.firstBuild[key]) {
this.$message.error('请补充完数据后再操作')
return
}
formData.append(key, this.firstBuild[key])
}
if (this.newCategoryType === 1) {
formData.append('parentId', this.parentId)
formData.append('resourceLevel', 1)
formData.append('permissionLevel', 1)
} else if (this.newCategoryType === 2) {
formData.append('parentId', this.parentId)
formData.append('resourceLevel', 2)
formData.append('permissionLevel', 2)
} else if (this.newCategoryType === 3) {
formData.append('parentId', this.parentId)
formData.append('resourceLevel', 3)
formData.append('permissionLevel', 3)
}
},
cancelNewCategory() {
this.newVisible = false
this.newCategory = this.initCategory
},
handleSelectTwo(item) {
this.form.parentId = item.id
},
handleSelect(item) {
this.form.parentId = item.id
this.cnCategoryNameTwo = ''
this.levelOne = item
},
update() {
var formData = new URLSearchParams()
for (var key in this.editBuild) {
if (!this.editBuild[key]) {
this.$message.error('请补充完数据后再操作')
return
}
formData.append(key, this.editBuild[key])
}
formData.append('parentId', this.currentRow.parentId)
formData.append('id', this.currentRow.id)
formData.append('resourceLevel', this.currentRow.permissionLevel)
formData.append('permissionLevel', this.currentRow.permissionLevel)
},
showEdit(row) {
this.visible = true
this.editBuild = {
permissionName: row.permissionName,
module: row.module,
permissionCode: row.permissionCode
}
this.currentRow = row
},
search() {
getFirstLevel().then(res => {
let data = res || []
data = data.map(item => {
item.childList = []
item.isLoadChild = false
item.cnCategoryName = item.permissionName
item.categoryLevel = item.resourceLevel
return item
})
this.data = data
this.list = data
})
},
findSourceDataById(id, list) {
const len = list.length
for (let i = 0; i < len; i += 1) {
const item = list[i]
if (item.id === id) {
return item
}
if (item.childList) {
const ret = this.findSourceDataById(id, item.childList)
if (ret) {
return ret
}
}
}
},
toggleExpend(d) {
let { data } = this
if (!d.isLoadChild) {
getNextLevel(d.id).then(r => {
r.forEach((item, index) => {
item.cnCategoryName = item.permissionName
item.categoryLevel = item.resourceLevel
})
const childList = r || []
this.expandData[d.id] = true
d.isLoadChild = true
d.childList = childList
this.list = this.makeFlatData(data)
})
} else {
this.expandData[d.id] = !this.expandData[d.id]
this.list = this.makeFlatData(data)
}
},
makeFlatData(list, level = 0) {
const len = list.length
let data = []
let i = 0
for (; i < len; i += 1) {
const item = list[i]
data.push(item)
if (item.childList && this.expandData[item.id]) {
const childList = this.makeFlatData(
item.childList,
level + 1
)
data = data.concat(childList)
}
}
return data
},
back() {
this.isContact = false
this.webArr = []
this.webPutaway = []
this.webCategoryId = ''
}
}
}
</script>
<style lang="scss" scoped>
.block-icon {
border: 1px solid #1ab394;
border-radius: 2px;
color: #1ab394;
display: inline-block;
height: 14px;
line-height: 14px;
text-align: center;
vertical-align: middle;
width: 14px;
}
.category-row {
display: inline-block;
width: 100%;
i.el-icon-edit {
color: #1ab394;
display: none;
margin-left: 20px;
font-size: 16px;
}
&:hover {
i {
display: inline-block;
}
}
}
.putaway-header {
font-size: 14px;
color: #606266;
margin-bottom: 10px;
}
.el-tag {
margin-left: 10px;
margin-bottom: 10px;
}
.button-new-tag {
margin-left: 10px;
height: 32px;
line-height: 30px;
padding-top: 0;
padding-bottom: 0;
}
.input-new-tag {
width: 90px;
margin-left: 10px;
vertical-align: bottom;
}
.header-title {
margin-bottom: 10px;
color: #606266;
}
.not-belong-Web {
min-height: 450px;
}
.category-item {
display: inline-block;
min-width: 220px;
vertical-align: top;
.title {
text-align: center;
font-size: 16px;
line-height: 35px;
}
.content {
width: 100%;
border: 1px solid #888;
height: 750px;
box-sizing: border-box;
overflow-y: hidden;
padding: 10px 0;
border-radius: 3px;
}
}
.category-list {
border: 1px solid #ccc;
height: 100%;
box-sizing: border-box;
overflow-y: auto;
width: 200px;
display: inline-block;
margin: 0 5px;
font-size: 0;
li {
padding: 5px;
width: 100%;
font-size: 14px;
box-sizing: border-box;
cursor: pointer;
i {
float: right;
}
&.active {
background: #58b7ff;
color: #fff !important;
}
}
}
.colorBlue {
color: #58b7ff;
}
.translate-item {
margin-bottom: 10px;
.left {
display: inline-block;
margin-right: 10px;
width: 80px;
text-align: right;
}
.right {
display: inline-block;
}
.category-word {
display: inline-block;
margin-right: 10px;
}
}
</style>
<style>
.bgc-yellow input {
background-color: #fff000;
}
</style>

@ -1,452 +0,0 @@
<template lang="html">
<el-card class="box-card">
<div class="search-bar">
<el-form :inline="true" :model="searchData" class="fl">
<el-input style="display: none;"></el-input>
<el-form-item label="角色名称">
<el-input v-model="searchData.roleName" placeholder="角色名称" @keyup.enter.native="onSearch()"></el-input>
</el-form-item>
</el-form>
<div class="fl">
<el-button type="text" @click="handleReset"></el-button>
<el-button type="primary" icon="el-icon-search" @click="onSearch"></el-button>
</div>
</div>
<div class="tools-bar">
<el-button type="success" icon="el-icon-plus" size="small" @click="dialogFormVisible = true;">新增角色</el-button>
</div>
<div>
<el-table
ref="singleTable"
:data="tableData"
border
highlight-current-row
style="width: 100%">
<el-table-column
type="index"
width="60">
</el-table-column>
<el-table-column
prop="roleName"
label="角色名"
width="120">
</el-table-column>
<el-table-column
label="操作权限"
prop="erpMemberPermissions"
:formatter="permListFormatter">
</el-table-column>
<el-table-column
label="操作"
fixed="right"
width="180">
<template slot-scope="scope">
<el-button type="text" size="small" @click="handleEditRoleName(scope.$index, scope.row)">修改角色名</el-button>
<el-button type="text" size="small" @click="handlePower(scope.$index, scope.row)">授权</el-button>
<el-button type="text" size="small" @click="handleDelete(scope.$index, scope.row)">删除</el-button>
</template>
</el-table-column>
</el-table>
<div class="pagination-bar">
<el-pagination
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
:page-sizes="[10, 25, 50, 100]"
:page-size="pageSize"
:current-page.sync="pageNumber"
layout="total, sizes, prev, pager, next, jumper"
:total="totalRecord">
</el-pagination>
</div>
</div>
<el-dialog :title="dialogTitle" :visible.sync="dialogVisible" @close="onDialogClose()" width="80%">
<el-form ref="roleForm" :rules="rules" :model="roleForm" label-width="120px">
<el-form-item v-if="dialogTitle !== '角色授权'" label="角色名称" prop="roleName">
<el-input v-model="roleForm.roleName"></el-input>
</el-form-item>
<el-form-item v-if="dialogTitle !== '角色授权'" label="角色代码" label-width="120px">
<el-input v-model="roleForm.roleCode" autocomplete="off"></el-input>
</el-form-item>
<el-form-item v-if="dialogTitle !== '角色授权'" label="状态" label-width="120px">
<el-select v-model="roleForm.status" placeholder="请选择状态">
<el-option label="停用" value='0'></el-option>
<el-option label="启用" value='1'></el-option>
</el-select>
</el-form-item>
<el-form-item v-if="dialogTitle=='新增角色并授权' || dialogTitle=='角色授权'" label="权限">
<el-tabs type="border-card">
<template v-for="(role, key) in roleTree">
<el-tab-pane :key="key" :label="role.permissionName">
<el-tree
:data="role.erpMemberPermissions"
show-checkbox
default-expand-all
node-key="id"
ref="tree"
highlight-current
:props="defaultTreeProps"
>
</el-tree>
</el-tab-pane>
</template>
</el-tabs>
</el-form-item>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button @click="dialogVisible = false"> </el-button>
<el-button type="info" @click="onEditSubmit()" v-if="dialogTitle=='修改角色名称'"></el-button>
<el-button type="info" @click="onEditRoleSubmit" v-if="dialogTitle=='角色授权'"></el-button>
<el-button type="primary" @click="onAddSubmit" v-if="dialogTitle=='新增角色并授权'"></el-button>
</div>
</el-dialog>
<el-dialog title="新增角色" :visible.sync="dialogFormVisible">
<el-form :model="form">
<el-form-item label="名称" label-width="120px">
<el-input v-model="form.roleName" autocomplete="off"></el-input>
</el-form-item>
<el-form-item label="角色代码" label-width="120px">
<el-input v-model="form.roleCode" autocomplete="off"></el-input>
</el-form-item>
<el-form-item label="状态" label-width="120px">
<el-select v-model="form.status" placeholder="请选择状态">
<el-option label="停用" value="0"></el-option>
<el-option label="启用" value="1"></el-option>
</el-select>
</el-form-item>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button @click="dialogFormVisible = false"> </el-button>
<el-button type="primary" @click="doAdd()"> </el-button>
</div>
</el-dialog>
</el-card>
</template>
<script>
import { getRoleList, getAllPermissiion } from '@/api/permission'
export default {
data() {
return {
form: {
roleName: '',
status: '',
roleCode: ''
},
dialogFormVisible: false,
dialogSize: 'large',
totalRecord: 0,
pageSize: 10,
pageNumber: 1,
dialogVisible: false,
dialogTitle: '新增角色并授权',
defaultTreeProps: {
children: 'erpMemberPermissions',
label: 'permissionName'
},
rules: {
roleName: [
{
required: true,
message: '角色名称不能为空',
trigger: 'blur'
}
]
},
searchData: {
roleName: ''
},
roleForm: {
id: '',
roleName: '',
permissions: '',
roleCode: '',
roleType: '',
status: ''
},
roleTree: [],
tableData: []
}
},
created() {
this.loadData()
this.onSearch()
},
methods: {
doAdd() {
if (
!this.form.roleName ||
!this.form.status ||
!this.form.roleCode
) {
this.$message.error('请填充信息后再提交!')
return
}
var formData = new FormData()
formData.append('roleName', this.form.roleName)
formData.append('status', this.form.status)
formData.append('roleCode', this.form.roleCode)
},
getTreeIndexByRootRoleId(id) {
let index
const len = this.roleTree.length
for (index = 0; index < len; index++) {
if (this.roleTree[index].id === id) {
return index
}
}
},
getRootRoleIdByRoleId(id) {
for (let i = 0; i < this.roleTree.length; i++) {
const roles = this.roleTree[i]
let hasRole = this.getRole(roles.erpMemberPermissions, id)
if (hasRole) {
return roles.id
}
}
},
getRole(roles, id) {
let hasRole
if (!roles) {
return
}
for (let i = 0; i < roles.length; i++) {
const role = roles[i]
if (role.id === id) {
hasRole = true
break
} else if (role.erpMemberPermissions) {
hasRole = this.getRole(role.erpMemberPermissions, id)
if (hasRole) {
break
}
}
}
return hasRole
},
isLeaf(id) {
let isLeaf
for (let i = 0; i < this.roleTree.length; i++) {
const roles = this.roleTree[i]
this.isLeafByRoleId(roles, id, () => {
isLeaf = true
})
if (isLeaf) {
return true
}
}
},
isLeafByRoleId(roles, id, fn) {
if (roles.id === id) {
if (roles.judge) {
fn()
}
if (!roles.erpMemberPermissions && roles.parentId !== 0) {
fn()
}
} else if (roles.erpMemberPermissions) {
roles.erpMemberPermissions.map(role => {
this.isLeafByRoleId(role, id, fn)
})
}
},
loadData() {
getAllPermissiion().then(res => {
this.roleTree = res
this.roleTree.forEach((item, index) => {
if (item.erpMemberPermissions) {
item.erpMemberPermissions.forEach(
(items, indexs) => {
if (item.erpMemberPermissions[indexs] && item.erpMemberPermissions[indexs].erpMemberPermissions && item.erpMemberPermissions[indexs].erpMemberPermissions.length === 0) {
this.roleTree[index].erpMemberPermissions[indexs].judge = true
}
}
)
}
})
})
},
onDialogClose() {
// this.$refs.roleForm.resetFields();
// if(this.$refs.tree) {
// for(let tree of this.$refs.tree) {
// tree.setCheckedKeys([]);
// }
// }
},
handleSizeChange(val) {
this.pageSize = val
this.onSearch()
},
handleCurrentChange(val) {
this.onSearch({ pageNumber: val })
},
handleReset() {
this.searchData = {
roleName: ''
}
this.onSearch()
},
onSearch({ pageNumber = 1 } = {}) {
getRoleList()
.then(res => {
this.tableData = res || []
})
},
permListFormatter(row, column, cellValue) {
let str = []
for (let item of cellValue) {
str.push(item.permissionName)
}
return str.join('')
},
handleDelete(index, row) {
this.$confirm('确认删除该角色?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {})
},
handlePower(index, row) {
this.dialogSize = 'large'
const keys = [
[],
[],
[],
[],
[],
[],
[],
[],
[],
[],
[],
[],
[],
[],
[]
]
this.roleForm.id = row.id
row.erpMemberPermissions.map(role => {
let id, rootRoleId, treeIndex
if (this.isLeaf(role.id)) {
id = role.id
rootRoleId = this.getRootRoleIdByRoleId(id)
treeIndex = this.getTreeIndexByRootRoleId(rootRoleId)
keys[treeIndex].push(id)
}
})
// console.log(keys)
setTimeout(() => {
const trees = this.$refs.tree
trees.map((tree, index) => {
tree.setCheckedKeys(keys[index])
})
})
this.dialogVisible = true
this.dialogTitle = '角色授权'
},
handleEditRoleName(index, row) {
this.dialogSize = 'tiny'
for (let x of Object.keys(this.roleForm)) {
this.roleForm[x] = row[x]
}
this.roleForm.status = String(this.roleForm.status)
this.dialogVisible = true
this.dialogTitle = '修改角色名称'
},
onAddSubmit() {
this.getPermissions()
let permissions = this.roleForm.permissions
this.$refs.roleForm.validate(valid => {
if (valid) {
if (!permissions) {
this.$message({
showClose: true,
message: '请选择权限',
type: 'warning'
})
return false
}
}
})
},
onEditSubmit() {
this.$refs.roleForm.validate(valid => {
if (valid) {
var formData = new URLSearchParams()
formData.append('roleName', this.roleForm.roleName)
formData.append('id', this.roleForm.id)
formData.append('roleCode', this.roleForm.roleCode)
formData.append('status', this.roleForm.status)
}
})
},
onEditRoleSubmit() {
this.getPermissions()
let permissions = this.roleForm.permissions
this.$refs.roleForm.validate(valid => {
if (valid) {
if (!permissions) {
this.$message({
showClose: true,
message: '请选择权限',
type: 'warning'
})
return
}
var formData = new URLSearchParams()
this.roleForm.permissions.split(',').forEach(element => {
formData.append('permissionIds', element)
})
}
})
},
getPermissions() {
let set = new Set()
for (let tree of this.$refs.tree) {
//
let nodes = tree.getCheckedNodes()
for (let node of nodes) {
let { id, parentId } = node
set.add(id)
set.add(parentId)
}
//
let nodesDOM = tree.$el.querySelectorAll('.el-tree-node')
let nodesVue = [].map.call(nodesDOM, node => node.__vue__)
for (let node of nodesVue.filter(
item => item.indeterminate === true
)) {
let { id, parentId } = {
id: node.$options.propsData.node.data.id,
parentId: node.$options.propsData.node.data.parentId
}
set.add(id)
set.add(parentId)
}
}
this.roleForm.permissions = [...set].join(',')
}
}
}
</script>
<style>
.fr{
float:right;
}
.fl{
float:left;
}
.search-bar{
overflow: hidden;
}
.tools-bar{
margin-bottom:20px;
}
</style>

@ -1,337 +0,0 @@
<template lang="html">
<el-card class="box-card">
<div class="search-bar">
<el-form :inline="true" :model="searchData" class="fl">
<el-input style="display: none;"></el-input>
<el-form-item label="登录名称">
<el-input v-model="searchData.loginName" placeholder="登录名称" @keyup.enter.native="onSearch()"></el-input>
</el-form-item>
</el-form>
<div class="fl">
<el-button type="text" @click="handleReset"></el-button>
<el-button type="primary" icon="el-icon-search" @click="onSearch"></el-button>
</div>
</div>
<div class="tools-bar">
<el-button type="success" icon="el-icon-plus" size="small" @click="dialogVisible = true;dialogTitle='新增用户'">新增用户</el-button>
</div>
<div>
<el-table
v-loading.body="tableLoading"
ref="singleTable"
:data="tableData"
border
highlight-current-row
style="width: 100%">
<el-table-column
type="index"
width="60">
</el-table-column>
<el-table-column
prop="status"
label="停用/启用"
align="center"
min-width="100">
<template slot-scope="scope">
<!-- <el-tag v-if="scope.row.status=='1'" color="#13CE66"></el-tag>
<el-tag v-if="scope.row.status=='0'" color="#FF4949"></el-tag> -->
<el-switch
v-model="scope.row.status"
:active-value="1"
:inactive-value="0"
active-text=""
inactive-text=""
@change="handleStatus(scope.row)">
</el-switch>
</template>
</el-table-column>
<el-table-column
prop="loginName"
label="登录名"
min-width="120">
</el-table-column>
<el-table-column
prop="name"
label="真实姓名"
min-width="120">
</el-table-column>
<el-table-column
prop="mobile"
label="联系电话"
width="130">
</el-table-column>
<el-table-column
prop="roleList"
:formatter="roleFormatter"
min-width="210"
label="权限">
</el-table-column>
<el-table-column
prop="address"
min-width="200"
label="联系地址">
</el-table-column>
<el-table-column
prop="email"
label="电子邮箱"
width="250">
</el-table-column>
<el-table-column
prop="lastLoginTime"
label="最后登录时间"
:formatter="toDateTime"
width="180">
</el-table-column>
<el-table-column
label="操作"
fixed="right"
width="170">
<template slot-scope="scope">
<div>
<el-button
type="text"
size="small"
@click="handleEdit(scope.$index, scope.row)"
>编辑</el-button>
<el-button
type="text"
size="small"
@click="handleResetPwd(scope.$index, scope.row)"
>重置密码</el-button>
</div>
</template>
</el-table-column>
</el-table>
<div class="pagination-bar">
<el-pagination
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
:page-sizes="[10, 25, 50, 100]"
:page-size="pageSize"
layout="total, sizes, prev, pager, next, jumper"
:total="totalRecord">
</el-pagination>
</div>
</div>
<el-dialog :title="dialogTitle" :visible.sync="dialogVisible" @close="onDialogClose()">
<el-form ref="dataForm" :rules="rules" :model="dataForm" label-width="80px">
<el-form-item label="登录名" prop="loginName">
<template v-if="dialogTitle=='修改用户信息'">{{dataForm.loginName}}</template>
<el-input v-else v-model="dataForm.loginName" placeholder="登录名"></el-input>
</el-form-item>
<el-form-item label="用户角色" prop="roleIds">
<el-select v-model="dataForm.tempRoleIds" multiple placeholder="请选择" style="width: 100%;">
<el-option
v-for="item in roles"
:key="item.id"
:label="item.roleName"
:value="item.id">
</el-option>
</el-select>
</el-form-item>
<el-form-item label="真实姓名" prop="name">
<el-input v-model="dataForm.name" placeholder="真实姓名"></el-input>
</el-form-item>
<el-form-item label="联系电话" prop="mobile">
<el-input v-model="dataForm.mobile" placeholder="联系电话"></el-input>
</el-form-item>
<el-form-item label="联系地址" prop="address">
<el-input v-model="dataForm.address" placeholder="联系地址"></el-input>
</el-form-item>
<el-form-item label="电子邮箱" prop="email">
<el-input v-model="dataForm.email" placeholder="电子邮箱"></el-input>
</el-form-item>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button @click="dialogVisible = false"> </el-button>
<el-button type="info" @click="onDialogSubmit()" v-if="dialogTitle=='修改用户信息'"></el-button>
<el-button type="primary" @click="onDialogSubmit()" v-else></el-button>
</div>
</el-dialog>
</el-card>
</template>
<script>
import { getUserList } from '@/api/permission'
import moment from 'moment'
export default {
data() {
return {
totalRecord: 0,
pageSize: 10,
tableLoading: false,
dialogVisible: false,
dialogTitle: '新增用户',
roles: [
{
id: 1,
roleName: '超级管理员'
},
{
id: 2,
roleName: '普通用户'
}
],
defaultTreeProps: {
children: 'childPermList',
label: 'permissionName'
},
rules: {
loginName: [
{
required: true,
message: '登录名不能为空',
trigger: 'blur'
},
{
min: 1,
max: 50,
message: '登录名长度在 1 到 50 个字符',
trigger: 'blur'
}
],
name: [
{
required: true,
message: '真实姓名不能为空',
trigger: 'blur'
},
{
min: 1,
max: 20,
message: '真实姓名长度在 1 到 20 个字符',
trigger: 'blur'
}
],
mobile: [
{
required: true,
message: '联系电话不能为空',
trigger: 'blur'
},
{
pattern: /^(13|15|18|14|17)[0-9]{9}$/,
message: '手机号码格式不正确',
trigger: 'blur'
}
],
email: [
{
required: true,
message: '请输入邮箱地址',
trigger: 'blur'
},
{
type: 'email',
message: '邮箱格式不正确',
trigger: 'blur, change'
}
]
},
searchData: {
loginName: ''
},
dataForm: {
id: '',
loginName: '',
tempRoleIds: [],
roleIds: '',
name: '',
mobile: '',
address: '',
email: ''
},
tableData: []
}
},
created() {
this.initList()
},
methods: {
async initList() {
const data = await getUserList()
this.tableData = data
},
handleStatus(row) {},
statusFormat(row, column, cellValue) {
return { '0': '停用', '1': '启用' }[cellValue] || ''
},
onDialogClose() {
this.dataForm.tempRoleIds = []
this.$refs.dataForm.resetFields()
},
handleSizeChange(val) {
this.pageSize = val
this.onSearch()
},
handleCurrentChange(val) {
this.onSearch({ pageNumber: val })
},
handleReset() {
this.searchData = {
loginName: ''
}
this.onSearch()
},
onSearch({ pageNumber = 1 } = {}) {},
toDateTime(row, column, cellValue) {
return cellValue
? moment(cellValue).format('YYYY-MM-DD HH:mm:ss')
: ''
},
roleFormatter(row, column, cellValue) {
let result = []
if (typeof row.erpMemberRoles === 'object' && row.erpMemberRoles.length > 0) {
for (let item of row.erpMemberRoles) {
result.push(item.roleName)
}
}
return result.join('')
},
handleChangeStatus(index, row) {},
handleResetPwd(index, row) {
this.$confirm('确认重置该用户的登录密码?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {})
},
handleEdit(index, row) {
this.dialogVisible = true
this.dialogTitle = '修改用户信息'
this.dataForm.tempRoleIds = []
for (let x of Object.keys(this.dataForm)) {
if (
x === 'tempRoleIds' &&
typeof row.roleList === 'object' &&
row.roleList.length > 0
) {
for (let item of row.roleList) {
this.dataForm.tempRoleIds.push(item.id)
}
} else {
this.dataForm[x] = row[x]
}
}
},
onDialogSubmit() {}
}
}
</script>
<style lang="scss">
.fr{
float:right;
}
.fl{
float:left;
}
.search-bar{
overflow: hidden;
}
</style>
<style>
.tools-bar{
margin-bottom:20px;
}
</style>

@ -1,149 +0,0 @@
/* 订单管理 */
const Order = () => import('@/pages/order-manage')
const OrderList = () => import('@/pages/order-manage/order-list')
const ProductManage = () => import('@/pages/order-manage/product-manage')
const ProductionList = () =>
import('@/pages/order-manage/product-manage/production-list')
const ReviewManage = () =>
import('@/pages/order-manage/product-manage/review-manage')
const ReturnGoods = () => import('@/pages/order-manage/return-goods')
/* 产品管理 */
const Goods = () => import('@/pages/goods-manage')
const GoodsList = () => import('@/pages/goods-manage/goods-list')
const GoodsClassify = () => import('@/pages/goods-manage/goods-classify')
// 权限管理
const Permission = () => import('@/pages/permission')
const UserManage = () => import('@/pages/permission/user-manage')
const RoleManage = () => import('@/pages/permission/role-manage')
const MenuManage = () => import('@/pages/permission/menu-manage')
/* 需要权限判断的路由 */
const dynamicRoutes = [
{
path: '/order',
component: Order,
name: 'order-manage',
meta: {
name: '订单管理',
icon: 'example'
},
children: [
{
path: 'list',
name: 'order-list',
component: OrderList,
meta: {
name: '订单列表',
icon: 'table'
}
},
{
path: 'product',
name: 'product-manage',
component: ProductManage,
meta: {
name: '生产管理',
icon: 'user'
},
children: [
{
path: 'list',
name: 'product-list',
component: ProductionList,
meta: {
name: '生产列表',
icon: 'table'
}
},
{
path: 'review',
name: 'review-manage',
component: ReviewManage,
meta: {
name: '审核管理',
icon: 'eye'
}
}
]
},
{
path: 'returnGoods',
name: 'return-goods',
component: ReturnGoods,
meta: {
name: '退货管理',
icon: 'nested'
}
}
]
},
{
path: '/goods',
component: Goods,
name: 'goods',
meta: {
name: '产品管理',
icon: 'user'
},
children: [
{
path: 'list',
name: 'goods-list',
component: GoodsList,
meta: {
name: '产品列表',
icon: 'table'
}
},
{
path: 'classify',
name: 'goods-classify',
component: GoodsClassify,
meta: {
name: '产品分类',
icon: 'tree'
}
}
]
},
{
path: '/permission',
component: Permission,
name: 'permission',
meta: {
name: '权限管理',
icon: 'table'
},
children: [
{
path: 'user',
name: 'user-manage',
component: UserManage,
meta: {
name: '用户管理',
icon: 'table'
}
},
{
path: 'role',
name: 'role-manage',
component: RoleManage,
meta: {
name: '角色管理',
icon: 'eye'
}
},
{
path: 'menu',
name: 'menu-manage',
component: MenuManage,
meta: {
name: '菜单管理',
icon: 'tree'
}
}
]
}
]
export default dynamicRoutes

@ -1,54 +0,0 @@
import Vue from 'vue'
import Router from 'vue-router'
import Login from '@/pages/login/login'
import NotFound from '@/pages/errorPage/404'
import Forbidden from '@/pages/errorPage/403'
import Layout from '@/pages/layout/index'
import Home from '@/pages/home/index'
Vue.use(Router)
/* 初始路由 */
export default new Router({
routes: [
{
path: '/login',
component: Login
}
]
})
/* 准备动态添加的路由 */
export const DynamicRoutes = [
{
path: '',
component: Layout,
name: 'container',
redirect: 'home',
meta: {
requiresAuth: true,
name: '首页'
},
children: [
{
id: 1,
path: 'home',
component: Home,
name: 'home',
meta: {
name: '首页',
icon: 'tree'
}
}
]
},
{
path: '/403',
component: Forbidden
},
{
path: '*',
component: NotFound
}
]

@ -1,3 +0,0 @@
export default {
}

@ -1,3 +0,0 @@
export default {
}

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

@ -1,5 +0,0 @@
import permission from './modules/permission'
export default {
permission
}

@ -1,59 +0,0 @@
import { fetchPermission } from '@/api/permission'
import router, { DynamicRoutes } from '@/router/index'
import { recursionRouter } from '@/utils/recursion-router'
import dynamicRouter from '@/router/dynamic-router'
export default {
namespaced: true,
state: {
permissionList: null /** 所有路由 */,
sidebarMenu: [] /** 导航菜单 */,
currentMenu: '' /** 当前active导航菜单 */,
control_list: [] /** 完整的权限列表 */,
avatar: ''/** 头像 */,
account: ''/** 用户角色 */
},
getters: {},
mutations: {
SET_AVATAR(state, avatar) {
state.avatar = avatar
},
SET_ACCOUNT(state, account) {
state.account = account
},
SET_PERMISSION(state, routes) {
state.permissionList = routes
},
CLEAR_PERMISSION(state) {
state.permissionList = null
},
SET_MENU(state, menu) {
state.sidebarMenu = menu
},
CLEAR_MENU(state) {
state.sidebarMenu = []
},
SET_CURRENT_MENU(state, currentMenu) {
state.currentMenu = currentMenu
},
SET_CONTROL_LIST(state, list) {
state.control_list = list
}
},
actions: {
async FETCH_PERMISSION({ commit, state }) {
let permissionList = await fetchPermission()
commit('SET_AVATAR', permissionList.avatar)
commit('SET_ACCOUNT', permissionList.name)
let routes = recursionRouter(permissionList.data, dynamicRouter)
let MainContainer = DynamicRoutes.find(v => v.path === '')
let children = MainContainer.children
commit('SET_CONTROL_LIST', [...children, ...dynamicRouter])
children.push(...routes)
commit('SET_MENU', children)
let initialRoutes = router.options.routes
router.addRoutes(DynamicRoutes)
commit('SET_PERMISSION', [...initialRoutes, ...DynamicRoutes])
}
}
}

@ -1,14 +0,0 @@
export default {
LOGIN_IN(state, token) {
state.UserToken = token
},
LOGIN_OUT(state) {
state.UserToken = ''
},
toggleNavCollapse(state) {
state.isSidebarNavCollapse = !state.isSidebarNavCollapse
},
setCrumbList(state, list) {
state.crumbList = list
}
}

@ -1,12 +0,0 @@
export default {
get UserToken() {
return localStorage.getItem('token')
},
set UserToken(value) {
localStorage.setItem('token', value)
},
/* 导航菜单是否折叠 */
isSidebarNavCollapse: false,
/* 面包屑导航列表 */
crumbList: []
}

@ -1,39 +0,0 @@
$mainColor:#151519;
@mixin table-center {
display: table-cell;
vertical-align: middle;
text-align: center;
}
@mixin poa-center($w, $h) {
position: absolute;
width: $w;
height: $h;
left: 50%;
top: 50%;
transition: translate(-50%, -50%)
}
@mixin flex-center {
display: flex;
justify-content: center;
align-items: center;
}
@mixin t-overflow($line:1) {
@if $line==1 {
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
@else {
display: -webkit-box;
-webkit-line-clamp: $line;
-webkit-box-orient: vertical;
overflow: hidden;
text-overflow: ellipsis;
}
}

@ -1,171 +0,0 @@
@charset "utf-8";
html {
color: #000;
background: #fff;
overflow-y: scroll;
-webkit-text-size-adjust: 100%;
-ms-text-size-adjust: 100%;
}
html * {
outline: none;
-webkit-text-size-adjust: none;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
box-sizing: border-box;
}
html,
body {
font-family: "Helvetica Neue",Helvetica,"PingFang SC","Hiragino Sans GB","Microsoft YaHei","微软雅黑",Arial,sans-serif;
height: 100%;
width: 100%;
overflow: auto;
}
body,
div,
dl,
dt,
dd,
ul,
ol,
li,
h1,
h2,
h3,
h4,
h5,
h6,
pre,
code,
form,
fieldset,
legend,
input,
textarea,
p,
blockquote,
th,
td,
hr,
button,
article,
aside,
details,
figcaption,
figure,
footer,
header,
hgroup,
menu,
nav,
section {
margin: 0;
padding: 0;
}
input,
select,
textarea {
font-size: 100%;
}
table {
border-collapse: collapse;
border-spacing: 0;
}
fieldset,
img {
border: 0;
}
abbr,
acronym {
border: 0;
font-variant: normal;
}
del {
text-decoration: line-through;
}
address,
caption,
cite,
code,
dfn,
em,
th,
i,
var {
font-style: normal;
font-weight: 500;
}
ol,
ul {
list-style: none;
}
caption,
th {
text-align: left;
}
h1,
h2,
h3,
h4,
h5,
h6 {
font-size: 100%;
font-weight: 500;
}
q:before,
q:after {
content: '';
}
sub,
sup {
font-size: 75%;
line-height: 0;
position: relative;
vertical-align: baseline;
}
sup {
top: -0.5em;
}
sub {
bottom: -0.25em;
}
a:hover {
text-decoration: underline;
}
ins,
a,
a:active,
a:visited,
a:link {
text-decoration: none;
}
.clearfix {
&:after {
display: table;
clear: both;
content: "";
visibility: hidden;
;
height: 0;
}
}

@ -1,81 +0,0 @@
.el-menu {
border: none;
.iconfont {
color: #fff;
font-size: 16px;
}
.el-submenu__title {
&:hover {
background: none !important;
}
i.el-submenu__icon-arrow {
color: #ddd;
font-size: 15px;
}
}
.el-menu-item-group__title {
padding: 0;
}
}
.el-breadcrumb {
display: inline-block;
vertical-align: middle;
font-size: 14px;
margin-left: 5px;
.el-breadcrumb__inner {
&.is-link {
display: inline-block;
font-weight: normal;
color: #424040 !important;
}
}
.is-last-link .is-link {
font-weight: normal;
color: #999 !important;
}
}
.sidebar-container {
transition: width .28s;
width: 180px ;
height: 100%;
position: fixed;
top: 0;
bottom: 0;
left: 0;
z-index: 1001;
background: rgba(0,0,0,0.5)
}
.sidebar-container.navCollapsed {
width: 63px ;
}
.navCollapsed{
.el-submenu {
&>.el-submenu__title {
&>span {
display: none;
}
.el-submenu__icon-arrow {
display: none;
}
}
}
}

@ -1,66 +0,0 @@
/* 侧边栏 */
.sidebar {
width: 200px !important;
height: 100%;
background: #304156;
transition: all 0.25s;
position: fixed;
top: 0;
bottom: 0;
left: 0;
z-index: 100;
overflow-x: hidden;
.iconfont {
margin-right: 8px;
color: #fff;
font-size: 18px;
}
>div.menu-container>li.el-menu-item,
>div.menu-container>li.el-submenu>.el-submenu__title {
border-bottom: 1px solid rgba(238, 238, 238, 0.1);
}
.el-menu-item {
background: #304156 !important;
}
/* 菜单hover时的背景 */
.el-submenu__title:hover,
.el-menu-item:hover {
background: #223041 !important;
}
/* 菜单active时的背景 */
/* .el-menu-item.is-active {
background: #293748 !important;
} */
}
/* 主体内容 */
.main-container {
min-height: 100%;
margin-left: 200px;
transition: margin-left 0.25s;
position: relative;
box-sizing: border-box;
padding: 60px 20px 0 20px;
}
/* 折叠菜单下的样式 */
.navCollapsed {
.sidebar {
width: 64px !important;
ul {
display: none;
}
.iconfont+span {
display: none;
}
.el-submenu__icon-arrow {
display: none;
}
}
.main-container {
margin-left: 64px;
}
.aside__top{
left:64px!important;
}
}

@ -1,5 +0,0 @@
@import './normalize.scss';
@import './reset_element.scss';
@import './sidebar.scss';
@import './loading.scss';
@import url('//at.alicdn.com/t/font_641452_q3ah7ae4qvndn29.css');

@ -1,35 +0,0 @@
.ajax-loading {
display: none;
.loading {
position: fixed;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
padding: 0 40px;
height: 80px;
line-height: 80px;
background: rgba(0, 0, 0, 0.75);
border-radius: 6px;
text-align: center;
z-index: 9999;
font-size: 16px;
color: #fff;
img {
width: 32px;
vertical-align: middle;
}
span {
margin-left: 12px;
}
}
.overlay {
position: fixed;
left: 0;
right: 0;
top: 0;
bottom: 0;
z-index: 9998;
background: rgb(255, 255, 255);
opacity: 0.1;
}
}

@ -1,33 +0,0 @@
/**
*
* @param {Array} userRouter 后台返回的用户权限json
* @param {Array} allRouter 前端配置好的所有动态路由的集合
* @return {Array} realRoutes 过滤后的路由
*/
export function recursionRouter(userRouter = [], allRouter = []) {
var realRoutes = allRouter
.filter(item => userRouter.includes(item.name))
.map(item => ({
...item,
children: item.children
? recursionRouter(userRouter, item.children)
: null
}))
return realRoutes
}
/**
*
* @param {Array} routes 用户过滤后的路由
*
* 递归为所有有子路由的路由设置第一个children.path为默认路由
*/
export function setDefaultRoute(routes) {
routes.forEach((v, i) => {
if (v.children && v.children.length > 0) {
v.redirect = { name: v.children[0].name }
setDefaultRoute(v.children)
}
})
}

@ -1,5 +0,0 @@
module.exports = {
env: {
jest: true
}
}

@ -1,12 +0,0 @@
import { shallowMount } from '@vue/test-utils'
import HelloWorld from '@/components/HelloWorld.vue'
describe('HelloWorld.vue', () => {
it('renders props.msg when passed', () => {
const msg = 'new message'
const wrapper = shallowMount(HelloWorld, {
propsData: { msg }
})
expect(wrapper.text()).toMatch(msg)
})
})

@ -1,160 +0,0 @@
const BundleAnalyzerPlugin = require('webpack-bundle-analyzer')
.BundleAnalyzerPlugin
const path = require('path')
const webpack = require('webpack')
const AddAssetHtmlPlugin = require('add-asset-html-webpack-plugin')
// 导入compression-webpack-plugin
const CompressionWebpackPlugin = require('compression-webpack-plugin')
// 定义压缩文件类型
const productionGzipExtensions = ['js', 'css']
function resolve(dir) {
return path.join(__dirname, dir)
}
const proxyTargetMap = {
prod: 'https://xxx.xxx.com/',
randy: 'http://47.105.71.81:3306',
peter: 'http://192.168.11.178:3001'
}
let proxyTarget = proxyTargetMap[process.env.API_TYPE] || proxyTargetMap.prod
let publicPath = process.env.NODE_ENV === 'production' ? '/' : '/'
let dllPublishPath = '/vendor'
module.exports = {
publicPath: publicPath,
outputDir: 'dist',
// 放置静态资源的地方 (js/css/img/font/...)
// assetsDir: '',
// 是否在保存的时候使用 `eslint-loader` 进行检查。
// 有效的值:`ture` | `false` | `"error"`
// 当设置为 `"error"` 时,检查出的错误会触发编译失败。
lintOnSave: true,
// 使用带有浏览器内编译器的完整构建版本
// 查阅 https://cn.vuejs.org/v2/guide/installation.html#运行时-编译器-vs-只包含运行时
// compiler: false,
// babel-loader 默认会跳过 node_modules 依赖。
// 通过这个选项可以显式转译一个依赖。
transpileDependencies: [
/* string or regex */
],
// 是否为生产环境构建生成 source map
productionSourceMap: false,
// 调整内部的 webpack 配置。
// 查阅 https://github.com/vuejs/vue-docs-zh-cn/blob/master/vue-cli/webpack.md
chainWebpack: config => {
// 移除 prefetch 插件,解决组件懒加载失效的问题
config.plugins.delete('prefetch')
// 添加新的svg-sprite-loader处理svgIcon
config.module
.rule('svgIcon')
.test(/\.svg$/)
.include.add(resolve('src/icons'))
.end()
.use('svg-sprite-loader')
.loader('svg-sprite-loader')
.tap(options => {
options = {
symbolId: 'icon-[name]'
}
return options
})
// 原有的svg图像处理loader添加exclude
config.module
.rule('svg')
.exclude.add(resolve('src/icons'))
.end()
},
// CSS 相关选项
css: {
// 将组件内的 CSS 提取到一个单独的 CSS 文件 (只用在生产环境中)
// 也可以是一个传递给 `extract-text-webpack-plugin` 的选项对象
extract: true,
// 是否开启 CSS source map
sourceMap: true,
// 为预处理器的 loader 传递自定义选项。比如传递给
// sass-loader 时,使用 `{ sass: { ... } }`。
loaderOptions: {},
// 为所有的 CSS 及其预处理文件开启 CSS Modules。
// 这个选项不会影响 `*.vue` 文件。
modules: false
},
// 在生产环境下为 Babel 和 TypeScript 使用 `thread-loader`
// 在多核机器下会默认开启。
parallel: require('os').cpus().length > 1,
// PWA 插件的选项。
// 查阅 https://github.com/vuejs/vue-docs-zh-cn/blob/master/vue-cli-plugin-pwa/README.md
pwa: {},
// 配置 webpack-dev-server 行为。
devServer: {
disableHostCheck: true,
open: process.platform === 'darwin',
host: 'localhost',
port: 8080,
https: false,
hotOnly: false,
// eslint-disable-next-line no-dupe-keys
open: true,
// 查阅 https://github.com/vuejs/vue-docs-zh-cn/blob/master/vue-cli/cli-service.md#配置代理
proxy: {
'/api': {
target: proxyTarget,
changeOrigin: true,
pathRewrite: {
'^/api': ''
}
}
},
before: app => {}
},
// eslint-disable-next-line no-dupe-keys
configureWebpack: config => {
if (process.env.NODE_ENV === 'production') {
// 为生产环境修改配置...
config.plugins.push(
new webpack.DllReferencePlugin({
context: process.cwd(),
manifest: require('./public/vendor/vendor-manifest.json')
}),
// 将 dll 注入到 生成的 html 模板中
new AddAssetHtmlPlugin({
// dll文件位置
filepath: path.resolve(__dirname, './public/vendor/*.js'),
// dll 引用路径
publicPath: dllPublishPath,
// dll最终输出的目录
outputPath: './vendor'
}),
// 开启压缩
new CompressionWebpackPlugin({
filename: '[path].gz[query]',
algorithm: 'gzip',
test: new RegExp(
'\\.(' + productionGzipExtensions.join('|') + ')$'
),
threshold: 10240,
minRatio: 0.8
})
)
if (process.env.npm_lifecycle_event === 'analyze') {
config.plugins.push(new BundleAnalyzerPlugin())
}
} else {
// 为开发环境修改配置...
}
},
// 第三方插件的选项
pluginOptions: {}
}

@ -1,40 +0,0 @@
const path = require('path')
const webpack = require('webpack')
const CleanWebpackPlugin = require('clean-webpack-plugin')
// dll文件存放的目录
const dllPath = 'public/vendor'
module.exports = {
entry: {
// 需要提取的库文件
vendor: ['vue', 'vue-router', 'vuex', 'axios', 'element-ui']
},
output: {
path: path.join(__dirname, dllPath),
// 保证每次打包出来的文件名都是唯一的
filename: `[name].dll.${Math.ceil(Math.random() * 10000)}.js`,
// vendor.dll.js中暴露出的全局变量名
// 保持与 webpack.DllPlugin 中名称一致
library: '[name]_[hash]'
},
plugins: [
// 清除之前的dll文件
new CleanWebpackPlugin(['*.*'], {
root: path.join(__dirname, dllPath)
}),
// 设置环境变量
new webpack.DefinePlugin({
'process.env': {
NODE_ENV: 'production'
}
}),
// manifest.json 描述动态链接库包含了哪些内容
new webpack.DllPlugin({
path: path.join(__dirname, dllPath, '[name]-manifest.json'),
// 保持与 output.library 中名称一致
name: '[name]_[hash]',
context: process.cwd()
})
]
}

File diff suppressed because it is too large Load Diff

@ -1,33 +0,0 @@
HELP.md
target/
!.mvn/wrapper/maven-wrapper.jar
!**/src/main/**/target/
!**/src/test/**/target/
### STS ###
.apt_generated
.classpath
.factorypath
.project
.settings
.springBeans
.sts4-cache
### IntelliJ IDEA ###
.idea
*.iws
*.iml
*.ipr
### NetBeans ###
/nbproject/private/
/nbbuild/
/dist/
/nbdist/
/.nb-gradle/
build/
!**/src/main/**/build/
!**/src/test/**/build/
### VS Code ###
.vscode/

@ -1,118 +0,0 @@
/*
* Copyright 2007-present the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import java.net.*;
import java.io.*;
import java.nio.channels.*;
import java.util.Properties;
public class MavenWrapperDownloader {
private static final String WRAPPER_VERSION = "0.5.6";
/**
* Default URL to download the maven-wrapper.jar from, if no 'downloadUrl' is provided.
*/
private static final String DEFAULT_DOWNLOAD_URL = "https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/"
+ WRAPPER_VERSION + "/maven-wrapper-" + WRAPPER_VERSION + ".jar";
/**
* Path to the maven-wrapper.properties file, which might contain a downloadUrl property to
* use instead of the default one.
*/
private static final String MAVEN_WRAPPER_PROPERTIES_PATH =
".mvn/wrapper/maven-wrapper.properties";
/**
* Path where the maven-wrapper.jar will be saved to.
*/
private static final String MAVEN_WRAPPER_JAR_PATH =
".mvn/wrapper/maven-wrapper.jar";
/**
* Name of the property which should be used to override the default download url for the wrapper.
*/
private static final String PROPERTY_NAME_WRAPPER_URL = "wrapperUrl";
public static void main(String args[]) {
System.out.println("- Downloader started");
File baseDirectory = new File(args[0]);
System.out.println("- Using base directory: " + baseDirectory.getAbsolutePath());
// If the maven-wrapper.properties exists, read it and check if it contains a custom
// wrapperUrl parameter.
File mavenWrapperPropertyFile = new File(baseDirectory, MAVEN_WRAPPER_PROPERTIES_PATH);
String url = DEFAULT_DOWNLOAD_URL;
if (mavenWrapperPropertyFile.exists()) {
FileInputStream mavenWrapperPropertyFileInputStream = null;
try {
mavenWrapperPropertyFileInputStream = new FileInputStream(mavenWrapperPropertyFile);
Properties mavenWrapperProperties = new Properties();
mavenWrapperProperties.load(mavenWrapperPropertyFileInputStream);
url = mavenWrapperProperties.getProperty(PROPERTY_NAME_WRAPPER_URL, url);
} catch (IOException e) {
System.out.println("- ERROR loading '" + MAVEN_WRAPPER_PROPERTIES_PATH + "'");
} finally {
try {
if (mavenWrapperPropertyFileInputStream != null) {
mavenWrapperPropertyFileInputStream.close();
}
} catch (IOException e) {
// Ignore ...
}
}
}
System.out.println("- Downloading from: " + url);
File outputFile = new File(baseDirectory.getAbsolutePath(), MAVEN_WRAPPER_JAR_PATH);
if (!outputFile.getParentFile().exists()) {
if (!outputFile.getParentFile().mkdirs()) {
System.out.println(
"- ERROR creating output directory '" + outputFile.getParentFile().getAbsolutePath() + "'");
}
}
System.out.println("- Downloading to: " + outputFile.getAbsolutePath());
try {
downloadFileFromURL(url, outputFile);
System.out.println("Done");
System.exit(0);
} catch (Throwable e) {
System.out.println("- Error downloading");
e.printStackTrace();
System.exit(1);
}
}
private static void downloadFileFromURL(String urlString, File destination) throws Exception {
if (System.getenv("MVNW_USERNAME") != null && System.getenv("MVNW_PASSWORD") != null) {
String username = System.getenv("MVNW_USERNAME");
char[] password = System.getenv("MVNW_PASSWORD").toCharArray();
Authenticator.setDefault(new Authenticator() {
@Override
protected PasswordAuthentication getPasswordAuthentication() {
return new PasswordAuthentication(username, password);
}
});
}
URL website = new URL(urlString);
ReadableByteChannel rbc;
rbc = Channels.newChannel(website.openStream());
FileOutputStream fos = new FileOutputStream(destination);
fos.getChannel().transferFrom(rbc, 0, Long.MAX_VALUE);
fos.close();
rbc.close();
}
}

Binary file not shown.

@ -1,2 +0,0 @@
distributionUrl=https://repo.maven.apache.org/maven2/org/apache/maven/apache-maven/3.8.1/apache-maven-3.8.1-bin.zip
wrapperUrl=https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.5.6/maven-wrapper-0.5.6.jar

@ -1,322 +0,0 @@
#!/bin/sh
# ----------------------------------------------------------------------------
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
# KIND, either express or implied. See the License for the
# specific language governing permissions and limitations
# under the License.
# ----------------------------------------------------------------------------
# ----------------------------------------------------------------------------
# Maven Start Up Batch script
#
# Required ENV vars:
# ------------------
# JAVA_HOME - location of a JDK home dir
#
# Optional ENV vars
# -----------------
# M2_HOME - location of maven2's installed home dir
# MAVEN_OPTS - parameters passed to the Java VM when running Maven
# e.g. to debug Maven itself, use
# set MAVEN_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000
# MAVEN_SKIP_RC - flag to disable loading of mavenrc files
# ----------------------------------------------------------------------------
if [ -z "$MAVEN_SKIP_RC" ]; then
if [ -f /etc/mavenrc ]; then
. /etc/mavenrc
fi
if [ -f "$HOME/.mavenrc" ]; then
. "$HOME/.mavenrc"
fi
fi
# OS specific support. $var _must_ be set to either true or false.
cygwin=false
darwin=false
mingw=false
case "$(uname)" in
CYGWIN*) cygwin=true ;;
MINGW*) mingw=true ;;
Darwin*)
darwin=true
# Use /usr/libexec/java_home if available, otherwise fall back to /Library/Java/Home
# See https://developer.apple.com/library/mac/qa/qa1170/_index.html
if [ -z "$JAVA_HOME" ]; then
if [ -x "/usr/libexec/java_home" ]; then
export JAVA_HOME="$(/usr/libexec/java_home)"
else
export JAVA_HOME="/Library/Java/Home"
fi
fi
;;
esac
if [ -z "$JAVA_HOME" ]; then
if [ -r /etc/gentoo-release ]; then
JAVA_HOME=$(java-config --jre-home)
fi
fi
if [ -z "$M2_HOME" ]; then
## resolve links - $0 may be a link to maven's home
PRG="$0"
# need this for relative symlinks
while [ -h "$PRG" ]; do
ls=$(ls -ld "$PRG")
link=$(expr "$ls" : '.*-> \(.*\)$')
if expr "$link" : '/.*' >/dev/null; then
PRG="$link"
else
PRG="$(dirname "$PRG")/$link"
fi
done
saveddir=$(pwd)
M2_HOME=$(dirname "$PRG")/..
# make it fully qualified
M2_HOME=$(cd "$M2_HOME" && pwd)
cd "$saveddir"
# echo Using m2 at $M2_HOME
fi
# For Cygwin, ensure paths are in UNIX format before anything is touched
if $cygwin; then
[ -n "$M2_HOME" ] &&
M2_HOME=$(cygpath --unix "$M2_HOME")
[ -n "$JAVA_HOME" ] &&
JAVA_HOME=$(cygpath --unix "$JAVA_HOME")
[ -n "$CLASSPATH" ] &&
CLASSPATH=$(cygpath --path --unix "$CLASSPATH")
fi
# For Mingw, ensure paths are in UNIX format before anything is touched
if $mingw; then
[ -n "$M2_HOME" ] &&
M2_HOME="$( (
cd "$M2_HOME"
pwd
))"
[ -n "$JAVA_HOME" ] &&
JAVA_HOME="$( (
cd "$JAVA_HOME"
pwd
))"
fi
if [ -z "$JAVA_HOME" ]; then
javaExecutable="$(which javac)"
if [ -n "$javaExecutable" ] && ! [ "$(expr \"$javaExecutable\" : '\([^ ]*\)')" = "no" ]; then
# readlink(1) is not available as standard on Solaris 10.
readLink=$(which readlink)
if [ ! $(expr "$readLink" : '\([^ ]*\)') = "no" ]; then
if $darwin; then
javaHome="$(dirname \"$javaExecutable\")"
javaExecutable="$(cd \"$javaHome\" && pwd -P)/javac"
else
javaExecutable="$(readlink -f \"$javaExecutable\")"
fi
javaHome="$(dirname \"$javaExecutable\")"
javaHome=$(expr "$javaHome" : '\(.*\)/bin')
JAVA_HOME="$javaHome"
export JAVA_HOME
fi
fi
fi
if [ -z "$JAVACMD" ]; then
if [ -n "$JAVA_HOME" ]; then
if [ -x "$JAVA_HOME/jre/sh/java" ]; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD="$JAVA_HOME/jre/sh/java"
else
JAVACMD="$JAVA_HOME/bin/java"
fi
else
JAVACMD="$(which java)"
fi
fi
if [ ! -x "$JAVACMD" ]; then
echo "Error: JAVA_HOME is not defined correctly." >&2
echo " We cannot execute $JAVACMD" >&2
exit 1
fi
if [ -z "$JAVA_HOME" ]; then
echo "Warning: JAVA_HOME environment variable is not set."
fi
CLASSWORLDS_LAUNCHER=org.codehaus.plexus.classworlds.launcher.Launcher
# traverses directory structure from process work directory to filesystem root
# first directory with .mvn subdirectory is considered project base directory
find_maven_basedir() {
if [ -z "$1" ]; then
echo "Path not specified to find_maven_basedir"
return 1
fi
basedir="$1"
wdir="$1"
while [ "$wdir" != '/' ]; do
if [ -d "$wdir"/.mvn ]; then
basedir=$wdir
break
fi
# workaround for JBEAP-8937 (on Solaris 10/Sparc)
if [ -d "${wdir}" ]; then
wdir=$(
cd "$wdir/.."
pwd
)
fi
# end of workaround
done
echo "${basedir}"
}
# concatenates all lines of a file
concat_lines() {
if [ -f "$1" ]; then
echo "$(tr -s '\n' ' ' <"$1")"
fi
}
BASE_DIR=$(find_maven_basedir "$(pwd)")
if [ -z "$BASE_DIR" ]; then
exit 1
fi
##########################################################################################
# Extension to allow automatically downloading the maven-wrapper.jar from Maven-central
# This allows using the maven wrapper in projects that prohibit checking in binary data.
##########################################################################################
if [ -r "$BASE_DIR/.mvn/wrapper/maven-wrapper.jar" ]; then
if [ "$MVNW_VERBOSE" = true ]; then
echo "Found .mvn/wrapper/maven-wrapper.jar"
fi
else
if [ "$MVNW_VERBOSE" = true ]; then
echo "Couldn't find .mvn/wrapper/maven-wrapper.jar, downloading it ..."
fi
if [ -n "$MVNW_REPOURL" ]; then
jarUrl="$MVNW_REPOURL/io/takari/maven-wrapper/0.5.6/maven-wrapper-0.5.6.jar"
else
jarUrl="https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.5.6/maven-wrapper-0.5.6.jar"
fi
while IFS="=" read key value; do
case "$key" in wrapperUrl)
jarUrl="$value"
break
;;
esac
done <"$BASE_DIR/.mvn/wrapper/maven-wrapper.properties"
if [ "$MVNW_VERBOSE" = true ]; then
echo "Downloading from: $jarUrl"
fi
wrapperJarPath="$BASE_DIR/.mvn/wrapper/maven-wrapper.jar"
if $cygwin; then
wrapperJarPath=$(cygpath --path --windows "$wrapperJarPath")
fi
if command -v wget >/dev/null; then
if [ "$MVNW_VERBOSE" = true ]; then
echo "Found wget ... using wget"
fi
if [ -z "$MVNW_USERNAME" ] || [ -z "$MVNW_PASSWORD" ]; then
wget "$jarUrl" -O "$wrapperJarPath"
else
wget --http-user=$MVNW_USERNAME --http-password=$MVNW_PASSWORD "$jarUrl" -O "$wrapperJarPath"
fi
elif command -v curl >/dev/null; then
if [ "$MVNW_VERBOSE" = true ]; then
echo "Found curl ... using curl"
fi
if [ -z "$MVNW_USERNAME" ] || [ -z "$MVNW_PASSWORD" ]; then
curl -o "$wrapperJarPath" "$jarUrl" -f
else
curl --user $MVNW_USERNAME:$MVNW_PASSWORD -o "$wrapperJarPath" "$jarUrl" -f
fi
else
if [ "$MVNW_VERBOSE" = true ]; then
echo "Falling back to using Java to download"
fi
javaClass="$BASE_DIR/.mvn/wrapper/MavenWrapperDownloader.java"
# For Cygwin, switch paths to Windows format before running javac
if $cygwin; then
javaClass=$(cygpath --path --windows "$javaClass")
fi
if [ -e "$javaClass" ]; then
if [ ! -e "$BASE_DIR/.mvn/wrapper/MavenWrapperDownloader.class" ]; then
if [ "$MVNW_VERBOSE" = true ]; then
echo " - Compiling MavenWrapperDownloader.java ..."
fi
# Compiling the Java class
("$JAVA_HOME/bin/javac" "$javaClass")
fi
if [ -e "$BASE_DIR/.mvn/wrapper/MavenWrapperDownloader.class" ]; then
# Running the downloader
if [ "$MVNW_VERBOSE" = true ]; then
echo " - Running MavenWrapperDownloader.java ..."
fi
("$JAVA_HOME/bin/java" -cp .mvn/wrapper MavenWrapperDownloader "$MAVEN_PROJECTBASEDIR")
fi
fi
fi
fi
##########################################################################################
# End of extension
##########################################################################################
export MAVEN_PROJECTBASEDIR=${MAVEN_BASEDIR:-"$BASE_DIR"}
if [ "$MVNW_VERBOSE" = true ]; then
echo $MAVEN_PROJECTBASEDIR
fi
MAVEN_OPTS="$(concat_lines "$MAVEN_PROJECTBASEDIR/.mvn/jvm.config") $MAVEN_OPTS"
# For Cygwin, switch paths to Windows format before running java
if $cygwin; then
[ -n "$M2_HOME" ] &&
M2_HOME=$(cygpath --path --windows "$M2_HOME")
[ -n "$JAVA_HOME" ] &&
JAVA_HOME=$(cygpath --path --windows "$JAVA_HOME")
[ -n "$CLASSPATH" ] &&
CLASSPATH=$(cygpath --path --windows "$CLASSPATH")
[ -n "$MAVEN_PROJECTBASEDIR" ] &&
MAVEN_PROJECTBASEDIR=$(cygpath --path --windows "$MAVEN_PROJECTBASEDIR")
fi
# Provide a "standardized" way to retrieve the CLI args that will
# work with both Windows and non-Windows executions.
MAVEN_CMD_LINE_ARGS="$MAVEN_CONFIG $@"
export MAVEN_CMD_LINE_ARGS
WRAPPER_LAUNCHER=org.apache.maven.wrapper.MavenWrapperMain
exec "$JAVACMD" \
$MAVEN_OPTS \
-classpath "$MAVEN_PROJECTBASEDIR/.mvn/wrapper/maven-wrapper.jar" \
"-Dmaven.home=${M2_HOME}" "-Dmaven.multiModuleProjectDirectory=${MAVEN_PROJECTBASEDIR}" \
${WRAPPER_LAUNCHER} $MAVEN_CONFIG "$@"

@ -1,182 +0,0 @@
@REM ----------------------------------------------------------------------------
@REM Licensed to the Apache Software Foundation (ASF) under one
@REM or more contributor license agreements. See the NOTICE file
@REM distributed with this work for additional information
@REM regarding copyright ownership. The ASF licenses this file
@REM to you under the Apache License, Version 2.0 (the
@REM "License"); you may not use this file except in compliance
@REM with the License. You may obtain a copy of the License at
@REM
@REM https://www.apache.org/licenses/LICENSE-2.0
@REM
@REM Unless required by applicable law or agreed to in writing,
@REM software distributed under the License is distributed on an
@REM "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
@REM KIND, either express or implied. See the License for the
@REM specific language governing permissions and limitations
@REM under the License.
@REM ----------------------------------------------------------------------------
@REM ----------------------------------------------------------------------------
@REM Maven Start Up Batch script
@REM
@REM Required ENV vars:
@REM JAVA_HOME - location of a JDK home dir
@REM
@REM Optional ENV vars
@REM M2_HOME - location of maven2's installed home dir
@REM MAVEN_BATCH_ECHO - set to 'on' to enable the echoing of the batch commands
@REM MAVEN_BATCH_PAUSE - set to 'on' to wait for a keystroke before ending
@REM MAVEN_OPTS - parameters passed to the Java VM when running Maven
@REM e.g. to debug Maven itself, use
@REM set MAVEN_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000
@REM MAVEN_SKIP_RC - flag to disable loading of mavenrc files
@REM ----------------------------------------------------------------------------
@REM Begin all REM lines with '@' in case MAVEN_BATCH_ECHO is 'on'
@echo off
@REM set title of command window
title %0
@REM enable echoing by setting MAVEN_BATCH_ECHO to 'on'
@if "%MAVEN_BATCH_ECHO%" == "on" echo %MAVEN_BATCH_ECHO%
@REM set %HOME% to equivalent of $HOME
if "%HOME%" == "" (set "HOME=%HOMEDRIVE%%HOMEPATH%")
@REM Execute a user defined script before this one
if not "%MAVEN_SKIP_RC%" == "" goto skipRcPre
@REM check for pre script, once with legacy .bat ending and once with .cmd ending
if exist "%HOME%\mavenrc_pre.bat" call "%HOME%\mavenrc_pre.bat"
if exist "%HOME%\mavenrc_pre.cmd" call "%HOME%\mavenrc_pre.cmd"
:skipRcPre
@setlocal
set ERROR_CODE=0
@REM To isolate internal variables from possible post scripts, we use another setlocal
@setlocal
@REM ==== START VALIDATION ====
if not "%JAVA_HOME%" == "" goto OkJHome
echo.
echo Error: JAVA_HOME not found in your environment. >&2
echo Please set the JAVA_HOME variable in your environment to match the >&2
echo location of your Java installation. >&2
echo.
goto error
:OkJHome
if exist "%JAVA_HOME%\bin\java.exe" goto init
echo.
echo Error: JAVA_HOME is set to an invalid directory. >&2
echo JAVA_HOME = "%JAVA_HOME%" >&2
echo Please set the JAVA_HOME variable in your environment to match the >&2
echo location of your Java installation. >&2
echo.
goto error
@REM ==== END VALIDATION ====
:init
@REM Find the project base dir, i.e. the directory that contains the folder ".mvn".
@REM Fallback to current working directory if not found.
set MAVEN_PROJECTBASEDIR=%MAVEN_BASEDIR%
IF NOT "%MAVEN_PROJECTBASEDIR%"=="" goto endDetectBaseDir
set EXEC_DIR=%CD%
set WDIR=%EXEC_DIR%
:findBaseDir
IF EXIST "%WDIR%"\.mvn goto baseDirFound
cd ..
IF "%WDIR%"=="%CD%" goto baseDirNotFound
set WDIR=%CD%
goto findBaseDir
:baseDirFound
set MAVEN_PROJECTBASEDIR=%WDIR%
cd "%EXEC_DIR%"
goto endDetectBaseDir
:baseDirNotFound
set MAVEN_PROJECTBASEDIR=%EXEC_DIR%
cd "%EXEC_DIR%"
:endDetectBaseDir
IF NOT EXIST "%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config" goto endReadAdditionalConfig
@setlocal EnableExtensions EnableDelayedExpansion
for /F "usebackq delims=" %%a in ("%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config") do set JVM_CONFIG_MAVEN_PROPS=!JVM_CONFIG_MAVEN_PROPS! %%a
@endlocal & set JVM_CONFIG_MAVEN_PROPS=%JVM_CONFIG_MAVEN_PROPS%
:endReadAdditionalConfig
SET MAVEN_JAVA_EXE="%JAVA_HOME%\bin\java.exe"
set WRAPPER_JAR="%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.jar"
set WRAPPER_LAUNCHER=org.apache.maven.wrapper.MavenWrapperMain
set DOWNLOAD_URL="https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.5.6/maven-wrapper-0.5.6.jar"
FOR /F "tokens=1,2 delims==" %%A IN ("%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.properties") DO (
IF "%%A"=="wrapperUrl" SET DOWNLOAD_URL=%%B
)
@REM Extension to allow automatically downloading the maven-wrapper.jar from Maven-central
@REM This allows using the maven wrapper in projects that prohibit checking in binary data.
if exist %WRAPPER_JAR% (
if "%MVNW_VERBOSE%" == "true" (
echo Found %WRAPPER_JAR%
)
) else (
if not "%MVNW_REPOURL%" == "" (
SET DOWNLOAD_URL="%MVNW_REPOURL%/io/takari/maven-wrapper/0.5.6/maven-wrapper-0.5.6.jar"
)
if "%MVNW_VERBOSE%" == "true" (
echo Couldn't find %WRAPPER_JAR%, downloading it ...
echo Downloading from: %DOWNLOAD_URL%
)
powershell -Command "&{"^
"$webclient = new-object System.Net.WebClient;"^
"if (-not ([string]::IsNullOrEmpty('%MVNW_USERNAME%') -and [string]::IsNullOrEmpty('%MVNW_PASSWORD%'))) {"^
"$webclient.Credentials = new-object System.Net.NetworkCredential('%MVNW_USERNAME%', '%MVNW_PASSWORD%');"^
"}"^
"[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12; $webclient.DownloadFile('%DOWNLOAD_URL%', '%WRAPPER_JAR%')"^
"}"
if "%MVNW_VERBOSE%" == "true" (
echo Finished downloading %WRAPPER_JAR%
)
)
@REM End of extension
@REM Provide a "standardized" way to retrieve the CLI args that will
@REM work with both Windows and non-Windows executions.
set MAVEN_CMD_LINE_ARGS=%*
%MAVEN_JAVA_EXE% %JVM_CONFIG_MAVEN_PROPS% %MAVEN_OPTS% %MAVEN_DEBUG_OPTS% -classpath %WRAPPER_JAR% "-Dmaven.multiModuleProjectDirectory=%MAVEN_PROJECTBASEDIR%" %WRAPPER_LAUNCHER% %MAVEN_CONFIG% %*
if ERRORLEVEL 1 goto error
goto end
:error
set ERROR_CODE=1
:end
@endlocal & set ERROR_CODE=%ERROR_CODE%
if not "%MAVEN_SKIP_RC%" == "" goto skipRcPost
@REM check for post script, once with legacy .bat ending and once with .cmd ending
if exist "%HOME%\mavenrc_post.bat" call "%HOME%\mavenrc_post.bat"
if exist "%HOME%\mavenrc_post.cmd" call "%HOME%\mavenrc_post.cmd"
:skipRcPost
@REM pause the script if MAVEN_BATCH_PAUSE is set to 'on'
if "%MAVEN_BATCH_PAUSE%" == "on" pause
if "%MAVEN_TERMINATE_CMD%" == "on" exit %ERROR_CODE%
exit /B %ERROR_CODE%

@ -1,126 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.0</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.example</groupId>
<artifactId>demo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>demo</name>
<description>recommend project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<!--mybatis-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.3.1.tmp</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.18</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.10</version>
</dependency>
<!-- 添加 模板引擎 依赖 -->
<dependency>
<groupId>org.apache.velocity</groupId>
<artifactId>velocity-engine-core</artifactId>
<version>2.2</version>
</dependency>
<!--代码生成器-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-generator</artifactId>
<version>3.3.1.tmp</version>
</dependency>
<!--Swagger-->
<dependency>
<groupId>com.spring4all</groupId>
<artifactId>swagger-spring-boot-starter</artifactId>
<version>1.7.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--使用日志slf4j+logback-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-logging</artifactId>
</dependency>
<!--使用aop-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-aop</artifactId>
</dependency>
<!--spring整合shiro-->
<dependency>
<groupId>org.apache.shiro</groupId>
<artifactId>shiro-spring</artifactId>
<version>1.4.0</version>
</dependency>
<!--fastjson Json处理工具包-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.76</version>
</dependency>
<!-- redis-->
<dependency>
<groupId>redis.clients</groupId>
<artifactId>jedis</artifactId>
<version>3.6.3</version>
</dependency>
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-redis</artifactId>
<version>2.5.3</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
<version>1.4.1.RELEASE</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.xml</include>
</includes>
</resource>
<resource>
<directory>src/main/resources</directory>
</resource>
</resources>
</build>
</project>

@ -1,15 +0,0 @@
package com.example.demo;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cache.annotation.EnableCaching;
@SpringBootApplication
@MapperScan("com.example.demo.mapper")
@EnableCaching
public class DemoApplication {
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
}

@ -1,50 +0,0 @@
package com.example.demo.config;
import org.apache.shiro.web.filter.authc.FormAuthenticationFilter;
import org.springframework.http.HttpStatus;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
// 过滤OPTIONS请求继承shiro的form表单过滤器对OPTIONS请求进行过滤复杂请求中OPTIONS请求不带token信息不能通过shiro认证
public class CORSAuthenticationFilter extends FormAuthenticationFilter {
private static final String REQUEST_TYPE = "OPTIONS";
public CORSAuthenticationFilter(){
super();
}
@Override
public boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue){
if (((HttpServletRequest) request).getMethod().toUpperCase().equals(REQUEST_TYPE)) {
return true;
}
return super.isAccessAllowed(request, response, mappedValue);
}
@Override
protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws Exception{
HttpServletResponse res = (HttpServletResponse)response;
HttpServletRequest req = (HttpServletRequest)request;
res.addHeader("Access-Control-Allow-Origin", req.getHeader("origin"));
setHeader(req,res);
res.setStatus(HttpServletResponse.SC_OK);
res.setCharacterEncoding("UTF-8");
return false;
}
// 为response设置header实现跨域
private void setHeader(HttpServletRequest request,HttpServletResponse response){
// 跨域的header设置
response.setHeader("Access-control-Allow-Origin", request.getHeader("Origin"));
response.setHeader("Access-Control-Allow-Methods", request.getMethod());
response.setHeader("Access-Control-Allow-Credentials", "true");
response.setHeader("Access-Control-Allow-Headers", request.getHeader("Access-Control-Request-Headers"));
// 防止乱码适用于传输JSON数据
// Content-Type, Content-Length, Authorization, Accept, X-Requested-With, yourHeaderField
response.setHeader("Content-Type","application/json;charset=UTF-8");
response.setStatus(HttpStatus.OK.value());
}
}

@ -1,32 +0,0 @@
package com.example.demo.config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
import org.springframework.web.filter.CorsFilter;
// 跨域访问控制
@Configuration
public class CorsConfig {
private CorsConfiguration buildConfig(){
CorsConfiguration corsConfiguration=new CorsConfiguration();
// 允许任何域名使用
corsConfiguration.addAllowedOriginPattern("*");
// 允许任何请求头使用
corsConfiguration.addAllowedHeader("*");
// 允许任何方法
corsConfiguration.addAllowedMethod("*");
// 允许携带信息
corsConfiguration.setAllowCredentials(true);
return corsConfiguration;
}
@Bean
public CorsFilter corsFilter(){
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
// 对接口配置跨域设置
source.registerCorsConfiguration("/**", buildConfig());
return new CorsFilter(source);
}
}

@ -1,66 +0,0 @@
package com.example.demo.config;
import com.example.demo.entity.Permission;
import com.example.demo.entity.Role;
import com.example.demo.entity.User;
import com.example.demo.service.UserService;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.authc.AuthenticationToken;
import org.apache.shiro.authc.SimpleAuthenticationInfo;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.util.ByteSource;
import org.springframework.beans.factory.annotation.Autowired;
import java.util.ArrayList;
import java.util.List;
public class EnceladusShiroRealm extends AuthorizingRealm {
@Autowired
private UserService userService;
// 进行权限校验时调用
@Override
protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection){
SimpleAuthorizationInfo simpleAuthorizationInfo=new SimpleAuthorizationInfo();
String userName=(String) principalCollection.getPrimaryPrincipal();
User user=userService.findAllUserInfoByUsername(userName);
List<String> stringRoleList=new ArrayList<>();
List<String> stringPermissionList=new ArrayList<>();
List<Role> roleList=user.getRoleList();
for(Role role:roleList){
stringRoleList.add(role.getName());
List<Permission> permissionList=role.getPermissionList();
for(Permission p:permissionList){
if (null != p) {
stringPermissionList.add(p.getName());
}
}
}
simpleAuthorizationInfo.addRoles(stringRoleList);
simpleAuthorizationInfo.addStringPermissions(stringPermissionList);
SecurityUtils.getSubject().getSession().setAttribute("roleList", stringRoleList);
return simpleAuthorizationInfo;
}
// 登录校验调用
@Override
protected SimpleAuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
String username=(String) token.getPrincipal();
System.out.println("principal:"+username);
User user=userService.findAllUserInfoByUsername(username);
System.out.println("principal password:"+user.getPassWord());
String passWord=user.getPassWord();
if(null==passWord|| "".equals(passWord)){
return null;
}
return new SimpleAuthenticationInfo(user.getUserName(), user.getPassWord(), ByteSource.Util.bytes(user.getSalt()), getName());
}
}

@ -1,86 +0,0 @@
package com.example.demo.config;
import com.example.demo.util.PasswordHelper;
import org.apache.shiro.authc.credential.HashedCredentialsMatcher;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.session.mgt.SessionManager;
import org.apache.shiro.session.mgt.eis.EnterpriseCacheSessionDAO;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.servlet.Filter;
import java.util.LinkedHashMap;
import java.util.Map;
@Configuration
public class ShiroConfig {
@Bean
public ShiroFilterFactoryBean shiroFilterFactoryBean(SecurityManager securityManager){
ShiroFilterFactoryBean shiroFilterFactoryBean=new ShiroFilterFactoryBean();
shiroFilterFactoryBean.setSecurityManager(securityManager);
Map<String, Filter> customFilterMap = new LinkedHashMap<>();
customFilterMap.put("corsAuthenticationFilter",new CORSAuthenticationFilter());
shiroFilterFactoryBean.setFilters(customFilterMap);
Map<String,String> filterChainDefinitionMap=new LinkedHashMap<>();
//author url定义必须通过认证才可以访问
//anon url可以匿名访问
shiroFilterFactoryBean.setLoginUrl("/login");
shiroFilterFactoryBean.setUnauthorizedUrl("/unauthor");
shiroFilterFactoryBean.setSuccessUrl("/home/index");
// 过滤器 按照顺序进行拦截
// author 所有已登陆用户可访问
// roles 有指定角色的用户可访问,通过[ ]指定具体角色,这里的角色名称与数据库中配置一致
// perms 有指定权限的用户可访问,通过[ ]指定具体权限,这里的权限名称与数据库中配置一致
// anon 所有用户可访问,通常作为指定页面的静态资源时使用
filterChainDefinitionMap.put("/*", "anon");
filterChainDefinitionMap.put("/logout","logout");
filterChainDefinitionMap.put("/login","anon");
filterChainDefinitionMap.put("/cart","roles[member]");
filterChainDefinitionMap.put("/myOrder","roles[member]");
shiroFilterFactoryBean.setFilterChainDefinitionMap(filterChainDefinitionMap);
return shiroFilterFactoryBean;
}
@Bean
public HashedCredentialsMatcher hashedCredentialsMatcher(){
HashedCredentialsMatcher hashedCredentialsMatcher=new HashedCredentialsMatcher();
hashedCredentialsMatcher.setHashAlgorithmName(PasswordHelper.ALGORITHM_NAME);
hashedCredentialsMatcher.setHashIterations(PasswordHelper.HASH_ITERATIONS);
return hashedCredentialsMatcher;
}
@Bean
public EnceladusShiroRealm shiroRealm(){
EnceladusShiroRealm enceladusShiroRealm=new EnceladusShiroRealm();
enceladusShiroRealm.setCredentialsMatcher(hashedCredentialsMatcher());
return enceladusShiroRealm;
}
@Bean
public SecurityManager securityManager(){
DefaultWebSecurityManager securityManager=new DefaultWebSecurityManager();
securityManager.setRealm(shiroRealm());
securityManager.setSessionManager(sessionManager());
return securityManager;
}
@Bean
public PasswordHelper passwordHelper(){
return new PasswordHelper();
}
// 将重写的shiro session注册
@Bean
public SessionManager sessionManager(){
ShiroSession shiroSession=new ShiroSession();
shiroSession.setSessionDAO(new EnterpriseCacheSessionDAO());
return shiroSession;
}
}

@ -1,39 +0,0 @@
package com.example.demo.config;
import org.apache.shiro.web.servlet.ShiroHttpServletRequest;
import org.apache.shiro.web.session.mgt.DefaultWebSessionManager;
import org.apache.shiro.web.util.WebUtils;
import org.springframework.util.StringUtils;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import java.io.Serializable;
public class ShiroSession extends DefaultWebSessionManager {
// 定义的请求头中使用的标记key用来传递token
private static final String AUTH_TOKEN = "authToken";
private static final String REFERENCED_SESSION_ID_SOURCE = "Stateless request";
public ShiroSession(){
super();
}
@Override
protected Serializable getSessionId(ServletRequest request, ServletResponse response){
// 获取请求头中对token值即为sessionId
String sessionId = WebUtils.toHttp(request).getHeader(AUTH_TOKEN);
System.out.println("请求头中的token:"+sessionId);
if(StringUtils.isEmpty(sessionId)){
// 没有携带token根据父类方法获取sessionId
return super.getSessionId(request,response);
}else {
// 请求头中如果有authToken则其值为sessionId
request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID_SOURCE, REFERENCED_SESSION_ID_SOURCE);
// sessionId
request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID, sessionId);
request.setAttribute(ShiroHttpServletRequest.REFERENCED_SESSION_ID_IS_VALID, Boolean.TRUE);
return sessionId;
}
}
}

@ -1,15 +0,0 @@
package com.example.demo.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
@Configuration
public class WebMvcConfig implements WebMvcConfigurer {
// 配置图片路径
@Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
// 和页面有关的图片放在项目的img目录下
registry.addResourceHandler("/img/**").addResourceLocations("classpath:/img/");
}
}

@ -1,115 +0,0 @@
package com.example.demo.controller;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.demo.entity.CartItem;
import com.example.demo.entity.Goods;
import com.example.demo.entity.User;
import com.example.demo.service.CartItemService;
import com.example.demo.service.GoodsService;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;
@RestController
@RequestMapping("/cart")
public class CartItemController {
@Autowired
private CartItemService cartItemService;
@Autowired
private GoodsService goodsService;
// 添加租赁物品到购物车
@RequestMapping("/add")
@Transactional(rollbackFor = {RuntimeException.class, Error.class})
public String add(@RequestBody Map<String,Object> map){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
Integer goodsId= (Integer) map.get("goodsId");
QueryWrapper<Goods> goodsQueryWrapper=new QueryWrapper<>();
goodsQueryWrapper.eq("goods_id",goodsId);
Goods goods=goodsService.getOne(goodsQueryWrapper);
System.out.println(goods);
CartItem cartItem=new CartItem();
cartItem.setUserId(user.getUserId());
cartItem.setGoodsId(goods.getGoodsId());
cartItem.setGoodsCount(1);
cartItem.setIsDeleted(0);
cartItem.setPrice(goods.getGoodsPrice());
cartItem.setGoodsCoverImg(goods.getGoodsCoverImg());
cartItem.setGoodsName(goods.getGoodsName());
System.out.println(cartItem);
cartItemService.save(cartItem);
return cartItem.getCartItemId().toString();
}else {
return "fail";
}
}
// 读取购物车
@RequestMapping("/list")
public String list(){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
Integer id=user.getUserId();
System.out.println("id:"+id);
QueryWrapper<CartItem> wrapper = new QueryWrapper<>();
wrapper.eq("user_id",id);
List<CartItem> cartItemList=cartItemService.list(wrapper);
System.out.println(cartItemList.toString());
return JSON.toJSONString(cartItemList);
}else {
return "fail";
}
}
// 删除购物车租赁物品
@RequestMapping("/delete")
public String delete(@RequestBody Map<String, Object> map){
Integer itemId= (Integer) map.get("cartItemId");
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
Integer id=user.getUserId();
System.out.println("id:"+id);
QueryWrapper<CartItem> wrapper = new QueryWrapper<>();
wrapper.and(i->i.eq("user_id",id).eq("cart_item_id",itemId));
boolean isDelete=cartItemService.remove(wrapper);
if(isDelete){
return "success";
}else {
return "fail";
}
}else {
return "fail";
}
}
// 修改购物车项目
@RequestMapping("/update")
public String update(@RequestBody CartItem cartItem){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
Integer id=user.getUserId();
Integer carItemId=cartItem.getCartItemId();
System.out.println("id:"+id);
QueryWrapper<CartItem> wrapper = new QueryWrapper<>();
wrapper.and(i->i.eq("user_id",id).eq("cart_item_id", carItemId));
boolean isUpdate=cartItemService.update(cartItem,wrapper);
if(isUpdate){
return "success";
}else {
return "fail";
}
}else {
return "fail";
}
}
}

@ -1,45 +0,0 @@
package com.example.demo.controller;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.demo.entity.Category;
import com.example.demo.service.CategoryService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@RestController
@RequestMapping("/category")
public class CategoryController {
@Autowired
private CategoryService categoryService;
// 列出所有分类
@RequestMapping("/list")
public String list(){
QueryWrapper<Category> wrapper = new QueryWrapper<>();
QueryWrapper<Category> childrenWrapper = new QueryWrapper<>();
Map<String,Object> result=new HashMap<>();
wrapper.eq("parent_id", 0);
List<Category> categoryParentList=categoryService.list(wrapper);
childrenWrapper.ne("parent_id", 0);
List<Category> categoryChildrenList=categoryService.list(childrenWrapper);
result.put("categoryParentList",categoryParentList);
result.put("categoryChildrenList",categoryChildrenList);
return JSON.toJSONString(result);
}
// 列出所有子分类
@RequestMapping("/listChildrenCategory")
public String listChildrenCategory(){
QueryWrapper<Category> childrenWrapper = new QueryWrapper<>();
childrenWrapper.eq("category_level", 2);
List<Category> categoryChildrenList=categoryService.list(childrenWrapper);
return JSON.toJSONString(categoryChildrenList);
}
}

@ -1,83 +0,0 @@
package com.example.demo.controller;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.demo.entity.Entrust;
import com.example.demo.entity.User;
import com.example.demo.service.EntrustService;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;
@RestController
@RequestMapping("/entrust")
public class EntrustController {
@Autowired
private EntrustService entrustService;
// 用户发布一个委托
@RequestMapping("/add")
public String add(@RequestBody Map<String,Object> entrustMap){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
Entrust entrust=new Entrust();
entrust.setEGoodsName((String) entrustMap.get("eGoodsName"));
entrust.setEGoodsIntro((String) entrustMap.get("eGoodsIntro"));
entrust.setEGoodsCategory((Integer) entrustMap.get("eGoodsCategory"));
entrust.setEGoodsCoverImg((String) entrustMap.get("eGoodsCoverImg"));
entrust.setEGoodsCarousel((String) entrustMap.get("eGoodsCarousel"));
entrust.setEGoodsDetailContent((String) entrustMap.get("eGoodsDetailContent"));
entrust.setEGoodsPrice(Double.parseDouble((String) entrustMap.get("eGoodsPrice")));
entrust.setEStockNum((Integer) entrustMap.get("eStockNum"));
System.out.println(entrust);
entrustService.save(entrust);
return entrust.getEntrustId().toString();
}else {
return "fail";
}
}
// 列出所有委托
@RequestMapping("/list")
public String list(){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
boolean isAdmin=SecurityUtils.getSubject().hasRole("admin");
if(null!=user){
if(isAdmin){
List<Entrust> entrustList=entrustService.list();
return JSON.toJSONString(entrustList);
}else {
return "fail";
}
}else {
return "fail";
}
}
// 根据用户id列出委托
@RequestMapping("/listById")
public String listById(@RequestBody Map<String,Object> map){
Integer id= (Integer) map.get("entrustId");
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
System.out.println("编辑委托:"+id);
boolean isAdmin=SecurityUtils.getSubject().hasRole("admin");
if(null!=user){
if(isAdmin){
QueryWrapper<Entrust> entrustQueryWrapper = new QueryWrapper<>();
entrustQueryWrapper.eq("entrust_id",id);
Entrust entrust=entrustService.getOne(entrustQueryWrapper);
return JSON.toJSONString(entrust);
}else {
return "fail";
}
}else {
return "fail";
}
}
}

@ -1,55 +0,0 @@
package com.example.demo.controller;
import com.example.demo.entity.User;
import org.apache.shiro.SecurityUtils;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import java.io.File;
import java.io.IOException;
import java.util.UUID;
@RestController
@RequestMapping("/file")
public class FileController {
@RequestMapping("/upload")
public String fileUpload(@RequestParam(value = "img") MultipartFile file){
System.out.println("进入上传");
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
System.out.println(user);
if(null!=user){
if(file.isEmpty()){
System.out.println("文件是空的");
return "fail";
}
System.out.println("有文件");
// 文件名
String fileName = file.getOriginalFilename();
System.out.println(fileName);
// 后缀名
// String suffixName = fileName.substring(fileName.lastIndexOf("."));
// 上传后的路径
String filePath = "/project/gitProject_recommend/src/demo/backend/target/classes/img/";
// 新文件名
UUID uuid=UUID.randomUUID();
fileName = uuid + ".jpg";
System.out.println(fileName);
File dest = new File(filePath + fileName);
if (!dest.getParentFile().exists()) {
dest.getParentFile().mkdirs();
}
try {
file.transferTo(dest);
} catch (IOException e) {
e.printStackTrace();
}
return uuid.toString();
}else {
System.out.println("没有用户");
}
return null;
}
}

@ -1,93 +0,0 @@
package com.example.demo.controller;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.demo.entity.Goods;
import com.example.demo.entity.User;
import com.example.demo.service.EntrustService;
import com.example.demo.service.GoodsService;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;
@RestController
@RequestMapping("/goods")
public class GoodsController {
@Autowired
private GoodsService goodsService;
@Autowired
private EntrustService entrustService;
// 根据关键字搜索租赁物品
@RequestMapping("/search")
@Cacheable(value = "platRedis",key = "#map")
public String search(@RequestBody Map<String,Object> map){
String key= (String) map.get("key");
QueryWrapper<Goods> wrapper = new QueryWrapper<>();
wrapper.like("goods_name",key);
System.out.println(key);
List<Goods> goodsList=goodsService.list(wrapper);
return JSON.toJSONString(goodsList);
}
// 获取物品详情
@RequestMapping("/detail")
public String detail(@RequestBody Map<String,Object> map){
Integer key= (Integer) map.get("key");
QueryWrapper<Goods> wrapper = new QueryWrapper<>();
wrapper.eq("goods_id",key);
System.out.println(key);
Goods goods=goodsService.getOne(wrapper);
return JSON.toJSONString(goods);
}
// 从委托添加租赁物品
@RequestMapping("/add")
@Transactional(rollbackFor = {RuntimeException.class, Error.class})
public String add(@RequestBody Map<String,Object> map){
Goods goods=JSON.parseObject(JSON.toJSONString(map.get("entrust")),Goods.class);
Double price=Double.valueOf((Integer)map.get("itPrice"));
Integer entrustId=(Integer)map.get("entrustId");
goods.setGoodsPrice(price);
System.out.println(price);
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
boolean isAdmin=SecurityUtils.getSubject().hasRole("admin");
if(null!=user){
if(isAdmin){
System.out.println(goods);
goods.setGoodsStatus(1);
goodsService.save(goods);
entrustService.removeById(entrustId);
return goods.getGoodsId().toString();
}else {
return "not admin";
}
}else {
return "fail";
}
}
@RequestMapping("/searchByOrder")
public String searchByOrder(@RequestBody Map<String,Object> map){
String key= (String) map.get("key");
String order= (String) map.get("order");
QueryWrapper<Goods> wrapper = new QueryWrapper<>();
wrapper.like("goods_name",key);
wrapper.orderByAsc(order);
System.out.println(key);
List<Goods> goodsList=goodsService.list(wrapper);
return JSON.toJSONString(goodsList);
}
}

@ -1,91 +0,0 @@
package com.example.demo.controller;
import com.example.demo.entity.User;
import com.example.demo.entity.UserRole;
import com.example.demo.service.UserRoleService;
import com.example.demo.service.UserService;
import com.example.demo.util.PasswordHelper;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.IncorrectCredentialsException;
import org.apache.shiro.authc.UnknownAccountException;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.io.Serializable;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Map;
@RestController
@RequestMapping("/home")
public class HomeController {
@Autowired
private UserService userService;
@Autowired
private UserRoleService userRoleService;
@Autowired
public PasswordHelper passwordHelper;
// 登录
@RequestMapping("/login")
public String login(@RequestBody Map<String,Object> map){
String userName= (String) map.get("userName");
String passWord= (String) map.get("passWord");
UsernamePasswordToken usernamePasswordToken=new UsernamePasswordToken(userName,passWord);
Subject subject= SecurityUtils.getSubject();
try{
System.out.println("执行login前:");
subject.login(usernamePasswordToken);
}catch (IncorrectCredentialsException ice){
return "password error!";
}catch (UnknownAccountException uae){
return "username error!";
}
User user=userService.findAllUserInfoByUsername(userName);
subject.getSession().setAttribute("user",user);
Serializable tokenId = subject.getSession().getId();
boolean isAdmin=SecurityUtils.getSubject().hasRole("admin");
System.out.println(isAdmin);
System.out.println(SecurityUtils.getSubject().getSession().getAttribute("roleList"));
return String.valueOf(tokenId);
}
// 注册
@RequestMapping("/register")
@Transactional(rollbackFor = {RuntimeException.class, Error.class})
public String register(@RequestBody User user){
System.out.println(user);
Date d = new Date();
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
user.setCreateTime(sdf.format(d));
passwordHelper.encryptPassword(user);
userService.register(user);
UserRole userRole=new UserRole();
userRole.setUserId(user.getUserId());
userRole.setRoleId(1);
userRoleService.save(userRole);
if(null!=user.getUserId()){
return "success";
}
return "fail";
}
// 登出
@RequestMapping("/logout")
public String register(){
Subject subject = SecurityUtils.getSubject();
subject.logout();
return "logout success";
}
}

@ -1,35 +0,0 @@
package com.example.demo.controller;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.demo.entity.IndexConfig;
import com.example.demo.service.IndexConfigService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;
@RestController
@RequestMapping("/index-config")
public class IndexConfigController {
@Autowired
private IndexConfigService indexConfigService;
// 获取推荐列表
@RequestMapping("/list")
public String list(@RequestBody Map<String,Object> map){
Integer indexType= (Integer) map.get("indexType");
QueryWrapper<IndexConfig> indexConfigQueryWrapper=new QueryWrapper<>();
indexConfigQueryWrapper.eq("config_type",indexType);
List<IndexConfig> indexConfigList= indexConfigService.list(indexConfigQueryWrapper);
if(null!=indexConfigList){
return JSON.toJSONString(indexConfigList);
}else {
return "fail";
}
}
}

@ -1,151 +0,0 @@
package com.example.demo.controller;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.example.demo.entity.CartItem;
import com.example.demo.entity.Order;
import com.example.demo.entity.OrderItem;
import com.example.demo.entity.User;
import com.example.demo.service.CartItemService;
import com.example.demo.service.OrderItemService;
import com.example.demo.service.OrderService;
import org.apache.shiro.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Random;
@RestController
@RequestMapping("/order")
public class OrderController {
@Autowired
private OrderService orderService;
@Autowired
private OrderItemService orderItemService;
@Autowired
private CartItemService cartItemService;
// 添加订单
@RequestMapping("/add")
public String add(@RequestBody Order order){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
System.out.println(order);
order.setUserId(user.getUserId());
order.setUserAddress(user.getAddress());
order.setUserName(user.getUserName());
order.setUserPhone(user.getPhone());
order.setOrderNum(createNum());
orderService.save(order);
return order.getOrderId().toString();
}else {
return "fail";
}
}
// 根据用户列出订单列表
@RequestMapping("/listByUser")
public String listByUser(){
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
System.out.println(user.getUserId());
QueryWrapper<Order> wrapper = new QueryWrapper<>();
wrapper.eq("user_id",user.getUserId());
List<Order> orderList=orderService.list(wrapper);
for(Order order : orderList){
if(null!=order.getOrderId()){
QueryWrapper<OrderItem> orderItemWrapper = new QueryWrapper<>();
orderItemWrapper.eq("order_id",order.getOrderId());
List<OrderItem> orderItemList=orderItemService.list(orderItemWrapper);
order.setOrderItemList(orderItemList);
}
}
return JSON.toJSONString(orderList);
}else {
return "fail";
}
}
// 随机生成订单号
private String createNum(){
// 获取当前时间
SimpleDateFormat dmDate = new SimpleDateFormat("yyyyMMddHHmmss");
// 定义随机数
Random random = new Random();
// 随机数长度位数
int ran = random.nextInt(1000000);
Date date = new Date();
String dateran = dmDate.format(date);
String randomMath = dateran+ran;
return randomMath;
}
// 从购物车直接下单
@RequestMapping("/addOrderByCart")
@Transactional(rollbackFor = {RuntimeException.class, Error.class})
public String addOrderByCart(@RequestBody Map<String,Object> map) throws ParseException {
List<CartItem> cartItemList=JSON.parseArray(JSON.toJSONString(map.get("cartItemList")), CartItem.class);
Double totalPrice= Double.parseDouble((String) map.get("totalPrice"));
User user = (User) SecurityUtils.getSubject().getSession().getAttribute("user");
if(null!=user){
System.out.println(cartItemList);
System.out.println(totalPrice);
Order order=new Order();
order.setOrderNum(createNum());
order.setUserId(user.getUserId());
order.setTotalPrice(totalPrice);
order.setPayStatus(1);
Date dNow = new Date( );
SimpleDateFormat ft = new SimpleDateFormat ("yyyy-MM-dd hh:mm:ss");
order.setPayTime(ft.format(dNow));
order.setOrderStatus(1);
order.setUserName(user.getUserName());
order.setUserPhone(user.getPhone());
order.setUserAddress(user.getAddress());
order.setCreateTime(ft.format(dNow));
boolean isSaveOrder=orderService.save(order);
if(isSaveOrder){
Integer orderId=order.getOrderId();
for(CartItem item:cartItemList){
OrderItem tmp=new OrderItem();
tmp.setOrderId(orderId);
tmp.setGoodsId(item.getGoodsId());
tmp.setGoodsName(item.getGoodsName());
tmp.setGoodsCoverImg(item.getGoodsCoverImg());
tmp.setPrice(item.getSingleTotalPrice());
tmp.setGoodsCount(item.getGoodsCount());
String format = "yyyy-MM-dd'T'HH:mm:ss.SSSZ";
SimpleDateFormat sdf = new SimpleDateFormat(format);
tmp.setCreateTime(item.getCreateTime().split("T")[0]);
tmp.setEndTime(item.getEndTime().split("T")[0]);
tmp.setUserId(user.getUserId());
boolean isSaveOrderItem=orderItemService.save(tmp);
if(isSaveOrderItem){
QueryWrapper<CartItem> cartItemQueryWrapper=new QueryWrapper<>();
cartItemQueryWrapper.eq("cart_item_id",item.getCartItemId());
cartItemService.remove(cartItemQueryWrapper);
}else {
return "fail";
}
}
}
return "success";
}else {
return "fail";
}
}
}

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save