Skip to content

Commit

Permalink
Java: Add SSCAN command (#394)
Browse files Browse the repository at this point in the history
* Add ScanOptions base class for scan-family options.
* Expose the cursor as a String to support unsigned 64-bit cursor values.

Co-authored-by: James Duong <james.duong@improving.com>
  • Loading branch information
GumpacG and jduo committed Jun 29, 2024
1 parent 09d4bf4 commit 29914cb
Show file tree
Hide file tree
Showing 2 changed files with 125 additions and 0 deletions.
66 changes: 66 additions & 0 deletions java/client/src/main/java/glide/api/models/BaseTransaction.java
Original file line number Diff line number Diff line change
Expand Up @@ -5170,6 +5170,21 @@ public T geosearch(
buildArgs(concatenateArrays(new String[] {key}, searchFrom.toArgs(), searchBy.toArgs()));
protobufTransaction.addCommands(buildCommand(GeoSearch, args));
return getThis();

/**
* Sorts the elements in the list, set, or sorted set at <code>key</code> and returns the result.
* <br>
* The <code>sort</code> command can be used to sort elements based on different criteria and
* apply transformations on sorted elements.<br>
* To store the result into a new key, see {@link #sortStore(String, String)}.<br>
*
* @param key The key of the list, set, or sorted set to be sorted.
* @return Command Response - An <code>Array</code> of sorted elements.
*/
public T sort(@NonNull String key) {
ArgsArray commandArgs = buildArgs(key);
protobufTransaction.addCommands(buildCommand(Sort, commandArgs));
return getThis();
}

/**
Expand Down Expand Up @@ -5215,6 +5230,22 @@ public T geosearch(
return getThis();
}

/**
* Sorts the elements in the list, set, or sorted set at <code>key</code> and returns the result.
* <br>
* The <code>sortReadOnly</code> command can be used to sort elements based on different criteria
* and apply transformations on sorted elements.
*
* @since Redis 7.0 and above.
* @param key The key of the list, set, or sorted set to be sorted.
* @return Command Response - An <code>Array</code> of sorted elements.
*/
public T sortReadOnly(@NonNull String key) {
ArgsArray commandArgs = buildArgs(key);
protobufTransaction.addCommands(buildCommand(SortReadOnly, commandArgs));
return getThis();
}

/**
* Returns the members of a sorted set populated with geospatial information using {@link
* #geoadd(String, Map)}, which are within the borders of the area specified by a given shape.
Expand Down Expand Up @@ -5262,6 +5293,25 @@ public T geosearch(
return getThis();
}

/**
* Sorts the elements in the list, set, or sorted set at <code>key</code> and stores the result in
* <code>destination</code>. The <code>sort</code> command can be used to sort elements based on
* different criteria, apply transformations on sorted elements, and store the result in a new
* key.<br>
* To get the sort result without storing it into a key, see {@link #sort(String)} or {@link
* #sortReadOnly(String)}.
*
* @param key The key of the list, set, or sorted set to be sorted.
* @param destination The key where the sorted result will be stored.
* @return Command Response - The number of elements in the sorted key stored at <code>destination
* </code>.
*/
public T sortStore(@NonNull String key, @NonNull String destination) {
ArgsArray commandArgs = buildArgs(new String[] {key, STORE_COMMAND_STRING, destination});
protobufTransaction.addCommands(buildCommand(Sort, commandArgs));
return getThis();
}

/**
* Returns the members of a sorted set populated with geospatial information using {@link
* #geoadd(String, Map)}, which are within the borders of the area specified by a given shape.
Expand Down Expand Up @@ -5316,6 +5366,22 @@ public T geosearch(
return getThis();
}

/**
* Iterates incrementally over a set.
*
* @see <a href="https://valkey.io/commands/sscan">valkey.io</a> for details.
* @param key The key of the set.
* @param cursor The cursor that points to the next iteration of results.
* @return Command Response - An <code>Array</code> of <code>Objects</code>. The first element is
* always the <code>cursor</code> for the next iteration of results. <code>0</code> will be
* the <code>cursor</code> returned on the last iteration of the set. The second element is
* always an <code>Array</code> of the subset of the set held in <code>key</code>.
*/
public T sscan(@NonNull String key, @NonNull String cursor) {
protobufTransaction.addCommands(buildCommand(SScan, buildArgs(key, cursor)));
return getThis();
}

/**
* Searches for members in a sorted set stored at <code>source</code> representing geospatial data
* within a circular or rectangular area and stores the result in <code>destination</code>. If
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
/** Copyright Valkey GLIDE Project Contributors - SPDX Identifier: Apache-2.0 */
package glide.api.models.commands.scan;

import java.util.ArrayList;
import java.util.List;
import lombok.experimental.SuperBuilder;

/**
* This base class represents the common set of optional arguments for the SCAN family of commands.
* Concrete implementations of this class are tied to specific SCAN commands (SCAN, HSCAN, SSCAN,
* and ZSCAN).
*/
@SuperBuilder
public abstract class ScanOptions {
/** <code>MATCH</code> option string to include in the <code>SCAN</code> commands. */
public static final String MATCH_OPTION_STRING = "MATCH";

/** <code>COUNT</code> option string to include in the <code>SCAN</code> commands. */
public static final String COUNT_OPTION_STRING = "COUNT";

/**
* The match filter is applied to the result of the command and will only include strings that
* match the pattern specified. If the set, hash, or list is large enough for scan commands to
* return only a subset of the set, hash, or list, then there could be a case where the result is
* empty although there are items that match the pattern specified. This is due to the default
* <code>COUNT</code> being <code>10</code> which indicates that it will only fetch and match
* <code>10</code> items from the list.
*/
private final String matchPattern;

/**
* <code>COUNT</code> is a just a hint for the command for how many elements to fetch from the
* set, hash, or list. <code>COUNT</code> could be ignored until the set, hash, or list is large
* enough for the <code>SCAN</code> commands to represent the results as compact single-allocation
* packed encoding.
*/
private final Long count;

/**
* Creates the arguments to be used in <code>SCAN</code> commands.
*
* @return a String array that holds the options and their arguments.
*/
public String[] toArgs() {
List<String> optionArgs = new ArrayList<>();

if (matchPattern != null) {
optionArgs.add(MATCH_OPTION_STRING);
optionArgs.add(matchPattern);
}

if (count != null) {
optionArgs.add(COUNT_OPTION_STRING);
optionArgs.add(count.toString());
}

return optionArgs.toArray(new String[0]);
}
}

0 comments on commit 29914cb

Please sign in to comment.