Interagieren mit Azure Cache for Redis mithilfe von .NET

Abgeschlossen

In der Regel verwendet eine Clientanwendung eine Clientbibliothek, um Anforderungen zu erstellen und Befehle für eine Redis Cache-Instanz auszuführen. Eine Liste von Clientbibliotheken finden Sie direkt auf der Seite zu Redis-Clients.

Ausführen von Befehlen in Redis Cache

Ein beliebter Hochleistungs-Redis-Client für die .NET-Sprache ist StackExchange.Redis. Das Paket ist über NuGet verfügbar und kann Ihrem .NET-Code mithilfe der Befehlszeile oder der IDE hinzugefügt werden. Im Folgenden finden Sie Beispiele für die Verwendung des Clients.

Herstellen einer Verbindung mit Redis Cache mit „StackExchange.Redis“

Denken Sie daran, dass wir die Hostadresse, die Portnummer und einen Zugriffsschlüssel verwenden, um eine Verbindung mit einem Redis-Server herzustellen. Azure bietet auch eine Verbindungszeichenfolge für einige Redis-Clients, die diese Daten zu einer einzigen Zeichenfolge bündelt. Diese sieht etwa wie folgt aus (wobei die Felder cache-name und password-here echte Werte enthalten):

[cache-name].redis.cache.windows.net:6380,password=[password-here],ssl=True,abortConnect=False

Sie können diese Zeichenfolge an StackExchange.Redis übergeben, um eine Verbindung mit dem Server herzustellen.

Beachten Sie, dass zwei zusätzliche Parameter am Ende angefügt werden:

  • ssl: Stellt sicher, dass die Kommunikation verschlüsselt ist.
  • abortConnection: Ermöglicht das Herstellen einer Verbindung, auch wenn der Server zum jeweiligen Zeitpunkt nicht verfügbar ist.

Es gibt andere optionale Parameter, die Sie an die Zeichenfolge anfügen können, um die Clientbibliothek zu konfigurieren.

Erstellen einer Verbindung

Das wichtigste Verbindungsobjekt in StackExchange.Redis ist die Klasse StackExchange.Redis.ConnectionMultiplexer. Dieses Objekt abstrahiert den Prozess beim Herstellen einer Verbindung mit einem Redis-Server (oder einer Gruppe von Servern). Dieses wurde für die effiziente Verwaltung von Verbindungen optimiert und muss bestehen bleiben, solange Sie auf den Cache zugreifen müssen.

Sie erstellen eine ConnectionMultiplexer-Instanz mit der statischen ConnectionMultiplexer.Connect- oder ConnectionMultiplexer.ConnectAsync-Methode, indem Sie eine Verbindungszeichenfolge oder ein ConfigurationOptions-Objekt übergeben.

Im Folgenden finden Sie ein einfaches Beispiel:

using StackExchange.Redis;
...
var connectionString = "[cache-name].redis.cache.windows.net:6380,password=[password-here],ssl=True,abortConnect=False";
var redisConnection = ConnectionMultiplexer.Connect(connectionString);

Wenn Sie über ConnectionMultiplexer verfügen, sollten Sie in erster Linie drei Dinge tun:

  • Zugreifen auf eine Redis-Datenbank.
  • Verwenden Sie die Herausgeber-/Abonnentfeatures von Redis, die sich außerhalb des Bereichs dieses Moduls befinden.
  • Greifen Sie für Wartungs- oder Überwachungszwecke auf einen einzelnen Server zu.

Zugreifen auf eine Redis-Datenbank

Der IDatabase-Typ stellt die Redis-Datenbank dar. Diesen können Sie mithilfe der Methode GetDatabase() abrufen:

IDatabase db = redisConnection.GetDatabase();

Tipp

Das von GetDatabase zurückgegebene Objekt ist ein einfaches Objekt und muss nicht gespeichert werden. Nur ConnectionMultiplexer muss erhalten werden.

Wenn Sie über das Objekt IDatabase verfügen, können Sie Methoden für die Interaktion mit dem Cache ausführen. Alle Methoden weisen synchrone und asynchrone Versionen auf, die Task-Objekte zurückgeben, damit sie mit den Schlüsselwörtern async und await kompatibel sind.

Im Folgenden finden Sie ein Beispiel für das Speichern eines Schlüssel-Wert-Paares im Cache:

bool wasSet = db.StringSet("favorite:flavor", "i-love-rocky-road");

Die Methode StringSet gibt bool zurück, was darauf hinweist, dass der Wert festgelegt (true) oder nicht festgelegt (false) wurde. Anschließend kann der Wert mit der Methode StringGet abgerufen werden:

string value = db.StringGet("favorite:flavor");
Console.WriteLine(value); // displays: ""i-love-rocky-road""

Abrufen und Festlegen von Binärwerten

Denken Sie daran, dass Redis-Schlüssel und -Werte binärsicher sind. Diese Methoden können verwendet werden, um Binärdaten zu speichern. Mithilfe impliziter Konvertierungsoperatoren für byte[]-Typen können Sie unkompliziert mit den Daten arbeiten:

byte[] key = ...;
byte[] value = ...;

db.StringSet(key, value);
byte[] key = ...;
byte[] value = db.StringGet(key);

StackExchange.Redis stellt Schlüssel mithilfe des Typs RedisKey dar. Diese Klasse weist implizite Konvertierungen in und von string und byte[] auf, sodass sowohl Text- als auch Binärschlüssel problemlos verwendet werden können. Werte werden durch den Typ RedisValue dargestellt. Wie bei RedisKey stehen Ihnen implizite Konvertierungen zur Verfügung, mit denen Sie string oder byte[] übergeben können.

Andere gängige Vorgänge

