Search Scripting API

The scripting API was developed to allow easy access to search and aggregation functionality via API calls. The scripting API provides only one dataset, one list of messages, or the results of one aggregation. Most of the request parameters are optional to further simplify the process.

Response content types differ based on the provided accept header. Supported values are:

  • text/plain

  • text/csv

  • application/json

Although plaintext and CSV responses have different formats, they contain the same amount of data. Compared to these, the JSON response contains more information about the columns in the schema property and effective time range in the metadata property.

Search Messages

This endpoint allows direct access to messages from the search page. Messages are sorted by timestamp with the most recent first by default. A typical use would be to obtain the latest X amount of messages (default is 10), where you define which fields in the response are relevant.

GET https://example.org/api/search/messages?fields=source,

http_method,http_response_code,took_ms

POST https://example.org/api/search/messages

Copy
{
    "query": "http_method:POST",
    "streams": ["620f890b70fb980467aca611"],
    "fields": [
        "timestamp",
        "source",
        "http_method",
        "http_response_code",
        "took_ms"
    ],
    "from": 2,
    "size": 15,
    "timerange": {
        "type": "keyword",
        "keyword": "last five minutes"
    },
    "sort": "took_ms",
    "sort_order": "desc"
}

GET requests accept the same parameters as POST requests. The only exception is that POST requests accept time ranges. The time range parameter accepts: relative, absolute, and keyword. For more information about the time frame selector, please see this Graylog documentation.

Hint:  The default for the streams, sources, and inputs endpoints is title. To display the ID append the item name with .id.

Example Requests and Responses

Here are some sample requests and responses. The text/csv, text/plain and application/json values in the accept header determine the format of the response you get back.

Copy
➜  curl  -H 'Accept: text/csv' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/messages?fields=source,http_method,http_response_code,took_ms'
"field: source","field: http_method","field: http_response_code","field: took_ms"
"example.org","GET","200","36"
"example.org","GET","200","36"
"example.org","GET","200","48"
"example.org","PUT","200","129"
"example.org","POST","201","134"
"example.org","POST","201","134"
"example.org","GET","200","52"
"example.org","GET","200","48"
"example.org","GET","200","48"
"example.org","GET","200","63"

 

Copy
➜  curl  -H 'Accept: text/plain' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/messages?fields=source,http_method,http_response_code,took_ms'
┌────────────────────────┬────────────────────────┬────────────────────────┬───────────────────────┐
│field: source           │field: http_method      │field:                  │field: took_ms         │
│                        │                        │http_response_code      │                       │
├────────────────────────┼────────────────────────┼────────────────────────┼───────────────────────┤
│example.org             │GET                     │200                     │56                     │
│example.org             │GET                     │200                     │45                     │
│example.org             │GET                     │200                     │44                     │
│example.org             │GET                     │200                     │56                     │
│example.org             │GET                     │200                     │42                     │
│example.org             │DELETE                  │204                     │89                     │
│example.org             │DELETE                  │204                     │89                     │
│example.org             │GET                     │200                     │38                     │
│example.org             │GET                     │200                     │38                     │
│example.org             │DELETE                  │204                     │95                     │
└────────────────────────┴────────────────────────┴────────────────────────┴───────────────────────┘%     

 

