一、概述
本文主要以简单的例子展示NodeJS与CODESYS的PLC进行OPCUA通信。NodeJS作为OPC UA Client, CODESYS的PLC作为 OPC UA Server。NodeJS的代码只是node-opcua的基本Client代码。
本文主要是介绍CODESYS的PLC自带OPCUA Server的配置情况。不涉及 CODESYS付费的OPCUA库的功能。
二、NodeJS代码
var opcua = require('node-opcua');
var async = require("async");
var connectionOption = {};
connectionOption.securityPolicy = opcua.SecurityPolicy.Basic256Sha256;
connectionOption.securityMode = opcua.MessageSecurityMode.SignAndEncrypt;
connectionOption.keepSessionAlive = true;
connectionOption.requestedSessionTimeout = 1000;
connectionOption.endpointMustExist = false;
async function main() {
//a)创建OPC UA Client并连接到OPC UA Server
try {
var url = "opc.tcp://192.168.1.3:4840 None";
client = opcua.OPCUAClient.create(connectionOption);
await client.connect(url);
} catch (err) {
console.log(err);
return;
}
if (!client) {
console.log("连接失败!");
return;
}
//b)创建会话
try {
var userIdentity = {};
// 匿名登录
userIdentity.type = opcua.UserTokenType.Anonymous;
//采用用户密码
//userIdentity.type = opcua.UserTokenType.UserName;
//userIdentity.userName = "XXXX";
//userIdentity.password = "XXXX";
session = await client.createSession(userIdentity);
if (!session) {
console.log("创建会话失败!");
return;
}
console.log("创建会话成功!");
} catch (err) {
console.log(err);
return;
}
//c)获取节点信息
try
{
await session.browse("RootFolder", function(err, browse_result) {
if (!err) {
browse_result.references.forEach(function(reference) {
console.log("RootFolder:", reference.toString());
});
}
});
}
catch (err) {
console.log(err);
return;
}
//c)读取节点值
var nodeIdS1 = 'ns=4;s=|var|Shenzen Leadshine-SM-x86_64-Linux.Application.PLC_PRG.var1'; //节点Id
var nodeIdS2 = 'ns=4;s=|var|Shenzen Leadshine-SM-x86_64-Linux.Application.PLC_PRG.var2'; //节点Id
console.log(' 尝试读取');
try {
var nodesToRead = [
{
nodeId: nodeIdS1,
attributeId: opcua.AttributeIds.Value
},
{
nodeId: nodeIdS2,
attributeId: opcua.AttributeIds.Value
}
];
var nodesValue;
await session.read(nodesToRead, function (err, dataValue) {
if (!err) {
let count,i,obj;
count = dataValue.length;
console.log("nodes count=",count);
for(i=0;i<count;i++)
{
obj = dataValue[i].value;
console.log("value = "+obj.value);
}
}
if (err) {
console.log(' 读错误: ' + err);
}
});
} catch (err) {
console.log(err);
return;
}
console.log(' 读取完毕');
console.log(' 尝试写 ');
//d)写数据
try {
var nodesToWrite = [
{
nodeId: nodeIdS1,
attributeId: opcua.AttributeIds.Value,
value: {
value: {
dataType: opcua.DataType.Int16,
value: 100
}
}
},
{
nodeId: nodeIdS2,
attributeId: opcua.AttributeIds.Value,
value: {
value: {
dataType: opcua.DataType.Int16,
value: 0
}
}
}
];
session.write(nodesToWrite, function (err, statusCodes) {
if (err) {
console.log(' 写错误: ' + err);
}
});
} catch (err) {
console.log(err);
return;
}
console.log(' 写数据成功!');
}
main();
三、CODESYS的配置
CODESYS IDE的版本是 V3.5 SP19。
步骤1
创建OPCUA server的证书。为了日后与Client进行交换证书。创建Server证书时,请注意Server证书的有效时间长度,NodeJS OPC UA Client自动创建的自签名证书的时间长度,与Server证书的有效时间长度是一致的。
步骤2
用终端启动NodeJS的opcua client代码,node-opcua将会自动生成自签名的Client的证书并且提交至目标server(CODESYS的plc)。
NodeJS第一次连接Server由于证书未受信任,会被Server拒绝。
刷新CODESYS的Device的Quarantined Certificates,会发现node-opcua提交的client证书。然后将该证书拖至Trusted Certificates中,即可完成配置为信任证书。
NodeJS再次连接Server,即可完成连接。