Die Schnittstelle IDatabase umfasst weitere Methoden für die Arbeit mit Redis Cache. Es gibt Methoden zum Arbeiten mit Hashes, Listen, Gruppen und sortierten Mengen.

Im Folgenden werden gängigere Beispiele vorgestellt, die mit einzelnen Schlüsseln arbeiten. Sie können den Quellcode für die Schnittstelle lesen, um die vollständige Liste anzuzeigen.

Methode Beschreibung
CreateBatch Erstellt eine Gruppe von Vorgängen, die an den Server als einzelne Einheit gesendet, jedoch nicht unbedingt als Einheit verarbeitet werden.
CreateTransaction Erstellt eine Gruppe von Vorgängen, die an den Server als einzelne Einheit gesendet und als einzelne Einheit auf dem Server verarbeitet werden.
KeyDelete Löscht das Schlüssel-Wert-Paar.
KeyExists Gibt zurück, ob der angegebene Schlüssel im Cache vorhanden ist.
KeyExpire Legt den Ablauf der Gültigkeitsdauer (Time to Live, TTL) eines Schlüssels fest.
KeyRename Benennt einen Schlüssel.
KeyTimeToLive Gibt die TTL für einen Schlüssel zurück.
KeyType Gibt die Zeichenfolgendarstellung des Typs des Werts zurück, der im Schlüssel gespeichert ist. Es können die folgenden verschiedenen Typen zurückgegeben werden: string, list, set, zset, hash.

Ausführen anderer Befehle

Das IDatabase-Objekt enthält die Methoden Execute und ExecuteAsync, mit denen Textbefehle an den Redis-Server übergeben werden können. Beispiel:

var result = db.Execute("ping");
Console.WriteLine(result.ToString()); // displays: "PONG"

Die Methoden Execute und ExecuteAsync geben ein RedisResult-Objekt zurück, das Daten mit zwei Eigenschaften enthält:

  • Resp2Type, die einen string zurückgibt, der den Typ des Ergebnisses angibt - STRING, INTEGER usw.
  • IsNull: Ein True/False-Wert, der erkannt wird, wenn das Ergebnis null lautet.

Anschließend können Sie ToString() in RedisResult verwenden, um den tatsächlichen Rückgabewert zu erhalten.

Sie können mit Execute beliebige unterstützte Befehle ausführen, beispielsweise können alle mit dem Cache verbundene Clients („CLIENT-LIST“) abgerufen werden:

var result = await db.ExecuteAsync("client", "list");
Console.WriteLine($"Type = {result.Resp2Type}\r\nResult = {result}");

Dadurch werden alle verbundenen Clients ausgegeben:

Type = BulkString
Result = id=9469 addr=16.183.122.154:54961 fd=18 name=DESKTOP-AAAAAA age=0 idle=0 flags=N db=0 sub=1 psub=0 multi=-1 qbuf=0 qbuf-free=0 obl=0 oll=0 omem=0 ow=0 owmem=0 events=r cmd=subscribe numops=5
id=9470 addr=16.183.122.155:54967 fd=13 name=DESKTOP-BBBBBB age=0 idle=0 flags=N db=0 sub=0 psub=0 multi=-1 qbuf=0 qbuf-free=32768 obl=0 oll=0 omem=0 ow=0 owmem=0 events=r cmd=client numops=17

Speichern von komplexeren Werten

Redis ist auf sicheren Binärzeichenfolgen aufgebaut, Sie können jedoch Objektdiagramme zwischenspeichern, indem Sie sie in ein Textformat serialisieren, in der Regel XML oder JSON. Nehmen Sie beispielsweise an, das GameStats-Objekt für unsere Statistiken sieht wie folgt aus:

public class GameStat
{
    public string Id { get; set; }
    public string Sport { get; set; }
    public DateTimeOffset DatePlayed { get; set; }
    public string Game { get; set; }
    public IReadOnlyList<string> Teams { get; set; }
    public IReadOnlyList<(string team, int score)> Results { get; set; }

    public GameStat(string sport, DateTimeOffset datePlayed, string game, string[] teams, IEnumerable<(string team, int score)> results)
    {
        Id = Guid.NewGuid().ToString();
        Sport = sport;
        DatePlayed = datePlayed;
        Game = game;
        Teams = teams.ToList();
        Results = results.ToList();
    }

    public override string ToString()
    {
        return $"{Sport} {Game} played on {DatePlayed.Date.ToShortDateString()} - " +
               $"{String.Join(',', Teams)}\r\n\t" + 
               $"{String.Join('\t', Results.Select(r => $"{r.team } - {r.score}\r\n"))}";
    }
}

Wir könnten die Bibliothek Newtonsoft.Json verwenden, um eine Instanz dieses Objekts in eine Zeichenfolge umzuwandeln:

var stat = new GameStat("Soccer", new DateTime(2019, 7, 16), "Local Game", 
                new[] { "Team 1", "Team 2" },
                new[] { ("Team 1", 2), ("Team 2", 1) });

string serializedValue = Newtonsoft.Json.JsonConvert.SerializeObject(stat);
bool added = db.StringSet("event:1950-world-cup", serializedValue);

Wir könnten diese abrufen und anhand des umgekehrten Vorgangs wieder in ein Objekt konvertieren:

var result = db.StringGet("event:2019-local-game");
var stat = Newtonsoft.Json.JsonConvert.DeserializeObject<GameStat>(result.ToString());
Console.WriteLine(stat.Sport); // displays "Soccer"

Bereinigen der Verbindung

Wenn die Verbindung nicht mehr benötigt wird, können Sie die ConnectionMultiplexer Dispose. Dadurch werden alle Verbindungen und die Kommunikation mit dem Server getrennt.

redisConnection.Dispose();
redisConnection = null;