Redis i Python – dobrze dobrana para #9

Cześć.

Za nami ogrom wiedzy podzielonej na osiem wpisów. Dzisiejszy, dziewiąty, dotyczyć będzie pewnej bardzo przydatnej funkcjonalności Redisa. Pokaże jak skonfigurować i używać notyfikacja. Standardowo, jak w każdym poprzednim artykule, tak i w tym będę opierał się na wiedzy która już została przeze opublikowana. Zachęcam więc do zapoznania się z poprzednimi wpisami:

Czy są notyfikacje redisowe?

Notyfikacje to powiadomienia które wysyła Redis (via publish na konkretnym kanale) generowane w momencie pracy na innych kluczach. Brzmi zawile, więc może przykład: możemy tak skonfigurować Redisa by ten robił publish na pewny kanał z informacją o np. usunięciu jakiegoś klucza. Albo z dodaniem elementu do listy. Albo z dodaniem elementu do strumienia. Możliwości jest dużo, zbyt dużo by pokazać każdą z nich w tym wpisie, więc jest on bardziej przysłowiową wędką niż rybą.

Kanały

Subskrybować możemy się na kanały których nazwy wyglądają tak:

1
2
__keyspace@0__:mykey
__keyevent@0__:del

pierwszy, zwany „key-space notification” po subskrypcji pozwoli na odbieranie wiadomości na temat konkretnego klucza (w przykładzie mykey). Drugi, zwany „key-event notification” będzie dostarczał informacje dla podanego typu operacji (w przykładzie dla del). Nie trudno się domyśleć że jeśli usuniemy klucz o nazwie „mykey” to na pierwszym kanale dostaniemy wiadomość o treści „del” a na drugim „mykey”.

Konfiguracja

Notyfikacje można włączyć na dwa sposoby. Jeden z nich jest trwały, tj ustawienie jest respektowane nawet po restarcie Redisa a drugi pozwala na konfigurację ulotną. Oczywiście tę drugą można zapisać i tym samym sprawić, że zostanie zapamiętana. Skonfigurowanie powiadomień sprowadza się do wyboru konkretnych literek z tych które odpowiadają za efekt jaki chcemy uzyskać:

1
2
3
4
5
6
7
8
9
10
11
12
13
K     Keyspace events, published with __keyspace@<db>__ prefix.
E     Keyevent events, published with __keyevent@<db>__ prefix.
g     Generic commands (non-type specific) like DEL, EXPIRE, RENAME, ...
$     String commands
l     List commands
s     Set commands
h     Hash commands
z     Sorted set commands
t     Stream commands
x     Expired events (events generated every time a key expires)
e     Evicted events (events generated when a key is evicted for maxmemory)
m     Key miss events (events generated when a key that doesn't exist is accessed)
A     Alias for "g$lshztxe", so that the "AKE" string means all the events except "m".

a wiec dla przykładu, jeśli chcemy aby Redis publikował na kanałach typu key-space informacje o komendach dotyczących list to konfiguracją będzie „Kl”. Jeśli chcemy by nie tylko o listach informował a o stringach też, to konfiguracją będzie „Kl$”. Przyznać muszę, że jest to słabo czytelne, ale idzie się przyzwyczaić.

Włączyć notyfikację można poprzez:

1
redis-cli config set notify-keyspace-events K$

co sprawi, że Redis zacznie wysyłać notyfikację zgodnie ze wskazanym ustawieniem. Utrwalenie można osiągnąć wykonując polecenie:

1
redis-cli config rewrite

które po prostu zapisuje aktualną konfigurację do pliku redis.conf w którym również manualnie można zmienić ilość pożądanych notyfikacji.


Czekaj, stop!

Podoba Ci się to co tworzę? Jeśli tak to zapraszam Cię do zapisania się na newsletter:

Aby potwierdzić swoją subskrypcję, odbierz pocztę i kliknij w link potwierdzający:) jeśli maila nie ma to poczekaj chwile i/lub sprawdź folder spam/inne/oferty itp :)

Aby potwierdzić swoją subskrypcję, odbierz pocztę i kliknij w link potwierdzający:) jeśli maila nie ma to poczekaj chwile i/lub sprawdź folder spam/inne/oferty itp :)
a w ramach prezentu otrzymasz całkowicie za darmo, dwa dokumenty PDF „6 (nie zawsze oczywistych) błędów popełnianych podczas nauki programowania” który jest jednym z efektów ponad siedmioletniej pracy i obserwacji rozwoju niejednego programisty oraz „Wstęp do testowania w Pythonie”, będący wprowadzeniem do biblioteki PyTest.
Jeśli to Cię interesuje to zapraszam również na swoje social media.

