This is an automated email from the ASF dual-hosted git repository.

iilyak pushed a commit to branch couch-stats-resource-tracker-v3-rebase-http-2
in repository https://gitbox.apache.org/repos/asf/couchdb.git

commit 3c27b489e8515bb3d6a2bd89dab262c0d916498b
Author: ILYA Khlopotov <[email protected]>
AuthorDate: Fri Jun 27 09:42:12 2025 -0700

    Split query function into query_{group_by|sort_by|count_by}
---
 .../src/couch_stats_resource_tracker.hrl           |  2 +-
 src/couch_stats/src/csrt.erl                       | 64 ++++++++++++++++---
 src/couch_stats/src/csrt_httpd.erl                 |  6 +-
 src/couch_stats/src/csrt_query.erl                 | 73 ++++++++++++----------
 4 files changed, 99 insertions(+), 46 deletions(-)

diff --git a/src/couch_stats/src/couch_stats_resource_tracker.hrl 
b/src/couch_stats/src/couch_stats_resource_tracker.hrl
index bf03a88b4..aba38c16e 100644
--- a/src/couch_stats/src/couch_stats_resource_tracker.hrl
+++ b/src/couch_stats/src/couch_stats_resource_tracker.hrl
@@ -191,7 +191,7 @@
 -type tuple_of_field_values() :: tuple().
 -type tuple_of_field_names() :: tuple().
 
--type query_options() :: #{aggregation => group_by | sort_by | count_by, limit 
=> pos_integer()}.
+-type query_options() :: #{limit => pos_integer()}.
 -type aggregation_key() :: tuple_of_field_names().
 -type aggregation_values() :: tuple_of_field_values().
 -type query_result() :: #{aggregation_key() => non_neg_integer()}.
diff --git a/src/couch_stats/src/csrt.erl b/src/couch_stats/src/csrt.erl
index 1864f9f44..1efdf5ec3 100644
--- a/src/couch_stats/src/csrt.erl
+++ b/src/couch_stats/src/csrt.erl
@@ -92,8 +92,12 @@
     find_workers_by_pidref/1,
     group_by/2,
     group_by/3,
-    query/2,
-    query/4,
+    query_group_by/3,
+    query_group_by/4,
+    query_sort_by/3,
+    query_sort_by/4,
+    query_count_by/2,
+    query_count_by/3,
     query_matcher/1,
     query_matcher/2,
     sorted/1,
@@ -495,21 +499,63 @@ query_matcher(MatcherName) ->
 query_matcher(MatcherName, Limit) ->
     csrt_query:query_matcher(MatcherName, Limit).
 
--spec query(MatcherName :: string(), Keys :: binary() | rctx_field() | 
[binary()] | [rctx_field()]) ->
+-spec query_group_by(MatcherName, AggregationKeys, ValueKey) ->
     {ok, query_result()}
-    | {error, any()}.
-query(MatcherName, AggregationKeys) ->
-    csrt_query:query(MatcherName, AggregationKeys).
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()],
+    ValueKey :: binary() | rctx_field().
+query_group_by(MatcherName, AggregationKeys, ValueKey) ->
+    csrt_query:query_group_by(MatcherName, AggregationKeys, ValueKey, #{}).
+
+-spec query_group_by(MatcherName, AggregationKeys, ValueKey, Options :: 
query_options()) ->
+    {ok, query_result()}
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()],
+    ValueKey :: binary() | rctx_field().
+query_group_by(MatcherName, AggregationKeys, ValueKey, Options) ->
+    csrt_query:query_group_by(MatcherName, AggregationKeys, ValueKey, Options).
+
+-spec query_sort_by(MatcherName, AggregationKeys, ValueKey) ->
+    {ok, query_result()}
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()],
+    ValueKey :: binary() | rctx_field().
+query_sort_by(MatcherName, AggregationKeys, ValueKey) ->
+    csrt_query:query_sort_by(MatcherName, AggregationKeys, ValueKey, #{}).
 
--spec query(MatcherName, AggregationKeys, ValueKey, Options :: 
query_options()) ->
+-spec query_sort_by(MatcherName, AggregationKeys, ValueKey, Options :: 
query_options()) ->
     {ok, query_result()}
     | {error, any()}
 when
     MatcherName :: string(),
     AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()],
     ValueKey :: binary() | rctx_field().
