# BigQuery

> Seed BigQuery tables and check the rows your services write.

Source: https://axx.nimbusxr.us/references/packs/gcp-bigquery/

Seed BigQuery tables and check the rows your services write.

The steps use the scenario's project (`the {word} gcp project with the following properties:`, from gcp-core). Tables are named `dataset.table` (in the project) or `project.dataset.table`.

A **seed** is a YAML or JSON file that maps tables to the rows to insert (a streaming insert, `tabledata.insertAll`):

```yaml
billing.carrier_rates:
  - carrier: KESTREL
    service: express
    price_per_kg: 1.35
```

**Checks** wait (10 seconds unless `within {duration}` says otherwise) until the table has a row, or a number of rows, meeting every condition: `column | value` rows, with a dotted path into `RECORD` columns (`address.city`), compared as text: numbers as written, `NUMERIC` as its decimal, `TIMESTAMP` in RFC 3339 (`2026-09-24T09:30:00Z`), `DATE` as `2026-09-24`; `null` for NULL. A check reads the columns its conditions name, of up to 5,000 rows of the table: check the tables your scenarios write, not warehouse-size ones.

Add it to a project with `axx pack add gcp-bigquery`; it builds on [`gcp-core`](https://axx.nimbusxr.us/references/packs/gcp-core/), which comes with it.

## Steps

### `gcp-bigquery.seed`

```gherkin
Given a {filepath} bigquery seed
```

Insert the rows of a seed file into their tables: YAML or JSON that maps tables (`dataset.table` or `project.dataset.table`) to lists of rows. The rows are streamed in (`tabledata.insertAll`).

| Parameter | Takes | For example |
|---|---|---|
| `{filepath}` | a file of the project: a path relative to the feature file's directory, the `resources` directories or axx.yaml's directory (looked for in that order), or an absolute path, quoted when it has a space | `seeds/parcels.yaml`, `kafka/scan-delivered.json` |

**Example:**

```gherkin
Given a seeds/carrier-rates.yaml bigquery seed
```

_Since 0.1.0._

### `gcp-bigquery.row`

```gherkin
Then [[within {duration} ]]the {word} bigquery table has a row where:
  | column | value |
```

The table may start with the row naming its columns, as above, or go straight to its rows.

Check that the table has a row with those values in those columns.

- The check waits for it: 10 seconds, or `within {duration}`.
- Name the table `dataset.table`, or `project.dataset.table` for another project's.
- Values compare as text: numbers as written, `NUMERIC` as its decimal, `TIMESTAMP` in RFC 3339 (`2026-09-24T09:30:00Z`), `DATE` as `2026-09-24`, `DATETIME` as `2026-09-24T09:30:00`, `BYTES` in base64; `null` for NULL.
- The check reads only the columns the step names, of up to 5,000 rows.

| Parameter | Takes | For example |
|---|---|---|
| `{duration}` | a duration in seconds (`s`) or minutes (`m`) | `5s`, `2m` |
| `{word}` | one word, with no spaces | `parcels`, `PX-4101` |

Each row names a column, or a dotted path into a `RECORD` column (`address.city`), and the value in it.

**Variants**, the parts in `[[...]]` said or left out:

- `the {word} bigquery table has a row where:`
- `within {duration} the {word} bigquery table has a row where:`

**Example:**

```gherkin
Then within 30s the billing.invoice_lines bigquery table has a row where:
  | invoice  | INV-2026-09-KES2 |
  | parcel   | PX-5103          |
  | status   | OVERCHARGED      |
  | billed   | 2.5              |
  | expected | 1.35             |
```

_Since 0.1.0._

### `gcp-bigquery.rows`

```gherkin
Then [[within {duration} ]]the {word} bigquery table has {int} row(s) where:
  | column | value |
```

The table may start with the row naming its columns, as above, or go straight to its rows.

Check that exactly that many rows of the table have those values in those columns.

- The check waits for it: 10 seconds, or `within {duration}`.
- Name the table `dataset.table`, or `project.dataset.table` for another project's.
- Values compare as text: numbers as written, `NUMERIC` as its decimal, `TIMESTAMP` in RFC 3339 (`2026-09-24T09:30:00Z`), `DATE` as `2026-09-24`, `DATETIME` as `2026-09-24T09:30:00`, `BYTES` in base64; `null` for NULL.
- The check reads only the columns the step names, of up to 5,000 rows.

| Parameter | Takes | For example |
|---|---|---|
| `{duration}` | a duration in seconds (`s`) or minutes (`m`) | `5s`, `2m` |
| `{word}` | one word, with no spaces | `parcels`, `PX-4101` |
| `{int}` | a whole number | `200`, `3` |

Each row names a column, or a dotted path into a `RECORD` column (`address.city`), and the value in it.

**Variants**, the parts in `[[...]]` said or left out:

- `the {word} bigquery table has {int} row(s) where:`
- `within {duration} the {word} bigquery table has {int} row(s) where:`

**Example:**

```gherkin
Then the billing.invoice_lines bigquery table has 2 rows where:
  | invoice | INV-2026-09-KES1 |
  | status  | MATCHED          |
```

_Since 0.1.0._
