wenlele
3 years ago
50 changed files with 3194 additions and 321 deletions
@ -0,0 +1,257 @@ |
|||||
|
'use strict'; |
||||
|
const moment = require('moment') |
||||
|
|
||||
|
async function get (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
const { limit, page, orderBy, orderDirection, keyword, forbidden, paraphraseCustom } = ctx.query |
||||
|
|
||||
|
const sequelize = ctx.fs.dc.ORM; |
||||
|
let findOption = { |
||||
|
attributes: { |
||||
|
include: [ |
||||
|
[sequelize.fn('COUNT', sequelize.col('cameraStatusLogs.id')), 'logCount'] |
||||
|
] |
||||
|
}, |
||||
|
where: {}, |
||||
|
order: [ |
||||
|
[orderBy || 'id', orderDirection || 'DESC'] |
||||
|
], |
||||
|
distinct: true, |
||||
|
subQuery: false, |
||||
|
group: [ |
||||
|
'cameraStatus.id', |
||||
|
'cameraStatusLogs.status_id', |
||||
|
// 'cameraStatusResolves.id'
|
||||
|
], |
||||
|
include: [ |
||||
|
// {
|
||||
|
// model: models.CameraStatusResolve,
|
||||
|
// attributes: { exclude: ['statusId'] },
|
||||
|
// required: false,
|
||||
|
// duplicating: true
|
||||
|
// },
|
||||
|
{ |
||||
|
model: models.CameraStatusLog, |
||||
|
attributes: [], |
||||
|
duplicating: false, |
||||
|
required: false, |
||||
|
} |
||||
|
], |
||||
|
} |
||||
|
if (orderBy) { |
||||
|
if (orderBy == 'logCount') { |
||||
|
findOption.order = sequelize.literal(`"logCount" ${orderDirection || 'DESC'}`) |
||||
|
} |
||||
|
} |
||||
|
if (limit) { |
||||
|
findOption.limit = limit |
||||
|
} |
||||
|
if (page && limit) { |
||||
|
findOption.offset = page * limit |
||||
|
} |
||||
|
if (keyword) { |
||||
|
findOption.where['$or'] = { |
||||
|
describe: { |
||||
|
$like: `%${keyword}%` |
||||
|
}, |
||||
|
paraphrase: { |
||||
|
$like: `%${keyword}%` |
||||
|
}, |
||||
|
paraphraseCustom: { |
||||
|
$like: `%${keyword}%` |
||||
|
}, |
||||
|
} |
||||
|
} |
||||
|
if (forbidden) { |
||||
|
if (forbidden === 'true') { |
||||
|
findOption.where.forbidden = true |
||||
|
} else if (forbidden === 'false') { |
||||
|
findOption.where.forbidden = false |
||||
|
} |
||||
|
} |
||||
|
if (paraphraseCustom) { |
||||
|
if (paraphraseCustom === 'true') { |
||||
|
findOption.where.paraphraseCustom = null |
||||
|
} else if (paraphraseCustom === 'false') { |
||||
|
findOption.where.paraphraseCustom = { |
||||
|
$ne: null |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
const statusRes = await models.CameraStatus.findAll(findOption) |
||||
|
|
||||
|
delete findOption.order |
||||
|
delete findOption.limit |
||||
|
delete findOption.offset |
||||
|
delete findOption.attributes |
||||
|
delete findOption.group |
||||
|
const count = await models.CameraStatus.count(findOption) |
||||
|
|
||||
|
const statusIds = statusRes.map(r => r.id) |
||||
|
const statusResolveRes = await models.CameraStatusResolve.findAll({ |
||||
|
where: { |
||||
|
statusId: { |
||||
|
$in: statusIds |
||||
|
} |
||||
|
} |
||||
|
}) |
||||
|
|
||||
|
for (let { dataValues: s } of statusRes) { |
||||
|
const corResolve = statusResolveRes.filter(r => r.statusId === s.id) |
||||
|
s.resolve = corResolve |
||||
|
} |
||||
|
|
||||
|
ctx.status = 200; |
||||
|
ctx.body = { |
||||
|
count, |
||||
|
rows: statusRes, |
||||
|
} |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function getSimpleAll (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const statusRes = await models.CameraStatus.findAll({ |
||||
|
attributes: ['id', 'platform', 'status', 'describe'], |
||||
|
}) |
||||
|
ctx.status = 200; |
||||
|
ctx.body = statusRes |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function banned (ctx) { |
||||
|
try { |
||||
|
const { models } = ctx.fs.dc; |
||||
|
const data = ctx.request.body; |
||||
|
|
||||
|
// 库记录
|
||||
|
await models.CameraStatus.update({ |
||||
|
forbidden: data.forbidden |
||||
|
}, { |
||||
|
where: { |
||||
|
id: data.statusId |
||||
|
} |
||||
|
}) |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function paraphraseCustom (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
const data = ctx.request.body |
||||
|
|
||||
|
await models.CameraStatus.update({ |
||||
|
paraphraseCustom: data.paraphrase, |
||||
|
}, { |
||||
|
where: { |
||||
|
id: { $in: data.statusId } |
||||
|
} |
||||
|
}) |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function resolveEdit (ctx) { |
||||
|
const transaction = await ctx.fs.dc.orm.transaction(); |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
const data = ctx.request.body |
||||
|
|
||||
|
await models.CameraStatusResolve.destroy({ |
||||
|
where: { |
||||
|
statusId: data.statusId |
||||
|
}, |
||||
|
transaction |
||||
|
}) |
||||
|
|
||||
|
await models.CameraStatusResolve.bulkCreate( |
||||
|
data.resolve.map(r => { |
||||
|
return { |
||||
|
statusId: data.statusId, |
||||
|
resolve: r |
||||
|
} |
||||
|
}), |
||||
|
{ transaction } |
||||
|
) |
||||
|
|
||||
|
await transaction.commit(); |
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
await transaction.rollback(); |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function statusCheck (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
const { status, platform, describe } = ctx.query |
||||
|
|
||||
|
if (!status || !platform) { |
||||
|
throw 'status and platform is required' |
||||
|
} |
||||
|
|
||||
|
const statusRes = await models.CameraStatus.findOne({ |
||||
|
where: { |
||||
|
status, |
||||
|
platform, |
||||
|
}, |
||||
|
include: [{ |
||||
|
model: models.CameraStatusResolve, |
||||
|
attributes: { exclude: ['statusId'] }, |
||||
|
}], |
||||
|
}) |
||||
|
|
||||
|
if (!statusRes && describe) { |
||||
|
await models.CameraStatus.create({ |
||||
|
status, platform, describe |
||||
|
}) |
||||
|
} |
||||
|
|
||||
|
ctx.status = 200; |
||||
|
ctx.body = statusRes |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = { |
||||
|
message: typeof error == 'string' ? error : undefined |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
module.exports = { |
||||
|
get, |
||||
|
getSimpleAll, |
||||
|
banned, |
||||
|
paraphraseCustom, |
||||
|
resolveEdit, |
||||
|
statusCheck, |
||||
|
}; |
@ -0,0 +1,85 @@ |
|||||
|
'use strict'; |
||||
|
const moment = require('moment') |
||||
|
|
||||
|
async function edit (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function get (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function banned (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function del (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function copy (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
async function detail (ctx) { |
||||
|
try { |
||||
|
const models = ctx.fs.dc.models; |
||||
|
const { userId, token } = ctx.fs.api |
||||
|
|
||||
|
ctx.status = 204; |
||||
|
} catch (error) { |
||||
|
ctx.fs.logger.error(`path: ${ctx.path}, error: ${error}`); |
||||
|
ctx.status = 400; |
||||
|
ctx.body = {} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
|
||||
|
module.exports = { |
||||
|
edit, get, banned, del, copy, detail |
||||
|
}; |
@ -0,0 +1,79 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatus = sequelize.define("cameraStatus", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_status_id_uindex" |
||||
|
}, |
||||
|
platform: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: "平台分类 yingshi gb", |
||||
|
primaryKey: false, |
||||
|
field: "platform", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
status: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "status", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
describe: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: true, |
||||
|
defaultValue: null, |
||||
|
comment: "错误描述", |
||||
|
primaryKey: false, |
||||
|
field: "describe", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
paraphrase: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: true, |
||||
|
defaultValue: null, |
||||
|
comment: "释义", |
||||
|
primaryKey: false, |
||||
|
field: "paraphrase", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
forbidden: { |
||||
|
type: DataTypes.BOOLEAN, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: "是否禁用", |
||||
|
primaryKey: false, |
||||
|
field: "forbidden", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
paraphraseCustom: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: true, |
||||
|
defaultValue: null, |
||||
|
comment: "自定义释义", |
||||
|
primaryKey: false, |
||||
|
field: "paraphrase_custom", |
||||
|
autoIncrement: false |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatus = CameraStatus; |
||||
|
return CameraStatus; |
||||
|
}; |
@ -0,0 +1,47 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatusLog = sequelize.define("cameraStatusLog", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_status_log_id_uindex_2" |
||||
|
}, |
||||
|
statusId: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "status_id", |
||||
|
autoIncrement: false, |
||||
|
references: { |
||||
|
key: "id", |
||||
|
model: "cameraStatus" |
||||
|
} |
||||
|
}, |
||||
|
time: { |
||||
|
type: DataTypes.DATE, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "time", |
||||
|
autoIncrement: false |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status_log", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatusLog = CameraStatusLog; |
||||
|
return CameraStatusLog; |
||||
|
}; |
@ -0,0 +1,79 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatusPushConfig = sequelize.define("cameraStatusPushConfig", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_online_status_push_config_id_uindex" |
||||
|
}, |
||||
|
name: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "name", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
pushWay: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: "推送方式 email / phone", |
||||
|
primaryKey: false, |
||||
|
field: "push_way", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
noticeWay: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: "通知方式 offline / online / timing", |
||||
|
primaryKey: false, |
||||
|
field: "notice_way", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
createUser: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "create_user", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
forbidden: { |
||||
|
type: DataTypes.BOOLEAN, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "forbidden", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
timing: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: true, |
||||
|
defaultValue: null, |
||||
|
comment: "定时推送时间", |
||||
|
primaryKey: false, |
||||
|
field: "timing", |
||||
|
autoIncrement: false |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status_push_config", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatusPushConfig = CameraStatusPushConfig; |
||||
|
return CameraStatusPushConfig; |
||||
|
}; |
@ -0,0 +1,61 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatusPushLog = sequelize.define("cameraStatusPushLog", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_status_push_log_id_uindex" |
||||
|
}, |
||||
|
pushConfigId: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: true, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "push_config_id", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
receiver: { |
||||
|
type: DataTypes.JSONB, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "receiver", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
time: { |
||||
|
type: DataTypes.DATE, |
||||
|
allowNull: true, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "time", |
||||
|
autoIncrement: false |
||||
|
}, |
||||
|
pushWay: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "push_way", |
||||
|
autoIncrement: false |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status_push_log", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatusPushLog = CameraStatusPushLog; |
||||
|
return CameraStatusPushLog; |
||||
|
}; |
@ -0,0 +1,51 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatusPushMonitor = sequelize.define("cameraStatusPushMonitor", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_status_push_monitor_id_uindex" |
||||
|
}, |
||||
|
configId: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "config_id", |
||||
|
autoIncrement: false, |
||||
|
references: { |
||||
|
key: "id", |
||||
|
model: "cameraStatusPushConfig" |
||||
|
} |
||||
|
}, |
||||
|
cameraId: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "camera_id", |
||||
|
autoIncrement: false, |
||||
|
references: { |
||||
|
key: "id", |
||||
|
model: "camera" |
||||
|
} |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status_push_monitor", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatusPushMonitor = CameraStatusPushMonitor; |
||||
|
return CameraStatusPushMonitor; |
||||
|
}; |
@ -0,0 +1,47 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatusPushReceiver = sequelize.define("cameraStatusPushReceiver", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_status_push_receiver_id_uindex" |
||||
|
}, |
||||
|
configId: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "config_id", |
||||
|
autoIncrement: false, |
||||
|
references: { |
||||
|
key: "id", |
||||
|
model: "cameraStatusPushConfig" |
||||
|
} |
||||
|
}, |
||||
|
receiver: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: "接受者信息 邮箱或者电话号码", |
||||
|
primaryKey: false, |
||||
|
field: "receiver", |
||||
|
autoIncrement: false |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status_push_receiver", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatusPushReceiver = CameraStatusPushReceiver; |
||||
|
return CameraStatusPushReceiver; |
||||
|
}; |
@ -0,0 +1,47 @@ |
|||||
|
/* eslint-disable*/ |
||||
|
'use strict'; |
||||
|
|
||||
|
module.exports = dc => { |
||||
|
const DataTypes = dc.ORM; |
||||
|
const sequelize = dc.orm; |
||||
|
const CameraStatusResolve = sequelize.define("cameraStatusResolve", { |
||||
|
id: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: true, |
||||
|
field: "id", |
||||
|
autoIncrement: true, |
||||
|
unique: "camera_status_resolve_id_uindex" |
||||
|
}, |
||||
|
statusId: { |
||||
|
type: DataTypes.INTEGER, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "status_id", |
||||
|
autoIncrement: false, |
||||
|
references: { |
||||
|
key: "id", |
||||
|
model: "cameraStatus" |
||||
|
} |
||||
|
}, |
||||
|
resolve: { |
||||
|
type: DataTypes.STRING, |
||||
|
allowNull: false, |
||||
|
defaultValue: null, |
||||
|
comment: null, |
||||
|
primaryKey: false, |
||||
|
field: "resolve", |
||||
|
autoIncrement: false |
||||
|
} |
||||
|
}, { |
||||
|
tableName: "camera_status_resolve", |
||||
|
comment: "", |
||||
|
indexes: [] |
||||
|
}); |
||||
|
dc.models.CameraStatusResolve = CameraStatusResolve; |
||||
|
return CameraStatusResolve; |
||||
|
}; |
@ -0,0 +1,44 @@ |
|||||
|
'use strict'; |
||||
|
|
||||
|
const status = require('../../controllers/status'); |
||||
|
const push = require('../../controllers/status/push'); |
||||
|
|
||||
|
module.exports = function (app, router, opts) { |
||||
|
app.fs.api.logAttr['GET/status'] = { content: '获取状态码', visible: false }; |
||||
|
router.get('/status', status.get); |
||||
|
|
||||
|
app.fs.api.logAttr['GET/status/simple_all'] = { content: '获取全部状态码简略信息', visible: false }; |
||||
|
router.get('/status/simple_all', status.getSimpleAll); |
||||
|
|
||||
|
app.fs.api.logAttr['PUT/status/banned'] = { content: '禁用状态码自定义', visible: false }; |
||||
|
router.put('/status/banned', status.banned); |
||||
|
|
||||
|
app.fs.api.logAttr['POST/status/custom'] = { content: '自定义状态码释义', visible: false }; |
||||
|
router.post('/status/custom', status.paraphraseCustom); |
||||
|
|
||||
|
app.fs.api.logAttr['POST/status/resolve'] = { content: '编辑解决方案', visible: false }; |
||||
|
router.post('/status/resolve', status.resolveEdit); |
||||
|
|
||||
|
app.fs.api.logAttr['GET/status/check'] = { content: '查取指定状态码信息', visible: false }; |
||||
|
router.get('/status/check', status.statusCheck); |
||||
|
|
||||
|
// 信鸽推送
|
||||
|
app.fs.api.logAttr['POST/status/push'] = { content: '编辑推送配置', visible: false }; |
||||
|
router.post('/status/push', push.edit); |
||||
|
|
||||
|
app.fs.api.logAttr['GET/status/push'] = { content: '获取推送配置', visible: false }; |
||||
|
router.get('/status/push', push.get); |
||||
|
|
||||
|
app.fs.api.logAttr['PUT/status/push/banned'] = { content: '禁用推送配置', visible: false }; |
||||
|
router.put('/status/push/banned', push.banned); |
||||
|
|
||||
|
app.fs.api.logAttr['DEL/status/push/:pushId'] = { content: '删除推送配置', visible: false }; |
||||
|
router.delete('/status/push/:pushId', push.del); |
||||
|
|
||||
|
app.fs.api.logAttr['GET/status/push/:pushId/copy'] = { content: '赋值推送配置', visible: false }; |
||||
|
router.get('/status/push/:pushId/copy', push.copy); |
||||
|
|
||||
|
app.fs.api.logAttr['GET/status/push/:pushId/detail'] = { content: '获取推送配置详情', visible: false }; |
||||
|
router.get('/status/push/:pushId/detail', push.detail); |
||||
|
// 信鸽推送 END
|
||||
|
}; |
@ -0,0 +1,3 @@ |
|||||
|
{ |
||||
|
"editor.wordWrap": "on" |
||||
|
} |
@ -0,0 +1,17 @@ |
|||||
|
{ |
||||
|
// 使用 IntelliSense 了解相关属性。 |
||||
|
// 悬停以查看现有属性的描述。 |
||||
|
// 欲了解更多信息,请访问: https://go.microsoft.com/fwlink/?linkid=830387 |
||||
|
"version": "0.2.0", |
||||
|
"configurations": [ |
||||
|
{ |
||||
|
"type": "node", |
||||
|
"request": "launch", |
||||
|
"name": "启动程序", |
||||
|
"skipFiles": [ |
||||
|
"<node_internals>/**" |
||||
|
], |
||||
|
"program": "${workspaceFolder}\\index.js" |
||||
|
} |
||||
|
] |
||||
|
} |
@ -0,0 +1,69 @@ |
|||||
|
try { |
||||
|
const { Pool, Client } = require('pg') |
||||
|
const XLSX = require('xlsx') |
||||
|
const path = require('path') |
||||
|
|
||||
|
// 连接数据库
|
||||
|
const pool = new Pool({ |
||||
|
user: 'postgres', |
||||
|
host: '10.8.30.32', |
||||
|
database: 'video_access', |
||||
|
password: '123', |
||||
|
port: 5432, |
||||
|
}) |
||||
|
|
||||
|
const fun = async () => { |
||||
|
// note: we don't try/catch this because if connecting throws an exception
|
||||
|
// we don't need to dispose of the client (it will be undefined)
|
||||
|
const client = await pool.connect() |
||||
|
try { |
||||
|
await client.query('BEGIN') |
||||
|
|
||||
|
// 读取数据文件
|
||||
|
let workbook = XLSX.readFile(path.join(__dirname, '云录制错误码.xlsx')) |
||||
|
let firstSheetName = workbook.SheetNames[0]; |
||||
|
let worksheet = workbook.Sheets[firstSheetName]; |
||||
|
let res = XLSX.utils.sheet_to_json(worksheet); |
||||
|
|
||||
|
// console.log(res);
|
||||
|
|
||||
|
for (let d of res) { |
||||
|
let statusRes = await client.query(`SELECT * FROM camera_status WHERE status=$1`, [d['错误码']]); |
||||
|
let statusRows = statusRes.rows |
||||
|
|
||||
|
if (statusRows.length) { |
||||
|
|
||||
|
} else { |
||||
|
console.log(`增加${d['错误码']}`); |
||||
|
const statusInQuery = `INSERT INTO "camera_status" (platform, status, describe, paraphrase) VALUES($1, $2, $3, $4) RETURNING id;` |
||||
|
const statusRows = (await client.query(statusInQuery, ['yingshi', d['错误码'], d['错误描述'], d['释义']])).rows |
||||
|
// console.log(statusRows);
|
||||
|
if (d['解决方案']) { |
||||
|
let resolveArr = d['解决方案'].split(';'); |
||||
|
// await client.query(`DELETE FROM "camera_status_solution" WHERE status_id=$1`, [statusRows[0].id]);
|
||||
|
for (let r of resolveArr) { |
||||
|
await client.query( |
||||
|
`INSERT INTO "camera_status_resolve" (status_id, resolve) VALUES($1, $2) RETURNING id;`, |
||||
|
[statusRows[0].id, r] |
||||
|
) |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
// await client.query('ROLLBACK')
|
||||
|
await client.query('COMMIT') |
||||
|
console.log('执行完毕~') |
||||
|
} catch (e) { |
||||
|
await client.query('ROLLBACK') |
||||
|
console.log('执行错误~') |
||||
|
throw e |
||||
|
} finally { |
||||
|
client.release(); |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
fun() |
||||
|
} catch (error) { |
||||
|
console.error(error) |
||||
|
} |
@ -0,0 +1,16 @@ |
|||||
|
{ |
||||
|
"name": "appkey-generator", |
||||
|
"version": "1.0.0", |
||||
|
"description": "tool", |
||||
|
"main": "index.js", |
||||
|
"scripts": { |
||||
|
"test": "mocha", |
||||
|
"start": "set NODE_ENV=development&&node index" |
||||
|
}, |
||||
|
"author": "liu", |
||||
|
"license": "ISC", |
||||
|
"dependencies": { |
||||
|
"pg": "^7.18.2", |
||||
|
"xlsx": "^0.17.1" |
||||
|
} |
||||
|
} |
Binary file not shown.
@ -0,0 +1,141 @@ |
|||||
|
|
||||
|
-- ---------------------------- |
||||
|
-- Records of camera_status |
||||
|
-- ---------------------------- |
||||
|
INSERT INTO "public"."camera_status" VALUES (2, 'yingshi', '5000', '服务端内部处理异常', '服务端内部错误码', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (3, 'yingshi', '5400', '私有化协议vtm检测私有化协议中码流类型小于0或者设备序列号为空等非法参数场景返回(app不重试取流)', '客户端参数出错', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (4, 'yingshi', '5402', '回放找不到录像文件', '设备回放找不到录像文件', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (5, 'yingshi', '5403', '操作码或信令密钥与设备不匹配', '操作码或信令密钥与设备不匹配', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (6, 'yingshi', '5404', '设备不在线', '设备不在线', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (7, 'yingshi', '5405', '流媒体向设备发送或接受信令超时/cas响应超时', '设备回应信令10秒超时', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (8, 'yingshi', '5406', 'token失效', 'token失效', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (9, 'yingshi', '5407', '客户端的URL格式错误', '客户端的URL格式错误', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (10, 'yingshi', '5409', '预览开启隐私保护', '预览开启隐私保护', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (11, 'yingshi', '5411', 'token无权限', 'token无权限、用户无权限', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (12, 'yingshi', '5412', 'session不存在', 'session不存在', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (13, 'yingshi', '5413', '验证token的他异常(不具体)', 'token验证失败', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (14, 'yingshi', '5415', '设备通道错', '设备判断请求通道不存在', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (15, 'yingshi', '5416', '设备资源受限', '设备资源受限', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (16, 'yingshi', '5451', '设备不支持的码流类型', '设备不支持的码流类型', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (17, 'yingshi', '5452', '设备链接流媒体服务器失败', '设备链接流媒体服务器失败', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (18, 'yingshi', '5454', '流媒体中关于设备取流会话不存在', '流媒体中关于设备取流会话不存在', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (19, 'yingshi', '5455', '设备通道未关联', '设备通道未关联', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (20, 'yingshi', '5456', '设备通道关联设备不在线', '设备通道关联设备不在线', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (21, 'yingshi', '5457', '客户端不支持端到端加密', '客户端不支持端到端加密', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (22, 'yingshi', '5458', '设备不支持当前并发ECDH密', '设备不支持当前并发ECDH密', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (23, 'yingshi', '5459', 'VTDU 处理ECDH 加密失败', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (24, 'yingshi', '5492', '设备不支持的命令', '设备不支持的命令', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (25, 'yingshi', '5500', '服务器处理失败', '服务器处理失败', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (26, 'yingshi', '5503', 'vtm返回分配vtdu失败', 'vtm返回分配vtdu失败', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (27, 'yingshi', '5504', '流媒体vtdu达到最大负载', '流媒体vtdu达到最大负载', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (28, 'yingshi', '5544', '设备返回无视频源', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (29, 'yingshi', '5545', '视频分享时间已经结束', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (30, 'yingshi', '5546', 'vtdu返回达到取流并发路数限制', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (31, 'yingshi', '5547', 'vtdu返回开放平台用户并发限制', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (32, 'yingshi', '5556', 'ticket校验失败', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (33, 'yingshi', '5557', '回放服务器等待流头超时', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (34, 'yingshi', '5558', '查找录像开始时间错误', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (35, 'yingshi', '5560', '群组分享取流二次验证失败', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (36, 'yingshi', '5561', '分享群组用户被锁住', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (37, 'yingshi', '5562', '群组分享用户权限变更', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (38, 'yingshi', '5563', '认证服务连接失败', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (39, 'yingshi', '5564', '认证超时', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (40, 'yingshi', '5565', '缓存无效', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (41, 'yingshi', '5566', '不在分享时间内预览', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (42, 'yingshi', '5567', '分享通道被锁定', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (43, 'yingshi', '5568', '未找到认证类型', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (44, 'yingshi', '5569', '认证返回的参数异常', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (45, 'yingshi', '5600', '分享设备不在分享时间内', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (46, 'yingshi', '5601', '群组分享用户没权限', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (47, 'yingshi', '5602', '群组分享权限变更', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (48, 'yingshi', '5530', '机房故障不可用', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (49, 'yingshi', '5701', 'cas信令返回格式错误', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (50, 'yingshi', '5702', 'SPGW请求Cas、Status透传超时', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (51, 'yingshi', '5703', 'SPGW请求http不通', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (52, 'yingshi', '6001', '客户端参数出错', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (53, 'yingshi', '6099', '客户端默认错误', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (54, 'yingshi', '6101', '不支持的命令', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (55, 'yingshi', '6102', '设备流头发送失败', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (56, 'yingshi', '6103', 'cas/设备返回错误1', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (57, 'yingshi', '6104', 'cas/设备返回错误-1', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (58, 'yingshi', '6105', '设备返回错误码3', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (59, 'yingshi', '6106', '设备返回错误码4', '一般常见于多通道设 备预览 1、通道不存在 2、通道子码流不存在 3、通道不在线', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (60, 'yingshi', '6107', '设备返回错误码5', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (61, 'yingshi', '6108', 'cas信令回应重复', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (62, 'yingshi', '6109', '视频广场取消分享', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (63, 'yingshi', '6110', '设备信令默认错误', '设备错误返回的错误码,不具体', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (64, 'yingshi', '6501', '设备数据链路和实际链路不匹配', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (65, 'yingshi', '6502', '设备数据链路重复建立连接', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (66, 'yingshi', '6503', '设备数据链路端口不匹配', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (67, 'yingshi', '6504', '缓存设备数据链路失败(内存块不足)', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (68, 'yingshi', '6505', '设备发送确认头消息重复', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (69, 'yingshi', '6506', '设备数据先于确定头部到达', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (70, 'yingshi', '6508', '设备数据头部长度非法', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (71, 'yingshi', '6509', '索引找不到设备数据管理块', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (72, 'yingshi', '6510', '设备数据链路vtdu内存块协议状态不匹配', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (73, 'yingshi', '6511', '设备数据头部没有streamkey错误', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (74, 'yingshi', '6512', '设备数据头部非法(较笼统)', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (75, 'yingshi', '6513', '设备数据长度过小', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (76, 'yingshi', '6514', '设备老协议推流头部没有streamkey错误', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (77, 'yingshi', '6515', '设备老协议推流数据非法', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (78, 'yingshi', '6516', '设备老协议索引找不到内存管理块', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (79, 'yingshi', '6517', '设备老协议推流数据非法', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (80, 'yingshi', '6518', '设备数据包过大', NULL, 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (81, 'yingshi', '6519', '设备推流链路网络不稳定', '设备长时间未推流超时', 'f', NULL); |
||||
|
INSERT INTO "public"."camera_status" VALUES (82, 'yingshi', '6520', '设备推流链路网络不稳定(默认)', '设备网络异常', 'f', NULL); |
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
|
||||
|
-- ---------------------------- |
||||
|
-- Records of camera_status_resolve |
||||
|
-- ---------------------------- |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (2, 2, '检测服务端是否正常'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (3, 3, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (4, 4, '检查是否有存储卡并且接触良好'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (5, 6, '检查设备网络'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (6, 6, '重启设备接入萤石云'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (7, 7, '检查设备网络'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (8, 7, '重启设备'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (9, 8, '刷新重试或者重启设备'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (10, 9, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (11, 13, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (12, 14, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (13, 15, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (14, 16, '刷新重试或者切换到高清模式'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (15, 17, '检查设备网络,重启设备,刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (16, 19, '检查设备通道是否关联'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (17, 20, '检查设备通道是否上线'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (18, 25, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (19, 26, 'vtdu服务异常,请请稍后重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (20, 27, '服务器负载达到上限,请稍后重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (21, 28, '设备是否接触良好'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (22, 28, '如果一直无法解决,请联系技术支持'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (23, 30, '请升级为企业版,放开并发限制'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (24, 31, '请确定开放平台用户预览是否超过用户并发数量限制'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (25, 33, '刷新重试,检测设备网络,重启设备'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (26, 48, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (27, 49, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (28, 50, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (29, 51, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (30, 52, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (31, 54, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (32, 55, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (33, 56, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (34, 57, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (35, 58, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (36, 59, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (37, 60, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (38, 61, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (39, 63, '刷新重试,或者重启设备'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (40, 64, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (41, 65, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (42, 66, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (43, 67, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (44, 68, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (45, 69, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (46, 70, '刷新重试,或者重启设备'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (47, 71, '刷新重试'); |
||||
|
INSERT INTO "public"."camera_status_resolve" VALUES (48, 80, '刷新重试,或者重启设备'); |
||||
|
|
@ -0,0 +1,140 @@ |
|||||
|
create table if not exists camera_status |
||||
|
( |
||||
|
id serial not null, |
||||
|
platform varchar(32) not null, |
||||
|
status varchar(32) not null, |
||||
|
describe varchar(1024), |
||||
|
paraphrase varchar(1024), |
||||
|
forbidden boolean default false not null, |
||||
|
paraphrase_custom varchar(1024), |
||||
|
constraint camera_status_pk |
||||
|
primary key (id) |
||||
|
); |
||||
|
|
||||
|
comment on column camera_status.platform is '平台分类 yingshi gb'; |
||||
|
|
||||
|
comment on column camera_status.describe is '错误描述'; |
||||
|
|
||||
|
comment on column camera_status.paraphrase is '释义'; |
||||
|
|
||||
|
comment on column camera_status.forbidden is '是否禁用'; |
||||
|
|
||||
|
comment on column camera_status.paraphrase_custom is '自定义释义'; |
||||
|
|
||||
|
create unique index if not exists camera_status_id_uindex |
||||
|
on camera_status (id); |
||||
|
|
||||
|
|
||||
|
|
||||
|
create table if not exists camera_status_log |
||||
|
( |
||||
|
id serial not null, |
||||
|
status_id integer not null, |
||||
|
time timestamp not null, |
||||
|
constraint camera_status_log_pk |
||||
|
primary key (id), |
||||
|
constraint camera_status_log_camera_status_id_fk |
||||
|
foreign key (status_id) references camera_status |
||||
|
); |
||||
|
|
||||
|
create unique index if not exists camera_status_log_id_uindex |
||||
|
on camera_status_log (id); |
||||
|
|
||||
|
create unique index if not exists camera_status_log_id_uindex_2 |
||||
|
on camera_status_log (id); |
||||
|
|
||||
|
|
||||
|
create table if not exists camera_status_push_config |
||||
|
( |
||||
|
id serial not null, |
||||
|
name varchar(64) not null, |
||||
|
push_way varchar(32) not null, |
||||
|
notice_way varchar(32) not null, |
||||
|
create_user integer not null, |
||||
|
forbidden boolean default false not null, |
||||
|
timing varchar(32), |
||||
|
constraint camera_online_status_push_config_pk |
||||
|
primary key (id) |
||||
|
); |
||||
|
|
||||
|
comment on column camera_status_push_config.push_way is '推送方式 email / phone'; |
||||
|
|
||||
|
comment on column camera_status_push_config.notice_way is '通知方式 offline / online / timing'; |
||||
|
|
||||
|
comment on column camera_status_push_config.timing is '定时推送时间'; |
||||
|
|
||||
|
create unique index if not exists camera_online_status_push_config_id_uindex |
||||
|
on camera_status_push_config (id); |
||||
|
|
||||
|
|
||||
|
|
||||
|
create table if not exists camera_status_push_log |
||||
|
( |
||||
|
id serial not null, |
||||
|
push_config_id integer, |
||||
|
receiver jsonb not null, |
||||
|
time timestamp, |
||||
|
push_way varchar(128) not null, |
||||
|
constraint camera_status_push_log_pk |
||||
|
primary key (id) |
||||
|
); |
||||
|
|
||||
|
comment on table camera_status_push_log is '上下线推送日志'; |
||||
|
|
||||
|
create unique index if not exists camera_status_push_log_id_uindex |
||||
|
on camera_status_push_log (id); |
||||
|
|
||||
|
|
||||
|
|
||||
|
create table if not exists camera_status_push_monitor |
||||
|
( |
||||
|
id serial not null, |
||||
|
config_id integer not null, |
||||
|
camera_id integer not null, |
||||
|
constraint camera_status_push_monitor_pk |
||||
|
primary key (id), |
||||
|
constraint camera_status_push_monitor_camera_id_fk |
||||
|
foreign key (camera_id) references camera, |
||||
|
constraint camera_status_push_monitor_camera_status_push_config_id_fk |
||||
|
foreign key (config_id) references camera_status_push_config |
||||
|
); |
||||
|
|
||||
|
create unique index if not exists camera_status_push_monitor_id_uindex |
||||
|
on camera_status_push_monitor (id); |
||||
|
|
||||
|
|
||||
|
|
||||
|
create table if not exists camera_status_push_receiver |
||||
|
( |
||||
|
id serial not null, |
||||
|
config_id integer not null, |
||||
|
receiver varchar(64) not null, |
||||
|
constraint camera_status_push_receiver_pk |
||||
|
primary key (id), |
||||
|
constraint camera_status_push_receiver_camera_status_push_config_id_fk |
||||
|
foreign key (config_id) references camera_status_push_config |
||||
|
); |
||||
|
|
||||
|
comment on column camera_status_push_receiver.receiver is '接受者信息 邮箱或者电话号码'; |
||||
|
|
||||
|
create unique index if not exists camera_status_push_receiver_id_uindex |
||||
|
on camera_status_push_receiver (id); |
||||
|
|
||||
|
|
||||
|
create table if not exists camera_status_resolve |
||||
|
( |
||||
|
id serial not null, |
||||
|
status_id integer not null, |
||||
|
resolve varchar(1024) not null, |
||||
|
constraint camera_status_resolve_pk |
||||
|
primary key (id), |
||||
|
constraint camera_status_resolve_camera_status_id_fk |
||||
|
foreign key (status_id) references camera_status |
||||
|
); |
||||
|
|
||||
|
comment on table camera_status_resolve is '错误码解决方案'; |
||||
|
|
||||
|
create unique index if not exists camera_status_resolve_id_uindex |
||||
|
on camera_status_resolve (id); |
||||
|
|
||||
|
|
After Width: | Height: | Size: 85 KiB |
After Width: | Height: | Size: 387 B |
After Width: | Height: | Size: 85 KiB |
After Width: | Height: | Size: 205 KiB |
Binary file not shown.
@ -0,0 +1,121 @@ |
|||||
|
import React, { useState, useEffect } from "react"; |
||||
|
import { |
||||
|
Modal, |
||||
|
CheckboxGroup, |
||||
|
Checkbox, |
||||
|
} from "@douyinfe/semi-ui"; |
||||
|
|
||||
|
function Setup(props) { |
||||
|
const { |
||||
|
close, |
||||
|
tableType, |
||||
|
tableList |
||||
|
} = props; |
||||
|
const [check, setCheck] = useState([]); |
||||
|
|
||||
|
const checkboxcss = { width: "25%", height: 16, margin: "0 0 20px 0" }; |
||||
|
|
||||
|
useEffect(() => { |
||||
|
//获取是否勾选信息 |
||||
|
const checkItem = localStorage.getItem(tableType); |
||||
|
setCheck(checkItem?JSON.parse(checkItem) : []) |
||||
|
ischeck(); |
||||
|
}, []); |
||||
|
function ischeck(value) { |
||||
|
if (check.length >= 8) { |
||||
|
if (check.includes(value)) { |
||||
|
return false; |
||||
|
} else { |
||||
|
return true; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
return ( |
||||
|
<Modal |
||||
|
title={ |
||||
|
<div> |
||||
|
表格属性设置 |
||||
|
<span |
||||
|
style={{ |
||||
|
width: 50, |
||||
|
lineHeight: "19px", |
||||
|
display: "inline-block", |
||||
|
|
||||
|
color: "white", |
||||
|
textAlign: "center", |
||||
|
marginLeft: 6, |
||||
|
background: |
||||
|
check.length == 8 |
||||
|
? "rgba(40, 123, 255, 1)" |
||||
|
: "rgba(176, 176, 176, 1)", |
||||
|
}} |
||||
|
> |
||||
|
{check.length}/8 |
||||
|
</span> |
||||
|
</div> |
||||
|
} |
||||
|
visible={true} |
||||
|
style={{ width: 600 }} |
||||
|
onOk={() => { |
||||
|
localStorage.setItem(tableType, JSON.stringify(check)); |
||||
|
close(); |
||||
|
}} |
||||
|
onCancel={() => { |
||||
|
close(); |
||||
|
}} |
||||
|
> |
||||
|
<CheckboxGroup |
||||
|
style={{ width: "100%", fontSize: 14 }} |
||||
|
key="primary1" |
||||
|
direction="horizontal" |
||||
|
defaultValue={check} |
||||
|
aria-label="表格属性设置" |
||||
|
onChange={(check) => { |
||||
|
setCheck(check); |
||||
|
ischeck(); |
||||
|
}} |
||||
|
> |
||||
|
{tableList.map((item,index)=>{ |
||||
|
return( |
||||
|
<div |
||||
|
key={index} |
||||
|
style={{ |
||||
|
width: 550, |
||||
|
border: "1px solid #EAEAEA", |
||||
|
padding: "0px 5px", |
||||
|
borderRadius: 4, |
||||
|
marginBottom: "20px", |
||||
|
}} |
||||
|
> |
||||
|
<div |
||||
|
style={{ |
||||
|
borderBottom: "1px solid #EAEAEA", |
||||
|
marginLeft: "10px", |
||||
|
padding: "8px 0px", |
||||
|
}} |
||||
|
> |
||||
|
{item.title} |
||||
|
</div> |
||||
|
<div style={{ padding: "15px 12px", width: 530 }}> |
||||
|
{item.list.map((itm) => { |
||||
|
return ( |
||||
|
<Checkbox |
||||
|
key={itm.value} |
||||
|
value={itm.value} |
||||
|
style={checkboxcss} |
||||
|
disabled={ischeck(itm.value)} |
||||
|
> |
||||
|
{itm.name} |
||||
|
</Checkbox> |
||||
|
); |
||||
|
})} |
||||
|
</div> |
||||
|
</div> |
||||
|
)})} |
||||
|
</CheckboxGroup> |
||||
|
</Modal> |
||||
|
); |
||||
|
} |
||||
|
|
||||
|
export default Setup; |
@ -1,191 +0,0 @@ |
|||||
import React, { useState, useEffect } from "react"; |
|
||||
import { |
|
||||
Modal, |
|
||||
CheckboxGroup, |
|
||||
Checkbox, |
|
||||
} from "@douyinfe/semi-ui"; |
|
||||
|
|
||||
function Setup(props) { |
|
||||
const { |
|
||||
visible, |
|
||||
close, |
|
||||
SETUPS, |
|
||||
CAMERAS, |
|
||||
cameraSetup, |
|
||||
} = props; |
|
||||
const [check, setCheck] = useState([]); |
|
||||
|
|
||||
const checkboxcss = { width: "25%", height: 16, margin: "0 0 20px 0" }; |
|
||||
|
|
||||
useEffect(() => { |
|
||||
//获取是否勾选信息 |
|
||||
const nvrItem = localStorage.getItem(SETUPS); |
|
||||
const cameraItem = localStorage.getItem(CAMERAS); |
|
||||
if (cameraSetup) { |
|
||||
setCheck(cameraItem ? JSON.parse(cameraItem) : []); |
|
||||
} else { |
|
||||
setCheck(nvrItem ? JSON.parse(nvrItem) : []); |
|
||||
} |
|
||||
ischeck(); |
|
||||
}, []); |
|
||||
|
|
||||
const equipmentNVR = [ |
|
||||
{ name: "设备厂家", value: "manufactor" }, |
|
||||
{ name: "添加账号", value: "accountNumber" }, |
|
||||
{ name: "通道数", value: "passageway" }, |
|
||||
{ name: "端口", value: "port" }, |
|
||||
{ name: "设备状态", value: "state" }, |
|
||||
{ name: "创建时间", value: "time" }, |
|
||||
]; |
|
||||
const projectNVR = [ |
|
||||
{ name: "项目名称", value: "name" }, |
|
||||
{ name: "pcode", value: "pcode" }, |
|
||||
{ name: "结构物", value: "structure" }, |
|
||||
]; |
|
||||
const equipmentCamera = [ |
|
||||
{ name: "设备厂家", value: "manufactor" }, |
|
||||
{ name: "接入类型", value: "type" }, |
|
||||
{ name: "设备状态", value: "state" }, |
|
||||
{ name: "云台支持", value: "support" }, |
|
||||
{ name: "内存卡信息", value: "memoryCard" }, |
|
||||
{ name: "设备创建时间", value: "time" }, |
|
||||
{ name: "设备添加账号", value: "account" }, |
|
||||
]; |
|
||||
const projectCamera = [ |
|
||||
{ name: "项目名称", value: "name" }, |
|
||||
{ name: "pcode", value: "pcode" }, |
|
||||
{ name: "结构物", value: "structure" }, |
|
||||
{ name: "测点", value: "measuringPoint" }, |
|
||||
{ name: "监测因素", value: "factor" }, |
|
||||
]; |
|
||||
|
|
||||
function ischeck(value) { |
|
||||
if (check.length >= 8) { |
|
||||
if (check.includes(value)) { |
|
||||
return false; |
|
||||
} else { |
|
||||
return true; |
|
||||
} |
|
||||
} |
|
||||
} |
|
||||
|
|
||||
return ( |
|
||||
<Modal |
|
||||
title={ |
|
||||
<div> |
|
||||
表格属性设置 |
|
||||
<span |
|
||||
style={{ |
|
||||
width: 50, |
|
||||
lineHeight: "19px", |
|
||||
display: "inline-block", |
|
||||
|
|
||||
color: "white", |
|
||||
textAlign: "center", |
|
||||
marginLeft: 6, |
|
||||
background: |
|
||||
check.length == 8 |
|
||||
? "rgba(40, 123, 255, 1)" |
|
||||
: "rgba(176, 176, 176, 1)", |
|
||||
}} |
|
||||
> |
|
||||
{check.length}/8 |
|
||||
</span> |
|
||||
</div> |
|
||||
} |
|
||||
visible={visible} |
|
||||
style={{ width: 600 }} |
|
||||
onOk={() => { |
|
||||
cameraSetup |
|
||||
? localStorage.setItem(CAMERAS, JSON.stringify(check)) |
|
||||
: localStorage.setItem(SETUPS, JSON.stringify(check)); |
|
||||
close(); |
|
||||
}} |
|
||||
onCancel={() => { |
|
||||
close(); |
|
||||
}} |
|
||||
> |
|
||||
<CheckboxGroup |
|
||||
style={{ width: "100%", fontSize: 14 }} |
|
||||
key="primary1" |
|
||||
direction="horizontal" |
|
||||
defaultValue={check} |
|
||||
aria-label="表格属性设置" |
|
||||
onChange={(check) => { |
|
||||
setCheck(check); |
|
||||
ischeck(); |
|
||||
}} |
|
||||
> |
|
||||
<div |
|
||||
style={{ |
|
||||
width: 550, |
|
||||
border: "1px solid #EAEAEA", |
|
||||
padding: "0px 5px", |
|
||||
borderRadius: 4, |
|
||||
marginBottom: "20px", |
|
||||
}} |
|
||||
> |
|
||||
<div |
|
||||
style={{ |
|
||||
borderBottom: "1px solid #EAEAEA", |
|
||||
marginLeft: "10px", |
|
||||
padding: "8px 0px", |
|
||||
}} |
|
||||
> |
|
||||
设备信息 |
|
||||
</div> |
|
||||
<div style={{ padding: "15px 12px", width: 530 }}> |
|
||||
{(cameraSetup ? equipmentCamera : equipmentNVR).map((item) => { |
|
||||
return ( |
|
||||
<Checkbox |
|
||||
key={item.value} |
|
||||
value={item.value} |
|
||||
style={checkboxcss} |
|
||||
disabled={ischeck(item.value)} |
|
||||
> |
|
||||
{item.name} |
|
||||
</Checkbox> |
|
||||
); |
|
||||
})} |
|
||||
</div> |
|
||||
</div> |
|
||||
|
|
||||
<div |
|
||||
style={{ |
|
||||
width: 550, |
|
||||
border: "1px solid #EAEAEA", |
|
||||
padding: "0px 5px", |
|
||||
borderRadius: 4, |
|
||||
}} |
|
||||
> |
|
||||
<div |
|
||||
style={{ |
|
||||
borderBottom: "1px solid #EAEAEA", |
|
||||
|
|
||||
marginLeft: "10px", |
|
||||
padding: "8px 0px", |
|
||||
}} |
|
||||
> |
|
||||
项目信息 |
|
||||
</div> |
|
||||
<div style={{ padding: "15px 12px", width: 530 }}> |
|
||||
{(cameraSetup ? projectCamera : projectNVR).map((item) => { |
|
||||
return ( |
|
||||
<Checkbox |
|
||||
key={item.value} |
|
||||
value={item.value} |
|
||||
style={checkboxcss} |
|
||||
disabled={ischeck(item.value)} |
|
||||
> |
|
||||
{item.name} |
|
||||
</Checkbox> |
|
||||
); |
|
||||
})} |
|
||||
</div> |
|
||||
</div> |
|
||||
</CheckboxGroup> |
|
||||
</Modal> |
|
||||
); |
|
||||
} |
|
||||
|
|
||||
export default Setup; |
|
@ -1,5 +1,9 @@ |
|||||
'use strict'; |
'use strict'; |
||||
|
|
||||
export default { |
import * as statuscode from './statuscode' |
||||
|
// import * as camera from './camera'
|
||||
|
|
||||
|
export default { |
||||
|
// ...statuscode,...camera
|
||||
|
...statuscode |
||||
} |
} |
@ -0,0 +1,65 @@ |
|||||
|
"use strict"; |
||||
|
|
||||
|
import { basicAction } from "@peace/utils"; |
||||
|
import { ApiTable } from "$utils"; |
||||
|
|
||||
|
export function getStatus(query) { |
||||
|
return (dispatch) => |
||||
|
basicAction({ |
||||
|
type: "get", |
||||
|
dispatch: dispatch, |
||||
|
actionType: "GET_STATUS", |
||||
|
query: query, |
||||
|
url: `${ApiTable.getStatus}`, |
||||
|
msg: { option: "获取状态码列表信息" }, |
||||
|
reducer: { name: "StatusList" }, |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
export function putStatueBanned(data, forbidden) { |
||||
|
return (dispatch) => |
||||
|
basicAction({ |
||||
|
type: "put", |
||||
|
dispatch: dispatch, |
||||
|
actionType: "PUT_STATUEBANNED", |
||||
|
data, |
||||
|
url: `${ApiTable.putStatueBanned}`, |
||||
|
msg: { option: forbidden ? "启用" : "禁用" }, //禁用状态码自定义
|
||||
|
reducer: {}, |
||||
|
}); |
||||
|
} |
||||
|
export function postStatusResolve(data) { |
||||
|
return (dispatch) => |
||||
|
basicAction({ |
||||
|
type: "post", |
||||
|
dispatch: dispatch, |
||||
|
data, |
||||
|
actionType: "POST_STATUS_RESOLVE", |
||||
|
url: `${ApiTable.postStatusResolve}`, |
||||
|
msg: { option: "" }, //编辑解决方案
|
||||
|
reducer: { name: "" }, |
||||
|
}); |
||||
|
} |
||||
|
export function postStatusCustom(data) { |
||||
|
return (dispatch) => |
||||
|
basicAction({ |
||||
|
type: "post", |
||||
|
dispatch: dispatch, |
||||
|
data, |
||||
|
actionType: "POST_STATUS_CUSTOM", |
||||
|
url: `${ApiTable.postStatusCustom}`, |
||||
|
msg: { option: "" }, //自定义状态码释义
|
||||
|
reducer: { name: "" }, |
||||
|
}); |
||||
|
} |
||||
|
export function getStatusSimpleAll() { |
||||
|
return (dispatch) => |
||||
|
basicAction({ |
||||
|
type: "get", |
||||
|
dispatch: dispatch, |
||||
|
actionType: "GET_STATUS_SIMPLE_ALL", |
||||
|
url: `${ApiTable.getStatusSimpleAll}`, |
||||
|
msg: { option: "" }, //获取摄像头能力列表
|
||||
|
reducer: { name: "" }, |
||||
|
}); |
||||
|
} |
@ -0,0 +1,178 @@ |
|||||
|
import React, { useState, useRef, useEffect } from "react"; |
||||
|
import { connect } from "react-redux"; |
||||
|
import { Modal, Spin,Input,TagInput ,Select} from "@douyinfe/semi-ui"; |
||||
|
function programmeModal (props) { |
||||
|
const { |
||||
|
close, |
||||
|
rowId, |
||||
|
dispatch, |
||||
|
actions, |
||||
|
nodesAll,//是否批量 |
||||
|
tableNews,//表格行全数据 |
||||
|
} = props; |
||||
|
const { offline } = actions; |
||||
|
|
||||
|
const [notesValue, setNotesValue] = useState('');//释义 |
||||
|
const [codeList, setCodeList] = useState([]);//状态码列表 |
||||
|
const [codeIdList, setcodeIdList] = useState([]);//选中的状态码id |
||||
|
const [platform, setPlatform] = useState(['yingshi']);//选中的平台 |
||||
|
|
||||
|
//初始化 |
||||
|
useEffect(() => { |
||||
|
setNotesValue(tableNews.paraphraseCustom||'') |
||||
|
dispatch( |
||||
|
offline.getStatusSimpleAll() |
||||
|
).then((res) => { |
||||
|
let mycodeList=[]; |
||||
|
if(res.payload&&res.payload.data){ |
||||
|
for (let index = 0; index < res.payload.data.length; index++) { |
||||
|
mycodeList.push({id:res.payload.data[index].id,status:res.payload.data[index].status+' '+res.payload.data[index].describe,platform:res.payload.data[index].platform}) |
||||
|
} |
||||
|
} |
||||
|
setCodeList(mycodeList) |
||||
|
}) |
||||
|
}, []); |
||||
|
|
||||
|
function handleOk () { |
||||
|
//点击弹框确定 右边按钮 |
||||
|
if(nodesAll){ |
||||
|
dispatch( |
||||
|
offline.postStatusCustom({ |
||||
|
statusId:codeIdList, |
||||
|
paraphrase:notesValue |
||||
|
}) |
||||
|
).then((res) => { |
||||
|
close(); |
||||
|
}) |
||||
|
} |
||||
|
else{ |
||||
|
dispatch( |
||||
|
offline.postStatusCustom({ |
||||
|
statusId:[rowId], |
||||
|
paraphrase:notesValue |
||||
|
}) |
||||
|
).then((res) => { |
||||
|
close(); |
||||
|
}) |
||||
|
} |
||||
|
} |
||||
|
function handleCancel () { |
||||
|
close(); |
||||
|
//点击弹框取消 左边按钮 |
||||
|
} |
||||
|
function onChange(value){//输入自定义释义 |
||||
|
if(value!==''){ |
||||
|
setNotesValue(value) |
||||
|
} |
||||
|
else{ |
||||
|
setNotesValue(null) |
||||
|
} |
||||
|
} |
||||
|
function onSelect(value){//选择状态码 |
||||
|
setcodeIdList(value) |
||||
|
} |
||||
|
function oneSelect(value){//切换平台 |
||||
|
setPlatform(value) |
||||
|
} |
||||
|
return ( |
||||
|
<> |
||||
|
<Modal |
||||
|
title={nodesAll?'批量设置':'释义'} |
||||
|
okText="确定" |
||||
|
cancelText="取消" |
||||
|
visible={true} |
||||
|
onOk={handleOk} |
||||
|
width={607} |
||||
|
onCancel={handleCancel} |
||||
|
> |
||||
|
{nodesAll?( |
||||
|
<div style={{margin:"17px 32px 28px 32px"}}> |
||||
|
<div style={{display: 'flex',alignItems: 'center'}}> |
||||
|
<div style={{width:84,textAlign:'right',color: 'rgba(0,0,0,0.65)'}}>状态码:</div> |
||||
|
<div> |
||||
|
<Select defaultValue='yingshi' onChange={oneSelect} style={{ width: 108 }}> |
||||
|
<Select.Option value='yingshi'>萤石云</Select.Option> |
||||
|
<Select.Option value='gb'>国标摄像头</Select.Option> |
||||
|
</Select> |
||||
|
</div> |
||||
|
<div style={{marginLeft:12}}> |
||||
|
<Select filter multiple style={{ width: 300 }} onChange={onSelect} placeholder='请选择状态码' maxTagCount={1} autoClearSearchValue={false}> |
||||
|
{codeList.map((item) => { |
||||
|
return( |
||||
|
item.platform==platform ? ( |
||||
|
<Select.Option key={item.id} value={item.id}> |
||||
|
{item.status} |
||||
|
</Select.Option> |
||||
|
) : ( |
||||
|
"" |
||||
|
) |
||||
|
) |
||||
|
})} |
||||
|
</Select> |
||||
|
</div> |
||||
|
</div> |
||||
|
<div style={{display: 'flex',alignItems: 'center',marginTop:21}}> |
||||
|
<div style={{width:84,textAlign:'right',color: 'rgba(0,0,0,0.65)'}}>修改释义:</div> |
||||
|
<div style={{width:'100%'}}><Input |
||||
|
style={{width:'100%'}} |
||||
|
value={notesValue} |
||||
|
onChange={onChange} |
||||
|
maxLength={18} |
||||
|
placeholder="请输入自定义释义" |
||||
|
showClear> |
||||
|
</Input></div> |
||||
|
</div> |
||||
|
</div> |
||||
|
):( |
||||
|
<div style={{margin:"17px 32px 28px 32px"}}> |
||||
|
<div style={{color: 'rgba(0,0,0,0.65)',fontWeight: 600}}>当视频出错时,提示以下内容:</div> |
||||
|
<div style={{marginTop:12}}><Input |
||||
|
style={{width:'100%'}} |
||||
|
value={notesValue} |
||||
|
onChange={onChange} |
||||
|
maxLength={18} |
||||
|
placeholder="请输入自定义释义" |
||||
|
showClear> |
||||
|
</Input> |
||||
|
</div> |
||||
|
</div> |
||||
|
)} |
||||
|
<div style={{display:'flex',margin:'0px 20px',alignItems: 'center',justifyContent: 'space-between'}}> |
||||
|
<div style={{display:'flex',justifyContent: 'center', |
||||
|
alignItems:'center', width: 240, height: 146 , |
||||
|
background: "url(/assets/images/background/codeBefore.png)",backgroundSize: "100% 100%",}}> |
||||
|
<div style={{color: 'rgba(255,255,255,0.8)',textShadow: '0px 1px 1px rgba(0,0,0,0)',textAlign: 'center',width: 130}}> |
||||
|
{tableNews.paraphrase||'初始化释义'} |
||||
|
</div> |
||||
|
</div> |
||||
|
<div> |
||||
|
<img |
||||
|
src="/assets/images/background/codeArrow.png" |
||||
|
alt="设置" |
||||
|
style={{ width: 18, height: 15 }} |
||||
|
/> |
||||
|
</div> |
||||
|
<div style={{ display:'flex',justifyContent: 'center', |
||||
|
alignItems:'center', width: 240, height: 146 , |
||||
|
background: "url(/assets/images/background/codeAfter.png)",backgroundSize: "100% 100%",}}> |
||||
|
<div style={{color: 'rgba(255,255,255,1)',textShadow: '0px 1px 1px #001969',textAlign: 'center',width: 130}}> |
||||
|
{notesValue} |
||||
|
</div> |
||||
|
</div> |
||||
|
</div> |
||||
|
</Modal> |
||||
|
</> |
||||
|
); |
||||
|
} |
||||
|
function mapStateToProps (state) { |
||||
|
const { auth, global, members, CameraKind, CameraAbility } = state; |
||||
|
return { |
||||
|
loading: members.isRequesting, |
||||
|
user: auth.user, |
||||
|
actions: global.actions, |
||||
|
CameraKind: CameraKind.data || [], |
||||
|
CameraAbility: CameraAbility.data || [], |
||||
|
}; |
||||
|
} |
||||
|
|
||||
|
export default connect(mapStateToProps)(programmeModal); |
@ -0,0 +1,85 @@ |
|||||
|
import React, { useState, useRef, useEffect } from "react"; |
||||
|
import { connect } from "react-redux"; |
||||
|
import { Modal, Spin,Input,TagInput } from "@douyinfe/semi-ui"; |
||||
|
|
||||
|
function programmeModal (props) { |
||||
|
const { |
||||
|
close, |
||||
|
rowId, |
||||
|
dispatch, |
||||
|
actions, |
||||
|
resolve,//解决方案 |
||||
|
} = props; |
||||
|
const { offline } = actions;//接口 |
||||
|
const [myresolve, setMyResolve] = useState([]);//解决方案 |
||||
|
//初始化 |
||||
|
useEffect(() => { |
||||
|
let resolvearr=[] |
||||
|
for (let index = 0; index < resolve.length; index++) { |
||||
|
resolvearr.push(resolve[index].resolve) |
||||
|
} |
||||
|
setMyResolve(resolvearr) |
||||
|
}, []); |
||||
|
|
||||
|
function handleOk () { |
||||
|
//点击弹框确定 右边按钮 |
||||
|
dispatch( |
||||
|
offline.postStatusResolve({ |
||||
|
statusId:rowId, |
||||
|
resolve:myresolve |
||||
|
}) |
||||
|
).then((res) => { |
||||
|
close(); |
||||
|
}) |
||||
|
} |
||||
|
function handleCancel () { |
||||
|
close(); |
||||
|
//点击弹框取消 左边按钮 |
||||
|
} |
||||
|
function onChange(value){ |
||||
|
setMyResolve(value) |
||||
|
} |
||||
|
return ( |
||||
|
<> |
||||
|
<Modal |
||||
|
title="方案" |
||||
|
okText="确定" |
||||
|
cancelText="取消" |
||||
|
visible={true} |
||||
|
onOk={handleOk} |
||||
|
width={607} |
||||
|
onCancel={handleCancel} |
||||
|
> |
||||
|
<div style={{margin:"17px 56px 18px 31px"}}> |
||||
|
<div style={{color:'rgba(0, 0, 0, 0.65)',}}> |
||||
|
解决方案设置: |
||||
|
</div> |
||||
|
<div style={{color:'rgba(0, 0, 0, 0.45)',fontSize:12,marginTop:4}}> |
||||
|
敲击回车键后,输入内容将成为标签 |
||||
|
</div> |
||||
|
<div style={{marginTop:10}}> |
||||
|
<TagInput |
||||
|
defaultValue={myresolve} |
||||
|
placeholder='请输入解决方案' |
||||
|
size='large' |
||||
|
maxLength={18} |
||||
|
onChange={onChange} |
||||
|
/> |
||||
|
</div> |
||||
|
</div> |
||||
|
</Modal> |
||||
|
</> |
||||
|
); |
||||
|
} |
||||
|
function mapStateToProps (state) { |
||||
|
const { auth, global, members, CameraKind, CameraAbility } = state; |
||||
|
return { |
||||
|
loading: members.isRequesting, |
||||
|
user: auth.user, |
||||
|
actions: global.actions, |
||||
|
CameraKind: CameraKind.data || [], |
||||
|
CameraAbility: CameraAbility.data || [], |
||||
|
}; |
||||
|
} |
||||
|
|
||||
|
export default connect(mapStateToProps)(programmeModal); |
@ -0,0 +1,299 @@ |
|||||
|
import React, { useState, useRef, useEffect, useImperativeHandle } from "react"; |
||||
|
import { connect } from "react-redux"; |
||||
|
import { Modal, Form, Row, Col, Spin } from "@douyinfe/semi-ui"; |
||||
|
import { IconTickCircle } from "@douyinfe/semi-icons"; |
||||
|
|
||||
|
import moment from "moment"; |
||||
|
|
||||
|
function pushModal (props) { |
||||
|
const { modalName, pushRef } = props; |
||||
|
const { dispatch, actions, vender, close } = props; |
||||
|
const pushData = props.pushData || {}; //修改时传来的值 |
||||
|
const form = useRef(); |
||||
|
const [visible, setVisible] = useState(false); //是否显示弹框 |
||||
|
const [isloading, setloading] = useState(false); //是否显示loading |
||||
|
const [loadingTip, setloadingTip] = useState("获取中...请稍后..."); //loading tip的值 |
||||
|
const [step, setstep] = useState("none"); //第几步 |
||||
|
const [okText, setokText] = useState("测试校验"); //ok弹框text 右边 |
||||
|
const [cancelText, setcancelText] = useState("取消"); //取消弹框text 左边 |
||||
|
const [formObj, setformObj] = useState(); //接口入参 |
||||
|
|
||||
|
function showDialog () { |
||||
|
//打开弹框 |
||||
|
setVisible(true); |
||||
|
} |
||||
|
function positionForm (val) { |
||||
|
let zz = /^(-?\d+)(\.\d+)?$/; |
||||
|
if (!val) { |
||||
|
return "请输入或拾取高德经纬度坐标"; |
||||
|
} else if (val.split(",").length != 2) { |
||||
|
return "请输入格式为116.354169,39.835452的经纬度坐标"; |
||||
|
} else if (!zz.test(val.split(",")[0])) { |
||||
|
return "只能填写数字"; |
||||
|
} else if (!zz.test(val.split(",")[1])) { |
||||
|
return "只能填写数字"; |
||||
|
} else { |
||||
|
return ""; |
||||
|
} |
||||
|
} |
||||
|
function handleOk () { |
||||
|
//点击弹框确定 右边按钮 |
||||
|
if (step == "none") { |
||||
|
form.current |
||||
|
.validate() |
||||
|
.then((values) => { |
||||
|
//表单校验 |
||||
|
console.log(values) |
||||
|
let valuesObj = JSON.parse(JSON.stringify(values)); |
||||
|
valuesObj.longitude = values.position.split(",")[0]; |
||||
|
valuesObj.latitude = values.position.split(",")[1]; |
||||
|
delete valuesObj.position; |
||||
|
if (pushData.id) { |
||||
|
valuesObj.id = pushData.id; |
||||
|
} |
||||
|
var front = new moment(); //验证前时间 |
||||
|
setloading(true); |
||||
|
dispatch( |
||||
|
actions.equipmentWarehouse.getCheck({ |
||||
|
serialNo: valuesObj.serialNo, |
||||
|
}) |
||||
|
).then((res) => { |
||||
|
var after = new moment(); //验证后时间 |
||||
|
var duration = moment.duration(after.diff(front))._data.milliseconds; |
||||
|
if (res.success) { |
||||
|
setTimeout( |
||||
|
() => { |
||||
|
setloadingTip("已完成"); |
||||
|
setTimeout(() => { |
||||
|
setstep("block"); |
||||
|
setloading(false); |
||||
|
setokText("确认"); |
||||
|
setcancelText("上一步"); |
||||
|
setloadingTip("获取中...请稍后..."); |
||||
|
}, 1000); |
||||
|
}, |
||||
|
duration > 2000 ? 0 : 2000 - duration |
||||
|
); |
||||
|
} else { |
||||
|
setTimeout( |
||||
|
() => { |
||||
|
setloadingTip("校验失败"); |
||||
|
setTimeout(() => { |
||||
|
setstep("none"); |
||||
|
setloading(false); |
||||
|
setokText("测试校验"); |
||||
|
setcancelText("取消"); |
||||
|
setloadingTip("获取中...请稍后..."); |
||||
|
}, 1000); |
||||
|
}, |
||||
|
duration > 2000 ? 0 : 2000 - duration |
||||
|
); |
||||
|
} |
||||
|
}); |
||||
|
setformObj(valuesObj); |
||||
|
}) |
||||
|
.catch((errors) => { |
||||
|
//表单校验失败 |
||||
|
console.log("errors", errors); |
||||
|
}); |
||||
|
} else { |
||||
|
dispatch(actions.equipmentWarehouse.addchangepush(formObj)).then((res) => { |
||||
|
setVisible(false); |
||||
|
close(); |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
|
function handleAfterClose () { |
||||
|
//在关闭之后 |
||||
|
setstep("none"); |
||||
|
setokText("测试校验"); |
||||
|
setcancelText("取消"); |
||||
|
} |
||||
|
function handleCancel () { |
||||
|
//点击弹框取消 左边按钮 |
||||
|
if (step == "none") { |
||||
|
setVisible(false); |
||||
|
} else { |
||||
|
setstep("none"); |
||||
|
setokText("测试校验"); |
||||
|
setcancelText("取消"); |
||||
|
} |
||||
|
} |
||||
|
function handleLocation () { |
||||
|
//高德经纬度 |
||||
|
window.open("https://lbs.amap.com/tools/picker", "_blank"); |
||||
|
} |
||||
|
useImperativeHandle(pushRef, () => ({ |
||||
|
//传给父组件方法 |
||||
|
//aa即为子组件暴露给父组件的方法 |
||||
|
pushNumber: () => formObj.serialNo |
||||
|
})); |
||||
|
return ( |
||||
|
<> |
||||
|
<div onClick={showDialog}>{modalName == "add" ? "创建推送" : "修改"}</div> |
||||
|
<Modal |
||||
|
title={modalName == "add" ? "创建推送" : "修改"} |
||||
|
okText={okText} |
||||
|
cancelText={cancelText} //取消按钮 |
||||
|
visible={visible} |
||||
|
onOk={handleOk} |
||||
|
width={782} |
||||
|
height={720} |
||||
|
afterClose={handleAfterClose} |
||||
|
onCancel={handleCancel} |
||||
|
> |
||||
|
<Spin tip={loadingTip} spinning={isloading}> |
||||
|
<div |
||||
|
style={{ |
||||
|
paddingLeft: 16, |
||||
|
display: step == "none" ? "block" : "none", |
||||
|
}} |
||||
|
> |
||||
|
<Form |
||||
|
allowEmpty |
||||
|
labelPosition="left" |
||||
|
labelAlign="left" |
||||
|
labelWidth="90px" |
||||
|
onValueChange={(values) => console.log(values)} |
||||
|
getFormApi={(formApi) => (form.current = formApi)} |
||||
|
> |
||||
|
<Row> |
||||
|
<Col span={12}> |
||||
|
<Form.Input |
||||
|
maxLength="39" |
||||
|
field="serialNo" |
||||
|
label="设备编号:" |
||||
|
initValue={pushData.serialNo || ""} |
||||
|
placeholder="请输入设备编号" |
||||
|
style={{ width: 149 }} |
||||
|
rules={[{ required: true, message: "请输入设备编号" }]} |
||||
|
/> |
||||
|
</Col> |
||||
|
<Col span={12}> |
||||
|
<Form.InputNumber |
||||
|
formatter={(value) => `${value}`.replace(/\D/g, "")} |
||||
|
hideButtons={true} |
||||
|
maxLength="15" |
||||
|
field="regionCode" |
||||
|
label="行政区区码:" |
||||
|
initValue={pushData.regionCode || ""} |
||||
|
placeholder="请输入行政区区码" |
||||
|
style={{ width: 149 }} |
||||
|
/> |
||||
|
</Col> |
||||
|
<Col span={24}> |
||||
|
<Form.Input |
||||
|
maxLength="36" |
||||
|
field="name" |
||||
|
label="设备名称:" |
||||
|
initValue={pushData.name || ""} |
||||
|
placeholder="请输入设备名称" |
||||
|
style={{ width: 421 }} |
||||
|
rules={[ |
||||
|
{ |
||||
|
required: true, |
||||
|
message: "请输入设备名称、常用项目或位置定义", |
||||
|
}, |
||||
|
]} |
||||
|
/> |
||||
|
</Col> |
||||
|
<Col span={24}> |
||||
|
<Form.Select |
||||
|
label="设备厂家:" |
||||
|
field="venderId" |
||||
|
initValue={pushData.venderId || null} |
||||
|
placeholder="请选择设备厂家" |
||||
|
style={{ width: 421 }} |
||||
|
rules={[{ required: true, message: "请选择设备厂家" }]} |
||||
|
> |
||||
|
{vender.map((item, index) => ( |
||||
|
<Form.Select.Option key={index} value={item.id}> |
||||
|
{item.name} |
||||
|
</Form.Select.Option> |
||||
|
))} |
||||
|
</Form.Select> |
||||
|
</Col> |
||||
|
<Col span={24} style={{ display: "flex" }}> |
||||
|
<Form.Input |
||||
|
maxLength="39" |
||||
|
field="position" |
||||
|
label="安装位置:" |
||||
|
initValue={ |
||||
|
pushData.longitude && pushData.latitude |
||||
|
? pushData.longitude + "," + pushData.latitude |
||||
|
: "" |
||||
|
} |
||||
|
placeholder="请输入或拾取高德经纬度坐标" |
||||
|
style={{ width: 386 }} |
||||
|
validate={positionForm} |
||||
|
rules={[ |
||||
|
{ |
||||
|
required: true, |
||||
|
message: "请输入或拾取高德经纬度坐标", |
||||
|
}, |
||||
|
]} |
||||
|
/> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: 32, |
||||
|
height: 32, |
||||
|
background: "#1859C1", |
||||
|
marginLeft: 4, |
||||
|
display: "flex", |
||||
|
justifyContent: "center", |
||||
|
alignItems: "center", |
||||
|
cursor: "pointer", |
||||
|
marginTop: 12, |
||||
|
borderRadius: 3 + "px", |
||||
|
}} |
||||
|
onClick={handleLocation} |
||||
|
> |
||||
|
<img |
||||
|
src="../../../assets/images/background/location.png" |
||||
|
width={16} |
||||
|
height={20} |
||||
|
/> |
||||
|
</div> |
||||
|
</Col> |
||||
|
</Row> |
||||
|
</Form> |
||||
|
</div> |
||||
|
|
||||
|
<div style={{ height: 224, display: step }}> |
||||
|
<div |
||||
|
style={{ |
||||
|
paddingTop: 50, |
||||
|
display: "flex", |
||||
|
justifyContent: "center", |
||||
|
}} |
||||
|
> |
||||
|
<IconTickCircle style={{ color: "#04B234", fontSize: 60 }} /> |
||||
|
</div> |
||||
|
<div |
||||
|
style={{ |
||||
|
marginTop: 20, |
||||
|
display: "flex", |
||||
|
justifyContent: "center", |
||||
|
}} |
||||
|
> |
||||
|
是否确认创建推送? |
||||
|
</div> |
||||
|
</div> |
||||
|
</Spin> |
||||
|
</Modal> |
||||
|
</> |
||||
|
); |
||||
|
} |
||||
|
|
||||
|
function mapStateToProps (state) { |
||||
|
const { auth, global, members, vender } = state; |
||||
|
return { |
||||
|
loading: members.isRequesting, |
||||
|
user: auth.user, |
||||
|
actions: global.actions, |
||||
|
members: members.data, |
||||
|
vender: vender.data || [], //设备厂家 |
||||
|
}; |
||||
|
} |
||||
|
|
||||
|
export default connect(mapStateToProps)(pushModal); |
@ -1,20 +1,566 @@ |
|||||
import React, { useEffect } from 'react'; |
import React, { useState, useEffect, useRef } from "react"; |
||||
import { connect } from 'react-redux'; |
import { connect } from "react-redux"; |
||||
import { Coming } from '$components' |
import moment from "moment"; |
||||
import '../style.less' |
import { Button, Form, Table, Pagination, Skeleton, Popconfirm, Popover, Tag, } from "@douyinfe/semi-ui"; |
||||
|
import "../style.less"; |
||||
|
import { ApiTable } from "$utils"; |
||||
|
import { Setup } from "$components"; |
||||
|
import PushModal from "../components/pushModal"; |
||||
|
// import SideSheets from "../components/sideSheet"; |
||||
|
// import { skeletonScreen } from "../components/skeletonScreen"; |
||||
|
// import { ReminderBox } from "../../../components/index"; |
||||
|
|
||||
|
export const accessType = [ |
||||
|
{ name: "萤石云", key: "yingshi" }, |
||||
|
{ name: "NVR", key: "nvr" }, |
||||
|
{ name: "IPC", key: "ipc" }, |
||||
|
{ name: "级联", key: "cascade" }, |
||||
|
]; |
||||
|
|
||||
const Carrierpigeon = (props) => { |
const Carrierpigeon = (props) => { |
||||
|
const { history, dispatch, actions, user, loading, equipmentWarehouseNvr } = props; |
||||
|
const { equipmentWarehouse } = actions; |
||||
|
const [setup, setSetup] = useState(false); |
||||
|
const [sideSheet, setSideSheet] = useState(false); |
||||
|
const [setupp, setSetupp] = useState([]); |
||||
|
const [venderList, setvenderList] = useState([]); //厂商信息 |
||||
|
const [query, setQuery] = useState({ limit: 10, page: 0 }); //页码信息 |
||||
|
const [search, setearch] = useState({}); //搜索条件 |
||||
|
const [rowId, setRowId] = useState(); //表格数据id |
||||
|
const [reminder, setReminder] = useState(false); //提醒弹框 |
||||
|
const api = useRef(); |
||||
|
const searchData = useRef(search) |
||||
|
const limits = useRef(); //每页实际条数 |
||||
|
const page = useRef(query.page); |
||||
|
const PIGEON = "pigeon"; |
||||
|
const USER = "user" + props.user.id |
||||
|
const nvrRef = useRef(); //获取子组件的设备编号 |
||||
|
const tableList = [//表格属性 |
||||
|
{ |
||||
|
title: '推送信息', |
||||
|
list: [ |
||||
|
{ name: "策略类型", value: "PolicyType" }, |
||||
|
{ name: "推送机制", value: "PushMechanism" }, |
||||
|
{ name: "监听设备数量", value: "DevicesNumber" }, |
||||
|
{ name: "累计推送次数", value: "PushNumber" }, |
||||
|
] |
||||
|
}, |
||||
|
]; |
||||
|
useEffect(() => { |
||||
|
dispatch(actions.equipmentWarehouse.getVender()).then((res) => { |
||||
|
setvenderList(res.payload.data); |
||||
|
attribute(res.payload.data); |
||||
|
}); |
||||
|
//初始化表格显示设置 |
||||
|
localStorage.getItem(PIGEON) == null |
||||
|
? localStorage.setItem( |
||||
|
PIGEON, |
||||
|
JSON.stringify(["PolicyType", "PushMechanism", "DevicesNumber", "PushNumber"]) |
||||
|
) |
||||
|
: ""; |
||||
|
}, []); |
||||
|
|
||||
return ( |
useEffect(() => { |
||||
<Coming /> |
equipmentGetNvr(); |
||||
) |
}, [query, search]); |
||||
} |
|
||||
|
const equipmentGetNvr = () => { |
||||
|
searchData.current = { ...query, ...search } |
||||
|
dispatch(equipmentWarehouse.getNvr(searchData.current)).then((res) => { |
||||
|
limits.current = res.payload.data.data.length |
||||
|
}); |
||||
|
} |
||||
|
|
||||
|
function equipmentStatus (data) { |
||||
|
switch (data) { |
||||
|
case "email": |
||||
|
return "邮件通知" |
||||
|
case "note": |
||||
|
return "短信通知" |
||||
|
default: |
||||
|
return "未知" |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
function colorStatus (data) { |
||||
|
switch (data) { |
||||
|
case "ON": |
||||
|
return "#04B234" |
||||
|
case "ONLINE": |
||||
|
return "#04B234" |
||||
|
case "OFF": |
||||
|
return "rgba(0, 0, 0, 0.45)" |
||||
|
default: |
||||
|
return "#1859C1" |
||||
|
} |
||||
|
} |
||||
|
const columns = [ |
||||
|
{ |
||||
|
title: "序号", |
||||
|
render: (_, record, index) => { |
||||
|
return index + 1; |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "策略名称", |
||||
|
dataIndex: "name", |
||||
|
render: (_, r, index) => { |
||||
|
console.log("r:" + r.name); |
||||
|
return r.name |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "操作", |
||||
|
width: "20%", |
||||
|
dataIndex: "", |
||||
|
render: (_, row) => { |
||||
|
return ( |
||||
|
<div style={{ display: "flex" }}> |
||||
|
<Button theme="borderless"> |
||||
|
<PushModal |
||||
|
modalName="revise" |
||||
|
/> |
||||
|
</Button> |
||||
|
<Button |
||||
|
theme="borderless" |
||||
|
onClick={() => { |
||||
|
setSideSheet(true); |
||||
|
setRowId(row.id); |
||||
|
}} |
||||
|
> |
||||
|
禁用 |
||||
|
</Button> |
||||
|
<Popconfirm |
||||
|
title="是否确定删除?" |
||||
|
arrowPointAtCenter={false} |
||||
|
showArrow={true} |
||||
|
position="topRight" |
||||
|
onConfirm={() => { |
||||
|
dispatch(equipmentWarehouse.delNvr(row.id)).then(() => { |
||||
|
if (page.current > 0 && limits.current < 2) { |
||||
|
setQuery({ limit: 10, page: page.current - 1 }) |
||||
|
} else { |
||||
|
setQuery({ limit: 10, page: page.current }) |
||||
|
} |
||||
|
}); |
||||
|
}} |
||||
|
> |
||||
|
<Button theme="borderless">删除</Button> |
||||
|
</Popconfirm> |
||||
|
<Button theme="borderless"> |
||||
|
复制 |
||||
|
</Button> |
||||
|
<Button theme="borderless"> |
||||
|
日志 |
||||
|
</Button> |
||||
|
</div> |
||||
|
); |
||||
|
}, |
||||
|
}, |
||||
|
]; |
||||
|
|
||||
|
//获取表格属性设置 |
||||
|
function attribute (data) { |
||||
|
const arr = localStorage.getItem(PIGEON) |
||||
|
? JSON.parse(localStorage.getItem(PIGEON)) |
||||
|
: []; |
||||
|
|
||||
|
const column = [ |
||||
|
{ |
||||
|
title: "推送机制", |
||||
|
dataIndex: "venderId", |
||||
|
key: "PushMechanism", |
||||
|
render: (_, r, index) => { |
||||
|
let manufactorName = data.find((item) => item.id == r.venderId); |
||||
|
return manufactorName ? manufactorName.name : ""; |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "监听设备数量", |
||||
|
dataIndex: "DevicesNum", |
||||
|
key: "DevicesNumber", |
||||
|
render: (_, r, index) => { |
||||
|
return r.name |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "累计推送次数", |
||||
|
dataIndex: "PushNum", |
||||
|
key: "PushNumber", |
||||
|
render: (_, r, index) => { |
||||
|
return (r.name + '次') |
||||
|
}, |
||||
|
}, |
||||
|
|
||||
|
{ |
||||
|
title: "策略类型", |
||||
|
dataIndex: "size", |
||||
|
key: "PolicyType", |
||||
|
render: (_, r, index) => { |
||||
|
let status = r.gbNvr; |
||||
|
return ( |
||||
|
<div> |
||||
|
<span |
||||
|
style={{ |
||||
|
width: 8, |
||||
|
height: 8, |
||||
|
display: "inline-block", |
||||
|
borderRadius: "50%", |
||||
|
backgroundColor: status ? colorStatus(status.online) : "", |
||||
|
margin: "0 8px 0 0", |
||||
|
}} |
||||
|
/> |
||||
|
{status ? "邮件通知" : equipmentStatus(status.email)} |
||||
|
</div> |
||||
|
); |
||||
|
}, |
||||
|
}, |
||||
|
]; |
||||
|
for (let i = 0; i < arr.length; i++) { |
||||
|
let colum = column.filter((item) => { |
||||
|
return item.key === arr[i]; |
||||
|
}); |
||||
|
columns.splice(i + 2, 0, colum[0]); |
||||
|
} |
||||
|
setSetupp(columns); |
||||
|
} |
||||
|
|
||||
|
//表格请求数据中station属性数据的展示 |
||||
|
// function station (r, name, projects) { |
||||
|
// let data = [] |
||||
|
// if (projects == "projects") { |
||||
|
// r.station.map((v) => { |
||||
|
// if (v.structure.projects.length > 0) { |
||||
|
// v.structure.projects.map((item) => data.push(item[name])) |
||||
|
// } |
||||
|
// }) |
||||
|
// } else { |
||||
|
// r.station.map((v, index) => data.push(v.structure[name])) |
||||
|
// } |
||||
|
// let dataSet = [...(new Set(data))] |
||||
|
// return dataSet.length > 0 ? <Popover |
||||
|
// key="updateTime" |
||||
|
// position="top" |
||||
|
// content={ |
||||
|
// dataSet.length > 1 ? <article style={{ padding: 12 }}>{dataSet.map((v, index) => <div key={index}>{v}</div>)}</article> : "" |
||||
|
// } |
||||
|
// > |
||||
|
// <Tag>{dataSet.length > 1 ? `${dataSet[0]}...` : dataSet.length > 0 ? dataSet[0] : ""}</Tag> |
||||
|
// </Popover> : "" |
||||
|
|
||||
|
// } |
||||
|
|
||||
|
//条件赛选样式 |
||||
|
const screen = { |
||||
|
width: 193, |
||||
|
marginRight: 20, |
||||
|
marginBottom: 16, |
||||
|
color: "rgba(0, 0, 0, 0.65)", |
||||
|
}; |
||||
|
|
||||
|
return ( |
||||
|
<> |
||||
|
<div> |
||||
|
<video |
||||
|
id="nvrBanner" |
||||
|
autoPlay |
||||
|
loop |
||||
|
muted |
||||
|
style={{ width: "100%", objectFit: "cover", height: 171 }} |
||||
|
src="/assets/video/nvr_banner.mp4" |
||||
|
type="video/mp4" |
||||
|
/> |
||||
|
<div style={{ position: "absolute", top: 12 }}> |
||||
|
<div |
||||
|
style={{ |
||||
|
fontSize: 22, |
||||
|
paddingTop: 15, |
||||
|
marginLeft: 21, |
||||
|
}} |
||||
|
> |
||||
|
信鸽服务 |
||||
|
</div> |
||||
|
<div |
||||
|
style={{ |
||||
|
fontSize: 14, |
||||
|
paddingTop: 18, |
||||
|
marginLeft: 20, |
||||
|
}} |
||||
|
> |
||||
|
对设备状态变更进行监听,通过短信或邮件通知指定人员 |
||||
|
</div> |
||||
|
<div |
||||
|
style={{ |
||||
|
fontSize: 14, |
||||
|
marginTop: 28, |
||||
|
marginLeft: 21, |
||||
|
width: 89, |
||||
|
height: 32, |
||||
|
lineHeight: "32px", |
||||
|
textAlign: "center", |
||||
|
backgroundColor: "#D9EAFF", |
||||
|
color: "#1859C1", |
||||
|
cursor: "pointer", |
||||
|
}} |
||||
|
> |
||||
|
<PushModal |
||||
|
modalName="add" |
||||
|
/> |
||||
|
{/* <NvrModal |
||||
|
modalName="add" |
||||
|
venderList={venderList} |
||||
|
nvrRef={nvrRef} |
||||
|
close={() => { |
||||
|
const remind = localStorage.getItem(USER); |
||||
|
console.log(remind) |
||||
|
if (!remind) { |
||||
|
setReminder(true) |
||||
|
} |
||||
|
equipmentGetNvr(); |
||||
|
}} |
||||
|
/> */} |
||||
|
</div> |
||||
|
</div> |
||||
|
</div> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: "100%", |
||||
|
background: "#FFFFFF", |
||||
|
borderRadius: 3, |
||||
|
padding: "8px 20px", |
||||
|
marginTop: 20, |
||||
|
}} |
||||
|
> |
||||
|
<div |
||||
|
style={{ |
||||
|
height: 22, |
||||
|
fontSize: 16, |
||||
|
fontFamily: "PingFangSC-Medium, PingFang SC", |
||||
|
fontWeight: "bold", |
||||
|
color: " rgba(0, 0, 0, 0.85)", |
||||
|
lineHeight: "22px", |
||||
|
marginBottom: 16, |
||||
|
}} |
||||
|
> |
||||
|
筛选条件 |
||||
|
</div> |
||||
|
<div style={{ display: "flex" }}> |
||||
|
<Form |
||||
|
onSubmit={(values) => console.log(values)} |
||||
|
// onValueChange={values=>console.log(values)} |
||||
|
getFormApi={(formApi) => (api.current = formApi)} |
||||
|
layout="horizontal" |
||||
|
style={{ position: "relative", width: "100%", flex: 1 }} |
||||
|
> |
||||
|
<Form.Input |
||||
|
label="策略名称:" |
||||
|
field="keyword" |
||||
|
maxLength="36" |
||||
|
placeholder="请输入策略名称" |
||||
|
labelPosition="left" |
||||
|
style={screen} |
||||
|
/> |
||||
|
<Form.Select |
||||
|
label="策略类型:" |
||||
|
labelPosition="left" |
||||
|
field="PolicyType" |
||||
|
style={screen} |
||||
|
placeholder="全部" |
||||
|
showClear |
||||
|
> |
||||
|
<Form.Select.Option value="ALL">全部</Form.Select.Option> |
||||
|
<Form.Select.Option value="OFF">短信通知</Form.Select.Option> |
||||
|
<Form.Select.Option value="UNKONW">邮件通知</Form.Select.Option> |
||||
|
</Form.Select> |
||||
|
</Form> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: 150, |
||||
|
display: "flex", |
||||
|
justifyContent: "flex-end", |
||||
|
alignItems: "flex-end", |
||||
|
}} |
||||
|
> |
||||
|
<Button |
||||
|
theme="solid" |
||||
|
type="primary" |
||||
|
style={{ |
||||
|
width: 65, |
||||
|
height: 30, |
||||
|
borderRadius: 3, |
||||
|
marginBottom: 20, |
||||
|
marginRight: 20, |
||||
|
}} |
||||
|
onClick={() => { |
||||
|
api.current.validate().then((v) => { |
||||
|
setearch(v); |
||||
|
setQuery({ limit: 10, page: 0 }) |
||||
|
}); |
||||
|
}} |
||||
|
> |
||||
|
搜索 |
||||
|
</Button> |
||||
|
<Button |
||||
|
theme="light" |
||||
|
type="primary" |
||||
|
style={{ |
||||
|
width: 65, |
||||
|
height: 30, |
||||
|
backGround: "#FFFFFF", |
||||
|
borderRadius: 3, |
||||
|
border: "1px solid #D9D9D9", |
||||
|
marginBottom: 20, |
||||
|
}} |
||||
|
onClick={() => { |
||||
|
api.current.reset(); |
||||
|
setearch({}); |
||||
|
setQuery({ limit: 10, page: 0 }) |
||||
|
}} |
||||
|
> |
||||
|
重置 |
||||
|
</Button> |
||||
|
</div> |
||||
|
</div> |
||||
|
</div> |
||||
|
<div style={{ background: "#FFFFFF", marginTop: 5 }}> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: "100%", |
||||
|
display: "flex", |
||||
|
justifyContent: "space-between", |
||||
|
padding: "13px 20px", |
||||
|
}} |
||||
|
> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: 64, |
||||
|
height: 22, |
||||
|
fontSize: 16, |
||||
|
fontfAmily: "PingFangSC-Medium, PingFang SC", |
||||
|
fontWeight: "bold", |
||||
|
color: "rgba(0, 0, 0, 0.85)", |
||||
|
lineHeight: "22px", |
||||
|
}} |
||||
|
> |
||||
|
策略详情 |
||||
|
</div> |
||||
|
<div> |
||||
|
<Button |
||||
|
style={{ |
||||
|
width: 32, |
||||
|
height: 32, |
||||
|
background: "#D9D9D9", |
||||
|
borderadius: 3, |
||||
|
marginRight: 20, |
||||
|
}} |
||||
|
type="primary" |
||||
|
key="primary" |
||||
|
onClick={() => { |
||||
|
setSetup(true); |
||||
|
}} |
||||
|
> |
||||
|
<img |
||||
|
src="/assets/images/background/setup.png" |
||||
|
alt="设置" |
||||
|
style={{ width: 18, height: 18 }} |
||||
|
/> |
||||
|
</Button> |
||||
|
</div> |
||||
|
</div> |
||||
|
<Skeleton |
||||
|
loading={loading} |
||||
|
// placeholder={skeletonScreen()} |
||||
|
active={true} |
||||
|
> |
||||
|
<Table |
||||
|
columns={setupp.filter((s) => s)} |
||||
|
dataSource={equipmentWarehouseNvr.data} |
||||
|
bordered={false} |
||||
|
empty="暂无数据" |
||||
|
style={{ |
||||
|
padding: "0px 20px", |
||||
|
}} |
||||
|
pagination={false} |
||||
|
/> |
||||
|
</Skeleton> |
||||
|
|
||||
|
<div |
||||
|
style={{ |
||||
|
display: "flex", |
||||
|
justifyContent: "flex-end", |
||||
|
padding: "20px 20px", |
||||
|
}} |
||||
|
> |
||||
|
<span style={{ lineHeight: "30px" }}> |
||||
|
共{equipmentWarehouseNvr.total}条策略 |
||||
|
</span> |
||||
|
<Pagination |
||||
|
total={equipmentWarehouseNvr.total} |
||||
|
showSizeChanger |
||||
|
currentPage={query.page + 1} |
||||
|
pageSizeOpts={[10, 20, 30, 40]} |
||||
|
onChange={(currentPage, pageSize) => { |
||||
|
setQuery({ limit: pageSize, page: currentPage - 1 }); |
||||
|
page.current = currentPage - 1 |
||||
|
}} |
||||
|
/> |
||||
|
</div> |
||||
|
|
||||
|
{setup ? ( |
||||
|
<Setup |
||||
|
tableType={PIGEON} |
||||
|
tableList={tableList} |
||||
|
close={() => { |
||||
|
setSetup(false); |
||||
|
attribute(venderList); |
||||
|
}} |
||||
|
/> |
||||
|
) : ( |
||||
|
"" |
||||
|
)} |
||||
|
|
||||
|
{/* {sideSheet ? ( |
||||
|
<SideSheets |
||||
|
visible={true} |
||||
|
rowId={rowId} |
||||
|
accessType={accessType} |
||||
|
venderList={venderList} |
||||
|
close={() => { |
||||
|
setSideSheet(false); |
||||
|
}} |
||||
|
/> |
||||
|
) : ( |
||||
|
[] |
||||
|
)} */} |
||||
|
{/* <ReminderBox |
||||
|
title="是否继续添加NVR摄像头?" |
||||
|
wait="再等等" |
||||
|
toadd="去添加" |
||||
|
visible={reminder} |
||||
|
USER={USER} |
||||
|
onOk={() => { |
||||
|
history.push({ pathname: '/equipmentWarehouse/camera', query: { addNvr: true, serialNo: nvrRef.current.nvrNumber() } }); |
||||
|
localStorage.setItem('vcmp_selected_sider', JSON.stringify("camera")) |
||||
|
setReminder(false) |
||||
|
}} |
||||
|
close={() => { |
||||
|
setReminder(false) |
||||
|
}} |
||||
|
/> */} |
||||
|
</div> |
||||
|
</> |
||||
|
); |
||||
|
}; |
||||
|
|
||||
function mapStateToProps (state) { |
function mapStateToProps (state) { |
||||
const { auth } = state; |
const { auth, global, members, equipmentWarehouseNvr } = state; |
||||
return { |
return { |
||||
user: auth.user, |
loading: equipmentWarehouseNvr.isRequesting && !equipmentWarehouseNvr.data, |
||||
}; |
user: auth.user, |
||||
|
actions: global.actions, |
||||
|
members: members.data, |
||||
|
equipmentWarehouseNvr: equipmentWarehouseNvr.data || {}, |
||||
|
}; |
||||
} |
} |
||||
|
|
||||
export default connect(mapStateToProps)(Carrierpigeon); |
export default connect(mapStateToProps)(Carrierpigeon); |
||||
|
@ -1,20 +1,550 @@ |
|||||
import React, { useEffect } from 'react'; |
import React, { useState, useEffect, useRef } from "react"; |
||||
import { connect } from 'react-redux'; |
import { connect } from "react-redux"; |
||||
import { Coming } from '$components' |
import moment from "moment"; |
||||
import '../style.less' |
import { Button, Form, Table, Pagination, Skeleton, Popconfirm, Popover, Tag, } from "@douyinfe/semi-ui"; |
||||
|
import { IconSort,IconCaretdown,IconCaretup } from '@douyinfe/semi-icons'; |
||||
|
import "../style.less"; |
||||
|
import {Setup} from "$components"; |
||||
|
|
||||
|
import ProgrammeModal from "../components/programmeModal"; |
||||
|
import NotesModal from "../components/notesModal"; |
||||
|
// import { skeletonScreen } from "../components/skeletonScreen"; |
||||
|
|
||||
|
export const accessType = { |
||||
|
"yingshi": "萤石云", |
||||
|
"nvr": "NVR", |
||||
|
"ipc": "IPC", |
||||
|
"cascade": "级联" |
||||
|
}; |
||||
|
|
||||
const Statuscode = (props) => { |
const Statuscode = (props) => { |
||||
|
const { history, dispatch, actions, user, loading, StatusList } = props; |
||||
|
const { offline } = actions; |
||||
|
const [setup, setSetup] = useState(false);//表格设置弹框 |
||||
|
const [programme, setProgramme] = useState(false);//方案弹框 |
||||
|
const [notes, setNotes] = useState(false);//释义弹框 |
||||
|
const [setupp, setSetupp] = useState([]); |
||||
|
const [query, setQuery] = useState({ limit: 10, page: 0 }); //页码信息 |
||||
|
const [search, setearch] = useState({}); //搜索条件 |
||||
|
const [rowId, setRowId] = useState(); //表格数据id |
||||
|
const api = useRef(); |
||||
|
const searchData = useRef(search) |
||||
|
const page = useRef(query.page); |
||||
|
const CODE = "code"; |
||||
|
const [nodesAll, setNodesAll] = useState(true);//是否批量 |
||||
|
const [mysorter, setMysorter] = useState(true);//排序 |
||||
|
const sorter = useRef(false);//排序 |
||||
|
const [resolve, setResolve] = useState([]);//解决方案 |
||||
|
const [tableNews, setTableNews] = useState([]);//表格当前行数据 |
||||
|
const tableList = [//表格属性 |
||||
|
{ |
||||
|
title:'状态码信息', |
||||
|
list:[ |
||||
|
{ name: "常规解决方案", value: "resolve" }, |
||||
|
{ name: "状态频率", value: "logCount" }, |
||||
|
] |
||||
|
}, |
||||
|
]; |
||||
|
useEffect(() => { |
||||
|
//初始化表格显示设置 |
||||
|
attribute(); |
||||
|
localStorage.getItem(CODE) == null |
||||
|
? localStorage.setItem( |
||||
|
CODE, |
||||
|
JSON.stringify(["resolve", "logCount"]) |
||||
|
) |
||||
|
: ""; |
||||
|
}, [sorter.current]); |
||||
|
|
||||
return ( |
useEffect(() => { |
||||
<Coming /> |
codegetStatus(); |
||||
) |
}, [query, search]); |
||||
} |
|
||||
|
const codegetStatus = () => { |
||||
|
searchData.current = { ...query, ...search } |
||||
|
dispatch(offline.getStatus(searchData.current)).then((res) => { |
||||
|
|
||||
|
}); |
||||
|
} |
||||
|
const columns = [ |
||||
|
{ |
||||
|
title: "状态码", |
||||
|
dataIndex: "status", |
||||
|
render: (_, record, index) => { |
||||
|
return record.status |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "平台", |
||||
|
dataIndex: "platform", |
||||
|
render: (_, r, index) => { |
||||
|
let platform=r.platform |
||||
|
return accessType[platform] |
||||
|
|
||||
|
}, |
||||
|
}, |
||||
|
|
||||
|
{ |
||||
|
title: "错误描述", |
||||
|
dataIndex: "describe", |
||||
|
render: (_, r, index) => { |
||||
|
return r.describe |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "释义", |
||||
|
dataIndex: "paraphrase", |
||||
|
render: (_, r, index) => { |
||||
|
return r.paraphrase |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "我的自定义释义", |
||||
|
dataIndex: "paraphraseCustom", |
||||
|
render: (_, r, index) => { |
||||
|
return r.paraphraseCustom |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title: "操作", |
||||
|
width: "20%", |
||||
|
dataIndex: "", |
||||
|
render: (_, row) => { |
||||
|
return ( |
||||
|
<div style={{ display: "flex" }}> |
||||
|
{row.forbidden ? ( |
||||
|
<Button |
||||
|
theme="borderless" |
||||
|
onClick={() => { |
||||
|
dispatch( |
||||
|
offline.putStatueBanned( |
||||
|
{ |
||||
|
statusId: row.id, |
||||
|
forbidden: !row.forbidden, |
||||
|
}, |
||||
|
row.forbidden |
||||
|
) |
||||
|
).then(() => { |
||||
|
codegetStatus(); |
||||
|
}); |
||||
|
}} |
||||
|
> |
||||
|
启用 |
||||
|
</Button> |
||||
|
) : ( |
||||
|
<Popconfirm |
||||
|
title="禁用后下级业务系统将无法获取该视频流的所有信息。" |
||||
|
arrowPointAtCenter={false} |
||||
|
showArrow={true} |
||||
|
position="topRight" |
||||
|
onConfirm={() => { |
||||
|
dispatch( |
||||
|
offline.putStatueBanned( |
||||
|
{ |
||||
|
statusId: row.id, |
||||
|
forbidden: !row.forbidden, |
||||
|
}, |
||||
|
row.forbidden |
||||
|
) |
||||
|
).then(() => { |
||||
|
codegetStatus(); |
||||
|
}); |
||||
|
}} |
||||
|
> |
||||
|
<Button theme="borderless">禁用</Button> |
||||
|
</Popconfirm> |
||||
|
)} |
||||
|
<Button |
||||
|
theme="borderless" |
||||
|
onClick={() => { |
||||
|
setNotes(true); |
||||
|
setNodesAll(false); |
||||
|
setTableNews(row); |
||||
|
setRowId(row.id); |
||||
|
}} |
||||
|
> |
||||
|
释义 |
||||
|
</Button> |
||||
|
<Button theme="borderless" |
||||
|
onClick={() => { |
||||
|
setProgramme(true); |
||||
|
setRowId(row.id); |
||||
|
setResolve(row.resolve); |
||||
|
}}> |
||||
|
方案 |
||||
|
</Button> |
||||
|
</div> |
||||
|
); |
||||
|
}, |
||||
|
}, |
||||
|
]; |
||||
|
function tosorter(){ |
||||
|
setMysorter(false) |
||||
|
if(sorter.current=="descend"){ |
||||
|
searchData.current = { ...query, ...search, orderDirection:'ASC',orderBy:'logCount'} |
||||
|
dispatch(offline.getStatus(searchData.current)).then((res) => { |
||||
|
sorter.current='ascend' |
||||
|
setMysorter('ascend') |
||||
|
}); |
||||
|
} |
||||
|
else if(sorter.current=="ascend"){ |
||||
|
searchData.current = { ...query, ...search} |
||||
|
dispatch(offline.getStatus(searchData.current)).then((res) => { |
||||
|
sorter.current='' |
||||
|
setMysorter('') |
||||
|
}); |
||||
|
} |
||||
|
else{ |
||||
|
searchData.current = { ...query, ...search, orderDirection:'DESC',orderBy:'logCount'} |
||||
|
dispatch(offline.getStatus(searchData.current)).then((res) => { |
||||
|
sorter.current='descend' |
||||
|
setMysorter('descend') |
||||
|
}); |
||||
|
} |
||||
|
} |
||||
|
//获取表格属性设置 |
||||
|
function attribute () { |
||||
|
const arr = localStorage.getItem(CODE) |
||||
|
? JSON.parse(localStorage.getItem(CODE)) |
||||
|
: []; |
||||
|
const column = [ |
||||
|
{ |
||||
|
title: "常规解决方案", |
||||
|
dataIndex: "resolve", |
||||
|
key:'resolve', |
||||
|
render: (_, r, index) => { |
||||
|
let myresolve='' |
||||
|
if(r.resolve.length>0){ |
||||
|
let myresolveList=[]; |
||||
|
for (let index = 0; index < r.resolve.length; index++) { |
||||
|
if(r.resolve[index]&&r.resolve[index].resolve){ |
||||
|
myresolveList.push(r.resolve[index].resolve) |
||||
|
} |
||||
|
} |
||||
|
myresolve=myresolveList.join(';'); |
||||
|
} |
||||
|
return myresolve |
||||
|
}, |
||||
|
}, |
||||
|
{ |
||||
|
title:(<span onClick={tosorter}> |
||||
|
状态频率(近30日) |
||||
|
{mysorter=='descend'?<IconCaretdown />:mysorter=='ascend'?<IconCaretup />:<IconSort />} |
||||
|
</span>), |
||||
|
dataIndex: "logCount", |
||||
|
key:'logCount', |
||||
|
render: (_, r, index) => { |
||||
|
return r.logCount |
||||
|
}, |
||||
|
}, |
||||
|
]; |
||||
|
let mycolumns=columns |
||||
|
for (let i = 0; i < arr.length; i++) { |
||||
|
let colum = column.filter((item) => { |
||||
|
return item.key === arr[i]; |
||||
|
}); |
||||
|
mycolumns.splice(i + 5, 0, colum[0]); |
||||
|
} |
||||
|
setSetupp(mycolumns); |
||||
|
} |
||||
|
//条件赛选样式 |
||||
|
const screen = { |
||||
|
width: 193, |
||||
|
marginRight: 20, |
||||
|
marginBottom: 16, |
||||
|
color: "rgba(0, 0, 0, 0.65)", |
||||
|
}; |
||||
|
|
||||
|
return ( |
||||
|
<> |
||||
|
<div> |
||||
|
<video |
||||
|
id="nvrBanner" |
||||
|
autoPlay |
||||
|
loop |
||||
|
muted |
||||
|
style={{ width: "100%", objectFit: "cover", height: 171 }} |
||||
|
src="/assets/video/nvr_banner.mp4" |
||||
|
type="video/mp4" |
||||
|
/> |
||||
|
<div style={{ position: "absolute", top: 12 }}> |
||||
|
<div |
||||
|
style={{ |
||||
|
fontSize: 22, |
||||
|
paddingTop: 15, |
||||
|
marginLeft: 21, |
||||
|
}} |
||||
|
> |
||||
|
状态码管理 |
||||
|
</div> |
||||
|
<div |
||||
|
style={{ |
||||
|
fontSize: 14, |
||||
|
paddingTop: 18, |
||||
|
marginLeft: 20, |
||||
|
}} |
||||
|
> |
||||
|
系统支持状态码显示内容的释义修改,当设备异常时,会为您显示自定义释义内容。 |
||||
|
</div> |
||||
|
</div> |
||||
|
</div> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: "100%", |
||||
|
background: "#FFFFFF", |
||||
|
borderRadius: 3, |
||||
|
padding: "8px 20px", |
||||
|
marginTop: 20, |
||||
|
}} |
||||
|
> |
||||
|
<div |
||||
|
style={{ |
||||
|
height: 22, |
||||
|
fontSize: 16, |
||||
|
fontFamily: "PingFangSC-Medium, PingFang SC", |
||||
|
fontWeight: "bold", |
||||
|
color: " rgba(0, 0, 0, 0.85)", |
||||
|
lineHeight: "22px", |
||||
|
marginBottom: 16, |
||||
|
}} |
||||
|
> |
||||
|
筛选条件 |
||||
|
</div> |
||||
|
<div style={{ display: "flex" }}> |
||||
|
<Form |
||||
|
onSubmit={(values) => console.log(values)} |
||||
|
// onValueChange={values=>console.log(values)} |
||||
|
getFormApi={(formApi) => (api.current = formApi)} |
||||
|
layout="horizontal" |
||||
|
style={{ position: "relative", width: "100%", flex: 1 }} |
||||
|
> |
||||
|
<Form.Input |
||||
|
label="释义搜索:" |
||||
|
field="keyword" |
||||
|
maxLength="36" |
||||
|
placeholder="请输入错误描述、释义或自定义释义" |
||||
|
labelPosition="left" |
||||
|
style={screen} |
||||
|
/> |
||||
|
<Form.Select |
||||
|
label="启用状态:" |
||||
|
labelPosition="left" |
||||
|
style={screen} |
||||
|
field="forbidden" |
||||
|
placeholder="全部" |
||||
|
showClear |
||||
|
> |
||||
|
<Form.Select.Option value="">全部</Form.Select.Option> |
||||
|
<Form.Select.Option value="false">启用</Form.Select.Option> |
||||
|
<Form.Select.Option value="true">禁用</Form.Select.Option> |
||||
|
</Form.Select> |
||||
|
<Form.Select |
||||
|
label="状态查询:" |
||||
|
labelPosition="left" |
||||
|
field="paraphraseCustom" |
||||
|
style={screen} |
||||
|
placeholder="全部" |
||||
|
showClear |
||||
|
> |
||||
|
<Form.Select.Option value="">全部</Form.Select.Option> |
||||
|
<Form.Select.Option value="false">已设置</Form.Select.Option> |
||||
|
<Form.Select.Option value="true">未设置</Form.Select.Option> |
||||
|
</Form.Select> |
||||
|
</Form> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: 150, |
||||
|
display: "flex", |
||||
|
justifyContent: "flex-end", |
||||
|
alignItems: "flex-end", |
||||
|
}} |
||||
|
> |
||||
|
<Button |
||||
|
theme="solid" |
||||
|
type="primary" |
||||
|
style={{ |
||||
|
width: 65, |
||||
|
height: 30, |
||||
|
borderRadius: 3, |
||||
|
marginBottom: 20, |
||||
|
marginRight: 20, |
||||
|
}} |
||||
|
onClick={() => { |
||||
|
api.current.validate().then((v) => { |
||||
|
setearch(v); |
||||
|
setQuery({ limit: 10, page: 0 }) |
||||
|
}); |
||||
|
}} |
||||
|
> |
||||
|
搜索 |
||||
|
</Button> |
||||
|
<Button |
||||
|
theme="light" |
||||
|
type="primary" |
||||
|
style={{ |
||||
|
width: 65, |
||||
|
height: 30, |
||||
|
backGround: "#FFFFFF", |
||||
|
borderRadius: 3, |
||||
|
border: "1px solid #D9D9D9", |
||||
|
marginBottom: 20, |
||||
|
}} |
||||
|
onClick={() => { |
||||
|
api.current.reset(); |
||||
|
setearch({}); |
||||
|
setQuery({ limit: 10, page: 0 }) |
||||
|
}} |
||||
|
> |
||||
|
重置 |
||||
|
</Button> |
||||
|
</div> |
||||
|
</div> |
||||
|
</div> |
||||
|
<div style={{ background: "#FFFFFF", marginTop: 5 }}> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: "100%", |
||||
|
display: "flex", |
||||
|
justifyContent: "space-between", |
||||
|
padding: "13px 20px", |
||||
|
}} |
||||
|
> |
||||
|
<div |
||||
|
style={{ |
||||
|
width: 84, |
||||
|
height: 22, |
||||
|
fontSize: 16, |
||||
|
fontfAmily: "PingFangSC-Medium, PingFang SC", |
||||
|
fontWeight: "bold", |
||||
|
color: "rgba(0, 0, 0, 0.85)", |
||||
|
lineHeight: "22px", |
||||
|
}} |
||||
|
> |
||||
|
状态码详情 |
||||
|
</div> |
||||
|
<div> |
||||
|
<Button |
||||
|
style={{ |
||||
|
width: 32, |
||||
|
height: 32, |
||||
|
background: "#D9D9D9", |
||||
|
borderadius: 3, |
||||
|
marginRight: 20, |
||||
|
}} |
||||
|
type="primary" |
||||
|
key="primary" |
||||
|
onClick={() => { |
||||
|
setSetup(true); |
||||
|
}} |
||||
|
> |
||||
|
<img |
||||
|
src="/assets/images/background/setup.png" |
||||
|
alt="设置" |
||||
|
style={{ width: 18, height: 18 }} |
||||
|
/> |
||||
|
</Button> |
||||
|
<Button |
||||
|
theme="solid" |
||||
|
type="primary" |
||||
|
style={{ |
||||
|
width: 65, |
||||
|
height: 32, |
||||
|
borderRadius: 3, |
||||
|
}} |
||||
|
onClick={() => { |
||||
|
setNotes(true); |
||||
|
setNodesAll(true); |
||||
|
setTableNews([]); |
||||
|
}} |
||||
|
> |
||||
|
批量设置 |
||||
|
</Button> |
||||
|
</div> |
||||
|
</div> |
||||
|
<Skeleton |
||||
|
loading={loading} |
||||
|
// placeholder={skeletonScreen()} |
||||
|
active={true} |
||||
|
> |
||||
|
<Table |
||||
|
columns={setupp.filter((s) => s)} |
||||
|
dataSource={StatusList.rows} |
||||
|
bordered={false} |
||||
|
empty="暂无数据" |
||||
|
style={{ |
||||
|
padding: "0px 20px", |
||||
|
}} |
||||
|
pagination={false} |
||||
|
/> |
||||
|
</Skeleton> |
||||
|
|
||||
|
<div |
||||
|
style={{ |
||||
|
display: "flex", |
||||
|
justifyContent: "flex-end", |
||||
|
padding: "20px 20px", |
||||
|
}} |
||||
|
> |
||||
|
<span style={{ lineHeight: "30px" }}> |
||||
|
共{StatusList.count}个状态码 |
||||
|
</span> |
||||
|
<Pagination |
||||
|
total={StatusList.count} |
||||
|
showSizeChanger |
||||
|
currentPage={query.page + 1} |
||||
|
pageSizeOpts={[10, 20, 30, 40]} |
||||
|
onChange={(currentPage, pageSize) => { |
||||
|
setQuery({ limit: pageSize, page: currentPage - 1 }); |
||||
|
page.current = currentPage - 1 |
||||
|
}} |
||||
|
/> |
||||
|
</div> |
||||
|
|
||||
|
{setup ? ( |
||||
|
<Setup |
||||
|
tableType={CODE} |
||||
|
tableList={tableList} |
||||
|
close={() => { |
||||
|
setSetup(false); |
||||
|
attribute(); |
||||
|
}} |
||||
|
/> |
||||
|
) : ( |
||||
|
"" |
||||
|
)} |
||||
|
{programme&&<ProgrammeModal |
||||
|
rowId={rowId} |
||||
|
resolve={resolve} |
||||
|
close={() => { |
||||
|
setProgramme(false); |
||||
|
setRowId(); |
||||
|
codegetStatus(); |
||||
|
}} |
||||
|
/>} |
||||
|
{notes&&<NotesModal |
||||
|
rowId={rowId} |
||||
|
nodesAll={nodesAll} |
||||
|
tableNews={tableNews} |
||||
|
close={() => { |
||||
|
setNotes(false); |
||||
|
setRowId(); |
||||
|
codegetStatus(); |
||||
|
}} |
||||
|
/>} |
||||
|
</div> |
||||
|
</> |
||||
|
); |
||||
|
}; |
||||
|
|
||||
function mapStateToProps (state) { |
function mapStateToProps (state) { |
||||
const { auth } = state; |
const { auth, global, members, StatusList } = state; |
||||
return { |
return { |
||||
user: auth.user, |
loading: StatusList.isRequesting && !StatusList.data, |
||||
}; |
user: auth.user, |
||||
|
actions: global.actions, |
||||
|
members: members.data, |
||||
|
StatusList: StatusList.data || {}, |
||||
|
}; |
||||
} |
} |
||||
|
|
||||
export default connect(mapStateToProps)(Statuscode); |
export default connect(mapStateToProps)(Statuscode); |
||||
|
Loading…
Reference in new issue