openioctopus/octopus:master
into master
1 year ago
@@ -28,7 +28,7 @@ export function editUser(data) { | |||||
return request({ | return request({ | ||||
url: `/v1/usermanage/user/${data.id}`, | url: `/v1/usermanage/user/${data.id}`, | ||||
method: 'put', | method: 'put', | ||||
data: { fullname: data.fullname, password: data.password, resourcePools: data.resourcePools } | |||||
data | |||||
}) | }) | ||||
} | } | ||||
// 冻结账号 | // 冻结账号 | ||||
@@ -18,6 +18,7 @@ label { | |||||
} | } | ||||
html { | html { | ||||
min-width: 1200px; | |||||
height: 100%; | height: 100%; | ||||
box-sizing: border-box; | box-sizing: border-box; | ||||
} | } | ||||
@@ -38,8 +38,8 @@ | |||||
<el-input v-model="ruleForm.name" /> | <el-input v-model="ruleForm.name" /> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item label="机时价格" prop="price"> | <el-form-item label="机时价格" prop="price"> | ||||
<el-input-number v-model="ruleForm.price" :min="0" :max="10" label="描述文字" /> | |||||
<span>价格1~10,仅支持正整数</span> | |||||
<el-input-number v-model="ruleForm.price" :min="0" label="描述文字" :precision="0"/> | |||||
<span class="red">仅支持正整数</span> | |||||
</el-form-item> | </el-form-item> | ||||
<el-form-item label="资源信息" prop="resourceQuantity"> | <el-form-item label="资源信息" prop="resourceQuantity"> | ||||
<div v-for="(item, index) in ruleForm.resourceQuantity" :key="index"> | <div v-for="(item, index) in ruleForm.resourceQuantity" :key="index"> | ||||
@@ -257,4 +257,5 @@ | |||||
.line { | .line { | ||||
text-align: center; | text-align: center; | ||||
} | } | ||||
.red{color:#409EFF;margin-left: 10px;font-weight: 800;} | |||||
</style> | </style> |
@@ -19,7 +19,7 @@ | |||||
</el-row> | </el-row> | ||||
<el-row> | <el-row> | ||||
<el-col :span="12"> | <el-col :span="12"> | ||||
<div>选用数据集:<span>{{ data.dataSetName + ":" + data.dataSetVersion }}</span></div> | |||||
<div>选用数据集:<span>{{ (data.dataSetName&&data.dataSetVersion)?data.dataSetName + ":" + data.dataSetVersion:'' }}</span></div> | |||||
</el-col> | </el-col> | ||||
<el-col :span="12"> | <el-col :span="12"> | ||||
<div>是否分布式:<span>{{ data.isDistributed?'是':'否' }}</span></div> | <div>是否分布式:<span>{{ data.isDistributed?'是':'否' }}</span></div> | ||||
@@ -12,10 +12,9 @@ | |||||
<el-form-item v-if="user" label="密码确认" :label-width="formLabelWidth" prop="confirm"> | <el-form-item v-if="user" label="密码确认" :label-width="formLabelWidth" prop="confirm"> | ||||
<el-input v-model="ruleForm.confirm" type="password" /> | <el-input v-model="ruleForm.confirm" type="password" /> | ||||
</el-form-item> | </el-form-item> | ||||
<!-- <el-form-item label="验证码" :label-width="formLabelWidth" placeholder="请输入验证码" prop="code" v-if="user"> | |||||
<el-input v-model="ruleForm.verifyCode" class="verifyCode"></el-input> | |||||
<VerificationCode :changeCode.sync='verifyCode'></VerificationCode> | |||||
</el-form-item> --> | |||||
<el-form-item v-if="user" label="电话" :label-width="formLabelWidth" prop="phone"> | |||||
<el-input v-model="ruleForm.phone" /> | |||||
</el-form-item> | |||||
<el-form-item v-if="group" label="群组名称" :label-width="formLabelWidth" prop="name"> | <el-form-item v-if="group" label="群组名称" :label-width="formLabelWidth" prop="name"> | ||||
<el-input v-model.trim="ruleForm.name" /> | <el-input v-model.trim="ruleForm.name" /> | ||||
</el-form-item> | </el-form-item> | ||||
@@ -33,6 +32,9 @@ | |||||
<el-form-item v-if="user" label="姓名" :label-width="formLabelWidth" prop="fullname"> | <el-form-item v-if="user" label="姓名" :label-width="formLabelWidth" prop="fullname"> | ||||
<el-input v-model.trim="ruleForm.fullname" /> | <el-input v-model.trim="ruleForm.fullname" /> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item label="备注" prop="desc" v-if="user" :label-width="formLabelWidth"> | |||||
<el-input type="textarea" v-model="ruleForm.desc" maxlength="100" show-word-limit="true"></el-input> | |||||
</el-form-item> | |||||
</el-form> | </el-form> | ||||
<div slot="footer" class="dialog-footer"> | <div slot="footer" class="dialog-footer"> | ||||
<el-button @click="cancel">取 消</el-button> | <el-button @click="cancel">取 消</el-button> | ||||
@@ -75,18 +77,50 @@ | |||||
} | } | ||||
callback(new Error("请输入合法的邮箱地址")); | callback(new Error("请输入合法的邮箱地址")); | ||||
} | } | ||||
var checkPhone = (rule, value, callback) => { | |||||
if (value === '') { | |||||
callback(); | |||||
} else { | |||||
let reg = /^(13|14|15|17|18|19)[0-9]{9}$/ | |||||
if (reg.test(value)) { | |||||
callback(); | |||||
} | |||||
else { | |||||
callback("请输入正确手机号码"); | |||||
} | |||||
} | |||||
}; | |||||
var validatePass = (rule, value, callback) => { | |||||
if (value === '') { | |||||
callback(new Error('请输入密码')); | |||||
} else { | |||||
if (this.ruleForm.confirm !== '') { | |||||
this.$refs.ruleForm.validateField('confirm'); | |||||
} | |||||
callback(); | |||||
} | |||||
}; | |||||
var validatePass2 = (rule, value, callback) => { | |||||
if (value === '') { | |||||
callback(new Error('请再次输入密码')); | |||||
} else if (value !== this.ruleForm.password) { | |||||
callback(new Error('两次输入密码不一致!')); | |||||
} else { | |||||
callback(); | |||||
} | |||||
}; | |||||
return { | return { | ||||
fileList: [], | fileList: [], | ||||
ruleForm: { | ruleForm: { | ||||
fullname: '', | fullname: '', | ||||
password: '', | password: '', | ||||
confirm: '', | confirm: '', | ||||
phone: '', | |||||
resourcePoolId: '', | resourcePoolId: '', | ||||
name: '', | name: '', | ||||
userIds: [], | userIds: [], | ||||
email: undefined | |||||
email: undefined, | |||||
desc: '' | |||||
}, | }, | ||||
CreateFormVisible: true, | CreateFormVisible: true, | ||||
user: false, | user: false, | ||||
@@ -103,12 +137,16 @@ | |||||
], | ], | ||||
password: [ | password: [ | ||||
{ required: true, message: '请输入密码', trigger: 'blur' }, | { required: true, message: '请输入密码', trigger: 'blur' }, | ||||
{ min: 8, message: '密码长度不得少于8位', trigger: 'blur' } | |||||
{ min: 8, message: '密码长度不得少于8位', trigger: 'blur' }, | |||||
{ validator: validatePass, trigger: 'blur' } | |||||
], | ], | ||||
confirm: [ | confirm: [ | ||||
{ required: true, message: '请再次输入密码', trigger: 'blur' } | |||||
{ validator: validatePass2, trigger: 'blur' } | |||||
], | |||||
phone: [ | |||||
{ required: false, message: '请输入电话' }, | |||||
{ validator: checkPhone, trigger: "blur" } | |||||
], | ], | ||||
name: [ | name: [ | ||||
{ required: true, message: '请输入群组名', trigger: 'blur' } | { required: true, message: '请输入群组名', trigger: 'blur' } | ||||
@@ -214,46 +252,40 @@ | |||||
confirm() { | confirm() { | ||||
this.$refs['ruleForm'].validate((valid) => { | this.$refs['ruleForm'].validate((valid) => { | ||||
if (valid) { | if (valid) { | ||||
if (this.ruleForm.confirm === this.ruleForm.password) { | |||||
if (this.user) { | |||||
const data = { fullname: this.ruleForm.fullname, password: this.ruleForm.password, email: this.ruleForm.email, gender: 1 } | |||||
createUser(data).then(response => { | |||||
if (response.success === true) { | |||||
this.$message({ | |||||
message: '新增用户成功', | |||||
type: 'success' | |||||
}); | |||||
this.$emit('confirm', false) | |||||
} else { | |||||
this.$message({ | |||||
message: this.getErrorMsg(response.error.subcode), | |||||
type: 'warning' | |||||
}); | |||||
} | |||||
}) | |||||
} else if (this.group) { | |||||
const data = { name: this.ruleForm.name, resourcePoolId: this.ruleForm.resourcePoolId, userIds: this.ruleForm.userIds } | |||||
createGroup(data).then(response => { | |||||
if (response.success === true) { | |||||
this.$message({ | |||||
message: '新增群组成功', | |||||
type: 'success' | |||||
}); | |||||
this.$emit('confirm', false) | |||||
} else { | |||||
this.$message({ | |||||
message: this.getErrorMsg(response.error.subcode), | |||||
type: 'warning' | |||||
}); | |||||
} | |||||
}) | |||||
} | |||||
} else { | |||||
this.$message({ | |||||
message: '输入密码不一致!', | |||||
type: 'warning' | |||||
}); | |||||
if (this.user) { | |||||
const data = { fullname: this.ruleForm.fullname, password: this.ruleForm.password, email: this.ruleForm.email, gender: 1, phone: this.ruleForm.phone.toString(), desc: this.ruleForm.desc } | |||||
createUser(data).then(response => { | |||||
if (response.success === true) { | |||||
this.$message({ | |||||
message: '新增用户成功', | |||||
type: 'success' | |||||
}); | |||||
this.$emit('confirm', false) | |||||
} else { | |||||
this.$message({ | |||||
message: this.getErrorMsg(response.error.subcode), | |||||
type: 'warning' | |||||
}); | |||||
} | |||||
}) | |||||
} else if (this.group) { | |||||
const data = { name: this.ruleForm.name, resourcePoolId: this.ruleForm.resourcePoolId, userIds: this.ruleForm.userIds } | |||||
createGroup(data).then(response => { | |||||
if (response.success === true) { | |||||
this.$message({ | |||||
message: '新增群组成功', | |||||
type: 'success' | |||||
}); | |||||
this.$emit('confirm', false) | |||||
} else { | |||||
this.$message({ | |||||
message: this.getErrorMsg(response.error.subcode), | |||||
type: 'warning' | |||||
}); | |||||
} | |||||
}) | |||||
} | } | ||||
} else { | } else { | ||||
console.log('error submit!!'); | console.log('error submit!!'); | ||||
return false; | return false; | ||||
@@ -1,21 +1,23 @@ | |||||
<template> | <template> | ||||
<div> | <div> | ||||
<el-dialog :title="userType==='user'?'重置密码':'编辑群组信息'" width="35%" :visible.sync="CreateFormVisible" | |||||
<el-dialog :title="userType==='user'?'编辑用户信息':'编辑群组信息'" width="35%" :visible.sync="CreateFormVisible" | |||||
:before-close="handleDialogClose" :close-on-click-modal="false"> | :before-close="handleDialogClose" :close-on-click-modal="false"> | ||||
<el-form ref="ruleForm" :model="ruleForm" :rules="rules" label-width="100px" class="demo-ruleForm"> | <el-form ref="ruleForm" :model="ruleForm" :rules="rules" label-width="100px" class="demo-ruleForm"> | ||||
<el-form-item v-if="user" label="用户名称" :label-width="formLabelWidth"> | <el-form-item v-if="user" label="用户名称" :label-width="formLabelWidth"> | ||||
<el-input v-model="ruleForm.fullName" disabled /> | <el-input v-model="ruleForm.fullName" disabled /> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item v-if="user" label="用户新密码" :label-width="formLabelWidth" prop="password"> | |||||
<el-input v-model="ruleForm.password" /> | |||||
<el-form-item v-if="user&&password" label="用户新密码" :label-width="formLabelWidth" prop="password"> | |||||
<el-input v-model="ruleForm.password" type="password" /> | |||||
</el-form-item> | </el-form-item> | ||||
<el-form-item v-if="user" label="密码确认" :label-width="formLabelWidth" prop="confirm"> | |||||
<el-input v-model="ruleForm.confirm" /> | |||||
<el-form-item v-if="user&&password" label="密码确认" :label-width="formLabelWidth" prop="confirm"> | |||||
<el-input v-model="ruleForm.confirm" type="password" /> | |||||
</el-form-item> | |||||
<el-form-item v-if="user&&edite" label="电话" :label-width="formLabelWidth" prop="phone"> | |||||
<el-input v-model="ruleForm.phone" /> | |||||
</el-form-item> | |||||
<el-form-item label="备注" prop="desc" v-if="user&&edite" :label-width="formLabelWidth"> | |||||
<el-input type="textarea" v-model="ruleForm.desc" maxlength="100" show-word-limit="true"></el-input> | |||||
</el-form-item> | </el-form-item> | ||||
<!-- <el-form-item label="验证码" :label-width="formLabelWidth" placeholder="请输入验证码" prop="code" v-if="user"> | |||||
<el-input v-model="ruleForm.verifyCode" class="verifyCode"></el-input> | |||||
<VerificationCode :changeCode.sync='verifyCode'></VerificationCode> | |||||
</el-form-item> --> | |||||
<el-form-item v-if="group" label="群组名称" :label-width="formLabelWidth" prop="name"> | <el-form-item v-if="group" label="群组名称" :label-width="formLabelWidth" prop="name"> | ||||
<el-input v-model="ruleForm.name" disabled /> | <el-input v-model="ruleForm.name" disabled /> | ||||
</el-form-item> | </el-form-item> | ||||
@@ -56,9 +58,45 @@ | |||||
flag: { | flag: { | ||||
type: String, | type: String, | ||||
default: "" | default: "" | ||||
}, | |||||
type: { | |||||
type: String, | |||||
default: 'edite' | |||||
} | } | ||||
}, | }, | ||||
data() { | data() { | ||||
var checkPhone = (rule, value, callback) => { | |||||
if (value === '') { | |||||
callback(); | |||||
} else { | |||||
let reg = /^(13|14|15|17|18|19)[0-9]{9}$/ | |||||
if (reg.test(value)) { | |||||
callback(); | |||||
} | |||||
else { | |||||
callback("请输入正确手机号码"); | |||||
} | |||||
} | |||||
}; | |||||
var validatePass = (rule, value, callback) => { | |||||
if (value === '') { | |||||
callback(new Error('请输入密码')); | |||||
} else { | |||||
if (this.ruleForm.confirm !== '') { | |||||
this.$refs.ruleForm.validateField('confirm'); | |||||
} | |||||
callback(); | |||||
} | |||||
}; | |||||
var validatePass2 = (rule, value, callback) => { | |||||
if (value === ''||value==undefined) { | |||||
callback(new Error('请再次输入密码')); | |||||
} else if (value !== this.ruleForm.password) { | |||||
callback(new Error('两次输入密码不一致!')); | |||||
} else { | |||||
callback(); | |||||
} | |||||
}; | |||||
return { | return { | ||||
fileList: [], | fileList: [], | ||||
ruleForm: { | ruleForm: { | ||||
@@ -67,7 +105,10 @@ | |||||
fullname: '', | fullname: '', | ||||
resourcePoolId: '', | resourcePoolId: '', | ||||
name: '', | name: '', | ||||
userIds: [] | |||||
userIds: [], | |||||
email: undefined, | |||||
desc: '', | |||||
phone: '' | |||||
}, | }, | ||||
verifyCode: "", | verifyCode: "", | ||||
CreateFormVisible: true, | CreateFormVisible: true, | ||||
@@ -77,12 +118,13 @@ | |||||
userOptions: [], | userOptions: [], | ||||
rules: { | rules: { | ||||
password: [ | password: [ | ||||
{ required: true, message: '请输入密码', trigger: 'blur' } | |||||
{ required: true, message: '请输入密码', trigger: 'blur' }, | |||||
{ min: 8, message: '密码长度不得少于8位', trigger: 'blur' }, | |||||
{ validator: validatePass, trigger: 'blur' } | |||||
], | ], | ||||
confirm: [ | confirm: [ | ||||
{ required: true, message: '请再次输入密码', trigger: 'blur' } | |||||
{ validator: validatePass2, trigger: 'blur' } | |||||
], | ], | ||||
name: [ | name: [ | ||||
{ required: true, message: '请输入用户名', trigger: 'blur' } | { required: true, message: '请输入用户名', trigger: 'blur' } | ||||
@@ -93,11 +135,17 @@ | |||||
], | ], | ||||
resourcePoolId: [ | resourcePoolId: [ | ||||
{ required: true, message: '请选择资源池', trigger: 'change' } | { required: true, message: '请选择资源池', trigger: 'change' } | ||||
] | |||||
], | |||||
phone: [ | |||||
{ required: false, message: '请输入电话' }, | |||||
{ validator: checkPhone, trigger: "blur" } | |||||
], | |||||
}, | }, | ||||
formLabelWidth: '120px', | formLabelWidth: '120px', | ||||
pageSize: 100, | pageSize: 100, | ||||
userCount: 1 | |||||
userCount: 1, | |||||
edite: false, | |||||
password: false | |||||
} | } | ||||
}, | }, | ||||
@@ -106,7 +154,16 @@ | |||||
this.user = true | this.user = true | ||||
this.group = false | this.group = false | ||||
this.ruleForm.fullName = this.row.fullName | this.ruleForm.fullName = this.row.fullName | ||||
this.ruleForm.phone = this.row.phone | |||||
this.ruleForm.desc = this.row.desc | |||||
this.id = this.row.id | this.id = this.row.id | ||||
if (this.type == 'password') { | |||||
this.password = true | |||||
this.edite = false | |||||
} else { | |||||
this.password = false | |||||
this.edite = true | |||||
} | |||||
} else { | } else { | ||||
this.group = true | this.group = true | ||||
this.user = false | this.user = false | ||||
@@ -197,27 +254,25 @@ | |||||
this.$refs['ruleForm'].validate((valid) => { | this.$refs['ruleForm'].validate((valid) => { | ||||
if (valid) { | if (valid) { | ||||
if (this.userType === 'user') { | if (this.userType === 'user') { | ||||
if (this.ruleForm.confirm === this.ruleForm.password) { | |||||
const data = { fullname: this.ruleForm.fullname, password: this.ruleForm.password, id: this.id } | |||||
editUser(data).then(response => { | |||||
if (response.success) { | |||||
this.$message({ | |||||
message: '修改成功', | |||||
type: 'success' | |||||
}); | |||||
} else { | |||||
this.$message({ | |||||
message: response.error.message, | |||||
type: 'error' | |||||
}); | |||||
} | |||||
}) | |||||
} else { | |||||
this.$message({ | |||||
message: '输入密码不一致!', | |||||
type: 'warning' | |||||
}); | |||||
let data = {} | |||||
if (this.password) { data = { fullname: this.ruleForm.fullname, password: this.ruleForm.password, id: this.id } } | |||||
else { | |||||
data = { id: this.id, phone: this.ruleForm.phone.toString(), desc: this.ruleForm.desc } | |||||
} | } | ||||
editUser(data).then(response => { | |||||
if (response.success) { | |||||
this.$message({ | |||||
message: '修改成功', | |||||
type: 'success' | |||||
}); | |||||
this.$emit('confirm', false) | |||||
} else { | |||||
this.$message({ | |||||
message: response.error.message, | |||||
type: 'error' | |||||
}); | |||||
} | |||||
}) | |||||
} else { | } else { | ||||
const data = { name: this.ruleForm.name, resourcePoolId: this.ruleForm.resourcePoolId, id: this.id, userIds: this.ruleForm.userIds } | const data = { name: this.ruleForm.name, resourcePoolId: this.ruleForm.resourcePoolId, id: this.id, userIds: this.ruleForm.userIds } | ||||
editGroup(data).then(response => { | editGroup(data).then(response => { | ||||
@@ -226,6 +281,7 @@ | |||||
message: '修改成功', | message: '修改成功', | ||||
type: 'success' | type: 'success' | ||||
}); | }); | ||||
this.$emit('confirm', false) | |||||
} else { | } else { | ||||
this.$message({ | this.$message({ | ||||
message: this.getErrorMsg(response.error.subcode), | message: this.getErrorMsg(response.error.subcode), | ||||
@@ -234,7 +290,7 @@ | |||||
} | } | ||||
}) | }) | ||||
} | } | ||||
this.$emit('confirm', false) | |||||
} else { | } else { | ||||
console.log('error submit!!'); | console.log('error submit!!'); | ||||
return false; | return false; | ||||
@@ -18,6 +18,11 @@ | |||||
<span>{{ scope.row.email }}</span> | <span>{{ scope.row.email }}</span> | ||||
</template> | </template> | ||||
</el-table-column> | </el-table-column> | ||||
<el-table-column v-if="user" label="电话" align="center"> | |||||
<template slot-scope="scope"> | |||||
<span>{{ scope.row.phone }}</span> | |||||
</template> | |||||
</el-table-column> | |||||
<el-table-column v-if="group" label="群组名称" align="center"> | <el-table-column v-if="group" label="群组名称" align="center"> | ||||
<template slot-scope="scope"> | <template slot-scope="scope"> | ||||
<span>{{ scope.row.name }}</span> | <span>{{ scope.row.name }}</span> | ||||
@@ -33,6 +38,11 @@ | |||||
<span>{{ scope.row.status===1?'已冻结':'已激活' }}</span> | <span>{{ scope.row.status===1?'已冻结':'已激活' }}</span> | ||||
</template> | </template> | ||||
</el-table-column> | </el-table-column> | ||||
<el-table-column v-if="user" label="备注" align="center"> | |||||
<template slot-scope="scope"> | |||||
<span>{{ scope.row.desc }}</span> | |||||
</template> | |||||
</el-table-column> | |||||
<el-table-column label="创建时间" align="center"> | <el-table-column label="创建时间" align="center"> | ||||
<template slot-scope="scope"> | <template slot-scope="scope"> | ||||
<span>{{ scope.row.createdAt | parseTime }}</span> | <span>{{ scope.row.createdAt | parseTime }}</span> | ||||
@@ -43,18 +53,19 @@ | |||||
<span>{{ scope.row.updatedAt | parseTime }}</span> | <span>{{ scope.row.updatedAt | parseTime }}</span> | ||||
</template> | </template> | ||||
</el-table-column> | </el-table-column> | ||||
<el-table-column label="操作" align="center"> | |||||
<el-table-column label="操作" align="center" width="300"> | |||||
<template slot-scope="scope"> | <template slot-scope="scope"> | ||||
<el-button v-if="user" type="text" @click="handleUserEdit(scope.row)">编辑</el-button> | |||||
<el-button v-if="user" type="text" @click="handleUserEdit(scope.row)">资源池</el-button> | |||||
<el-button v-if="scope.row.status===2 && user" type="text" @click="handleFreeze(scope.row)">冻结 | <el-button v-if="scope.row.status===2 && user" type="text" @click="handleFreeze(scope.row)">冻结 | ||||
</el-button> | </el-button> | ||||
<el-button v-if="scope.row.status===1 && user" type="text" @click="handleThaw( scope.row)">激活 | <el-button v-if="scope.row.status===1 && user" type="text" @click="handleThaw( scope.row)">激活 | ||||
</el-button> | </el-button> | ||||
<el-button v-if="user" type="text" @click="handleReset(scope.row)">重置密码</el-button> | |||||
<el-button v-if="user" type="text" @click="handleReset(scope.row,'password')">修改密码</el-button> | |||||
<el-button v-if="user" type="text" @click="handleReset(scope.row,'edite')">编辑</el-button> | |||||
<el-button v-if="group" type="text" @click="handleEdit(scope.row)">编辑</el-button> | <el-button v-if="group" type="text" @click="handleEdit(scope.row)">编辑</el-button> | ||||
<!-- <el-button @click="handleDelete(scope.row)" type="text" v-if="group">删除</el-button> --> | <!-- <el-button @click="handleDelete(scope.row)" type="text" v-if="group">删除</el-button> --> | ||||
<el-button type="text" @click="handleDetail(scope.row)">{{ user?'用户详情':'群组详情' }}</el-button> | |||||
<el-button v-if="user" type="text" @click="handleUserConfig(scope.row)">用户配置</el-button> | |||||
<el-button type="text" @click="handleDetail(scope.row)">{{ user?'所属群组':'用户列表' }}</el-button> | |||||
<!-- <el-button v-if="user" type="text" @click="handleUserConfig(scope.row)">用户配置</el-button> --> | |||||
</template> | </template> | ||||
</el-table-column> | </el-table-column> | ||||
</el-table> | </el-table> | ||||
@@ -67,13 +78,14 @@ | |||||
<addDialog v-if="CreateVisible" :flag="flag" @cancel="cancel" @confirm="confirm" @close="close" /> | <addDialog v-if="CreateVisible" :flag="flag" @cancel="cancel" @confirm="confirm" @close="close" /> | ||||
<!-- 创修改信息对话框 --> | <!-- 创修改信息对话框 --> | ||||
<operateDialog v-if="operateVisible" :row="row" :user-type="change" @cancel="cancel" @confirm="confirm" | <operateDialog v-if="operateVisible" :row="row" :user-type="change" @cancel="cancel" @confirm="confirm" | ||||
@close="close" /> | |||||
@close="close" :type='type'/> | |||||
<!-- 用户配置对话框 --> | <!-- 用户配置对话框 --> | ||||
<userConfig v-if="userConfigVisible" :conKey="conKey" :conValue="conValue" :row="row" @cancel="cancel" | <userConfig v-if="userConfigVisible" :conKey="conKey" :conValue="conValue" :row="row" @cancel="cancel" | ||||
@confirm="confirm" @close="close"> | @confirm="confirm" @close="close"> | ||||
</userConfig> | </userConfig> | ||||
<!-- 资源池绑定对话框 --> | <!-- 资源池绑定对话框 --> | ||||
<userEdit v-if="userEdit" :userResourcePoolList="userResourcePoolList" :row="row" @cancel="cancel" @confirm="confirm" @close="close"> | |||||
<userEdit v-if="userEdit" :userResourcePoolList="userResourcePoolList" :row="row" @cancel="cancel" | |||||
@confirm="confirm" @close="close"> | |||||
</userEdit> | </userEdit> | ||||
<!-- 详情对话框 --> | <!-- 详情对话框 --> | ||||
<el-dialog :title="user?'用户名' + userName:'群组名' + groupName" :visible.sync="detailVisible" width="30%" center | <el-dialog :title="user?'用户名' + userName:'群组名' + groupName" :visible.sync="detailVisible" width="30%" center | ||||
@@ -141,7 +153,9 @@ | |||||
pageSize: 10 | pageSize: 10 | ||||
}, | }, | ||||
conKey: [], | conKey: [], | ||||
conValue: {} | |||||
conValue: {}, | |||||
time: null, | |||||
type:'' | |||||
} | } | ||||
}, | }, | ||||
created() { | created() { | ||||
@@ -164,12 +178,12 @@ | |||||
this.searchForm = [] | this.searchForm = [] | ||||
} | } | ||||
this.getList(this.searchData) | this.getList(this.searchData) | ||||
// this.timer = setInterval(this.getList, 1000); | |||||
}, | |||||
beforeDestroy() { | |||||
clearTimeout(this.timer); | |||||
this.timer = null; | |||||
}, | }, | ||||
// beforeDestroy() { | |||||
// clearInterval(this.timer); | |||||
// this.timer = null; | |||||
// }, | |||||
methods: { | methods: { | ||||
handleUserEdit(row) { | handleUserEdit(row) { | ||||
this.row = row | this.row = row | ||||
@@ -177,7 +191,7 @@ | |||||
if (response.success) { | if (response.success) { | ||||
if (response.data !== null && response.data.resourcePools !== null) { | if (response.data !== null && response.data.resourcePools !== null) { | ||||
this.userEdit = true | this.userEdit = true | ||||
this.userResourcePoolList =response.data.resourcePools | |||||
this.userResourcePoolList = response.data.resourcePools | |||||
} else { | } else { | ||||
this.userResourcePoolList = [] | this.userResourcePoolList = [] | ||||
} | } | ||||
@@ -241,9 +255,10 @@ | |||||
} | } | ||||
}) | }) | ||||
}, | }, | ||||
handleReset(row) { | |||||
handleReset(row,type) { | |||||
this.row = row | this.row = row | ||||
this.operateVisible = true | this.operateVisible = true | ||||
this.type=type | |||||
}, | }, | ||||
handleUserConfig(row) { | handleUserConfig(row) { | ||||
this.row = row | this.row = row | ||||
@@ -298,7 +313,8 @@ | |||||
this.operateVisible = val | this.operateVisible = val | ||||
this.userConfigVisible = val | this.userConfigVisible = val | ||||
this.userEdit = val | this.userEdit = val | ||||
this.getList(this.searchData) | |||||
this.timer = setTimeout(this.getList, 500) | |||||
}, | }, | ||||
close(val) { | close(val) { | ||||
this.CreateVisible = val | this.CreateVisible = val | ||||
@@ -311,6 +327,9 @@ | |||||
this.CreateVisible = true | this.CreateVisible = true | ||||
}, | }, | ||||
getList(data) { | getList(data) { | ||||
if (!data) { | |||||
data = this.searchData | |||||
} | |||||
if (this.userTabType === 1) { | if (this.userTabType === 1) { | ||||
getUserList(data).then(response => { | getUserList(data).then(response => { | ||||
if (response.success) { | if (response.success) { | ||||
@@ -5,10 +5,7 @@ export default MyDirective.install = function(vue, options) { | |||||
bind(el, binding) { | bind(el, binding) { | ||||
const selectDom = el.querySelector('.el-select-dropdown .el-select-dropdown__wrap') | const selectDom = el.querySelector('.el-select-dropdown .el-select-dropdown__wrap') | ||||
selectDom.addEventListener('scroll', function() { | selectDom.addEventListener('scroll', function() { | ||||
const isEnd = this.scrollHeight - this.scrollTop <= this.clientHeight | |||||
if (isEnd) { | |||||
binding.value() | binding.value() | ||||
} | |||||
}) | }) | ||||
} | } | ||||
}) | }) |
@@ -7,7 +7,7 @@ | |||||
<breadcrumb class="breadcrumb-container" /> | <breadcrumb class="breadcrumb-container" /> | ||||
</el-row> | </el-row> | ||||
</el-col> | </el-col> | ||||
<el-col :span="10"> | |||||
<el-col :span="24"> | |||||
<div class="right-menu"> | <div class="right-menu"> | ||||
<el-row class="demo-avatar demo-basic"> | <el-row class="demo-avatar demo-basic"> | ||||
<el-dropdown> | <el-dropdown> | ||||
@@ -171,6 +171,7 @@ | |||||
height: 100%; | height: 100%; | ||||
color: #409EFF; | color: #409EFF; | ||||
font-size: 20px; | font-size: 20px; | ||||
min-width: 400px; | |||||
.avatar-container { | .avatar-container { | ||||
margin-right: 30px; | margin-right: 30px; | ||||
@@ -20,6 +20,7 @@ label { | |||||
html { | html { | ||||
height: 100%; | height: 100%; | ||||
box-sizing: border-box; | box-sizing: border-box; | ||||
min-width: 1200px; | |||||
} | } | ||||
#app { | #app { | ||||
@@ -7,45 +7,64 @@ | |||||
</el-col> | </el-col> | ||||
</el-row> | </el-row> | ||||
<el-row type="flex" justify="center"> | <el-row type="flex" justify="center"> | ||||
<el-col :span="6"> | |||||
<el-col :span="6" v-show="!show"> | |||||
<div> | <div> | ||||
<el-form ref="loginForm" :model="loginForm" :rules="rules" label-width="80px"> | |||||
<el-form-item prop="fullName" label="姓名" v-if="show" key="fullName"> | |||||
<el-input v-model="loginForm.fullName" type="text" auto-complete="off" | |||||
<el-form ref="loginForm1" :model="loginForm1" :rules="rules1" label-width="80px"> | |||||
<el-form-item prop="username" label="邮箱" key="username"> | |||||
<el-input v-model="loginForm1.username" type="text" auto-complete="off" | |||||
placeholder="请输入邮箱号" /> | |||||
</el-form-item> | |||||
<el-form-item label="密码" prop="password"> | |||||
<el-input type="password" v-model="loginForm1.password" autocomplete="off"></el-input> | |||||
</el-form-item> | |||||
<el-form-item> | |||||
<el-row type="flex" :gutter="20"> | |||||
<el-col :span="18" :offset="9"> | |||||
<el-button type="primary" @click="login()">绑定并登录</el-button> | |||||
</el-col> | |||||
</el-row> | |||||
</el-form-item> | |||||
<el-form-item> | |||||
<el-row type="flex" :gutter="20"> | |||||
<el-col :span="18" :offset="9"> | |||||
<el-link type="primary" @click="goRegister">未注册?点击注册</el-link> | |||||
</el-col> | |||||
</el-row> | |||||
</el-form-item> | |||||
</el-form> | |||||
</div> | |||||
</el-col> | |||||
<el-col :span="6" v-show="show"> | |||||
<div> | |||||
<el-form ref="loginForm2" :model="loginForm2" :rules="rules2" label-width="80px"> | |||||
<el-form-item prop="fullName" label="姓名" key="fullName"> | |||||
<el-input v-model="loginForm2.fullName" type="text" auto-complete="off" | |||||
placeholder="请输入姓名" /> | placeholder="请输入姓名" /> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item prop="gender" label="性别" v-if="show" key="gender"> | |||||
<el-radio-group v-model="loginForm.gender"> | |||||
<el-form-item prop="gender" label="性别" key="gender"> | |||||
<el-radio-group v-model="loginForm2.gender"> | |||||
<el-radio :label="1">男</el-radio> | <el-radio :label="1">男</el-radio> | ||||
<el-radio :label="2">女</el-radio> | <el-radio :label="2">女</el-radio> | ||||
</el-radio-group> | </el-radio-group> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item prop="username" label="邮箱" key="username"> | <el-form-item prop="username" label="邮箱" key="username"> | ||||
<el-input v-model="loginForm.username" type="text" auto-complete="off" | |||||
<el-input v-model="loginForm2.username" type="text" auto-complete="off" | |||||
placeholder="请输入邮箱号" /> | placeholder="请输入邮箱号" /> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item prop="password" label="密码" key="password"> | |||||
<el-input v-model="loginForm.password" type="password" auto-complete="off" | |||||
placeholder="密码" /> | |||||
<el-form-item label="密码" prop="password"> | |||||
<el-input type="password" v-model="loginForm2.password" autocomplete="off"></el-input> | |||||
</el-form-item> | |||||
<el-form-item label="确认密码" prop="checkPass"> | |||||
<el-input type="password" v-model="loginForm2.checkPass" autocomplete="off"></el-input> | |||||
</el-form-item> | </el-form-item> | ||||
<el-form-item> | <el-form-item> | ||||
<el-row type="flex" :gutter="20"> | <el-row type="flex" :gutter="20"> | ||||
<el-col :span="18" :offset="9" v-if="!show"> | |||||
<el-button type="primary" @click="login()">绑定并登录</el-button> | |||||
</el-col> | |||||
<el-col :span="18" :offset="9" v-if="show"> | |||||
<el-col :span="18" :offset="9"> | |||||
<el-button type="primary" @click="register()">注册并登录</el-button> | <el-button type="primary" @click="register()">注册并登录</el-button> | ||||
</el-col> | </el-col> | ||||
</el-row> | </el-row> | ||||
</el-form-item> | </el-form-item> | ||||
<el-form-item> | <el-form-item> | ||||
<el-row type="flex" :gutter="20" v-if="hidden"> | |||||
<el-col :span="18" :offset="9"> | |||||
<el-link type="primary" @click="goRegister">未注册?点击注册</el-link> | |||||
</el-col> | |||||
</el-row> | |||||
</el-form-item> | |||||
<el-form-item v-if="show"> | |||||
<el-row type="flex" justify="end"> | <el-row type="flex" justify="end"> | ||||
<el-col :span="4"> | <el-col :span="4"> | ||||
<el-link type="primary" @click="goLogin()">返回登录</el-link> | <el-link type="primary" @click="goLogin()">返回登录</el-link> | ||||
@@ -55,6 +74,7 @@ | |||||
</el-form> | </el-form> | ||||
</div> | </div> | ||||
</el-col> | </el-col> | ||||
</el-row> | </el-row> | ||||
</div> | </div> | ||||
</template> | </template> | ||||
@@ -72,22 +92,62 @@ | |||||
} | } | ||||
callback(new Error("请输入合法的邮箱")); | callback(new Error("请输入合法的邮箱")); | ||||
}; | }; | ||||
var validatePass = (rule, value, callback) => { | |||||
if (value === '') { | |||||
console.log('value='+value) | |||||
callback(new Error('请输入密码')); | |||||
} else { | |||||
if (this.loginForm2.checkPass !== '') { | |||||
this.$refs.loginForm2.validateField('checkPass'); | |||||
} | |||||
callback(); | |||||
} | |||||
}; | |||||
var validatePass2 = (rule, value, callback) => { | |||||
if (value === '') { | |||||
callback(new Error('请再次输入密码')); | |||||
} else if (value !== this.loginForm2.password) { | |||||
callback(new Error('两次输入密码不一致!')); | |||||
} else { | |||||
callback(); | |||||
} | |||||
}; | |||||
return { | return { | ||||
show: false, | show: false, | ||||
hidden: true, | hidden: true, | ||||
loginForm: { | |||||
loginForm1: { | |||||
username: '', | |||||
password: '', | |||||
bind: { platform: '', userId: '', userName: '' } | |||||
}, | |||||
loginForm2: { | |||||
fullName: '', | fullName: '', | ||||
username: undefined, | |||||
password: undefined, | |||||
gender: undefined, | |||||
username: '', | |||||
password: '', | |||||
gender: '', | |||||
checkPass: '', | |||||
bind: { platform: '', userId: '', userName: '' } | bind: { platform: '', userId: '', userName: '' } | ||||
}, | }, | ||||
rules: { | |||||
rules1: { | |||||
username: [{ required: true, message: "请输入邮箱号", trigger: "blur" }, | |||||
{ validator: checkEmail, trigger: "blur" } | |||||
], | |||||
password: [ | |||||
{ validator: validatePass, trigger: 'blur' }, | |||||
{ min: 8, message: '密码长度不能小于8位', trigger: 'blur' } | |||||
], | |||||
}, | |||||
rules2: { | |||||
username: [{ required: true, message: "请输入邮箱号", trigger: "blur" }, | username: [{ required: true, message: "请输入邮箱号", trigger: "blur" }, | ||||
{ validator: checkEmail, trigger: "blur" } | { validator: checkEmail, trigger: "blur" } | ||||
], | ], | ||||
password: [{ required: true, message: '请输入用户密码', trigger: 'blur' }, | |||||
{ min: 8, message: '密码长度不能小于8位', trigger: 'blur' }], | |||||
password: [ | |||||
{ validator: validatePass, trigger: 'blur' }, | |||||
{ min: 8, message: '密码长度不能小于8位', trigger: 'blur' } | |||||
], | |||||
checkPass: [ | |||||
{ validator: validatePass2, trigger: 'blur' } | |||||
], | |||||
fullName: [{ required: true, message: '请输入姓名', trigger: 'blur' }], | fullName: [{ required: true, message: '请输入姓名', trigger: 'blur' }], | ||||
gender: [ | gender: [ | ||||
{ required: true, message: '请选择性别', trigger: 'change' } | { required: true, message: '请选择性别', trigger: 'change' } | ||||
@@ -97,9 +157,12 @@ | |||||
}, | }, | ||||
created() { | created() { | ||||
this.getThirdInfo() | this.getThirdInfo() | ||||
this.loginForm.bind.platform = sessionStorage.getItem("platform") | |||||
this.loginForm.bind.userName = sessionStorage.getItem("thirdUserName") | |||||
this.loginForm.bind.userId = sessionStorage.getItem("thirdUserId") | |||||
this.loginForm1.bind.platform = sessionStorage.getItem("platform") | |||||
this.loginForm1.bind.userName = sessionStorage.getItem("thirdUserName") | |||||
this.loginForm1.bind.userId = sessionStorage.getItem("thirdUserId") | |||||
this.loginForm2.bind.platform = sessionStorage.getItem("platform") | |||||
this.loginForm2.bind.userName = sessionStorage.getItem("thirdUserName") | |||||
this.loginForm2.bind.userId = sessionStorage.getItem("thirdUserId") | |||||
}, | }, | ||||
computed: { | computed: { | ||||
}, | }, | ||||
@@ -123,11 +186,41 @@ | |||||
this.show = false | this.show = false | ||||
this.hidden = true | this.hidden = true | ||||
}, | }, | ||||
// 登录并绑定 | |||||
login() { | |||||
// 在点击提交之前校验表单 | |||||
let loginForm = JSON.parse(JSON.stringify(this.loginForm1)); | |||||
delete loginForm.fullName | |||||
delete loginForm.gender | |||||
this.$refs['loginForm1'].validate((valid) => { | |||||
if (valid) { | |||||
login(loginForm).then((res) => { | |||||
if (res.success) { | |||||
this.$message({ | |||||
message: '登录成功', | |||||
type: 'success' | |||||
}); | |||||
setToken(res.data.token) | |||||
this.$router.push({ path: '/index' }) | |||||
} else { | |||||
this.$message({ | |||||
message: this.getErrorMsg(res.error.subcode), | |||||
type: 'warning' | |||||
}); | |||||
} | |||||
}).catch(() => { | |||||
}) | |||||
} else { | |||||
return false; | |||||
} | |||||
}); | |||||
}, | |||||
// 注册并绑定 | // 注册并绑定 | ||||
register() { | register() { | ||||
this.$refs['loginForm'].validate((valid) => { | |||||
this.$refs['loginForm2'].validate((valid) => { | |||||
if (valid) { | if (valid) { | ||||
register(this.loginForm).then( | |||||
register(this.loginForm2).then( | |||||
response => { | response => { | ||||
if (response.success) { | if (response.success) { | ||||
this.$message({ | this.$message({ | ||||
@@ -159,35 +252,7 @@ | |||||
} | } | ||||
}); | }); | ||||
}, | }, | ||||
// 登录并绑定 | |||||
login() { | |||||
let loginForm = JSON.parse(JSON.stringify(this.loginForm)); | |||||
delete loginForm.fullName | |||||
delete loginForm.gender | |||||
this.$refs['loginForm'].validate((valid) => { | |||||
if (valid) { | |||||
login(loginForm).then((res) => { | |||||
if (res.success) { | |||||
this.$message({ | |||||
message: '登录成功', | |||||
type: 'success' | |||||
}); | |||||
setToken(res.data.token) | |||||
this.$router.push({ path: '/index' }) | |||||
} else { | |||||
this.$message({ | |||||
message: this.getErrorMsg(res.error.subcode), | |||||
type: 'warning' | |||||
}); | |||||
} | |||||
}).catch(() => { | |||||
}) | |||||
} else { | |||||
return false; | |||||
} | |||||
}); | |||||
}, | |||||
} | } | ||||
} | } | ||||
</script> | </script> | ||||
@@ -19,7 +19,8 @@ | |||||
</el-row> | </el-row> | ||||
<el-row> | <el-row> | ||||
<el-col :span="12"> | <el-col :span="12"> | ||||
<div>选用数据集:<span>{{ data.dataSetName + ":" + data.dataSetVersion }}</span></div> | |||||
<div>选用数据集:<span>{{ (data.dataSetName&&data.dataSetVersion)?data.dataSetName + ":" + | |||||
data.dataSetVersion:'' }}</span></div> | |||||
</el-col> | </el-col> | ||||
<el-col :span="12"> | <el-col :span="12"> | ||||
<div>是否分布式:<span>{{ data.isDistributed?'是':'否' }}</span></div> | <div>是否分布式:<span>{{ data.isDistributed?'是':'否' }}</span></div> | ||||
@@ -27,7 +28,8 @@ | |||||
</el-row> | </el-row> | ||||
<el-row> | <el-row> | ||||
<el-col v-if="!show" :span="12"> | <el-col v-if="!show" :span="12"> | ||||
<div>资源规格:<span>{{ data.config[0].resourceSpecName + '' + data.config[0].resourceSpecPrice + '机时/h' }}</span> | |||||
<div>资源规格:<span>{{ data.config[0].resourceSpecName + '' + data.config[0].resourceSpecPrice + '机时/h' | |||||
}}</span> | |||||
</div> | </div> | ||||
</el-col> | </el-col> | ||||
<el-col v-if="!show" :span="12"> | <el-col v-if="!show" :span="12"> | ||||
@@ -47,14 +49,9 @@ | |||||
<el-divider /> | <el-divider /> | ||||
<div class="taskList">分布式任务列表</div> | <div class="taskList">分布式任务列表</div> | ||||
<div> | <div> | ||||
<el-table | |||||
:data="tableData" | |||||
style="width: 100%" | |||||
row-key="name" | |||||
:tree-props="{children: 'replicaStates', hasChildren: 'hasChildren'}" | |||||
default-expand-all | |||||
height="700" | |||||
> | |||||
<el-table :data="tableData" style="width: 100%" row-key="name" | |||||
:tree-props="{children: 'replicaStates', hasChildren: 'hasChildren'}" default-expand-all | |||||
height="700"> | |||||
<el-table-column prop="name" label="任务名称" width="200px" :show-overflow-tooltip="true" /> | <el-table-column prop="name" label="任务名称" width="200px" :show-overflow-tooltip="true" /> | ||||
<el-table-column label="是否主任务"> | <el-table-column label="是否主任务"> | ||||
<template slot-scope="scope"> | <template slot-scope="scope"> | ||||
@@ -67,7 +64,7 @@ | |||||
<el-table-column label="资源规格"> | <el-table-column label="资源规格"> | ||||
<template slot-scope="scope"> | <template slot-scope="scope"> | ||||
<span v-if="!scope.row.isChildren"> | <span v-if="!scope.row.isChildren"> | ||||
{{ scope.row.resourceSpecName + '' + scope.row.resourceSpecPrice + '机时/h' }} | |||||
{{ scope.row.resourceSpecName + '' + scope.row.resourceSpecPrice + '机时/h' }} | |||||
</span> | </span> | ||||
</template> | </template> | ||||
</el-table-column> | </el-table-column> | ||||
@@ -105,7 +102,7 @@ | |||||
} | } | ||||
}, | }, | ||||
computed: { | computed: { | ||||
show: function() { | |||||
show: function () { | |||||
if (this.data.isDistributed === true) { | if (this.data.isDistributed === true) { | ||||
return true | return true | ||||
} else { return false } | } else { return false } | ||||
@@ -131,7 +128,7 @@ | |||||
} | } | ||||
}, | }, | ||||
methods: { | methods: { | ||||
command: function(data) { | |||||
command: function (data) { | |||||
let command = data.command | let command = data.command | ||||
if (data.parameters != null && data.parameters.length != 0) { | if (data.parameters != null && data.parameters.length != 0) { | ||||
data.parameters.forEach( | data.parameters.forEach( | ||||
@@ -42,14 +42,14 @@ module.exports = { | |||||
}, | }, | ||||
proxy: { | proxy: { | ||||
[process.env.VUE_APP_BASE_API]: { | [process.env.VUE_APP_BASE_API]: { | ||||
target: 'http://192.168.204.155/', | |||||
target: 'http://192.168.202.71/', | |||||
changeOrigin: true, | changeOrigin: true, | ||||
pathRewrite: { | pathRewrite: { | ||||
['^' + process.env.VUE_APP_BASE_API]: '/openaiserver' | ['^' + process.env.VUE_APP_BASE_API]: '/openaiserver' | ||||
} | } | ||||
}, | }, | ||||
[process.env.VUE_APP_BASE_API2]: { | [process.env.VUE_APP_BASE_API2]: { | ||||
target: 'http://192.168.204.155/', | |||||
target: 'http://192.168.202.71/', | |||||
changeOrigin: true, | changeOrigin: true, | ||||
pathRewrite: { | pathRewrite: { | ||||
['^' + process.env.VUE_APP_BASE_API]: '' | ['^' + process.env.VUE_APP_BASE_API]: '' | ||||
@@ -76,6 +76,7 @@ message UserItem { | |||||
int32 gender = 7; | int32 gender = 7; | ||||
int32 status = 8; | int32 status = 8; | ||||
repeated string resourcePools = 9; | repeated string resourcePools = 9; | ||||
string desc=10; | |||||
} | } | ||||
message ListUserRequest { | message ListUserRequest { | ||||
@@ -111,6 +112,7 @@ message AddUserRequest { | |||||
string phone = 3 [(validate.rules).string = {pattern: "^(13|14|15|17|18|19)[0-9]{9}$", ignore_empty:true}]; | string phone = 3 [(validate.rules).string = {pattern: "^(13|14|15|17|18|19)[0-9]{9}$", ignore_empty:true}]; | ||||
string password = 4 [(validate.rules).string = {min_len: 8, max_len: 30}]; | string password = 4 [(validate.rules).string = {min_len: 8, max_len: 30}]; | ||||
int32 gender = 5 [(validate.rules).int32 = {in: [1,2]}]; | int32 gender = 5 [(validate.rules).int32 = {in: [1,2]}]; | ||||
string desc = 6 ; | |||||
} | } | ||||
message AddUserReply { | message AddUserReply { | ||||
@@ -125,6 +127,7 @@ message UpdateUserRequest { | |||||
string phone = 3 [(validate.rules).string = {pattern: "^(13|14|15|17|18|19)[0-9]{9}$", ignore_empty:true}]; | string phone = 3 [(validate.rules).string = {pattern: "^(13|14|15|17|18|19)[0-9]{9}$", ignore_empty:true}]; | ||||
int32 gender = 4 [(validate.rules).int32 = {in: [1,2],ignore_empty: true}]; | int32 gender = 4 [(validate.rules).int32 = {in: [1,2],ignore_empty: true}]; | ||||
repeated string resourcePools = 5; | repeated string resourcePools = 5; | ||||
string desc = 6 ; | |||||
} | } | ||||
UpdateItem user = 2 [(validate.rules).message.required = true]; | UpdateItem user = 2 [(validate.rules).message.required = true]; | ||||
} | } | ||||
@@ -12,7 +12,7 @@ data: | |||||
baseServerAddr: dns:///127.0.0.1:9001 | baseServerAddr: dns:///127.0.0.1:9001 | ||||
baseServerRequestTimeout: 30s | baseServerRequestTimeout: 30s | ||||
redis: | redis: | ||||
addr: 192.168.202.73:30635 | |||||
addr: 192.168.202.73:30207 | |||||
username: | username: | ||||
password: abcde | password: abcde | ||||
service: | service: |
@@ -2,6 +2,7 @@ package service | |||||
import ( | import ( | ||||
"context" | "context" | ||||
"github.com/jinzhu/copier" | |||||
pb "server/admin-server/api/v1" | pb "server/admin-server/api/v1" | ||||
"server/admin-server/internal/conf" | "server/admin-server/internal/conf" | ||||
"server/admin-server/internal/data" | "server/admin-server/internal/data" | ||||
@@ -10,8 +11,6 @@ import ( | |||||
"server/common/errors" | "server/common/errors" | ||||
"server/common/log" | "server/common/log" | ||||
"time" | "time" | ||||
"github.com/jinzhu/copier" | |||||
) | ) | ||||
type UserService struct { | type UserService struct { | ||||
@@ -58,6 +57,7 @@ func (s *UserService) ListUser(ctx context.Context, req *pb.ListUserRequest) (*p | |||||
Gender: int32(user.Gender), | Gender: int32(user.Gender), | ||||
Status: int32(user.Status), | Status: int32(user.Status), | ||||
ResourcePools: user.ResourcePools, | ResourcePools: user.ResourcePools, | ||||
Desc: user.Desc, | |||||
} | } | ||||
} | } | ||||
@@ -102,6 +102,7 @@ func (s *UserService) GetUser(ctx context.Context, req *pb.GetUserRequest) (*pb. | |||||
Gender: int32(user.Gender), | Gender: int32(user.Gender), | ||||
Status: int32(user.Status), | Status: int32(user.Status), | ||||
ResourcePools: user.ResourcePools, | ResourcePools: user.ResourcePools, | ||||
Desc: user.Desc, | |||||
}, | }, | ||||
Workspaces: workspaces, | Workspaces: workspaces, | ||||
}, nil | }, nil | ||||
@@ -114,12 +115,12 @@ func (s *UserService) AddUser(ctx context.Context, req *pb.AddUserRequest) (*pb. | |||||
Email: req.Email, | Email: req.Email, | ||||
Phone: req.Phone, | Phone: req.Phone, | ||||
Gender: innterapi.GenderType(req.Gender), | Gender: innterapi.GenderType(req.Gender), | ||||
Desc: req.Desc, | |||||
}) | }) | ||||
if err != nil { | if err != nil { | ||||
return nil, err | return nil, err | ||||
} | } | ||||
user := addUserReply.User | user := addUserReply.User | ||||
_, err = s.data.BillingClient.CreateBillingOwner(ctx, &innterapi.CreateBillingOwnerRequest{ | _, err = s.data.BillingClient.CreateBillingOwner(ctx, &innterapi.CreateBillingOwnerRequest{ | ||||
@@ -151,6 +152,7 @@ func (s *UserService) UpdateUser(ctx context.Context, req *pb.UpdateUserRequest) | |||||
Phone: req.User.Phone, | Phone: req.User.Phone, | ||||
Gender: innterapi.GenderType(req.User.Gender), | Gender: innterapi.GenderType(req.User.Gender), | ||||
ResourcePools: req.User.ResourcePools, | ResourcePools: req.User.ResourcePools, | ||||
Desc: req.User.Desc, | |||||
}) | }) | ||||
if err != nil { | if err != nil { | ||||
@@ -167,6 +169,7 @@ func (s *UserService) UpdateUser(ctx context.Context, req *pb.UpdateUserRequest) | |||||
Phone: result.User.Phone, | Phone: result.User.Phone, | ||||
Gender: int32(result.User.Gender), | Gender: int32(result.User.Gender), | ||||
Status: int32(result.User.Status), | Status: int32(result.User.Status), | ||||
Desc: result.User.Desc, | |||||
}, | }, | ||||
}, nil | }, nil | ||||
} | } | ||||
@@ -49,6 +49,7 @@ message UserItem { | |||||
repeated Bind bind = 10; | repeated Bind bind = 10; | ||||
string ftpUserName = 11; | string ftpUserName = 11; | ||||
repeated string resourcePools = 12; | repeated string resourcePools = 12; | ||||
string desc=13; | |||||
} | } | ||||
message Bind { | message Bind { | ||||
@@ -64,6 +65,7 @@ message AddUserRequest { | |||||
string password = 4 [(validate.rules).string = {min_len: 8, max_len: 30}]; | string password = 4 [(validate.rules).string = {min_len: 8, max_len: 30}]; | ||||
GenderType gender = 5 [(validate.rules).enum = {in: [1,2]}]; | GenderType gender = 5 [(validate.rules).enum = {in: [1,2]}]; | ||||
Bind bind = 6; | Bind bind = 6; | ||||
string desc=7; | |||||
} | } | ||||
message AddUserReply { | message AddUserReply { | ||||
@@ -99,6 +101,7 @@ message ListUserRequest { | |||||
string phone = 7 [(validate.rules).string = {pattern: "^(13|14|15|17|18|19)[0-9]{9}$", ignore_empty:true}]; | string phone = 7 [(validate.rules).string = {pattern: "^(13|14|15|17|18|19)[0-9]{9}$", ignore_empty:true}]; | ||||
string searchKey = 8 [(validate.rules).string = {max_len: 50}]; | string searchKey = 8 [(validate.rules).string = {max_len: 50}]; | ||||
UserStatus status = 9 [(validate.rules).enum = {defined_only: true}]; | UserStatus status = 9 [(validate.rules).enum = {defined_only: true}]; | ||||
string desc = 10; | |||||
} | } | ||||
message ListUserReply { | message ListUserReply { | ||||
@@ -116,6 +119,7 @@ message UpdateUserRequest { | |||||
UserStatus status = 7 [(validate.rules).enum = {defined_only: true}]; | UserStatus status = 7 [(validate.rules).enum = {defined_only: true}]; | ||||
repeated Bind bind = 8; | repeated Bind bind = 8; | ||||
repeated string resourcePools = 9; | repeated string resourcePools = 9; | ||||
string desc=10; | |||||
} | } | ||||
message UpdateUserReply { | message UpdateUserReply { | ||||
@@ -13,10 +13,10 @@ server: | |||||
data: | data: | ||||
database: | database: | ||||
driver: mysql | driver: mysql | ||||
source: root:root@tcp(192.168.204.155:30336)/octopus?charset=utf8&parseTime=True&loc=Local | |||||
source: root:root@tcp(192.168.202.73:30336)/octopus?charset=utf8&parseTime=True&loc=Local | |||||
kubernetes: | kubernetes: | ||||
masterUrl: https://192.168.204.155:6443/ | |||||
configPath: /home/hackmong/openi/155config | |||||
masterUrl: https://192.168.202.73:6443/ | |||||
configPath: ./73kubeconfig | |||||
minio: | minio: | ||||
base: | base: | ||||
endPoint: 192.168.202.73:31311 | endPoint: 192.168.202.73:31311 | ||||
@@ -36,11 +36,11 @@ data: | |||||
apiVersion: v1.0 | apiVersion: v1.0 | ||||
useSSL: false | useSSL: false | ||||
redis: | redis: | ||||
addr: 192.168.203.154:30635 | |||||
addr: 192.168.202.73:30635 | |||||
username: | username: | ||||
password: abcde | password: abcde | ||||
influxdb: | influxdb: | ||||
addr: 192.168.203.154:8086 | |||||
addr: 192.168.202.73:30086 | |||||
username: octopus | username: octopus | ||||
password: octopus | password: octopus | ||||
database: octopus | database: octopus | ||||
@@ -54,6 +54,7 @@ type User struct { | |||||
Bind Binds `gorm:"type:json;comment:'第三方账号绑定信息'"` | Bind Binds `gorm:"type:json;comment:'第三方账号绑定信息'"` | ||||
FtpUserName string `gorm:"type:varchar(100);uniqueIndex:ftpUserName;comment:'ftp用户名'"` | FtpUserName string `gorm:"type:varchar(100);uniqueIndex:ftpUserName;comment:'ftp用户名'"` | ||||
ResourcePools ResourcePools `gorm:"type:json;comment:'资源池'"` | ResourcePools ResourcePools `gorm:"type:json;comment:'资源池'"` | ||||
Desc string `gorm:"type:varchar(100);default:'';index;comment:'备注'"` | |||||
} | } | ||||
func (User) TableName() string { | func (User) TableName() string { | ||||
@@ -74,6 +75,7 @@ type UserList struct { | |||||
SearchKey string | SearchKey string | ||||
Status int32 | Status int32 | ||||
Bind Binds | Bind Binds | ||||
Desc string | |||||
} | } | ||||
func (u UserList) Where(db *gorm.DB) *gorm.DB { | func (u UserList) Where(db *gorm.DB) *gorm.DB { | ||||
@@ -155,6 +157,7 @@ type UserQuery struct { | |||||
Phone string | Phone string | ||||
Bind *Bind | Bind *Bind | ||||
FtpUserName string | FtpUserName string | ||||
Desc string | |||||
} | } | ||||
type UserAdd struct { | type UserAdd struct { | ||||
@@ -167,6 +170,7 @@ type UserAdd struct { | |||||
Status int32 | Status int32 | ||||
Bind *Bind | Bind *Bind | ||||
ResourcePools []string | ResourcePools []string | ||||
Desc string | |||||
} | } | ||||
type UserUpdate struct { | type UserUpdate struct { | ||||
@@ -179,12 +183,14 @@ type UserUpdate struct { | |||||
Bind Binds | Bind Binds | ||||
FtpUserName string | FtpUserName string | ||||
ResourcePools []string | ResourcePools []string | ||||
Desc string | |||||
} | } | ||||
type UserUpdateCond struct { | type UserUpdateCond struct { | ||||
Id string | Id string | ||||
Email string | Email string | ||||
Phone string | Phone string | ||||
Desc string | |||||
} | } | ||||
type UserListIn struct { | type UserListIn struct { | ||||
@@ -10,9 +10,8 @@ import ( | |||||
"gorm.io/gorm/clause" | "gorm.io/gorm/clause" | ||||
commerrors "server/common/errors" | |||||
"gorm.io/gorm" | "gorm.io/gorm" | ||||
commerrors "server/common/errors" | |||||
) | ) | ||||
type UserDao interface { | type UserDao interface { | ||||
@@ -71,7 +70,7 @@ func (d *userDao) Find(ctx context.Context, condition *model.UserQuery) (*model. | |||||
result = db.Where(&model.User{ | result = db.Where(&model.User{ | ||||
Id: condition.Id, | Id: condition.Id, | ||||
Email: condition.Email, | Email: condition.Email, | ||||
Phone: condition.Phone, | |||||
Phone: condition.Phone, | |||||
FtpUserName: condition.FtpUserName, | FtpUserName: condition.FtpUserName, | ||||
}).First(&user) | }).First(&user) | ||||
} else { | } else { | ||||
@@ -97,7 +96,6 @@ func (d *userDao) Find(ctx context.Context, condition *model.UserQuery) (*model. | |||||
} | } | ||||
result = db.Where(querySql, params...).First(&user) | result = db.Where(querySql, params...).First(&user) | ||||
} | } | ||||
if result.Error != nil { | if result.Error != nil { | ||||
if errors.Is(result.Error, gorm.ErrRecordNotFound) { | if errors.Is(result.Error, gorm.ErrRecordNotFound) { | ||||
return nil, nil | return nil, nil | ||||
@@ -123,6 +121,7 @@ func (d *userDao) Add(ctx context.Context, user *model.UserAdd) (*model.User, er | |||||
Status: user.Status, | Status: user.Status, | ||||
Bind: bindInfo, | Bind: bindInfo, | ||||
ResourcePools: user.ResourcePools, | ResourcePools: user.ResourcePools, | ||||
Desc: user.Desc, | |||||
} | } | ||||
result := db.Omit("ftp_user_name").Create(&u) | result := db.Omit("ftp_user_name").Create(&u) | ||||
@@ -142,6 +141,7 @@ func (d *userDao) Update(ctx context.Context, cond *model.UserUpdateCond, user * | |||||
Id: cond.Id, | Id: cond.Id, | ||||
Email: cond.Email, | Email: cond.Email, | ||||
Phone: cond.Phone, | Phone: cond.Phone, | ||||
Desc: cond.Desc, | |||||
} | } | ||||
result := d.db.Model(&condition).Updates(model.User{ | result := d.db.Model(&condition).Updates(model.User{ | ||||
@@ -154,6 +154,7 @@ func (d *userDao) Update(ctx context.Context, cond *model.UserUpdateCond, user * | |||||
Bind: user.Bind, | Bind: user.Bind, | ||||
FtpUserName: user.FtpUserName, | FtpUserName: user.FtpUserName, | ||||
ResourcePools: user.ResourcePools, | ResourcePools: user.ResourcePools, | ||||
Desc: user.Desc, | |||||
}) | }) | ||||
if result.Error != nil { | if result.Error != nil { | ||||
return nil, result.Error | return nil, result.Error | ||||
@@ -37,6 +37,7 @@ const ( | |||||
k8sTaskNamePrefix = "task" | k8sTaskNamePrefix = "task" | ||||
NoDistributedJobNum = 1 | NoDistributedJobNum = 1 | ||||
shmResource = "shm" | shmResource = "shm" | ||||
readonlyCodeDir = "/readonlycode" | |||||
) | ) | ||||
type trainJobService struct { | type trainJobService struct { | ||||
@@ -137,8 +138,11 @@ func (s *trainJobService) TrainJob(ctx context.Context, req *api.TrainJobRequest | |||||
return &api.TrainJobReply{JobId: trainJobId}, nil | return &api.TrainJobReply{JobId: trainJobId}, nil | ||||
} | } | ||||
func (s *trainJobService) buildCmd(config *model.Config) []string { | |||||
cmd := fmt.Sprintf("cd %s;%s ", s.conf.Service.DockerCodePath, config.Command) | |||||
func (s *trainJobService) buildCmd(job *model.TrainJob, config *model.Config) []string { | |||||
cmd := config.Command | |||||
if job.AlgorithmId != "" { | |||||
cmd = fmt.Sprintf("cp -r %s/* %s;cd %s;%s ", readonlyCodeDir, s.conf.Service.DockerCodePath, s.conf.Service.DockerCodePath, config.Command) | |||||
} | |||||
if len(config.Parameters) == 0 { | if len(config.Parameters) == 0 { | ||||
return []string{"sh", "-c", cmd} | return []string{"sh", "-c", cmd} | ||||
} else { | } else { | ||||
@@ -474,18 +478,6 @@ func (s *trainJobService) submitJob(ctx context.Context, job *model.TrainJob, st | |||||
minAvailable += i.TaskNumber | minAvailable += i.TaskNumber | ||||
//挂载卷 | //挂载卷 | ||||
volumeMounts := []v1.VolumeMount{ | volumeMounts := []v1.VolumeMount{ | ||||
{ | |||||
Name: "data", | |||||
MountPath: s.conf.Service.DockerCodePath, | |||||
SubPath: startJobInfo.algorithmPath, | |||||
ReadOnly: true, | |||||
}, | |||||
{ | |||||
Name: "data", | |||||
MountPath: s.conf.Service.DockerDatasetPath, | |||||
SubPath: startJobInfo.datasetPath, | |||||
ReadOnly: true, | |||||
}, | |||||
{ | { | ||||
Name: "data", | Name: "data", | ||||
MountPath: s.conf.Service.DockerModelPath, | MountPath: s.conf.Service.DockerModelPath, | ||||
@@ -504,6 +496,32 @@ func (s *trainJobService) submitJob(ctx context.Context, job *model.TrainJob, st | |||||
}, | }, | ||||
} | } | ||||
if startJobInfo.algorithmPath != "" { | |||||
volumeMounts = append(volumeMounts, | |||||
v1.VolumeMount{ | |||||
Name: "data", | |||||
MountPath: readonlyCodeDir, | |||||
SubPath: startJobInfo.algorithmPath, | |||||
ReadOnly: true, | |||||
}, | |||||
v1.VolumeMount{ | |||||
Name: "code", | |||||
MountPath: s.conf.Service.DockerCodePath, | |||||
ReadOnly: false, | |||||
}) | |||||
} | |||||
if startJobInfo.datasetPath != "" { | |||||
volumeMounts = append(volumeMounts, | |||||
v1.VolumeMount{ | |||||
Name: "data", | |||||
MountPath: s.conf.Service.DockerDatasetPath, | |||||
SubPath: startJobInfo.datasetPath, | |||||
ReadOnly: true, | |||||
}) | |||||
} | |||||
volumes := []v1.Volume{ | volumes := []v1.Volume{ | ||||
{ | { | ||||
Name: "data", | Name: "data", | ||||
@@ -520,6 +538,11 @@ func (s *trainJobService) submitJob(ctx context.Context, job *model.TrainJob, st | |||||
Path: "/etc/localtime", | Path: "/etc/localtime", | ||||
}}, | }}, | ||||
}, | }, | ||||
{ | |||||
Name: "code", | |||||
VolumeSource: v1.VolumeSource{ | |||||
EmptyDir: &v1.EmptyDirVolumeSource{}}, | |||||
}, | |||||
} | } | ||||
//add shareMemory for each subTask | //add shareMemory for each subTask | ||||
@@ -562,7 +585,7 @@ func (s *trainJobService) submitJob(ctx context.Context, job *model.TrainJob, st | |||||
Limits: startJobInfo.specs[i.ResourceSpecId].resources, | Limits: startJobInfo.specs[i.ResourceSpecId].resources, | ||||
}, | }, | ||||
VolumeMounts: volumeMounts, | VolumeMounts: volumeMounts, | ||||
Command: s.buildCmd(i), | |||||
Command: s.buildCmd(job, i), | |||||
}, | }, | ||||
}, | }, | ||||
NodeSelector: startJobInfo.specs[i.ResourceSpecId].nodeSelectors, | NodeSelector: startJobInfo.specs[i.ResourceSpecId].nodeSelectors, | ||||
@@ -2,17 +2,15 @@ package user | |||||
import ( | import ( | ||||
"context" | "context" | ||||
"golang.org/x/crypto/bcrypt" | |||||
api "server/base-server/api/v1" | api "server/base-server/api/v1" | ||||
"server/base-server/internal/common" | "server/base-server/internal/common" | ||||
"server/base-server/internal/conf" | "server/base-server/internal/conf" | ||||
"server/base-server/internal/data" | "server/base-server/internal/data" | ||||
"server/base-server/internal/data/dao/model" | "server/base-server/internal/data/dao/model" | ||||
"server/common/errors" | "server/common/errors" | ||||
"server/common/utils" | |||||
"server/common/log" | "server/common/log" | ||||
"golang.org/x/crypto/bcrypt" | |||||
"server/common/utils" | |||||
) | ) | ||||
type UserService struct { | type UserService struct { | ||||
@@ -52,6 +50,7 @@ func (s *UserService) ListUser(ctx context.Context, req *api.ListUserRequest) (* | |||||
SearchKey: req.SearchKey, | SearchKey: req.SearchKey, | ||||
Phone: req.Phone, | Phone: req.Phone, | ||||
Status: int32(req.Status), | Status: int32(req.Status), | ||||
Desc: req.Desc, | |||||
}) | }) | ||||
if err != nil { | if err != nil { | ||||
return nil, err | return nil, err | ||||
@@ -91,6 +90,7 @@ func (s *UserService) ListUser(ctx context.Context, req *api.ListUserRequest) (* | |||||
UpdatedAt: user.UpdatedAt.Unix(), | UpdatedAt: user.UpdatedAt.Unix(), | ||||
Bind: bindInfo, | Bind: bindInfo, | ||||
ResourcePools: user.ResourcePools, | ResourcePools: user.ResourcePools, | ||||
Desc: user.Desc, | |||||
} | } | ||||
users[idx] = item | users[idx] = item | ||||
} | } | ||||
@@ -156,6 +156,7 @@ func (s *UserService) FindUser(ctx context.Context, req *api.FindUserRequest) (* | |||||
UpdatedAt: user.UpdatedAt.Unix(), | UpdatedAt: user.UpdatedAt.Unix(), | ||||
Bind: bindInfo, | Bind: bindInfo, | ||||
ResourcePools: user.ResourcePools, | ResourcePools: user.ResourcePools, | ||||
Desc: user.Desc, | |||||
}, | }, | ||||
} | } | ||||
@@ -238,6 +239,7 @@ func (s *UserService) AddUser(ctx context.Context, req *api.AddUserRequest) (*ap | |||||
user.Status = int32(api.UserStatus_ACTIVITY) | user.Status = int32(api.UserStatus_ACTIVITY) | ||||
user.Bind = cond.Bind | user.Bind = cond.Bind | ||||
user.ResourcePools = []string{s.conf.Service.Resource.DefaultPoolName} | user.ResourcePools = []string{s.conf.Service.Resource.DefaultPoolName} | ||||
user.Desc=req.Desc | |||||
u, err := s.data.UserDao.Add(ctx, &user) | u, err := s.data.UserDao.Add(ctx, &user) | ||||
if err != nil { | if err != nil { | ||||
return nil, err | return nil, err | ||||
@@ -295,6 +297,7 @@ func (s *UserService) UpdateUser(ctx context.Context, req *api.UpdateUserRequest | |||||
Gender: int32(req.Gender), | Gender: int32(req.Gender), | ||||
Status: int32(req.Status), | Status: int32(req.Status), | ||||
ResourcePools: req.ResourcePools, | ResourcePools: req.ResourcePools, | ||||
Desc: req.Desc, | |||||
} | } | ||||
if len(bindInfo) > 0 { | if len(bindInfo) > 0 { | ||||
user.Bind = bindInfo | user.Bind = bindInfo | ||||
@@ -307,7 +310,6 @@ func (s *UserService) UpdateUser(ctx context.Context, req *api.UpdateUserRequest | |||||
} | } | ||||
user.Password = string(password) | user.Password = string(password) | ||||
} | } | ||||
result, err := s.data.UserDao.Update(ctx, &model.UserUpdateCond{Id: userId}, &user) | result, err := s.data.UserDao.Update(ctx, &model.UserUpdateCond{Id: userId}, &user) | ||||
if err != nil { | if err != nil { | ||||
return nil, err | return nil, err | ||||
@@ -333,6 +335,7 @@ func (s *UserService) UpdateUser(ctx context.Context, req *api.UpdateUserRequest | |||||
Status: api.UserStatus(result.Status), | Status: api.UserStatus(result.Status), | ||||
Password: result.Password, | Password: result.Password, | ||||
Bind: bindInfo2, | Bind: bindInfo2, | ||||
Desc: result.Desc, | |||||
}, | }, | ||||
}, nil | }, nil | ||||
} | } | ||||
Dear OpenI User
Thank you for your continuous support to the Openl Qizhi Community AI Collaboration Platform. In order to protect your usage rights and ensure network security, we updated the Openl Qizhi Community AI Collaboration Platform Usage Agreement in January 2024. The updated agreement specifies that users are prohibited from using intranet penetration tools. After you click "Agree and continue", you can continue to use our services. Thank you for your cooperation and understanding.
For more agreement content, please refer to the《Openl Qizhi Community AI Collaboration Platform Usage Agreement》