All posts
Guide

MCP for Agencies: Delegate Audits to Claude

Learn how agencies can use Claude MCP servers to automate AI visibility audits at scale. Step-by-step guide for delegating SearchFit audits.

KKevin15 minutes read

MCP for Agencies: Delegate Audits to Claude

The Audit Bottleneck Agencies Face

You're running audits for 15 clients. Each one needs visibility across ChatGPT, Perplexity, Gemini, Claude, and Grok. Each one needs to know: Are we cited? Are our competitors? What's our share of voice in AI search? The manual work stacks fast. Your team spends hours pulling data, running checks, formatting reports, and then doing it again next month.

There's a better way. Model Context Protocol (MCP) lets you offload these audits to Claude, running them programmatically and at scale. Instead of your team manually logging into SearchFIT's platform for each client, Claude can execute audits, pull data, and generate reports autonomously, with your oversight and control.

This guide walks you through setting up MCP for agencies, connecting Claude to your audit workflow, and shipping client deliverables faster. By the end, you'll have a repeatable system that scales from 5 clients to 50 without proportional headcount growth.

Why MCP Matters for Agency Audits

MCP is an open protocol that connects Claude to tools, data sources, and workflows. Think of it as a standardized way to give Claude access to your systems, without hardcoding API keys or building custom integrations for each client.

For agencies managing AI visibility, MCP solves three concrete problems:

First, it eliminates manual data collection. Instead of logging into multiple platforms and exporting CSVs, Claude queries your audit system directly and extracts the metrics you need.

Second, it enforces audit trails. When Claude runs a client audit, every step is logged. You can see exactly what data was accessed, when, and why. This matters for compliance and client trust. Frameworks like zero-trust capability delegation for MCP agents ensure that Claude only accesses the specific client data it's authorized to touch, not all clients at once.

Third, it scales reporting without scaling headcount. Once your MCP server is built and Claude is connected, adding a new client audit is a prompt away. No new scripts, no new workflows, no new team members.

The federal government has already adopted MCP for connecting Claude and other AI systems to public data, recognizing that standardized, auditable connections between AI and data sources improve accuracy and reliability. Agencies can apply the same logic: standardize how Claude accesses client audit data, and you get faster, more reliable reporting.

Prerequisites: What You Need Before Starting

Before you set up MCP for audits, confirm you have these components in place:

SearchFIT account with API access. You need to be able to pull AI visibility data programmatically. SearchFIT's AI tracking gives you visibility across ChatGPT, Perplexity, Claude, Gemini, and other engines. You'll need API credentials to query this data from your MCP server.

Claude API access. You'll be using Claude (via API) to run audits, not the web interface. Sign up for Claude API access at Anthropic if you haven't already.

Basic familiarity with MCP servers. You don't need to be a developer, but you should understand that MCP servers are small applications that expose tools to Claude. The MCP servers guidebook explains authentication, permissions, and audit logs in detail.

A development environment. You'll need a machine where you can run a server (local or cloud). Node.js or Python is typical, depending on your MCP server implementation.

Client data structure. Know how you're storing client audit requests, database, spreadsheet, or CRM. You'll be querying this to feed Claude the right context.

If you're missing any of these, pause and set them up first. The rest of this guide assumes you have all four in place.

Step 1: Design Your MCP Server for Audit Delegation

Your MCP server is the bridge between Claude and your audit system. It needs to expose tools that Claude can call to run audits and fetch results.

Start by defining the tools your MCP server will expose. At minimum, you need:

Audit Trigger Tool. Accepts a client ID and domain, then initiates an AI visibility scan across all engines. Returns a scan ID and status.

Data Fetch Tool. Accepts a scan ID and returns structured audit results: citations found, competitor visibility, share of voice, trends over time.

Report Generation Tool. Accepts audit results and client metadata, then formats a report (PDF, HTML, or markdown) ready to send to the client.

Client Lookup Tool. Accepts a client ID and returns the client's domain, industry, competitors, and any custom audit parameters you've set.

Each tool should have clear inputs and outputs. Claude needs to know what data to pass in and what to expect back. Use the Claude Code architecture documentation as a reference, it explains how Claude Code handles tools, permissions, and sandboxing, all of which apply to MCP servers.

Here's a rough structure:

MCP Server
├── Authentication (API key validation)
├── Tools
│   ├── trigger_audit(client_id, domain)
│   ├── fetch_audit_results(scan_id)
│   ├── generate_report(scan_id, client_id)
│   └── lookup_client(client_id)
└── Audit Logs (every call is recorded)

Each tool call is logged with a timestamp, the user (Claude), the client ID, and the result. This audit trail is non-negotiable for agencies, your clients need to know their data wasn't accessed without reason.

Step 2: Implement Permission Scoping

Here's the critical part: Claude should never have access to all client data at once. If you're running an audit for Client A, Claude should only be able to query Client A's data.

This is called permission scoping, and it's the foundation of secure delegation. When Claude makes a tool call, your MCP server checks: Is Claude authorized to access this client? If not, the call is rejected.

Implement scoping like this:

1. Assign each audit request a scope. When you (or your system) ask Claude to audit Client A, you pass a scope parameter: scope: client_a. Claude receives this scope and can only call tools within that scope.

2. Validate scope on every tool call. Before your MCP server executes any tool, it checks: Does the current scope match the requested data? If Claude tries to fetch Client B's data while scoped to Client A, the server rejects it.

3. Log all scope violations. If someone (or some automation) tries to access out-of-scope data, log it. Alert your team. This is a red flag.

The zero-trust capability delegation framework provides a detailed model for this. The idea is simple: assume Claude is untrusted by default, and only grant access to specific data based on explicit scope parameters. This prevents accidents (Claude accidentally querying the wrong client) and malicious scenarios (a compromised API key being used to scrape all client data).

Step 3: Set Up SearchFIT API Integration

Your MCP server needs to talk to SearchFIT to pull AI visibility data. This is the core of your audit.

First, get your SearchFIT API credentials. Log into your SearchFIT account, go to Settings > API, and generate a key. Store it securely, never commit it to version control.

In your MCP server code, create a SearchFIT client:

import requests

class SearchFITClient:
def __init__(self, api_key):
self.api_key = api_key
self.base_url = "https://api.searchfit.ai"

def get_ai_visibility(self, domain):
"""Fetch AI visibility metrics for a domain across all engines."""
headers = {"Authorization": f"Bearer {self.api_key}"}
response = requests.get(
f"{self.base_url}/visibility/{domain}",
headers=headers
)
return response.json()

def get_citations(self, domain, engine):
"""Fetch citations for a domain in a specific AI engine."""
headers = {"Authorization": f"Bearer {self.api_key}"}
response = requests.get(
f"{self.base_url}/citations/{domain}?engine={engine}",
headers=headers
)
return response.json()

This client handles authentication and data fetching. Your MCP server's tools will use this client to pull data, then return it to Claude.

Next, test the connection. Query a domain you know and verify you get back citation data, rankings, and visibility scores. If the API is working, you're ready to wire it into your tools.

Step 4: Build the Audit Trigger Tool

This tool tells SearchFIT to scan a domain and return a scan ID. Claude will call this first to kick off the audit.

def trigger_audit(client_id: str, domain: str, scope: str) -> dict:
"""
Trigger an AI visibility audit for a domain.

Args:
client_id: Unique identifier for the client
domain: Domain to audit (e.g., example.com)
scope: Permission scope (must match client_id)

Returns:
Scan ID and status
"""
# Validate scope
if scope != client_id:
return {"error": "Scope mismatch. Unauthorized.", "status": "rejected"}

# Log the request
log_audit_event("trigger_audit", client_id, domain, scope)

# Trigger the scan
searchfit = SearchFITClient(api_key=os.getenv("SEARCHFIT_API_KEY"))
result = searchfit.trigger_scan(domain)

return {
"scan_id": result["scan_id"],
"status": "initiated",
"domain": domain,
"client_id": client_id
}

When Claude calls this tool, it passes the client ID and domain. The server validates the scope, logs the event, and triggers the scan. The scan ID is returned so Claude can fetch results later.

Step 5: Build the Data Fetch Tool

Once the audit is complete, Claude needs to retrieve the results. This tool fetches citation data, competitor visibility, and share of voice metrics.

def fetch_audit_results(scan_id: str, client_id: str, scope: str) -> dict:
"""
Fetch results from a completed audit.

Args:
scan_id: ID of the scan to fetch
client_id: Client who requested the audit
scope: Permission scope

Returns:
Audit results with citations, competitors, and metrics
"""
# Validate scope
if scope != client_id:
return {"error": "Scope mismatch. Unauthorized.", "status": "rejected"}

