Skip to content

Commit b3d3c5f

Browse files
authored
Add shortcut for count() (opensearch-project#4142)
1 parent 9042f36 commit b3d3c5f

6 files changed

Lines changed: 68 additions & 2 deletions

File tree

docs/user/ppl/cmd/stats.rst

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -80,7 +80,7 @@ COUNT
8080
Description
8181
>>>>>>>>>>>
8282

83-
Usage: Returns a count of the number of expr in the rows retrieved by a SELECT statement.
83+
Usage: Returns a count of the number of expr in the rows retrieved by a SELECT statement. The ``C()`` function can be used as an abbreviation for ``COUNT()``.
8484

8585
Example::
8686

@@ -92,6 +92,14 @@ Example::
9292
| 4 |
9393
+---------+
9494

95+
os> source=accounts | stats c();
96+
fetched rows / total rows = 1/1
97+
+-----+
98+
| c() |
99+
|-----|
100+
| 4 |
101+
+-----+
102+
95103
SUM
96104
---
97105

integ-test/src/test/java/org/opensearch/sql/calcite/remote/CalcitePPLAggregationIT.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,10 @@ public void testSimpleCount() throws IOException {
6060
executeQuery(String.format("source=%s | stats count() as c", TEST_INDEX_BANK));
6161
verifySchema(actual, schema("c", "bigint"));
6262
verifyDataRows(actual, rows(7));
63+
64+
actual = executeQuery(String.format("source=%s | stats c() as count_emp", TEST_INDEX_BANK));
65+
verifySchema(actual, schema("count_emp", "bigint"));
66+
verifyDataRows(actual, rows(7));
6367
}
6468

6569
@Test

integ-test/src/test/java/org/opensearch/sql/ppl/StatsCommandIT.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,6 +88,14 @@ public void testStatsCountAll() throws IOException {
8888
verifySchema(response, schema("count()", null, "int"));
8989
}
9090
verifyDataRows(response, rows(1000));
91+
92+
response = executeQuery(String.format("source=%s | stats c()", TEST_INDEX_ACCOUNT));
93+
if (isCalciteEnabled()) {
94+
verifySchema(response, schema("c()", null, "bigint"));
95+
} else {
96+
verifySchema(response, schema("c()", null, "int"));
97+
}
98+
verifyDataRows(response, rows(1000));
9199
}
92100

93101
@Test

ppl/src/main/antlr/OpenSearchPPLParser.g4

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -459,7 +459,7 @@ statsAggTerm
459459
// aggregation functions
460460
statsFunction
461461
: statsFunctionName LT_PRTHS valueExpression RT_PRTHS # statsFunctionCall
462-
| COUNT LT_PRTHS RT_PRTHS # countAllFunctionCall
462+
| (COUNT | C) LT_PRTHS RT_PRTHS # countAllFunctionCall
463463
| PERCENTILE_SHORTCUT LT_PRTHS valueExpression RT_PRTHS # percentileShortcutFunctionCall
464464
| (DISTINCT_COUNT | DC | DISTINCT_COUNT_APPROX) LT_PRTHS valueExpression RT_PRTHS # distinctCountFunctionCall
465465
| takeAggFunction # takeAggFunctionCall

ppl/src/test/java/org/opensearch/sql/ppl/calcite/CalcitePPLAggregationTest.java

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,19 @@ public void testSimpleCount() {
3030

3131
String expectedSparkSql = "" + "SELECT COUNT(*) `c`\n" + "FROM `scott`.`EMP`";
3232
verifyPPLToSparkSQL(root, expectedSparkSql);
33+
34+
ppl = "source=EMP | stats c() as count_emp";
35+
root = getRelNode(ppl);
36+
expectedLogical =
37+
""
38+
+ "LogicalAggregate(group=[{}], count_emp=[COUNT()])\n"
39+
+ " LogicalTableScan(table=[[scott, EMP]])\n";
40+
verifyLogical(root, expectedLogical);
41+
expectedResult = "count_emp=14\n";
42+
verifyResult(root, expectedResult);
43+
44+
expectedSparkSql = "" + "SELECT COUNT(*) `count_emp`\n" + "FROM `scott`.`EMP`";
45+
verifyPPLToSparkSQL(root, expectedSparkSql);
3346
}
3447

3548
@Test
@@ -86,6 +99,27 @@ public void testMultipleAggregatesWithAliases() {
8699
verifyPPLToSparkSQL(root, expectedSparkSql);
87100
}
88101

102+
@Test
103+
public void testMultipleAggregatesWithCountAbbreviation() {
104+
String ppl =
105+
"source=EMP | stats avg(SAL) as avg_sal, max(SAL) as max_sal, min(SAL) as min_sal, c()"
106+
+ " as cnt";
107+
RelNode root = getRelNode(ppl);
108+
String expectedLogical =
109+
"LogicalAggregate(group=[{}], avg_sal=[AVG($0)], max_sal=[MAX($0)], min_sal=[MIN($0)],"
110+
+ " cnt=[COUNT()])\n"
111+
+ " LogicalProject(SAL=[$5])\n"
112+
+ " LogicalTableScan(table=[[scott, EMP]])\n";
113+
verifyLogical(root, expectedLogical);
114+
String expectedResult = "avg_sal=2073.214285; max_sal=5000.00; min_sal=800.00; cnt=14\n";
115+
verifyResult(root, expectedResult);
116+
117+
String expectedSparkSql =
118+
"SELECT AVG(`SAL`) `avg_sal`, MAX(`SAL`) `max_sal`, MIN(`SAL`) `min_sal`, COUNT(*) `cnt`\n"
119+
+ "FROM `scott`.`EMP`";
120+
verifyPPLToSparkSQL(root, expectedSparkSql);
121+
}
122+
89123
@Test
90124
public void testMultipleAggregatesWithAliasesByClause() {
91125
String ppl =

ppl/src/test/java/org/opensearch/sql/ppl/parser/AstBuilderTest.java

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -240,6 +240,18 @@ public void testStatsCommand() {
240240
defaultStatsArgs()));
241241
}
242242

243+
@Test
244+
public void testStatsCommandWithCountAbbreviation() {
245+
assertEqual(
246+
"source=t | stats c()",
247+
agg(
248+
relation("t"),
249+
exprList(alias("c()", aggregate("count", AstDSL.allFields()))),
250+
emptyList(),
251+
emptyList(),
252+
defaultStatsArgs()));
253+
}
254+
243255
@Test
244256
public void testStatsCommandWithByClause() {
245257
assertEqual(

0 commit comments

Comments
 (0)