完成自动类型检查和查询功能

This commit is contained in:
Yu Sun
2022-07-12 22:36:14 +08:00
parent 5fdfc04349
commit 68f86c94b7
4 changed files with 113 additions and 31 deletions

View File

@@ -13,6 +13,7 @@ init_db($options['server_name'], $options['user'], $options['password']);
$worker = new Worker('http://0.0.0.0:8888'); $worker = new Worker('http://0.0.0.0:8888');
$worker -> name = 'CaptureWorker'; $worker -> name = 'CaptureWorker';
$worker -> count = 200;
$worker -> onWorkerStart = function(Worker $worker) { $worker -> onWorkerStart = function(Worker $worker) {
global $options, $dbconn; global $options, $dbconn;
@@ -27,6 +28,9 @@ $worker -> onMessage = function(TcpConnection $connection, Request $request) {
// 先预处理POST内容 // 先预处理POST内容
if ($request->header('content-type') === 'application/json') { if ($request->header('content-type') === 'application/json') {
$post = $request -> post(); $post = $request -> post();
if (isset($post['action'])) {
$post = json_decode(json_encode($post, JSON_PRESERVE_ZERO_FRACTION));
}
} else { } else {
$body = $request -> rawBody(); $body = $request -> rawBody();
if ($body === "") { if ($body === "") {
@@ -49,7 +53,7 @@ $worker -> onMessage = function(TcpConnection $connection, Request $request) {
} }
} }
if (is_array($post)) { if (isset($post) and is_array($post)) {
if (count($post) !== 0) { if (count($post) !== 0) {
// Axios发送的POST是array // Axios发送的POST是array
if (is_array($post) and isset($post['action'])) { if (is_array($post) and isset($post['action'])) {
@@ -90,8 +94,7 @@ $worker -> onMessage = function(TcpConnection $connection, Request $request) {
'errmsg' => '未登记过的工序单元!' 'errmsg' => '未登记过的工序单元!'
))); )));
$connection -> send($response); $connection -> send($response);
} } else if ($data_capture -> check_res === 'MISMATCH_TYPE') {
if ($data_capture -> check_res === 'MISMATCH_TYPE') {
$response = new Response(200, [ $response = new Response(200, [
'Content-Type' => 'application/json;charset=utf-8', 'Content-Type' => 'application/json;charset=utf-8',
], json_encode(array( ], json_encode(array(
@@ -104,13 +107,13 @@ $worker -> onMessage = function(TcpConnection $connection, Request $request) {
$res = $data_capture -> set_node_data(); $res = $data_capture -> set_node_data();
if ($res === true) { if ($res === true) {
$connection -> send(json_encode(array( $connection -> send(json_encode(array(
'action' => 'result_set_data', 'action' => 'result_set_node_data',
'errcode' => 0, 'errcode' => 0,
'errmsg' => '' 'errmsg' => ''
))); )));
} else { } else {
$connection -> send(json_encode(array( $connection -> send(json_encode(array(
'action' => 'result_set_data', 'action' => 'result_set_node_data',
'errcode' => 4002, 'errcode' => 4002,
'errmsg' => 'ROLLBACKed: Bad data received (structure and/or values)' 'errmsg' => 'ROLLBACKed: Bad data received (structure and/or values)'
))); )));
@@ -187,6 +190,11 @@ $worker -> onMessage = function(TcpConnection $connection, Request $request) {
'code' => 1, 'code' => 1,
'msg' => '服务器内部逻辑错误,请联系开发者!' 'msg' => '服务器内部逻辑错误,请联系开发者!'
))); )));
else if ($data === "TOO_MANY")
$connection -> send(json_encode(array(
'code' => 1,
'msg' => '结果太多(超过二百万条),请收紧查询条件!'
)));
else else
$connection -> send(json_encode(array( $connection -> send(json_encode(array(
'code' => 0, 'code' => 0,

View File

@@ -32,7 +32,9 @@ class EDataCapture {
$code_type[$v['code']] = $v['type']; $code_type[$v['code']] = $v['type'];
}); });
foreach ($this -> post -> param -> data as $row) { foreach ($this -> post -> param -> data as &$row) {
if (($code_type[$row -> code]) === 'float' and is_int($row -> value))
$row -> value = (float) number_format((float) $row -> value, 1, '.', '');
$check_func = 'is_' . $code_type[$row -> code]; $check_func = 'is_' . $code_type[$row -> code];
if (!$check_func($row -> value)) { if (!$check_func($row -> value)) {
$this -> check_res = 'MISMATCH_TYPE'; $this -> check_res = 'MISMATCH_TYPE';
@@ -61,11 +63,11 @@ class EDataCapture {
); );
foreach ($chunk as $row) { foreach ($chunk as $row) {
$sql_values[] = sprintf( $sql_values[] = sprintf(
"('%s', '%s', %s, %s)", "('%s', '%s', '%s', '%s')",
$code, $code,
$row['value'], $row['value'] === false ? 'f' : $row['value'],
$row['device_code'] ?? 'DEFAULT', $row['device_code'] ?? NULL,
$row['batch'] ?? 'DEFAULT' $row['batch'] ?? NULL
); );
} }
$res[] = pg_query($this -> dbconn, $sql_head . implode(',', $sql_values)); $res[] = pg_query($this -> dbconn, $sql_head . implode(',', $sql_values));
@@ -85,28 +87,40 @@ class EDataCapture {
} }
function get_node_data() { function get_node_data() {
$name_type = pg_fetch_assoc(pg_query($this -> dbconn, sprintf( // 先把code和name的对应关系拿到快于OUTER JOIN
"SELECT name, type
FROM hf_mes_scada_data_capture_node_configure
WHERE working_subclass = '%s'
AND code = '%s'",
$this -> get['working_subclass'],
$this -> get['code']
)));
$res = pg_fetch_all(pg_query($this -> dbconn, sprintf( $res = pg_fetch_all(pg_query($this -> dbconn, sprintf(
"SELECT id, v_%s AS value, device_code, batch, capture_time "SELECT code, name
FROM hf_mes_scada_data_capture_node_data_%s FROM hf_mes_scada_data_capture_node_configure
WHERE code = '%s'", WHERE working_subclass = '%s'",
$name_type['type'], $this -> get['working_subclass']
$this -> get['working_subclass'],
$this -> get['code']
))); )));
array_walk($res, function(&$v, $k) use ($name_type) { $code_name = [];
$v['name'] = $name_type['name']; array_walk($res, function(&$v, $k) use (&$code_name) {
$code_name[$v['code']] = $v['name'];
}); });
$sql_cmd = sprintf(
"SELECT id, code, COALESCE(v_string, v_int::text, v_float::text, v_bool::text) AS value, device_code, batch, capture_time
FROM hf_mes_scada_data_capture_node_data_%s
WHERE capture_time >= '%s' AND capture_time <= '%s'",
$this -> get['working_subclass'],
date("Y-m-d H:i:s", $this -> get['start_time'] / 1000),
date("Y-m-d H:i:s", $this -> get['end_time'] / 1000)
);
if (isset($this -> get['code']))
$sql_cmd .= sprintf(" AND code = '%s'", $this -> get['code']);
$res = pg_fetch_all(pg_query($this -> dbconn, $sql_cmd));
if (count($res) > 2e6)
return "TOO_MANY";
array_walk($res, function(&$v, $k) use ($code_name) {
$v['name'] = $code_name[$v['code']];
});
return $res; return $res;
} }
} }

View File

@@ -26,7 +26,19 @@ export default ({ service, request, serviceForMock, requestForMock, mock, faker,
return request({ url: '?query=codes&working_subclass=' + workingSubclass }) return request({ url: '?query=codes&working_subclass=' + workingSubclass })
}, },
QUERY_NODE_DATA (workingSubclass, code) { QUERY_NODE_DATA ({
return request({ url: '?query=node_data&working_subclass=' + workingSubclass + '&code=' + code }) workingSubclass,
startTime,
endTime,
code
} = {}) {
let url = '?query=node_data&working_subclass=' + workingSubclass + '&start_time=' + startTime + '&end_time=' + endTime
if (code) {
url += `&code=${code}`
}
return request({
url: url,
timeout: 20000
})
} }
}) })

View File

@@ -14,6 +14,19 @@
:value="workingSubclass"> :value="workingSubclass">
</el-option> </el-option>
</el-select> </el-select>
</el-form-item>
<el-form-item label="采集时间">
<el-date-picker
v-model="formInline.time"
type="datetimerange"
:clearable="false"
:picker-options="pickerOptions"
range-separator=""
start-placeholder="开始日期"
end-placeholder="结束日期"
value-format="timestamp"
align="right">
</el-date-picker>
</el-form-item> </el-form-item>
<el-form-item label="节点编码"> <el-form-item label="节点编码">
<el-select <el-select
@@ -73,16 +86,46 @@
</template> </template>
<script> <script>
const now = new Date()
export default { export default {
data () { data () {
return { return {
formInline: { formInline: {
workingSubclass: '', workingSubclass: '',
time: [now - 3600 * 1000 * 24 * 7, +now],
code: '' code: ''
}, },
workingSubclasses: [], workingSubclasses: [],
codes: [], codes: [],
data: [] data: [],
pickerOptions: {
shortcuts: [{
text: '最近一周',
onClick (picker) {
const end = new Date()
const start = new Date()
start.setTime(start.getTime() - 3600 * 1000 * 24 * 7)
picker.$emit('pick', [start, end])
}
}, {
text: '最近一个月',
onClick (picker) {
const end = new Date()
const start = new Date()
start.setTime(start.getTime() - 3600 * 1000 * 24 * 30)
picker.$emit('pick', [start, end])
}
}, {
text: '最近三个月',
onClick (picker) {
const end = new Date()
const start = new Date()
start.setTime(start.getTime() - 3600 * 1000 * 24 * 90)
picker.$emit('pick', [start, end])
}
}]
}
} }
}, },
methods: { methods: {
@@ -102,7 +145,12 @@ export default {
}, },
async getData () { async getData () {
try { try {
this.data = await this.$api.QUERY_NODE_DATA(this.formInline.workingSubclass, this.formInline.code) this.data = await this.$api.QUERY_NODE_DATA({
workingSubclass: this.formInline.workingSubclass,
startTime: this.formInline.time[0],
endTime: this.formInline.time[1],
code: this.formInline.code
})
} catch (e) { } catch (e) {
console.log(e) console.log(e)
} }