Skip to content
Closed
Show file tree
Hide file tree
Changes from 23 commits
Commits
Show all changes
55 commits
Select commit Hold shift + click to select a range
cb05d55
Source generator: support source-generating compiled companion NodeSets
marcschier Jul 20, 2026
a9edb38
Add OPC UA Robotics companion SDK
marcschier Jul 20, 2026
12a5800
Add OPC UA — OpenUSD binding integration (libraries, connector, sampl…
marcschier Jul 20, 2026
f6e2161
review: locks, browse continuation points, INullable guards, Robotics…
marcschier Jul 21, 2026
25065b4
review: Variant sink API, history continuation+batch, IAsyncDisposabl…
marcschier Jul 21, 2026
59288ae
review: DI+fluent AddOpenUsdConnector (both surfaces), options object…
marcschier Jul 21, 2026
8049ca1
review: digest as ByteString, AttachStageAssets ArrayOf<T>, fix e2e d…
marcschier Jul 21, 2026
52c9aec
review: add unit tests for UsdFileSink, Convert, sinks, options, fact…
marcschier Jul 21, 2026
332335c
review: remove dead IntentFromTypeId, use named type-id consts, add D…
marcschier Jul 21, 2026
8b565f3
review: net48 test compat (avoid DateTime.UnixEpoch), dispose connect…
marcschier Jul 21, 2026
f3091fb
review: add OpenUsd.Client and Robotics.Client unit test project sources
marcschier Jul 21, 2026
0e0112d
Merge origin/master into marcschier/openusd-integration
marcschier Jul 22, 2026
d3ba2ad
robot sample: create robotics instances via generated CreateInstanceO…
marcschier Jul 22, 2026
6ec1482
Use INullable semantics in OpenUSD APIs
marcschier Jul 22, 2026
2e1268e
Add referenced-model fluent accessor generation
marcschier Jul 23, 2026
8752610
Add common OPC UA Robotics contracts
marcschier Jul 23, 2026
21efcf1
Add fluent OPC UA Robotics server hosting
marcschier Jul 23, 2026
904d088
Add fluent OPC UA Robotics topology builders
marcschier Jul 24, 2026
e83b999
Add OPC UA RSL and GPOS positioning support
marcschier Jul 24, 2026
f52e80b
Generate typed NodeSet method signatures
marcschier Jul 25, 2026
d9436e3
Merge remote-tracking branch 'origin/marcschier/openusd-integration' …
marcschier Jul 25, 2026
afe21af
Merge remote-tracking branch 'origin/master' into marcschier/robotics…
marcschier Jul 25, 2026
0748861
Add Robotics package documentation
marcschier Jul 25, 2026
2c5c1a5
Address PR review feedback on the Robotics SDK
marcschier Jul 26, 2026
e418545
OpenUSD: fix critical/high spec-conformance defects (Part 1 0.3.0)
marcschier Jul 26, 2026
1b84b67
Remove reintroduced AsBoxedObject uses in the OpenUSD connector
marcschier Jul 26, 2026
e474273
Add standard Robotics operations, Programs, and a shared FileDirector…
marcschier Jul 26, 2026
5dadd32
Add Robotics operation conventions and the high-level client facade
marcschier Jul 26, 2026
8a653f7
Migrate MinimalRobotServer onto the stock Robotics hosting
marcschier Jul 26, 2026
808894b
Split Robotics server tests into a dedicated project and fix a net48 …
marcschier Jul 27, 2026
be15437
Add the OpenUSD Scene Materialization (Part 2) companion SDK
marcschier Jul 27, 2026
474273f
Use the new ConnectionPaths member instead of a side channel
marcschier Jul 27, 2026
a408a7d
Add an in-process OpenUSD viewport to the connector behind --view
marcschier Jul 27, 2026
afaf9c6
Model the robot cell on a real KUKA KR 16-2 and give it a pick-and-pl…
marcschier Jul 27, 2026
f0c1a3c
Make the pump twin a real EN 733 pump that visibly runs
marcschier Jul 27, 2026
2de0c54
Fix the net8.0 build and the pump E2E expectation after the viewport …
marcschier Jul 27, 2026
62ba83c
Sample the mobile robot's frame atomically in the positioning E2E tests
marcschier Jul 28, 2026
53c50e8
Merge origin/master into marcschier/robotics-3827-api
marcschier Jul 28, 2026
4e62c5a
Merge origin/master into marcschier/robotics-3827-api
marcschier Jul 28, 2026
1870c69
Merge origin/master into marcschier/robotics-3827-api
marcschier Jul 28, 2026
95a4dbb
Consume the OpenUSD packages from nuget.org and add the viewer to UA.…
marcschier Jul 29, 2026
f47e899
Stop node copies from consuming NodeIds from the NodeIdFactory
marcschier Jul 29, 2026
362a6ab
Address PR review feedback: docs, naming, and file layout
marcschier Jul 29, 2026
f4474e6
Merge the Robotics and OpenUSD test projects per review feedback
marcschier Jul 29, 2026
1236122
Put the call on the assignment line where it fits
marcschier Jul 29, 2026
6a63237
Unify the GPS provider seam behind one IGeoLocationProvider
marcschier Jul 29, 2026
8320f83
Poll a geo location provider that cannot push
marcschier Jul 29, 2026
92c8238
Fix security review findings and correct a stale-generator test baseline
marcschier Jul 29, 2026
93b41b1
Restore the pump NodeId baseline
marcschier Jul 29, 2026
1705eef
Keep the inherited method declaration when an override keeps its sign…
marcschier Jul 29, 2026
67d45f2
Resolve unqualified file system path segments in the provider namespace
marcschier Jul 29, 2026
190e053
Skip single-TFM projects in solution builds pinned to another framework
marcschier Jul 29, 2026
8f46468
Cover the OpenUSD connector, sinks and scene server with unit tests
marcschier Jul 30, 2026
7a07782
Merge origin/master into marcschier/robotics-3827-api
marcschier Jul 30, 2026
512feae
Fix the net4x build break and the pump baseline found while splitting…
marcschier Jul 30, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
Expand Up @@ -28,3 +28,7 @@

# OPC UA
*.uanodes binary

# Preserve official NodeSet artifacts byte-for-byte.
src/Opc.Ua.Positioning/Model/*.csv binary
src/Opc.Ua.Positioning/Model/*.xml binary
10 changes: 7 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ across industrial control, manufacturing, energy, and IoT systems.
## 📦 What it is

- **A full-stack OPC UA implementation** — Core / Client / Server /
PubSub / GDS / LDS / Complex Types / Device Integration libraries
PubSub / GDS / LDS / Complex Types / Device Integration / Positioning libraries
built on .NET, with UA-TCP and HTTPS transports.
- **Cross-platform** — runs on .NET 10, .NET 9, .NET 8 (LTS),
.NET Framework 4.8, and .NET Standard 2.1; ships
Expand All @@ -34,8 +34,9 @@ across industrial control, manufacturing, energy, and IoT systems.
- **Companion-spec coverage** — Part 9 (Alarms & Conditions), Part 11
(Historical Access), Part 13 (Aggregates), Part 16 (State Machines),
Part 17 (Alias Names), Part 18 (Role Management), Part 20 (File
Transfer), Part 100 (Device Integration), OPC 10100-1 (WoT
Connectivity).
Transfer), Part 100 (Device Integration), Parts 210/211 (Relative
Spatial Location and Global Positioning), OPC 10100-1 (WoT Connectivity),
OPC 40001-1 (Industrial Automation), OPC 40010-1 (Robotics).
- **Modern developer surface** — first-class `Microsoft.Extensions.DependencyInjection`
hosting (`services.AddOpcUa()`), fluent server + client builders,
source-generated NodeManagers and DataTypes, and an MCP server so
Expand Down Expand Up @@ -99,6 +100,9 @@ Each sample has its own `README.md` with build and run instructions.
- [Pump Device Integration Server](samples/PumpDeviceIntegrationServer/README.md) —
minimal Device Integration (Part 100) server using
`Opc.Ua.Di.Server`'s fluent builder.
- [Minimal Robot Server](samples/MinimalRobotServer/README.md) — OPC 40010
Robotics with independently configurable RSL/GPOS motion and live OpenUSD
transforms.

More sample projects are maintained in the companion
[OPC UA .NET Samples](https://github.com/OPCFoundation/UA-.NETStandard-Samples)
Expand Down
14 changes: 14 additions & 0 deletions UA.slnx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
<Project Path="samples/MinimalCalcServer/MinimalCalcServer.csproj" />
<Project Path="samples/MinimalClient/MinimalClient.csproj" />
<Project Path="samples/PumpDeviceIntegrationServer/PumpDeviceIntegrationServer.csproj" />
<Project Path="samples/MinimalRobotServer/MinimalRobotServer.csproj" />
<Project Path="samples/Quickstarts.Servers/Quickstarts.Servers.csproj" />
<Project Path="samples/RedundantClient/RedundantClient.csproj" />
</Folder>
Expand Down Expand Up @@ -66,6 +67,15 @@
<Project Path="src/Opc.Ua.Di.Client/Opc.Ua.Di.Client.csproj" />
<Project Path="src/Opc.Ua.Di.Server/Opc.Ua.Di.Server.csproj" />
<Project Path="src/Opc.Ua.Di/Opc.Ua.Di.csproj" />
<Project Path="src/Opc.Ua.OpenUsd/Opc.Ua.OpenUsd.csproj" />
<Project Path="src/Opc.Ua.OpenUsd.Server/Opc.Ua.OpenUsd.Server.csproj" />
<Project Path="src/Opc.Ua.OpenUsd.Client/Opc.Ua.OpenUsd.Client.csproj" />
<Project Path="src/Opc.Ua.Positioning/Opc.Ua.Positioning.csproj" />
<Project Path="src/Opc.Ua.Positioning.Client/Opc.Ua.Positioning.Client.csproj" />
<Project Path="src/Opc.Ua.Positioning.Server/Opc.Ua.Positioning.Server.csproj" />
<Project Path="src/Opc.Ua.Robotics/Opc.Ua.Robotics.csproj" />
<Project Path="src/Opc.Ua.Robotics.Server/Opc.Ua.Robotics.Server.csproj" />
<Project Path="src/Opc.Ua.Robotics.Client/Opc.Ua.Robotics.Client.csproj" />
<Project Path="src/Opc.Ua.Gds.Client.Common/Opc.Ua.Gds.Client.Common.csproj" />
<Project Path="src/Opc.Ua.Gds.Common/Opc.Ua.Gds.Common.csproj" />
<Project Path="src/Opc.Ua.Gds.Server.Common/Opc.Ua.Gds.Server.Common.csproj" />
Expand Down Expand Up @@ -218,6 +228,8 @@
<Project Path="tests/Opc.Ua.Core.Encoders.Tests/Opc.Ua.Core.Encoders.Tests.csproj" />
<Project Path="tests/Opc.Ua.Core.Security.Tests/Opc.Ua.Core.Security.Tests.csproj" />
<Project Path="tests/Opc.Ua.Di.Tests/Opc.Ua.Di.Tests.csproj" />
<Project Path="tests/Opc.Ua.OpenUsd.Client.Tests/Opc.Ua.OpenUsd.Client.Tests.csproj" />
<Project Path="tests/Opc.Ua.Robotics.Client.Tests/Opc.Ua.Robotics.Client.Tests.csproj" />
<Project Path="tests/Opc.Ua.Core.Diagnostics.Tests/Opc.Ua.Core.Diagnostics.Tests.csproj" />
<Project Path="tests/Opc.Ua.Bindings.Https.WebApi.Tests/Opc.Ua.Bindings.Https.WebApi.Tests.csproj" />
<Project Path="tests/Opc.Ua.Features.Tests/Opc.Ua.Features.Tests.csproj" />
Expand All @@ -239,6 +251,7 @@
<Project Path="tests/Opc.Ua.PubSub.Schema.Tests/Opc.Ua.PubSub.Schema.Tests.csproj" />
<Project Path="tests/Opc.Ua.PubSub.Server.Tests/Opc.Ua.PubSub.Server.Tests.csproj" />
<Project Path="tests/Opc.Ua.PubSub.Diagnostics.Tests/Opc.Ua.PubSub.Diagnostics.Tests.csproj" />
<Project Path="tests/Opc.Ua.Positioning.Tests/Opc.Ua.Positioning.Tests.csproj" />
<Project Path="tests/Opc.Ua.Redundancy.PubSub.Tests/Opc.Ua.Redundancy.PubSub.Tests.csproj" />
<Project Path="tests/Opc.Ua.Security.Certificates.Tests/Opc.Ua.Security.Certificates.Tests.csproj" />
<Project Path="tests/Opc.Ua.Server.Tests/Opc.Ua.Server.Tests.csproj" />
Expand All @@ -262,6 +275,7 @@
</Folder>
<Folder Name="/tools/">
<Project Path="tools/Opc.Ua.Mcp/Opc.Ua.Mcp.csproj" />
<Project Path="tools/Opc.Ua.OpenUsd.Connector/Opc.Ua.OpenUsd.Connector.csproj" />
</Folder>
<Folder Name="/tools/MigrationAnalyzer/">
<Project Path="tools/Opc.Ua.MigrationAnalyzer.CodeFixer/Opc.Ua.MigrationAnalyzer.CodeFixer.csproj" />
Expand Down
69 changes: 69 additions & 0 deletions docs/DependencyInjection.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@ you need finer control.
| `Opc.Ua.Server` | `builder.AddServer(opt => …)` | `IOpcUaServerBuilder` | yes | `OpcUa:Server` |
| `Opc.Ua.Server` (node manager)| `builder.AddNodeManager<T>()` | `IOpcUaServerBuilder` | — | — |
| `Opc.Ua.Server` (runtime NodeSet) | `builder.AddRuntimeNodeSet(…)` | `IOpcUaServerBuilder` | — | — |
| `Opc.Ua.Positioning.Server` | `serverBuilder.AddPositioningServer()` / `AddPositioningFor<T>()` | `IPositioningServerBuilder` | yes (via `AddServer`) | — |
Comment thread
marcschier marked this conversation as resolved.
| `Opc.Ua.Positioning.Client` | `clientBuilder.AddPositioningClient()` | `IOpcUaClientBuilder` | — | — |
| `Opc.Ua.Robotics.Server` | `serverBuilder.AddRobotics(opt => …)` | `IOpcUaServerBuilder` | yes (via `AddServer`) | — |
| `Opc.Ua.Robotics.Server` (model) | `serverBuilder.AddRoboticsModel<T>()` | `IOpcUaServerBuilder` | — | — |
| `Opc.Ua.Robotics.Server` (build) | `serverBuilder.ConfigureRobotics(…)` / `ConfigureRoboticsFor<T>(…)` | `IOpcUaServerBuilder` | — | — |
| `Opc.Ua.Gds.Client.Common` | `builder.AddGdsClient(opt => …)` | `IGdsClientBuilder` | — | `OpcUa:Gds:Client` |
| `Opc.Ua.Gds.Server.Common` | `builder.AddGdsServer(opt => …)` | `IGdsServerBuilder` | yes | `OpcUa:Gds:Server` |
| `Opc.Ua.Lds.Server` | `builder.AddLdsServer(opt => …)` | `ILdsServerBuilder` | yes | `OpcUa:Lds` |
Expand Down Expand Up @@ -662,6 +667,69 @@ services.AddOpcUa()
`AddHistorianFileStore(provider, path)` combines the historian provider registration with a Part 20
file-system mount for demo and lab servers.

### Positioning

Use `AddPositioningServer()` when Positioning owns its node manager. Use
`AddPositioningFor<TNodeManager>()` when an existing companion node manager
loads and owns the RSL/GPOS models:

```csharp
IPositioningServerBuilder positioning = services
.AddOpcUa()
.AddServer(options => { /* endpoint and application options */ })
.AddPositioningServer();

