SYT.Fiskaly
1.0.0-rc.9
dotnet add package SYT.Fiskaly --version 1.0.0-rc.9
NuGet\Install-Package SYT.Fiskaly -Version 1.0.0-rc.9
<PackageReference Include="SYT.Fiskaly" Version="1.0.0-rc.9" />
<PackageVersion Include="SYT.Fiskaly" Version="1.0.0-rc.9" />
<PackageReference Include="SYT.Fiskaly" />
paket add SYT.Fiskaly --version 1.0.0-rc.9
#r "nuget: SYT.Fiskaly, 1.0.0-rc.9"
#:package SYT.Fiskaly@1.0.0-rc.9
#addin nuget:?package=SYT.Fiskaly&version=1.0.0-rc.9&prerelease
#tool nuget:?package=SYT.Fiskaly&version=1.0.0-rc.9&prerelease
SYT.Fiskaly
SYT.Fiskaly is a production-oriented .NET SDK for Fiskaly SIGN DE v2 and the Fiskaly
Management API.
It provides strongly typed clients, resilient HTTP pipelines, typed identifiers, and configuration validation for:
- TSS lifecycle via
ITssClient - Client lifecycle via
IClientManagementClient - Transactions via
ITransactionClient - Exports via
IExportClient - Management API organizations via
IOrganizationClient - Management API API keys via
IApiKeyClient - Authentication via
IFiskalyAuthenticationService - Scoped per-organization credentials via
IFiskalyCredentialScopeFactory - Raw transaction response bodies via
TxResponse.RawJson, for fiscal audit
Package
- Package ID:
SYT.Fiskaly - Current channel:
1.0.0-rc.5 - Target framework:
net10.0 - License:
MIT - Repository:
https://github.com/i7aket/SYT.Fiskaly - NuGet debugging support: portable PDBs via
.snupkg, XML docs, and Source Link-compatible repository metadata
Installation
dotnet add package SYT.Fiskaly --prerelease
Configuration
Minimum infrastructure settings:
{
"Fiskaly": {
"BaseUrl": "https://kassensichv-middleware.fiskaly.com/api/v2/",
"ManagementBaseUrl": "https://dashboard.fiskaly.com/api/v0/"
}
}
Default ApiKey / ApiSecret are optional. Configure them only when the process should have a
global fallback credential pair. If credentials are supplied later via
IFiskalyCredentialScopeFactory, the SDK can start without default secrets.
Optional transport validation flags:
Fiskaly:AllowHttpForPrivateNetworks=trueallowshttp://for RFC1918/link-local/private LAN hosts.Fiskaly:AllowHttpForPublicHosts=trueallowshttp://for public hosts. Keep this off unless you intentionally run an insecure proxy endpoint.
Optional per-client overrides are available under:
Fiskaly:AuthClientFiskaly:AdminClientFiskaly:TssClientFiskaly:TransactionClientFiskaly:ExportClientFiskaly:ClientManagementClientFiskaly:OrganizationClientFiskaly:ApiKeyClient
Registration
using SYT.Fiskaly;
builder.Services.AddFiskaly(builder.Configuration);
Quick Start
using SYT.Fiskaly.SignDE.Tss;
using SYT.Fiskaly.SignDE.Tss.ValueObjects;
ITssClient tssClient = app.Services.GetRequiredService<ITssClient>();
TssId tssId = TssId.New();
var created = await tssClient.CreateTssAsync(tssId, cancellationToken: ct);
Console.WriteLine($"Created TSS: {created.Id}");
Control Plane Example
This is the recommended pattern for control-plane services that create managed organizations, issue runtime API keys, and then operate in the scope of those runtime credentials.
using SYT.Fiskaly.Authentication;
using SYT.Fiskaly.Authentication.Credentials;
using SYT.Fiskaly.Authentication.ValueObjects;
using SYT.Fiskaly.Management.ApiKeys;
using SYT.Fiskaly.Management.ApiKeys.Requests;
using SYT.Fiskaly.Management.Organizations;
IOrganizationClient organizations = sp.GetRequiredService<IOrganizationClient>();
IApiKeyClient apiKeys = sp.GetRequiredService<IApiKeyClient>();
IFiskalyCredentialScopeFactory scopes = sp.GetRequiredService<IFiskalyCredentialScopeFactory>();
OrganizationId organizationId = OrganizationId.From("9b8ad703-b85c-4dec-882d-2dc7525ada3f");
var createdKey = await apiKeys.CreateApiKeyAsync(
organizationId,
new CreateApiKeyRequest
{
Name = "runtime-berlin-register-01"
},
ct);
using IDisposable scope = scopes.BeginScope(new ApiKeyCredentials(
ApiKey.From(createdKey.Key ?? throw new InvalidOperationException("API key was not returned.")),
ApiSecret.From(createdKey.Secret ?? throw new InvalidOperationException("API secret was not returned."))));
var runtimeOrganization = await organizations.GetOrganizationAsync(organizationId, ct);
Console.WriteLine($"Scoped organization lookup: {runtimeOrganization.Name}");
SIGN DE Transaction Example
using SYT.Fiskaly.SignDE.Clients.ValueObjects;
using SYT.Fiskaly.SignDE.Common;
using SYT.Fiskaly.SignDE.Transactions;
using SYT.Fiskaly.SignDE.Transactions.Enums;
using SYT.Fiskaly.SignDE.Transactions.Requests;
using SYT.Fiskaly.SignDE.Transactions.Schemas;
using SYT.Fiskaly.SignDE.Transactions.ValueObjects;
using SYT.Fiskaly.SignDE.Tss.ValueObjects;
ITransactionClient transactionClient = sp.GetRequiredService<ITransactionClient>();
TssId tssId = TssId.From("d9ee9052-fd45-4846-af24-818d10353cdb");
ClientId clientId = ClientId.From("0d918f2a-3c47-4662-a665-8e565d61109b");
TxId txId = TxId.New();
StartTransactionRequest start = new()
{
ClientId = clientId,
Metadata = MetadataCollection.Empty.Add("cashpoint", "POS-01")
};
_ = await transactionClient.StartTransactionAsync(tssId, txId, start, ct);
Receipt receipt = new()
{
ReceiptType = ReceiptType.Receipt,
AmountsPerVatRate =
[
new VatRateAmount
{
VatRate = VatRate.Normal,
Amount = MoneyAmount.Create(45.00m, CurrencyCode.EUR)
}
],
AmountsPerPaymentType =
[
new PaymentTypeAmount
{
PaymentType = PaymentType.Cash,
Amount = MoneyAmount.Create(45.00m, CurrencyCode.EUR)
}
]
};
FinishTransactionRequest finish = FinishTransactionRequest.CreateReceipt(
clientId,
receipt,
MetadataCollection.Empty.Add("cashpoint", "POS-01"));
var finished = await transactionClient.FinishTransactionAsync(tssId, txId, finish, ct);
Console.WriteLine($"Tx finished: {finished.Id}, qr={finished.QrCodeData}");
TEST and LIVE Environments
- Fiskaly API keys are organization-scoped and environment-scoped.
TESTandLIVEare separate operational environments.- New managed organizations are typically provisioned and exercised in
TESTfirst. - Moving to
LIVEis an explicit Management API and operational step. It is not an automaticTEST -> LIVEpromotion. - Runtime services should use credentials issued for the exact target organization and environment.
Validation Rules
Fiskaly:ApiKeyandFiskaly:ApiSecretare optional as a pair.- If one is configured, the other must also be configured.
- When
Fiskaly:ApiSecretis set, it must be exactly 43 alphanumeric characters. BaseUrlandManagementBaseUrlmust be absolute and end with/.- HTTPS is required by default.
- HTTP is allowed only for localhost, or private networks when
AllowHttpForPrivateNetworks=true. - HTTP for public hosts is allowed only when
AllowHttpForPublicHosts=true.
Default Resilience Profiles
| Client | Timeout (s) | RetryCount | CircuitBreakerThreshold | CircuitBreakerDuration (s) |
|---|---|---|---|---|
AuthClient |
10 | 2 | 0 | 10 |
AdminClient |
10 | 1 | 5 | 30 |
TssClient |
30 | 3 | 5 | 60 |
TransactionClient |
45 | 5 | 10 | 90 |
ExportClient |
120 | 2 | 3 | 240 |
ClientManagementClient |
30 | 3 | 5 | 60 |
OrganizationClient |
30 | 3 | 5 | 60 |
ApiKeyClient |
30 | 3 | 5 | 60 |
Runtime Override in Code
using SYT.Fiskaly;
using SYT.Fiskaly.Configuration;
builder.Services.AddFiskaly(builder.Configuration, configure: cfg =>
{
cfg.TransactionClient.UseHighResilience();
cfg.ApiKeyClient.DisableResilience();
});
Error Handling
Production usage typically maps SDK exceptions to domain-level failures:
FiskalyApiExceptionFiskalyTimeoutExceptionFiskalyCredentialsNotConfiguredExceptionFiskalyException
Release Notes
See CHANGELOG.md for the current release history.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- Microsoft.AspNetCore.WebUtilities (>= 10.0.2)
- Microsoft.Extensions.Configuration.Abstractions (>= 10.0.2)
- Microsoft.Extensions.Http (>= 10.0.2)
- Microsoft.Extensions.Http.Resilience (>= 10.2.0)
- Microsoft.Extensions.Logging.Abstractions (>= 10.0.2)
- Microsoft.Extensions.Options.ConfigurationExtensions (>= 10.0.2)
- Microsoft.Extensions.Options.DataAnnotations (>= 10.0.2)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 1.0.0-rc.9 | 141 | 8/22/2026 |
| 1.0.0-rc.8 | 83 | 8/12/2026 |
| 1.0.0-rc.7 | 94 | 8/6/2026 |
| 1.0.0-rc.6 | 85 | 8/4/2026 |
| 1.0.0-rc.5 | 82 | 8/1/2026 |
| 1.0.0-rc.4 | 480 | 4/12/2026 |
| 1.0.0-rc.3 | 96 | 4/11/2026 |
| 1.0.0-rc.2 | 161 | 3/10/2026 |
| 1.0.0-rc.1 | 101 | 2/28/2026 |
Release candidate naming the SIGN DE export for what it is, and refusing a request fiskaly would silently
reinterpret.
Breaking. This is an RC and the changes are source-level; the compiler points at every one.
- DsfinvkArchive is now ExportArchive, in SYT.Fiskaly.SignDE.Exports. The SIGN DE export endpoints do not
produce DSFinV-K data: fiskaly's own spec describes the payload as "the SMAERS initialization information,
the signed log messages, and the certificates to verify them", and a real archive holds ASN.1 .log records,
X.509 certificates and one info.csv - no DSFinV-K CSVs at all. DSFinV-K is a separate fiskaly product on a
separate host. The old name sent at least one integrator looking for an API that does not exist here.
- The three request classes collapse into one ExportRequest. fiskaly models this endpoint as a single flat
querystring of nine optional parameters; the split was an SDK invention, and two of the three emitted
identical requests whenever only a counter range was set.
- TriggerFullExportAsync / TriggerClientExportAsync / TriggerLogExportAsync collapse into TriggerExportAsync.
All three called the same endpoint and differed only in a log line.
- client_id is now enforced as exclusive. fiskaly documents that every other query parameter is ignored when
it is set, and DsfinvkFullExportRequest let you combine them - so an export could silently cover a different
range than the caller asked for. Use ExportRequest.ForClient(clientId), which cannot be built wrong.
- Request validation now raises FiskalyValidationException, inside the FiskalyException hierarchy. The three
range checks that already existed threw a bare InvalidOperationException and surfaced as HTTP 500 in
consuming applications - the same defect rc.7 fixed for downloads.
- The DSFinV-K segment model is removed: DsfinvkSegment, DsfinvkSegmentType, IDsfinvkVersionStrategy,
DsfinvkV2SegmentStrategy, UnknownDsfinvkSegment, MasterDataSegment, TransactionSegment and
CashPointClosingSegment, along with the strategy parameter on DownloadExportAsync. It classified archive
entries by substring on the file name and matched nothing a real export contains - every entry of the
bundled sample fell through to Unknown - while OpenJsonDocument could only throw on ASN.1 records.
Downloads now return the bytes verbatim, which is what an archived journal has to be.
SYT.Fiskaly.Dsfinvk.Enums is untouched: BusinessCaseType and DsfinvkPaymentType are genuine DSFinV-K
taxonomy and are named correctly.