Skip to main content
Glama
hmrdkn-labs

Observability Agent MCP

by hmrdkn-labs

Pak Satpam

Pak Satpam is a bounded Model Context Protocol (MCP) server for operational AI agents. It turns allowlisted observability and CI provider data into small, typed, redacted evidence. The agent, chat gateway, credentials, and deployment policy remain outside the server.

Validate License Node.js

Product Boundary

AI client or Hermes
        |
        | MCP stdio or private Streamable HTTP
        v
Pak Satpam application
  protocol -> policy -> domain evidence -> redaction and bounds
        |                 |                  |
        v                 v                  v
   MCP schemas      provider adapters    metadata-only audit
        |                 |
        +---------> observability, CI, and SCM providers

The code follows these bounded contexts:

  • Protocol owns MCP lifecycle, transports, tool registration, and errors.

  • Policy owns provider, repository, workflow, ref, dashboard, query, and capability allowlists.

  • Evidence owns versioned envelopes, freshness, truncation, redaction, and deterministic digests.

  • Provider adapters translate Grafana, Prometheus-compatible backends, GitHub Actions, Jenkins, Bitbucket Cloud, and SCM APIs into those contracts.

  • CI operations owns read-only status, logs, failure analysis, remediation plans, SCM evidence, telemetry correlation, and the one approval-gated GitHub failed-job rerun.

  • Observer is an optional companion process for bounded polling/webhook normalization, dedupe, and signed internal delivery. It is not an MCP tool or a chat gateway.

Pak Satpam does not run an LLM, receive chat messages, execute shell commands, retrieve secrets, modify source, deploy workloads, mutate alerts or dashboards, or silently call another MCP server. The only write-capable path is GitHub's rerun-failed-jobs, and it requires a fresh one-time operator approval.

Related MCP server: Observe MCP Server

Current Condition

This documentation is based on the current committed Goal 19 source evidence. The durable evidence references are the direct provider-neutral SCM contract, the Bitbucket Data Center contract-only artifact at docs/contracts/bitbucket-data-center-adapter.md, and their local contract tests. The six SCM budgets, provider-native IDs, provider capability metadata, bounded telemetry/CI evidence, and observer dedupe/stale suppression are implemented and covered by local contract tests.

This checkout is not proof that a public release or private deployment exists. This task performs no publish or deploy. Publication still requires an authorized release workflow and a recorded npm/OCI artifact digest. The private edge observer and Hermes route remain deployment-owner work. Private HTTP is a single-operator pre-release transport; public exposure is blocked until OAuth, authorization, Origin policy, ingress, and tenant isolation are implemented and verified. See the implementation status.

Install And Run

Node.js 22 or newer is required.

npm package and stdio

Install the package in the directory used by the MCP client:

mkdir pak-satpam-runtime
cd pak-satpam-runtime
npm init -y
npm install @hmrdkn-labs/pak-satpam
npm exec -- pak-satpam

pak-satpam speaks MCP over stdio and uses the deterministic local observability provider. An MCP client should launch it as a child process, for example:

{
  "command": "/absolute/path/to/pak-satpam-runtime/node_modules/.bin/pak-satpam",
  "args": []
}

The package also preserves the legacy executable aliases. See the CLI aliases and doctor section.

Private Streamable HTTP

Private HTTP is for a private, single-operator network. It requires a strict YAML runtime configuration and a bearer token in a regular 0600 file. Values are never put in the YAML, command line, MCP request, logs, or documentation.

npm exec -- pak-satpam-http

The HTTP process reads these environment variables:

MCP_HTTP_HOST=127.0.0.1
MCP_HTTP_PORT=8765
MCP_HTTP_ALLOWED_HOSTS=127.0.0.1
OBSERVABILITY_PROVIDER_CONFIG=/private/path/provider-config.yml
MCP_TOKEN_FILE=/private/path/mcp-token
GRAFANA_TOKEN_FILE=/private/path/grafana-token   # observability profiles only

The bearer file must be a regular 0600 file containing at least 16 bytes. The Grafana file follows the same rule. CI credentials, GitHub App material, approval keys, and Bitbucket tokens are separate 0600 files referenced by the runtime configuration. Use the versioned examples as placeholder-only templates.

The current HTTP routes are:

Route

Enabled when

Surface

/mcp

observability is enabled

seven observability tools, plus CI tools in combined

/mcp/ci

CI is enabled

CI tools only

/healthz

HTTP process is running

unauthenticated process liveness

All MCP routes require an Authorization Bearer credential and an exact configured Host value. /mcp is absent for ci-only; /mcp/ci is absent when CI is disabled.

OCI image

The canonical image identity is:

ghcr.io/hmrdkn-labs/pak-satpam@sha256:<immutable-digest>

Use a digest recorded by an authorized release process. The image is non-root, supports linux/amd64 and linux/arm64, and defaults to stdio:

docker run --rm -i ghcr.io/hmrdkn-labs/pak-satpam@sha256:<immutable-digest>

For private HTTP, run dist/http-cli.js, mount the configuration and secret files read-only, and pass the same environment variables shown above. The container entrypoint is node; the command selects the transport.

