@tier0/opcua-client 0.1.0 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/BENCHMARK.md +53 -2
- package/README.md +180 -14
- package/THIRD_PARTY_NOTICES.md +20 -0
- package/binding.gyp +1 -1
- package/lib/client.js +48 -7
- package/lib/connection-registry.js +68 -0
- package/lib/native.js +25 -10
- package/lib/points.js +187 -21
- package/lib/prebuild.js +42 -0
- package/lib/security-file-store.js +119 -0
- package/lib/security.js +96 -0
- package/node_modules/node-addon-api/LICENSE.md +9 -0
- package/node_modules/node-addon-api/README.md +95 -0
- package/node_modules/node-addon-api/common.gypi +21 -0
- package/node_modules/node-addon-api/except.gypi +25 -0
- package/node_modules/node-addon-api/index.js +14 -0
- package/node_modules/node-addon-api/napi-inl.deprecated.h +186 -0
- package/node_modules/node-addon-api/napi-inl.h +7244 -0
- package/node_modules/node-addon-api/napi.h +3420 -0
- package/node_modules/node-addon-api/node_addon_api.gyp +42 -0
- package/node_modules/node-addon-api/node_api.gyp +9 -0
- package/node_modules/node-addon-api/noexcept.gypi +26 -0
- package/node_modules/node-addon-api/nothing.c +0 -0
- package/node_modules/node-addon-api/package-support.json +21 -0
- package/node_modules/node-addon-api/package.json +481 -0
- package/node_modules/node-addon-api/tools/README.md +73 -0
- package/node_modules/node-addon-api/tools/check-napi.js +99 -0
- package/node_modules/node-addon-api/tools/clang-format.js +71 -0
- package/node_modules/node-addon-api/tools/conversion.js +301 -0
- package/nodes/browse.html +27 -2
- package/nodes/connection.html +293 -6
- package/nodes/connection.js +160 -23
- package/nodes/read.html +42 -3
- package/nodes/read.js +51 -12
- package/nodes/subscribe.html +57 -5
- package/nodes/subscribe.js +386 -99
- package/nodes/write.html +29 -2
- package/nodes/write.js +2 -1
- package/package.json +15 -4
- package/prebuilds/linux-x64-musl/opcua_open62541.node +0 -0
- package/scripts/build-offline-prebuild.sh +15 -0
- package/scripts/build-open62541.sh +14 -4
- package/scripts/build-test-server.sh +23 -0
- package/scripts/install.js +28 -0
- package/scripts/verify-offline-package.js +20 -0
- package/scripts/verify-runtime.js +20 -0
- package/src/addon.cc +707 -119
- package/vendor/open62541-LICENSE +373 -0
- package/vendor/open62541-v1.4.16.tar.gz +0 -0
package/nodes/write.js
CHANGED
|
@@ -28,7 +28,8 @@ module.exports = function registerWriteNode(RED) {
|
|
|
28
28
|
operation: 'write',
|
|
29
29
|
total: results.length,
|
|
30
30
|
good: results.filter((item) => item.statusCode === 'Good').length,
|
|
31
|
-
clientDiagnostics: node.connection.
|
|
31
|
+
clientDiagnostics: node.connection.getDiagnostics?.() ||
|
|
32
|
+
node.connection.client.getDiagnostics(),
|
|
32
33
|
};
|
|
33
34
|
send(msg);
|
|
34
35
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tier0/opcua-client",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.4.0",
|
|
4
4
|
"description": "High-scale OPC UA client nodes for Node-RED powered by open62541",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"repository": {
|
|
@@ -16,21 +16,29 @@
|
|
|
16
16
|
"nodes",
|
|
17
17
|
"src",
|
|
18
18
|
"scripts",
|
|
19
|
+
"prebuilds",
|
|
20
|
+
"vendor",
|
|
19
21
|
"README.md",
|
|
20
22
|
"BENCHMARK.md",
|
|
23
|
+
"THIRD_PARTY_NOTICES.md",
|
|
21
24
|
"LICENSE"
|
|
22
25
|
],
|
|
23
26
|
"scripts": {
|
|
24
|
-
"install": "
|
|
27
|
+
"install": "node scripts/install.js",
|
|
25
28
|
"build:open62541": "bash scripts/build-open62541.sh",
|
|
29
|
+
"build:offline-prebuild": "bash scripts/build-offline-prebuild.sh",
|
|
30
|
+
"build:test-server": "bash scripts/build-test-server.sh",
|
|
26
31
|
"build": "node-gyp rebuild",
|
|
27
32
|
"clean": "node-gyp clean",
|
|
28
33
|
"test": "node --test test/*.test.js",
|
|
29
|
-
"test:native": "node test/native.integration.js && node test/native.queue.integration.js && node test/reconnect.integration.js",
|
|
34
|
+
"test:native": "node test/native.integration.js && node test/native.queue.integration.js && node test/native.command-queue.integration.js && node test/reconnect.integration.js",
|
|
30
35
|
"test:reconnect": "node test/reconnect.integration.js",
|
|
36
|
+
"test:secure": "node test/secure.integration.js",
|
|
37
|
+
"test:offline-runtime": "node scripts/verify-runtime.js",
|
|
31
38
|
"test:stress": "node test/stress.js",
|
|
32
39
|
"test:nodered": "node test/nodered.integration.js",
|
|
33
|
-
"test:nodered:reconnect": "OPCUA_NODERED_RECONNECT=1 node test/nodered.integration.js"
|
|
40
|
+
"test:nodered:reconnect": "OPCUA_NODERED_RECONNECT=1 node test/nodered.integration.js",
|
|
41
|
+
"prepack": "node scripts/verify-offline-package.js"
|
|
34
42
|
},
|
|
35
43
|
"keywords": [
|
|
36
44
|
"node-red",
|
|
@@ -55,6 +63,9 @@
|
|
|
55
63
|
"dependencies": {
|
|
56
64
|
"node-addon-api": "^8.3.1"
|
|
57
65
|
},
|
|
66
|
+
"bundledDependencies": [
|
|
67
|
+
"node-addon-api"
|
|
68
|
+
],
|
|
58
69
|
"devDependencies": {
|
|
59
70
|
"node-gyp": "^11.4.2"
|
|
60
71
|
}
|
|
Binary file
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
set -euo pipefail
|
|
3
|
+
|
|
4
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd -P)"
|
|
5
|
+
ROOT_DIR="$(cd "${SCRIPT_DIR}/.." && pwd -P)"
|
|
6
|
+
|
|
7
|
+
cd "${ROOT_DIR}"
|
|
8
|
+
npm run build:open62541
|
|
9
|
+
node-gyp rebuild "$@"
|
|
10
|
+
|
|
11
|
+
PREBUILD_KEY="$(node -p "require('./lib/prebuild').prebuildKey()")"
|
|
12
|
+
DESTINATION="${ROOT_DIR}/prebuilds/${PREBUILD_KEY}/opcua_open62541.node"
|
|
13
|
+
mkdir -p "$(dirname "${DESTINATION}")"
|
|
14
|
+
cp "${ROOT_DIR}/build/Release/opcua_open62541.node" "${DESTINATION}"
|
|
15
|
+
echo "Built ${DESTINATION}"
|
|
@@ -6,18 +6,28 @@ ROOT_DIR="$(cd "${SCRIPT_DIR}/.." && pwd -P)"
|
|
|
6
6
|
VERSION="${OPEN62541_VERSION:-1.4.16}"
|
|
7
7
|
BUILD_ROOT="${ROOT_DIR}/.build/open62541-src"
|
|
8
8
|
INSTALL_ROOT="${OPEN62541_PREFIX:-${ROOT_DIR}/.build/open62541}"
|
|
9
|
+
VENDORED_ARCHIVE="${ROOT_DIR}/vendor/open62541-v${VERSION}.tar.gz"
|
|
9
10
|
|
|
10
|
-
if [[ ! -
|
|
11
|
+
if [[ ! -f "${BUILD_ROOT}/CMakeLists.txt" ]]; then
|
|
11
12
|
rm -rf "${BUILD_ROOT}"
|
|
12
|
-
|
|
13
|
-
|
|
13
|
+
mkdir -p "${BUILD_ROOT}"
|
|
14
|
+
if [[ -f "${VENDORED_ARCHIVE}" ]]; then
|
|
15
|
+
tar -xzf "${VENDORED_ARCHIVE}" --strip-components=1 -C "${BUILD_ROOT}"
|
|
16
|
+
elif [[ "${OPCUA_CLIENT_OFFLINE_ONLY:-0}" == "1" ]]; then
|
|
17
|
+
echo "Bundled open62541 archive is missing: ${VENDORED_ARCHIVE}" >&2
|
|
18
|
+
exit 1
|
|
19
|
+
else
|
|
20
|
+
rm -rf "${BUILD_ROOT}"
|
|
21
|
+
git clone --depth 1 --branch "v${VERSION}" \
|
|
22
|
+
https://github.com/open62541/open62541.git "${BUILD_ROOT}"
|
|
23
|
+
fi
|
|
14
24
|
fi
|
|
15
25
|
|
|
16
26
|
cmake -S "${BUILD_ROOT}" -B "${BUILD_ROOT}/build" \
|
|
17
27
|
-DCMAKE_BUILD_TYPE=Release \
|
|
18
28
|
-DCMAKE_POSITION_INDEPENDENT_CODE=ON \
|
|
19
29
|
-DBUILD_SHARED_LIBS=OFF \
|
|
20
|
-
-DUA_ENABLE_ENCRYPTION=
|
|
30
|
+
-DUA_ENABLE_ENCRYPTION=OPENSSL \
|
|
21
31
|
-DUA_BUILD_EXAMPLES=OFF \
|
|
22
32
|
-DUA_BUILD_UNIT_TESTS=OFF \
|
|
23
33
|
-DCMAKE_INSTALL_PREFIX="${INSTALL_ROOT}"
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
set -euo pipefail
|
|
3
|
+
|
|
4
|
+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd -P)"
|
|
5
|
+
ROOT_DIR="$(cd "${SCRIPT_DIR}/.." && pwd -P)"
|
|
6
|
+
OPEN62541_ROOT="${OPEN62541_PREFIX:-${ROOT_DIR}/.build/open62541}"
|
|
7
|
+
OUTPUT="${OPCUA_TEST_SERVER_BINARY:-${ROOT_DIR}/build/open62541-test-server}"
|
|
8
|
+
LIBRARY="${OPEN62541_ROOT}/lib/libopen62541.a"
|
|
9
|
+
|
|
10
|
+
if [[ ! -f "${LIBRARY}" ]]; then
|
|
11
|
+
echo "open62541 static library not found: ${LIBRARY}" >&2
|
|
12
|
+
echo "Run npm run build:open62541 first." >&2
|
|
13
|
+
exit 1
|
|
14
|
+
fi
|
|
15
|
+
|
|
16
|
+
mkdir -p "$(dirname "${OUTPUT}")"
|
|
17
|
+
"${CC:-cc}" -std=c99 -O2 -Wall -Wextra \
|
|
18
|
+
-I"${OPEN62541_ROOT}/include" \
|
|
19
|
+
"${ROOT_DIR}/test/fixture/open62541_server.c" \
|
|
20
|
+
"${LIBRARY}" -lssl -lcrypto -lpthread -lm -ldl \
|
|
21
|
+
-o "${OUTPUT}"
|
|
22
|
+
|
|
23
|
+
echo "Built ${OUTPUT}"
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const path = require('node:path');
|
|
4
|
+
const { spawnSync } = require('node:child_process');
|
|
5
|
+
const { prebuildKey, resolvePrebuilt } = require('../lib/prebuild');
|
|
6
|
+
|
|
7
|
+
const packageRoot = path.resolve(__dirname, '..');
|
|
8
|
+
const prebuilt = resolvePrebuilt(packageRoot);
|
|
9
|
+
|
|
10
|
+
if (prebuilt && process.env.OPCUA_CLIENT_FORCE_BUILD !== '1') {
|
|
11
|
+
console.log(`Using bundled OPC UA native addon for ${prebuildKey()}`);
|
|
12
|
+
process.exit(0);
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
function run(command, args) {
|
|
16
|
+
const result = spawnSync(command, args, {
|
|
17
|
+
cwd: packageRoot,
|
|
18
|
+
env: process.env,
|
|
19
|
+
stdio: 'inherit',
|
|
20
|
+
shell: process.platform === 'win32',
|
|
21
|
+
});
|
|
22
|
+
if (result.error) throw result.error;
|
|
23
|
+
if (result.status !== 0) process.exit(result.status || 1);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
console.log(`No bundled native addon for ${prebuildKey()}; building from bundled source`);
|
|
27
|
+
run('bash', ['scripts/build-open62541.sh']);
|
|
28
|
+
run('node-gyp', ['rebuild']);
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const fs = require('node:fs');
|
|
4
|
+
const path = require('node:path');
|
|
5
|
+
|
|
6
|
+
const root = path.resolve(__dirname, '..');
|
|
7
|
+
const required = [
|
|
8
|
+
'vendor/open62541-v1.4.16.tar.gz',
|
|
9
|
+
'vendor/open62541-LICENSE',
|
|
10
|
+
'prebuilds/linux-x64-musl/opcua_open62541.node',
|
|
11
|
+
'node_modules/node-addon-api/package.json',
|
|
12
|
+
];
|
|
13
|
+
const missing = required.filter((entry) => !fs.existsSync(path.join(root, entry)));
|
|
14
|
+
|
|
15
|
+
if (missing.length) {
|
|
16
|
+
console.error(`Offline package is incomplete:\n- ${missing.join('\n- ')}`);
|
|
17
|
+
process.exit(1);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
console.log('Offline package inputs verified');
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
const { prebuildKey } = require('../lib/prebuild');
|
|
4
|
+
const { loadAddon } = require('../lib/native');
|
|
5
|
+
|
|
6
|
+
const addon = loadAddon();
|
|
7
|
+
const required = [
|
|
8
|
+
'connectAsync',
|
|
9
|
+
'disconnectAsync',
|
|
10
|
+
'browseAsync',
|
|
11
|
+
'readManyAsync',
|
|
12
|
+
'writeManyAsync',
|
|
13
|
+
'createSubscriptionAsync',
|
|
14
|
+
];
|
|
15
|
+
const missing = required.filter((name) => typeof addon[name] !== 'function');
|
|
16
|
+
if (missing.length) {
|
|
17
|
+
throw new Error(`Native addon is missing exports: ${missing.join(', ')}`);
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
console.log(`Offline native addon loaded for ${prebuildKey()} on ${process.version}`);
|