1. OPC UA 服务器基础搭建
任务目标
在网关设备(以 Ubuntu 22.04 x64 为例)上安装并配置一个 OPC UA 服务器,使其能够启动并接受客户端连接。本案例使用开源实现 open62541,通过编译内置示例服务器并修改监听端口,完成最小可验证的服务器搭建。
环境与依赖
- 操作系统:Ubuntu 22.04 LTS(x86_64)
- 编译工具:
gcc、cmake(≥3.10)、git - 依赖库:无需额外第三方库,open62541 编译时自动处理
sudo apt update
sudo apt install -y gcc cmake git
实现步骤
open62541 提供单文件发行版(open62541.c + open62541.h),可直接编译运行,无需完整源码树。以下步骤下载单文件版本并编写服务器启动代码。
# 下载 open62541 单文件版本(v1.3)
wget https://github.com/open62541/open62541/releases/download/v1.3.10/open62541-linux64.tar.gz
tar -xzf open62541-linux64.tar.gz
# 解压后得到 open62541.h 和 open62541.c
服务器代码
创建 server.c,实现一个监听端口可配置的 OPC UA 服务器。服务器启动后创建默认对象节点,并持续运行直到收到中断信号。
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <open62541.h>
static UA_Boolean running = true;
static void stopHandler(int sig) {
UA_LOG_INFO(UA_Log_Stdout, UA_LOGCATEGORY_USERLAND, "收到信号 %d,正在停止服务器...", sig);
running = false;
}
int main(int argc, char** argv) {
uint16_t port = 4840; // 默认端口
if (argc > 1) {
port = (uint16_t)atoi(argv[1]);
if (port == 0) {
fprintf(stderr, "无效端口号: %s\n", argv[1]);
return 1;
}
}
signal(SIGINT, stopHandler);
signal(SIGTERM, stopHandler);
UA_Server *server = UA_Server_new();
UA_ServerConfig *config = UA_Server_getConfig(server);
UA_ServerConfig_setMinimal(config, port, NULL);
UA_StatusCode retval = UA_Server_run(server, &running);
if (retval != UA_STATUSCODE_GOOD) {
UA_LOG_ERROR(UA_Log_Stdout, UA_LOGCATEGORY_USERLAND,
"服务器运行失败,错误码: 0x%08X", retval);
UA_Server_delete(server);
return 1;
}
UA_Server_delete(server);
UA_LOG_INFO(UA_Log_Stdout, UA_LOGCATEGORY_USERLAND, "服务器已正常退出");
return 0;
}
编译与运行
# 编译(与 open62541.c 一起编译)
gcc -std=c99 -O2 server.c open62541.c -o ua_server -lm
# 启动服务器(默认端口 4840)
./ua_server
# 指定端口启动(例如 16664)
./ua_server 16664
验证方法
服务器启动后,使用 OPC UA 客户端工具连接验证。推荐使用 UaExpert(图形化)或 opcua-client 命令行工具。以下为命令行验证方式:
# 安装 python 客户端库(用于快速验证)
pip install opcua
# 连接测试脚本(保存为 test_client.py)
from opcua import Client
client = Client("opc.tcp://127.0.0.1:4840")
try:
client.connect()
print("连接成功,服务器名称:", client.get_server_node().get_child("0:Server").get_value())
finally:
client.disconnect()
python3 test_client.py
通过条件:服务器控制台输出监听启动日志,客户端脚本打印 连接成功 且无异常抛出。若使用 UaExpert,在地址栏输入 opc.tcp://127.0.0.1:4840,双击服务器节点可浏览到 Objects 文件夹即表示连接正常。
常见问题
- 端口被占用:启动时提示
bind: Address already in use,更换端口或使用ss -tlnp | grep 4840查找占用进程。 - 防火墙拦截:若客户端从其他机器连接,需放行对应端口:
sudo ufw allow 4840/tcp。 - 编译警告:忽略
deprecated相关警告不影响运行,如需消除可添加-Wno-deprecated-declarations编译选项。