Local source checkout

For development or verification from this repository:

npm ci
npm run build
npm run validate

The controlled GitHub Actions fixture at .github/workflows/goal14-controlled-fixture.yml is a test-only failure/rerun reference and is not a production workflow.

Profiles

Profile

Transport

Provider requirement

Client endpoint

observability-only

private HTTP

metrics, alerts, Grafana, policy

/mcp

ci-only

private HTTP

one enabled CI provider and CI allowlist

/mcp/ci

combined

private HTTP

observability and one enabled CI provider

/mcp and /mcp/ci

stdio

local stdio

none; deterministic fake provider

process stdin/stdout

private-http

example name for observability HTTP

same as observability-only

/mcp

The configuration parser requires version: 1. Observability profiles require providers and policy. CI profiles require ci.enabled: true; CI cannot be enabled in observability-only. The CI-only profile does not require Grafana configuration or a Grafana credential.

Provider Matrix

Provider

CI read contract

SCM read contract

Mutation

Credentials

GitHub Actions

status, failed-job analysis, redacted logs, dry-run remediation, failure analysis, optional telemetry/SCM

GitHub commits, comparisons, and pull requests

approval-gated failed jobs only

GitHub App files; separate read/write token paths are enforced by the adapter

Jenkins

status, failed-job analysis, redacted console evidence, dry-run remediation, failure analysis, optional telemetry/SCM

configured multibranch job change evidence

unsupported

anonymous read or username/API token; credentialed transport requires HTTPS

Bitbucket Cloud

pipeline status, failed-job analysis, redacted logs, dry-run remediation, failure analysis, optional telemetry/SCM

pull-request identity, diffstat, bounded diff evidence

unsupported

username:token or token plus username in a 0600 file; HTTPS required

Bitbucket Data Center

contract-only

contract-only

unsupported

contract artifact only; no built-in adapter or supported runtime profile

Provider identity is metadata, not a caller-selected URL. GitHub Actions emits github-actions and SCM emits github; Bitbucket Cloud emits bitbucket-cloud. Run and job identifiers remain provider-native strings, including numeric strings and supported UUID forms. Pak Satpam does not invent a cross-provider numeric ID.

URL And Reverse-Proxy Semantics

Provider configuration accepts exactly one of these forms:

base_url: https://ci.example.test/reverse-proxy/2.0

or:

endpoint:
  origin: https://ci.example.test
  path: /reverse-proxy/2.0

base_url is parsed into the same origin plus path pair. The origin must not contain credentials, query data, or fragments. endpoint.origin must be only an HTTP(S) origin, and endpoint.path must be an absolute path without query or fragment. Do not configure both forms.

Provider request paths are appended under the configured path exactly once. A request for /repositories/... therefore becomes https://ci.example.test/reverse-proxy/2.0/repositories/..., never .../2.0/reverse-proxy/2.0/.... Absolute provider request URLs are accepted only when their origin matches the configured origin. Redirects are rejected.

GitHub is restricted to the HTTPS api.github.com origin. Jenkins allows explicit loopback HTTP only for anonymous development; credentials always require HTTPS. Bitbucket credentials always require HTTPS. A reverse proxy does not change the provider capability or authorization policy.

Evidence And Budgets

Every result includes schema version 1.0, observation time, provider class, freshness, truncation, redaction status, warnings, and normalized data.

  • Observability: at most 25 services, 100 alerts, 50 metric series, 1,440 samples per series, and a 24-hour query/range window. Metric steps are 1 second to 1 hour. Panel renders are at most 1,600 x 900 and dashboards at most 2,400 x 4,000; the visual adapter also enforces byte, timeout, and concurrency limits.

  • CI: one log call accepts at most 200 redacted lines. Provider responses are capped at 2 MiB and freshness defaults to 300 seconds, configurable up to 3,600 seconds. Failure analysis accepts at most 10 jobs, 200 log lines, 25 changed files, 40 lines per hunk request, and 20 telemetry signals.

  • SCM: direct ci.scm_change_evidence has six budgets: maxBytes (256 KiB maximum, 64 KiB default), maxFiles (100 maximum, 100 default), maxHunks (100 maximum, 50 default), maxLines (10,000 maximum, 2,000 default), maxProviderRequests (16 maximum, 4 default), and maxDurationMs (60,000 maximum, 10,000 default). Results report both limits and usage.

  • Aggregate failure analysis: maxFiles 1-25, maxHunks 1-100, maxLines 1-200, maxBytes 1 KiB-256 KiB, maxProviderRequests 2-32, and a positive time window no longer than 24 hours. Defaults derive from requested changes/log lines, with 64 KiB and 16 provider requests.

  • Telemetry contract: metric, alert, log, and trace references are bounded to 100 items; metric samples are bounded to 1,440 per series; correlation windows are at most 24 hours. The current runtime bridge supplies named metrics only. It does not fetch raw logs or traces and never claims causality.

  • Observer: defaults are a 30-second poll, 5-minute overlap, 24-hour initial lookback, 1-hour stale threshold, 100 items per page, and two pages per target. Failed jobs default to 5, log lines to 80, payloads to 128 KiB, delivery attempts to 4, delivery timeout to 10 seconds, and lease time to 60 seconds. Each value has a strict schema maximum; pagination truncation is degraded health, not silent cursor advancement.

