Skip to content

Commit 8c4b292

Browse files
committed
use Expiration (from MSETEX) in new SET API (combined with ValueCondition)
1 parent 788f5e0 commit 8c4b292

File tree

13 files changed

+45
-58
lines changed

13 files changed

+45
-58
lines changed

src/StackExchange.Redis/Expiration.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -237,7 +237,7 @@ private static void ThrowMode(ExpirationMode mode) =>
237237
/// <inheritdoc/>
238238
public override bool Equals(object? obj) => obj is Expiration other && _valueAndMode == other._valueAndMode;
239239

240-
internal int Tokens => Mode switch
240+
internal int TokenCount => Mode switch
241241
{
242242
ExpirationMode.Default or ExpirationMode.NotUsed => 0,
243243
ExpirationMode.KeepTtl or ExpirationMode.Persist => 1,

src/StackExchange.Redis/Interfaces/IDatabase.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3410,7 +3410,7 @@ IEnumerable<SortedSetEntry> SortedSetScan(
34103410
/// <param name="flags">The flags to use for this operation.</param>
34113411
/// <returns><see langword="true"/> if the string was set, <see langword="false"/> otherwise.</returns>
34123412
/// <remarks><seealso href="https://redis.io/commands/set"/></remarks>
3413-
bool StringSet(RedisKey key, RedisValue value, TimeSpan? expiry = null, bool keepTtl = false, When when = When.Always, CommandFlags flags = CommandFlags.None);
3413+
bool StringSet(RedisKey key, RedisValue value, TimeSpan? expiry, bool keepTtl, When when, CommandFlags flags);
34143414

34153415
/// <summary>
34163416
/// Set <paramref name="key"/> to hold the string <paramref name="value"/>, if it matches the given <paramref name="when"/> condition.
@@ -3421,8 +3421,8 @@ IEnumerable<SortedSetEntry> SortedSetScan(
34213421
/// <param name="when">The condition to enforce.</param>
34223422
/// <param name="flags">The flags to use for this operation.</param>
34233423
/// <remarks>See <seealso href="https://redis.io/commands/delex"/>.</remarks>
3424-
#pragma warning disable RS0027
3425-
bool StringSet(RedisKey key, RedisValue value, TimeSpan? expiry, ValueCondition when, CommandFlags flags = CommandFlags.None);
3424+
#pragma warning disable RS0027 // Public API with optional parameter(s) should have the most parameters amongst its public overloads
3425+
bool StringSet(RedisKey key, RedisValue value, Expiration expiry = default, ValueCondition when = default, CommandFlags flags = CommandFlags.None);
34263426
#pragma warning restore RS0027
34273427

34283428
/// <summary>

src/StackExchange.Redis/Interfaces/IDatabaseAsync.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -839,11 +839,11 @@ IAsyncEnumerable<SortedSetEntry> SortedSetScanAsync(
839839
Task<bool> StringSetAsync(RedisKey key, RedisValue value, TimeSpan? expiry, When when, CommandFlags flags);
840840

841841
/// <inheritdoc cref="IDatabase.StringSet(RedisKey, RedisValue, TimeSpan?, bool, When, CommandFlags)"/>
842-
Task<bool> StringSetAsync(RedisKey key, RedisValue value, TimeSpan? expiry = null, bool keepTtl = false, When when = When.Always, CommandFlags flags = CommandFlags.None);
842+
Task<bool> StringSetAsync(RedisKey key, RedisValue value, TimeSpan? expiry, bool keepTtl, When when, CommandFlags flags = CommandFlags.None);
843843

844-
/// <inheritdoc cref="IDatabase.StringSet(RedisKey, RedisValue, TimeSpan?, ValueCondition, CommandFlags)"/>
844+
/// <inheritdoc cref="IDatabase.StringSet(RedisKey, RedisValue, Expiration, ValueCondition, CommandFlags)"/>
845845
#pragma warning disable RS0027 // Public API with optional parameter(s) should have the most parameters amongst its public overloads
846-
Task<bool> StringSetAsync(RedisKey key, RedisValue value, TimeSpan? expiry, ValueCondition when, CommandFlags flags = CommandFlags.None);
846+
Task<bool> StringSetAsync(RedisKey key, RedisValue value, Expiration expiry = default, ValueCondition when = default, CommandFlags flags = CommandFlags.None);
847847
#pragma warning restore RS0027
848848

849849
/// <inheritdoc cref="IDatabase.StringSet(KeyValuePair{RedisKey, RedisValue}[], When, CommandFlags)"/>

src/StackExchange.Redis/KeyspaceIsolation/KeyPrefixed.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -783,7 +783,7 @@ public Task<long> StringIncrementAsync(RedisKey key, long value = 1, CommandFlag
783783
public Task<long> StringLengthAsync(RedisKey key, CommandFlags flags = CommandFlags.None) =>
784784
Inner.StringLengthAsync(ToInner(key), flags);
785785

786-
public Task<bool> StringSetAsync(RedisKey key, RedisValue value, TimeSpan? expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
786+
public Task<bool> StringSetAsync(RedisKey key, RedisValue value, Expiration expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
787787
=> Inner.StringSetAsync(ToInner(key), value, expiry, when, flags);
788788

789789
public Task<bool> StringSetAsync(KeyValuePair<RedisKey, RedisValue>[] values, When when = When.Always, CommandFlags flags = CommandFlags.None) =>

src/StackExchange.Redis/KeyspaceIsolation/KeyPrefixedDatabase.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -765,7 +765,7 @@ public long StringIncrement(RedisKey key, long value = 1, CommandFlags flags = C
765765
public long StringLength(RedisKey key, CommandFlags flags = CommandFlags.None) =>
766766
Inner.StringLength(ToInner(key), flags);
767767

768-
public bool StringSet(RedisKey key, RedisValue value, TimeSpan? expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
768+
public bool StringSet(RedisKey key, RedisValue value, Expiration expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
769769
=> Inner.StringSet(ToInner(key), value, expiry, when, flags);
770770

771771
public bool StringSet(KeyValuePair<RedisKey, RedisValue>[] values, When when = When.Always, CommandFlags flags = CommandFlags.None) =>

src/StackExchange.Redis/Message.ValueCondition.cs

Lines changed: 5 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ internal partial class Message
77
public static Message Create(int db, CommandFlags flags, RedisCommand command, in RedisKey key, in ValueCondition when)
88
=> new KeyConditionMessage(db, flags, command, key, when);
99

10-
public static Message Create(int db, CommandFlags flags, RedisCommand command, in RedisKey key, in RedisValue value, TimeSpan? expiry, in ValueCondition when)
10+
public static Message Create(int db, CommandFlags flags, RedisCommand command, in RedisKey key, in RedisValue value, Expiration expiry, in ValueCondition when)
1111
=> new KeyValueExpiryConditionMessage(db, flags, command, key, value, expiry, when);
1212

1313
private sealed class KeyConditionMessage(
@@ -36,35 +36,22 @@ private sealed class KeyValueExpiryConditionMessage(
3636
RedisCommand command,
3737
in RedisKey key,
3838
in RedisValue value,
39-
TimeSpan? expiry,
39+
Expiration expiry,
4040
in ValueCondition when)
4141
: CommandKeyBase(db, flags, command, key)
4242
{
4343
private readonly RedisValue _value = value;
4444
private readonly ValueCondition _when = when;
45-
private readonly TimeSpan? _expiry = expiry == TimeSpan.MaxValue ? null : expiry;
45+
private readonly Expiration _expiry = expiry;
4646

47-
public override int ArgCount => 2 + _when.TokenCount + (_expiry is null ? 0 : 2);
47+
public override int ArgCount => 2 + _expiry.TokenCount + _when.TokenCount;
4848

4949
protected override void WriteImpl(PhysicalConnection physical)
5050
{
5151
physical.WriteHeader(Command, ArgCount);
5252
physical.Write(Key);
5353
physical.WriteBulkString(_value);
54-
if (_expiry.HasValue)
55-
{
56-
var ms = (long)_expiry.GetValueOrDefault().TotalMilliseconds;
57-
if ((ms % 1000) == 0)
58-
{
59-
physical.WriteBulkString("EX"u8);
60-
physical.WriteBulkString(ms / 1000);
61-
}
62-
else
63-
{
64-
physical.WriteBulkString("PX"u8);
65-
physical.WriteBulkString(ms);
66-
}
67-
}
54+
_expiry.WriteTo(physical);
6855
_when.WriteTo(physical);
6956
}
7057
}

src/StackExchange.Redis/Message.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1711,7 +1711,7 @@ public override int GetHashSlot(ServerSelectionStrategy serverSelectionStrategy)
17111711
// - MSETNX {key1} {value1} [{key2} {value2}...]
17121712
// - MSETEX {count} {key1} {value1} [{key2} {value2}...] [standard-expiry-tokens]
17131713
public override int ArgCount => Command == RedisCommand.MSETEX
1714-
? (1 + (2 * values.Length) + expiry.Tokens + (when is When.Exists or When.NotExists ? 1 : 0))
1714+
? (1 + (2 * values.Length) + expiry.TokenCount + (when is When.Exists or When.NotExists ? 1 : 0))
17151715
: (2 * values.Length); // MSET/MSETNX only support simple syntax
17161716

17171717
protected override void WriteImpl(PhysicalConnection physical)

src/StackExchange.Redis/PublicAPI/PublicAPI.Shipped.txt

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -776,7 +776,6 @@ StackExchange.Redis.IDatabase.StringLength(StackExchange.Redis.RedisKey key, Sta
776776
StackExchange.Redis.IDatabase.StringLongestCommonSubsequence(StackExchange.Redis.RedisKey first, StackExchange.Redis.RedisKey second, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> string?
777777
StackExchange.Redis.IDatabase.StringLongestCommonSubsequenceLength(StackExchange.Redis.RedisKey first, StackExchange.Redis.RedisKey second, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> long
778778
StackExchange.Redis.IDatabase.StringLongestCommonSubsequenceWithMatches(StackExchange.Redis.RedisKey first, StackExchange.Redis.RedisKey second, long minLength = 0, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> StackExchange.Redis.LCSMatchResult
779-
StackExchange.Redis.IDatabase.StringSet(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry = null, bool keepTtl = false, StackExchange.Redis.When when = StackExchange.Redis.When.Always, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> bool
780779
StackExchange.Redis.IDatabase.StringSet(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.When when) -> bool
781780
StackExchange.Redis.IDatabase.StringSet(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags) -> bool
782781
StackExchange.Redis.IDatabase.StringSet(System.Collections.Generic.KeyValuePair<StackExchange.Redis.RedisKey, StackExchange.Redis.RedisValue>[]! values, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags) -> bool
@@ -1023,7 +1022,6 @@ StackExchange.Redis.IDatabaseAsync.StringLongestCommonSubsequenceLengthAsync(Sta
10231022
StackExchange.Redis.IDatabaseAsync.StringLongestCommonSubsequenceWithMatchesAsync(StackExchange.Redis.RedisKey first, StackExchange.Redis.RedisKey second, long minLength = 0, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<StackExchange.Redis.LCSMatchResult>!
10241023
StackExchange.Redis.IDatabaseAsync.StringSetAndGetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry = null, bool keepTtl = false, StackExchange.Redis.When when = StackExchange.Redis.When.Always, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<StackExchange.Redis.RedisValue>!
10251024
StackExchange.Redis.IDatabaseAsync.StringSetAndGetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags) -> System.Threading.Tasks.Task<StackExchange.Redis.RedisValue>!
1026-
StackExchange.Redis.IDatabaseAsync.StringSetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry = null, bool keepTtl = false, StackExchange.Redis.When when = StackExchange.Redis.When.Always, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<bool>!
10271025
StackExchange.Redis.IDatabaseAsync.StringSetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.When when) -> System.Threading.Tasks.Task<bool>!
10281026
StackExchange.Redis.IDatabaseAsync.StringSetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags) -> System.Threading.Tasks.Task<bool>!
10291027
StackExchange.Redis.IDatabaseAsync.StringSetAsync(System.Collections.Generic.KeyValuePair<StackExchange.Redis.RedisKey, StackExchange.Redis.RedisValue>[]! values, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags) -> System.Threading.Tasks.Task<bool>!
@@ -2086,9 +2084,11 @@ static StackExchange.Redis.ValueCondition.implicit operator StackExchange.Redis.
20862084
static StackExchange.Redis.ValueCondition.NotExists.get -> StackExchange.Redis.ValueCondition
20872085
static StackExchange.Redis.ValueCondition.operator !(in StackExchange.Redis.ValueCondition value) -> StackExchange.Redis.ValueCondition
20882086
StackExchange.Redis.IDatabase.StringDelete(StackExchange.Redis.RedisKey key, StackExchange.Redis.ValueCondition when, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> bool
2089-
StackExchange.Redis.IDatabase.StringSet(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.ValueCondition when, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> bool
20902087
StackExchange.Redis.IDatabaseAsync.StringDeleteAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.ValueCondition when, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<bool>!
2091-
StackExchange.Redis.IDatabaseAsync.StringSetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, StackExchange.Redis.ValueCondition when, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<bool>!
2088+
StackExchange.Redis.IDatabase.StringSet(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, StackExchange.Redis.Expiration expiry = default(StackExchange.Redis.Expiration), StackExchange.Redis.ValueCondition when = default(StackExchange.Redis.ValueCondition), StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> bool
2089+
StackExchange.Redis.IDatabase.StringSet(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, bool keepTtl, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags) -> bool
2090+
StackExchange.Redis.IDatabaseAsync.StringSetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, StackExchange.Redis.Expiration expiry = default(StackExchange.Redis.Expiration), StackExchange.Redis.ValueCondition when = default(StackExchange.Redis.ValueCondition), StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<bool>!
2091+
StackExchange.Redis.IDatabaseAsync.StringSetAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.RedisValue value, System.TimeSpan? expiry, bool keepTtl, StackExchange.Redis.When when, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<bool>!
20922092
[SER002]StackExchange.Redis.IDatabase.StringDigest(StackExchange.Redis.RedisKey key, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> StackExchange.Redis.ValueCondition?
20932093
[SER002]StackExchange.Redis.IDatabaseAsync.StringDigestAsync(StackExchange.Redis.RedisKey key, StackExchange.Redis.CommandFlags flags = StackExchange.Redis.CommandFlags.None) -> System.Threading.Tasks.Task<StackExchange.Redis.ValueCondition?>!
20942094
[SER002]StackExchange.Redis.ValueCondition.AsDigest() -> StackExchange.Redis.ValueCondition

src/StackExchange.Redis/RedisDatabase.Strings.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -48,19 +48,19 @@ private Message GetStringDeleteMessage(in RedisKey key, in ValueCondition when,
4848
return ExecuteAsync(msg, ResultProcessor.Digest);
4949
}
5050

51-
public Task<bool> StringSetAsync(RedisKey key, RedisValue value, TimeSpan? expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
51+
public Task<bool> StringSetAsync(RedisKey key, RedisValue value, Expiration expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
5252
{
5353
var msg = GetStringSetMessage(key, value, expiry, when, flags);
5454
return ExecuteAsync(msg, ResultProcessor.Boolean);
5555
}
5656

57-
public bool StringSet(RedisKey key, RedisValue value, TimeSpan? expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
57+
public bool StringSet(RedisKey key, RedisValue value, Expiration expiry, ValueCondition when, CommandFlags flags = CommandFlags.None)
5858
{
5959
var msg = GetStringSetMessage(key, value, expiry, when, flags);
6060
return ExecuteSync(msg, ResultProcessor.Boolean);
6161
}
6262

63-
private Message GetStringSetMessage(in RedisKey key, in RedisValue value, TimeSpan? expiry, in ValueCondition when, CommandFlags flags, [CallerMemberName] string? operation = null)
63+
private Message GetStringSetMessage(in RedisKey key, in RedisValue value, Expiration expiry, in ValueCondition when, CommandFlags flags, [CallerMemberName] string? operation = null)
6464
{
6565
switch (when.Kind)
6666
{

0 commit comments

Comments
 (0)