Překvapení (žádné události vypršení platnosti, když doba životnosti klíče dosáhne nuly) není vázáno na Python, ale spíše na způsob, jakým Redis vyprší platnost klíčů.
Dokument Redis o načasování událostí, jejichž platnost vypršela
Časování událostí, jejichž platnost vypršela
Platnost klíčů s přiřazenou dobou životnosti vyprší Redis dvěma způsoby:
- Když je klíč zpřístupněn příkazem a je zjištěno, že jeho platnost vypršela.
- Prostřednictvím systému na pozadí, který postupně vyhledává na pozadí klíče s vypršenou platností, aby bylo možné sbírat také klíče, ke kterým se nikdy nepřistupuje.
Události, jejichž platnost vypršela, se generují, když se přistoupí ke klíči a některý z výše uvedených systémů zjistí, že jeho platnost vypršela, v důsledku toho neexistují žádné záruky, že server Redis bude schopen vygenerovat událost s vypršenou platností v době, kdy klíč začne fungovat. dosáhne hodnoty nula.
Pokud žádný příkaz necílí na klíč neustále a existuje mnoho klíčů s přiřazeným TTL, může dojít k významnému zpoždění mezi okamžikem, kdy doba platnosti klíče klesne na nulu, a časem, kdy je vygenerována událost, jejíž platnost vypršela.
Události, jejichž platnost vypršela, jsou generovány, když server Redis smaže klíč a ne, když doba života teoreticky dosáhne hodnoty nula.
Malý test na konzoli
když Redis běží ($ sudo service redis-server start
)
Založil jsem jednu konzoli a předplatil jsem:
$ redis-cli
PSUBSCRIBE "__key*__:*"
Poté v jiné konzoli:
$ redis-cli
> config set notify-keyspace-events AKE
co se přihlásí k odběru všech druhů akcí
Potom jsem pokračoval v experimentech v této druhé konzoli:
> set aaa aaa
> del aaa
> set aaa ex 5
> get aaa
Všechny aktivity byly vidět v předplacené konzoli. Pouze vypršení platnosti klíče bylo někdy o několik sekund zpožděno, někdy přišlo právě včas.
Všimněte si také, že ve zprávách jsou drobné rozdíly, jedna zpráva [email protected]__:expire
další [email protected]__:expired
.
Ukázkový posluchač spy.py
import redis
import time
r = redis.StrictRedis()
pubsub = r.pubsub()
pubsub.psubscribe("*")
for msg in pubsub.listen():
print time.time(), msg
Tento kód se zaregistruje do všech existujících kanálů ve výchozím redis a vytiskne, co bude publikováno.
Spusťte to:
$ python spy.py
a v jiné konzoli zkuste nastavit klíč s expirací. Uvidíte všechny události.
Pro následující vstup redis-cli.
$ redis-cli
127.0.0.1:6379> set a aha
OK
127.0.0.1:6379> set b bebe ex 3
OK
127.0.0.1:6379> set b bebe ex 3
OK
dostaneme špionážní výstup:
1401548400.27 {'pattern': None, 'type': 'psubscribe', 'channel': '*', 'data': 1L}
1401548428.36 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:a', 'data': 'set'}
1401548428.36 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:set', 'data': 'a'}
1401548436.8 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:b', 'data': 'set'}
1401548436.8 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:set', 'data': 'b'}
1401548436.8 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:b', 'data': 'expire'}
1401548436.8 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:expire', 'data': 'b'}
1401548439.82 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:b', 'data': 'expired'}
1401548439.82 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:expired', 'data': 'b'}
1401548484.46 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:b', 'data': 'set'}
1401548484.46 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:set', 'data': 'b'}
1401548484.46 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:b', 'data': 'expire'}
1401548484.46 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:expire', 'data': 'b'}
1401548487.51 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:b', 'data': 'expired'}
1401548487.51 {'pattern': '*', 'type': 'pmessage', 'channel': '[email protected]__:expired', 'data': 'b'}