positioning
.AddGlobalPositionProvider<MyGlobalPositionProvider>()
.AddRelativeSpatialLocationProvider<MyRelativeLocationProvider>()
.ConfigurePositioningFor<PositioningNodeManager>(context =>
{
// Build and register RSL/GPOS instances through context.AddressSpace.
return default;
});
```

Client factories compose the generated proxies over the managed session:

```csharp
services.AddOpcUa()
.AddClient(options => { /* endpoint and application options */ })
.AddPositioningClient();
```

See [Relative Spatial Location and Global Positioning](Positioning.md).

### Robotics

`AddRobotics()` registers the stock `RoboticsNodeManager`, the built-in DI/IA/
Robotics model provider, and the ordered Robotics configuration pipeline. It
owns the DI namespace, so it cannot be combined with `AddOpcUaDi()`.

```csharp
services
.AddOpcUa()
.AddServer(options => { /* endpoint and application options */ })
.AddRobotics(options =>
options.InstanceNamespaceUri = "urn:example:robot-cell")
.AddRoboticsModel<MyExtraModelProvider>()
.ConfigureRobotics(async context =>
{
await context.AddMotionDeviceSystemAsync("RobotCell", system =>
{
// Add controllers, motion devices, axes, power trains, and
// safety states through the fluent Robotics builders.
}, context.CancellationToken);
});
```

Use `ConfigureRobotics<TConfigurator>()` for a dependency-injected class-based
code-behind implementing `IRoboticsConfigurator`, and
`ConfigureRoboticsFor<TNodeManager>(…)` when the application already owns a
compatible `DiNodeManager`. Configurators run in registration order and share
one `IRoboticsBuildContext` per manager startup.

See the [Robotics developer guide](Robotics.md).

## Client feature

`builder.AddClient(opt => …)` registers a lazy `ManagedSession` factory
Expand Down Expand Up @@ -1293,5 +1361,6 @@ services.AddOpcUa()
- [Source Generated NodeManagers](SourceGeneratedNodeManagers.md) — `IAsyncNodeManagerFactory` from a model design XML.
- [Native AOT](NativeAoT.md) — AOT testing setup.
- [GDS Developer Guide](GDS.md) — GDS service interfaces and provider patterns.
- [Robotics](Robotics.md) — OPC 40010 hosting, model providers, and topology builders.
- [WoT Connectivity](WoTConnectivity.md) — OPC 10100-1 information model.
- [Diagnostics](Diagnostics.md) — `ITelemetryContext` end-to-end.
151 changes: 151 additions & 0 deletions docs/OpenUsd.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,151 @@
# OPC UA — OpenUSD binding

This guide covers the client- and server-side libraries that bridge an OPC UA address space to an
[OpenUSD](https://openusd.org/) stage. For the OPC 40010 Robotics companion SDK used to label and drive robot-cell
twins, see [Robotics](Robotics.md).

> The OPC UA — OpenUSD Bindings companion model is a **draft** (experimental) model. The type NodeIds and the
> `Server/OpenUSD/Representations` registry described here are subject to change until the companion specification is
> ratified.

## Libraries

| Package | Role |
| --- | --- |
| `OPCFoundation.NetStandard.Opc.Ua.OpenUsd` | The draft OpenUSD-binding companion model (source-generated NodeStates). |
| `OPCFoundation.NetStandard.Opc.Ua.OpenUsd.Client` | The generic, domain-agnostic `OpenUsdConnector`, the `IUsdSink` abstraction, and the file/mock sinks. |
| `OPCFoundation.NetStandard.Opc.Ua.OpenUsd.Server` | Server-side authoring helpers (`UsdAssetDelivery`, representation authoring). |
| `OPCFoundation.NetStandard.Opc.Ua.OpenUsd.Connector` | A ready-to-run console connector tool built on the client library. |

## The connector

`OpenUsdConnector` is a **client**: it discovers a server's `OpenUsdRepresentation` instances through the Part 1
`Server/OpenUSD/Representations` registry, subscribes to the bound source Variables, applies the declared conversion,
and writes the target USD attributes into an `IUsdSink`. It is domain-agnostic — it knows only the OpenUSD binding
model, never "pump" or "robot".

### Progressive API

The simplest usage needs only a connected session and a sink:

```csharp
using Opc.Ua.OpenUsd.Client;

