Skip to content

Commit 0ecb3c1

Browse files
committed
Iterate on type safety for zadd
Motivation: Issue #60 called for improving the type safety of the options available for the `zadd` command, and MR !70 made some great headway, but attempted to cram too much into a single enum. Modifications: - Break the `RedisSortedSetAddOption.returnChangedCount` value into an additional boolean param Result: Using `zadd` should now be more straight forward, while being type safe.
1 parent 2605763 commit 0ecb3c1

File tree

2 files changed

+30
-26
lines changed

2 files changed

+30
-26
lines changed

Sources/RediStack/Commands/SortedSetCommands.swift

Lines changed: 25 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -47,45 +47,43 @@ extension RedisClient {
4747
// MARK: General
4848

4949
/// The supported options for the `zadd` command with Redis SortedSet types.
50-
/// - Important: Per Redis documentation, `.onlyUpdateExistingElements` and `.onlyAddNewElements` are mutually exclusive!
51-
/// - Note: `INCR` is not supported by this library in `zadd`. Use the `zincrby(:element:in:)` method instead.
50+
///
5251
/// See [https://redis.io/commands/zadd#zadd-options-redis-302-or-greater](https://redis.io/commands/zadd#zadd-options-redis-302-or-greater)
5352
public enum RedisSortedSetAddOption: String {
5453
/// When adding elements, any that do not already exist in the SortedSet will be ignored and the score of the existing element will be updated.
5554
case onlyUpdateExistingElements = "XX"
5655
/// When adding elements, any that already exist in the SortedSet will be ignored and the score of the existing element will not be updated.
5756
case onlyAddNewElements = "NX"
58-
/// `zadd` normally returns the number of new elements added to the set,
59-
/// but this option will instead have the command return the number of elements changed.
60-
///
61-
/// "Changed" in this context are new elements added, and elements that had their score updated.
62-
case returnChangedCount = "CH"
6357
}
6458

6559
extension RedisClient {
6660
/// Adds elements to a sorted set, assigning their score to the values provided.
61+
/// - Note: `INCR` is not supported by this library in `zadd`. Use the `zincrby(:element:in:)` method instead.
6762
///
6863
/// See [https://redis.io/commands/zadd](https://redis.io/commands/zadd)
6964
/// - Parameters:
7065
/// - elements: A list of elements and their score to add to the sorted set.
7166
/// - key: The key of the sorted set.
72-
/// - options: A set of options defined by Redis for this command to execute under.
73-
/// - Returns: The number of elements added to the sorted set.
67+
/// - option: An option for modifying the behavior of the command.
68+
/// - returnChangedCount: `zadd` normally returns the number of new elements added to the set,
69+
/// but setting this to `true` will instead have the command return the number of elements changed.
70+
///
71+
/// "Changed" in this context are new elements added, and elements that had their score updated.
72+
/// - Returns: The number of elements added to the sorted set, unless `returnChangedCount` was set to `true`.
7473
@inlinable
7574
public func zadd<Value: RESPValueConvertible>(
7675
_ elements: [(element: Value, score: Double)],
7776
to key: String,
78-
options: Set<RedisSortedSetAddOption> = []
77+
option: RedisSortedSetAddOption? = nil,
78+
returnChangedCount: Bool = false
7979
) -> EventLoopFuture<Int> {
80-
assert(options.count <= 2, "Invalid number of options provided.")
81-
assert(
82-
!(options.contains(.onlyAddNewElements) && options.contains(.onlyUpdateExistingElements)),
83-
".onlyAddNewElements and .onlyUpdateExistingElements options are mutually exclusive."
84-
)
85-
8680
var args: [RESPValue] = [.init(bulk: key)]
87-
args.add(contentsOf: options) { (array, option) in
88-
array.append(.init(bulk: option.rawValue))
81+
82+
if let opt = option {
83+
args.append(.init(bulk: opt.rawValue))
84+
}
85+
if returnChangedCount {
86+
args.append(.init(bulk: "CH"))
8987
}
9088
args.add(contentsOf: elements, overestimatedCountBeingAdded: elements.count * 2) { (array, next) in
9189
array.append(.init(bulk: next.score.description))
@@ -102,15 +100,20 @@ extension RedisClient {
102100
/// - Parameters:
103101
/// - element: The element and its score to add to the sorted set.
104102
/// - key: The key of the sorted set.
105-
/// - options: A set of options defined by Redis for this command to execute under.
106-
/// - Returns: `true` if the element was added or score was updated in the sorted set.
103+
/// - option: An option for modifying the behavior of the command.
104+
/// - returnChangedCount: `zadd` normally returns the number of new elements added to the set,
105+
/// but setting this to `true` will instead have the command return the number of elements changed.
106+
///
107+
/// "Changed" in this context are new elements added, and elements that had their score updated.
108+
/// - Returns: `true` if the element was added or score was updated in the sorted set, depending on the `option` and `returnChangedCount` settings set.
107109
@inlinable
108110
public func zadd<Value: RESPValueConvertible>(
109111
_ element: (element: Value, score: Double),
110112
to key: String,
111-
options: Set<RedisSortedSetAddOption> = []
113+
option: RedisSortedSetAddOption? = nil,
114+
returnChangedCount: Bool = false
112115
) -> EventLoopFuture<Bool> {
113-
return zadd([element], to: key, options: options)
116+
return zadd([element], to: key, option: option, returnChangedCount: returnChangedCount)
114117
.map { return $0 == 1 }
115118
}
116119

Tests/RediStackTests/Commands/SortedSetCommandsTests.swift

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -43,18 +43,19 @@ final class SortedSetCommandsTests: RedisIntegrationTestCase {
4343
XCTAssertEqual(count, 1)
4444
count = try connection.zadd([(30, 5)], to: #function).wait()
4545
XCTAssertEqual(count, 0)
46-
count = try connection.zadd([(30, 6), (31, 0), (32, 1)], to: #function, options: [.onlyAddNewElements]).wait()
46+
count = try connection.zadd([(30, 6), (31, 0), (32, 1)], to: #function, option: .onlyAddNewElements).wait()
4747
XCTAssertEqual(count, 2)
4848
count = try connection.zadd(
4949
[(32, 2), (33, 3)],
5050
to: #function,
51-
options: [.onlyUpdateExistingElements, .returnChangedCount]
51+
option: .onlyUpdateExistingElements,
52+
returnChangedCount: true
5253
).wait()
5354
XCTAssertEqual(count, 1)
5455

55-
var success = try connection.zadd((30, 7), to: #function, options: [.returnChangedCount]).wait()
56+
var success = try connection.zadd((30, 7), to: #function, returnChangedCount: true).wait()
5657
XCTAssertTrue(success)
57-
success = try connection.zadd((30, 8), to: #function, options: [.onlyAddNewElements]).wait()
58+
success = try connection.zadd((30, 8), to: #function, option: .onlyAddNewElements).wait()
5859
XCTAssertFalse(success)
5960
}
6061

0 commit comments

Comments
 (0)