PxApi is a .NET 9.0 Web API for accessing PX statistical datasets. It provides table listings, table metadata and data retrieval with flexible dimension filtering and caching across multiple storage backends (local file system, Azure File Share, Azure Blob Storage).
- Table listing with paging (
/tables/{database}) - Table metadata in JSON-stat 2.0 (
/meta/{database}/{table}) - Data retrieval with filter semantics (code, range, positional) via GET query parameters or POST body (
/data/{database}/{table}) - Content negotiation (JSON-stat 2.0 or CSV) using the
Acceptheader - Cache management endpoints (database level and single table) (
/cache/{database}//cache/{database}/{id}) - Global and per-database caching (file lists, metadata, data, last updated timestamps, grouping metadata)
- Feature flags (Swagger visibility of cache endpoints)
- Controller-specific API key authentication for all endpoints
- Multiple storage types: Mounted (local / network), Azure File Share, Azure Blob Storage
- Query size limits returning HTTP 413 when exceeded
- Swagger / OpenAPI documentation with custom schema & document filters
- HEAD and OPTIONS support for discoverability and CORS pre-flight
GET /databases?lang=fi
Returns a list of available databases with their metadata.
Authentication: Requires valid API key in X-Databases-API-Key header when databases authentication is enabled.
Query parameters:
lang(optional, defaultfi): Language used for name and description resolution.
Responses:
200 OKJSON array containing database listing items400 Bad Requestrequested language not supported401 Unauthorizedmissing / invalid API key (when authentication configured)
Additional methods:
HEAD /databasesvalidates existence of the database collection resourceOPTIONS /databasesreturns Allow header (GET,HEAD,OPTIONS)
GET /tables/{database}?lang=fi&page=1&pageSize=50
Returns a paged list of tables ordered by PX file name.
Authentication: Requires valid API key in X-Tables-API-Key header when tables authentication is enabled.
Query parameters:
lang(optional, defaultfi): Language used for metadata resolution.page(optional, >=1, default1)pageSize(optional, 1-100, default50)
Responses:
200 OKJSON body containing table listing and paging info400 Bad Requestinvalid paging values or unsupported language401 Unauthorizedmissing / invalid API key (when authentication configured)404 Not Founddatabase missing
Additional methods:
HEAD /tables/{database}validates existence and paging valuesOPTIONS /tables/{database}returns Allow header (GET,HEAD,OPTIONS)
GET /meta/{database}/{table}?lang=fi
Returns JSON-stat 2.0 metadata (structure only, no data filtering).
Authentication: Requires valid API key in X-Metadata-API-Key header when metadata authentication is enabled.
Query parameters:
lang(optional): If omitted uses table default language
Responses:
200 OKJSON-stat 2.0 metadata400 Bad Requestlanguage not available401 Unauthorizedmissing / invalid API key (when authentication configured)404 Not Founddatabase or table missing500 Internal Server Errorunexpected error
Additional methods:
HEAD /meta/{database}/{table}existence & language validation onlyOPTIONS /meta/{database}/{table}returns Allow header (GET,HEAD,OPTIONS)
GET /data/{database}/{table}?filters=TIME:from=2020&filters=TIME:to=2024&filters=REGION:code=001,002
Retrieves data values applying filters to dimensions. Content negotiation support for json and csv:
Authentication: Requires valid API key in X-Data-API-Key header when data authentication is enabled.
Accept: application/jsonor*/*-> JSON-stat 2.0Accept: text/csv-> CSV format with containing table description, selected value names and data.
####CSV Export Structure:####
- Table description as A1 cell header
- Stub dimensions (rows) and heading dimensions (columns) based on PX file metadata
- Automatic filtering of single-value elimination/total dimensions for cleaner output
- Formatting of missing values using PX-standard dot codes (
.,..,..., etc.) - Culture-invariant number formatting with period as decimal separator
Filter syntax (GET query parameters):
Each filter supplied via repeated filters query parameter: dimensionCode:filterType=value
Supported filterType values:
codeone or many codes (comma-separated), supports*wildcardfromlower bound for range (supports wildcard*inside value)toupper bound for range (supports wildcard*inside value)firstselects first N positions (positive integer)lastselects last N positions (positive integer)
Rules:
- One filter per dimension.
- Wildcard
*matches zero or more characters in code/from/to values.
POST alternative:
POST /data/{database}/{table} with JSON body mapping dimension codes to filter objects.
Example body:
{
"TIME": { "type": "from", "query": ["2020"] },
"REGION": { "type": "code", "query": ["001", "002"] }
}Query parameters (POST):
langoptional language (defaults to table default)
Responses (GET & POST):
200 OKJSON-stat 2.0 object or CSV text400 Bad Requestinvalid filters / language not available401 Unauthorizedmissing / invalid API key (when authentication configured)404 Not Founddatabase or table missing406 Not AcceptableunsupportedAcceptheader value413 Payload Too Largerequest cell count exceeds configured limit415 Unsupported Media Type(POST invalid content type)
Additional methods:
HEAD /data/{database}/{table}?lang=fiexistence & language validation onlyOPTIONS /data/{database}/{table}returns Allow header (GET,POST,HEAD,OPTIONS)
Requires feature flag CacheController = true and valid API key when authentication is enabled.
Authentication: Requires valid API key in X-Cache-API-Key header when cache authentication is enabled.
DELETE /cache/{database}clears all cache entries (file list, metadata, data, last updated) for a database.DELETE /cache/{database}/{id}clears all cache entries for a single table.
Responses:
200 OKsuccess message401 Unauthorizedmissing / invalid API key (when authentication configured)404 Not Founddatabase or table not found500 Internal Server Errorunexpected error
Filter object structure:
{
"<DIMENSION_CODE>": {
"type": "code | from | to | first | last",
"query": ["value1", "value2"]
}
}Notes:
first/lastuse a single positive integer value inquery.from/touse one value each.codecan contain multiple codes.
Provided via appsettings.json.
Key sections:
RootUrlBase absolute URL used for generated links & OpenAPI servers.DataBasesArray of database definitions:TypeOne ofMounted,FileShare,BlobStorageIdUnique idCacheConfigPer-database cache sizing overridesCustomBackend-specific connection settings
CacheGlobal memory cache sizing (applies toMemoryCache):MaxSizeBytes(default 524288000)DefaultDataCellSizeDefaultUpdateTaskSizeDefaultTableGroupSizeDefaultFileListSizeDefaultMetaSize
QueryLimitsRequest size limits:JsonMaxCells(used for any future JSON minimal format endpoints)JsonStatMaxCells(enforced in current data endpoints; exceeding returns 413)
FeatureManagementFeature flags (e.g.CacheController)AuthenticationController-specific API key settings - see Authentication section belowOpenApiMetadata (contact, license) for Swagger document
PxApi supports controller-specific API key authentication. Each controller can be independently configured with its own API key and header name. Authentication is optional and disabled by default.
{
"Authentication": {
"Cache": {
"Key": "your-cache-api-key",
"HeaderName": "X-Cache-API-Key"
},
"Databases": {
"Key": "your-databases-api-key",
"HeaderName": "X-Databases-API-Key"
},
"Tables": {
"Key": "your-tables-api-key",
"HeaderName": "X-Tables-API-Key"
},
"Metadata": {
"Key": "your-metadata-api-key",
"HeaderName": "X-Metadata-API-Key"
},
"Data": {
"Key": "your-data-api-key",
"HeaderName": "X-Data-API-Key"
}
}
}- Authentication is optional - if no key is provided for a controller, that controller's endpoints will not require authentication
- Each controller can be independently configured
- When configured, clients must provide the correct API key in the specified header
- API keys are compared directly with the configured values
- Custom header names can be configured for each controller (defaults shown above)
- Environment variables can override configuration values using the pattern:
Authentication__<Controller>__<Property>(e.g.,Authentication__Data__Key)
- Cache:
X-Cache-API-Key - Databases:
X-Databases-API-Key - Tables:
X-Tables-API-Key - Metadata:
X-Metadata-API-Key - Data:
X-Data-API-Key
You can configure authentication via environment variables:
# Example: Configure Data controller authentication
Authentication__Data__Key=your-data-api-key
Authentication__Data__HeaderName=X-Custom-Data-Key
# Example: Configure Databases controller authentication
Authentication__Databases__Key=your-databases-api-key
- Store API keys securely and never commit them to version control
- Use environment variables or secure configuration management for production deployments
- Rotate API keys periodically
- Use HTTPS in production to protect API keys in transit
- Consider using different API keys for different controllers based on access requirements
- Ensure API keys are sufficiently long and randomly generated for security
Global cache size limit controlled via Cache.MaxSizeBytes. Individual item sizes use defaults above or per-database overrides. Cached entities:
- File lists
- Metadata objects
- Data arrays
- Last updated timestamps (per PX file)
- Groupings (if implemented via
CacheConfig.Groupings)
- Mounted (local / network path) direct file access
- Azure File Share via Azure Storage SDK
- Azure Blob Storage via Azure Storage SDK
Specify desired format with Accept header:
application/json-> JSON-stat 2.0text/csv-> Table description, selected value names and data in CSV format*/*or empty -> JSON-stat 2.0
Central exception handling returns standardized 500 responses and 400 responses for invalid requests. Specific endpoints return 400/404/406/413/415 as described.
- Configure
appsettings.jsonwith databases, cache settings, and optionally authentication. - Run the application.
- Access Swagger UI at root (
/) for interactive documentation (openapi/document.json).
Apache License 2.0. See docs/LICENSE.md.