fix: 移除管理端残留验证码交互 (#32)
This commit is contained in:
@@ -1,14 +1,6 @@
|
||||
import request from '@/utils/request'
|
||||
|
||||
// 获取验证码
|
||||
export function getCodeImg() {
|
||||
return request({
|
||||
url: '/api/v1/captcha',
|
||||
method: 'get'
|
||||
})
|
||||
}
|
||||
|
||||
// 查询 此接口不在验证数据权限
|
||||
// 查询公开应用配置;此接口不校验数据权限。
|
||||
export function getSetting() {
|
||||
return request({
|
||||
url: '/api/v1/app-config',
|
||||
|
||||
@@ -102,29 +102,6 @@
|
||||
</el-input>
|
||||
</el-form-item>
|
||||
|
||||
<el-form-item label="验证码" prop="code">
|
||||
<div class="captcha-row">
|
||||
<el-input
|
||||
v-model="loginForm.code"
|
||||
placeholder="请输入验证码"
|
||||
name="code"
|
||||
type="text"
|
||||
tabindex="3"
|
||||
maxlength="5"
|
||||
autocomplete="off"
|
||||
size="large"
|
||||
:prefix-icon="Key"
|
||||
@keyup.enter="handleLogin"
|
||||
/>
|
||||
<div class="captcha-wrap" title="点击刷新" @click="getCode">
|
||||
<img v-if="codeUrl" :src="codeUrl" class="captcha-img" alt="验证码">
|
||||
<div v-else class="captcha-placeholder">
|
||||
<el-icon class="is-loading"><Loading /></el-icon>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</el-form-item>
|
||||
|
||||
<el-button
|
||||
:loading="loading"
|
||||
type="primary"
|
||||
@@ -142,27 +119,22 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getCodeImg } from '@/api/login'
|
||||
import { User, Lock, Key, View, Hide, Monitor, Loading } from '@element-plus/icons-vue'
|
||||
import { User, Lock, View, Hide, Monitor } from '@element-plus/icons-vue'
|
||||
|
||||
export default {
|
||||
name: 'LoginPage',
|
||||
setup() {
|
||||
return { User, Lock, Key, View, Hide, Monitor, Loading }
|
||||
return { User, Lock, View, Hide, Monitor }
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
codeUrl: '',
|
||||
loginForm: {
|
||||
username: 'admin',
|
||||
password: '123456',
|
||||
code: '',
|
||||
uuid: ''
|
||||
password: ''
|
||||
},
|
||||
loginRules: {
|
||||
username: [{ required: true, trigger: 'blur', message: '用户名不能为空' }],
|
||||
password: [{ required: true, trigger: 'blur', message: '密码不能为空' }],
|
||||
code: [{ required: true, trigger: 'change', message: '验证码不能为空' }]
|
||||
password: [{ required: true, trigger: 'blur', message: '密码不能为空' }]
|
||||
},
|
||||
passwordType: 'password',
|
||||
capsTooltip: false,
|
||||
@@ -185,7 +157,6 @@ export default {
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getCode()
|
||||
this.getSystemSetting()
|
||||
},
|
||||
mounted() {
|
||||
@@ -202,15 +173,6 @@ export default {
|
||||
document.title = ret.sys_app_name
|
||||
})
|
||||
},
|
||||
getCode() {
|
||||
this.codeUrl = ''
|
||||
getCodeImg().then((res) => {
|
||||
if (res !== undefined) {
|
||||
this.codeUrl = res.data
|
||||
this.loginForm.uuid = res.id
|
||||
}
|
||||
})
|
||||
},
|
||||
checkCapslock({ shiftKey, key } = {}) {
|
||||
if (key && key.length === 1) {
|
||||
if ((shiftKey && key >= 'a' && key <= 'z') || (!shiftKey && key >= 'A' && key <= 'Z')) {
|
||||
@@ -238,7 +200,6 @@ export default {
|
||||
})
|
||||
.catch(() => {
|
||||
this.loading = false
|
||||
this.getCode()
|
||||
})
|
||||
}
|
||||
})
|
||||
@@ -562,48 +523,6 @@ export default {
|
||||
}
|
||||
}
|
||||
|
||||
/* ── 验证码 ── */
|
||||
.captcha-row {
|
||||
display: flex;
|
||||
gap: 10px;
|
||||
align-items: center;
|
||||
|
||||
.el-input {
|
||||
flex: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.captcha-wrap {
|
||||
width: 110px;
|
||||
height: 40px;
|
||||
flex-shrink: 0;
|
||||
border-radius: 8px;
|
||||
border: 1px solid #e5e7eb;
|
||||
overflow: hidden;
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background: #f9fafb;
|
||||
transition: border-color 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: #3b82f6;
|
||||
}
|
||||
}
|
||||
|
||||
.captcha-img {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
object-fit: cover;
|
||||
display: block;
|
||||
}
|
||||
|
||||
.captcha-placeholder {
|
||||
color: #c1c7d0;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
/* ── 登录按钮 ── */
|
||||
.submit-btn {
|
||||
width: 100%;
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
import { shallowMount } from '@vue/test-utils'
|
||||
import LoginPage from '@/views/login/index.vue'
|
||||
|
||||
describe('admin login page', () => {
|
||||
function mountPage() {
|
||||
return shallowMount(LoginPage, {
|
||||
global: {
|
||||
config: { warnHandler: () => {} },
|
||||
mocks: {
|
||||
$route: { query: {}},
|
||||
$router: { push: jest.fn(() => Promise.resolve()) },
|
||||
$store: { dispatch: jest.fn(() => Promise.resolve({ sys_app_name: 'Chorus' })) }
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
test('uses only username and password fields', () => {
|
||||
const wrapper = mountPage()
|
||||
|
||||
expect(wrapper.vm.loginForm).toEqual({ username: 'admin', password: '' })
|
||||
expect(Object.keys(wrapper.vm.loginRules)).toEqual(['username', 'password'])
|
||||
expect(wrapper.find('[name="code"]').exists()).toBe(false)
|
||||
expect(wrapper.text()).not.toContain('验证码')
|
||||
expect(wrapper.vm.getCode).toBeUndefined()
|
||||
})
|
||||
|
||||
test('submits only the password login contract', async() => {
|
||||
const dispatch = jest.fn(() => Promise.resolve())
|
||||
const context = {
|
||||
$refs: { loginForm: { validate: callback => callback(true) }},
|
||||
$router: { push: jest.fn(() => Promise.resolve()) },
|
||||
$store: { dispatch },
|
||||
loginForm: { username: 'admin', password: 'synthetic-password' },
|
||||
redirect: undefined,
|
||||
otherQuery: {},
|
||||
loading: false
|
||||
}
|
||||
|
||||
LoginPage.methods.handleLogin.call(context)
|
||||
await Promise.resolve()
|
||||
|
||||
expect(dispatch).toHaveBeenCalledWith('user/login', {
|
||||
username: 'admin',
|
||||
password: 'synthetic-password'
|
||||
})
|
||||
})
|
||||
})
|
||||
Reference in New Issue
Block a user