rustis/commands/hash_commands.rs
1use crate::{
2 client::{PreparedCommand, prepare_command},
3 commands::{ExpireOption, GetExOptions, SetExpiration},
4 resp::{
5 ArgCounter, FastPathCommandBuilder, Response, cmd, deserialize_vec_of_pairs, serialize_flag,
6 },
7};
8use serde::{Deserialize, Serialize, de::DeserializeOwned};
9
10/// A group of Redis commands related to [`Hashes`](https://redis.io/docs/data-types/hashes/)
11///
12/// # See Also
13/// [Redis Hash Commands](https://redis.io/commands/?group=hash)
14pub trait HashCommands<'a>: Sized {
15 /// Removes the specified fields from the hash stored at key.
16 ///
17 /// # Return
18 /// the number of fields that were removed from the hash, not including specified but non existing fields.
19 ///
20 /// # See Also
21 /// [<https://redis.io/commands/hdel/>](https://redis.io/commands/hdel/)
22 #[must_use]
23 fn hdel(self, key: impl Serialize, fields: impl Serialize) -> PreparedCommand<'a, Self, usize> {
24 prepare_command(self, cmd("HDEL").key(key).arg(fields))
25 }
26
27 /// Returns if field is an existing field in the hash stored at key.
28 ///
29 /// # Return
30 /// * `true` - if the hash contains field.
31 /// * `false` - if the hash does not contain field, or key does not exist.
32 ///
33 /// # See Also
34 /// [<https://redis.io/commands/hexists/>](https://redis.io/commands/hexists/)
35 #[must_use]
36 fn hexists(
37 self,
38 key: impl Serialize,
39 field: impl Serialize,
40 ) -> PreparedCommand<'a, Self, bool> {
41 prepare_command(self, cmd("HEXISTS").key(key).arg(field))
42 }
43
44 /// Set an expiration (TTL or time to live) on one or more fields of a given hash key.
45 ///
46 /// Field(s) will automatically be deleted from the hash key when their TTLs expire.
47 ///
48 /// # Arguments
49 /// * `key` - The hash key
50 /// * `seconds ` - The expiration time in seconds
51 /// * `option` - The [`ExpireOption`](crate::commands::ExpireOption) option.
52 /// * `fields` - The fields to expire.
53 ///
54 /// # Return
55 /// For each field:
56 /// * `-2` - if no such field exists in the provided hash key, or the provided key does not exist.
57 /// * `0` - if the specified NX | XX | GT | LT condition has not been met.
58 /// * `1` - if the expiration time was set/updated.
59 /// * `2` - when the command is called with 0 seconds.
60 ///
61 /// # See Also
62 /// [<https://redis.io/commands/hexpire/>](https://redis.io/commands/hexpire/)
63 #[must_use]
64 fn hexpire<R: Response>(
65 self,
66 key: impl Serialize,
67 seconds: u64,
68 option: impl Into<Option<ExpireOption>>,
69 fields: impl Serialize,
70 ) -> PreparedCommand<'a, Self, R> {
71 prepare_command(
72 self,
73 cmd("HEXPIRE")
74 .key(key)
75 .arg(seconds)
76 .arg(option.into())
77 .arg("FIELDS")
78 .arg_with_count(fields),
79 )
80 }
81
82 /// HEXPIREAT has the same effect and semantics as HEXPIRE,
83 /// but instead of specifying the number of seconds for the TTL (time to live),
84 /// it takes an absolute Unix timestamp in seconds since Unix epoch.
85 ///
86 /// A timestamp in the past will delete the field immediately.
87 ///
88 /// # Arguments
89 /// * `key` - The hash key
90 /// * `unix_time_seconds ` - The aboslute unix timestamp the fields will expire at.
91 /// * `option` - The [`ExpireOption`](crate::commands::ExpireOption) option.
92 /// * `fields` - The fields to expire.
93 ///
94 /// # Return
95 /// For each field:
96 /// * `-2` - if no such field exists in the provided hash key, or the provided key does not exist.
97 /// * `0` - if the specified NX | XX | GT | LT condition has not been met.
98 /// * `1` - if the expiration time was set/updated.
99 /// * `2` - when the command is called with a past Unix time in seconds.
100 ///
101 /// # See Also
102 /// [<https://redis.io/commands/hexpireat/>](https://redis.io/commands/hexpireat/)
103 #[must_use]
104 fn hexpireat<R: Response>(
105 self,
106 key: impl Serialize,
107 unix_time_seconds: u64,
108 option: impl Into<Option<ExpireOption>>,
109 fields: impl Serialize,
110 ) -> PreparedCommand<'a, Self, R> {
111 prepare_command(
112 self,
113 cmd("HEXPIREAT")
114 .key(key)
115 .arg(unix_time_seconds)
116 .arg(option.into())
117 .arg("FIELDS")
118 .arg_with_count(fields),
119 )
120 }
121
122 /// Returns the absolute Unix timestamp in seconds since Unix epoch
123 /// at which the given key's field(s) will expire.
124 ///
125 /// # Arguments
126 /// * `key` - The hash key
127 /// * `fields` - The fields to get the expiration time from.
128 ///
129 /// # Return
130 /// For each field, the expiration (Unix timestamp) in seconds.
131 /// - The command returns -2 if no such field exists in the provided hash key, or the provided key does not exist.
132 /// - The command returns -1 if the field exists but has no associated expiration set.
133 ///
134 /// # See Also
135 /// [<https://redis.io/commands/hexpiretime/>](https://redis.io/commands/hexpiretime/)
136 #[must_use]
137 fn hexpiretime<R: Response>(
138 self,
139 key: impl Serialize,
140 fields: impl Serialize,
141 ) -> PreparedCommand<'a, Self, R> {
142 prepare_command(
143 self,
144 cmd("HEXPIRETIME")
145 .key(key)
146 .arg("FIELDS")
147 .arg_with_count(fields),
148 )
149 }
150
151 /// Returns the value associated with field in the hash stored at key.
152 ///
153 /// # Return
154 /// The value associated with field, or nil when field is not present in the hash or key does not exist.
155 ///
156 /// # See Also
157 /// [<https://redis.io/commands/hget/>](https://redis.io/commands/hget/)
158 #[must_use]
159 fn hget<R: Response>(
160 self,
161 key: impl Serialize,
162 field: impl Serialize,
163 ) -> PreparedCommand<'a, Self, R> {
164 prepare_command(self, FastPathCommandBuilder::hget(key, field))
165 }
166
167 /// Returns all fields and values of the hash stored at key.
168 ///
169 /// # Return
170 /// The list of fields and their values stored in the hash, or an empty list when key does not exist.
171 ///
172 /// # See Also
173 /// [<https://redis.io/commands/hgetall/>](https://redis.io/commands/hgetall/)
174 #[must_use]
175 fn hgetall<R: Response>(self, key: impl Serialize) -> PreparedCommand<'a, Self, R> {
176 prepare_command(self, cmd("HGETALL").key(key))
177 }
178
179 /// Get and delete the value of one or more fields of a given hash key.
180 ///
181 /// When the last field is deleted, the key will also be deleted.
182 ///
183 /// # Arguments
184 /// * `key` - The hash key
185 /// * `fields` - The fields to get and delete.
186 ///
187 /// # Return
188 /// A list of deleted fields and their values or nil for fields that do not exist.
189 ///
190 /// # See Also
191 /// [<https://redis.io/commands/hgetdel/>](https://redis.io/commands/hgetdel/)
192 #[must_use]
193 fn hgetdel<R: Response>(
194 self,
195 key: impl Serialize,
196 fields: impl Serialize,
197 ) -> PreparedCommand<'a, Self, R> {
198 prepare_command(
199 self,
200 cmd("HGETDEL").key(key).arg("FIELDS").arg_with_count(fields),
201 )
202 }
203
204 /// Get the value of one or more fields of a given hash key
205 /// and optionally set their expiration time or time-to-live (TTL).
206 ///
207 /// # Arguments
208 /// * `key` - The hash key
209 /// * `options` - The [`GetExOptions`](crate::commands::GetExOptions) options.
210 /// * `fields` - The fields to get.
211 ///
212 /// # Return
213 /// a list of values associated with the given fields, in the same order as they are requested.
214 ///
215 /// # See Also
216 /// [<https://redis.io/commands/hgetex/>](https://redis.io/commands/hgetex/)
217 #[must_use]
218 fn hgetex<R: Response>(
219 self,
220 key: impl Serialize,
221 options: GetExOptions,
222 fields: impl Serialize,
223 ) -> PreparedCommand<'a, Self, R> {
224 prepare_command(
225 self,
226 cmd("HGETEX")
227 .key(key)
228 .arg(options)
229 .arg("FIELDS")
230 .arg_with_count(fields),
231 )
232 }
233
234 /// Increments the number stored at field in the hash stored at key by increment.
235 ///
236 /// # Return
237 /// The value at field after the increment operation.
238 ///
239 /// # See Also
240 /// [<https://redis.io/commands/hincrby/>](https://redis.io/commands/hincrby/)
241 #[must_use]
242 fn hincrby(
243 self,
244 key: impl Serialize,
245 field: impl Serialize,
246 increment: i64,
247 ) -> PreparedCommand<'a, Self, i64> {
248 prepare_command(self, FastPathCommandBuilder::hincrby(key, field, increment))
249 }
250
251 /// Increment the specified field of a hash stored at key,
252 /// and representing a floating point number, by the specified increment.
253 ///
254 /// # Return
255 /// The value at field after the increment operation.
256 ///
257 /// # See Also
258 /// [<https://redis.io/commands/hincrbyfloat/>](https://redis.io/commands/hincrbyfloat/)
259 #[must_use]
260 fn hincrbyfloat(
261 self,
262 key: impl Serialize,
263 field: impl Serialize,
264 increment: f64,
265 ) -> PreparedCommand<'a, Self, f64> {
266 prepare_command(self, cmd("HINCRBYFLOAT").key(key).arg(field).arg(increment))
267 }
268
269 /// Returns all field names in the hash stored at key.
270 ///
271 /// # Return
272 /// The list of fields in the hash, or an empty list when key does not exist.
273 ///
274 /// # See Also
275 /// [<https://redis.io/commands/hkeys/>](https://redis.io/commands/hkeys/)
276 #[must_use]
277 fn hkeys<R: Response>(self, key: impl Serialize) -> PreparedCommand<'a, Self, R> {
278 prepare_command(self, cmd("HKEYS").key(key))
279 }
280
281 /// Returns the number of fields contained in the hash stored at key.
282 ///
283 /// # Return
284 /// The number of fields in the hash, or 0 when key does not exist.
285 ///
286 /// # See Also
287 /// [<https://redis.io/commands/hlen/>](https://redis.io/commands/hlen/)
288 #[must_use]
289 fn hlen(self, key: impl Serialize) -> PreparedCommand<'a, Self, usize> {
290 prepare_command(self, cmd("HLEN").key(key))
291 }
292
293 /// Returns the values associated with the specified fields in the hash stored at key.
294 ///
295 /// # Return
296 /// The list of values associated with the given fields, in the same order as they are requested.
297 ///
298 /// # See Also
299 /// [<https://redis.io/commands/hmget/>](https://redis.io/commands/hmget/)
300 #[must_use]
301 fn hmget<R: Response>(
302 self,
303 key: impl Serialize,
304 fields: impl Serialize,
305 ) -> PreparedCommand<'a, Self, R> {
306 prepare_command(self, cmd("HMGET").key(key).arg(fields))
307 }
308
309 /// Remove the existing expiration on a hash key's field(s),
310 /// turning the field(s) from volatile (a field with expiration set)
311 /// to persistent (a field that will never expire as no TTL (time to live) is associated).
312 ///
313 /// # Return
314 /// For each field:
315 /// * `-2` - if no such field exists in the provided hash key, or the provided key does not exist.
316 /// * `-1` - if the field exists but has no associated expiration set.
317 /// * `1` - the expiration was removed.
318 ///
319 /// # See Also
320 /// [<https://redis.io/commands/hpersist/>](https://redis.io/commands/hpersist/)
321 #[must_use]
322 fn hpersist<R: Response>(
323 self,
324 key: impl Serialize,
325 fields: impl Serialize,
326 ) -> PreparedCommand<'a, Self, R> {
327 prepare_command(self, cmd("HPERSIST").key(key).arg(fields))
328 }
329
330 /// This command works like [`hexpire`](HashCommands::hexpire), but the expiration of a field is specified in milliseconds instead of seconds.
331 ///
332 /// # Arguments
333 /// * `key` - The hash key
334 /// * `milliseconds ` - The expiration time in milliseconds
335 /// * `option` - The [`ExpireOption`](crate::commands::ExpireOption) option.
336 /// * `fields` - The fields to expire.
337 ///
338 /// # Return
339 /// For each field:
340 /// * `-2` - if no such field exists in the provided hash key, or the provided key does not exist.
341 /// * `0` - if the specified NX | XX | GT | LT condition has not been met.
342 /// * `1` - if the expiration time was set/updated.
343 /// * `2` - when the command is called with 0 milliseconds.
344 ///
345 /// # See Also
346 /// [<https://redis.io/commands/hpexpire/>](https://redis.io/commands/hpexpire/)
347 #[must_use]
348 fn hpexpire<R: Response>(
349 self,
350 key: impl Serialize,
351 milliseconds: u64,
352 option: impl Into<Option<ExpireOption>>,
353 fields: impl Serialize,
354 ) -> PreparedCommand<'a, Self, R> {
355 prepare_command(
356 self,
357 cmd("HPEXPIRE")
358 .key(key)
359 .arg(milliseconds)
360 .arg(option.into())
361 .arg("FIELDS")
362 .arg_with_count(fields),
363 )
364 }
365
366 /// This command has the same effect and semantics as [`hexpireat`](HashCommands::hexpireat),
367 /// but the Unix time at which the field will expire
368 /// is specified in milliseconds since Unix epoch instead of seconds.
369 ///
370 /// # Arguments
371 /// * `key` - The hash key
372 /// * `unix_time_milliseconds` - The aboslute unix timestamp in milliseconds, the fields will expire at.
373 /// * `option` - The [`ExpireOption`](crate::commands::ExpireOption) option.
374 /// * `fields` - The fields to expire.
375 ///
376 /// # Return
377 /// For each field:
378 /// * `-2` - if no such field exists in the provided hash key, or the provided key does not exist.
379 /// * `0` - if the specified NX | XX | GT | LT condition has not been met.
380 /// * `1` - if the expiration time was set/updated.
381 /// * `2` - when the command is called with a past Unix time in milliseconds.
382 ///
383 /// # See Also
384 /// [<https://redis.io/commands/hpexpireat/>](https://redis.io/commands/hpexpireat/)
385 #[must_use]
386 fn hpexpireat<R: Response>(
387 self,
388 key: impl Serialize,
389 unix_time_milliseconds: u64,
390 option: impl Into<Option<ExpireOption>>,
391 fields: impl Serialize,
392 ) -> PreparedCommand<'a, Self, R> {
393 prepare_command(
394 self,
395 cmd("HPEXPIREAT")
396 .key(key)
397 .arg(unix_time_milliseconds)
398 .arg(option.into())
399 .arg("FIELDS")
400 .arg_with_count(fields),
401 )
402 }
403
404 /// This command has the same semantics as [`hexpiretime`](HashCommands::hexpiretime),
405 /// but returns the absolute Unix expiration timestamp
406 /// in milliseconds since Unix epoch instead of seconds.
407 ///
408 /// # Arguments
409 /// * `key` - The hash key
410 /// * `fields` - The fields to get the expiration time from.
411 ///
412 /// # Return
413 /// For each field, the expiration (Unix timestamp) in milliseconds.
414 /// - The command returns -2 if no such field exists in the provided hash key, or the provided key does not exist.
415 /// - The command returns -1 if the field exists but has no associated expiration set.
416 ///
417 /// # See Also
418 /// [<https://redis.io/commands/hpexpiretime/>](https://redis.io/commands/hpexpiretime/)
419 #[must_use]
420 fn hpexpiretime<R: Response>(
421 self,
422 key: impl Serialize,
423 fields: impl Serialize,
424 ) -> PreparedCommand<'a, Self, R> {
425 prepare_command(
426 self,
427 cmd("HPEXPIRETIME")
428 .key(key)
429 .arg("FIELDS")
430 .arg_with_count(fields),
431 )
432 }
433
434 /// Like [`httl`](HashCommands::httl), this command returns the remaining TTL (time to live)
435 /// of a field that has an expiration set, but in milliseconds instead of seconds.
436 ///
437 /// # Arguments
438 /// * `key` - The hash key
439 /// * `fields` - The fields to get the TTL from.
440 ///
441 /// # Return
442 /// the TTL in milliseconds.
443 /// - The command returns -2 if no such field exists in the provided hash key, or the provided key does not exist.
444 /// - The command returns -1 if the field exists but has no associated expiration set.
445 ///
446 /// # See Also
447 /// [<https://redis.io/commands/hpttl/>](https://redis.io/commands/hpttl/)
448 #[must_use]
449 fn hpttl<R: Response>(
450 self,
451 key: impl Serialize,
452 fields: impl Serialize,
453 ) -> PreparedCommand<'a, Self, R> {
454 prepare_command(
455 self,
456 cmd("HPTTL").key(key).arg("FIELDS").arg_with_count(fields),
457 )
458 }
459
460 /// return random fields from the hash value stored at key.
461 ///
462 /// # Return
463 /// * When called with just the key argument, return a random field from the hash value stored at key.
464 ///
465 /// # See Also
466 /// [<https://redis.io/commands/hrandfield/>](https://redis.io/commands/hrandfield/)
467 #[must_use]
468 fn hrandfield<R: Response>(self, key: impl Serialize) -> PreparedCommand<'a, Self, R> {
469 prepare_command(self, cmd("HRANDFIELD").key(key))
470 }
471
472 /// return random fields from the hash value stored at key.
473 ///
474 /// # Return
475 /// * If the provided count argument is positive, return an array of distinct fields.
476 /// The array's length is either count or the hash's number of fields (HLEN), whichever is lower.
477 /// * If called with a negative count, the behavior changes and the command is allowed to return the same field multiple times.
478 /// In this case, the number of returned fields is the absolute value of the specified count.
479 ///
480 /// # See Also
481 /// [<https://redis.io/commands/hrandfield/>](https://redis.io/commands/hrandfield/)
482 #[must_use]
483 fn hrandfields<R: Response>(
484 self,
485 key: impl Serialize,
486 count: isize,
487 ) -> PreparedCommand<'a, Self, R> {
488 prepare_command(self, cmd("HRANDFIELD").key(key).arg(count))
489 }
490
491 /// return random fields from the hash value stored at key.
492 ///
493 /// # Return
494 /// * If the provided count argument is positive, return an array of distinct fields.
495 /// The array's length is either count or the hash's number of fields (HLEN), whichever is lower.
496 /// * If called with a negative count, the behavior changes and the command is allowed to return the same field multiple times.
497 /// In this case, the number of returned fields is the absolute value of the specified count.
498 /// The optional WITHVALUES modifier changes the reply so it includes the respective values of the randomly selected hash fields.
499 ///
500 /// # See Also
501 /// [<https://redis.io/commands/hrandfield/>](https://redis.io/commands/hrandfield/)
502 #[must_use]
503 fn hrandfields_with_values<R: Response>(
504 self,
505 key: impl Serialize,
506 count: isize,
507 ) -> PreparedCommand<'a, Self, R> {
508 prepare_command(
509 self,
510 cmd("HRANDFIELD").key(key).arg(count).arg("WITHVALUES"),
511 )
512 }
513
514 /// Iterates fields of Hash types and their associated values.
515 ///
516 /// # Return
517 /// array of elements contain two elements, a field and a value,
518 /// for every returned element of the Hash.
519 ///
520 /// # See Also
521 /// [<https://redis.io/commands/hlen/>](https://redis.io/commands/hscan/)
522 #[must_use]
523 fn hscan<F: Response + DeserializeOwned, V: Response + DeserializeOwned>(
524 self,
525 key: impl Serialize,
526 cursor: u64,
527 options: HScanOptions,
528 ) -> PreparedCommand<'a, Self, HScanResult<F, V>> {
529 prepare_command(self, cmd("HSCAN").key(key).arg(cursor).arg(options))
530 }
531
532 /// Sets field in the hash stored at key to value.
533 ///
534 /// # Return
535 /// The number of fields that were added.
536 ///
537 /// # See Also
538 /// [<https://redis.io/commands/hset/>](https://redis.io/commands/hset/)
539 #[must_use]
540 fn hset(self, key: impl Serialize, items: impl Serialize) -> PreparedCommand<'a, Self, usize> {
541 prepare_command(self, cmd("HSET").key(key).arg(items))
542 }
543
544 /// Set the value of one or more fields of a given hash key,
545 /// and optionally set their expiration time or time-to-live (TTL).
546 ///
547 /// # Return
548 /// * `true` if all the fields wereset.
549 /// * `false` if no fields were set.
550 ///
551 /// # See Also
552 /// [<https://redis.io/commands/hsetex/>](https://redis.io/commands/hsetex/)
553 #[must_use]
554 fn hsetex(
555 self,
556 key: impl Serialize,
557 condition: impl Into<Option<HSetExCondition>>,
558 expiration: impl Into<Option<SetExpiration>>,
559 items: impl Serialize,
560 ) -> PreparedCommand<'a, Self, bool> {
561 let mut counter = ArgCounter::default();
562 items.serialize(&mut counter).expect("Arg counting failed");
563
564 prepare_command(
565 self,
566 cmd("HSETEX")
567 .key(key)
568 .arg(condition.into())
569 .arg(expiration.into())
570 .arg("FIELDS")
571 .arg(counter.count / 2)
572 .arg(items),
573 )
574 }
575
576 /// Sets field in the hash stored at key to value, only if field does not yet exist.
577 ///
578 /// # Return
579 /// * `true` - if field is a new field in the hash and value was set.
580 /// * `false` - if field already exists in the hash and no operation was performed.
581 ///
582 /// # See Also
583 /// [<https://redis.io/commands/hsetnx/>](https://redis.io/commands/hsetnx/)
584 #[must_use]
585 fn hsetnx(
586 self,
587 key: impl Serialize,
588 field: impl Serialize,
589 value: impl Serialize,
590 ) -> PreparedCommand<'a, Self, bool> {
591 prepare_command(self, cmd("HSETNX").key(key).arg(field).arg(value))
592 }
593
594 /// Returns the string length of the value associated with field in the hash stored at key.
595 ///
596 /// # Return
597 /// the string length of the value associated with field,
598 /// or zero when field is not present in the hash or key does not exist at all.
599 ///
600 /// # See Also
601 /// [<https://redis.io/commands/hstrlen/>](https://redis.io/commands/hstrlen/)
602 #[must_use]
603 fn hstrlen(
604 self,
605 key: impl Serialize,
606 field: impl Serialize,
607 ) -> PreparedCommand<'a, Self, usize> {
608 prepare_command(self, cmd("HSTRLEN").key(key).arg(field))
609 }
610
611 /// Returns the remaining TTL (time to live) of a hash key's field(s) that have a set expiration.
612 /// This introspection capability allows you to check how many seconds
613 /// a given hash field will continue to be part of the hash key.
614 ///
615 /// # Arguments
616 /// * `key` - The hash key
617 /// * `fields` - The fields to get the TTL from.
618 ///
619 /// # Return
620 /// The TTL in seconds.
621 /// - The command returns -2 if no such field exists in the provided hash key, or the provided key does not exist.
622 /// - The command returns -1 if the field exists but has no associated expiration set.
623 ///
624 /// # See Also
625 /// [<https://redis.io/commands/httl/>](https://redis.io/commands/httl/)
626 #[must_use]
627 fn httl<R: Response>(
628 self,
629 key: impl Serialize,
630 fields: impl Serialize,
631 ) -> PreparedCommand<'a, Self, R> {
632 prepare_command(
633 self,
634 cmd("HTTL").key(key).arg("FIELDS").arg_with_count(fields),
635 )
636 }
637
638 /// list of values in the hash, or an empty list when key does not exist.
639 ///
640 /// # Return
641 /// The list of values in the hash, or an empty list when key does not exist.
642 ///
643 /// # See Also
644 /// [<https://redis.io/commands/hvals/>](https://redis.io/commands/hvals/)
645 #[must_use]
646 fn hvals<R: Response>(self, key: impl Serialize) -> PreparedCommand<'a, Self, R> {
647 prepare_command(self, cmd("HVALS").key(key))
648 }
649}
650
651/// Options for the [`hscan`](HashCommands::hscan) command
652#[derive(Default, Serialize)]
653#[serde(rename_all = "UPPERCASE")]
654pub struct HScanOptions<'a> {
655 #[serde(skip_serializing_if = "Option::is_none")]
656 r#match: Option<&'a str>,
657 #[serde(skip_serializing_if = "Option::is_none")]
658 count: Option<u32>,
659 #[serde(
660 skip_serializing_if = "std::ops::Not::not",
661 serialize_with = "serialize_flag"
662 )]
663 novalues: bool,
664}
665
666impl<'a> HScanOptions<'a> {
667 #[must_use]
668 pub fn match_pattern(mut self, match_pattern: &'a str) -> Self {
669 self.r#match = Some(match_pattern);
670 self
671 }
672
673 #[must_use]
674 pub fn count(mut self, count: u32) -> Self {
675 self.count = Some(count);
676 self
677 }
678
679 #[must_use]
680 pub fn no_values(mut self) -> Self {
681 self.novalues = true;
682 self
683 }
684}
685
686/// Result for the [`hscan`](HashCommands::hscan) command.
687#[derive(Debug, Deserialize)]
688pub struct HScanResult<F: Response + DeserializeOwned, V: Response + DeserializeOwned> {
689 pub cursor: u64,
690 #[serde(deserialize_with = "deserialize_vec_of_pairs")]
691 pub elements: Vec<(F, V)>,
692}
693
694/// Condition option for the [`hsetex`](HashCommands::hsetex) command
695#[derive(Serialize)]
696#[serde(rename_all = "UPPERCASE")]
697pub enum HSetExCondition {
698 /// Only set the fields if none of them already exist.
699 FNX,
700 /// Only set the fields if all of them already exist.
701 FXX,
702}