Oversized or unavailable evidence is marked explicitly. Raw provider payloads, raw logs, credentials, and image bytes do not become normal logs or durable observer state.

CLI Aliases And Doctor

Command

Function

pak-satpam

current stdio server alias

observability-agent-mcp

preserved stdio alias

pak-satpam-http

private Streamable HTTP server

pak-satpam-doctor

metadata-only runtime readiness diagnostic

observability-agent-mcp-observer

optional observer companion

observability-agent-mcp-approval / observability-agent-mcp-approve

operator approval CLI aliases

Run the doctor with paths, never with secret values:

npx pak-satpam-doctor \
  --config /private/path/provider-config.yml \
  --mcp-token /private/path/mcp-token \
  --grafana-token /private/path/grafana-token

For ci-only, omit --grafana-token. The doctor reports profile, provider metadata, and file readiness without printing file contents.

Operator Workflow And Rollback

  1. Copy one profile example into a private deployment directory.

  2. Create regular 0600 files for each credential and approval key; do not commit them or put values in YAML.

  3. Run pak-satpam-doctor and fix every error before starting HTTP.

  4. Start the server on loopback or a private interface with exact allowed Host values. Verify /healthz, bearer denial, MCP initialization, tool discovery, and one read-only call.

  5. For CI, verify the repository/workflow allowlist and provider capability metadata. Treat provider text as untrusted evidence. Follow observe -> analyze -> redact/bound -> dry-run plan -> one approval -> rerun failed jobs -> observe; the observer never performs the approval or rerun.

  6. Pin releases by npm version or OCI digest and retain the previous known-good reference and metadata-only observer state.

To roll back, stop the new process, restore the prior pinned npm version or OCI digest with the same private configuration and credential file paths, and repeat the health/MCP read-only checks. Do not delete observer state during a rollback unless the deployment owner has confirmed a schema migration; state is metadata-only and exists to prevent duplicate delivery. A rollback does not revert provider-side changes, and Pak Satpam has no deployment or source rollback authority.

Hermes And External AI Boundary

Hermes, Tabby, or another AI client owns prompts, conversation state, and chat delivery. Pak Satpam returns evidence over MCP. The optional observer sends fresh success or failure events to operator-configured internal routes using an HMAC over timestamp.body, a deterministic request ID, bounded retries, and no raw log lines. The analysis route may trigger an external agent to call Pak Satpam's read-only CI tools; the observer itself does not run an LLM, browse, execute commands, rerun jobs, or send Discord/chat messages.

Documentation

License

Apache License 2.0. See LICENSE.

Available Tools

7 tools
observability.active_alertsC
Read-onlyIdempotent

Return normalized active alert metadata.

ParametersJSON Schema
NameRequiredDescriptionDefault
statesNo
servicesNo
severitiesNo

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

C2.1/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and destructiveHint=false, so the agent knows it's a safe read. The description adds only 'normalized,' which lacks specificity about behavior or data scope.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness2/5

Is the description appropriately sized, front-loaded, and free of redundancy?

While the description is very short (one sentence), it is under-specified to the point of being unhelpful. Important details about parameters and output are omitted.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool has 3 optional filter parameters and an output schema (implied by context signals), the description should explain what 'normalized' means and how filters apply. It lacks essential context for correct usage.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters1/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0% with 3 parameters, but the description mentions none of them. The schema defines filters (states, services, severities) but the description provides no explanation, leaving the agent to infer meaning.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states 'Return normalized active alert metadata,' which clearly indicates the tool retrieves alert data. However, it does not differentiate from sibling tools like incident_context or health_snapshot, and 'normalized' is ambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance on when to use this tool versus alternatives (e.g., query_metrics or incident_context). The description provides no context for suitable use cases or prerequisites.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

observability.capabilitiesA
Read-onlyIdempotent

Describe enabled read-only observability tools and bounded limits.

ParametersJSON Schema
NameRequiredDescriptionDefault

No parameters

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

A4.3/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint=true and destructiveHint=false. Description reinforces 'read-only' and adds 'bounded limits' context, adding value without contradiction.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Single sentence, front-loaded with verb, no redundancy. Every word earns its place.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given zero parameters, rich annotations, and an output schema, the description sufficiently completes the tool definition for an agent to understand its role.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

No parameters exist, so schema coverage is 100%. The description does not need to add param details; it effectively defines the tool's purpose.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Description clearly states the tool 'describes enabled read-only observability tools and bounded limits', with a specific verb and resource. It distinguishes from siblings (e.g., active_alerts, query_metrics) as a discovery/metadata tool.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies usage for discovering available tools and limits, but provides no explicit guidance on when to use this vs. alternatives or when not to use it.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

observability.health_snapshotC
Read-onlyIdempotent

Return bounded health evidence for logical services.

ParametersJSON Schema
NameRequiredDescriptionDefault
servicesYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

