node-red-contrib-iiot-opcua
Version:
An Industrial IoT OPC UA toolbox contribution package for Node-RED based on node-opcua.
160 lines (157 loc) • 6.74 kB
JavaScript
/*
The BSD 3-Clause License
Copyright 2022 - DATATRONiQ GmbH (https://datatroniq.com)
Copyright (c) 2018-2022 Klaus Landsdorf (http://node-red.plus/)
All rights reserved.
node-red-contrib-iiot-opcua
*/
'use strict';
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const opcua_iiot_core_method_1 = __importDefault(require("./core/opcua-iiot-core-method"));
const opcua_iiot_core_1 = require("./core/opcua-iiot-core");
/**
* OPC UA node representation for Node-RED OPC UA IIoT method call.
*
* @param RED
*/
module.exports = (RED) => {
// SOURCE-MAP-REQUIRED
function OPCUAIIoTMethodCaller(config) {
RED.nodes.createNode(this, config);
this.objectId = config.objectId;
this.methodId = config.methodId;
this.methodType = config.methodType;
this.value = config.value;
this.justValue = config.justValue;
this.name = config.name;
this.showStatusActivities = config.showStatusActivities;
this.showErrors = config.showErrors;
this.inputArguments = config.inputArguments;
this.connector = RED.nodes.getNode(config.connector);
let self = this;
self.iiot = (0, opcua_iiot_core_1.initCoreNode)();
const handleMethodError = (err, msg) => {
opcua_iiot_core_method_1.default.internalDebugLog(err);
if (self.showErrors) {
this.error(err, msg);
}
if ((0, opcua_iiot_core_1.isSessionBad)(err)) {
this.emit('opcua_client_not_ready');
}
};
const handleMethodWarn = (message) => {
if (self.showErrors) {
this.warn(message);
}
opcua_iiot_core_method_1.default.internalDebugLog(message);
};
const callMethodOnSession = (session, msg) => {
if ((0, opcua_iiot_core_1.checkSessionNotValid)(session, 'MethodCaller')) {
return;
}
if (msg.payload.methodId && msg.payload.inputArguments) {
opcua_iiot_core_method_1.default.getArgumentDefinition(self.connector.iiot.opcuaSession, msg).then(function (results) {
opcua_iiot_core_method_1.default.detailDebugLog('Call Argument Definition Results: ' + JSON.stringify(results));
callMethod(msg, results);
}).catch((err) => {
(0, opcua_iiot_core_1.isInitializedIIoTNode)(self) ? handleMethodError(err, msg) : opcua_iiot_core_method_1.default.internalDebugLog(err.message);
});
}
else {
opcua_iiot_core_method_1.default.internalDebugLog(new Error('No Method Id And/Or Parameters'));
}
};
const getDataValue = (message, result, definitionResults) => {
if (self.justValue) {
if (message.payload.inputArguments) {
delete message.payload['inputArguments'];
}
return null;
}
else {
return {
result,
definition: definitionResults
};
}
};
const callMethod = (msg, definitionResults) => {
opcua_iiot_core_method_1.default.callMethods(self.connector.iiot.opcuaSession, msg).then((data) => {
opcua_iiot_core_method_1.default.detailDebugLog('Methods Call Results: ' + JSON.stringify(data));
let result = null;
let outputArguments = [];
let message = Object.assign({}, data.msg);
message.payload.nodetype = 'method';
message.payload.methodType = data.msg.payload.methodType;
for (result of data.results) {
outputArguments.push({ statusCode: result.statusCode, outputArguments: result.outputArguments });
}
message.payload.results = data.results;
message.payload.definition = definitionResults;
message.payload.value = getDataValue(message, data.results, definitionResults) || outputArguments;
// TODO: we have to check this again what value is to be ...
/* ?.map((item: TodoTypeAny) => {
if (item.statusCode) {
return {
...item,
statusCode: {
value: item.statusCode._value,
description: item.statusCode._description,
name: item.statusCode._name,
}
}
}
return item
})*/
message.payload.outputArguments = outputArguments;
this.send(message);
}).catch((err) => {
opcua_iiot_core_method_1.default.internalDebugLog(err);
if (self.showErrors) {
this.error(err, msg);
}
});
};
const errorHandler = (err, msg) => {
this.error(err, msg);
};
const emitHandler = (msg) => {
this.emit(msg);
};
const statusHandler = (status) => {
this.status(status);
};
this.on('input', function (msg) {
if (!(0, opcua_iiot_core_1.checkConnectorState)(self, msg, 'MethodCaller', errorHandler, emitHandler, statusHandler)) {
return;
}
const message = opcua_iiot_core_method_1.default.buildCallMessage(self, msg);
if (opcua_iiot_core_method_1.default.invalidMessage(self, message, handleMethodWarn)) {
return;
}
callMethodOnSession(self.connector.iiot.opcuaSession, message);
});
const onAlias = (event, callback) => {
// @ts-ignore
this.on(event, callback);
};
(0, opcua_iiot_core_1.registerToConnector)(self, statusHandler, onAlias, errorHandler);
this.on('close', (done) => {
(0, opcua_iiot_core_1.deregisterToConnector)(self, () => {
(0, opcua_iiot_core_1.resetIiotNode)(self);
done();
});
});
if (process.env.TEST === "true")
self.functions = {
handleMethodError,
handleMethodWarn,
callMethodOnSession
};
}
RED.nodes.registerType('OPCUA-IIoT-Method-Caller', OPCUAIIoTMethodCaller);
};
//# sourceMappingURL=opcua-iiot-method-caller.js.map