grafana / grafana/github-datasource

Bug: Workflow_Runs query type consistently returns 0 rows when same URL+token directly returns data

Open
#774 0 comments 0 reactions 0 assignees View on GitHub
Dominant language
Go
Stars
310
Forks
70
Avg merge
2d 20h
Merged PRs (30d)
3

Description

# Bug: `Workflow_Runs` query type returns 0 rows when the same URL+token directly returns the expected data

## What you expected to happen

A `Workflow_Runs` query against a valid `owner` / `repository` / `workflow` should return the workflow runs visible to the configured credentials, like:

```
GET /repos/{owner}/{repo}/actions/workflows/{workflow}/runs?created=..
```

would return when called directly.

## What actually happened

The plugin returns `status: 200` with a valid frame schema (14 fields: `id`, `name`, `head_branch`, …) but **all field value arrays are empty** (`[]`). Other query types (`Workflows`, `Issues`, `Pull_Requests`, `Repositories`, `Commits`) against the same datasource work correctly and return populated data.

## Steps to reproduce

1. Configure the datasource against an org with at least one repo and one workflow that has recent runs.
2. Add a panel with query:

```json
{
"queryType": "Workflow_Runs",
"options": {
"owner": "",
"repository": "",
"workflow": ".yml"
}
}
```

3. Set the dashboard time range to a window that contains real runs.
4. Inspect the panel. The query returns no rows.

For reference, the same underlying API endpoint called directly with the exact `created=..` filter the plugin would construct (using either an App installation token or a PAT) returns the expected runs:

```bash
curl -H "Authorization: token $TOKEN" \
-H "Accept: application/vnd.github+json" \
"https://api.github.com/repos///actions/workflows/.yml/runs?created=..&per_page=100"
# → total_count: 12, returns 12 runs
```

## Query inspector evidence

Request body sent by the plugin (captured via Grafana's query inspector):

```json
{
"queries": [{
"refId": "A",
"datasource": { "type": "grafana-github-datasource", "uid": "..." },
"queryType": "Workflow_Runs",
"options": {
"owner": "",
"repository": "",
"workflow": ".yml"
},
"datasourceId": 62,
"intervalMs": 600000,
"maxDataPoints": 1180
}],
"from": "1781300092199",
"to": "1781904892199"
}
```

Plugin response:

```json
{
"results": {
"A": {
"status": 200,
"frames": [{
"schema": {
"name": "workflow_run",
"fields": [
{ "name": "id", "type": "number", ... },
{ "name": "name", "type": "string", ... },
{ "name": "head_branch", ... },
{ "name": "head_sha", ... },
{ "name": "created_at", "type": "time", ... },
{ "name": "updated_at", ... },
{ "name": "run_started_at", ... },
{ "name": "html_url", ... },
{ "name": "url", ... },
{ "name": "status", ... },
{ "name": "conclusion", ... },
{ "name": "event", ... },
{ "name": "workflow_id", ... },
{ "name": "run_number", ... }
]
},
"data": { "values": [[], [], [], [], [], [], [], [], [], [], [], [], [], []] }
}]
}
}
}
```

Schema is correct; values are empty for every field.

## What we ruled out during debugging

We spent a few hours narrowing this down. The matrix of combinations that all produced the same `0 rows` result:

| Variable | Tested | Result |
|---|---|---|
| Plugin version | v2.3.0, v2.5.1, v2.6.0, v2.8.0 | All: 0 rows |
| Auth | GitHub App (ghinstallation) + Personal Access Token | Both: 0 rows |
| Workflow `workflow` value | basename (`x.yml`), numeric ID (``), full path (`.github/workflows/x.yml`) | Basename and ID: 0 rows. Full path: `workflow not found` error (expected). |
| Workflow choice | several different workflows in the same repo | All: 0 rows |
| Repository choice | several different repos in the same org | All: 0 rows |
| Time range | `now-7d`, `now-30d`, explicit epoch ms covering known-good runs | All: 0 rows |
| Direct API call with the same install token / PAT | Same URL the plugin would construct, same `created=..` filter | **Returns the expected runs** (12 in our test) |

App permissions used (verified by minting an installation token via JWT and inspecting `/app/installations/{id}/access_tokens` response):

```json
"permissions": {
"actions": "read",
"contents": "read",
"issues": "read",
"metadata": "read",
"pull_requests": "read"
}
```

`repository_selection: "all"`.

## Environment

- Grafana: `12.1.1`
- Plugin: confirmed across `2.3.0`, `2.5.1`, `2.6.0`, `2.8.0`
- Auth tested: GitHub App (with valid permissions including `actions: read`) and Personal Access Token (with `repo, workflow, read:org` scopes)
- Cluster: EKS, plugin running in the official Grafana Helm chart deployment
- Other query types from this plugin against the same datasource all work: `Workflows` (lists workflows), `Issues`, `Pull_Requests`, `Repositories`, `Commits`

## Possible related fix

PR #526 (fixes #503) addressed a similar "0 rows" problem in the `Workflows` query type — root cause was in `pkg/models/workflows.go` / `pkg/github/workflows.go` around `CreatedAt`/`UpdatedAt` time filtering with nil-handling and the addition of a `None` time field option.

`Workflow_Runs` does not expose a similar `None` option (the time filter is always applied based on the dashboard time range, constructed inside `pkg/github/client/client.go` as `created=..`). It's plausible the same underlying issue with time filter construction affects this query type but is not covered by #526's fix.

## Hypothesis

The fact that:

- The plugin returns HTTP 200 (so the call to GitHub succeeded)
- The schema is fully populated (14 expected fields)
- Yet `data.values` arrays are all empty
- And a manual curl with the exact same URL+token returns runs

…suggests something between the GitHub response and the frame serialization is dropping rows. The fact that PR #526's fix on the `Workflows` query type added "improve time filtering logic with better nil handling" makes me suspect the same neighborhood — perhaps the response is being parsed and rows are filtered out by some predicate that shouldn't apply.

I'd be happy to add more diagnostic information (debug-level logs from the plugin, network trace) if useful — please indicate what would help most.

## Workaround

For now we removed the `Workflow_Runs`-based panels from our dashboard and use only the query types that work (`Workflows`, `Issues`, `Pull_Requests`, `Repositories`). Workflow-run metrics remain unavailable to us via this plugin.

---

Contributor guide

Open the contributing guide

Research direction

Trace the Workflow_Runs query from its handler into pkg/github/client/client.go, then compare the time-filtering and response handling with pkg/models/workflows.go and pkg/github/workflows.go, which are implicated by PR #526. Reproduce the empty frame using the supplied query and compare the constructed request with the successful curl; done means known runs populate all 14 fields for the selected dashboard range.

Written by the indexing model from the issue text.

Assessment

Tech stack
github, go
Domain
api, backend
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
52/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.