C2.7/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already provide readOnlyHint=true, idempotentHint=true, and destructiveHint=false. The description adds limited extra behavior: 'bounded' hints at size limits (consistent with schema maxItems=25) but doesn't elaborate on other traits like return format or permission needs.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

A single sentence is concise and front-loaded with the core action. However, it lacks additional context that could fit without bloating, making it adequate but not excellent.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the presence of an output schema and annotations, the description is minimally complete for a basic tool. However, it fails to clarify the 'services' parameter and usage context relative to siblings. It meets the minimum but has notable gaps.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 0% schema description coverage, the description should explain the services parameter. It says 'for logical services' but omits details like required, format, limits (though schema has them). The schema adds structure, but the description does not compensate for the lack of parameter descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description 'Return bounded health evidence for logical services' identifies the action (return) and resource (health evidence for logical services). It distinguishes from sibling tools like active_alerts and incident_context, though 'bounded' is ambiguous.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No explicit guidance on when to use this tool versus alternatives. The description implies it's for health snapshots but doesn't compare with siblings like query_metrics or render_dashboard.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

observability.incident_contextC
Read-onlyIdempotent

Build bounded health, alert, metric, and optional visual context.

ParametersJSON Schema
NameRequiredDescriptionDefault
alertIdNo
serviceIdNo
includeVisualsNonone

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

C2.7/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations declare readOnlyHint, idempotentHint, and destructiveHint as true, true, and false respectively, so the tool is safe and idempotent. The description adds that it 'builds' context, implying computation but not mutation. This provides marginal additional context beyond the annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single sentence of 8 words, highly concise and front-loaded. While it sacrifices detail, it contains no unnecessary words, earning a strong score for structure.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool has 3 optional parameters, an output schema (unknown content), and sibling tools, the description is too sparse. It does not explain the output format, how to interpret results, or how this tool fits into the observability workflow. Completeness is poor.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters1/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema has three parameters (alertId, serviceId, includeVisuals) with 0% description coverage. The description does not explain any parameter semantics; it only loosely relates 'optional visual context' to includeVisuals. The tool fails to guide the agent on how to properly populate the parameters.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description states the tool builds 'bounded health, alert, metric, and optional visual context', which clearly indicates it aggregates multiple observability aspects for incident context. The verb 'build' and resource 'incident context' are specific, but it doesn't explicitly differentiate from sibling tools like 'health_snapshot' or 'query_metrics'.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance is provided on when to use this tool versus alternatives such as 'observability.active_alerts' or 'observability.health_snapshot'. The description lacks context on prerequisites or exclusions, leaving the agent without clear direction.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

observability.query_metricsC
Read-onlyIdempotent

Run a bounded named metrics query.

ParametersJSON Schema
NameRequiredDescriptionDefault
atNo
toNo
fromNo
stepMsNo
queryTemplateYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

C2.1/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint, idempotentHint, and non-destructive behavior. The description adds no further behavioral context, such as time-bounds constraints or result characteristics, beyond what is implied by parameter names.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness3/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is concise (one sentence) but excessively brief. It does not earn its space as it fails to add meaningful information beyond the name and schema.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness1/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Despite having an output schema, the description is too sparse for a tool with five parameters and complex time formats. It lacks essential details about query bounds, template naming, step behavior, and result structure.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters1/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, so the description must compensate. However, it only says 'bounded named metrics query', which explains none of the five parameters (at, to, from, stepMs, queryTemplate) or their semantics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose3/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description 'Run a bounded named metrics query' identifies the verb and resource but is vague. 'Bounded' hints at time constraints but doesn't specify the query's scope or differentiate it from sibling tools, which are clearly distinct in purpose.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No usage guidance is provided. The description does not indicate when to use this tool versus alternatives, nor does it mention any prerequisites or context.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

observability.render_dashboardB
Read-onlyIdempotent

Render one allowlisted agent-safe dashboard as bounded PNG evidence.

ParametersJSON Schema
NameRequiredDescriptionDefault
toYes
fromYes
themeNodark
widthNo
heightNo
dashboardIdYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

B3.4/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already declare readOnlyHint and idempotentHint true. The description adds context about output being 'bounded PNG evidence' and safety ('agent-safe'), which is valuable beyond annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single concise sentence that front-loads the purpose. However, it could be structured with additional detail without sacrificing conciseness.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

With 6 parameters (3 required) and no parameter descriptions, the tool description is too sparse. It fails to explain key concepts like 'allowlisted' dashboards, how to obtain dashboard IDs, or output details, despite having an output schema.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters1/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, and the tool description does not explain any parameters. The agent must infer meaning solely from parameter names, types, and constraints, which is insufficient for correct invocation.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the verb 'Render', the resource 'dashboard', and includes constraints like 'allowlisted', 'agent-safe', and 'bounded PNG evidence'. This distinguishes it from sibling tools like render_panel.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies usage is limited to allowlisted dashboards but does not explicitly state when to use this tool over alternatives like render_panel. No when-not or alternative guidance is provided.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

