C# SDK
The C# SDK is a strongly-typed client library for the EnergyCAP REST API. It provides auto-generated methods for every API endpoint, typed request/response models, and built-in JSON serialization — so you can work with EnergyCAP data as native C# objects.
Installation
Install from NuGet:
dotnet add package EnergyCap.Sdk
Or via the Package Manager Console:
Install-Package EnergyCap.Sdk
| Package | EnergyCap.Sdk |
| Current version | 8.2512.6600 |
| Target framework | .NET Standard 2.0 |
| Dependency | Microsoft.Rest.ClientRuntime >= 2.3.11 |
Compatibility
The SDK targets .NET Standard 2.0, which means it works with:
- .NET 6, 7, 8, 9, 10+
- .NET Core 2.0+
- .NET Framework 4.6.1+
Namespaces
| Namespace | Contains |
|---|---|
EnergyCap.Sdk |
The EnergyCapApi client class and interface |
EnergyCap.Sdk.Models |
All request body and response model classes |
EnergyCap.Sdk.Extensions |
EnergyCapApiClientFactory, EnergyCapEnvironments, and helper extensions |
Quick Start
1. Create a client
Use EnergyCapApiClientFactory to create an authenticated client. This factory configures the underlying HttpClient with the correct authorization headers and JSON serialization settings.
using EnergyCap.Sdk;
using EnergyCap.Sdk.Models;
using EnergyCap.Sdk.Extensions;
var settings = new EnergyCapClientSettingsApiKeyAuth
{
ApiKey = "YOUR_API_KEY"
};
var client = await EnergyCapApiClientFactory.CreateClientAsync(settings);
2. Make a request
// Get the first page of meters
var response = await client.GetMetersWithHttpMessagesAsync(
pageSize: 10, pageNumber: 1);
foreach (var meter in response.Body)
{
Console.WriteLine($"{meter.MeterId}: {meter.MeterCode} — {meter.MeterInfo}");
}
Client Configuration
EnergyCapClientSettingsApiKeyAuth supports the following options:
| Property | Type | Default | Description |
|---|---|---|---|
ApiKey |
string |
required | Your EnergyCAP API key |
EnvironmentUrl |
string |
Encoded in the API key | Override the target environment URL. Not recommended for hosted customers — the API key already encodes the correct environment. |
TimeoutSeconds |
int |
100 | Seconds before a request times out. Increase for bulk operations or large exports. |
UserAgentSuffix |
string |
null |
Appended to the User-Agent header on all requests. Useful for identifying your integration in server logs. |
HttpClientHandler |
HttpClientHandler |
null |
Custom handler for the underlying HttpClient (e.g. for proxy configuration). |
DelegatingHandlers |
DelegatingHandler[] |
null |
Pipeline handlers for logging, retry logic, or other cross-cutting concerns. |
Environment URLs
The SDK provides environment constants in EnergyCapEnvironments:
// Use a specific environment
var settings = new EnergyCapClientSettingsApiKeyAuth
{
ApiKey = "YOUR_API_KEY",
EnvironmentUrl = EnergyCapEnvironments.Implementation
};
See Environments for the full list of available environments.
Common Operations
Retrieve a single resource
// Get a specific meter by ID
var meter = await client.GetMeterAsync(meterId: 1234);
Console.WriteLine($"{meter.MeterCode}: {meter.MeterInfo}");
List resources with filters
// Get all electric meters
var meters = await client.GetMetersAsync(
filter: "commodityCode equals 'ELECTRIC'");
foreach (var meter in meters)
{
Console.WriteLine($"{meter.MeterId}: {meter.MeterCode}");
}
See Filters for the full filter syntax.
Create a resource
// Create a new account
var request = new AccountCreateRequest
{
AccountCode = "ACCT-NEW-001",
AccountInfo = "New Office Account",
VendorId = 10,
AccountTypeId = 1
};
var account = await client.CreateAccountAsync(body: request);
Console.WriteLine($"Created account {account.AccountId}");
Update a resource
// Update an existing meter
var update = new MeterEditRequest
{
MeterCode = "MTR-001-UPDATED",
MeterInfo = "Updated Meter Description"
};
var meter = await client.EditMeterAsync(meterId: 1234, body: update);
Delete a resource
await client.DeleteMeterAsync(meterId: 1234);
Pagination
List endpoints return paginated results. The SDK has two method variants for each list endpoint:
| Method | Returns | Use when |
|---|---|---|
GetMetersAsync(...) |
IList<MeterResponse> |
You only need the data and don’t care about page count |
GetMetersWithHttpMessagesAsync(...) |
HttpOperationResponse with .Body and .Headers |
You need pagination metadata (TotalPages, TotalNumberOfRecords, etc.) |
Iterating through all pages
var allMeters = new List<MeterResponse>();
int page = 1;
int totalPages = 1;
int pageSize = 500;
while (page <= totalPages)
{
var response = await client.GetMetersWithHttpMessagesAsync(
pageSize: pageSize, pageNumber: page);
allMeters.AddRange(response.Body);
totalPages = response.Headers.TotalPages.Value;
page++;
}
Console.WriteLine($"Retrieved {allMeters.Count} meters across {totalPages} pages");
Pagination headers
The WithHttpMessagesAsync response headers include:
| Header | Type | Description |
|---|---|---|
PageNumber |
int? |
Current page number |
PageSize |
int? |
Items per page |
TotalPages |
int? |
Total number of pages |
TotalNumberOfRecords |
int? |
Total matching records |
Parallel page fetching
Once you know the total page count from the first request, fetch remaining pages concurrently:
// Get first page to determine total pages
var firstResponse = await client.GetMetersWithHttpMessagesAsync(
pageSize: 500, pageNumber: 1);
var allMeters = new List<MeterResponse>(firstResponse.Body);
int totalPages = firstResponse.Headers.TotalPages.Value;
// Fetch remaining pages in parallel (limit concurrency to 5)
var semaphore = new SemaphoreSlim(5);
var tasks = Enumerable.Range(2, totalPages - 1).Select(async pageNum =>
{
await semaphore.WaitAsync();
try
{
var response = await client.GetMetersWithHttpMessagesAsync(
pageSize: 500, pageNumber: pageNum);
return response.Body;
}
finally
{
semaphore.Release();
}
});
var pages = await Task.WhenAll(tasks);
foreach (var page in pages)
{
allMeters.AddRange(page);
}
Console.WriteLine($"Retrieved {allMeters.Count} meters");
See Pagination for more details.
Field Reduction
Reduce response payload size by requesting only the fields you need:
// Only return meterId, meterCode, and meterInfo
var meters = await client.GetMetersAsync(
field: "meterId,meterCode,meterInfo");
See Field Reduction for include/exclude modes and more examples.
Error Handling
The SDK throws HttpOperationException when the API returns a non-success status code. The exception includes the full HTTP response for debugging:
using Microsoft.Rest;
try
{
var meter = await client.GetMeterAsync(meterId: 99999);
}
catch (HttpOperationException ex)
{
Console.WriteLine($"Status: {ex.Response.StatusCode}");
Console.WriteLine($"Body: {ex.Response.Content}");
// Common status codes:
// 400 — Bad request (check your parameters)
// 401 — Unauthorized (invalid or expired API key)
// 404 — Resource not found
// 429 — Rate limited (wait and retry)
}
Handling rate limits
try
{
var meters = await client.GetMetersAsync();
}
catch (HttpOperationException ex) when (ex.Response.StatusCode == System.Net.HttpStatusCode.TooManyRequests)
{
// Wait and retry after a delay
await Task.Delay(TimeSpan.FromSeconds(10));
var meters = await client.GetMetersAsync();
}
Advanced Configuration
Custom timeout for long-running operations
var settings = new EnergyCapClientSettingsApiKeyAuth
{
ApiKey = "YOUR_API_KEY",
TimeoutSeconds = 600 // 10 minutes for large bill imports
};
Adding a delegating handler for logging
public class LoggingHandler : DelegatingHandler
{
protected override async Task<HttpResponseMessage> SendAsync(
HttpRequestMessage request, CancellationToken cancellationToken)
{
Console.WriteLine($"{request.Method} {request.RequestUri}");
var response = await base.SendAsync(request, cancellationToken);
Console.WriteLine($" → {(int)response.StatusCode} {response.StatusCode}");
return response;
}
}
var settings = new EnergyCapClientSettingsApiKeyAuth
{
ApiKey = "YOUR_API_KEY",
DelegatingHandlers = new DelegatingHandler[] { new LoggingHandler() }
};
Proxy configuration
var handler = new HttpClientHandler
{
Proxy = new WebProxy("http://proxy.example.com:8080"),
UseProxy = true
};
var settings = new EnergyCapClientSettingsApiKeyAuth
{
ApiKey = "YOUR_API_KEY",
HttpClientHandler = handler
};
Legacy: Credential Authentication
var settings = new EnergyCapClientSettingsCredentialAuth
{
DataSource = "your_datasource",
Username = "your_username",
Password = "your_password",
EnvironmentUrl = EnergyCapEnvironments.Implementation,
TimeoutSeconds = 300
};
var client = await EnergyCapApiClientFactory.CreateClientAsync(settings);
With credential auth, you must set EnvironmentUrl explicitly because there is no API key to derive it from.