// session is a connected ISession (for example a ManagedSession).
var sink = new UsdFileSink("live.usda");
await using var connector = new OpenUsdConnector(session, sink);

await connector.StartAsync(cancellationToken); // discover + subscribe + compose
// ... the sink now receives live updates ...
await connector.StopAsync(cancellationToken); // stop streaming
```

`OpenUsdConnector` implements `IAsyncDisposable`; `await using` (or an explicit `DisposeAsync`) stops streaming and
closes any connector-owned remote sessions opened for cross-server federation. The caller-provided primary session is
never closed by the connector.

Advanced behaviour is configured through `OpenUsdConnectorOptions`:

```csharp
var options = new OpenUsdConnectorOptions
{
EnableCommands = true, // opt in to UsdToUaCommand actuation (fail-closed by default)
RemoteSessionFactory = (endpointUrl, ct) => OpenRemoteSessionAsync(endpointUrl, ct), // §5.14 cross-server federation
MaxAssetBytes = 32 * 1024 * 1024, // per-asset read cap
MaxTotalAssetBytes = 128L * 1024 * 1024, // per-fetch read cap
};
await using var connector = new OpenUsdConnector(session, sink, options, telemetry);
```

### Values cross the boundary as `Variant`

`IUsdSink` never exposes `object`. A scalar attribute is a `double`, a colour is a three-element `float` array
(`ArrayOf<float>`), and a token/visibility value is a `string` — all carried as `Variant`:

```csharp
public interface IUsdSink
{
void SetAttribute(string primPath, string propertyName, Variant value);
void SetTimeSample(string primPath, string propertyName, DateTime time, Variant value);
void ComposePrim(string primPath, OpenUsdCompositionArc arc, string? assetReference, bool active);
IDisposable BeginBatch();
}
```

Two sinks ship in the box:

* `UsdFileSink` authors a text USD override layer (`live.usda`). It validates every prim-path segment and property
name as a USD identifier, escapes token values, and rejects unsafe asset references, so a hostile or malformed name
from the server cannot corrupt or inject into the layer.
* `MockUsdSink` is an in-memory, thread-safe sink used by tests and diagnostics.

`BeginBatch()` lets a file-backed sink defer flushes; history replay uses it to author many time samples with a single
file write.

### History replay and commands

* `ReplayHistoryAsync(startTime, endTime, ct)` replays Part 11 history for every `UaHistoryToUsd` binding, following
continuation points and authoring the returned values as USD time samples. Sources that do not historize degrade to
zero samples without throwing.
* `IssueCommandAsync(value, ct)` actuates the opt-in `UsdToUaCommand` binding. It is **fail-closed**: it throws unless
the connector was constructed with `EnableCommands = true`.

### Integrity

When a stage advertises a `RootLayerDigest`, the connector verifies it (constant-time) before authoring any opinions,
and refuses to compose on a mismatch. Served asset closures (`FetchServedAssetsAsync`) are streamed through the Part 5
`FileType`, digest-verified fail-closed, and cached under sanitized relative paths (path-traversal is defended).

## Dependency injection

Both a standalone `IServiceCollection` extension and the fluent `IOpcUaClientBuilder` extension register the singleton
`OpenUsdConnectorFactory`; the direct constructors remain available as a non-DI fallback.

```csharp
// Standalone.
services.AddOpenUsdConnector(o => o.EnableCommands = true);

