Merge branch 'wvp-28181-2.0'

# Conflicts:
#	sql/update.sql
#	src/main/java/com/genersoft/iot/vmp/gb28181/transmit/event/request/impl/InviteRequestProcessor.java
#	src/main/java/com/genersoft/iot/vmp/media/zlm/ZLMHttpHookListener.java
#	src/main/java/com/genersoft/iot/vmp/media/zlm/ZLMRTPServerFactory.java
#	src/main/java/com/genersoft/iot/vmp/service/impl/MediaServerServiceImpl.java
#	src/main/java/com/genersoft/iot/vmp/service/impl/MediaServiceImpl.java
#	src/main/java/com/genersoft/iot/vmp/service/impl/PlayServiceImpl.java
This commit is contained in:
648540858
2022-08-09 14:41:21 +08:00
204 changed files with 4646 additions and 1896 deletions

View File

@@ -86,7 +86,7 @@ export default {
}).then(function (res) {
console.log(JSON.stringify(res));
if (res.data.code == 0 && res.data.msg == "success") {
that.$cookies.set("session", {"username": that.username}) ;
that.$cookies.set("session", {"username": that.username,"roleId":res.data.data.role.id}) ;
//登录成功后
that.cancelEnterkeyDefaultAction();
that.$router.push('/');

View File

@@ -143,7 +143,7 @@ export default {
});
},
chooseChannel: function(platform) {
this.$refs.chooseChannelDialog.openDialog(platform.serverGBId, platform.name, platform.catalogId, this.initData)
this.$refs.chooseChannelDialog.openDialog(platform.serverGBId, platform.name, platform.catalogId, platform.treeType, this.initData)
},
initData: function() {
this.getPlatformList();

View File

@@ -34,6 +34,8 @@
<el-button icon="el-icon-delete" size="mini" style="margin-right: 1rem;"
:disabled="multipleSelection.length === 0" type="danger" @click="batchDel">批量移除
</el-button>
<el-button icon="el-icon-plus" size="mini" style="margin-right: 1rem;" type="primary" @click="addStream">添加通道
</el-button>
<el-button icon="el-icon-refresh-right" circle size="mini" @click="refresh()"></el-button>
</div>
</div>
@@ -56,20 +58,25 @@
<el-table-column label="开始时间" min-width="200">
<template slot-scope="scope">
<el-button-group>
{{ dateFormat(parseInt(scope.row.createStamp)) }}
{{ scope.row.pushTime == null? "-":scope.row.pushTime }}
</el-button-group>
</template>
</el-table-column>
<el-table-column label="正在推流" min-width="100">
<template slot-scope="scope">
{{ (scope.row.status == false && scope.row.gbId == null) || scope.row.status ? '是' : '否' }}
{{scope.row.pushIng ? '是' : '否' }}
</template>
</el-table-column>
<el-table-column label="本平台推流" min-width="100">
<template slot-scope="scope">
{{scope.row.pushIng && !!scope.row.self ? '是' : '否' }}
</template>
</el-table-column>
<el-table-column label="操作" min-width="360" fixed="right">
<template slot-scope="scope">
<el-button size="medium" icon="el-icon-video-play"
v-if="(scope.row.status == false && scope.row.gbId == null) || scope.row.status"
v-if="scope.row.pushIng === true"
@click="playPush(scope.row)" type="text">播放
</el-button>
<el-divider direction="vertical"></el-divider>
@@ -103,7 +110,7 @@
<script>
import streamProxyEdit from './dialog/StreamProxyEdit.vue'
import devicePlayer from './dialog/devicePlayer.vue'
import addStreamTOGB from './dialog/addStreamTOGB.vue'
import addStreamTOGB from './dialog/pushStreamEdit.vue'
import uiHeader from '../layout/UiHeader.vue'
import importChannel from './dialog/importChannel.vue'
import MediaServer from './service/MediaServer'
@@ -195,10 +202,15 @@ export default {
}
}).then(function (res) {
that.getListLoading = false;
that.$refs.devicePlayer.openDialog("streamPlay", null, null, {
streamInfo: res.data.data,
hasAudio: true
});
if (res.data.code === 0 ) {
that.$refs.devicePlayer.openDialog("streamPlay", null, null, {
streamInfo: res.data.data,
hasAudio: true
});
}else {
that.$message.error(res.data.msg);
}
}).catch(function (error) {
console.error(error);
that.getListLoading = false;
@@ -242,24 +254,14 @@ export default {
console.error(error);
});
},
dateFormat: function (/** timestamp=0 **/) {
let ts = arguments[0] || 0;
let t, y, m, d, h, i, s;
t = ts ? new Date(ts) : new Date();
y = t.getFullYear();
m = t.getMonth() + 1;
d = t.getDate();
h = t.getHours();
i = t.getMinutes();
s = t.getSeconds();
// 可根据需要在这里定义时间格式
return y + '-' + (m < 10 ? '0' + m : m) + '-' + (d < 10 ? '0' + d : d) + ' ' + (h < 10 ? '0' + h : h) + ':' + (i < 10 ? '0' + i : i) + ':' + (s < 10 ? '0' + s : s);
},
importChannel: function () {
this.$refs.importChannel.openDialog(() => {
})
},
addStream: function (){
this.$refs.addStreamTOGB.openDialog(null, this.initData);
},
batchDel: function () {
this.$confirm(`确定删除选中的${this.multipleSelection.length}个通道?`, '提示', {
confirmButtonText: '确定',

View File

@@ -0,0 +1,236 @@
<template>
<div id="app" style="width: 100%">
<div class="page-header">
<div class="page-title">用户列表</div>
<div class="page-header-btn">
<el-button icon="el-icon-plus" size="mini" style="margin-right: 1rem;" type="primary" @click="addUser">
添加用户
</el-button>
</div>
</div>
<!--用户列表-->
<el-table :data="userList" style="width: 100%;font-size: 12px;" :height="winHeight"
header-row-class-name="table-header">
<el-table-column prop="username" label="用户名" min-width="160"/>
<el-table-column prop="pushKey" label="pushkey" min-width="160"/>
<el-table-column prop="role.name" label="类型" min-width="160"/>
<el-table-column label="操作" min-width="450" fixed="right">
<template slot-scope="scope">
<el-button size="medium" icon="el-icon-edit" type="text" @click="edit(scope.row)">修改密码</el-button>
<el-divider direction="vertical"></el-divider>
<el-button size="medium" icon="el-icon-edit" type="text" @click="changePushKey(scope.row)">修改pushkey</el-button>
<el-divider direction="vertical"></el-divider>
<el-button size="medium" icon="el-icon-delete" type="text" @click="deleteUser(scope.row)"
style="color: #f56c6c">删除
</el-button>
</template>
</el-table-column>
</el-table>
<changePasswordForAdmin ref="changePasswordForAdmin"></changePasswordForAdmin>
<changePushKey ref="changePushKey"></changePushKey>
<addUser ref="addUser"></addUser>
<el-pagination
style="float: right"
@size-change="handleSizeChange"
@current-change="currentChange"
:current-page="currentPage"
:page-size="count"
:page-sizes="[15, 25, 35, 50]"
layout="total, sizes, prev, pager, next"
:total="total">
</el-pagination>
</div>
</template>
<script>
import uiHeader from '../layout/UiHeader.vue'
import changePasswordForAdmin from './dialog/changePasswordForAdmin.vue'
import changePushKey from './dialog/changePushKey.vue'
import addUser from '../components/dialog/addUser.vue'
export default {
name: 'userManager',
components: {
uiHeader,
changePasswordForAdmin,
changePushKey,
addUser
},
data() {
return {
userList: [], //设备列表
currentUser: {}, //当前操作设备对象
videoComponentList: [],
updateLooper: 0, //数据刷新轮训标志
currentUserLenth: 0,
winHeight: window.innerHeight - 200,
currentPage: 1,
count: 15,
total: 0,
getUserListLoading: false
};
},
mounted() {
this.initData();
this.updateLooper = setInterval(this.initData, 10000);
},
destroyed() {
this.$destroy('videojs');
clearTimeout(this.updateLooper);
},
methods: {
initData: function () {
this.getUserList();
},
currentChange: function (val) {
this.currentPage = val;
this.getUserList();
},
handleSizeChange: function (val) {
this.count = val;
this.getUserList();
},
getUserList: function () {
let that = this;
this.getUserListLoading = true;
this.$axios({
method: 'get',
url: `/api/user/users`,
params: {
page: that.currentPage,
count: that.count
}
}).then(function (res) {
that.total = res.data.total;
that.userList = res.data.list;
that.getUserListLoading = false;
}).catch(function (error) {
that.getUserListLoading = false;
});
},
edit: function (row) {
this.$refs.changePasswordForAdmin.openDialog(row, () => {
this.$refs.changePasswordForAdmin.close();
this.$message({
showClose: true,
message: "密码修改成功",
type: "success",
});
setTimeout(this.getUserList, 200)
})
},
deleteUser: function (row) {
let msg = "确定删除此用户?"
if (row.online !== 0) {
msg = "<strong>确定删除此用户?</strong>"
}
this.$confirm(msg, '提示', {
dangerouslyUseHTMLString: true,
confirmButtonText: '确定',
cancelButtonText: '取消',
center: true,
type: 'warning'
}).then(() => {
this.$axios({
method: 'delete',
url: `/api/user/delete?id=${row.id}`
}).then((res) => {
this.getUserList();
}).catch((error) => {
console.error(error);
});
}).catch(() => {
});
},
changePushKey: function (row) {
this.$refs.changePushKey.openDialog(row, () => {
this.$refs.changePushKey.close();
this.$message({
showClose: true,
message: "pushKey修改成功",
type: "success",
});
setTimeout(this.getUserList, 200)
})
},
addUser: function () {
// this.$refs.addUser.openDialog()
this.$refs.addUser.openDialog( () => {
this.$refs.addUser.close();
this.$message({
showClose: true,
message: "用户添加成功",
type: "success",
});
setTimeout(this.getUserList, 200)
})
}
}
}
</script>
<style>
.videoList {
display: flex;
flex-wrap: wrap;
align-content: flex-start;
}
.video-item {
position: relative;
width: 15rem;
height: 10rem;
margin-right: 1rem;
background-color: #000000;
}
.video-item-img {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
margin: auto;
width: 100%;
height: 100%;
}
.video-item-img:after {
content: "";
display: inline-block;
position: absolute;
z-index: 2;
top: 0;
bottom: 0;
left: 0;
right: 0;
margin: auto;
width: 3rem;
height: 3rem;
background-image: url("../assets/loading.png");
background-size: cover;
background-color: #000000;
}
.video-item-title {
position: absolute;
bottom: 0;
color: #000000;
background-color: #ffffff;
line-height: 1.5rem;
padding: 0.3rem;
width: 14.4rem;
}
</style>

View File

@@ -32,7 +32,7 @@
<el-button v-if="!showTree" icon="iconfont icon-tree" circle size="mini" @click="switchTree()"></el-button>
</div>
</div>
<devicePlayer ref="devicePlayer" v-loading="isLoging"></devicePlayer>
<devicePlayer ref="devicePlayer" ></devicePlayer>
<el-container v-loading="isLoging" style="height: 82vh;">
<el-aside width="auto" style="height: 82vh; background-color: #ffffff; overflow: auto" v-if="showTree" >
<DeviceTree ref="deviceTree" :device="device" :onlyCatalog="true" :clickEvent="treeNodeClickEvent" ></DeviceTree>
@@ -124,7 +124,6 @@
import devicePlayer from './dialog/devicePlayer.vue'
import uiHeader from '../layout/UiHeader.vue'
import moment from "moment";
import DviceService from "./service/DeviceService";
import DeviceService from "./service/DeviceService";
import DeviceTree from "./common/DeviceTree";
@@ -318,7 +317,7 @@ export default {
changeSubchannel(itemData) {
this.beforeUrl = this.$router.currentRoute.path;
var url = `/${this.$router.currentRoute.name}/${this.$router.currentRoute.params.deviceId}/${itemData.channelId}/${this.$router.currentRoute.params.count}/1`
var url = `/${this.$router.currentRoute.name}/${this.$router.currentRoute.params.deviceId}/${itemData.channelId}`
this.$router.push(url).then(() => {
this.searchSrt = "";
this.channelType = "";

View File

@@ -5,8 +5,8 @@
<i v-if="!playing" class="iconfont icon-play jessibuca-btn" @click="playBtnClick"></i>
<i v-if="playing" class="iconfont icon-pause jessibuca-btn" @click="pause"></i>
<i class="iconfont icon-stop jessibuca-btn" @click="destroy"></i>
<i v-if="isNotMute" class="iconfont icon-audio-high jessibuca-btn" @click="jessibuca.mute()"></i>
<i v-if="!isNotMute" class="iconfont icon-audio-mute jessibuca-btn" @click="jessibuca.cancelMute()"></i>
<i v-if="isNotMute" class="iconfont icon-audio-high jessibuca-btn" @click="mute()"></i>
<i v-if="!isNotMute" class="iconfont icon-audio-mute jessibuca-btn" @click="cancelMute()"></i>
</div>
<div class="buttons-box-right">
<span class="jessibuca-btn">{{ kBps }} kb/s</span>
@@ -243,6 +243,16 @@ export default {
this.err = "";
this.performance = "";
},
mute: function () {
if (jessibucaPlayer[this._uid]) {
jessibucaPlayer[this._uid].mute();
}
},
cancelMute: function () {
if (jessibucaPlayer[this._uid]) {
jessibucaPlayer[this._uid].cancelMute();
}
},
destroy: function () {
if (jessibucaPlayer[this._uid]) {
jessibucaPlayer[this._uid].destroy();

View File

@@ -324,7 +324,7 @@ export default {
*/
getThreadsLoad: function () {
let that = this;
if (that.mediaServerChoose != null) {
if (!!that.mediaServerChoose) {
this.$axios({
method: 'get',
url: '/zlm/' + that.mediaServerChoose + '/index/api/getThreadsLoad'
@@ -375,7 +375,7 @@ export default {
},
getLoadCount: function () {
let that = this;
if (that.mediaServerChoose != null) {
if (!!that.mediaServerChoose) {
that.mediaServer.getMediaServer(that.mediaServerChoose, (data) => {
if (data.code == 0) {
that.loadCount = data.data.count
@@ -473,42 +473,46 @@ export default {
},
getAllSession: function () {
let that = this;
that.allSessionData = [];
this.$axios({
method: 'get',
url: '/zlm/' + that.mediaServerChoose + '/index/api/getAllSession'
}).then(function (res) {
res.data.data.forEach(item => {
let data = {
peer_ip: item.peer_ip,
local_ip: item.local_ip,
typeid: item.typeid,
id: item.id
};
that.allSessionData.push(data);
this.allSessionData = [];
if (!!this.mediaServerChoose) {
this.$axios({
method: 'get',
url: '/zlm/' + this.mediaServerChoose + '/index/api/getAllSession'
}).then((res)=> {
res.data.data.forEach(item => {
let data = {
peer_ip: item.peer_ip,
local_ip: item.local_ip,
typeid: item.typeid,
id: item.id
};
this.allSessionData.push(data);
});
});
});
}
},
getServerConfig: function () {
let that = this;
this.$axios({
method: 'get',
url: '/zlm/' + that.mediaServerChoose + '/index/api/getServerConfig'
}).then(function (res) {
let info = res.data.data[0];
let serverInfo = {}
for (let i = 0; i < Object.keys(info).length; i++) {
let key = Object.keys(info)[i];
let group = key.substring(0, key.indexOf("."))
let itemKey = key.substring(key.indexOf(".") + 1)
if (!serverInfo[group]) serverInfo[group] = {}
serverInfo[group][itemKey] = info[key]
}
if (!!this.mediaServerChoose) {
this.$axios({
method: 'get',
url: '/zlm/' + this.mediaServerChoose + '/index/api/getServerConfig'
}).then((res)=> {
let info = res.data.data[0];
let serverInfo = {}
for (let i = 0; i < Object.keys(info).length; i++) {
let key = Object.keys(info)[i];
let group = key.substring(0, key.indexOf("."))
let itemKey = key.substring(key.indexOf(".") + 1)
if (!serverInfo[group]) serverInfo[group] = {}
serverInfo[group][itemKey] = info[key]
}
this.serverConfig = serverInfo;
this.visible = true;
});
}
that.serverConfig = serverInfo;
that.visible = true;
});
},
getWVPServerConfig: function () {
let that = this;
@@ -531,6 +535,14 @@ export default {
},
reStartServer: function () {
let that = this;
if (!!!this.mediaServerChoose) {
this.$message({
type: 'info',
message: '未选择节点'
});
return;
}
this.$confirm('此操作将重启媒体服务器, 是否继续?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
@@ -571,17 +583,19 @@ export default {
console.log(JSON.stringify(tabledata[index]));
},
deleteSession: function (id) {
let that = this;
this.$axios({
method: 'get',
url: '/zlm/' + that.mediaServerChoose + '/index/api/kick_session?id=' + id
}).then(function (res) {
that.getAllSession();
that.$message({
type: 'success',
message: '删除成功!'
if (!!this.mediaServerChoose) {
this.$axios({
method: 'get',
url: '/zlm/' + this.mediaServerChoose + '/index/api/kick_session?id=' + id
}).then((res)=>{
this.getAllSession();
this.$message({
type: 'success',
message: '删除成功!'
});
});
});
}
},
getNameFromKey: function (key) {
let nameData = {

View File

@@ -63,34 +63,39 @@ export default {
}
if (res.data.data != null) {
if (res.data.data.total == 0) {
if (res.data.data.errorMsg !== null ){
this.msg = res.data.data.errorMsg;
this.syncStatus = "exception"
}else {
this.msg = `等待同步中`;
this.timmer = setTimeout(this.getProgress, 300)
}
}else {
if (res.data.data.total == res.data.data.current) {
this.syncStatus = "success"
this.percentage = 100;
this.msg = '同步成功';
}else {
if (res.data.syncIng) {
if (res.data.data.total == 0) {
if (res.data.data.errorMsg !== null ){
this.msg = res.data.data.errorMsg;
this.syncStatus = "exception"
}else {
this.total = res.data.data.total;
this.current = res.data.data.current;
this.percentage = Math.floor(Number(res.data.data.current)/Number(res.data.data.total)* 10000)/100;
this.msg = `同步中...[${res.data.data.current}/${res.data.data.total}]`;
this.msg = `等待同步中`;
this.timmer = setTimeout(this.getProgress, 300)
}
}else {
if (res.data.data.total == res.data.data.current) {
this.syncStatus = "success"
this.percentage = 100;
this.msg = '同步成功';
}else {
if (res.data.data.errorMsg !== null ){
this.msg = res.data.data.errorMsg;
this.syncStatus = "exception"
}else {
this.total = res.data.data.total;
this.current = res.data.data.current;
this.percentage = Math.floor(Number(res.data.data.current)/Number(res.data.data.total)* 10000)/100;
this.msg = `同步中...[${res.data.data.current}/${res.data.data.total}]`;
this.timmer = setTimeout(this.getProgress, 300)
}
}
}
}else {
this.syncStatus = "success"
this.percentage = 100;
this.msg = '同步成功';
}
}
}else {
if (this.syncFlag) {
this.syncStatus = "success"

View File

@@ -0,0 +1,159 @@
<template>
<div id="addUser" v-loading="isLoging">
<el-dialog
title="添加用户"
width="40%"
top="2rem"
:close-on-click-modal="false"
:visible.sync="showDialog"
:destroy-on-close="true"
@close="close()"
>
<div id="shared" style="margin-right: 20px;">
<el-form ref="passwordForm" :rules="rules" status-icon label-width="80px">
<el-form-item label="用户名" prop="username">
<el-input v-model="username" autocomplete="off"></el-input>
</el-form-item>
<el-form-item label="用户类型" prop="roleId" >
<el-select v-model="roleId" placeholder="请选择" style="width: 100%">
<el-option
v-for="item in options"
:key="item.id"
:label="item.name"
:value="item.id">
</el-option>
</el-select>
</el-form-item>
<el-form-item label="密码" prop="password">
<el-input v-model="password" autocomplete="off"></el-input>
</el-form-item>
<el-form-item label="确认密码" prop="confirmPassword">
<el-input v-model="confirmPassword" autocomplete="off"></el-input>
</el-form-item>
<el-form-item>
<div style="float: right;">
<el-button type="primary" @click="onSubmit">保存</el-button>
<el-button @click="close">取消</el-button>
</div>
</el-form-item>
</el-form>
</div>
</el-dialog>
</div>
</template>
<script>
export default {
name: "addUser",
props: {},
computed: {},
created() {
this.getAllRole();
},
data() {
let validatePass1 = (rule, value, callback) => {
if (value === '') {
callback(new Error('请输入新密码'));
} else {
if (this.confirmPassword !== '') {
this.$refs.passwordForm.validateField('confirmPassword');
}
callback();
}
};
let validatePass2 = (rule, value, callback) => {
if (this.confirmPassword === '') {
callback(new Error('请再次输入密码'));
} else if (this.confirmPassword !== this.password) {
callback(new Error('两次输入密码不一致!'));
} else {
callback();
}
};
return {
value:"",
options: [],
loading: false,
username: null,
password: null,
roleId: null,
confirmPassword: null,
listChangeCallback: null,
showDialog: false,
isLoging: false,
rules: {
newPassword: [{required: true, validator: validatePass1, trigger: "blur"}, {
pattern: /^(?=.*[a-zA-Z])(?=.*\d)(?=.*[~!@#$%^&*()_+`\-={}:";'<>?,.\/]).{8,20}$/,
message: "密码长度在8-20位之间,由字母+数字+特殊字符组成",
},],
confirmPassword: [{required: true, validator: validatePass2, trigger: "blur"}],
},
};
},
methods: {
openDialog: function (callback) {
this.listChangeCallback = callback;
this.showDialog = true;
},
onSubmit: function () {
this.$axios({
method: 'post',
url: "/api/user/add",
params: {
username: this.username,
password: this.password,
roleId: this.roleId
}
}).then((res) => {
if (res.data.code === 0) {
this.$message({
showClose: true,
message: '添加成功',
type: 'success',
});
this.showDialog = false;
this.listChangeCallback()
} else {
this.$message({
showClose: true,
message: res.data.msg,
type: 'error'
});
}
}).catch((error) => {
console.error(error)
});
},
close: function () {
this.showDialog = false;
this.password = null;
this.confirmPassword = null;
this.username = null;
this.roleId = null;
},
getAllRole:function () {
this.$axios({
method: 'get',
url: "/api/role/all"
}).then((res) => {
this.loading = true;
console.info(res)
res.data
console.info(res.data.code)
if (res.data.code === 0) {
console.info(res.data.data)
this.options=res.data.data
}
}).catch((error) => {
console.error(error)
});
}
},
};
</script>

View File

@@ -49,11 +49,42 @@ export default {
props: ['platformId'],
created() {},
data() {
let checkId = (rule, value, callback) => {
console.log("checkId")
console.log(this.treeType)
console.log(rule)
console.log(value)
console.log(value.length)
console.log(this.level)
if (!value) {
return callback(new Error('编号不能为空'));
}
if (this.treeType === "BusinessGroup" && value.length !== 20) {
return callback(new Error('编号必须由20位数字组成'));
}
if (this.treeType === "CivilCode" && value.length <= 8 && value.length%2 !== 0) {
return callback(new Error('行政区划必须是八位以下的偶数个数字组成'));
}
if (this.treeType === "BusinessGroup") {
let catalogType = value.substring(10, 13);
console.log(catalogType)
// 216 为虚拟组织 215 为业务分组;目录第一级必须为业务分组, 业务分组下为虚拟组织,虚拟组织下可以有其他虚拟组织
if (this.level === 1 && catalogType !== "215") {
return callback(new Error('业务分组模式下第一层目录的编号11到13位必须为215'));
}
if (this.level > 1 && catalogType !== "216") {
return callback(new Error('业务分组模式下第一层以下目录的编号11到13位必须为216'));
}
}
callback();
}
return {
submitCallback: null,
showDialog: false,
isLoging: false,
isEdit: false,
treeType: null,
level: 0,
form: {
id: null,
name: null,
@@ -62,12 +93,12 @@ export default {
},
rules: {
name: [{ required: true, message: "请输入名称", trigger: "blur" }],
id: [{ required: true, message: "请输入ID", trigger: "blur" }]
id: [{ required: true, trigger: "blur",validator: checkId }]
},
};
},
methods: {
openDialog: function (isEdit, id, name, parentId, callback) {
openDialog: function (isEdit, id, name, parentId, treeType, level, callback) {
console.log("parentId: " + parentId)
console.log(this.form)
this.isEdit = isEdit;
@@ -77,6 +108,8 @@ export default {
this.form.parentId = parentId;
this.showDialog = true;
this.submitCallback = callback;
this.treeType = treeType;
this.level = level;
},
onSubmit: function () {
console.log("onSubmit");

View File

@@ -0,0 +1,121 @@
<template>
<div id="changePassword" v-loading="isLoging">
<el-dialog
title="修改密码"
width="40%"
top="2rem"
:close-on-click-modal="false"
:visible.sync="showDialog"
:destroy-on-close="true"
@close="close()"
>
<div id="shared" style="margin-right: 20px;">
<el-form ref="passwordForm" :rules="rules" status-icon label-width="80px">
<el-form-item label="新密码" prop="newPassword" >
<el-input v-model="newPassword" autocomplete="off"></el-input>
</el-form-item>
<el-form-item label="确认密码" prop="confirmPassword">
<el-input v-model="confirmPassword" autocomplete="off"></el-input>
</el-form-item>
<el-form-item>
<div style="float: right;">
<el-button type="primary" @click="onSubmit">保存</el-button>
<el-button @click="close">取消</el-button>
</div>
</el-form-item>
</el-form>
</div>
</el-dialog>
</div>
</template>
<script>
export default {
name: "changePasswordForAdmin",
props: {},
computed: {},
created() {},
data() {
let validatePass1 = (rule, value, callback) => {
if (value === '') {
callback(new Error('请输入新密码'));
} else {
if (this.confirmPassword !== '') {
this.$refs.passwordForm.validateField('confirmPassword');
}
callback();
}
};
let validatePass2 = (rule, value, callback) => {
if (this.confirmPassword === '') {
callback(new Error('请再次输入密码'));
} else if (this.confirmPassword !== this.newPassword) {
callback(new Error('两次输入密码不一致!'));
} else {
callback();
}
};
return {
newPassword: null,
confirmPassword: null,
userId: null,
showDialog: false,
isLoging: false,
listChangeCallback: null,
form: {},
rules: {
newPassword: [{ required: true, validator: validatePass1, trigger: "blur" }, {
pattern: /^(?=.*[a-zA-Z])(?=.*\d)(?=.*[~!@#$%^&*()_+`\-={}:";'<>?,.\/]).{8,20}$/,
message: "密码长度在8-20位之间,由字母+数字+特殊字符组成",
},],
confirmPassword: [{ required: true, validator: validatePass2, trigger: "blur" }],
},
};
},
methods: {
openDialog: function (row, callback) {
console.log(row)
this.showDialog = true;
this.listChangeCallback = callback;
if (row != null) {
this.form = row;
}
},
onSubmit: function () {
this.$axios({
method: 'post',
url:"/api/user/changePasswordForAdmin",
params: {
password: this.newPassword,
userId: this.form.id,
}
}).then((res)=> {
if (res.data === "success"){
this.$message({
showClose: true,
message: '修改成功',
type: 'success'
});
this.showDialog = false;
}else {
this.$message({
showClose: true,
message: '修改密码失败,是否已登录(接口鉴权关闭无法修改密码)',
type: 'error'
});
}
}).catch((error)=> {
console.error(error)
});
},
close: function () {
this.showDialog = false;
this.newPassword = null;
this.confirmPassword = null;
this.userId=null;
this.adminId=null;
},
},
};
</script>

View File

@@ -0,0 +1,102 @@
<template>
<div id="changepushKey" v-loading="isLoging">
<el-dialog
title="修改pushKey"
width="42%"
top="2rem"
:close-on-click-modal="false"
:visible.sync="showDialog"
:destroy-on-close="true"
@close="close()"
>
<div id="shared" style="margin-right: 18px;">
<el-form ref="pushKeyForm" :rules="rules" status-icon label-width="86px">
<el-form-item label="新pushKey" prop="newPushKey" >
<el-input v-model="newPushKey" autocomplete="off"></el-input>
</el-form-item>
<el-form-item>
<div style="float: right;">
<el-button type="primary" @click="onSubmit">保存</el-button>
<el-button @click="close">取消</el-button>
</div>
</el-form-item>
</el-form>
</div>
</el-dialog>
</div>
</template>
<script>
export default {
name: "changePushKey",
props: {},
computed: {},
created() {},
data() {
let validatePass1 = (rule, value, callback) => {
if (value === '') {
callback(new Error('请输入新pushKey'));
} else {
callback();
}
};
return {
newPushKey: null,
confirmpushKey: null,
userId: null,
showDialog: false,
isLoging: false,
listChangeCallback: null,
form: {},
rules: {
newpushKey: [{ required: true, validator: validatePass1, trigger: "blur" }],
},
};
},
methods: {
openDialog: function (row, callback) {
console.log(row)
this.showDialog = true;
this.listChangeCallback = callback;
if (row != null) {
this.form = row;
}
},
onSubmit: function () {
this.$axios({
method: 'post',
url:"/api/user/changePushKey",
params: {
pushKey: this.newPushKey,
userId: this.form.id,
}
}).then((res)=> {
console.log(res.data)
if (res.data.msg === "success"){
this.$message({
showClose: true,
message: '修改成功',
type: 'success'
});
this.showDialog = false;
this.listChangeCallback();
}else {
this.$message({
showClose: true,
message: '修改pushKey失败是否已登录接口鉴权关闭无法修改pushKey',
type: 'error'
});
}
}).catch((error)=> {
console.error(error)
});
},
close: function () {
this.showDialog = false;
this.newpushKey = null;
this.userId=null;
this.adminId=null;
},
},
};
</script>

View File

@@ -8,7 +8,7 @@
<el-tab-pane label="目录结构" name="catalog">
<el-container>
<el-main v-bind:style="{backgroundColor: '#FFF', maxHeight: winHeight + 'px'}">
<chooseChannelForCatalog ref="chooseChannelForCatalog" :platformId=platformId :platformName=platformName :defaultCatalogId=defaultCatalogId :catalogIdChange="catalogIdChange" ></chooseChannelForCatalog>
<chooseChannelForCatalog ref="chooseChannelForCatalog" :platformId=platformId :platformName=platformName :defaultCatalogId=defaultCatalogId :catalogIdChange="catalogIdChange" :treeType=treeType ></chooseChannelForCatalog>
</el-main>
</el-container>
</el-tab-pane>
@@ -66,18 +66,20 @@ export default {
platformName: "",
defaultCatalogId: "",
showDialog: false,
treeType: null,
chooseData: {},
winHeight: window.innerHeight - 250,
};
},
methods: {
openDialog(platformId, platformName, defaultCatalogId, closeCallback) {
openDialog(platformId, platformName, defaultCatalogId, treeType, closeCallback) {
this.platformId = platformId
this.platformName = platformName
this.defaultCatalogId = defaultCatalogId
this.showDialog = true
this.closeCallback = closeCallback
this.treeType = treeType
},
tabClick (tab, event){

View File

@@ -38,7 +38,7 @@
import catalogEdit from './catalogEdit.vue'
export default {
name: 'chooseChannelForCatalog',
props: ['platformId', 'platformName', 'defaultCatalogId', 'catalogIdChange'],
props: ['platformId', 'platformName', 'defaultCatalogId', 'catalogIdChange', 'treeType'],
created() {
this.chooseId = this.defaultCatalogId;
this.defaultCatalogIdSign = this.defaultCatalogId;
@@ -102,8 +102,9 @@ export default {
},
addCatalog: function (parentId, node){
let that = this;
console.log(this.treeType)
// 打开添加弹窗
that.$refs.catalogEdit.openDialog(false, null, null, parentId, ()=>{
that.$refs.catalogEdit.openDialog(false, null, null, parentId, this.treeType, node.level, ()=>{
node.loaded = false
node.expand();
});

View File

@@ -174,7 +174,6 @@ export default {
page: that.currentPage,
count: that.count,
query: that.searchSrt,
pushing: that.pushing,
platformId: that.platformId,
catalogId: that.catalogId,
mediaServerId: that.mediaServerId

View File

@@ -388,7 +388,7 @@ export default {
url: '/zlm/' +this.mediaServerId+ '/index/api/getMediaInfo?vhost=__defaultVhost__&schema=rtmp&app='+ this.app +'&stream='+ this.streamId
}).then(function (res) {
that.tracksLoading = false;
if (res.data.code == 0 && res.data.online) {
if (res.data.code == 0 && res.data.tracks) {
that.tracks = res.data.tracks;
}else{
that.tracksNotLoaded = true;

View File

@@ -78,6 +78,12 @@
<el-option label="8" value="8"></el-option>
</el-select>
</el-form-item>
<el-form-item label="目录结构" prop="treeType" >
<el-select v-model="platform.treeType" style="width: 100%" >
<el-option key="WGS84" label="行政区划" value="CivilCode"></el-option>
<el-option key="GCJ02" label="业务分组" value="BusinessGroup"></el-option>
</el-select>
</el-form-item>
<el-form-item label="字符集" prop="characterSet">
<el-select
v-model="platform.characterSet"
@@ -91,7 +97,6 @@
<el-form-item label="其他选项">
<el-checkbox label="启用" v-model="platform.enable" @change="checkExpires"></el-checkbox>
<el-checkbox label="云台控制" v-model="platform.ptz"></el-checkbox>
<el-checkbox label="共享所有直播流" v-model="platform.shareAllLiveStream"></el-checkbox>
<el-checkbox label="拉起离线推流" v-model="platform.startOfflinePush"></el-checkbox>
</el-form-item>
<el-form-item>
@@ -153,10 +158,10 @@ export default {
keepTimeout: 60,
transport: "UDP",
characterSet: "GB2312",
shareAllLiveStream: false,
startOfflinePush: false,
catalogGroup: 1,
administrativeDivision: null,
treeType: "BusinessGroup",
},
rules: {
name: [{ required: true, message: "请输入平台名称", trigger: "blur" }],
@@ -194,6 +199,7 @@ export default {
that.platform.devicePort = res.data.devicePort;
that.platform.username = res.data.username;
that.platform.password = res.data.password;
that.platform.treeType = "BusinessGroup";
that.platform.administrativeDivision = res.data.username.substr(0, 6);
}).catch(function (error) {
console.log(error);
@@ -217,11 +223,11 @@ export default {
this.platform.keepTimeout = platform.keepTimeout;
this.platform.transport = platform.transport;
this.platform.characterSet = platform.characterSet;
this.platform.shareAllLiveStream = platform.shareAllLiveStream;
this.platform.catalogId = platform.catalogId;
this.platform.startOfflinePush = platform.startOfflinePush;
this.platform.catalogGroup = platform.catalogGroup;
this.platform.administrativeDivision = platform.administrativeDivision;
this.platform.treeType = platform.treeType;
this.onSubmit_text = "保存";
this.saveUrl = "/api/platform/save";
}
@@ -242,32 +248,49 @@ export default {
},
onSubmit: function () {
if (this.onSubmit_text === "保存") {
this.$confirm("修改目录结构会导致关联目录与通道数据被清空", '提示', {
dangerouslyUseHTMLString: true,
confirmButtonText: '确定',
cancelButtonText: '取消',
center: true,
type: 'warning'
}).then(() => {
this.saveForm()
}).catch(() => {
});
}else {
this.saveForm()
}
},
saveForm: function (){
var that = this;
that.$axios({
method: 'post',
url: this.saveUrl,
data: that.platform
}).then(function (res) {
if (res.data.code === 0) {
that.$message({
showClose: true,
message: "保存成功",
type: "success",
});
that.showDialog = false;
if (that.listChangeCallback != null) {
that.listChangeCallback();
}
}else {
that.$message({
showClose: true,
message: res.data.msg,
type: "error",
});
if (res.data.code === 0) {
that.$message({
showClose: true,
message: "保存成功",
type: "success",
});
that.showDialog = false;
if (that.listChangeCallback != null) {
that.listChangeCallback();
}
}).catch(function (error) {
console.log(error);
});
}else {
that.$message({
showClose: true,
message: res.data.msg,
type: "error",
});
}
}).catch(function (error) {
console.log(error);
});
},
close: function () {
this.showDialog = false;
@@ -293,7 +316,7 @@ export default {
keepTimeout: 60,
transport: "UDP",
characterSet: "GB2312",
shareAllLiveStream: false,
treeType: "BusinessGroup",
startOfflinePush: false,
catalogGroup: 1,
}

View File

@@ -15,20 +15,25 @@
<el-input v-model="proxyParam.name" clearable></el-input>
</el-form-item>
<el-form-item label="流应用名" prop="app">
<el-input v-model="proxyParam.app" clearable :disabled="true"></el-input>
<el-input v-model="proxyParam.app" clearable :disabled="edit"></el-input>
</el-form-item>
<el-form-item label="流ID" prop="stream">
<el-input v-model="proxyParam.stream" clearable :disabled="true"></el-input>
<el-input v-model="proxyParam.stream" clearable :disabled="edit"></el-input>
</el-form-item>
<el-form-item label="国标编码" prop="gbId">
<el-input v-model="proxyParam.gbId" placeholder="设置国标编码可推送到国标" clearable></el-input>
</el-form-item>
<el-form-item label="经度" prop="longitude" v-if="proxyParam.gbId">
<el-input v-model="proxyParam.longitude" placeholder="经度" clearable></el-input>
</el-form-item>
<el-form-item label="纬度" prop="latitude" v-if="proxyParam.gbId">
<el-input v-model="proxyParam.latitude" placeholder="经度" clearable></el-input>
</el-form-item>
<el-form-item>
<div style="float: right;">
<el-button type="primary" @click="onSubmit">保存</el-button>
<el-button @click="close">取消</el-button>
</div>
</el-form-item>
</el-form>
</div>
@@ -38,7 +43,7 @@
<script>
export default {
name: "streamProxyEdit",
name: "pushStreamEdit",
props: {},
computed: {},
created() {},
@@ -63,13 +68,15 @@ export default {
listChangeCallback: null,
showDialog: false,
isLoging: false,
edit: false,
proxyParam: {
name: null,
app: null,
stream: null,
gbId: null,
longitude: null,
latitude: null,
},
rules: {
name: [{ required: true, message: "请输入名称", trigger: "blur" }],
app: [{ required: true, message: "请输入应用名", trigger: "blur" }],
@@ -84,30 +91,63 @@ export default {
this.listChangeCallback = callback;
if (proxyParam != null) {
this.proxyParam = proxyParam;
}
this.edit = true
}else{
this.proxyParam= {
name: null,
app: null,
stream: null,
gbId: null,
longitude: null,
latitude: null,
}
this.edit = false
}
},
onSubmit: function () {
console.log("onSubmit");
var that = this;
that.$axios({
method:"post",
url:`/api/push/save_to_gb`,
data: that.proxyParam
}).then(function (res) {
if (this.edit) {
this.$axios({
method:"post",
url:`/api/push/save_to_gb`,
data: this.proxyParam
}).then( (res) => {
if (res.data == "success") {
that.$message({
this.$message({
showClose: true,
message: "保存成功",
type: "success",
});
that.showDialog = false;
if (that.listChangeCallback != null) {
that.listChangeCallback();
this.showDialog = false;
if (this.listChangeCallback != null) {
this.listChangeCallback();
}
}
}).catch(function (error) {
}).catch((error)=> {
console.log(error);
});
});
}else {
this.$axios({
method:"post",
url:`/api/push/add`,
data: this.proxyParam
}).then( (res) => {
if (res.data.code === 0) {
this.$message({
showClose: true,
message: "保存成功",
type: "success",
});
this.showDialog = false;
if (this.listChangeCallback != null) {
this.listChangeCallback();
}
}
}).catch((error)=> {
console.log(error);
});
}
},
close: function () {
console.log("关闭加入GB");
@@ -131,6 +171,9 @@ export default {
if (this.platform.enable && this.platform.expires == "0") {
this.platform.expires = "300";
}
},
handleNodeClick: function (node){
}
},
};