Skip to content

Commit e892aec

Browse files
authored
Add string_size, series_cos, series_sin, series_sum, series_tan (#401)
1 parent 168c246 commit e892aec

File tree

9 files changed

+793
-3
lines changed

9 files changed

+793
-3
lines changed

apl/apl-features.mdx

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -218,6 +218,7 @@ keywords: ['axiom documentation', 'documentation', 'axiom', 'APL', 'axiom proces
218218
| String function | [strcat_delim](/apl/scalar-functions/string-functions#strcat-delim) | Concatenates 2–64 arguments with a delimiter. |
219219
| String function | [strcat](/apl/scalar-functions/string-functions#strcat) | Concatenates 1–64 arguments. |
220220
| String function | [strcmp](/apl/scalar-functions/string-functions#strcmp) | Compares two strings. |
221+
| String function | [string-size](/apl/scalar-functions/string-functions/string-size) | Returns the length, in characters, of the input string. |
221222
| String function | [strlen](/apl/scalar-functions/string-functions#strlen) | Returns the length of a string. |
222223
| String function | [strrep](/apl/scalar-functions/string-functions#strrep) | Repeats a string a given number of times. |
223224
| String function | [substring](/apl/scalar-functions/string-functions#substring) | Extracts a substring. |
@@ -298,11 +299,15 @@ keywords: ['axiom documentation', 'documentation', 'axiom', 'APL', 'axiom proces
298299
| Time series function | [series_acos](/apl/scalar-functions/time-series/series-acos) | Returns the inverse cosine (arccos) of a series. |
299300
| Time series function | [series_asin](/apl/scalar-functions/time-series/series-asin) | Returns the inverse sine (arcsin) of a series. |
300301
| Time series function | [series_atan](/apl/scalar-functions/time-series/series-atan) | Returns the inverse tangent (arctan) of a series. |
302+
| Time series function | [series_cos](/apl/scalar-functions/time-series/series-cos) | Returns the cosine of a series. |
301303
| Time series function | [series_greater](/apl/scalar-functions/time-series/series-greater) | Returns the elements of a series that are greater than a specified value. |
302304
| Time series function | [series_greater_equals](/apl/scalar-functions/time-series/series-greater-equals) | Returns the elements of a series that are greater than or equal to a specified value. |
303305
| Time series function | [series_less](/apl/scalar-functions/time-series/series-less) | Returns the elements of a series that are less than a specified value. |
304306
| Time series function | [series_less_equals](/apl/scalar-functions/time-series/series-less-equals) | Returns the elements of a series that are less than or equal to a specified value. |
305307
| Time series function | [series_not_equals](/apl/scalar-functions/time-series/series-not-equals) | Returns the elements of a series that aren’t equal to a specified value. |
308+
| Time series function | [series_sin](/apl/scalar-functions/time-series/series-sin) | Returns the sine of a series. |
309+
| Time series function | [series_sum](/apl/scalar-functions/time-series/series-sum) | Returns the sum of a series. |
310+
| Time series function | [series_tan](/apl/scalar-functions/time-series/series-tan) | Returns the tangent of a series. |
306311
| Type function | [iscc](/apl/scalar-functions/type-functions/iscc) | Checks whether a value is a valid credit card (CC) number. |
307312
| Type function | [isimei](/apl/scalar-functions/type-functions/isimei) | Checks whether a value is a valid International Mobile Equipment Identity (IMEI) number. |
308313
| Type function | [ismap](/apl/scalar-functions/type-functions/ismap) | Checks whether a value is of the `dynamic` type and represents a mapping. |

apl/scalar-functions/string-functions.mdx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@ The table summarizes the string functions available in APL.
4141
| [strcat_delim](#strcat-delim) | Concatenates between 2 and 64 arguments, with delimiter, provided as first argument. |
4242
| [strcat](#strcat) | Concatenates between 1 and 64 arguments. |
4343
| [strcmp](#strcmp) | Compares two strings. |
44+
| [string-size](/apl/scalar-functions/string-functions/string-size) | Returns the length, in characters, of the input string. |
4445
| [strlen](#strlen) | Returns the length, in characters, of the input string. |
4546
| [strrep](#strrep) | Repeats given string provided number of times (default = 1). |
4647
| [substring](#substring) | Extracts a substring from a source string. |
Lines changed: 148 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,148 @@
1+
---
2+
title: string_size
3+
description: 'This page explains how to use the string_size function in APL.'
4+
---
5+
6+
The `string_size` function returns the number of bytes in a string. You use it when you want to measure the length of text fields such as user IDs, URLs, or status codes. This function is useful for detecting anomalies, filtering out unusually long values, or analyzing patterns in textual data.
7+
8+
For example, you can use `string_size` to detect requests with excessively long URIs, identify outlier user IDs, or monitor payload lengths in traces.
9+
10+
## For users of other query languages
11+
12+
If you come from other query languages, this section explains how to adjust your existing queries to achieve the same results in APL.
13+
14+
<AccordionGroup>
15+
<Accordion title="Splunk SPL users">
16+
17+
In Splunk SPL, you typically use the `len` function to calculate the number of characters in a string. In APL, you use `string_size` to calculate the number of bytes in a string.
18+
19+
<CodeGroup>
20+
```sql Splunk example
21+
... | eval uri_length=len(uri)
22+
````
23+
24+
```kusto APL equivalent
25+
['sample-http-logs']
26+
| extend uri_length = string_size(uri)
27+
```
28+
29+
</CodeGroup>
30+
31+
</Accordion>
32+
<Accordion title="ANSI SQL users">
33+
34+
In ANSI SQL, you use the `LENGTH` or `CHAR_LENGTH` function to calculate string length. In APL, the equivalent is `string_size` to calculate the number of bytes in a string.
35+
36+
<CodeGroup>
37+
```sql SQL example
38+
SELECT LENGTH(uri) AS uri_length
39+
FROM sample_http_logs;
40+
```
41+
42+
```kusto APL equivalent
43+
['sample-http-logs']
44+
| extend uri_length = string_size(uri)
45+
```
46+
47+
</CodeGroup>
48+
49+
</Accordion>
50+
</AccordionGroup>
51+
52+
## Usage
53+
54+
### Syntax
55+
56+
```kusto
57+
string_size(source)
58+
```
59+
60+
### Parameters
61+
62+
| Parameter | Type | Description |
63+
| --------- | -------- | ---------------------------- |
64+
| `source` | `string` | The input string expression. |
65+
66+
### Returns
67+
68+
An integer representing the number of bytes in the string. If the string is empty, the function returns `0`.
69+
70+
## Use case examples
71+
72+
<Tabs>
73+
<Tab title="Log analysis">
74+
75+
You can use `string_size` to detect unusually long URIs that might indicate an attempted exploit or malformed request.
76+
77+
**Query**
78+
79+
```kusto
80+
['sample-http-logs']
81+
| extend uri_length = string_size(uri)
82+
| where uri_length > 100
83+
| project _time, method, uri, uri_length, status
84+
```
85+
86+
[Run in Playground](https://play.axiom.co/axiom-play-qf1k/query?initForm=%7B%22apl%22%3A%22%5B'sample-http-logs'%5D%20%7C%20extend%20uri_length%20%3D%20string_size%28uri%29%20%7C%20where%20uri_length%20%3E%2010%20%7C%20project%20_time%2C%20method%2C%20uri%2C%20uri_length%2C%20status%22%7D)
87+
88+
**Output**
89+
90+
| _time | method | uri | uri_length | status |
91+
| -------------------- | ------ | --------------------------------- | ----------- | ------ |
92+
| 2025-09-11T10:01:45Z | GET | /search/products?q=... | 142 | 200 |
93+
| 2025-09-11T10:02:13Z | POST | /checkout/submit/order/details... | 187 | 400 |
94+
95+
This query finds all HTTP requests with URIs longer than 10 characters and lists their details.
96+
97+
</Tab>
98+
<Tab title="OpenTelemetry traces">
99+
100+
You can measure the length of trace IDs or span IDs to ensure data consistency and identify malformed identifiers.
101+
102+
**Query**
103+
104+
```kusto
105+
['otel-demo-traces']
106+
| extend trace_length = string_size(trace_id)
107+
| summarize avg_length = avg(trace_length) by ['service.name']
108+
```
109+
110+
[Run in Playground](https://play.axiom.co/axiom-play-qf1k/query?initForm=%7B%22apl%22%3A%22%5B'otel-demo-traces'%5D%20%7C%20extend%20trace_length%20%3D%20string_size%28trace_id%29%20%7C%20summarize%20avg_length%20%3D%20avg%28trace_length%29%20by%20%5B'service.name'%5D%22%7D)
111+
112+
**Output**
113+
114+
| service.name | avg_length |
115+
| --------------- | ----------- |
116+
| frontend | 32 |
117+
| checkoutservice | 32 |
118+
| loadgenerator | 31.8 |
119+
120+
This query calculates the average trace ID length per service to verify identifier consistency across the system.
121+
122+
</Tab>
123+
<Tab title="Security logs">
124+
125+
You can check for anomalous user IDs by looking at the length of the `id` field. Very short or very long IDs may signal invalid or suspicious activity.
126+
127+
**Query**
128+
129+
```kusto
130+
['sample-http-logs']
131+
| extend id_length = string_size(id)
132+
| where id_length < 5 or id_length > 20
133+
| project _time, id, id_length, status, ['geo.country']
134+
```
135+
136+
[Run in Playground](https://play.axiom.co/axiom-play-qf1k/query?initForm=%7B%22apl%22%3A%22%5B'sample-http-logs'%5D%20%7C%20extend%20id_length%20%3D%20string_size(id)%20%7C%20where%20id_length%20%3C%205%20or%20id_length%20%3E%2020%20%7C%20project%20_time%2C%20id%2C%20id_length%2C%20status%2C%20%5B'geo.country'%5D%22%7D)
137+
138+
**Output**
139+
140+
| _time | id | id_length | status | geo.country |
141+
| -------------------- | ----------------------------- | ---------- | ------ | ----------- |
142+
| 2025-09-11T09:55:01Z | a12 | 3 | 401 | US |
143+
| 2025-09-11T09:58:42Z | user_long_id_example_test | 24 | 200 | DE |
144+
145+
This query detects requests with suspiciously short or long user IDs, which might indicate invalid credentials or malicious activity.
146+
147+
</Tab>
148+
</Tabs>

apl/scalar-functions/time-series/overview.mdx

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,12 @@ The table summarizes the time series functions available in APL.
1212
| [series_acos](/apl/scalar-functions/time-series/series-acos) | Returns the inverse cosine (arccos) of a series. |
1313
| [series_asin](/apl/scalar-functions/time-series/series-asin) | Returns the inverse sine (arcsin) of a series. |
1414
| [series_atan](/apl/scalar-functions/time-series/series-atan) | Returns the inverse tangent (arctan) of a series. |
15+
| [series_cos](/apl/scalar-functions/time-series/series-cos) | Returns the cosine of a series. |
1516
| [series_greater](/apl/scalar-functions/time-series/series-greater) | Returns the elements of a series that are greater than a specified value. |
1617
| [series_greater_equals](/apl/scalar-functions/time-series/series-greater-equals) | Returns the elements of a series that are greater than or equal to a specified value. |
1718
| [series_less](/apl/scalar-functions/time-series/series-less) | Returns the elements of a series that are less than a specified value. |
1819
| [series_less_equals](/apl/scalar-functions/time-series/series-less-equals) | Returns the elements of a series that are less than or equal to a specified value. |
1920
| [series_not_equals](/apl/scalar-functions/time-series/series-not-equals) | Returns the elements of a series that aren’t equal to a specified value. |
21+
| [series_sin](/apl/scalar-functions/time-series/series-sin) | Returns the sine of a series. |
22+
| [series_sum](/apl/scalar-functions/time-series/series-sum) | Returns the sum of a series. |
23+
| [series_tan](/apl/scalar-functions/time-series/series-tan) | Returns the tangent of a series. |
Lines changed: 153 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,153 @@
1+
---
2+
title: series_cos
3+
description: 'This page explains how to use the series_cos function in APL.'
4+
---
5+
6+
The `series_cos` function returns the cosine of each element in a numeric array. You can use it to apply trigonometric transformations across entire time series or vectorized data in one step. This function is useful when you want to analyze periodic patterns, normalize angles, or apply mathematical transformations to series data such as request durations, response times, or trace latencies.
7+
8+
You often use `series_cos` together with other series functions like `series_sin` and `series_tan` to perform mathematical modeling, anomaly detection, or seasonality analysis in logs and telemetry data.
9+
10+
## For users of other query languages
11+
12+
If you come from other query languages, this section explains how to adjust your existing queries to achieve the same results in APL.
13+
14+
<AccordionGroup>
15+
<Accordion title="Splunk SPL users">
16+
17+
In Splunk SPL, trigonometric functions like `cos` operate on single field values, not on arrays. To compute cosine across multiple values, you typically expand the values into events and then apply the `eval cos(field)` transformation. In APL, `series_cos` works natively on dynamic arrays, so you can directly transform an entire series in one call.
18+
19+
<CodeGroup>
20+
```sql Splunk example
21+
... | eval cos_val=cos(angle)
22+
````
23+
24+
```kusto APL equivalent
25+
print arr=dynamic([0, 1.57, 3.14])
26+
| extend cos_arr=series_cos(arr)
27+
```
28+
29+
</CodeGroup>
30+
31+
</Accordion>
32+
<Accordion title="ANSI SQL users">
33+
34+
ANSI SQL does not provide direct support for array-wide trigonometric functions. The `COS()` function only works on single numeric values. To achieve array-like functionality, you usually need to unnest arrays and apply `COS()` row by row. In APL, `series_cos` eliminates this need by directly accepting an array and returning a transformed array.
35+
36+
<CodeGroup>
37+
```sql SQL example
38+
SELECT COS(angle) AS cos_val
39+
FROM Angles;
40+
```
41+
42+
```kusto APL equivalent
43+
print arr=dynamic([0, 1.57, 3.14])
44+
| extend cos_arr=series_cos(arr)
45+
```
46+
47+
</CodeGroup>
48+
49+
</Accordion>
50+
</AccordionGroup>
51+
52+
## Usage
53+
54+
### Syntax
55+
56+
```kusto
57+
series_cos(array)
58+
```
59+
60+
### Parameters
61+
62+
| Parameter | Type | Description |
63+
| --------- | -------------------------- | --------------------------- |
64+
| `array` | dynamic (array of numbers) | An array of numeric values. |
65+
66+
### Returns
67+
68+
A dynamic array where each element is the cosine of the corresponding input element.
69+
70+
## Use case examples
71+
72+
<Tabs>
73+
<Tab title="Log analysis">
74+
75+
You want to model periodic patterns in request durations by applying the cosine function to the values. This is useful if you want to normalize cyclical metrics for further analysis.
76+
77+
**Query**
78+
79+
```kusto
80+
['sample-http-logs']
81+
| summarize durations=make_list(req_duration_ms) by id
82+
| extend cos_durations=series_cos(durations)
83+
```
84+
85+
[Run in Playground](https://play.axiom.co/axiom-play-qf1k/query?initForm=%7B%22apl%22%3A%22%5B'sample-http-logs'%5D%20%7C%20summarize%20durations%3Dmake_list(req_duration_ms)%20by%20id%20%7C%20extend%20cos_durations%3Dseries_cos(durations)%22%7D)
86+
87+
**Output**
88+
89+
| id | durations | cos_durations |
90+
| -- | ---------------- | ------------------------ |
91+
| u1 | [120, 300, 450] | [0.814, -0.990, -0.737] |
92+
| u2 | [50, 250, 400] | [0.965, -0.801, -0.966] |
93+
94+
This query collects request durations per user ID and applies the cosine transformation to the entire array.
95+
96+
</Tab>
97+
<Tab title="OpenTelemetry traces">
98+
99+
You want to apply trigonometric transformations to span durations to explore cyclical behavior in distributed traces.
100+
101+
**Query**
102+
103+
```kusto
104+
['otel-demo-traces']
105+
| summarize spans=make_list(duration) by ['service.name']
106+
| extend cos_spans=series_cos(spans)
107+
```
108+
109+
[Run in Playground](https://play.axiom.co/axiom-play-qf1k/query?initForm=%7B%22apl%22%3A%22%5B'otel-demo-traces'%5D%20%7C%20summarize%20spans%3Dmake_list(duration)%20by%20%5B'service.name'%5D%20%7C%20extend%20cos_spans%3Dseries_cos(spans)%22%7D)
110+
111+
**Output**
112+
113+
| service.name | spans | cos_spans |
114+
| --------------- | --------------------- | ----------------- |
115+
| frontend | [00:00:01, 00:00:03] | [0.540, -0.990] |
116+
| checkoutservice | [00:00:02, 00:00:04] | [-0.416, -0.653] |
117+
118+
This query groups spans by service and computes the cosine for each span duration, which can be used in advanced mathematical modeling of latency patterns.
119+
120+
</Tab>
121+
<Tab title="Security logs">
122+
123+
You want to explore whether cosine transformations reveal patterns in request durations for suspicious traffic sources.
124+
125+
**Query**
126+
127+
```kusto
128+
['sample-http-logs']
129+
| summarize durations=make_list(req_duration_ms) by ['geo.country']
130+
| extend cos_blocked=series_cos(durations)
131+
```
132+
133+
[Run in Playground](https://play.axiom.co/axiom-play-qf1k/query?initForm=%7B%22apl%22%3A%22%5B'sample-http-logs'%5D%20%7C%20summarize%20durations%3Dmake_list(req_duration_ms)%20by%20%5B'geo.country'%5D%20%7C%20extend%20cos_blocked%3Dseries_cos(durations)%22%7D)
134+
135+
**Output**
136+
137+
| geo.country | blocked_durations | cos_blocked |
138+
| ----------- | ------------------ | ------------------------ |
139+
| US | [200, 400, 600] | [-0.416, -0.653, 0.960] |
140+
| DE | [100, 250, 500] | [0.540, -0.801, 0.284] |
141+
142+
This query applies the cosine function to blocked request durations grouped by country, which can help highlight periodic access attempts from malicious sources.
143+
144+
</Tab>
145+
</Tabs>
146+
147+
## List of related functions
148+
149+
- [series_abs](/apl/scalar-functions/time-series/series-abs): Returns the absolute value of each element in an array. Use it to normalize negative values in arrays.
150+
- [series_acos](/apl/scalar-functions/time-series/series-acos): Computes the arccosine of each element in an array. Use when you want the inverse cosine.
151+
- [series_atan](/apl/scalar-functions/time-series/series-atan): Computes the arctangent of each element in an array. Use when you want the inverse tangent.
152+
- [series_sin](/apl/scalar-functions/time-series/series-sin): Returns the sine of each element in an array. Use it when analyzing cyclical data with a phase shift.
153+
- [series_tan](/apl/scalar-functions/time-series/series-tan): Returns the tangent of each element in an array. Use it when you want to transform arrays with tangent-based periodicity.

0 commit comments

Comments
 (0)