Jak i do ewentualnego postawienia mi kawy :)

Przykład

Stwórzmy program który będzie nasłuchiwał na każdą zmianę klucza wynikającą z komend dedykowanych stringowi:

1
2
3
4
5
6
7
8
9
10
11
from redis import Redis

redis_connection = Redis(decode_responses=True, db=0)

redis_connection.config_set('notify-keyspace-events', 'K$')

pub_sub = redis_connection.pubsub()
pub_sub.subscribe('__keyspace@0__:test_key')

for message in pub_sub.listen():
  print(message)

uruchom program i wykonaj z poziomu redis-cli komendę:

1
2
127.0.0.1:6379> set test_key 15
OK

która momentalnie sprawi, że program wypisze:

1
{'type': 'message', 'pattern': None, 'channel': '__keyspace@0__:test_key', 'data': 'set'}

wykonaj teraz w redis-cli:

1
2
127.0.0.1:6379> append test_key 11
(integer) 4

a program zareaaguje nowym powiadomieniem:

1
{'type': 'message', 'pattern': None, 'channel': '__keyspace@0__:test_key', 'data': 'append'}

teraz usuń klucz i wykonaj:

1
2
127.0.0.1:6379> LPUSH test_key 1
(integer) 1

program na to nie zareagował. Wynika to wprost z konfiguracji, która pozwala na publikowanie tylko zdarzeń wygenerowanych w wyniku użycia komend dedykowanych stringom.

Jeśli uruchomisz taki program:

1
2
3
4
5
6
7
8
9
10
11
from redis import Redis

redis_connection = Redis(decode_responses=True, db=0)

redis_connection.config_set('notify-keyspace-events', 'E$')

pub_sub = redis_connection.pubsub()
pub_sub.subscribe('__keyevent@0__:set')

for message in pub_sub.listen():
  print(message)

to dostaniesz powiadomienia o każdym użyciu komendy SET a jako wiadomość przyjdzie nazwa klucza, na której komenda się wykonała, np.:

1
{'type': 'message', 'pattern': None, 'channel': '__keyevent@0__:set', 'data': 'test_key'}

Kończąc

To o czym należy pamiętać, to o tym że Redis pcha powiadomienia przez mechanizm kanałów pub-sub, co ma swoje zalety i wady. Ale nie ma sensu by je powtarzać – jeden z poprzednich artykułów jest poświęcony właśnie temu mechanizmowi. Ciekawostką jest, że te powiadomienia kiedyś bardzo pomogły mi, w takim trybie „turbo-hot-fix”, uszczelnić pewien proces. Ustawienie klucza jednoznacznie określało że powinna się po nim zadziać pewna akcja. Akcja z wyniku błędu nie zawsze się wykonywała a notyfikacje pomogły mi ekspresowo złapać ten moment i obsłużyć niefortunne przypadki. Tak czy siak, warto wiedzieć że takie sztuczki istnieją.

Dzięki za wizytę,
Mateusz Mazurek
Mateusz M.

Ostatnie wpisy

Podsumowanie: luty i marzec 2024

Ostatnio tygodnie były tak bardzo wypełnione, że nie udało mi się napisać nawet krótkiego podsumowanie. Więc dziś zbiorczo podsumuję luty… Read More

1 tydzień ago

Podsumowanie: styczeń 2024

Zapraszam na krótkie podsumowanie miesiąca. Książki W styczniu przeczytałem "Homo Deus: Historia jutra". Książka łudząco podoba do wcześniejszej książki tego… Read More

2 miesiące ago

Podsumowanie roku 2023

Cześć! Zapraszam na podsumowanie roku 2023. Książki Zacznijmy od książek. W tym roku cel 35 książek nie został osiągnięty. Niemniej… Read More

3 miesiące ago

Podsumowanie: grudzień 2023

Zapraszam na krótkie podsumowanie miesiąca. Książki W grudniu skończyłem czytać Mein Kampf. Nudna książka. Ciekawsze fragmenty można by było streścić… Read More

4 miesiące ago

Praca zdalna – co z nią dalej?

Cześć, ostatnio w Internecie pojawiło się dużo artykułów, które nie były przychylne pracy zdalnej. Z drugiej strony większość komentarzy pod… Read More

4 miesiące ago

Podsumowanie: listopad 2023

Zapraszam na krótkie podsumowanie miesiąca. Książki W listopadzie dokończyłem cykl "Z mgły zrodzony" Sandersona. Tylko "Stop prawa" mi nie do… Read More

5 miesięcy ago