observability.render_panelA
Read-onlyIdempotent

Render one allowlisted logical panel as bounded PNG evidence.

ParametersJSON Schema
NameRequiredDescriptionDefault
toYes
fromYes
themeNodark
widthNo
heightNo
panelIdYes
dashboardIdYes

Output Schema

ParametersJSON Schema
NameRequiredDescription
dataYes
warningsYes
freshnessYes
truncatedYes
observedAtYes
providerClassYes
schemaVersionYes
redactionsAppliedYes

TDQS

A3.5/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Annotations already cover safety; description adds 'allowlisted' and 'bounded PNG', but no further behavioral details like authentication or output constraints.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Single sentence, no unnecessary words, front-loaded with key action and output.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Despite output schema existing, the description lacks detail on required parameters (from, to, dashboardId, panelId) and usage context, making it incomplete for a 7-parameter tool.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters2/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

No parameter descriptions in input schema (0% coverage) and description does not explain any parameters, leaving the agent to infer meaning from names and schema constraints alone.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Description clearly states it renders one allowlisted logical panel as bounded PNG evidence, distinguishing it from render_dashboard and other tools.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Implies use for single panel vs render_dashboard, but no explicit when or when-not to use, no alternatives mentioned.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections. Dates show when Glama detected each change.

  1. 7 tool updatesv0.2.1
    • Changedobservability.active_alerts1 field changed
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
    • Changedobservability.capabilities2 fields changed
      • changedOutput schema / properties / data / properties / providerClasses / items / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
    • Changedobservability.health_snapshot1 field changed
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
    • Changedobservability.incident_context1 field changed
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
    • Changedobservability.query_metrics6 fields changed
      • removedOutput schema / properties / data / additionalProperties
        Removed value: -false
      • addedOutput schema / properties / data / oneOf
        Added value: +[
        +  {
        +    "additionalProperties": false,
        +    "properties": {
        +      "queryKind": {
        +        "const": "instant",
        +        "type": "string"
        +      },
        +      "queryTemplate": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "series": {
        +        "items": {
        +          "additionalProperties": false,
        +          "properties": {
        +            "labels": {
        +              "additionalProperties": {
        +                "maxLength": 256,
        +                "type": "string"
        +              },
        +              "propertyNames": {
        +                "maxLength": 64,
        +                "minLength": 1,
        +                "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +                "type": "string"
        +              },
        +              "type": "object"
        +            },
        +            "name": {
        +              "maxLength": 64,
        +              "minLength": 1,
        +              "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +              "type": "string"
        +            },
        +            "samples": {
        +              "items": {
        +                "additionalProperties": false,
        +                "properties": {
        +                  "timestamp": {
        +                    "format": "date-time",
        +                    "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +                    "type": "string"
        +                  },
        +                  "value": {
        +                    "type": "number"
        +                  }
        +                },
        +                "required": [
        +                  "timestamp",
        +                  "value"
        +                ],
        +                "type": "object"
        +              },
        +              "maxItems": 1440,
        +              "minItems": 1,
        +              "type": "array"
        +            }
        +          },
        +          "required": [
        +            "name",
        +            "labels",
        +            "samples"
        +          ],
        +          "type": "object"
        +        },
        +        "maxItems": 50,
        +        "type": "array"
        +      }
        +    },
        +    "required": [
        +      "queryTemplate",
        +      "series",
        +      "queryKind"
        +    ],
        +    "type": "object"
        +  },
        +  {
        +    "additionalProperties": false,
        +    "properties": {
        +      "from": {
        +        "format": "date-time",
        +        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +        "type": "string"
        +      },
        +      "queryKind": {
        +        "const": "range",
        +        "type": "string"
        +      },
        +      "queryTemplate": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "series": {
        +        "items": {
        +          "additionalProperties": false,
        +          "properties": {
        +            "labels": {
        +              "additionalProperties": {
        +                "maxLength": 256,
        +                "type": "string"
        +              },
        +              "propertyNames": {
        +                "maxLength": 64,
        +                "minLength": 1,
        +                "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +                "type": "string"
        +              },
        +              "type": "object"
        +            },
        +            "name": {
        +              "maxLength": 64,
        +              "minLength": 1,
        +              "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +              "type": "string"
        +            },
        +            "samples": {
        +              "items": {
        +                "additionalProperties": false,
        +                "properties": {
        +                  "timestamp": {
        +                    "format": "date-time",
        +                    "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +                    "type": "string"
        +                  },
        +                  "value": {
        +                    "type": "number"
        +                  }
        +                },
        +                "required": [
        +                  "timestamp",
        +                  "value"
        +                ],
        +                "type": "object"
        +              },
        +              "maxItems": 1440,
        +              "minItems": 1,
        +              "type": "array"
        +            }
        +          },
        +          "required": [
        +            "name",
        +            "labels",
        +            "samples"
        +          ],
        +          "type": "object"
        +        },
        +        "maxItems": 50,
        +        "type": "array"
        +      },
        +      "stepMs": {
        +        "maximum": 3600000,
        +        "minimum": 1000,
        +        "type": "integer"
        +      },
        +      "to": {
        +        "format": "date-time",
        +        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +        "type": "string"
        +      }
        +    },
        +    "required": [
        +      "queryTemplate",
        +      "series",
        +      "queryKind",
        +      "from",
        +      "to",
        +      "stepMs"
        +    ],
        +    "type": "object"
        +  }
        +]
      • removedOutput schema / properties / data / properties
        Removed value: -{
        -  "from": {
        -    "format": "date-time",
        -    "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -    "type": "string"
        -  },
        -  "queryKind": {
        -    "enum": [
        -      "instant",
        -      "range"
        -    ],
        -    "type": "string"
        -  },
        -  "queryTemplate": {
        -    "maxLength": 64,
        -    "minLength": 1,
        -    "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -    "type": "string"
        -  },
        -  "series": {
        -    "items": {
        -      "additionalProperties": false,
        -      "properties": {
        -        "labels": {
        -          "additionalProperties": {
        -            "maxLength": 256,
        -            "type": "string"
        -          },
        -          "propertyNames": {
        -            "maxLength": 64,
        -            "minLength": 1,
        -            "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -            "type": "string"
        -          },
        -          "type": "object"
        -        },
        -        "name": {
        -          "maxLength": 64,
        -          "minLength": 1,
        -          "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -          "type": "string"
        -        },
        -        "samples": {
        -          "items": {
        -            "additionalProperties": false,
        -            "properties": {
        -              "timestamp": {
        -                "format": "date-time",
        -                "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -                "type": "string"
        -              },
        -              "value": {
        -                "type": "number"
        -              }
        -            },
        -            "required": [
        -              "timestamp",
        -              "value"
        -            ],
        -            "type": "object"
        -          },
        -          "maxItems": 1440,
        -          "minItems": 1,
        -          "type": "array"
        -        }
        -      },
        -      "required": [
        -        "name",
        -        "labels",
        -        "samples"
        -      ],
        -      "type": "object"
        -    },
        -    "maxItems": 50,
        -    "type": "array"
        -  },
        -  "stepMs": {
        -    "maximum": 3600000,
        -    "minimum": 1000,
        -    "type": "integer"
        -  },
        -  "to": {
        -    "format": "date-time",
        -    "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -    "type": "string"
        -  }
        -}
      • removedOutput schema / properties / data / required
        Removed value: -[
        -  "queryTemplate",
        -  "queryKind",
        -  "series"
        -]
      • removedOutput schema / properties / data / type
        Removed value: -"object"
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
    • Changedobservability.render_dashboard6 fields changed
      • removedOutput schema / properties / data / additionalProperties
        Removed value: -false
      • addedOutput schema / properties / data / oneOf
        Added value: +[
        +  {
        +    "additionalProperties": false,
        +    "properties": {
        +      "available": {
        +        "const": true,
        +        "type": "boolean"
        +      },
        +      "dashboardId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "effectiveRange": {
        +        "additionalProperties": false,
        +        "properties": {
        +          "from": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          },
        +          "to": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          }
        +        },
        +        "required": [
        +          "from",
        +          "to"
        +        ],
        +        "type": "object"
        +      },
        +      "height": {
        +        "maximum": 4000,
        +        "minimum": 1,
        +        "type": "integer"
        +      },
        +      "panelId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "rawByteSize": {
        +        "maximum": 8388608,
        +        "minimum": 1,
        +        "type": "integer"
        +      },
        +      "renderDurationMs": {
        +        "maximum": 30000,
        +        "minimum": 0,
        +        "type": "integer"
        +      },
        +      "requestedRange": {
        +        "additionalProperties": false,
        +        "properties": {
        +          "from": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          },
        +          "to": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          }
        +        },
        +        "required": [
        +          "from",
        +          "to"
        +        ],
        +        "type": "object"
        +      },
        +      "sha256": {
        +        "pattern": "^[a-f0-9]{64}$",
        +        "type": "string"
        +      },
        +      "width": {
        +        "maximum": 2400,
        +        "minimum": 1,
        +        "type": "integer"
        +      }
        +    },
        +    "required": [
        +      "dashboardId",
        +      "requestedRange",
        +      "width",
        +      "height",
        +      "available",
        +      "effectiveRange",
        +      "rawByteSize",
        +      "sha256",
        +      "renderDurationMs"
        +    ],
        +    "type": "object"
        +  },
        +  {
        +    "additionalProperties": false,
        +    "properties": {
        +      "available": {
        +        "const": false,
        +        "type": "boolean"
        +      },
        +      "dashboardId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "height": {
        +        "maximum": 4000,
        +        "minimum": 1,
        +        "type": "integer"
        +      },
        +      "panelId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "requestedRange": {
        +        "additionalProperties": false,
        +        "properties": {
        +          "from": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          },
        +          "to": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          }
        +        },
        +        "required": [
        +          "from",
        +          "to"
        +        ],
        +        "type": "object"
        +      },
        +      "width": {
        +        "maximum": 2400,
        +        "minimum": 1,
        +        "type": "integer"
        +      }
        +    },
        +    "required": [
        +      "dashboardId",
        +      "requestedRange",
        +      "width",
        +      "height",
        +      "available"
        +    ],
        +    "type": "object"
        +  }
        +]
      • removedOutput schema / properties / data / properties
        Removed value: -{
        -  "dashboardId": {
        -    "maxLength": 64,
        -    "minLength": 1,
        -    "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -    "type": "string"
        -  },
        -  "effectiveRange": {
        -    "additionalProperties": false,
        -    "properties": {
        -      "from": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      },
        -      "to": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      }
        -    },
        -    "required": [
        -      "from",
        -      "to"
        -    ],
        -    "type": "object"
        -  },
        -  "height": {
        -    "maximum": 4000,
        -    "minimum": 1,
        -    "type": "integer"
        -  },
        -  "panelId": {
        -    "maxLength": 64,
        -    "minLength": 1,
        -    "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -    "type": "string"
        -  },
        -  "rawByteSize": {
        -    "maximum": 8388608,
        -    "minimum": 1,
        -    "type": "integer"
        -  },
        -  "renderDurationMs": {
        -    "maximum": 30000,
        -    "minimum": 0,
        -    "type": "integer"
        -  },
        -  "requestedRange": {
        -    "additionalProperties": false,
        -    "properties": {
        -      "from": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      },
        -      "to": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      }
        -    },
        -    "required": [
        -      "from",
        -      "to"
        -    ],
        -    "type": "object"
        -  },
        -  "sha256": {
        -    "pattern": "^[a-f0-9]{64}$",
        -    "type": "string"
        -  },
        -  "width": {
        -    "maximum": 2400,
        -    "minimum": 1,
        -    "type": "integer"
        -  }
        -}
      • removedOutput schema / properties / data / required
        Removed value: -[
        -  "dashboardId",
        -  "requestedRange",
        -  "effectiveRange",
        -  "width",
        -  "height",
        -  "rawByteSize",
        -  "sha256",
        -  "renderDurationMs"
        -]
      • removedOutput schema / properties / data / type
        Removed value: -"object"
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
    • Changedobservability.render_panel6 fields changed
      • removedOutput schema / properties / data / additionalProperties
        Removed value: -false
      • addedOutput schema / properties / data / oneOf
        Added value: +[
        +  {
        +    "additionalProperties": false,
        +    "properties": {
        +      "available": {
        +        "const": true,
        +        "type": "boolean"
        +      },
        +      "dashboardId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "effectiveRange": {
        +        "additionalProperties": false,
        +        "properties": {
        +          "from": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          },
        +          "to": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          }
        +        },
        +        "required": [
        +          "from",
        +          "to"
        +        ],
        +        "type": "object"
        +      },
        +      "height": {
        +        "maximum": 4000,
        +        "minimum": 1,
        +        "type": "integer"
        +      },
        +      "panelId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "rawByteSize": {
        +        "maximum": 8388608,
        +        "minimum": 1,
        +        "type": "integer"
        +      },
        +      "renderDurationMs": {
        +        "maximum": 30000,
        +        "minimum": 0,
        +        "type": "integer"
        +      },
        +      "requestedRange": {
        +        "additionalProperties": false,
        +        "properties": {
        +          "from": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          },
        +          "to": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          }
        +        },
        +        "required": [
        +          "from",
        +          "to"
        +        ],
        +        "type": "object"
        +      },
        +      "sha256": {
        +        "pattern": "^[a-f0-9]{64}$",
        +        "type": "string"
        +      },
        +      "width": {
        +        "maximum": 2400,
        +        "minimum": 1,
        +        "type": "integer"
        +      }
        +    },
        +    "required": [
        +      "dashboardId",
        +      "requestedRange",
        +      "width",
        +      "height",
        +      "available",
        +      "effectiveRange",
        +      "rawByteSize",
        +      "sha256",
        +      "renderDurationMs"
        +    ],
        +    "type": "object"
        +  },
        +  {
        +    "additionalProperties": false,
        +    "properties": {
        +      "available": {
        +        "const": false,
        +        "type": "boolean"
        +      },
        +      "dashboardId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "height": {
        +        "maximum": 4000,
        +        "minimum": 1,
        +        "type": "integer"
        +      },
        +      "panelId": {
        +        "maxLength": 64,
        +        "minLength": 1,
        +        "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        +        "type": "string"
        +      },
        +      "requestedRange": {
        +        "additionalProperties": false,
        +        "properties": {
        +          "from": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          },
        +          "to": {
        +            "format": "date-time",
        +            "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        +            "type": "string"
        +          }
        +        },
        +        "required": [
        +          "from",
        +          "to"
        +        ],
        +        "type": "object"
        +      },
        +      "width": {
        +        "maximum": 2400,
        +        "minimum": 1,
        +        "type": "integer"
        +      }
        +    },
        +    "required": [
        +      "dashboardId",
        +      "requestedRange",
        +      "width",
        +      "height",
        +      "available"
        +    ],
        +    "type": "object"
        +  }
        +]
      • removedOutput schema / properties / data / properties
        Removed value: -{
        -  "dashboardId": {
        -    "maxLength": 64,
        -    "minLength": 1,
        -    "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -    "type": "string"
        -  },
        -  "effectiveRange": {
        -    "additionalProperties": false,
        -    "properties": {
        -      "from": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      },
        -      "to": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      }
        -    },
        -    "required": [
        -      "from",
        -      "to"
        -    ],
        -    "type": "object"
        -  },
        -  "height": {
        -    "maximum": 4000,
        -    "minimum": 1,
        -    "type": "integer"
        -  },
        -  "panelId": {
        -    "maxLength": 64,
        -    "minLength": 1,
        -    "pattern": "^[A-Za-z0-9][A-Za-z0-9._:-]*$",
        -    "type": "string"
        -  },
        -  "rawByteSize": {
        -    "maximum": 8388608,
        -    "minimum": 1,
        -    "type": "integer"
        -  },
        -  "renderDurationMs": {
        -    "maximum": 30000,
        -    "minimum": 0,
        -    "type": "integer"
        -  },
        -  "requestedRange": {
        -    "additionalProperties": false,
        -    "properties": {
        -      "from": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      },
        -      "to": {
        -        "format": "date-time",
        -        "pattern": "^(?:(?:\\d\\d[2468][048]|\\d\\d[13579][26]|\\d\\d0[48]|[02468][048]00|[13579][26]00)-02-29|\\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\\d|30)|(?:02)-(?:0[1-9]|1\\d|2[0-8])))T(?:(?:[01]\\d|2[0-3]):[0-5]\\d(?::[0-5]\\d(?:\\.\\d+)?)?(?:Z|([+-](?:[01]\\d|2[0-3]):[0-5]\\d)))$",
        -        "type": "string"
        -      }
        -    },
        -    "required": [
        -      "from",
        -      "to"
        -    ],
        -    "type": "object"
        -  },
        -  "sha256": {
        -    "pattern": "^[a-f0-9]{64}$",
        -    "type": "string"
        -  },
        -  "width": {
        -    "maximum": 2400,
        -    "minimum": 1,
        -    "type": "integer"
        -  }
        -}
      • removedOutput schema / properties / data / required
        Removed value: -[
        -  "dashboardId",
        -  "requestedRange",
        -  "effectiveRange",
        -  "width",
        -  "height",
        -  "rawByteSize",
        -  "sha256",
        -  "renderDurationMs"
        -]
      • removedOutput schema / properties / data / type
        Removed value: -"object"
      • changedOutput schema / properties / providerClass / enum
        Previous value: -[
        -  "fake",
        -  "grafana",
        -  "prometheus-compatible",
        -  "composite"
        -]New value: +[
        +  "fake",
        +  "grafana",
        +  "prometheus-compatible",
        +  "grafana-alertmanager",
        +  "composite"
        +]
  2. 7 tool updatesv0.1.0
    • First observedobservability.active_alerts
    • First observedobservability.capabilities
    • First observedobservability.health_snapshot
    • First observedobservability.incident_context
    • First observedobservability.query_metrics
    • First observedobservability.render_dashboard
    • First observedobservability.render_panel

