# Parameters and request types

> Every PacketStream Search API request field, the Google surface each request type searches, the options each type accepts, and batch searches.

**Early beta.** Fields, limits, and availability may change during the beta. These pages describe what the API serves today. Questions or problems? [Contact support](https://packetstream.io/contact-us/).

Send the fields as a JSON body with `POST /v1/search`, or as query parameters with `GET /v1/search`. Only `query` is required.

```bash
curl -s https://api.packetstream.io/v1/search \
  -H "Authorization: Bearer $PACKETSTREAM_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"query": "espresso machines", "type": "shopping", "country": "gb", "page": 2}'
```

The same search as a GET:

```bash
curl -s -G https://api.packetstream.io/v1/search \
  -H "Authorization: Bearer $PACKETSTREAM_API_KEY" \
  --data-urlencode "query=espresso machines" \
  --data-urlencode "type=shopping" \
  --data-urlencode "country=gb" \
  --data-urlencode "page=2"
```

## Request fields

| Field | Type | Default | Description |
| --- | --- | --- | --- |
| `query` | string | required | The search text. Google operators such as `site:` pass through. 1 to 400 bytes after trimming, or 1 to 200 bytes for `autocomplete`. |
| `type` | string | `search` | What to search: web results, news, shopping, and so on. One of the [request types](https://packetstream.io/docs/search-api/parameters/#request-types), case-insensitive. |
| `country` | string | `us` | The country to search from. Two-letter ISO 3166-1 code, case-insensitive. |
| `language` | string | none | Google interface language. Up to 10 bytes, such as `en`, `de`, or `pt-BR`. |
| `location` | string | none | Canonical Google location name, such as `Austin,Texas,United States`. 1 to 200 bytes. Cannot be combined with `uule`. |
| `uule` | string | none | Encoded Google location token. Up to 512 bytes. Cannot be combined with `location`. Never echoed in responses. |
| `page` | integer | `1` | Result page. 1 to 10. |
| `device` | string | `desktop` | Device to search as. `desktop` or `mobile`. Mobile results usually carry fewer rich blocks. |
| `time_range` | string | none | Only return results from this recent period. `hour`, `day`, `week`, `month`, or `year`. |
| `safe_search` | boolean | `false` | `true` filters explicit results. |
| `google_domain` | string | none | Google domain to search, such as `google.co.uk`. Up to 32 bytes, case-insensitive. |
| `autocorrect` | boolean | `true` | `false` searches the query exactly as written. |
| `format` | string | `json` | Response format. `json` or `markdown`. Errors are always JSON. See [Markdown format](https://packetstream.io/docs/search-api/responses/#markdown-format). |

Validation rules:

- Unknown, repeated, and mistyped fields return `400 invalid_request`. The message names the field, for example `unknown request field "engine"`.
- A JSON `null` counts as an omitted field.
- In a GET, booleans are `true` or `false`, integers are plain decimal digits, and each parameter may appear once.
- A POST body may be at most 4,096 bytes, and so may a GET query string.

## Request types

Each type accepts only the options listed. Any other option returns `400 unsupported_option` before any charge, for example `device is not supported for type news`. Sending an option's default value, such as `"device": "desktop"` or `"page": 1`, is always accepted. `format` works with every type, and every type costs the same.

| Type | Returns | Options |
| --- | --- | --- |
| `search` | Google web results in `results`, plus [rich blocks](https://packetstream.io/docs/search-api/responses/#web-search-blocks) when Google shows them. | Every option |
| `news` | Google News articles. | `country`, `language`, `page` |
| `shopping` | Google Shopping offers. | `country`, `language`, `page` |
| `places` | Google Maps places. | `country`, `language` |
| `autocomplete` | Google query suggestions. | `country`, `language` |
| `scholar` | Google Scholar publications. | `language`, `page` |
| `ai_mode` | A Google AI Mode answer in `ai_mode`, with its references. No `results` list. | `country`, `language` |

The API never drops an option silently. If no search source can serve a supported combination at the moment, the request fails with `400 unsupported_option` and is not billed.

[Responses](https://packetstream.io/docs/search-api/responses/#result-items-by-type) lists the fields each type returns.

## Batch searches

`POST /v1/search/batch` runs 1 to 10 searches in one request:

```bash
curl -s https://api.packetstream.io/v1/search/batch \
  -H "Authorization: Bearer $PACKETSTREAM_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"searches": [
        {"query": "coffee grinders"},
        {"query": "coffee grinders", "type": "shopping"},
        {"query": "coffee grinders", "type": "news", "device": "mobile"}
      ]}'
```

The body is one JSON object whose only field is `searches`, an array of 1 to 10 items. Each item takes the [request fields](https://packetstream.io/docs/search-api/parameters/#request-fields), and its `format` can only be `json`. The body may be at most 16 KiB.

The response lists one entry per item, in request order. Each entry has the item's `index`, the HTTP `status` the item would have received on its own, and either the full [search response](https://packetstream.io/docs/search-api/responses/) or an `error`. In this shape, `…` stands for the left-out search fields:

```text
{
  "request_id": "0b8f6c3e-5a2d-4c71-9e40-7d1f2a6b9c58",
  "results": [
    { "index": 0, "status": 200, "request_id": "0b8f6c3e-…", "search": {…}, "results": […], "charged_units": 1, … },
    { "index": 1, "status": 200, "request_id": "0b8f6c3e-…", "search": {…}, "results": […], "charged_units": 1, … },
    { "index": 2, "status": 400, "error": { "code": "unsupported_option", "message": "device is not supported for type news" } }
  ],
  "charged_units": 2
}
```

- A valid batch returns HTTP 200 even when some items fail, so check each entry's `status`.
- Each item is a separate search. It is validated, rate-limited, checked against your balance, billed, and logged like a single search. The top-level `charged_units` counts the successful items.
- Entries share the batch `request_id`. The request ID and `index` together identify an item.
- Items are admitted in order, so when the rate limit or your balance runs out, later items fail first. A 10-item batch uses the key's whole burst of 10.
- Items run at the same time and share one 25-second deadline.
- A malformed body, such as one without `searches` or with more than 10 items, returns `400 invalid_request` for the whole request.
