Quick start
Start the daemon, build a ManagedClient, read a value — five minutes from install to a request that survives PHP-FPM.
This page wires the smallest end-to-end integration: daemon up, client connects to an OPC UA server through the daemon, reads one value, exits. Subsequent runs reuse the same session — that is the whole point.
1 — Start the daemon
vendor/bin/opcua-session-manager
Leave it running in the foreground for now. In production you wrap it in systemd — see Daemon · Running as a service.
2 — Connect and read
<?php
require __DIR__ . '/vendor/autoload.php';
use PhpOpcua\SessionManager\Client\ManagedClient;
use PhpOpcua\Client\Types\NodeId;
use PhpOpcua\Client\Types\StatusCode;
$client = new ManagedClient(
socketPath: '/tmp/opcua-session-manager.sock',
timeout: 30.0,
);
$client->connect('opc.tcp://localhost:4840');
$dv = $client->read(NodeId::numeric(0, 2261)); // ProductName
if (StatusCode::isGood($dv->statusCode)) {
echo "Connected to: " . $dv->getValue() . "\n";
}
$client->disconnect();
Run it twice. The first run pays the OPC UA handshake cost; the second run reuses the same daemon-held session and the read is ~10× faster.
3 — Verify the reuse
$client->connect('opc.tcp://localhost:4840');
if ($client->wasSessionReused()) {
echo "Reusing existing session — no handshake.\n";
} else {
echo "Fresh session — first connect from this configuration.\n";
}
wasSessionReused() is the ManagedClient-specific accessor that
tells you whether the last connect() matched an existing session
keyed by the same (endpointUrl, sanitized config) pair. See
ManagedClient · Session reuse.
4 — What disconnect does (and does not)
$client->disconnect();
ManagedClient::disconnect() sends a close IPC command to the
daemon. The daemon performs CloseSession against the OPC UA
server and removes the entry from its session store. The
daemon-side session is gone when disconnect() returns; the
next connect() with the same config pays the OPC UA handshake
again.
To keep the daemon session alive across multiple requests so the
reuse machinery can do its job, do not call disconnect()
between requests — keep the ManagedClient instance alive
(singleton bind in Laravel, long-running worker) and let the
daemon's inactivity timeout (--timeout, default 600 s)
reclaim idle sessions when nothing references them.
To bypass reuse on a particular connect call (force a fresh session even if one matches):
$client->connectForceNew('opc.tcp://localhost:4840');
connectForceNew() is the escape hatch for session isolation
(per-test scenarios, manual session resets). See
ManagedClient · Opening and closing.
5 — Where to go next
The ManagedClient reads, writes, browses, subscribes — every
method on OpcUaClientInterface works. For the operation pages
themselves (read, browse, subscribe, …), the documentation
lives in opcua-client:
opcua-client/doc/04-reading-writing.mdopcua-client/doc/03-browsing.mdopcua-client/doc/06-subscriptions.md
In this documentation the focus is on what changes when you go through the daemon:
- Why a session manager — the mental model.
- ManagedClient · Overview — what the wrapper does and what it does not.
- ManagedClient · Differences from the direct client — side-by-side comparison.
Tip
For a quick smoke-test of the daemon without any PHP, use
netcat to send a ping
command directly to the socket. It is the fastest way to confirm the
daemon is alive and accepting requests.