Page MenuHomePhabricator

Implement OpenSearch SLO for linked artifacts (ST6.2.2)
Closed, ResolvedPublic

Description

This ticket tracks Search Platform's work on hypothesis ST6.2.2, supporting the Product Derived Data team's KR ST6.2 (Product derived data). Product Derived Data requested our help; our commitment is to define and surface an OpenSearch SLO (Service Level Objective — a target for how reliably/quickly the service performs) for linked-artifacts indexing and search. This is our corresponding hypothesis in support of their KR; we own the platform piece, not the KR outcome.

Hypothesis

If we implement an OpenSearch SLO (availability and latency) for linked artifacts indexing and searching, we'll be able to use them to establish repeatable architectures with known trade-offs to offer product teams. Beyond the scope of this hypothesis, this will simplify design decisions and increase velocity (measurement of those will be captured in future KR reports).

What "done" looks like

Two audiences, two bars:

  • For Product Derived Data: a documented commitment from Search Platform on the defined SLO metrics — enough for them to plan against.
  • For Search Platform (ourselves): those metrics are actually captured and visible in our existing Grafana SLO dashboard.

Scope — SLIs to capture

The Service Level Indicators (SLIs — the measurements the SLO targets are based on):

  • Availability — uptime of the OpenSearch indexing/search service for linked artifacts.
  • Update/indexing latency — how quickly a newly linked artifact becomes searchable (i.e. update lag).

Out of scope / open question

  • General query latency is excluded — it varies too much by query type to set a fair SLO target.
  • Open question for the team: is there a *specific, well-bounded* query type whose lag is stable enough to be worth an SLI? Decide before committing.

Proposed sub-tasks

  • Confirm SLI definitions and thresholds with the team (availability, indexing latency).
  • Resolve the query-latency open question (in or out).
  • Instrument / verify metric collection for each SLI.
  • Add the SLIs to the existing Grafana SLO dashboard.
  • Document the SLO commitment and share with Product Derived Data.

Details

Related Changes in GitLab:
TitleReferenceAuthorSource BranchDest Branch
Consolidate the Search SLOs into one manifest and adds an availability SLO (T431145)repos/sre/slothslos!51pfischerpfischer/T431145/weighted-tags-query-latencymain
Customize query in GitLab

Event Timeline

This comment was removed by Aklapper.
This comment was removed by Aklapper.

@EBernhardson we realized a little late that @pfischer is OOO the next couple of weeks. Do you happen to know who might be his hypothesis delegate? It would be useful to have weekly reports continue there. :)

I'm not sure about the hypothesis delegate, but i can say the SLO's are DPE-SRE tasks, not search platform directly. Implementation will depend on their prioritization.

I think it's worth taking a step back here when Peter returns, so we look at what the hypothesis is requesting and what's covered by existing SLOs and infrastructure, and what needs to be new.

The essential request is: let's agree on a reusable solution for indexing and searching across per-page structured data, generated from arbitrary data pipelines, with operational guarantees on indexing latency, serving availability and query latency.

From previous informal chats with the Search team, I'm guessing that the answer will be: "The correct path for satisfying those requirements is to push weighted tags to the CirrusSearch cluster, so let's add an indexing latency SLO for weighted tags, and availability and latency SLOs to that cluster."

But alternatively the answer may be "We need a new cluster to satisfy this requirement, with its own SLOs", or even "Weighted tags are the wrong answer, we need to design something new before we even think of SLOs." So let's talk about what's feasible here, and what other parameters we're missing to make a decision.

For what it's worth, the existing indexing latency SLO does look helpful here!

The query latency half of this hypothesis is now measurable, and I have a concrete SLO to
propose.

What changed. T434975 added two dimensions to
mediawiki_CirrusSearch_request_time_seconds: weighted_tags (yes/no) and pool (the
pool counter bucket). Both are merged and fully rolled out as of 2026-09-10, so the share
of request volume without the labels is 0. Weighted tag searches can now be selected
directly, which was the missing piece: previously they were reported as type="full_text"
and could not be told apart from ordinary full text search.

What the data says

External traffic only (mw-api-ext plus mw-web), 24h:

measurevalue
p5032ms
p95117ms
p99228ms
requests under 250ms99.77%
volume~0.5 req/s, ~44k requests/day

For comparison, over the same window and the same namespaces, all searches together are at
p95 254ms and the searches without weighted tags at p95 329ms. Weighted tag queries are
markedly cheaper than average search, being filter shaped and skipping most text scoring,
which is the reason the 200ms aspiration is met with room to spare today.

Proposed SLO

95% of searches filtering on weighted tags complete in under 250ms, measured on
external traffic, over a 30 day rolling window. Sloth spec in review:
https://gitlab.wikimedia.org/repos/sre/slothslos/-/merge_requests/51

Three things about that wording are worth agreeing on explicitly.

250ms, not 200ms. MediaWiki emits this latency into a histogram whose bucket edges are
shared fleet-wide by statsd-exporter: 5ms, 10ms, 25ms, 50ms, 100ms, 250ms, 500ms, 1s, 2.5s,
5s, 10s, 30s, 60s. A threshold based SLI can only use an existing edge, and there is no
200ms edge. Committing to 200ms means first adding a CirrusSearch specific mapping to
charts/statsd-exporter/values.yaml in deployment-charts. Happy to do that if Derived Data
wants the round number, it just needs to land before the commitment is published.

Which traffic counts. Weighted tag queries by namespace, 24h averages:

namespacereq/sp95
mw-cron5.7423ms
mw-web0.26115ms
mw-api-ext0.25119ms
mw-jobrunner0.17206ms
mw-api-int0.1091ms