-query(MatcherName, AggregationKeys, ValueKey, Options) ->
-    csrt_query:query(MatcherName, AggregationKeys, ValueKey, Options).
+query_sort_by(MatcherName, AggregationKeys, ValueKey, Options) ->
+    csrt_query:query_sort_by(MatcherName, AggregationKeys, ValueKey, Options).
+
+-spec query_count_by(MatcherName, AggregationKeys) ->
+    {ok, query_result()}
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()].
+query_count_by(MatcherName, AggregationKeys) ->
+    csrt_query:query_count_by(MatcherName, AggregationKeys, #{}).
+
+-spec query_count_by(MatcherName, AggregationKeys, Options :: query_options()) 
->
+    {ok, query_result()}
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()].
+query_count_by(MatcherName, AggregationKeys, Options) ->
+    csrt_query:query_count_by(MatcherName, AggregationKeys, Options).
 
 sorted(Map) ->
     csrt_query:sorted(Map).
diff --git a/src/couch_stats/src/csrt_httpd.erl 
b/src/couch_stats/src/csrt_httpd.erl
index 577651205..3fb4f0212 100644
--- a/src/couch_stats/src/csrt_httpd.erl
+++ b/src/couch_stats/src/csrt_httpd.erl
@@ -64,7 +64,7 @@ handle_resource_status_req(Req) ->
 
 handle_count_by(Req, MatcherName, CountBy) ->
     AggregationKeys = couch_util:get_value(<<"aggregate_keys">>, CountBy),
-    case csrt:query(MatcherName, AggregationKeys, undefined, #{aggregation => 
count_by}) of
+    case csrt:query_count_by(MatcherName, AggregationKeys) of
         {ok, Map} ->
             send_json(Req, {aggregation_result_to_json(Map)});
         Else ->
@@ -75,7 +75,7 @@ handle_count_by(Req, MatcherName, CountBy) ->
 handle_sort_by(Req, MatcherName, SortBy) ->
     AggregationKeys = couch_util:get_value(<<"aggregate_keys">>, SortBy),
     CounterKey = couch_util:get_value(<<"counter_key">>, SortBy),
-    case csrt:query(MatcherName, AggregationKeys, CounterKey, #{aggregation => 
sort_by}) of
+    case csrt:query_sort_by(MatcherName, AggregationKeys, CounterKey) of
         {ok, Map} ->
             send_json(Req, {aggregation_result_to_json(Map)});
         Else ->
@@ -86,7 +86,7 @@ handle_sort_by(Req, MatcherName, SortBy) ->
 handle_group_by(Req, MatcherName, GroupBy) ->
     AggregationKeys = couch_util:get_value(<<"aggregate_keys">>, GroupBy),
     CounterKey = couch_util:get_value(<<"counter_key">>, GroupBy),
-    case csrt:query(MatcherName, AggregationKeys, CounterKey, #{aggregation => 
group_by}) of
+    case csrt:query_group_by(MatcherName, AggregationKeys, CounterKey) of
         {ok, Map} ->
             send_json(Req, {aggregation_result_to_json(Map)});
         Else ->
diff --git a/src/couch_stats/src/csrt_query.erl 
b/src/couch_stats/src/csrt_query.erl
index f96e3fc65..bacc44db3 100644
--- a/src/couch_stats/src/csrt_query.erl
+++ b/src/couch_stats/src/csrt_query.erl
@@ -34,8 +34,9 @@
     find_workers_by_pidref/1,
     group_by/3,
     group_by/4,
-    query/2,
-    query/4,
+    query_group_by/4,
+    query_sort_by/4,
+    query_count_by/3,
     query_matcher/1,
     query_matcher/2,
     query_matcher_rows/1,
@@ -322,14 +323,27 @@ get_matcher(MatcherName) ->
             {ok, Matcher}
     end.
 
--spec query(MatcherName :: string(), Keys :: binary() | rctx_field() | 
[binary()] | [rctx_field()]) ->
+-spec query_group_by(MatcherName, AggregationKeys, ValueKey, Options :: 
query_options()) ->
     {ok, query_result()}
