A better, smarter, and faster way to interact with Redis. While RediJson allows access to JSON models, direct hash calls remain the best way to maximize performance on Redis. Easily perform complex queries using LINQ and partially load/update your models.
$ dotnet add package Redis.SharpRedisSharp is a powerful, asynchronous C# library designed to simplify interactions with Redis, providing a robust model-based abstraction layer. Built on top of StackExchange.Redis, it offers features like automatic indexing, model hydration, unique constraints, and flexible querying, making it ideal for managing complex data structures in Redis.
IAsyncModel and manage them seamlessly.HydrateAsync() to populate models, including nested IAsyncModel instances with the [Hydrate] attribute.Text, Numeric, Tag).[Unique] attribute.RedisQuery system for searching and filtering data.AsyncLink and AsyncLinks components.Available on Nuget
dotnet add package Redis.Sharp
Initialize the RedisSingleton with your Redis server details:
RedisSingleton.Initialize("localhost", 6379, "yourpassword");
Implement IAsyncModel to create a Redis-backed model:
Note Profile or any other IAsyncModels nested within a IAsyncModel will be instantiated at the time the model is created.
using RedisSharp;
public class User : IAsyncModel
{
public string Id { get; set; }
public DateTime CreatedAt { get; set; }
[Unique]
public string Email { get; set; }
[Indexed(IndexType.Text)]
public string Name { get; set; }
[Hydrate]
public Profile Profile { get; set; }
public string IndexName() => "users";
}
public class Profile : IAsyncModel
{
public string Id { get; set; }
public DateTime CreatedAt { get; set; }
public string Bio { get; set; }
public string IndexName() => "profiles";
}
Models are created and stored in Redis using RedisRepository:
var user = new User { Id = "user1", Email = "user@example.com", Name = "John Doe", CreatedAt = DateTime.UtcNow };
var result = await RedisRepository.CreateAsync(user);
if (result.Succeeded)
{
Console.WriteLine("User created successfully!");
}
Models are loaded unhydrated by default. Use .HydrateAsync(); to populate them:
var user = await RedisRepository.LoadAsync<User>("user1");
// Hydrate specific properties
await user.HydrateAsync(u => u.Email, u => u.Name);
// Hydrate the entire model, including nested [Hydrate]-marked IAsyncModels (e.g., Profile)
await user.HydrateAsync();
Console.WriteLine($"User: {user.Name}, Profile Bio: {user.Profile.GetAsync().Result.Bio}");
Use the [Hydrate] attribute to fully load all of a nested IAsyncModels contents; however be warned that this is a recursive action that also loads it's own nested IAsyncModels
Save data effortlessly using:
myModel.PushAsync(s => s.MyProperty, s => s.MyOtherProperty);
To prevent accidental overwrites with incomplete or uninitialized models, PushAsync without selectors is intentionally restricted, ensuring only specified properties are saved.
Use RedisQuery to search and filter models:
var query = new RedisQuery<User>(s => s.Name == "John" && s => s.Name != "Benny")
.Where(s => s.Email == "user@example.com"));
var users = await query.ToListAsync();
foreach (var u in users)
{
Console.WriteLine($"Found: {u.Name}");
}
typical usage:
var myModel = RedisRepository.Query<MyModel>(s => s.MyProperty == xyz).ToListAsync();
Optional query extensions
Return the first item (if any) .FirstOrDefaultAsync()
This will select specific properties to be pre-populated by the server .SelectAsync(s => s.ItemA, s => s.ItemB)
ToPagedList(pageNumber, pageSize)
PagedSelectedAsync(pageNumber, pageSize)
AnyAsync(s => s.IsValid)
Use AsyncLink for single references and AsyncLinks for collections:
var profile = new Profile { Id = "profile1", Bio = "Software Engineer", CreatedAt = DateTime.UtcNow };
await RedisRepository.CreateAsync(profile);
await user.Profile.SetAsync(profile);
var loadedProfile = await user.Profile.GetAsync();
loadedProfile.HydrateAsync(s => s.Bio);
Console.WriteLine(loadedProfile.Bio); // "Software Engineer"
Delete models and their associated data:
await user.DeleteAsync(); // Cleans up all nested models and links
HydrateAsync to fetch data.[Indexed] to mark searchable properties; specify IndexType for custom behavior.PushAsync, HydrateAsync for collections) to minimize round-trips.PushResult or ModelCreationResult for operation success.Feel free to submit issues or pull requests! Ensure all contributions align with the project's coding standards and include tests where applicable.