Henara.Grpc.Client.DakotaSlim 1.2.0
Henara.Grpc.Client.DakotaSlim
Slim wiring of the Dakota external gRPC clients for a native host that already owns a Keycloak
session — written for the SmartVO Windows client
(physio-src/main/client/win/SmartVO).
It contains no interactive login and no token refresh. SmartVO's existing
KeycloakAuthService / SessionManager (WebView2 login, DPAPI refresh-token store, 30 s skew
auto-refresh) stays the single source of access tokens. This package only adapts that token onto the
Dakota gRPC calls.
Do not also call
AddNativeKeycloakAuthfromHenara.Grpc.Client.Common. That registers a second refresh-token rotator against the same Keycloak session (henara@auth.praxx.me, clienthenara-main-sso) and the two rotations invalidate each other (invalid_grant).SessionManagermust remain the only token authority.
Registration — SmartVO main host (one line, no extra class)
In the main host builder (client/win/SmartVO/Program.cs, the Host.CreateApplicationBuilder()
block). Ensure the OAuth singletons (ISessionManager and its dependencies — IKeycloakAuthService,
IUserProfileStore, ISecureStorage, …) are registered in this host, not only in the
onboarding ServiceCollection:
// endpoints — set before the host is built
Environment.SetEnvironmentVariable("URL_DAKOTA_PIPELINE", "https://<dakota-pipeline-host>:<port>");
Environment.SetEnvironmentVariable("URL_DAKOTA_REPORTER", "https://<dakota-reporter-host>:<port>");
builder.Services.AddSingleton<ISessionManager, SessionManager>(); // already present in SmartVO's OAuth setup
builder.Services.AddSlimNativeDakotaClient((sp, ct) =>
sp.GetRequiredService<ISessionManager>().GetValidAccessTokenAsync(ct));
That single call registers the internal ICallTokenProvider (which fetches the token via your lambda
on every RPC and prefixes Bearer ) and the Dakota clients (IDakotaGatewayClient,
IDakotaReporterClient). The lambda returns the raw token; the library adds Bearer. The two
URL_DAKOTA_* variables are read and validated at registration — they must be set first or
registration throws.
Conflict guard
AddSlimNativeDakotaClient throws at registration if an ICallTokenProvider or the native
KeycloakRefreshingTokenProvider (i.e. AddNativeKeycloakAuth) is already registered. The slim client
must be the only auth registration; calling both would run two refresh-token rotators against the
same Keycloak session and they would invalidate each other. Register the slim client alone, and before
any native Keycloak auth setup.
Usage
Resolve the clients from the same host's provider and call them; the bearer token is fetched per RPC
from SessionManager (auto-refreshed):
var reporter = provider.GetRequiredService<IDakotaReporterClient>();
await foreach (var p in reporter.GetDakotaStati(new DakotaFilter { CustomerId = new MatchesIntFilterDto(20131386) }))
Console.WriteLine($"{p.CreatedAt:o} {p.ReceiverIk} {p.FileName}");
var (rows, total) = await reporter.GetFilesPaged(page: 0, pageSize: 100, search: "");
var gateway = provider.GetRequiredService<IDakotaGatewayClient>();
await foreach (var r in gateway.DispatchDakotaProcess(pairs))
Console.WriteLine(r.IsDispatched ? r.PipelineId.ToString() : r.Message);
The reporting service scopes all results to the signed-in user's customer id(s); Henara admins see everything. The intake gate authorises the dispatch by the sender (praxis) IK carried in the file pair.
Endpoints / identity reference
| Setting | Value | Source |
|---|---|---|
| Keycloak realm | henara @ https://auth.praxx.me |
SmartVO OAuthConfig |
| Client id | henara-main-sso |
SmartVO OAuthConfig |
URL_DAKOTA_PIPELINE |
Dakota pipeline gateway gRPC URL | env var (set by host) |
URL_DAKOTA_REPORTER |
Dakota reporting gRPC URL | env var (set by host) |
http:// endpoints are served as plaintext h2c; GrpcClientBase enables call credentials over the
insecure channel automatically. Prefer https:// for production.
No packages depend on Henara.Grpc.Client.DakotaSlim.
.NET 10.0
- Henara.Grpc.Client.Dakota (>= 1.2.0)