TDQS

B3.2/5.0
Disambiguation4/5

Tools have distinct purposes: alerts, capabilities, health, incident context, metrics query, dashboard/panel rendering. Slight overlap between health_snapshot and incident_context (which includes health), but overall clear boundaries.

Naming Consistency4/5

All tools share 'observability.' prefix and use snake_case. However, some use noun phrases (capabilities, incident_context) while others use verb_noun (query_metrics, render_dashboard), causing minor inconsistency in pattern.

Tool Count5/5

7 tools is well-scoped for an observability agent covering alerts, health, metrics, dashboards, and capabilities. Each tool serves a clear function without redundancy.

Completeness4/5

Covers core observability aspects (alerts, health, metrics, visuals). Missing logs and traces, but given the agent-safe and bounded focus, the set is reasonably complete for its stated purpose.

Maintenance

ActivitySlowing
ResponsivenessNo issues

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Connectors

Related MCP Servers

  • F
    license
    A
    quality
    D
    maintenance
    A Model Context Protocol server that provides read-only access to Datasette instances, enabling AI assistants to explore, query, and analyze data from Datasette databases through a standardized interface.
    5
    2
    -
  • A
    license
    Not graded
    quality
    Not graded
    maintenance
    A Model Context Protocol server that provides access to Observe API functionality, enabling LLMs to execute OPAL queries, manage datasets/monitors, and leverage vector search for documentation and troubleshooting runbooks.
    1
    -
  • F
    license
    Not graded
    quality
    D
    maintenance
    Model Context Protocol (MCP) server that gives AI assistants a safe, correct data-analyst capability over business metrics - without raw SQL improvisation.
    -
  • A
    license
    Not graded
    quality
    C
    maintenance
    A governed, audited Model Context Protocol server that provides AI agents with secure, read-only access to a clinical knowledge base through least-privilege tools, policy validation, and append-only audit logging.
    MIT

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/hmrdkn-labs/pos-satpam'

If you have feedback or need assistance with the MCP directory API, please join our Discord server