API Client
Bulletcode.NET provides a built-in service for communicating with a REST API. In order to use it, add a reference to the Bulletcode.Client package and call the AddApiClient() extension method of IServiceCollection:
services.AddApiClient();
The ApiClientOptions class contains settings for the API client. They can be changed by passing a callback to the AddApiClient() method, or by adding a ApiClientOptions section to the appsettings.json file.
BaseAddress— specifies the base URL for the API.Timeout— specifies the default timeout for API requests. The default value is 30 seconds.AcceptedRetryAfter— specifies the default delay after which a request is resent after receiving anAcceptedresponse. The default value is 10 seconds.
The API client uses the same JSON serialization options as the API server implemented using Bulletcode.Web.Core. See JSON Serialization for more information.
When a request fails and the server returns an ErrorResult response, the API client throws an ErrorResultException containing the information about the error, in addition to the standard properties of the HttpRequestException. Otherwise, a plain HttpRequestException is thrown. See API Errors for more information.
IApiClient service
The IApiClient service can be used to perform requests to the API. It contains the following methods:
GetAsync()— performs aGETrequest to the given URL, with optional query string parameters, and deserializes the JSON response as an object.DownloadAsync()— performs aGETrequest to the given URL, with optional query string parameters, and returns the response as a byte array.PostAsync()— performs aPOSTrequest to the given URL. The object passed as the request body is serialized into JSON. A byte array can also be specified as the request body. When the result type is specified, the response is deserialized as an object of the given type; otherwise, the response is ignored.PutAsync()— performs aPUTrequest to the given URL. This method is analogous toPostAsync().PatchAsync()— performs aPATCHrequest to the given URL. This method is analogous toPostAsync().DeleteAsync()— performs aDELETErequest to the given URL. This method doesn’t use any request body and ignores the response body.
The following options can be specified for all requests:
Authentication— the type of the authentication token to use (see API Authentication below). By default, the access token is used.Timeout— an optional custom timeout for the request. If not specified, the value fromApiClientOptionsis used.HandleAcceptedResponse— when set totrue, the API client automatically resends the request after receiving a response withAcceptedstatus code. See Background Jobs for information about handling such requests on the server side. The default value isfalse.AcceptedRetryAfter— an optional delay after which a request is resent. If not specified, the value fromApiClientOptionsis used.
Additional options for DownloadAsync():
Accept— the optionalAcceptheader; anHttpRequestExceptionis thrown when the content type of the server’s response doesn’t match the specified value.RangeFrom— the optional start of the range to download.RangeTo— the optional end of the range to download.
Additional options for PostAsync() and PutAsync() methods with binary body:
ContentType— the content type of the request. By default,"application/octet-stream"is used. The server should be configured to access the request data for the specified content type as binary data (see MVC for more information).
Query string helper
The QueryStringSerializer helper class contains the following static methods for handling NameValueCollection objects:
Serialize()— converts an object into aNameValueCollectionin such way that it can be deserialized from the query string on the server side.DateTimevalues are serialized using the"yyyy-MM-dd"format;enumvalues are serialized as numbers;nullvalues are ignored; all other values are converted to culture invariant strings. This method is useful when performing aGETrequest with a complex query string.ToString()— converts aNameValueCollectionto a properly escaped string, including the leading'?'. An empty string is returned if the collection is empty.
API authentication
In order for the API authentication to work, the application must provide a service implementing the IAuthenticationProvider interface. It has a single method, AuthenticateAsync(), which should add the authentication header to the request.
The API client supports two types of authentication tokens: the access token represents an authenticated user, and the optional refresh token can be used to obtain a new access token when it expires. By default, the access token is used. The Authentication option passed to a method of the IApiClient can be used to select the refresh token or skip authentication.
Bulletcode.Client provides two classes that can be used as base classes for authentication providers:
AuthenticationProvidercan be used for applications which use both the access token and the refresh token. When an API request is being made, this class checks if the access token is still valid and refreshes it if it has expired. This is useful in case of mobile application, which can be inactive for an extended period of time.AuthenticationServiceis a background service, which periodically refreshes the access token to prevent it from expiring. It doesn’t use a separate refresh token. This is useful for desktop applications which can maintain a constant connection to the server.
Both classes call the abstract RefreshTokensAsync() method when the access token needs to be refreshed. This method should either call SetToken() and return true when a new token or pair of tokens are obtained, or call ClearToken() and return false if the token couldn’t be refreshed.
The class which inherits AuthenticationService should be registered as a singleton and as a hosted service, for example by calling:
services.AddHostedService( provider => provider.GetRequiredService<AccountService>() );
See also Token authentication for more information about implementing authentication for the API server.