Skip to main content
Glama

frontend-eyes

CI License: MIT

An MCP server that lets a coding agent see the page it just changed.

> make the pricing cards stack on mobile

  [frontend-eyes] capture http://localhost:5173/pricing
    mobile (360)       overflows by 224px - div.card is 180px wider than its parent
    tablet (768)       ok
    laptop (1280)      ok
    desktop (1920)     ok

  ...editing Pricing.tsx...

  [frontend-eyes] capture http://localhost:5173/pricing
    mobile (360)       ok
    tablet (768)       ok
    laptop (1280)      ok
    desktop (1920)     ok

That's the real output format, not a mock-up of one.


Why

Coding agents write front-end code blind. They change a stylesheet, can't see the result, and report success based on the diff they just wrote. Anyone who's watched an agent confidently break a layout and then tell you it's fixed knows the failure mode.

There are general browser-control servers, and they hand the agent a whole browser with fifty tools. That's a lot of tokens and a lot of ways to get lost. This one doesn't drive a browser. It answers the two questions that actually come up after a front-end change:

  1. What does it look like, at the sizes people use?

  2. Did anything throw or fail to load?

Narrow beats general here. Small responses, cheap enough to call every turn.

Related MCP server: websight

Tools

Tool

Returns

capture

Per-viewport overflow detection naming the one element responsible; screenshots on request

diagnose

Console errors, uncaught exceptions, failed requests

audit

Accessibility violations via axe, ranked, with the offending selector

v0.2

compare

Visual diff against the previous capture

v0.2

Responses are terse on purpose. Images come back only when asked for, because a screenshot costs thousands of tokens and most turns only need "360px overflows by 224px".

The overflow bit

The interesting part is naming one element.

When a box is too wide, every ancestor is too wide as well, so a list of offenders is mostly the path back to <body>. Worse, an oversized box shoves its later siblings further right than itself — so sorting by "furthest past the edge" picks a victim rather than the cause.

A culprit is an element that doesn't fit inside its own parent. Deepest one wins, since its ancestors are only wide on its account.

I arrived at the same rule independently in whylayout, and the two agree on the same page — div.tile.tile--wide, 550px wider than its parent at 1280. Two implementations reaching the same answer is about as much confidence as you get without a spec to check against.

Install

npm install -g frontend-eyes
{
  "mcpServers": {
    "frontend-eyes": {
      "command": "frontend-eyes",
      "args": ["--allow", "http://localhost:*"]
    }
  }
}

Safety

It only visits origins matched by --allow, which defaults to localhost and 127.0.0.1. This exists to look at the dev server on your own machine, not to browse the web on an agent's behalf.

Out-of-allowlist URLs are refused outright rather than confirmed. The caller is a model, so a confirmation prompt would just be answered by the model — refusal is the only response that means anything.

Checking it works

Point it at any dev server:

npm run build && node scripts/smoke.mjs http://localhost:5173

Against a page with a deliberately oversized grid item:

capture http://localhost:5173
mobile (360)       overflows by 1409.1px - div.tile.tile--wide is 1338px wider than its parent
tablet (768)       overflows by 1001.1px - div.tile.tile--wide is 930px wider than its parent
laptop (1280)      overflows by 555.1px - div.tile.tile--wide is 550px wider than its parent
desktop (1920)     overflows by 235.1px - div.tile.tile--wide is 550px wider than its parent

allowlist
  allow   http://localhost:5173
  refuse  https://example.com/
  refuse  http://localhost.evil.com/

That last refusal is the one worth having a test for — localhost.evil.com is a real domain someone else can own, and a naive startsWith('http://localhost') would wave it straight through.

How it's built

Everything with a decision in it is a pure function over plain data: which element is the culprit, how a viewport string parses, what the response says. Those get unit tests. The Playwright layer that actually drives Chromium doesn't, because mocking Playwright would only prove the mocks were called.

src/
  browser/   the origin allowlist, breakpoints, one reused browser
  dom/       the culprit rule - pure, over measurements
  format/    responses, terse by default
  tools/     capture and diagnose

21 unit tests. The browser half is verified by running scripts/smoke.mjs against a real dev server.

Not done yet

  • audit and compare. The uniforms are planned in PLAN.md, the code isn't written.

  • No screenshot baseline storage, which compare needs first.

  • Chromium only.

Licence

MIT

Available Tools

2 tools
captureCapture at breakpointsA

Load a page at several viewport widths and report which of them overflow sideways, naming the single element responsible. Returns text; pass screenshots:true only when an image is genuinely needed, as each one is expensive.

