Skip to content

Pre-flight manual

Install Houston

Houston is a standard Laravel app. Clone it, run composer setup, give it a GitHub token, and keep a queue worker and the scheduler running. On a laptop that takes a few commands.

  • MIT
  • PHP 8.5.12+
  • Node 22
  • SQLite by default
  • No Docker needed

Requirements

What Houston needs
PHP8.5.12 or newer
Composer2
Node and npmNode 22, to build the frontend
DatabaseSQLite by default; any database Laravel supports works
GitHubThe GitHub CLI, or a token that can read the repositories you want to measure

Step 1

Clone and set up

git clone https://github.com/vistik/houston.git
cd houston
composer setup

composer setup runs these, in order:

  1. 1composer install for the PHP dependencies
  2. 2copies .env.example to .env if there is no .env yet
  3. 3php artisan key:generate
  4. 4php artisan migrate --force to create the tables
  5. 5npm install and npm run build for the frontend

Step 2

Connect GitHub

Houston talks to GitHub with one token. Pick one of the two.

On your own machine: the GitHub CLI

gh auth login

When GITHUB_TOKEN is empty, Houston uses the CLI's token (gh auth token).

On a server: a token in .env

GITHUB_TOKEN=[your token]

A classic token needs no scopes for public repositories and the repo scope for private ones.

A fine-grained token needs read access to these repository permissions:
PermissionUsed for
MetadataRepository details
Pull requestsPull requests and reviews
ActionsWorkflow runs
DeploymentsDeployments
ContentsReleases and commit timestamps

Step 3

Run it

On your laptop

composer dev

This runs php artisan dev, which starts, side by side:

  • web server php artisan serve
  • scheduler php artisan schedule:work
  • queue worker php artisan queue:listen
  • log tail php artisan pail
  • Vite npm run dev

Then open http://localhost:8000. If Laravel Herd already serves the app, its .test address works too.

On a long-running server

Serve the app like any Laravel app, then keep two processes running: a queue worker for the syncs, and the scheduler.

php artisan queue:work

For the scheduler, either keep php artisan schedule:work running, or add the usual Laravel cron entry:

* * * * * cd /path/to/Houston && php artisan schedule:run >> /dev/null 2>&1

What the scheduler runs

houston:sync --queue
every 15 minutes, never overlapping: refreshes every watched repository
model:prune
daily: prunes old system events

Step 4

Add repositories

  1. 1Open Houston and click Watch repository.
  2. 2Enter owner/name, or paste the repository's GitHub URL.

A sync is queued straight away. The first one pulls the lookback window, 180 days by default, and can take a while on busy repositories. It pauses before it runs into GitHub's rate limits and resumes when they reset. Follow it under Settings → Syncs, where you can also change each repository's lookback window.

Want to see it work before pointing it at your own code? Watch a busy public repository such as laravel/framework.

From the command line:

php artisan houston:sync                    # every watched repository
php artisan houston:sync laravel/framework  # one repository
php artisan houston:sync --queue            # dispatch to the queue instead

Step 5

Teams and benchmarks

Teams

Create them under Settings → Teams and add people by their GitHub login, with the day they joined and, later, the day they left. Work counts for the team someone was on when they did it.

Benchmarks

Off until you set targets. Under Settings → Benchmarks, set your own, or add the 31 built-in standards (DORA, LinearB and suggested targets) with one click.

Step 6

Connect an AI assistant (MCP)

Houston runs a read-only MCP server with three tools (list-repositories, get-velocity-report, list-pull-requests) and a give-feedback prompt.

Locally, over stdio

Point your client at php artisan mcp:start houston. With Claude Code:

claude mcp add houston -- php /path/to/Houston/artisan mcp:start houston

Any other client, in its JSON config:

{
  "mcpServers": {
    "houston": {
      "command": "php",
      "args": ["/path/to/Houston/artisan", "mcp:start", "houston"]
    }
  }
}

Over HTTP, with a token

Set HOUSTON_MCP_TOKEN in .env to a long random string, then send it as a bearer token to /mcp:

claude mcp add --transport http houston http://localhost:8000/mcp \
    --header "Authorization: Bearer $HOUSTON_MCP_TOKEN"
No token set
404, endpoint off
Wrong or missing
401
Matching token
read-only access

Step 7

Configuration

Everything Houston-specific lives in config/houston.php and can be set from .env. Report defaults (period, grouping and the timezone every report is shown in) and benchmarks are set in the app under Settings.

Environment variables, defaults and what they do
GITHUB_TOKENgh auth tokenThe token used to talk to GitHub. Empty falls back to the GitHub CLI's token.
HOUSTON_GITHUB_RATE_LIMIT_RESERVE50Syncs pause when fewer requests are left, leaving room for anything else using the token.
HOUSTON_LOOKBACK_DAYS180Days of history a fresh sync pulls. Keep it at least twice the longest period you report on. Can be set per repository.
HOUSTON_STALE_AFTER_MINUTES15Viewing a repository whose cache is older than this queues a refresh.
HOUSTON_STALE_PR_DAYS7Open pull requests without activity for this long are flagged as stale.
HOUSTON_WORKING_DAYS1,2,3,4,5Working days as ISO day numbers (1 is Monday).
HOUSTON_WORKDAY_START / _END00:00 / 24:00Working hours. Use all seven days and 00:00 to 24:00 to measure calendar time.
HOUSTON_DEPLOY_ENVIRONMENT_PATTERN/^(prod|production|live)\b/iDeployments to a matching environment count for delivery metrics. Without them, published releases are used.
HOUSTON_REMEDIATION_PATTERN/^(revert|hotfix|rollback)\b/iPull requests whose title, branch or label matches count as remediations, which drive the change failure rate.
HOUSTON_MCP_TOKENemptyEnables the MCP endpoint at /mcp for clients that send this bearer token.
HOUSTON_AUTHtrueAsks for the single login before showing anything. php artisan houston:install creates the login; until then visitors see this guide.
HOUSTON_LANDINGfalseShows this website at / and /install. The app is at /dashboard either way; without the website, / goes straight there.

Security: authorized personnel only

  • Houston asks for its single login by default, and shows this guide until the login exists: php artisan houston:install creates it, or turns the login off with HOUSTON_AUTH=false. There are no per-user accounts.
  • Only /mcp is protected, by HOUSTON_MCP_TOKEN, and it is off until you set one.
  • Only turn the login off on localhost or a private network or VPN. On a public server, keep it on.

Houston standing by.

Star the repo to follow along, or open an issue if a step above didn't work for you.