-    | {error, any()}.
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()],
+    ValueKey :: binary() | rctx_field().
 %% {ok, #{{<<"adm">>,<<"bench-yktbb3as46rzffea">>} => 2}}
-query(MatcherName, AggregationKeys) ->
-    query(MatcherName, AggregationKeys, undefined, #{}).
+query_group_by(MatcherName, AggregationKeys, ValueKey, Options) ->
+    AggregationKey = parse_key(AggregationKeys),
+    VKey = parse_key(ValueKey),
+    Limit = maps:get(limit, Options, query_limit()),
+    maybe
+        ok ?= validate_not_error(AggregationKey),
+        ok ?= validate_not_error(VKey),
+        ok ?= validate_limit(Limit),
+        {ok, Matcher} ?= get_matcher(MatcherName),
+        group_by(Matcher, AggregationKey, VKey)
+    end.
 
--spec query(MatcherName, AggregationKeys, ValueKey, Options :: 
query_options()) ->
+-spec query_sort_by(MatcherName, AggregationKeys, ValueKey, Options :: 
query_options()) ->
     {ok, query_result()}
     | {error, any()}
 when
@@ -337,29 +351,33 @@ when
     AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()],
     ValueKey :: binary() | rctx_field().
 %% {ok, #{{<<"adm">>,<<"bench-yktbb3as46rzffea">>} => 2}}
-query(MatcherName, AggregationKeys, ValueKey, Options) ->
+query_sort_by(MatcherName, AggregationKeys, ValueKey, Options) ->
     AggregationKey = parse_key(AggregationKeys),
     VKey = parse_key(ValueKey),
     Limit = maps:get(limit, Options, query_limit()),
-    Aggregation = maps:get(aggregation, Options, none),
     maybe
         ok ?= validate_not_error(AggregationKey),
         ok ?= validate_not_error(VKey),
         ok ?= validate_limit(Limit),
-        ok ?= validate_aggregation(Aggregation),
         {ok, Matcher} ?= get_matcher(MatcherName),
-        case Aggregation of
-            group_by ->
-                group_by(Matcher, AggregationKey, VKey);
-            sort_by ->
-                sort_by(Matcher, AggregationKey, VKey);
-            count_by when VKey == undefined ->
-                count_by(Matcher, AggregationKey);
-            count_by ->
-                {error, {extra_argument, value_key}};
-            none ->
-                query_matcher_rows(Matcher, Limit)
-        end
+        sort_by(Matcher, AggregationKey, VKey)
+    end.
+
+-spec query_count_by(MatcherName, AggregationKeys, Options :: query_options()) 
->
+    {ok, query_result()}
+    | {error, any()}
+when
+    MatcherName :: string(),
+    AggregationKeys :: binary() | rctx_field() | [binary()] | [rctx_field()].
+%% {ok, #{{<<"adm">>,<<"bench-yktbb3as46rzffea">>} => 2}}
+query_count_by(MatcherName, AggregationKeys, Options) ->
+    AggregationKey = parse_key(AggregationKeys),
+    Limit = maps:get(limit, Options, query_limit()),
+    maybe
+        ok ?= validate_not_error(AggregationKey),
+        ok ?= validate_limit(Limit),
+        {ok, Matcher} ?= get_matcher(MatcherName),
+        count_by(Matcher, AggregationKey)
     end.
 
 validate_not_error({error, _} = Error) ->
@@ -380,17 +398,6 @@ validate_limit(Limit) when is_integer(Limit) ->
 validate_limit(Limit) ->
     {error, {invalid_limit, Limit}}.
 
-validate_aggregation(none) ->
-    ok;
-validate_aggregation(group_by) ->
-    ok;
-validate_aggregation(sort_by) ->
-    ok;
-validate_aggregation(count_by) ->
-    ok;
-validate_aggregation(Other) ->
-    {error, {invalid_aggregation, Other}}.
-
 -spec parse_key(Keys :: binary() | atom() | [binary()] | [atom()]) ->
     [rctx_field()]
     | throw({bad_request, Reason :: binary()}).

Reply via email to