Most weighted tag traffic is not user facing at all: mw-cron alone is roughly eleven
times the external volume, largely refreshLinkRecommendations. The SLI therefore covers
only mw-api-ext and mw-web, the two namespaces serving external traffic. mw-api-int
is excluded as internal API traffic, which costs about 16% of the events; the consequence
is that a request reaching MediaWiki through an internal service on a user's behalf is not
counted.

Why 95% and not 99%. Steady state is ~0.23% of requests over 250ms, so normal
operation consumes under 5% of a 95% error budget. Two bad days at a 25x degradation would
add ~0.33 percentage points to the 30 day ratio, about a tenth of that budget; against a
99% objective the same two days would eat half of it. Since the label has under a day of
history, I would rather start generous and tighten after a quarter of data than publish a
commitment we have to walk back. Note the window is 30 day rolling, so a bad weekend ages
out after 30 days rather than being cleared at the quarter boundary.

Caveats on the number

  • Latency is measured by MediaWiki, so it includes pool counter wait and the network round trip, not just the OpenSearch took time.
  • Cache hits never reach the histogram, so the denominator counts backend searches only.
  • Availability is scopeable the same way now: mediawiki_CirrusSearch_backend_failures_total{weighted_tags="yes"} carries the same labels, if we want an availability SLI alongside latency.

Follow-ups

  • A Grafana panel for the two new dimensions on the Elasticsearch Percentiles dashboard.
  • Revisit the objective once a quarter of data has accumulated.
  • Unrelated bug found while mapping the pool rules: Searcher::getPoolCounterType() keys on the syntax token deepcat, but DeepcatFeature::getFeatureName() records deepcategory and nothing records deepcat, so deep category searches never reach the expensive pool. I will file that separately.
Gehel changed the task status from Open to In Progress.Tue, Sep 15, 3:53 PM
Gehel triaged this task as High priority.
Gehel added a project: OKR-Work.

I revised the Search SLO. The four query latency SLIs the page carried were defined on Graphite metrics that no longer exist, and the Prometheus metrics that replaced them measure backend time instead of time to render, so nothing was measuring them and they never made it into a sloth config. I left them out for now. They are still in the page history, so we can pick them up again once we agree on how to measure them.

What remains are the three SLIs that matter for Derived Data. Two of them are general anyway (availability, update lag), and the query latency one is scoped to weighted tag searches, following Derived Data's requirements.

@Gehel, please let me know if you are okay with this from a DPE SRE perspective.

@GGoncalves-WMF, all three objectives are at 95% for now, which is the usual starting point here. The 250 ms latency threshold follows the histogram buckets we have available; 200 ms would need a CirrusSearch specific statsd-exporter mapping first, and I would rather add that later than block on it now. Please read these numbers as the minimum we commit to, not as what to expect in practice: we currently measure 99.3% of weighted tag searches within 250 ms, 99.986% availability, and 98.5% for update lag. I am happy to tighten the targets once we have a few quarters of data, I would just rather avoid that overhead now.

Thanks Peter! Quoting the summary from the SLO page:

We publish the realistic targets: 95% for availability, for weighted tags query latency within 250 ms, and for update lag within 10 minutes. Each has substantial headroom, deliberately: Search Platform has no 24-hour on-call, so the error budget has to absorb an incident that begins outside working hours and is not mitigated until the next working day, without the SLO forcing a page overnight.

This looks good to me!

Closing this out. The SLOs are defined in slothslos under search/ and documented on SLO/Search. Recording here the reasoning and the measurements, which are point-in-time and do not belong on the page.

Measured, 30 days to 2026-09-29

IndicatorTargetMeasuredSampleBudget used
Availability95%99.983%6.76 billion requests0.3%
Weighted tags latency < 250 ms95%98.4%5.03 million requests, 14 days32%
Update lag < 10 min, eqiad95%99.8%4%
Update lag < 10 min, codfw95%98.1%38%

Availability worst day 99.84%, worst hour 96.28% (over 90 days). The weighted tags figure is provisional: the label only reached full volume 14 days ago, and it has already drifted from 99.0% on the 16th to 98.4% today.

Why 95%

  • 95% is the usual boundary for a new SLO; confirmed with core SRE. No dependent team asked for tighter, and the requesting side (Derived Data) accepted 95% together with the 250 ms bucket.
  • The window is a fixed 90-day quarter, unshifted, so a quarter's budget is 4.5 days.
  • Availability spends ~0.3% of that in steady state, i.e. effectively the whole budget is available for incidents. Latency and codfw update lag are the tight ones at roughly a third.
  • Worth a look again after a full quarter, once weighted tags has real history.

Why a task and not a page

  • Only core SRE has an on-call rotation and gets paged, and they do not know search infrastructure, so a page at 03:00 buys nothing actionable.
  • DPE SRE has the knowledge but no rotation, and is not paged.
  • At 95% over a fixed quarter a whole dark weekend costs about 60 of the 108 hours of budget. One fits; two do not. That is enough room to respond on the next working day.
  • So: alerting by task only. Revisit if a tighter target is ever requested.

Why not cluster health as the SLI

  • Over the same 30 days production-search-codfw was non-green 2.9% of the time and red 0.22% (~1.5 hours); eqiad was non-green 0.44% and never red.
  • An SLI on health colour would therefore report ~97.1% for codfw while queries were actually succeeding at 99.983%. Yellow is routine shard recovery and still serves searches.
  • Proxy-level measurement would sit closer to the clusters, but there is no envoy or LVS telemetry for the search upstream in the ops Prometheus to build on.

Sizes behind the caveats listed on the page

rzl merged https://gitlab.wikimedia.org/repos/sre/slothslos/-/merge_requests/51

Consolidate the Search SLOs into one manifest and adds an availability SLO (T431145)