Skip to content

Add a docker compose Redash sandbox with seed data for trying rdsh end to end - #55

Merged
178inaba merged 5 commits into
mainfrom
feature/54-add-redash-sandbox
Aug 25, 2026
Merged

Add a docker compose Redash sandbox with seed data for trying rdsh end to end#55
178inaba merged 5 commits into
mainfrom
feature/54-add-redash-sandbox

Conversation

@178inaba

@178inaba 178inaba commented Aug 25, 2026

Copy link
Copy Markdown
Owner

Why

rdsh's tests all run against an in-process fake (internal/redash/redash_test.go), so nothing in the repository exercises the CLI against a real Redash. Checking a change by hand meant pointing rdsh at a production instance. This adds a throwaway local Redash with a data source and some data already in it, so rdsh run / rdsh query create / rdsh query update can be tried end to end on a laptop.

What

  • compose.yamlserver, scheduler, one worker consuming every queue, redis:7-alpine and postgres:17-alpine, all behind a redash profile so that no compose invocation that does not name the profile — docker compose run --rm lint above all — picks them up. Trimmed from the official setup compose: no nginx, one worker instead of three, and fixed secrets in the clear, since the instance is local and disposable. The lint service and the header comment that pins golangci-lint are untouched.
  • scripts/redash-seed.sql — mounted into the postgres image's docker-entrypoint-initdb.d. Creates a testdata database with signups (40 rows) and events (120 rows), whose columns cover what --param-type can express: a date, a timestamp, numbers and text.
  • scripts/redash-up.sh — creates the schema before the server starts, the admin user, a fixed API key and the data source, skipping whatever is already done, then prints the two export lines. --reset throws the Redash containers and volume away first.
  • README.md — a ### Redash sandbox subsection under ## Development.

No Go code changed, so the output format, the exit codes, skills/rdsh/SKILL.md, the cobra help strings and the plugin descriptions are all as they were. .github/dependabot.yml needed no change either.

Trying it

eval "$(scripts/redash-up.sh)"
rdsh run --data-source sandbox "SELECT count(*) FROM signups"

The first run pulls the Redash image, so give it a few minutes. Everything after that is seconds.

Decisions worth knowing about

The image tag is repeated on all three Redash services rather than living in the x-redash anchor. Dependabot's docker-compose ecosystem reads services.<name>.image; a tag hidden in a top-level extension field may never be bumped, and keeping the sandbox on the release users actually run is the reason these services live in compose.yaml at all instead of a separate file. Worth watching after this merges — the repository has no docker-compose Dependabot PR yet, so that behaviour is inferred from the documented ecosystem rather than observed here.

The sandbox is published on 127.0.0.1:15000, not 5000. Redash's own port cannot move — the image's entrypoint hardcodes gunicorn -b [::]:5000 — but 5000 is often already taken on a developer machine, and 15000 stays below the ephemeral range on both macOS and Linux. This is the one deviation from the issue, which named 5000.

The loopback half of that is deliberate rather than incidental: the admin password and the API key are fixed values committed in the clear, and Redash connects to whatever host a data source names, so an instance answering the LAN is a pivot into the network around it. Nothing about a throwaway sandbox needs to be reachable from another machine.

All of the script's own output goes to stderr. docker compose run forwards the container's output to the script's stdout, so redirecting each command individually would eventually leak a stray line into eval. main "$@" >&2 makes stdout structurally incapable of carrying anything but the two export lines; set -e means a failure never reaches them at all.

Two upstream details shape the script. The image's entrypoint passes manage arguments through an unquoted $*, so the data source's --options JSON must not contain a space. And manage users create_root exits 1 when the user already exists, so its existence check has to gate the call rather than tolerate a failure — which is why all three setup steps are guarded by a psql query instead.

--reset runs docker compose --profile redash down without -v, then removes the Redash volume by name. -v would take the gomod-cache and lint-cache volumes with it. The volume carries a fixed name: in compose.yaml so it can be named on its own, rather than through a project prefix that follows the checkout directory.

Rejected: a separate e2e/compose.yaml (takes the images out of Dependabot's view and adds a second entry point; the profile gives the same isolation), an interpolated ${REDASH_VERSION:-...} tag (Dependabot cannot bump one), and a Makefile or CONTRIBUTING.md for three one-line tasks.

Verified

Every acceptance criterion was run on an arm64 machine with Docker.

Results
# Criterion Result
1 eval "$(scripts/redash-up.sh)" && rdsh run --data-source sandbox "SELECT count(*) FROM signups" on a clean checkout prints 40, no config file involved
2 run the filtered SQL, then query create with since=2026-01-01 / --param-type since=date query page carries a result (latest_query_data_id set, the three expected rows on /api/queries/1/results.json), parameter stored as {"name":"since","type":"date","value":"2026-01-01"}
3 second run against the running stack exits 0, user/data-source/API-key state byte-identical, stdout exactly the same two lines
4 --reset on an initialised stack criteria 1 and 2 pass again; rdsh_gomod-cache and rdsh_lint-cache survive
5 tag changed to redash/redash:25.8.0 + --reset starts, manage.py version reports 25.8.0, criterion 1 passes; tag restored afterwards
6 docker compose run --rm lint, go test -race ./..., yq '.services.lint.image' compose.yaml 0 issues, all packages ok, reads golangci/golangci-lint:v2.12.2; no Redash service starts
7 admin login at the UI POST /login with admin@example.com / sandbox returns 302 to / with a session cookie; a wrong password does not

The seed data was checked directly too: 40 signups, 120 events, dates spanning 2025-11-04 to 2026-03-01 with 20 rows at or after 2026-01-01, so the >= '2026-01-01' filter in criterion 2 returns a proper subset rather than everything.

Out of scope

Go end-to-end tests against this stack (//go:build e2e) and a CI job that starts it, per the issue. Until those exist, a Dependabot bump of the Redash image is not verified automatically.

Closes #54

rdsh's tests run against an in-process fake, so trying the CLI against a
real Redash meant pointing it at a production instance. These services,
behind a `redash` profile so no existing compose invocation picks them up,
bring one up locally with a seeded database to query.
The stack needs the schema created before the server starts, an admin user,
a fixed API key and a data source pointing at the seed database. Doing that
by hand every time is what kept the sandbox from being useful, so the script
does it, skips whichever steps are already done, and prints the two export
lines that configure rdsh.
Where the fixed admin login, the mandatory --data-source and the teardown
and version-switch commands live, so the values the script hard-codes are
written down in the place a developer looks first.
@178inaba 178inaba self-assigned this Aug 25, 2026
Its admin password and API key are fixed values committed in the clear, and
Redash connects to whatever host a data source names, so an instance
answering the LAN is a pivot into the network it sits on. Nothing about the
sandbox needs to be reachable from another machine.
The five-minute deadline is only checked between attempts, so a port that
accepts a connection and then never answers — the state Redash passes
through while it boots — could block one curl far longer than the deadline.
@178inaba
178inaba merged commit 784bf20 into main Aug 25, 2026
2 checks passed
@178inaba
178inaba deleted the feature/54-add-redash-sandbox branch August 25, 2026 12:48
@daemon-bot daemon-bot Bot mentioned this pull request Aug 30, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add a docker compose Redash sandbox with seed data for trying rdsh end to end

1 participant