Copy
➜  curl  -H 'Accept: application/json' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/messages?fields=source,http_method,http_response_code,took_ms'
{
  "schema": [
    {
      "column_type": "field",
      "type": "unknown",
      "field": "source",
      "name": "field: source"
    },
    {
      "column_type": "field",
      "type": "string",
      "field": "http_method",
      "name": "field: http_method"
    },
    {
      "column_type": "field",
      "type": "unknown",
      "field": "http_response_code",
      "name": "field: http_response_code"
    },
    {
      "column_type": "field",
      "type": "numeric",
      "field": "took_ms",
      "name": "field: took_ms"
    }
  ],
  "datarows": [
    [
      "example.org",
      "GET",
      200,
      50
    ],
    [
      "example.org",
      "GET",
      200,
      50
    ],
    [
      "example.org",
      "GET",
      200,
      55
    ],
    [
      "example.org",
      "GET",
      200,
      63
    ],
    [
      "example.org",
      "GET",
      200,
      63
    ],
    [
      "example.org",
      "GET",
      200,
      63
    ],
    [
      "example.org",
      "GET",
      200,
      37
    ],
    [
      "example.org",
      "GET",
      200,
      46
    ],
    [
      "example.org",
      "GET",
      200,
      59
    ],
    [
      "example.org",
      "GET",
      200,
      52
    ]
  ],
  "metadata": {
    "effective_timerange": {
      "from": "2023-04-05T09:08:23.193Z",
      "to": "2023-04-06T09:08:23.193Z",
      "type": "absolute"
    }
  }

Aggregations

This endpoint allows executing one aggregation with several groupings and metrics. For example, you could group messages with HTTP requests by using a HTTP method and response code. You could also find the minimum and maximum response times for these groups.

Requests in GET and POST format retrieve the same data. POST requests allow additional configuration options that are not available in GET format. For example, with POST requests you can define limit and sort when grouping aggregations.

 

GET https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count

POST https://example.org/api/search/aggregate

Copy
{
    "query": "source:example.org",
    "streams": [
        "620f890b70fb980467aca611"
    ],
    "timerange": {
        "type": "keyword",
        "keyword": "last five minutes"
    },
    "group_by": [
        {
            "field": "http_method"
        },
        {
            "field": "http_response_code",
            "limit": 2
        }
    ],
    "metrics": [
        {
            "function": "min",
            "field": "took_ms"
        },
        {
            "function": "max",
            "field": "took_ms",
            "sort": "desc"
        }
    ]
}

Metrics are defined asfunction:field_namepairs. With POST requests you can additionally define metrics with sort. POST requests allow you to include more information than is possible with GET requests.

The percentile metric can also be further configured as so:

Copy
{
        "function": "percentile",
        "field": "took_ms",
        "configuration": 
        {"percentile": 90}
}

Other available metric functions are: average, count, latest, max, min, percentile, stdDev, sum, sumOfSquares, and variance.

Example Requests and Responses

Here are some sample requests and responses for aggregations. The text/plain, text/csv, and application/json values in the Accept header determine the format of the response you get back.

Copy
➜  curl  -H 'Accept: text/plain' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count'
┌────────────────────────┬────────────────────────┬───────────────────────┐
│grouping: http_method   │metric: avg(took_ms)    │metric: count()        │
├────────────────────────┼────────────────────────┼───────────────────────┤
│GET                     │84.59519448510214       │3326553                │
│DELETE                  │96.02973055642204       │330199                 │
│POST                    │170.11398232130765      │329323                 │
│PUT                     │132.19959919839678      │154690                 │
└────────────────────────┴────────────────────────┴───────────────────────┘

 

Copy
➜  curl  -H 'Accept: text/csv' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count'
"grouping: http_method","metric: avg(took_ms)","metric: count()"
"GET","84.58997204888469","3326522"
"DELETE","96.02450487553752","330220"
"POST","170.08947537817832","329342"
"PUT","132.2030966157029","154685"

 

Copy
➜ curl  -H 'Accept: application/json' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count'
{
  "schema": [
    {
      "column_type": "grouping",
      "type": "string",
      "field": "http_method",
      "name": "grouping: http_method"
    },
    {
      "column_type": "metric",
      "type": "numeric",
      "function": "avg",
      "field": "took_ms",
      "name": "metric: avg(took_ms)"
    },
    {
      "column_type": "metric",
      "type": "numeric",
      "function": "count",
      "name": "metric: count()"
    }
  ],
  "datarows": [
    [
      "GET",
      84.6043288978779,
      3326528
    ],
    [
      "DELETE",
      96.02355285311111,
      330236
    ],
    [
      "POST",
      170.09012904205252,
      329350
    ],
    [
      "PUT",
      132.20231038249952,
      154693
    ]
  ],
  "metadata": {
    "effective_timerange": {
      "from": "2023-04-05T09:14:39.731Z",
      "to": "2023-04-06T09:14:39.731Z",
      "type": "absolute"
    }
  }
}
Copy
{
    "query": "http_method:POST",
    "streams": ["620f890b70fb980467aca611"],
    "fields": [
        "timestamp",
        "source",
        "http_method",
        "http_response_code",
        "took_ms"
    ],
    "from": 2,
    "size": 15,
    "timerange": {
        "type": "keyword",
        "keyword": "last five minutes"
    },
    "sort": "took_ms",
    "sort_order": "desc"
}
Copy
➜  curl  -H 'Accept: text/csv' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/messages?fields=source,http_method,http_response_code,took_ms'
"field: source","field: http_method","field: http_response_code","field: took_ms"
"example.org","GET","200","36"
"example.org","GET","200","36"
"example.org","GET","200","48"
"example.org","PUT","200","129"
"example.org","POST","201","134"
"example.org","POST","201","134"
"example.org","GET","200","52"
"example.org","GET","200","48"
"example.org","GET","200","48"
"example.org","GET","200","63"
Copy
➜  curl  -H 'Accept: text/plain' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/messages?fields=source,http_method,http_response_code,took_ms'
┌────────────────────────┬────────────────────────┬────────────────────────┬───────────────────────┐
│field: source           │field: http_method      │field:                  │field: took_ms         │
│                        │                        │http_response_code      │                       │
├────────────────────────┼────────────────────────┼────────────────────────┼───────────────────────┤
│example.org             │GET                     │200                     │56                     │
│example.org             │GET                     │200                     │45                     │
│example.org             │GET                     │200                     │44                     │
│example.org             │GET                     │200                     │56                     │
│example.org             │GET                     │200                     │42                     │
│example.org             │DELETE                  │204                     │89                     │
│example.org             │DELETE                  │204                     │89                     │
│example.org             │GET                     │200                     │38                     │
│example.org             │GET                     │200                     │38                     │
│example.org             │DELETE                  │204                     │95                     │
└────────────────────────┴────────────────────────┴────────────────────────┴───────────────────────┘%     
Copy
➜  curl  -H 'Accept: application/json' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/messages?fields=source,http_method,http_response_code,took_ms'
{
  "schema": [
    {
      "column_type": "field",
      "type": "unknown",
      "field": "source",
      "name": "field: source"
    },
    {
      "column_type": "field",
      "type": "string",
      "field": "http_method",
      "name": "field: http_method"
    },
    {
      "column_type": "field",
      "type": "unknown",
      "field": "http_response_code",
      "name": "field: http_response_code"
    },
    {
      "column_type": "field",
      "type": "numeric",
      "field": "took_ms",
      "name": "field: took_ms"
    }
  ],
  "datarows": [
    [
      "example.org",
      "GET",
      200,
      50
    ],
    [
      "example.org",
      "GET",
      200,
      50
    ],
    [
      "example.org",
      "GET",
      200,
      55
    ],
    [
      "example.org",
      "GET",
      200,
      63
    ],
    [
      "example.org",
      "GET",
      200,
      63
    ],
    [
      "example.org",
      "GET",
      200,
      63
    ],
    [
      "example.org",
      "GET",
      200,
      37
    ],
    [
      "example.org",
      "GET",
      200,
      46
    ],
    [
      "example.org",
      "GET",
      200,
      59
    ],
    [
      "example.org",
      "GET",
      200,
      52
    ]
  ],
  "metadata": {
    "effective_timerange": {
      "from": "2023-04-05T09:08:23.193Z",
      "to": "2023-04-06T09:08:23.193Z",
      "type": "absolute"
    }
  }
Copy
{
    "query": "source:example.org",
    "streams": [
        "620f890b70fb980467aca611"
    ],
    "timerange": {
        "type": "keyword",
        "keyword": "last five minutes"
    },
    "group_by": [
        {
            "field": "http_method"
        },
        {
            "field": "http_response_code",
            "limit": 2
        }
    ],
    "metrics": [
        {
            "function": "min",
            "field": "took_ms"
        },
        {
            "function": "max",
            "field": "took_ms",
            "sort": "desc"
        }
    ]
}
Copy
{
        "function": "percentile",
        "field": "took_ms",
        "configuration": 
        {"percentile": 90}
}
Copy
➜  curl  -H 'Accept: text/plain' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count'
┌────────────────────────┬────────────────────────┬───────────────────────┐
│grouping: http_method   │metric: avg(took_ms)    │metric: count()        │
├────────────────────────┼────────────────────────┼───────────────────────┤
│GET                     │84.59519448510214       │3326553                │
│DELETE                  │96.02973055642204       │330199                 │
│POST                    │170.11398232130765      │329323                 │
│PUT                     │132.19959919839678      │154690                 │
└────────────────────────┴────────────────────────┴───────────────────────┘
Copy
➜  curl  -H 'Accept: text/csv' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count'
"grouping: http_method","metric: avg(took_ms)","metric: count()"
"GET","84.58997204888469","3326522"
"DELETE","96.02450487553752","330220"
"POST","170.08947537817832","329342"
"PUT","132.2030966157029","154685"
Copy
➜ curl  -H 'Accept: application/json' -H 'X-Requested-By: cli'  -u username:password 'https://example.org/api/search/aggregate?groups=http_method&metrics=avg:took_ms&metrics=count'
{
  "schema": [
    {
      "column_type": "grouping",
      "type": "string",
      "field": "http_method",
      "name": "grouping: http_method"
    },
    {
      "column_type": "metric",
      "type": "numeric",
      "function": "avg",
      "field": "took_ms",
      "name": "metric: avg(took_ms)"
    },
    {
      "column_type": "metric",
      "type": "numeric",
      "function": "count",
      "name": "metric: count()"
    }
  ],
  "datarows": [
    [
      "GET",
      84.6043288978779,
      3326528
    ],
    [
      "DELETE",
      96.02355285311111,
      330236
    ],
    [
      "POST",
      170.09012904205252,
      329350
    ],
    [
      "PUT",
      132.20231038249952,
      154693
    ]
  ],
  "metadata": {
    "effective_timerange": {
      "from": "2023-04-05T09:14:39.731Z",
      "to": "2023-04-06T09:14:39.731Z",
      "type": "absolute"
    }
  }
}