HistoryReadEvents (C)
如果服务端记录事件历史, 客户端可以按时间区间拉历史事件 (报警 / 条件).
配套
- 实时事件订阅请用 事件订阅.
- 历史变量数据请用 ReadRaw / ReadProcessed.
API
#include <darra_opcua/darra_opcua_history.h>
#include <darra_opcua/darra_opcua_event.h>
DARRA_OPCUA_API DarraUa_Status DARRA_OPCUA_CALL DarraUa_Session_HistoryReadEvents(
DarraUa_SessionHandle h,
const char* node_id_str, /* 通常 "i=2253" Server */
DarraUa_DateTime start_time,
DarraUa_DateTime end_time,
uint32_t num_values_per_node,
DarraUa_Event*** out_events,
uint32_t* out_count);
DarraUa_Event* 结构同 事件订阅.
内置 SelectClauses
固定 4 个标准字段 (与 Subscription Event 一致):
- Severity (UInt16)
- Message (LocalizedText)
- SourceName (String)
- Time (DateTime)
whereClause 留空 = 全部事件.
释放
DarraUa_EventArray_Delete(events, count);
_EventArray_Delete 释放数组本身、每个 Event 元素以及 Event 内部 strdup 出来的字符串字段.
用法
#include <darra_opcua/darra_opcua_history.h>
#include <darra_opcua/darra_opcua_event.h>
DarraUa_DateTime end = utc_now_ft();
DarraUa_DateTime start = end - 864000000000LL; /* 24 小时 */
DarraUa_Event** events = NULL;
uint32_t count = 0;
DarraUa_Status st = DarraUa_Session_HistoryReadEvents(
h, "i=2253",
start, end,
/*num*/ 0, /* 不限 */
&events, &count);
if (DARRA_UA_STATUS_IS_GOOD(st)) {
for (uint32_t i = 0; i < count; ++i) {
const DarraUa_Event* ev = events[i];
printf("[sev=%u] src=\"%s\" time=%lld msg=\"%s\"\n",
(unsigned)ev->severity,
ev->source_name ? ev->source_name : "",
(long long)ev->time,
ev->message ? ev->message : "");
}
}
DarraUa_EventArray_Delete(events, count);
服务端要求
- 必须支持 HistoryRead Events (服务端 ServerCapabilities 标志位)
- 事件源节点必须有 EventNotifier Attribute (12) bit 1 (HistoryRead) 置位
与实时事件订阅的关系
| API | 拿什么 |
|---|---|
DarraUa_Subscription_AddEventItem(...) | 实时事件 (订阅期间发生的) |
DarraUa_Session_HistoryReadEvents(...) | 历史事件 (服务端归档的) |
通常组合用: 启动时 ReadEvents 拉过去 24 小时, 然后订阅接管实时.