This commit adds the sort and window parameter to "sticker find"

The three new compare operators "eq", "gt" and "lt" are casting the values to int.

Sort supports:
- uri: sort by uri
- value: sort by value as string
- value_int: casts value to int

Closes #1894
This commit is contained in:
jcorporation
2024-03-07 20:52:11 +01:00
parent 1efb9d41db
commit 45553c5f61
8 changed files with 187 additions and 42 deletions

View File

@@ -78,7 +78,8 @@ public:
return CommandResult::OK;
}
virtual CommandResult Find(const char *uri, const char *name, StickerOperator op, const char *value) {
virtual CommandResult Find(const char *uri, const char *name, StickerOperator op, const char *value,
const char *sort, bool descending, RangeArg window) {
auto data = CallbackContext{
.name = name,
.sticker_type = sticker_type,
@@ -97,6 +98,7 @@ public:
uri,
name,
op, value,
sort, descending, window,
callback, &data);
return CommandResult::OK;
@@ -172,7 +174,8 @@ public:
database.ReturnSong(song);
}
CommandResult Find(const char *uri, const char *name, StickerOperator op, const char *value) override {
CommandResult Find(const char *uri, const char *name, StickerOperator op, const char *value,
const char *sort, bool descending, RangeArg window) override {
struct sticker_song_find_data data = {
response,
name,
@@ -180,6 +183,7 @@ public:
sticker_song_find(sticker_database, database, uri, data.name,
op, value,
sort, descending, window,
sticker_song_find_print_cb, &data);
return CommandResult::OK;
@@ -386,7 +390,37 @@ handle_sticker(Client &client, Request args, Response &r)
return handler->Delete(uri, sticker_name);
/* find */
if ((args.size() == 4 || args.size() == 6) && StringIsEqual(cmd, "find")) {
if (args.size() >= 4 && StringIsEqual(cmd, "find")) {
RangeArg window = RangeArg::All();
if (args.size() >= 6 && StringIsEqual(args[args.size() - 2], "window")) {
window = args.ParseRange(args.size() - 1);
args.pop_back();
args.pop_back();
}
auto sort = "";
bool descending = false;
if (args.size() >= 6 && StringIsEqual(args[args.size() - 2], "sort")) {
const char *s = args.back();
if (*s == '-') {
descending = true;
++s;
}
if (StringIsEqual(s, "uri") ||
StringIsEqual(s, "value") ||
StringIsEqual(s, "value_int")
) {
sort = s;
}
else {
r.FmtError(ACK_ERROR_ARG, "Unknown sort tag \"{}\"", s);
return CommandResult::ERROR;
}
args.pop_back();
args.pop_back();
}
bool has_op = args.size() > 4;
auto value = has_op ? args[5] : nullptr;
StickerOperator op = StickerOperator::EXISTS;
@@ -399,12 +433,18 @@ handle_sticker(Client &client, Request args, Response &r)
op = StickerOperator::LESS_THAN;
else if (StringIsEqual(op_s, ">"))
op = StickerOperator::GREATER_THAN;
else if (StringIsEqual(op_s, "eq"))
op = StickerOperator::EQUALS_INT;
else if (StringIsEqual(op_s, "lt"))
op = StickerOperator::LESS_THAN_INT;
else if (StringIsEqual(op_s, "gt"))
op = StickerOperator::GREATER_THAN_INT;
else {
r.FmtError(ACK_ERROR_ARG, "bad operator \"{}\"", op_s);
return CommandResult::ERROR;
}
}
return handler->Find(uri, sticker_name, op, value);
return handler->Find(uri, sticker_name, op, value, sort, descending, window);
}
r.Error(ACK_ERROR_ARG, "bad request");