campaign-preflight-mcp
캠페인 프리플라이트
Campaign Preflight는 아웃바운드 캠페인을 위한 읽기 전용 린터입니다. 발송 전에 구성, 연락처 데이터, 개인화, 억제, 일정, 발신자 문제를 잡아냅니다.
하는 일
모든 아웃바운드 팀은 실수가 담긴 캠페인을 한 번쯤 발송해 본 적이 있습니다. 구독을 취소한 사람이 메일을 받았고, 시퀀스가 잠재 고객이 답장한 후에도 계속 후속 메일을 보냈고, 병합 필드가 병합되지 않아 200명이 "Hi {{first_name}}"을 받았습니다.
발송이 끝난 후에야 알게 됩니다.
Campaign Preflight는 캠페인의 구성, 리드, 카피, 일정, 발신자, 억제 노출에 대해 76개의 결정적 검사를 실행하고, 모든 발견 사항에 대한 근거와 함께 발송 준비 상태 판정을 반환합니다. 공급자에 쓰기 작업을 하지 않으며 어떤 것도 활성화할 수 없습니다.
하지 않는 일을 뒤에 묻어 두지 않고 앞에 명시합니다:
전달 가능성을 보장하지 않습니다. 받은 편지함 배치가 아니라 구성과 데이터를 검사하며, 전달 가능성 점수를 임의로 만들어 내지 않습니다.
법률 자문을 제공하지 않습니다. 지역, 도메인, 옵트아웃 검사는 캠페인을 사용자가 직접 구성한 정책과 비교합니다 — GDPR, CAN-SPAM, CASL이 아닙니다.
사서함을 검증하지 않습니다. 주소 검사는 구문 검사일 뿐입니다. DNS도 SMTP도 없습니다.
공급자의 안전장치를 대체하지 않습니다. 그대로 켜 두세요.
결과는 특정 시점의 스냅샷입니다. 09:00에 통과한 캠페인은 09:05에 수정될 수 있습니다.
자세한 내용은 docs/limitations.md를 참조하세요.
Related MCP server: checkyourself
"확인했는데 괜찮아" ≠ "확인할 수 없었어"
이 둘을 구분하지 못하는 검사기는 검사기가 없는 것보다 나쁩니다. 권한 오류를 초록불로 바꿔 버리기 때문입니다.
Campaign Preflight는 이 구분을 구조적으로 만듭니다. 모든 공급자 읽기는 데이터 와 데이터가 존재하거나 존재하지 않는 이유를 반환하며, 모든 규칙은 필요한 데이터를 선언합니다. 해당 데이터를 사용할 수 없으면 엔진은 규칙이 실행되기 전에 UNKNOWN으로 단락시킵니다. 규칙은 이를 거부할 수 없습니다.
상황 | 결과 |
억제 목록을 읽었고, 일치하는 항목 없음 |
|
억제 목록이 제공되지 않음 |
|
억제 엔드포인트가 403 반환 |
|
캠페인의 리드가 0개 |
|
리드 엔드포인트에 연결 불가 |
|
판정은 두 가지가 아니라 네 가지입니다: READY, READY_WITH_WARNINGS, NOT_READY, INCOMPLETE.
요구 사항
Python 3.9 이상. 이것이 전부입니다.
이 패키지는 런타임 의존성이 없습니다 — 표준 라이브러리 외에는 아무것도 import하지 않습니다. httpx는 라이브 Instantly 공급자에만 필요한 선택적 추가 기능으로, 지연 import 뒤에 있습니다.
3.9 하한선은 의도적이며, 예상보다 의도적으로 낮게 잡았습니다. 플러그인이 사용자 머신에서 만날 수 있는 가장 오래된 인터프리터이며, 의존성이 없으므로 더 높일 이유가 없습니다. CI는 Linux, macOS, Windows에서 3.9부터 3.13까지, 그리고 아무것도 설치하지 않는 순수 인터프리터 작업을 실행합니다.
이 조합 덕분에 플러그인은 설치 단계 없이 실행됩니다. 이미 있는 python3을 사용합니다.
설치
Claude 플러그인으로 (마켓플레이스)
/plugin marketplace add katekruger/campaignpreflightplugin
/plugin install campaign-preflight이 저장소는 자체 마켓플레이스입니다. .claude-plugin/marketplace.json이 플러그인 매니페스트와 함께 루트에 있습니다.
Claude 플러그인으로 (로컬 체크아웃)
git clone https://github.com/katekruger/campaignpreflightplugin/plugin marketplace add ./campaignpreflightplugin
/plugin install campaign-preflightCLI로
pipx install campaign-preflight또는 체크아웃에서 바로, 아무것도 설치하지 않고:
PYTHONPATH=src python3 -m campaign_preflight.cli demoMCP 서버로
claude mcp add campaign-preflight -- campaign-preflight-mcp읽기 전용 도구 6개. 활성화, 편집, 가져오기, 발송을 할 수 있는 것은 없습니다. Claude Code 및 Claude Desktop 설정: docs/mcp.md.
빠른 시작
campaign-preflight demoAPI 키 없음. 네트워크 없음. 구성 없음.
CAMPAIGN PREFLIGHT
Campaign: Enterprise Q3 Outbound
Provider: demo
Readiness: NOT READY
Score: 0/100
Confidence: MEDIUM
BLOCKERS
[campaign.stop_on_reply]
Stop-on-reply is disabled: repliers will keep receiving follow-ups.
Remediation: Enable stop-on-reply on the campaign.
[personalization.prompt_injection]
1 contact(s) have prompt-injection text in their personalization.
Affected: s***********a@caldera.example.com
Remediation: Remove the affected personalization and review the enrichment source it came from.
[suppression.contact_listed]
1 contact(s) appear on the active suppression list.
Affected: m**********s@stonebridge.example.com
Remediation: Remove these contacts from the campaign before activation.
WARNINGS
[contacts.missing_first_name]
2 of 20 contacts (10.0%) are missing a first name.
Affected: i**o@summitforge.example.com, r******s@clearwater.example.com
Remediation: Backfill the missing first names, or use a fallback in your copy.
UNKNOWN
[senders.aggregate_capacity]
Sender capacity is unavailable: 1 of 3 senders report no daily limit.
Affected: r***n@example.com
------------------------------------------------------------------------------
Summary:
8 blockers, 17 failures, 21 warnings, 1 unknown, 32 passed
20 leads and 3 sender(s) checked in 0.0s
Confidence is MEDIUM: 1 check(s) could not run.
Point-in-time snapshot. Campaign state may change after this check ran.마지막 발견 사항에 주목하세요. 한 발신자가 일일 한도를 보고하지 않아 총 용량을 합산할 수 없습니다. 대부분의 도구는 한도를 보고하는 발신자만 합산해 숫자라고 부르겠지만, 이 도구는 모른다고 말하며 그 때문에 신뢰도를 HIGH에서 MEDIUM으로 낮춥니다.
그 구분이 바로 이 도구의 핵심 아이디어입니다.
자신의 캠페인 확인하기
플러그인이 설치되면 일상 언어로 설명하세요:
보내기 전에 이 캠페인을 확인해 줘.
내 리드 목록이야 — 문제 있는 게 있니? (붙여넣기 또는 업로드)
200명에게 3통짜리 이메일 시퀀스를 보내려고 해, 하루 80통, 평일 오전 9시~오후 5시 동부 시간. 괜찮을까?
들어가는 방법은 세 가지이며, 어떤 것도 계정이 필요 없습니다:
가지고 있는 것 | 일어나는 일 |
파일 (업로드 또는 디스크에 있음) | 직접 검사합니다. |
붙여넣은 목록 또는 일부 카피 | 임시 파일에 기록하고, 검사한 후 정리합니다. |
설명만 있음 | 캠페인 파일을 말한 내용으로 만들고, 보여준 후 검사합니다. |
모르는 것은 추측하지 않고 비워 둡니다 — 빈 필드는 "확인할 수 없음"으로 돌아오며, 그것이 정직한 답변입니다.
파일에서, 명령줄에서
campaign-preflight check \
--campaign examples/clean_campaign/campaign.yaml \
--leads examples/clean_campaign/leads.csv \
--suppressions examples/clean_campaign/suppressions.csv판정별로 하나씩, 세 가지 실제 예제가 저장소에 포함되어 있습니다:
예제 | 판정 | 종료 코드 |
|
| |
|
| |
|
|
CI에서
campaign-preflight check --campaign campaign.yaml --leads leads.csv --fail-on blocker종료 코드가 판정을 전달하므로 파이프라인에 바로 넣을 수 있습니다. docs/ci.md를 참조하세요.
내부 구성
저장소 루트 가 플러그인입니다. 트리의 두 번째 복사본은 없습니다.
.claude-plugin/ plugin manifest and marketplace manifest
skills/ the three skills, one directory each
bin/ launchers the MCP server and CLI run through
src/ the Python package: rules, engine, providers, reporters
tests/ unit, integration, contract
docs/ rules catalogue, configuration, MCP, CI, limitations, architecture
examples/ three worked campaigns, one per verdict
scripts/ generators and the plugin packager스킬
스킬 | 용도 |
| 직접 제공한 실제 캠페인 검사 — 파일, 붙여넣기, 또는 설명. |
| 번들된 샘플 데이터로 검사기가 실행되는 모습 보기. |
| 어떤 규칙이 있는지, 각 규칙이 무엇을 테스트하는지, 재조정 또는 비활성화 방법. |
경계는 의도적입니다. 각 설명은 자신의 상황을 명시하고 이웃을 가리키므로, 근접 실패도 복구 가능한 곳에 도달합니다.
검사 항목
일곱 범주에 걸친 76개 규칙. 전체 카탈로그: docs/rules.md.
범주 | 규칙 수 | 예시 |
캠페인 | 10 | 답장 시 중지 비활성화, 일일 볼륨이 임계값 초과, 발송 시간대 없음, 발송 가능일이 남지 않는 날짜 |
연락처 | 15 | 잘못된 형식의 주소, 중복(정확 및 대소문자 무시), 역할 사서함, 자리표시자 값, 제어 및 양방향 문자, 스프레드시트 수식 주입 |
억제 | 8 | 억제 목록에 있는 연락처 및 도메인, 기존 고객, 내부 주소, 경쟁사, 제한 지역 — 그리고 억제 검사가 실행될 수 있었는지 여부 |
개인화 | 13 | 렌더링되지 않은 병합 토큰, 잘못된 사람에게 보내는 인사말, 그들의 회사가 아닌 회사, 자신의 증거로 뒷받침되지 않는 주장, 오래된 리서치, 대상 페이지에서 긁어온 프롬프트 주입 텍스트 |
카피 | 13 | 첫 단계의 빈 제목, 깨진 링크, |
일정 | 9 | 잘못된 시간대, 주말 발송, 활성 일수 0, 시작 전에 끝나는 시간대, 캠페인 기간 내 DST 전환 |
발신자 | 8 | 건강 임계값 미만의 사서함, 오류 상태, 용량을 초과하는 볼륨 — 그리고 공급자가 말해 주지 않을 때의 정직한 |
이 중 어떤 것이든 도구에 물어보세요:
campaign-preflight rules list --category suppression
campaign-preflight rules explain senders.aggregate_capacity의도적으로 검사하지 않는 것
스팸 단어 규칙은 없습니다. "무료"와 "지금 행동하세요"는 어떤 증거도 아니며, 그런 목록을 넣으면 도구를 무시하도록 훈련하게 됩니다. 판단이 필요한 규칙 — 카피 길이, 링크 수, 생성 산출물 — 은 heuristic으로 표시되고 모든 보고서에 그렇게 라벨이 붙으며, 기본적으로 차단 항목이 되지 않습니다.
구성
Campaign Preflight는 합리적인 기본값과 구성 파일 없이 실행됩니다. 임계값이 다르거나, 자체 도메인 및 지역 목록에 의존하는 검사를 켜야 할 때 구성 파일을 추가하세요.
version: 1
settings:
target_timezone: America/New_York
required_variables: [first_name, company_name]
internal_domains: [ourcompany.example.com]
customer_domains: [bigcustomer.example.com]
allow_weekend_sending: false
rules:
campaign.daily_volume:
warning_above: 100
blocker_above: 250
senders.health_below_threshold:
minimum_score: 80
contacts.missing_job_title:
enabled: falsecampaign-preflight validate-config preflight.yaml
campaign-preflight check --campaign c.yaml --leads l.csv --config preflight.yaml검증은 의도적으로 엄격합니다. 알 수 없는 규칙 ID나 알 수 없는 옵션은 경고가 아니라 하드 오류입니다. 안전 검사를 조용히 비활성화하는 오타는 구성이 없는 것보다 나쁩니다.
전체 참조: docs/configuration.md.
읽기 전용이 중요한 이유
Campaign Preflight에는 쓰기를 수행하는 코드 경로가 없습니다. "우리가 선택하지 않았다"가 아니라 — 호출할 것이 아예 없습니다.
Instantly 공급자는 모든 요청을 명시적 허용 목록에 대해
(method, path)를 검사하는 전송 계층으로 라우팅하며, 요청이 프로세스를 떠나기 전에 예외를 발생시킵니다. 검사는 클라이언트 아래, 공급자 아래에 있으므로, 나중에PATCH를 추가하는 코드 변경은 캠페인을 조용히 편집하는 대신 크게 실패합니다.import 시점에 두 개의 가드가 실행됩니다: 허용 목록에
PUT,PATCH,DELETE,HEAD,OPTIONS가 포함될 수 없고,POST는 정확히 하나의 경로(/leads/list— 필터링된 읽기에 대한 Instantly의 문서화된 형식)에만 허용됩니다.MCP 서버는 등록된 도구의 이름에 변경 동사가 있거나 읽기 전용을 선언하지 않으면 시작을 거부합니다.
tests/contract/test_instantly_transport.py는 전체 method × path 행렬과 모든 문서화된 변경 엔드포인트를 테스트합니다. 거기서의 실패는 테스트 실패가 아니라 보안 사고입니다.
이것이 에이전트에게 라이브 캠페인을 맡겨도 안전한 이유입니다. 분석은 얻고 권한은 전혀 얻지 못합니다.
절대 하지 않을 일
캠페인 활성화, 일시중지, 재개 또는 예약
리드 생성, 업데이트, 이동, 병합 또는 삭제
억제 목록에 추가 또는 제거
이메일 보내기, 답장 또는 전달
전송 플랫폼의 모든 항목 수정
이러한 작업으로 가는 코드 경로는 존재하지 않으며, 두 개의 독립적인 가드(전송 허용 목록과 MCP 시작 시 검증)는 하나라도 추가되면 안전하게 차단(fail closed)됩니다.
종료 코드
코드 | 의미 |
|
|
|
|
|
|
|
|
| 구성 또는 입력 오류 |
| 공급자 또는 인증 오류 |
| 예기치 않은 내부 오류 |
--fail-on none|warning|high|blocker는 판정이 0이 아닌 종료 코드가 되는 기준을 높입니다. 판정 자체는 절대 변경하지 않습니다. INCOMPLETE는 심각도 임계값으로 무시되지 않습니다. 검사를 실행할 수 없는 것은 낮은 심각도의 발견 사항과는 다른 문제입니다.
점수 산정은 공개되며 숨겨지지 않습니다
score = 100 - sum(weight[status][severity] for every FAIL and WARN)
readiness:
NOT_READY any BLOCKER FAIL, or any HIGH FAIL
INCOMPLETE else if any critical rule is UNKNOWN
READY_WITH_WARNINGS else if any FAIL or WARN
READY otherwise그로부터 네 가지가 따라오며, 각각 테스트가 있습니다:
차단(blocker)은 항상
NOT_READY를 생성합니다. 점수가 이를 덮어쓸 수 없습니다.UNKNOWN은 아무것도 차감하지 않습니다. 공급자 장애가 나쁜 캠페인처럼 보여서는 안 됩니다. 대신 신뢰도를 낮춥니다.NOT_APPLICABLE은 아무것도 영향을 주지 않습니다.모든 차감 항목은 개별 명시됩니다.
--verbose는 직접 확인할 수 있도록 계산 과정을 출력합니다.
가중치와 중요 규칙 목록은 구성 가능합니다: docs/configuration.md.
아키텍처
flowchart LR
CLI[CLI] --> Engine
MCP[MCP server] --> Engine
Engine -->|gather| Provider{Provider}
Provider --> CSV[CSV / files]
Provider --> Instantly[Instantly v2]
Instantly --> Guard[ReadOnlyTransport]
Guard -->|allowlist| API[(Instantly API)]
Provider -->|data + why| Context[Frozen context]
Context --> Rules[76 rules]
Rules --> Score[Scoring]
Score --> Out[Terminal / JSON / Markdown]
style Guard fill:#4a1f1f,stroke:#c04040,color:#fff컨텍스트는 고정(frozen) Pydantic 모델이므로 "규칙은 입력을 절대 변경하지 않는다"는 검토가 아닌 타입 시스템에 의해 강제됩니다. 공급자별 동작은 전적으로 공급자 인터페이스 뒤에 있습니다.
전체 설계 및 위협 모델: docs/architecture.md.
개인정보 보호
기본적으로 수정(redact)됩니다. 사서함 로컬 부분은 마스킹됩니다 (
m**********s@stonebridge.example.com). 도메인은 유지됩니다. 도메인이 있어야 억제 발견 사항이 실행 가능하기 때문입니다.비밀 정보는 무조건 삭제됩니다.
--no-redact는 PII 마스킹만 비활성화하며 자격 증명 마스킹은 절대 비활성화하지 않습니다. 공급자가 오류 본문에 API 키를 그대로 반환하더라도 보고서에 들어갈 수 없습니다. 정확히 그 상황에 대한 테스트가 있습니다.기본적으로 어떤 것도 머신 밖으로 나가지 않습니다. 선택적 LLM 주장 평가기는 구성하지 않으면 꺼져 있으며,
validate-config는 구성이 이를 켤 때 경고합니다.보고서 파일은
0600권한으로 작성되며, 임시 파일에 쓴 후 이름을 변경합니다.샘플은 제한됩니다. 100,000개 리드 캠페인이 100,000줄을 출력할 수 없습니다.
성능
작업량 | 시간 |
데모 (20개 리드) | 0.02 s |
10,000개 리드 | 0.28 s |
100,000개 리드 | 3.0 s, 약 300 MB 최대 |
행은 한 번에 모두 읽지 않고 스트리밍됩니다. 페이지네이션, 재시도, 발신자 동시성, 출력 크기는 모두 제한됩니다.
개발
git clone https://github.com/katekruger/campaignpreflightplugin
cd campaignpreflightplugin
uv sync --all-extras
uv run pytestuv run ruff format . # format
uv run ruff check . # lint
uv run mypy # typecheck, strict
claude plugin validate . --strict # manifests
uv run python scripts/generate_rules_doc.py --check # docs/rules.md is current
./scripts/bump-version.sh --check # version fields agree
uv run python scripts/build_plugin.py # dist/campaign-preflight.plugin패키지 자체에는 런타임 의존성이 없습니다. dev 그룹은 테스트 스위트, 린터, 그리고 테스트 오라클로만 사용되는 두 라이브러리(선택적 Instantly 공급자용 httpx와 번들된 YAML 파서를 차등 테스트하기 위한 PyYAML)를 위해 존재합니다.
이유를 알기 전까지는 실수처럼 보이는 규칙들은 CLAUDE.md에 문서화되어 있습니다.
로드맵
동일한 읽기 전용 인터페이스 뒤의 추가 공급자 (Smartlead, HubSpot Sequences, Apollo)
도메인 평판 및 DNS 레코드 검사 (SPF, DKIM, DMARC 정렬)
PR 주석과 함께 CLI를 감싸는 GitHub Action
기준선 비교: 두 보고서를 비교하여 마지막 실행 이후 변경된 사항 표시
세그먼트별 임계값, 하나의 구성으로 여러 모션을 처리 가능
기여
규칙은 작고 순수하며 독립적으로 테스트 가능합니다. 새 규칙은 보통 클래스 하나, docstring 하나, 그리고 몇 개의 테스트로 구성됩니다. 자세한 내용은 CONTRIBUTING.md와 CODE_OF_CONDUCT.md를 참조하세요.
보안
취약점은 비공개로 보고해 주세요: SECURITY.md. 데이터가 없을 때 PASS를 반환한 규칙은 보안 문제로 간주됩니다.
라이선스
MIT. LICENSE 참조.
Available Tools
6 toolsexplain_preflight_ruleBRead-onlyIdempotent
READ-ONLY. Explain one rule: what it checks, what data it needs, and its configurable options.
| Name | Required | Description | Default |
|---|---|---|---|
| rule_id | Yes | e.g. campaign.daily_volume |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, so the safety profile is covered by structured data. The description's 'READ-ONLY' prefix reinforces but does not add to this. It adds minimal behavioral context beyond confirming the rule-explanation output, and does not contradict 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.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single, front-loaded sentence with zero waste. The 'READ-ONLY' prefix overlaps with annotations but is harmless. Appropriately sized for a simple single-parameter tool.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a low-complexity tool (1 parameter, no output schema, no nesting), the description is reasonably complete — it states what the returned explanation covers. It partially compensates for the missing output schema by describing the explanation's contents, though it doesn't address error behavior for an invalid rule_id. Adequate given the tool's simplicity.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% — rule_id is documented with an example ('campaign.daily_volume'). The description adds no parameter-level meaning beyond implying that rule_id selects the rule to explain, which the schema already conveys. Baseline 3 is appropriate since the schema carries the parameter burden.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb ('Explain') and resource ('one rule'), and clarifies what the explanation covers (checks, data needs, configurable options). It implicitly distinguishes from siblings like list_preflight_rules and validate_preflight_config, though it does not name them explicitly. A clear, well-scoped purpose.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
No guidance is given on when to use this tool versus its siblings. The description does not state that this should be used when detailed information about a single rule is needed as opposed to list_preflight_rules for enumeration or validate_preflight_config for config checking. No exclusions or alternative routing provided.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_preflight_rulesARead-onlyIdempotent
READ-ONLY. List the preflight rule catalogue, optionally filtered by category: campaign, contacts, suppression, personalization, copy, schedule, or senders.
| Name | Required | Description | Default |
|---|---|---|---|
| category | No |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, and the description's opening 'READ-ONLY' merely reinforces that. It adds no deeper behavioral detail beyond the filter (which is more parameter-related). No mention of pagination, output format, or rate limits, but for a simple read-only list tool, the annotations carry the transparency burden sufficiently.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single sentence that front-loads the read-only nature and the core action ('List'), followed by the only parameter detail. Every word earns its place; there is no redundancy or filler. Ideal conciseness.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a tool with one optional enum parameter, no output schema, and no nested objects, the description covers the purpose, the filter, and its optionality. It does not mention return format or relationships to sibling tools, but those are not critical for a simple listing operation. The description is sufficiently complete for an agent to call it correctly.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The input schema has 0% description coverage and only one optional enum parameter. The description explicitly lists all valid category values (campaign, contacts, suppression, personalization, copy, schedule, senders) and clarifies the parameter is optional ('optionally filtered'). This fully compensates for the schema's lack of descriptions, giving the agent complete knowledge of the parameter without opening the schema.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb ('List') and resource ('preflight rule catalogue'), and mentions optional filtering. The purpose is clear and not a tautology. It does not explicitly distinguish from siblings like preflight_demo or preflight_files, but the name and description make the function obvious enough that an agent could differentiate it.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives context on the optional 'category' filter and lists valid categories, implying when filtering might be useful. However, it provides no explicit guidance on when to use this tool versus alternatives, nor any when-not-to-use statements. The presence of sibling tools like 'validate_preflight_config' suggests related actions, but no comparison is made.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
preflight_demoARead-onlyIdempotent
READ-ONLY. Run the bundled synthetic demo campaign and return its readiness report. Uses synthetic data shipped with the package: no network calls and no credentials. Useful for showing what a report looks like.
| Name | Required | Description | Default |
|---|---|---|---|
| max_samples | No | Affected records shown per finding. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already mark readOnlyHint=true, destructiveHint=false, and idempotentHint=true, so the description's 'READ-ONLY' is redundant. However, it adds value by stating no network calls and no credentials, and that it uses synthetic data shipped with the package—behavioral details not present in annotations. No contradiction.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is three short sentences, each earning its place: the first states the action and safety profile, the second gives key behavioral context, and the third explains practical utility. It is front-loaded with READ-ONLY and has no fluff.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple demo tool with one optional parameter and no required inputs, the description fully covers what the agent needs: what it does, that it's safe (read-only, no network/credentials), and when it's useful (showing a report). No output schema exists, but the description doesn't need to detail report structure for a demo. Complete for its purpose.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%—the parameter max_samples is described as 'Affected records shown per finding.' The tool description does not mention the parameter at all, but since the schema fully covers it, the baseline of 3 applies. No additional semantic value added beyond the schema.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly states the tool runs a bundled synthetic demo campaign and returns a readiness report. The word 'demo' and 'synthetic' distinguish it from siblings like preflight_files or preflight_instantly_campaign, which likely operate on real data. This is a specific verb+resource with clear differentiation.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description explicitly notes it's 'useful for showing what a report looks like,' providing a direct use case. It also hints at no network calls and no credentials, implying it's safe for testing. However, it doesn't explicitly state when to prefer this over siblings, so it lacks explicit exclusions or alternative comparisons.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
preflight_filesARead-onlyIdempotent
READ-ONLY. Check a campaign described by local files and return its readiness report. Reads only the paths given here; no directory is scanned or walked. Optional inputs that are omitted are reported as unavailable capabilities, so a run without suppressions_path says the suppression checks did not run rather than implying the list is clean.
| Name | Required | Description | Default |
|---|---|---|---|
| leads_path | Yes | Absolute or relative path to an existing file. | |
| config_path | No | Absolute or relative path to an existing file. | |
| max_samples | No | Affected records shown per finding. | |
| senders_path | No | Absolute or relative path to an existing file. | |
| campaign_path | Yes | Absolute or relative path to an existing file. | |
| evidence_path | No | Absolute or relative path to an existing file. | |
| output_format | No | Shape of the returned report. | |
| suppressions_path | No | Absolute or relative path to an existing file. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Beyond the readOnly and idempotent annotations, the description adds critical behavioral context: it explicitly states that no directory scanning occurs and that omitted optional inputs are reported as 'unavailable capabilities' rather than clean results. This clarifies how the tool handles missing parameters, which is a significant behavioral nuance beyond the annotations alone.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is three sentences with no filler. The first sentence states purpose, the second clarifies input scope, and the third explains behavior on omission. It is front-loaded with the core action and each sentence earns its place by contributing distinct, necessary information.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With 8 parameters, no output schema, and no explicit enumeration of the checks performed, the description provides sufficient context: it defines the tool's domain (local files), its safety profile, and handling of missing inputs. The output_format parameter handles return shape, and sibling tools list_preflight_rules/explain_preflight_rule can cover rule details. It is complete enough for an agent to use correctly, though slightly more detail on what 'readiness' entails would elevate it.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The schema already provides descriptions for all 8 parameters (100% coverage), so the baseline is 3. The description adds meaning by explaining the collective effect of omitting optional parameters (e.g., suppressions_path yields 'suppression checks did not run'), which is a parameter-level semantic not present in the schema. This justifies a 4 over the baseline.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific action ('Check a campaign described by local files and return its readiness report') with a clear resource (local files). It distinguishes itself from siblings by emphasizing 'local files' and the scoping rule 'Reads only the paths given here', which sets it apart from tools like preflight_demo or preflight_instantly_campaign that likely handle other sources.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description implies usage for file-based campaigns and clarifies that only explicit paths are read, but it does not explicitly contrast with sibling tools or state when to choose this over preflight_instantly_campaign or preflight_demo. The guidance is implied rather than directive, so it misses the 'when/when-not' bar for a higher score.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
preflight_instantly_campaignARead-onlyIdempotent
READ-ONLY. Inspect a live Instantly campaign and return its readiness report. Reads the campaign, its leads, its sending accounts, and the workspace block list. Every request is checked against a read-only allowlist before it leaves the process, so no write, activation, or lead-mutation call is reachable. The API key is read from the INSTANTLY_API_KEY environment variable and is never accepted as a tool argument.
| Name | Required | Description | Default |
|---|---|---|---|
| lead_limit | No | ||
| campaign_id | Yes | Instantly campaign UUID. | |
| config_path | No | Absolute or relative path to an existing file. | |
| max_samples | No | Affected records shown per finding. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, idempotentHint=true, and destructiveHint=false, but the description adds valuable context: every request is checked against a read-only allowlist, and the API key is sourced from INSTANTLY_API_KEY rather than a tool argument. This discloses operational safeguards and security details beyond the annotations, enhancing the agent's understanding of constraints.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is concise at three sentences, with purpose front-loaded ('READ-ONLY. Inspect...'). However, there is slight redundancy: 'READ-ONLY' is repeated in the allowlist explanation. Despite this, the structure is efficient and each sentence adds relevant information—purpose, scope, and security mechanism.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a tool with no output schema, the description should explain what the readiness report contains, but it only says 'readiness report' without detailing its format or contents. It does mention the data sources (leads, accounts, block list) but not the report's structure. Given the absence of output schema, this is a notable gap. The description covers the operational context well (read-only, API key), but the return value remains underspecified.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 75% (campaign_id, config_path, max_samples have descriptions; lead_limit has only min/max). The tool description does not elaborate on any parameter semantics. Per the rubric, with high schema coverage, a baseline of 3 is appropriate. The lack of compensation for the undocumented lead_limit is a minor gap, but overall the schema carries most of the parameter information.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description clearly states the tool's action and target: 'Inspect a live Instantly campaign and return its readiness report.' This is a specific verb-resource combination and explicitly distinguishes it from sibling tools (preflight_demo, preflight_files, list_preflight_rules, etc.) by the 'live Instantly campaign' scope. The mention of reading leads, sending accounts, and block list further clarifies the exact domain.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description explains the scenario (inspecting a live campaign) and the read-only nature, but does not explicitly compare with alternatives or state when not to use it. It provides clear context for when this tool is appropriate (live campaign inspection) without listing excluded cases or directing to other preflight tools.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
validate_preflight_configARead-onlyIdempotent
READ-ONLY. Validate a rules configuration file without running any checks. Reports unknown rule ids, unknown options, and out-of-range values.
| Name | Required | Description | Default |
|---|---|---|---|
| config_path | Yes | Absolute or relative path to an existing file. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already carry the safety profile (readOnlyHint=true, idempotentHint=true, destructiveHint=false), and the leading 'READ-ONLY' merely restates readOnlyHint. The added value is the description of what validation reports (unknown rule ids, unknown options, out-of-range values), which is useful but modest. No contradiction with annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two tight sentences with no filler. The critical READ-ONLY safety flag is front-loaded, and the second sentence efficiently enumerates what the validation surfaces (unknown rule ids, options, out-of-range values). Slightly redundant with annotations but well-structured and brief.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple one-parameter, read-only validation tool, this is nearly complete: purpose, scope, safety, and output dimensions are all covered. No output schema exists, but the description names the three classes of findings an agent can expect, which is sufficient for a config-validator of this simplicity.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%; the schema already documents config_path as an absolute or relative path to an existing file. The description adds only the contextual hint that the path points to a configuration file, which aligns with but does not materially extend the schema. Baseline 3 is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Describes a specific verb (validate) applied to a specific resource (rules configuration file). It distinguishes itself from sibling tools like preflight_demo, preflight_files, and preflight_instantly_campaign by explicitly stating it does not run checks, and from list_preflight_rules/explain_preflight_rule by focusing on config validation rather than rule discovery. An agent can pick it apart from siblings without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Provides a clear context: validate a configuration file before executing checks. The phrase 'without running any checks' implicitly marks off the preflight_* siblings that do execute campaigns, giving a when-not signal. It does not name alternatives explicitly or give exclusion conditions, so it falls short of a 5.
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.
6 tool updates
v0.1.0- First observed
explain_preflight_rule - First observed
list_preflight_rules - First observed
preflight_demo - First observed
preflight_files - First observed
preflight_instantly_campaign - First observed
validate_preflight_config
TDQS
Scored across 6 tools
Each tool serves a clearly distinct purpose: three preflight runners for different input sources (demo, files, live), two for rule management (list and explain), and one for config validation. There is no overlap in their operations, and the descriptions make it obvious which to select.
Names use a consistent 'preflight_' prefix across all tools, but the pattern is not fully uniform: the first three are verbs implied by the domain (e.g., 'preflight_demo' runs a demo), while the last three explicitly start with verbs ('list_', 'explain_', 'validate_'). This is a minor deviation that agents can easily adapt to.
With six tools, the server is well-scoped and avoids unnecessary bloat. Each tool covers a distinct aspect of the preflight workflow—execution sources, rule catalog, and configuration—so the count feels appropriately sized for the domain.
The surface covers the core lifecycle: running preflights on demo, files, or a live Instantly campaign; inspecting and understanding rules; and validating config files. A minor gap is the lack of a tool to run preflight on a manually specified set of parameters or a generic input, but the provided sources handle common use cases adequately.
Maintenance
Related MCP Connectors
Read audiences, groups, mailings and campaign results without sending email or changing contacts.
Render markdown into email-safe HTML, lint drafts for deliverability problems, and preview emails.
MailBeast.ai is a cold email outreach platform. This server lets AI assistants create and launch campaigns with multi-step A/B sequences, manage leads and sending mailboxes (health, warmup, limits), read and answer replies from a unified inbox, and pull campaign analytics. OAuth 2.1 sign-in with read-only or read-and-write access; an API key header is also supported. Website: https://mailbeast.ai
Evidence-readiness MCP server: validate, audit, and score briefs, memos, and evidence packs.
Related MCP Servers
- AlicenseBqualityDmaintenanceA Model Context Protocol server that provides read-only access to Mailchimp's Marketing API for comprehensive email marketing data retrieval.3885 npm12MIT
- AlicenseAqualityAmaintenanceLocal-first production-readiness MCP server for AI-built apps. It runs read-only checks, produces an evidence-based readiness score, and guides fixes before launch.1111 npm7Apache 2.0
- FlicenseNot gradedqualityCmaintenanceRead-only MCP server that performs deterministic local preflights of agent-payment boundary documents and x402 v2 PaymentRequired JSON, and prepares unsubmitted public quote-request drafts without network calls or fund movement.1-
- AlicenseAqualityAmaintenanceA read-only MCP server that reports BI pipeline readiness, blockers, and the next allowed action for governed Power BI workflows. It never writes files, executes warehouse work, or grants human approvals.610 npm2Apache 2.0