Skip to content

Expand DI / Fluent API: injectability + one-shot ergonomics (client, server, PubSub, discovery/bindings) - #8

Closed
marcschier wants to merge 1 commit into
mainfrom
marcschier/di-fluent-api-completeness
Closed

Expand DI / Fluent API: injectability + one-shot ergonomics (client, server, PubSub, discovery/bindings)#8
marcschier wants to merge 1 commit into
mainfrom
marcschier/di-fluent-api-completeness

Conversation

@marcschier

Copy link
Copy Markdown
Owner

Description

Completes the dependency-injection / fluent-API review follow-up so that every feature is reachable and configurable from the services.AddOpcUa() chain, while keeping all existing granular registrations and direct-construct (new) fallbacks. The change is backward compatible — the single rename (WithAuthorizationServiceAddAuthorizationService) keeps an [Obsolete] alias.

Client — chainable IOpcUaClientBuilder overloads of AddComplexTypes / AddAlarms / AddWebApiTransportChannel; ManagedSessionOptions.LoadComplexTypes + AddManagedClient() one-shot; injectable multi-endpoint IManagedSessionFactory; DI factories AddHistorian / AddRoleManagement / AddFileTransfer / AddAliasNames; fail-fast options validation + AddDiscovery().

ServerIOpcUaServerFactory / AddServer<TServer>() seam (the hosted service no longer hardcodes new StandardServer) unlocking injectable durable subscriptions and session/subscription managers; plus AddHistorian, AddFileSystem (Part 20), AddSecretStore / AddCertificateManager / AddAliasNameStore; secure-by-default anonymous authenticator (marker-guarded, no double-registration).

PubSubAddUdpPubSub() / AddMqttPubSub() one-shots; IPubSubBuilder anchor unification (AddSecurityKeyServiceClient/Server/PushTarget, AddSchema, AddPcapCapture); ConfigureConfiguration() config-authoring bridge; IMqttTransportBuilder parity with UDP/Eth; order-independent pcap decoration.

Discovery / Bindings — LDS/GDS non-TCP endpoints fail loudly instead of silently; GDS AddInMemoryStores() + fast-fail when stores are missing; order-independent one-shot AddHttpsTransport() (Kestrel + HTTPS/WSS + optional WebApi/auth); AddAuthorizationService ([Obsolete] alias for WithAuthorizationService); root-level IOpcUaBuilder.AddPcap(); WotCon-server-without-AddServer startup guard.

Docs updated: Docs/DependencyInjection.md, Docs/PubSub.md, Docs/Transports.md, Docs/WebApi.md.

Validation performed locally: the 12 changed libraries and 9 affected test projects build clean (0 warnings / 0 errors) on net10.0 and net48; the full net10.0 sweep of the affected suites passes (~7,700 tests — Server 1920, GDS 904, LDS 149, Client 1577, ComplexTypes 2733, PubSub 1141 + Diagnostics 53, WotCon 344, HTTPS.WebApi 319); the net48 new-feature suites pass (Client 123, Server 43, PubSub 49, GDS 21, LDS 10, WotCon 8, ComplexTypes 7).

Related Issues

Follow-up to an internal DI / Fluent-API surface review (no single tracking issue). Happy to open a tracking issue / ADR if maintainers prefer before merge.

  • Fixes # (n/a — review follow-up)

Checklist

Put an x in the boxes that apply. You can complete these step by step after opening the PR.

  • I have signed the CLA and read the CONTRIBUTING doc.
  • I have added tests that prove my fix is effective or that my feature works and increased code coverage.
  • I have added all necessary documentation.
  • I have verified that my changes do not introduce (new) build or analyzer warnings.
  • I ran all tests locally using the UA.slnx solution against at least .net framework and .net 10, and all passed. (Ran the affected areas comprehensively on net10.0 + net48; a full UA.slnx run across both TFMs is still pending.)
  • I fixed all failing and flaky tests in the CI pipelines and all CodeQL warnings.
  • I have addressed all PR feedback received.

…ient, server, PubSub and discovery/bindings

Completes the dependency-injection / fluent-API review follow-up so every feature
is reachable and configurable from the services.AddOpcUa() chain, while keeping all
existing granular registrations and direct-construct fallbacks (backward compatible;
the one rename keeps an [Obsolete] alias).

Client: chainable IOpcUaClientBuilder overloads (AddComplexTypes/AddAlarms/
AddWebApiTransportChannel); ManagedSessionOptions.LoadComplexTypes + AddManagedClient();
injectable multi-endpoint IManagedSessionFactory; DI factories AddHistorian/
AddRoleManagement/AddFileTransfer/AddAliasNames; options fail-fast validation + AddDiscovery().

Server: IOpcUaServerFactory / AddServer<TServer>() seam -> injectable durable
subscriptions, session/subscription managers; AddHistorian, AddFileSystem (Part 20),
AddSecretStore/AddCertificateManager/AddAliasNameStore; secure-by-default anonymous
authenticator (marker-guarded).

PubSub: AddUdpPubSub()/AddMqttPubSub() one-shots; IPubSubBuilder anchor unification
(SKS/schema/pcap); ConfigureConfiguration(); IMqttTransportBuilder parity;
order-independent pcap decoration.

Discovery/Bindings: fail-loud non-TCP endpoints; GDS AddInMemoryStores()/fast-fail;
order-independent AddHttpsTransport() one-shot; AddAuthorizationService ([Obsolete]
alias for WithAuthorizationService), root-level AddPcap(), WotCon prerequisite guard.

Docs updated (DependencyInjection.md, PubSub.md, Transports.md, WebApi.md).
Validated: 12 libraries + 9 test projects build clean on net10.0 and net48; full net10
sweep ~7,700 tests pass; net48 new-feature suites pass.
@marcschier

Copy link
Copy Markdown
Owner Author

Superseded — retargeted to upstream OPCFoundation#3957.

@marcschier marcschier closed this Jul 5, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant