Monitor visual changes
Text can stay identical while a page falls apart visually — a broken hero image, a collapsed layout, a banner that silently vanished. This visual regression monitoring API renders the page, compares it against the last known-good capture, and tells you precisely what moved, appeared, or disappeared.
Why pixels lie less than text
A diff of raw HTML will happily tell you nothing changed when, in reality, a CSS file failed to load and your entire checkout page is now unstyled text on a white background. Design teams, QA engineers, and anyone running marketing or landing pages that must look a certain way need a check that renders the page like a real visitor would see it, then compares that rendering over time. That is the gap this endpoint fills.
What actually happens on each check
You call POST /web/monitor-visual with a URL and a check frequency; the task renders the page, captures it, and stores a visual fingerprint. On every subsequent comprobación, the new capture is compared region by region against the baseline. If the difference crosses a meaningful threshold, you get a result carrying the affected areas and a before/after reference — not a vague 'something changed' flag.
From single screenshots to a discipline
Visual regression testing grew out of frontend QA, where teams got tired of shipping a broken button color or a layout shift nobody caught in a manual review. Applying the same idea to live production pages — not just staging builds — closes a blind spot: things break in production for reasons staging never sees, from a CDN misconfiguration to a third-party widget going dark.
Built to sit inside your own automation
Every task is asynchronous: you receive a task_id immediately and the actual result later, via a signed webhook (recommended for pipelines) or a signed link valid for 24 hours. That means you can schedule checks from your own cron, feed results straight into an incident channel, or chain them after a deploy step — without holding a connection open or polling in a loop.
Pricing that matches what you use
The endpoint costs $0.040 per request plus $0.001 per comprobación, published and predictable. There is no free tier and no trial period — access requires prepaid balance, which keeps the checking capacity fast and free of abuse. A failed task is retried up to three times automatically and is never charged if it ultimately fails.
What you can do with it
Marketing page integrity
Confirm that a campaign landing page still renders its hero, pricing table, and call-to-action exactly as designed after every deploy.
Third-party widget failure
Catch the moment a chat widget, cookie banner, or embedded video silently stops loading and leaves a visible gap.
Competitor layout tracking
Watch a competitor's pricing or feature page for a visual redesign before the change shows up anywhere else.
Post-deploy visual QA
Run an automatic visual comprobación right after a release pipeline finishes, gating a rollback decision on the result.
FAQ
How does visual monitoring differ from checking if the HTML changed?
HTML can stay technically valid while the page renders broken — a missing stylesheet, a hidden section, an image that fails silently. This visual regression monitoring API compares actual rendered output, so it catches what a text diff misses.
Is there a free trial for the visual monitor endpoint?
There's no free tier — free tiers get abused and slow everyone down. Access runs on a prepaid ForHosting KIT balance: top up from $10.00 (it never expires) and each request is charged at its published price, so a call with no balance returns HTTP 402. No subscription, no tokens, no invented credits, and a failed task is never charged.
How do I get the comparison result?
Every call to POST /web/monitor-visual returns a task_id immediately; the result arrives via a signed webhook or a signed link valid for 24 hours, whichever you configure.
What counts as a comprobación?
Each individual visual check performed against the target URL — the baseline capture plus every subsequent comparison — is billed at $0.001, on top of the $0.040 base request cost.
Can I monitor pages that require login or specific viewport sizes?
Yes, the target URL and rendering parameters are set per request, so authenticated or device-specific pages can be checked as long as the page itself is reachable.
What happens if a check fails, like a timeout?
The task retries automatically up to three times; if it still fails, you get a clear error and are not charged for that failed attempt.
Do you keep my screenshots forever?
No. Captured data is deleted after the retention period and is never used for training — it exists only to serve your comparison and webhook delivery.
Can I run this in bulk across many URLs?
Yes, each URL is its own asynchronous request, so you can trigger monitor-visual checks across as many pages as you need from your own scheduler.
For developers — API access
Everything on this page is available programmatically. This section is for teams who want to wire it into their own systems; everyone else can just use the tool above.
API endpoint
Prefer to automate it? One authenticated POST creates the task; the result comes back by webhook or a signed link. The same capability also runs here on the web, and soon from our app, email and Telegram.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/web/monitor-visual \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"input":"…"}'const res = await fetch("https://api.kit.forhosting.com/web/monitor-visual", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"input": "…"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/web/monitor-visual",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"input": "…"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/web/monitor-visual", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"input":"…"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"input":"…"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/web/monitor-visual", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"input": "…"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "web.monitor_visual",
"status": "queued",
"_links": {
"result": "/tasks/tsk_…/result"
}
}The API is asynchronous: the call returns a task_id immediately and the result arrives by webhook. Polling is capped at 1 req/s per task.
Pricing
Published price — no tokens, no invented credits. A failed task is never charged.
Limits
timeout_sec | 30 |
max_crawl_pages | 25 |
Errors
| HTTP | Code | Meaning |
|---|---|---|
401 | unauthorized | Missing or invalid API key. |
402 | insufficient_balance | Your balance doesn't cover the task price. |
404 | unknown_type | That task type doesn't exist. |
429 | rate_limited | Too many requests. Use the webhook instead of polling. |
422 | task_failed | The task failed after 3 retries. You are never charged for it. |