pub struct Keys { /* private fields */ }Expand description
Every command that works on a key whatever the key holds.
DEL, EXISTS and TYPE, plus the whole expiry family. Keys are byte
strings the way Redis’s are, so anything that is bytes will do.
let db = yo::open(yo::MEMORY)?;
let keys = db.keys();
db.strings().set("greeting", "hello")?;
assert!(keys.exists("greeting")?);
assert!(keys.del("greeting")?);
assert!(!keys.exists("greeting")?);Implementations§
Source§impl Keys
impl Keys
Sourcepub fn exists(&self, key: impl AsRef<[u8]>) -> Result<bool>
pub fn exists(&self, key: impl AsRef<[u8]>) -> Result<bool>
Whether a key is there. EXISTS.
A key whose deadline has gone is not there, whether or not anything has got around to removing it yet.
§Errors
Code::Invalid if called from inside a callback that is already
holding this database.
Sourcepub fn count<K: AsRef<[u8]>>(&self, keys: &[K]) -> Result<usize>
pub fn count<K: AsRef<[u8]>>(&self, keys: &[K]) -> Result<usize>
How many of these keys are there. EXISTS with several.
The same key twice counts twice, which is Redis’s rule and is worth knowing before you use this to count distinct things.
§Errors
As Keys::exists.
Sourcepub fn expire_in(&self, key: impl AsRef<[u8]>, after: Duration) -> Result<bool>
pub fn expire_in(&self, key: impl AsRef<[u8]>, after: Duration) -> Result<bool>
Give a key this long to live, and say whether the deadline was set.
PEXPIRE.
A duration that has already gone, meaning zero, removes the key and answers true, because the deadline was applied and applying it is what took the key away. False means the key is not there.
§Errors
Code::Invalid for a duration that lands past what a millisecond
timestamp reaches, which is the year 4199, or if called from inside a
callback that is already holding this database.
Sourcepub fn expire_in_when(
&self,
key: impl AsRef<[u8]>,
after: Duration,
when: When,
) -> Result<bool>
pub fn expire_in_when( &self, key: impl AsRef<[u8]>, after: Duration, when: When, ) -> Result<bool>
The same with a condition on it. PEXPIRE with NX, XX, GT or
LT.
False now means either that the key is not there or that the condition
said no, which is the one place Redis’s reply is genuinely ambiguous.
Ask Keys::ttl first if you need to tell them apart.
§Errors
As Keys::expire_in.
Sourcepub fn expire_at(&self, key: impl AsRef<[u8]>, at: SystemTime) -> Result<bool>
pub fn expire_at(&self, key: impl AsRef<[u8]>, at: SystemTime) -> Result<bool>
Set the moment a key goes away, and say whether it was set.
PEXPIREAT.
A moment that has already gone removes the key, the same as
Keys::expire_in with nothing left on it.
§Errors
As Keys::expire_in.
Sourcepub fn expire_at_when(
&self,
key: impl AsRef<[u8]>,
at: SystemTime,
when: When,
) -> Result<bool>
pub fn expire_at_when( &self, key: impl AsRef<[u8]>, at: SystemTime, when: When, ) -> Result<bool>
Sourcepub fn deadline(&self, key: impl AsRef<[u8]>) -> Result<Option<SystemTime>>
pub fn deadline(&self, key: impl AsRef<[u8]>) -> Result<Option<SystemTime>>
The moment a key goes away, or None if it is missing or has no
deadline. PEXPIRETIME.
Keys::ttl is the one that tells those two apart. This one is for
when the answer needs to survive being written down, since a moment
stays true and a duration goes stale as soon as it is read.
§Errors
As Keys::exists.
Sourcepub fn persist(&self, key: impl AsRef<[u8]>) -> Result<bool>
pub fn persist(&self, key: impl AsRef<[u8]>) -> Result<bool>
Take a key’s deadline away and let it live, and say whether there was
one. PERSIST.
§Errors
As Keys::exists.
Sourcepub fn rename(
&self,
src: impl AsRef<[u8]>,
dst: impl AsRef<[u8]>,
) -> Result<Moved>
pub fn rename( &self, src: impl AsRef<[u8]>, dst: impl AsRef<[u8]>, ) -> Result<Moved>
Move a key to another name, over whatever was there. RENAME.
The value does not move and is not copied. A set or a hash is a slot number sitting in a record, and the same slot number under a different key is the same set, so this writes a new record and deletes the old one however large the value is. Renaming a set of a million members writes thirteen bytes.
The deadline travels with the source, and whatever the destination had
goes away with the value it belonged to. A key renamed onto itself is
Moved::Ok and keeps its deadline.
Moved::Taken cannot happen here, which is what
Keys::rename_if_new is for.
§Errors
As Keys::exists.
Sourcepub fn rename_if_new(
&self,
src: impl AsRef<[u8]>,
dst: impl AsRef<[u8]>,
) -> Result<Moved>
pub fn rename_if_new( &self, src: impl AsRef<[u8]>, dst: impl AsRef<[u8]>, ) -> Result<Moved>
Move a key to another name, but only if that name is free. RENAMENX.
A key renamed onto itself is Moved::Taken, because the destination
does exist and a key is not new because it is the one you already had.
That is the one place this and Keys::rename disagree about a call
neither of them has to do any work for.
§Errors
As Keys::exists.
Sourcepub fn copy(
&self,
src: impl AsRef<[u8]>,
dst: impl AsRef<[u8]>,
) -> Result<Moved>
pub fn copy( &self, src: impl AsRef<[u8]>, dst: impl AsRef<[u8]>, ) -> Result<Moved>
Copy a value to another key, leaving the destination alone if it is
already there. COPY.
This is the one call here that costs what the value is worth. Two keys
cannot share a body, because then adding a member to one would show up in
the other, so the body is cloned. Keys::rename is the call that moves
a large value for nothing, and it is the one to reach for when the old
name is not wanted afterwards.
The deadline is copied too, so a copy of a key with ten seconds left has ten seconds left. A destination whose deadline has already gone counts as free.
§Errors
As Keys::exists.
Sourcepub fn copy_over(
&self,
src: impl AsRef<[u8]>,
dst: impl AsRef<[u8]>,
) -> Result<Moved>
pub fn copy_over( &self, src: impl AsRef<[u8]>, dst: impl AsRef<[u8]>, ) -> Result<Moved>
Copy a value to another key, over whatever was there. COPY REPLACE.
Moved::Taken cannot happen here, the same way it cannot happen for
Keys::rename.
§Errors
As Keys::exists.
Sourcepub fn each(&self, f: impl FnMut(&[u8])) -> Result<()>
pub fn each(&self, f: impl FnMut(&[u8])) -> Result<()>
Every key in the database, one call each. KEYS * without the reply.
The key is handed over where it lies, so a walk of a million keys allocates nothing at all. It is only borrowed for the length of the call, which is what stops it from outliving the record it points into, so anything you want to keep has to be copied out inside the closure.
A key whose deadline has passed is not handed over, and it is deleted once the walk has finished, so a walk is also the cheapest way to clear out a database that has had a lot of things expire in it.
let db = yo::open(yo::MEMORY)?;
db.strings().set("a", "1")?;
db.strings().set("b", "2")?;
let mut n = 0;
db.keys().each(|_| n += 1)?;
assert_eq!(n, 2);§Errors
As Keys::exists, which includes calling any method on this database
from inside the closure.
Sourcepub fn all(&self) -> Result<Vec<Vec<u8>>>
pub fn all(&self) -> Result<Vec<Vec<u8>>>
Every key, copied out into a vector. KEYS *.
The convenient one, and the one that costs a key’s worth of memory per
key. Keys::each is the same walk without that.
§Errors
As Keys::exists.
Sourcepub fn matching(&self, pattern: impl AsRef<[u8]>) -> Result<Vec<Vec<u8>>>
pub fn matching(&self, pattern: impl AsRef<[u8]>) -> Result<Vec<Vec<u8>>>
Every key matching a glob pattern. KEYS pattern.
The same *, ?, [abc] and \ that Redis matches with, so a pattern
that works against a Redis client works here.
let db = yo::open(yo::MEMORY)?;
db.strings().set("user:1", "alice")?;
db.strings().set("user:2", "bob")?;
db.strings().set("session:1", "x")?;
assert_eq!(db.keys().matching("user:*")?.len(), 2);§Errors
As Keys::exists.
Sourcepub fn random(&self) -> Result<Option<Vec<u8>>>
pub fn random(&self) -> Result<Option<Vec<u8>>>
One key, chosen at random, or None if the database is empty.
RANDOMKEY.
A constant number of loads whatever the database holds, because it picks a place in the index and takes a key from there rather than walking to find one.
§Errors
As Keys::exists.