# Log the request
log_audit_event("fetch_results", client_id, scan_id, scope)

# Fetch from SearchFIT
searchfit = SearchFITClient(api_key=os.getenv("SEARCHFIT_API_KEY"))
results = searchfit.get_scan_results(scan_id)

return {
"scan_id": scan_id,
"domain": results["domain"],
"citations": results["citations"],  # {engine: [sources]}
"competitors": results["competitors"],  # Visibility of top competitors
"share_of_voice": results["share_of_voice"],  # % of mentions
"trends": results["trends"],  # Month-over-month changes
"timestamp": results["timestamp"]
}

This tool returns structured audit data. Claude can now analyze the results and spot patterns: Is the client losing citations to competitors? Is their share of voice declining? What engines are they missing?

Step 6: Build the Report Generation Tool

Claude now has raw audit data. This tool formats it into a client-ready report.

def generate_report(scan_id: str, client_id: str, scope: str, format: str = "markdown") -> dict:
"""
Generate a formatted audit report.

Args:
scan_id: ID of the audit
client_id: Client requesting the report
scope: Permission scope
format: Output format (markdown, html, or pdf)

Returns:
Formatted report content
"""
# Validate scope
if scope != client_id:
return {"error": "Scope mismatch. Unauthorized.", "status": "rejected"}

# Log the request
log_audit_event("generate_report", client_id, scan_id, scope)

# Fetch audit data
searchfit = SearchFITClient(api_key=os.getenv("SEARCHFIT_API_KEY"))
results = searchfit.get_scan_results(scan_id)
client_info = get_client_info(client_id)

# Generate report
if format == "markdown":
report = f"""
# AI Visibility Audit Report

**Client:** {client_info['name']}
**Domain:** {results['domain']}
**Date:** {results['timestamp']}

## Executive Summary

Your brand is cited in AI search results {len(results['citations'])} times across major engines.
Your share of voice is {results['share_of_voice']}% in your category.

## Citations by Engine

"""
for engine, sources in results["citations"].items():
report += f"\n### {engine}\n"
report += f"- {len(sources)} citations\n"

report += f"\n## Competitor Visibility\n"
for competitor, data in results["competitors"].items():
report += f"- {competitor}: {data['citations']} citations\n"

return {"format": "markdown", "content": report, "status": "generated"}

# Similar logic for HTML and PDF formats
return {"error": "Unsupported format", "status": "failed"}

This tool takes raw audit data and formats it into a professional report. Claude can customize the narrative, add analysis, and highlight key insights before sending it to the client.

Step 7: Set Up Audit Logging and Monitoring

Every tool call must be logged. This is non-negotiable. Your clients need audit trails, and you need visibility into what Claude is doing.

Implement logging like this:

import json
from datetime import datetime

def log_audit_event(event_type: str, client_id: str, resource: str, scope: str, result: str = "success"):
"""
Log an audit event with full context.
"""
log_entry = {
"timestamp": datetime.utcnow().isoformat(),
"event_type": event_type,
"client_id": client_id,
"resource": resource,
"scope": scope,
"result": result,
"user_agent": "claude-mcp"
}

# Write to audit log file
with open("audit.log", "a") as f:
f.write(json.dumps(log_entry) + "\n")

# Also write to a database for querying
store_audit_log(log_entry)

Every audit event is timestamped and stored. You can query this log to answer: When was Client A's data accessed? By whom? For what purpose? This transparency builds trust with clients and protects you if disputes arise.

For additional oversight, consider implementing a system like CCO-MCP (Claude Code Oversight), which provides real-time audit and approval for Claude tool calls. This gives you a dashboard where you can see Claude's actions in real-time and approve/reject them if needed.

Step 8: Connect Claude to Your MCP Server

Now that your server is built, connect Claude to it. You'll use the Claude API with the MCP protocol.

Create a client script that initializes Claude with your MCP server:

from anthropic import Anthropic
import json

client = Anthropic()

# Define your MCP server tools
tools = [
{
"name": "trigger_audit",
"description": "Trigger an AI visibility audit for a domain",
"input_schema": {
"type": "object",
"properties": {
"client_id": {"type": "string", "description": "Client ID"},
"domain": {"type": "string", "description": "Domain to audit"},
"scope": {"type": "string", "description": "Permission scope"}
},
"required": ["client_id", "domain", "scope"]
}
},
# ... other tools
]

def run_audit(client_id, domain):
"""
Run an audit by delegating to Claude with MCP tools.
"""

# Create the initial prompt
prompt = f"""
Run a complete AI visibility audit for client {client_id} with domain {domain}.

Steps:
1. Trigger the audit using trigger_audit tool
2. Wait for the scan to complete
3. Fetch the results using fetch_audit_results tool
4. Generate a markdown report using generate_report tool
5. Return the report content
"""

# Call Claude with tools
messages = [{"role": "user", "content": prompt}]

response = client.messages.create(
model="claude-3-5-sonnet-20241022",
max_tokens=4096,
tools=tools,
messages=messages
)

# Process Claude's response and tool calls
while response.stop_reason == "tool_use":
# Extract tool calls from response
tool_calls = [block for block in response.content if block.type == "tool_use"]

# Execute each tool call
tool_results = []
for tool_call in tool_calls:
result = execute_tool(tool_call.name, tool_call.input, scope=client_id)
tool_results.append({
"type": "tool_result",
"tool_use_id": tool_call.id,
"content": json.dumps(result)
})

# Send results back to Claude
messages.append({"role": "assistant", "content": response.content})
messages.append({"role": "user", "content": tool_results})

response = client.messages.create(
model="claude-3-5-sonnet-20241022",
max_tokens=4096,
tools=tools,
messages=messages
)

# Extract final response
return response.content[0].text

This script creates a conversation with Claude, passing your MCP tools. Claude calls the tools as needed to complete the audit, and you capture the results.

Step 9: Test Your Setup with a Pilot Client

Before rolling this out to all clients, test it with one. Pick a client with straightforward requirements and a domain you know well.

Run the audit and check:

1. Do the tools execute without errors? Run through each tool call manually and verify it works.

2. Are results accurate? Compare Claude's report to a manual audit. Do the citation counts match? Are the competitor rankings correct?

3. Is the audit log complete? Check your audit log file. Every tool call should be recorded with timestamp, client ID, and result.

4. Is the report useful? Show the generated report to your pilot client. Does it answer their questions? Is it formatted well? Does it drive action?

If all four checks pass, you're ready to scale. If not, debug the failing tool and re-test.

Step 10: Automate Audit Scheduling

Once your MCP setup is working, automate it. Instead of manually running audits, schedule them to run weekly or monthly.

Create a cron job or scheduled task that:

  1. Fetches all active clients from your database
  2. For each client, calls run_audit(client_id, domain)
  3. Captures the generated report
  4. Emails the report to the client (or uploads it to your portal)
import schedule
import time

def scheduled_audit_run():
"""
Run audits for all active clients.
"""
clients = get_active_clients()

for client in clients:
try:
report = run_audit(client["id"], client["domain"])
send_report_to_client(client["email"], report)
log_audit_event("scheduled_audit", client["id"], "success")
except Exception as e:
log_audit_event("scheduled_audit", client["id"], f"failed: {str(e)}")
notify_support(f"Audit failed for {client['id']}: {str(e)}")

# Schedule to run every Monday at 9 AM
schedule.every().monday.at("09:00").do(scheduled_audit_run)

while True:
schedule.run_pending()
time.sleep(60)

Now audits run automatically. Your team spends time on strategy, not data collection.

Pro Tip: Implement Compliance Reporting

If you're managing audits for regulated industries (finance, healthcare, legal), you might need compliance reports. Tools like compliance report generators for Claude Code can automate security audits and compliance documentation.

You can extend your MCP server to generate compliance reports showing:

  • Which data was accessed
  • When it was accessed
  • Who accessed it (Claude, via your MCP server)
  • What happened to the data (stored, reported, deleted)

This is especially useful for clients subject to GDPR, HIPAA, or PCI DSS. They want proof that their data is handled securely.

Pro Tip: Use Claude's Memory for Client Context

Claude supports persistent memory across conversations. You can use this to store client-specific context, competitor lists, custom metrics, historical baselines, so Claude doesn't have to re-fetch it on every audit.

When Claude runs an audit for Client A, it can recall: "Client A's top competitor is Company B. Last month their share of voice was 12%. Their target is 15%." This context helps Claude generate more insightful reports.

Scaling Beyond Single Audits

Once your basic MCP audit system is working, you can extend it:

Batch audits. Instead of auditing one client, audit 10 at once. Claude can parallelize tool calls, so multiple audits run simultaneously.

Custom metrics. Add tools that compute custom metrics for specific clients: branded search volume, competitor benchmarks, content gaps.

Anomaly detection. Add a tool that flags unusual patterns: sudden drops in citations, competitors entering a client's space, new ranking opportunities.

Content recommendations. Based on audit results, have Claude recommend content topics that could improve AI visibility. This turns audits into actionable strategy.

Each of these is a new tool in your MCP server. Claude can call them in any order, depending on what the audit requires.

Understanding MCP Architecture for Your Setup

To troubleshoot and extend your MCP implementation, understand how it works under the hood. The MCP server protocols guidebook covers authentication, permissions, and audit logs in detail. Key concepts:

Tools. Functions that Claude can call. Each tool has inputs, outputs, and side effects (like querying SearchFIT or logging data).

Permissions. Rules that control which tools Claude can call and what data it can access. Scoping (like our scope parameter) is one permission model.

Audit logs. Records of every tool call, including who called it, when, what data was accessed, and what the result was.

Authentication. How Claude proves it's authorized to call your MCP server. Typically API keys or OAuth tokens.

For enterprise setups, consider implementing unified agent policies for delegated authority. This ensures that if you're running audits for multiple agencies (or if your agency has multiple teams), each one has the right permissions and can't accidentally access another's data.

Troubleshooting Common Issues

Claude is calling tools in the wrong order. Rewrite your prompt to be more explicit about the sequence. Instead of "Run an audit," say "First, trigger the audit. Wait for the scan ID. Then, fetch the results using that scan ID." Claude will follow the steps.

Audit results are incomplete. Check your SearchFIT API integration. Are you getting back citation data for all engines? If one engine is missing, SearchFIT might not have indexed that domain yet. Give it 24 hours and re-run.

Scope validation is failing. Double-check that the scope parameter matches the client_id. If you're passing scope="client_a" but client_id="client_1", the validation will reject it. Make sure your naming is consistent.

Reports are taking too long to generate. If Claude is spending time on analysis, that's fine, it means it's thinking. But if the API calls themselves are slow, check your SearchFIT API quotas. You might be hitting rate limits.

Key Takeaways

MCP lets you delegate audits to Claude at scale. Instead of your team running audits manually, Claude does it programmatically, with your oversight.

Permission scoping prevents accidents. By restricting Claude to specific client data, you ensure it can't accidentally leak information or access unauthorized domains.

Audit logging builds trust. Every tool call is recorded. You can show clients exactly what happened with their data, when, and why.

Automation compounds over time. Setting up MCP takes effort upfront, but once it's working, adding new clients is trivial. Your team's audit capacity scales without proportional cost growth.

This is just the start. You can extend MCP to generate custom reports, detect anomalies, recommend content, and more. Each extension is a new tool in your server.

Start with the basics: trigger audits, fetch results, generate reports. Get that working for 3-5 clients. Then expand. By month three, you'll have a system that scales to 50+ clients without breaking a sweat.

The agencies winning in AI search aren't the ones running audits manually. They're the ones who've automated the audit, freeing their team to focus on strategy, how to actually rank in ChatGPT, Perplexity, and Gemini. MCP gets you there.

Next Steps

  1. Set up your SearchFIT API connection. Log into SearchFIT, generate an API key, and test a query.

  2. Build your MCP server. Use the code examples in this guide to create tools for triggering audits, fetching results, and generating reports. Start simple, you can add complexity later.

  3. Connect Claude to your MCP server. Use the Claude API to call your tools. Test with one client.

  4. Implement audit logging. Every tool call should be logged. This is non-negotiable.

  5. Scale gradually. Once one client works, add a second. Then a third. Once you've proven the system works, automate the scheduling.

  6. Explore SearchFIT's analytics to understand what metrics matter most for your clients. This informs what your MCP tools should expose.

You've got this. Build the system, test it, and scale it. Your clients will get faster audits, and your team will have more time for strategy.

Get SearchFIT Weekly

What we are learning about getting brands cited in AI search, in your inbox every week. Unsubscribe any time.