# How Better Stack uses Better Stack MCP

## Running our whole observability stack from our terminals

![BS_mcp-blog-cover_edge_2400x1260.png](https://imagedelivery.net/xZXo0QFi-1_4Zimer-T0XQ/abd11feb-403a-464a-5ab9-a1371380f000/lg2x =2400x1260)

The feature our team loves most is our MCP server. Every one of our engineers keeps it connected to their coding agent, and a few of them would rather lose their second monitor. Here’s one working day pieced together from real sessions across our engineering team, plus the prompts we use, so you can steal them.

The first thing that’s true is that agents read far more than they write. Over seven weeks our engineer Andrej (well, his agents) made about 3,300 MCP calls, and almost all of them were SQL over logs, spans and metrics, or error lookups. So of course, the real value of an agent is reading production logs and metrics faster than any of us can.

### Before anyone is online

Nobody became an engineer to triage errors over morning coffee, so we gave that job to an agent first.

<div style="position: relative; padding-bottom: 56.25%; height: 0; overflow: hidden;">
  <iframe 
    style="position: absolute; top: 0; left: 0; width: 100%; height: 100%;" 
    src="https://www.youtube.com/embed/oXyFnAjMNWE" 
    title="YouTube video player" 
    frameborder="0" 
    allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" 
    referrerpolicy="strict-origin-when-cross-origin" 
    allowfullscreen>
  </iframe>
</div>

It runs twice a day and works through every new error in our backend and frontend apps. For each one, it reads the stack trace and opens the code at the call site. Errors with a shared cause get grouped, so forty timeouts on forty endpoints become one issue. It then files that issue in Linear or links it to an existing one. Errors from browser extensions, ad blockers and very old browsers get resolved as noise. (If you’re still on Internet Explorer, we see you. We’ve decided to let it go.)

Back to Andrej. When he opens his laptop, a report is waiting for him: first seen, count in the last day, lifetime count, and what the agent did with each error. In its first month, the job filed about 220 issues, linked 80 duplicates and resolved about 50 noise errors. Andrej reviews what it filed and hasn’t triaged an error by hand since. He says he doesn’t miss it.

If you only automate one thing after reading this, make it this one:

```
[label Morning error triage]
Using the Better Stack MCP, list all new unresolved errors from the last 12 hours in [apps].
For each error, read the stack trace and open the code at the call site.
Group errors that share a root cause.
For each group, create a Linear issue with two or three sentences of triage context, or link it to an existing issue if one matches.
Resolve errors caused by browser extensions, ad blockers or unsupported browsers.
Finish with a table: error, first seen, count in the last 24h, lifetime count, action taken.
```

### A support ticket

A customer writes in to say they were unsubscribed from our emails without clicking anything.

Petr, another brilliant engineer on the team, pastes the ticket into his agent. The agent reads the production logs for that account and reconstructs what happened. The customer’s email security scanner had opened every link in the message, including the unsubscribe link, before the customer ever saw it. The scanner was being very thorough, just on the wrong side.

```
[label Reconstruct a support ticket]
Here's a support ticket: [paste]
Query our production logs in Better Stack around the account and time it mentions, and reconstruct what happened step by step.
Tell me which parts you confirmed from the data and which you're inferring.
```

Petr’s agent has made more than 1,300 MCP calls since July, and a good share of them went to tickets like this. The last line of the prompt matters most. An agent that tells you what it’s guessing is worth ten that sound confident.

### One error worth a closer look

Andrej picks an issue from the morning report and pastes its URL into a fresh session.

The agent loads the error and the occurrences around it, follows the trace ID into logs and spans, and reads the code path. The answer comes back in the same five parts every time. That’s deliberate, because nobody wants to read an essay before deciding whether something is on fire. Andrej’s next message is usually “prepare a PR”.

```
[label Investigate one error]
Check this error: [Errors URL]
Load it with the Better Stack MCP, look at the occurrences around it, follow the trace ID into logs and spans, and read the code path.
Answer with: evidence, likely sequence of events, impact, confidence, suggested fix.
```

### A regression report

A ticket says p95 latency on a sign-in endpoint jumped this week.

The agent breaks the request time down by span. Most of it is the mail relay and template rendering, and the numbers have looked like this for months. The ticket’s baseline came from a quiet weekend, and quiet weekends make terrible baselines.

```
[label Check a latency regression]
A ticket says p95 latency on [endpoint] jumped this week.
Pull the spans for that endpoint, break the request time down by span, and compare against the same weekday over the last three months.
Is this a real regression?
```

### Numbers before code

We have one strong opinion here: measure before you build. A query is much cheaper than finding out the answer in production.

Before changing how phone call answers get classified, an agent counted how often the current classifier gets them wrong. It was 3 to 4% of cases. That’s high enough to be worth fixing, and low enough that nobody needed to panic and rewrite the classifier. Petr does the same before his own changes: he checks how many accounts a change will affect and how quickly a source type actually gets created. In long refactors, agents check that an old code path is no longer used before anyone deletes it. It’s more polite than finding out from a customer.

```
[label Size a change before building it]
Before I change [behaviour], count from production logs how often [case] happens over the last 30 days and how many accounts it affects.
```

```
[label Confirm a code path is unused]
Query production for any calls to [function or endpoint] in the last 30 days.
I want to be sure it's unused before I delete it.
```

> Agents are great with just MCP, but the read-only db access we gave them later turned them into beasts. Especially Fable-class agents can just complete a full RCA, repro, fix loop unattended with that combo. - Paweł, Better Stack

### Shipping

Our fellow engineer Paweł, who treats agents the way some people treat browser tabs, runs about a dozen sessions at once. Each is named after its job: deployment steward, collector errors owner, ingesting on-call. It looks less like a terminal and more like a small company he manages.

The deployment steward checks every canary. When he asks, it injects a test event and returns a Live tail link showing the event arrived.

Another session was adding an anomaly alert to our error tracking dashboard template when it noticed, halfway through, that it had picked the wrong template. It paused the alert, deleted it and started again on the right one, which is more self-awareness than most of us manage on a Friday. Then it kept an eye on production while a job copied the alert to more than 3,000 dashboards.

When a client ships logs from a release candidate, Petr’s agent queries the source to confirm every row arrived with the right fields.

```
[label Compare before and after a deploy]
We just deployed [release]. Compare [job] durations and error counts for the hour before and after.
Tell me if anything regressed, and estimate when any backlog will drain.
```

That prompt comes from a hotfix shipped mid-incident. The agent confirmed the median job time was back to 1.2s and estimated when the alert would clear. Along the way, it found a job that had been lost in a restart, hours before it would have ruined someone’s afternoon.

### Deciding what to fix next

We can’t forget Tomas, our awesome CTO, who prompted the question every team should ask more often: across everything we collect, what actually costs our customers the most?

His agent pulled page load times, backend response times, query times and errors for each tenant through the MCP. It joined them against the score we keep for each customer and returned the issues ranked by real impact. The bug that annoys an engineer the most is rarely the one that hurts customers the most, and now there’s data to settle that argument.

```
[label Rank issues by customer impact]
Pull p75 page load time, backend response time, query time and error count per tenant ID for the last 14 days.
Join it with [customer list or scores] and give me an ordered list of issues ranked by customer impact.
```

### The page

In the evening, Paweł gets paged.

He opens a fresh session and types one word. We won’t print it here, but it’s the word most engineers say out loud when the pager goes off. It triggers a skill he wrote that finds the incident, reads the timeline, queries the logs around the start time and gives him a first read on what happened. In the session he recorded, a credential job had been killed twice while waiting on a network reply. That first read kept what was confirmed apart from what was guessed and suggested the next query. Paweł replied “do deeper read”, which is roughly the most an on-call engineer can type at that hour.

Pick whatever word comes to mind at 2am:

```
[label Start an incident investigation]
When I start a session with just "[word]", find the most recent incident in Better Stack, read its timeline, and query the logs around its start time.
Give me a first read on what happened. Separate what you confirmed from what you're guessing, and suggest the next query to run.
```

Some investigations go a long way down. One of Andrej’s started with error counts and ended at a kernel network queue dropping packets under load, several floors below the application.

### What makes it work

**The agents learn the job.** The prompts in this post are a good place to start, and you won’t need them for long. When an approach works and you tell the agent so, it saves that approach in a skill, a markdown doc in the repo or its memory, and uses it next time without being asked. Ask one to fix a bug and it goes straight to the production logs around the time the bug started. Ask it to triage issues and it checks how much the affected features are actually used in production before it ranks anything. Good feedback early on means less prompting later.

**Agents run queries in parallel.** A person forms a hypothesis and runs three queries, one after another. An agent runs thirty at the same time, and gets to the answer sooner even though plenty of those queries lead nowhere. That’s only affordable when queries are fast and cheap, which is why we built the storage layer first.

**The agents read the help first.** They call `query_help` before writing SQL, so queries on unfamiliar tables usually work on the first or second try. Honestly, that’s a better hit rate than ours.

**The data, the code and the PR share one session.** The question and the fix end up in the same conversation, and nobody loses context switching between twelve tabs.

**Anything that repeats goes on a schedule.** The morning triage job is just a prompt on a timer. If you do something every day, an agent should probably be doing it.

### Setup

```
[label Install the Better Stack plugin]
/plugin install better-stack
```

Run it inside Claude Code, then sign in through your browser. Setup for Cursor, Codex and Claude Desktop is in the docs.
