[
    {
        "id": "021725d4b1abdabc",
        "type": "tab",
        "label": "OPCUA Server LifeCycle",
        "disabled": false,
        "info": "",
        "env": []
    },
    {
        "id": "0f02860d554d1584",
        "type": "function",
        "z": "021725d4b1abdabc",
        "name": "Create Basic OPCUA Server with one counter variable",
        "func": "// Demonstrates the GLOBALS path — works under `functionExternalModules: false`.\n//\n// No `libs:` Setup-tab entry. No settings.js edit. The Sterfive palette\n// populates `global.get(\"sterfive\")` at startup via bootstrapOnce(); user\n// code reaches into it instead of importing.\nconst sterfive = global.get(\"sterfive\");\nif (!sterfive) {\n    node.error(\"global.get('sterfive') is not set — is opcua-for-nodered loaded?\");\n} else {\n    const { bootstrap, opcua } = sterfive;\n    const { bootstrapServer } = bootstrap;\n\n    const cfg = msg.config || {};\n\n    const handle = await bootstrapServer({\n        port: cfg.port ?? 4840,\n        endpoint: cfg.endpoint || \"node-red-server\",\n        nodesets: [\n            \"standard\",\n            \"di\",\n            \"ia\",\n            \"machinery\"\n        ],\n        onPopulate: (addressSpace, exposed) => {\n\n            const ns = addressSpace.getOwnNamespace();\n            exposed.myCounter = ns.addVariable({\n                organizedBy: \"RootFolder\",\n                nodeId: \"s=Counter\",\n                browseName: \"Counter\",\n                dataType: \"Double\",\n                value: { dataType: \"Double\", value: 3.14 },\n            });\n        },\n    });\n\n    flow.set(\"$myCounter\", handle.exposed.myCounter);\n    flow.set(\"$opcuaHandle\", handle);\n\n    node.send({ payload: `OPC UA Server (globals path) running at ${handle.server.getEndpointUrl()}` });\n}\n",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 540,
        "y": 160,
        "wires": [
            [
                "64ae7b5cc8d1e4db"
            ]
        ]
    },
    {
        "id": "033521086760a5b0",
        "type": "inject",
        "z": "021725d4b1abdabc",
        "name": "Start Server",
        "props": [
            {
                "p": "config",
                "v": "{ \"port\": 26550 }",
                "vt": "json"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "x": 210,
        "y": 160,
        "wires": [
            [
                "0f02860d554d1584"
            ]
        ]
    },
    {
        "id": "64ae7b5cc8d1e4db",
        "type": "debug",
        "z": "021725d4b1abdabc",
        "name": "debug output",
        "active": true,
        "tosidebar": true,
        "console": false,
        "tostatus": false,
        "complete": "payload",
        "targetType": "msg",
        "statusVal": "",
        "statusType": "auto",
        "x": 950,
        "y": 220,
        "wires": []
    },
    {
        "id": "0aa52f8b1ea87a02",
        "type": "function",
        "z": "021725d4b1abdabc",
        "name": "update OPCUA counter variable",
        "func": "var v = flow.get(\"$myCounter\");\nconst value = v.readValue()\nvalue.value.value += 1;\nv.setValueFromSource(value.value)\nreturn { ...msg, payload: value.value.value };",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 470,
        "y": 200,
        "wires": [
            [
                "64ae7b5cc8d1e4db"
            ]
        ]
    },
    {
        "id": "f68d6c162b1df7d0",
        "type": "inject",
        "z": "021725d4b1abdabc",
        "name": "Count Up",
        "props": [],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "x": 220,
        "y": 200,
        "wires": [
            [
                "0aa52f8b1ea87a02"
            ]
        ]
    },
    {
        "id": "08bb6ee005859876",
        "type": "inject",
        "z": "021725d4b1abdabc",
        "name": "Server Info",
        "props": [],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "x": 220,
        "y": 240,
        "wires": [
            [
                "c071cde5af35d520"
            ]
        ]
    },
    {
        "id": "c071cde5af35d520",
        "type": "function",
        "z": "021725d4b1abdabc",
        "name": "extract OPCUA server info",
        "func": "const sterfive = global.get(\"sterfive\");\nif (!sterfive) {\n    node.error(\"global.get('sterfive') is not set — is opcua-for-nodered loaded?\");\n    return;\n}\nconst { getServerInfo, displayServerInfo } = sterfive.bootstrap;\nconst handle = flow.get(\"$opcuaHandle\");\nif (!handle || !handle.isRunning()) {\n    node.warn(\"OPC UA server is not running\");\n    return;\n}\ndisplayServerInfo(handle.server);\nreturn { ...msg, payload: getServerInfo(handle.server) };\n",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 460,
        "y": 240,
        "wires": [
            [
                "64ae7b5cc8d1e4db"
            ]
        ]
    },
    {
        "id": "2902974f811e1761",
        "type": "inject",
        "z": "021725d4b1abdabc",
        "name": "Stop Server",
        "props": [],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "x": 210,
        "y": 280,
        "wires": [
            [
                "f71b56a0cebe3143"
            ]
        ]
    },
    {
        "id": "f71b56a0cebe3143",
        "type": "function",
        "z": "021725d4b1abdabc",
        "name": "stop OPCUA server",
        "func": "const handle = flow.get(\"$opcuaHandle\");\nif (!handle || !handle.isRunning()) {\n    node.warn(\"OPC UA server is not running\");\n    return;\n}\nawait handle.shutdown(2000);\nflow.set(\"$opcuaHandle\", undefined);\nflow.set(\"$myCounter\", undefined);\nreturn { ...msg, payload: \"OPC UA Server stopped\" };\n",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 430,
        "y": 280,
        "wires": [
            [
                "64ae7b5cc8d1e4db"
            ]
        ]
    }
]
