Skip to content

Quick Start And Client Integration

Use Microtec.Notifications.Client in application services. It wraps HTTP delivery, queue delivery, tenant headers, resilience policies, fluent payload builders, and optional proxy controllers.

Package References

In a consuming service, reference:

xml
<PackageReference Include="Microtec.Notifications.Client" Version="x.y.z" />
<PackageReference Include="Microtec.Notifications.Contracts" Version="x.y.z" />

If the service uses project references in the shared packages repository, reference the package projects instead.

Integration Shape

Register The Client

csharp
using Microtec.Notifications.Client.Extensions;

builder.Services.AddNotificationsClient(builder.Configuration);

With overrides:

csharp
builder.Services.AddNotificationsClient(
    builder.Configuration,
    options =>
    {
        options.BaseUrl = "https://notification-service.internal";
        options.ClientId = "erp";
        options.InternalApiKey = "<internal-api-key>";
        options.TimeoutSeconds = 30;
    });

The extension registers:

  • INotificationsClient
  • HTTP delivery strategy
  • queue delivery strategy
  • notification center client
  • channel config client
  • credentials client
  • device token client
  • WhatsApp provisioning client
  • seed defaults client
  • optional controllers from the client package

Queue delivery requires MassTransit IPublishEndpoint to be registered in the consuming application. Microtec services that already use the shared messaging setup normally have this. For an HTTP-only service, verify DI can resolve INotificationsClient after adding the package.

Configuration

json
{
  "NotificationsClient": {
    "BaseUrl": "https://notification-service.internal",
    "ClientId": "erp",
    "InternalApiKey": "<internal-api-key>",
    "TimeoutSeconds": 30,
    "SourceSystem": null,
    "Resilience": {
      "Retry": {
        "MaxRetryAttempts": 3,
        "InitialDelaySeconds": 1,
        "UseExponentialBackoff": true
      },
      "CircuitBreaker": {
        "FailureThreshold": 5,
        "DurationOfBreakSeconds": 30,
        "SamplingDurationSeconds": 60
      },
      "Timeout": {
        "TimeoutSeconds": 30
      }
    }
  }
}

Actual NotificationsClientOptions properties are:

PropertyDefaultDescription
BaseUrlhttp://localhost:2031Base URL of the Notification service.
ClientIderpCalling service identifier.
InternalApiKeyemptyInternal API key value sent as InternalApiKey.
TimeoutSeconds120HTTP client timeout.
SourceSystemnullOptional system sender identity. Makes payload Subdomain optional.
Resiliencedefault policy optionsPolly retry, timeout, and circuit breaker settings.

Send Email

csharp
using Microtec.Notifications.Client;
using Microtec.Notifications.Client.Builders;
using Microtec.Notifications.Contracts.Enums;

public sealed class InvoiceNotifier(INotificationsClient notifications)
{
    public async Task SendInvoiceEmailAsync(
        string email,
        string subdomain,
        CancellationToken ct)
    {
        var payload = NotificationBuilder.Email()
            .WithSubdomain(subdomain)
            .Subject("Invoice ready")
            .Body("<p>Your invoice is ready.</p>")
            .To(email)
            .ModuleName("Sales")
            .ServiceName("Invoices")
            .NotificationSettingType("InvoiceReady")
            .Build();

        await notifications.SendViaHttpAsync(payload, ct);
    }
}

Send SMS

csharp
var payload = NotificationBuilder.Sms()
    .WithSubdomain("acme")
    .To("+201000000000")
    .Region("EG")
    .Body("Your verification code is 123456")
    .Build();

await notifications.SendAsync(payload, DeliveryMode.Http, cancellationToken);

Send Push

Push requires one or more UserIds in the payload. The current client implementation also requires a valid current user id from ITenantContextManager when sending a PushPayload.

csharp
var payload = NotificationBuilder.Push()
    .WithSubdomain("acme")
    .ToUserIds([userId])
    .Title("Order approved")
    .Body("Your order has been approved.")
    .Platform(PlatformType.All)
    .ApplicationTarget(ApplicationTarget.ERP)
    .RouteUrl("/orders/123")
    .Build();

await notifications.SendViaHttpAsync(payload, cancellationToken);

Send WhatsApp Template

WhatsApp sends require an approved local WhatsApp template with a T2 template id.

csharp
var payload = NotificationBuilder.WhatsApp()
    .WithSubdomain("acme")
    .To("+201000000000")
    .WithTemplate(WhatsAppTemplateNames.SalesInvoiceEn)
    .WithTemplateParams(["Ahmed", "INV-1001"])
    .WithEntityId(invoiceId)
    .WithNotificationEntityType(NotificationEntityType.SalesInvoice)
    .Build();

await notifications.SendViaHttpAsync(payload, cancellationToken);

Use Queue Delivery

csharp
await notifications.SendViaQueueAsync(payload, cancellationToken);

Queue delivery publishes SendNotificationEvent. It confirms that the message was published, not that the provider accepted the notification.

Choosing Delivery Mode

Tenant Rules

ScenarioRequired context
Tenant notificationSet payload.Subdomain, call .WithSubdomain(...), or run inside a tenant context where ITenantContextManager.GetSubdomain() succeeds.
Source-system notificationSet payload.SourceSystem or configure NotificationsClient:SourceSystem.
Push notificationProvide payload UserIds and ensure the current context exposes a valid current user id.
Device token and Notification Center user APIsRequire X-Subdomain and X-User-Id context.

Optional Proxy Controllers

AddNotificationsClient(...) also adds controllers from the client package to the consuming app. Their default route prefix is api/notifications.

You can change it:

csharp
builder.Services.AddNotificationsClient(
    builder.Configuration,
    configureOptions: null,
    routePrefix: "api/internal/notifications");

The obsolete MapNotificationEndpoints() extension should not be used for new code. Controllers are registered by AddNotificationsClient(...).

Internal Documentation — Microtec