ParametersJSON Schema
NameRequiredDescriptionDefault
urlYesThe page to look at, e.g. http://localhost:5173/pricing
viewportsNoNames (mobile, tablet, laptop, desktop), sizes like 414x896, or widths like 414
screenshotsNoAttach a PNG per viewport. Off by default.

TDQS

A4.4/5.0
Behavior4/5

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

With no annotations provided, the description carries the disclosure burden and does well: it explains the tool loads pages, checks multiple viewports, reports overflow, returns text, and warns that screenshots are costly. It does not mention default viewport behavior or exact output formatting, but it discloses the most relevant operational traits.

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?

The description is two concise sentences. The first sentence front-loads the core purpose and expected output, and the second sentence delivers cost-aware guidance for a specific parameter. Every clause adds useful information without redundancy.

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

Completeness4/5

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

For a tool with three parameters and no output schema, the description covers the main behavior, return type, and parameter nuance. It leaves a minor gap by not specifying what happens when the optional viewports parameter is omitted, but an agent can still use the tool effectively with the provided information.

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?

The input schema already documents all three parameters at 100% coverage, so the baseline is 3. The description adds valuable meaning on top by warning that screenshots are expensive and should only be requested when genuinely needed, which helps agents avoid unnecessary resource use. The url and viewports parameters do not need additional explanation because the schema already covers them.

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 states a specific action: load a page at multiple viewport widths, check for sideways overflow, and name the single responsible element. It clearly distinguishes this tool from a generic 'capture' by explaining the analysis it performs and the text result it returns.

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

Usage Guidelines4/5

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

The description gives clear context for when to use the tool and practical guidance for the screenshots parameter, saying to pass screenshots:true only when an image is genuinely needed because each image is expensive. It does not explicitly compare to the sibling tool 'diagnose', but the intended use case is well implied.

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

diagnoseConsole and network errorsA

Load a page and report console errors, uncaught exceptions and failed requests. Listeners attach before navigation, so errors thrown during load are caught.

ParametersJSON Schema
NameRequiredDescriptionDefault
urlYesThe page to load
viewportNoWhich viewport to load it at. Defaults to laptop.

TDQS

A4/5.0
Behavior4/5

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

With no annotations provided, the description carries the behavioral burden. It discloses a key non-obvious trait: listeners attach before navigation, so load-time errors are captured. This adds meaningful context beyond the schema, though it does not detail edge cases like timeouts or unreachable pages.

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?

Two sentences with no filler. The primary action and outputs are front-loaded, and the second sentence adds the crucial listener-timing detail. Every word earns its place.

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

Completeness4/5

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

For a simple two-parameter diagnostic tool, the description covers the main invocation need and return content. It lacks explicit output-format details or failure behavior, and there is no output schema to compensate, but the core usage is adequately specified.

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

Parameters3/5

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

Schema description coverage is 100%, with clear descriptions for 'url' and 'viewport'. The tool description does not add parameter-level details beyond what the schema already provides, so the baseline score of 3 is appropriate.

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 states a specific verb and resource: load a page and report console errors, uncaught exceptions, and failed requests. This clearly differentiates it from the sibling tool 'capture', which implies visual capture rather than diagnostic reporting.

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?

Usage context is implied by the title and description: use this tool when you need to detect page-load errors, exceptions, or failed requests. However, there is no explicit guidance about when not to use it or how it relates to the sibling 'capture' tool.

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

TDQS

A4.2/5.0
Disambiguation5/5

capture is solely concerned with layout overflow across viewport widths, while diagnose handles console errors, exceptions, and failed requests. Their purposes are clearly separated with no meaningful overlap.

Naming Consistency4/5

Both tool names are lowercase imperative verbs and follow the same two-tool pattern, but they are generic single words rather than descriptive verb_noun pairs. This is still internally consistent, though slightly less informative.

Tool Count4/5

Two tools is small, but the server appears intentionally scoped to frontend issue detection rather than broad browser automation. The count is slightly thin yet reasonable for the stated purpose.

Completeness4/5

The pair covers common frontend failure modes: visual overflow and runtime/network errors. Missing areas like accessibility or performance checks are not obviously required by the server's narrow focus, though the surface is minimal.

Maintenance

ActivityMaintained
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

  • A
    license
    Not graded
    quality
    A
    maintenance
    Bridges AI coding agents with the browser to provide visual debugging, real-time error capture, screenshot capabilities, DOM inspection, and interactive wireframing through a reverse proxy with injected developer tools.
    58
    19
    Apache 2.0
  • A
    license
    Not graded
    quality
    D
    maintenance
    Enables AI agents to see, analyze, and visually verify web page changes through pixel-perfect diffing, theme extraction, layout analysis, and interactive element detection.
    8
    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/GeoCodeCrafter/frontend-eyes'

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