// Fluent, chained onto the client builder.
services.AddOpcUa()
.AddClient(configuration)
.AddOpenUsdConnector(o => o.MaxAssetBytes = 32 * 1024 * 1024);
```

Resolve the factory and create a connector per connected session:

```csharp
public sealed class TwinWorker(OpenUsdConnectorFactory connectors)
{
public async Task RunAsync(ISession session, IUsdSink sink, CancellationToken ct)
{
await using OpenUsdConnector connector = connectors.Create(session, sink);
await connector.StartAsync(ct);
// ...
}
}
```

Observability is threaded through `ITelemetryContext` (resolved from DI), which the factory passes to each connector.

## Server-side authoring

`UsdAssetDelivery.AttachStageAssets(context, stage, openUsdNs, assets)` serves artist-authored USD layers through the
address space as read-only Part 5 files with SHA-256 digests, so a generic connector can fetch, verify, cache, and
render the twin with no external asset resolver. `assets` is an `ArrayOf<ServedAsset>` and the method returns the
created `OpenUsdAssetState` nodes as an `ArrayOf<OpenUsdAssetState>`.

## Samples

* [`MinimalRobotServer`](../samples/MinimalRobotServer) — a self-contained server exposing an OPC 40010
MotionDeviceSystem with two independently mobile robots. OPC 10000-210 RSL
frames drive live `double3` translation/rotation, and OPC 10000-211 GPOS
locations drive geospatial metadata; a generic connector renders the cell
live. See [Positioning](Positioning.md).
* [`PumpDeviceIntegrationServer`](../samples/PumpDeviceIntegrationServer) — a DI pump line bound to OpenUSD, including
component composition, cross-server components, and served-asset delivery.

## The connector tool

`Opc.Ua.OpenUsd.Connector` is a console application that connects to any server implementing the draft binding,
discovers `Server/OpenUSD/Representations`, subscribes, optionally fetches the served asset closure, and authors a live
`live.usda` override layer. It is the end-to-end reference for the client library.
Loading
Loading