Nefarius.HttpClient.LiteDbCache 2.3.0

Prefix Reserved
dotnet add package Nefarius.HttpClient.LiteDbCache --version 2.3.0                
NuGet\Install-Package Nefarius.HttpClient.LiteDbCache -Version 2.3.0                
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="Nefarius.HttpClient.LiteDbCache" Version="2.3.0" />                
For projects that support PackageReference, copy this XML node into the project file to reference the package.
paket add Nefarius.HttpClient.LiteDbCache --version 2.3.0                
#r "nuget: Nefarius.HttpClient.LiteDbCache, 2.3.0"                
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
// Install Nefarius.HttpClient.LiteDbCache as a Cake Addin
#addin nuget:?package=Nefarius.HttpClient.LiteDbCache&version=2.3.0

// Install Nefarius.HttpClient.LiteDbCache as a Cake Tool
#tool nuget:?package=Nefarius.HttpClient.LiteDbCache&version=2.3.0                

Nefarius.HttpClient.LiteDbCache

GitHub Workflow Status Requirements Nuget Nuget

Adds disk-based response caching to HttpClient named instances using LiteDB.

Motivation

Sometimes a response from a remote HTTP service doesn't change frequently and fetching it again multiple times within a certain time span is wasteful and puts unnecessary delays on the caller. Offline caching to the rescue! However, manually storing and fetching responses gets verbose and complex fast, why not hide that complexity away and let IHttpClientFactory deal with it behind the scenes?

This library provides the extension method AddLiteDbCache you can chain your named HTTP client call with and specify an embedded database location to use for offline caching, no other code changes are required.

Why not use IMemoryCache?

The goal of the cache is to survive application/service restarts.

Why not use IDistributedCache?

This library is aimed at end-user clients where you wish to drag in as little dependency on 3rd party services as possible. An embedded database sitting in some folder does the trick there perfectly. It's usually not the brightest idea to require spinning up a Redis or MongoDB instance on a client's machine just to get some basic persisted storage capabilities. 😉

Features

  • Each named HTTP client gets its own backing cache database instance which is kept exclusively open by default throughout application lifetime for performance benefits.
  • Cached entries expiration (and exclusion) can be configured globally per named instance.

Some ideas

  • Per-request cache entry expiration options ( like MemoryCacheEntryOptions and similar) are technically possible; however due to how the HttpClient class is structured would require writing a ton of wrapper methods that supply these options to each HttpRequestMessage (which can not be conveniently overwritten); a task I am currently not fond of since it's a low priority anyway.
    • A great task for Source Generators!
  • The upstream Cache-Control header is currently completely ignored; it could be taken into consideration, if the user configured it to be honored.
  • Add some unit tests... maybe. Someday. 😅

How to use

Register one or more named HTTP clients with AddLiteDbCache. This example snippet registers a cached client that will query your public IP address using https://ifconfig.me/ and cache the response for 10 minutes to a local embedded database instance:

builder.Services.AddHttpClient("ifconfig", cfg =>
{
    cfg.BaseAddress = new Uri("https://ifconfig.me");
    
}).AddLiteDbCache(options =>
{
    // note: ensure that the path given already exists or you'll get a runtime exception
    options.ConnectionString = @"C:\Temp\ifconfig.db";
    options.CollectionName = "ifconfig-response-cache";
    options.EntryOptions.AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(10);
});

This cached named client can now be consumed like any other HttpClient wherever needed:

HttpClient client = _clientFactory.CreateClient("ifconfig");

HttpResponseMessage result = await client.GetAsync("/", ct);

string? publicIP = await result.Content.ReadAsStringAsync(ct);

If a cached entry exists, the response (headers, body content etc.) will be pulled and returned from the local database and no remote web request will be issued until the cache entry expires.

Advanced usage

Cache database access

Inject the ILiteDbCacheDatabaseInstances interface to get access to the LiteDatabase instances and other database management methods (cache purge and alike).

Documentation

Link to API docs.

Generating documentation

dotnet tool install --global Nefarius.Tools.XMLDoc2Markdown
dotnet publish -c Release -f net9.0 .\src\Nefarius.HttpClient.LiteDbCache.csproj
xmldoc2md .\src\bin\net9.0\publish\Nefarius.HttpClient.LiteDbCache.dll .\docs\

Sources & 3rd party credits

This library benefits from these awesome projects ❤ (appearance in no special order):

Product Compatible and additional computed target framework versions.
.NET net6.0 is compatible.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 was computed.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 is compatible.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 is compatible. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

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
2.3.0 404 11/20/2024
2.3.0-pre001 65 11/20/2024
2.2.2 351 7/9/2024
2.2.1 127 6/12/2024
2.2.0 277 6/12/2024
2.1.4 96 6/7/2024
2.1.3 98 6/7/2024
2.1.2 404 3/5/2024
2.1.1 105 2/27/2024
2.1.0-pre 115 2/24/2024
2.0.6 128 2/23/2024
2.0.5-pre 95 2/23/2024
2.0.4-pre 105 2/23/2024
1.9.0 127 2/22/2024
1.8.0 130 2/22/2024
1.7.1 114 2/21/2024
1.6.0 210 2/12/2024
1.5.1 133 1/25/2024
1.5.0 124 1/22/2024
1.4.0 170 1/22/2024
1.3.1 112 1/21/2024
1.3.0 116 1/21/2024
1.2.0 110 1/21/2024
1.1.0 115 1/21/2024
1.0.1 104 1/21/2024
1.0.0 130 1/21/2024