Skip to main content
Glama
Achlesha

sendhustle-mcp

Server Configuration

Describes the environment variables required to run the server.

NameRequiredDescriptionDefault
MCP_PORTNoPort for the HTTP transport when using --http (default: 3000).
SENDHUSTLE_API_KEYYesYour SendHustle API key (starts with sh_). Required for stdio mode; optional for HTTP mode (clients pass it via Bearer token).
SENDHUSTLE_BASE_URLNoAPI base URL for SendHustle (default: https://api.sendhustle.com).
SENDER_EMAIL_ADDRESSNoDefault sender email address from a verified domain (optional). If not provided, the `send_email` and `create_campaign` tools require a `from` argument on each call.
REPLY_TO_EMAIL_ADDRESSESNoComma-separated default reply-to email addresses (optional).

Instructions

Guidance the server publishes about itself, which clients place ahead of the tool catalog so the model reads it before choosing anything.

This server publishes no instructions, or was last inspected before Glama recorded them.

Capabilities

Features and capabilities supported by this server

Protocol revision2025-11-25

CapabilityDetails
tools
{
  "listChanged": false
}

Tools

Functions exposed to the LLM to take actions

NameDescription
send_emailA

Send a single email through SendHustle (POST /emails). Supports HTML and/or plain text, CC/BCC, reply-to, scheduling, attachments, tags, and custom headers. The "from" address must be on a verified domain; if omitted, the server default sender is used.

retrieve_emailA

Retrieve a sent email and its events by id (GET /emails/:id).

list_emailsA

List sent emails with cursor pagination (GET /emails).

create_domainA

Create a sender domain (POST /domains). The response includes DNS records you must add at your DNS provider before verifying.

list_domainsB

List sender domains (GET /domains).

create_audienceA

Create an audience — a named list of contacts (POST /audiences).

list_audiencesC

List audiences (GET /audiences).

create_contactA

Create a contact in a sending domain's contact pool (POST /contacts, domain-first). The same address on two domains is two records with separate consent.

list_contactsC

List a sending domain's contacts (GET /contacts?domain=..., domain-first). Optional segment_id restricts to that segment's members.

create_campaignA

Create a campaign targeting a sending domain's contact pool (POST /campaigns, domain-first). Send it later with send_campaign.

send_campaignA

Send a campaign now, or schedule it with scheduled_at (POST /campaigns/:id/send).

send_batch_emailsA

Send up to 100 emails in one request (POST /emails/batch). Pass an array of email objects, each with from/to/subject and html and/or text. Per-email "from" defaults to the configured sender if omitted.

update_emailA

Reschedule a scheduled email by setting a new send time (PATCH /emails/:id).

cancel_emailA

Cancel a scheduled email before it sends (POST /emails/:id/cancel).

list_email_attachmentsA

List a sent email's attachments (GET /emails/:id/attachments).

get_email_attachmentA

Retrieve metadata for one attachment of a sent email (GET /emails/:id/attachments/:attachmentId). Returns a download_url for the file.

list_received_emailsA

List inbound (received) emails with cursor pagination (GET /emails/receiving).

get_received_emailA

Retrieve a single received email by id (GET /emails/receiving/:id).

get_received_email_rawA

Download the original RFC822/MIME message of a received email (GET /emails/receiving/:id/raw). Returns the raw message as text.

forward_received_emailB

Forward a received email to other recipients (POST /emails/receiving/:id/forward). "from" must be a verified sending address; defaults to the configured sender.

list_received_email_attachmentsA

List a received email's attachments as metadata with download URLs (GET /emails/receiving/:id/attachments).

get_received_email_attachmentA

Retrieve metadata for one attachment of a received email, including its download_url. (GET /emails/receiving/:id/attachments/:attachmentId serves the raw bytes; this tool returns the matching metadata entry from the attachment list instead.)

delete_received_emailA

Permanently delete a received email, including its stored raw message and attachments (DELETE /emails/receiving/:id). This cannot be undone.

get_domainA

Retrieve a domain, including its DNS records and verification status (GET /domains/:id).

check_domain_mxA

MX preflight for a hostname before enabling receiving (GET /domains/mx-check). Returns { has_mx, ours, records } — whether the hostname already has MX records and whether they all point at our inbound host.

update_domainB

Update a domain's tracking/TLS/capabilities settings (PATCH /domains/:id).

verify_domainA

Trigger verification of a domain after its DNS records are in place (POST /domains/:id/verify).

delete_domainB

Delete a domain (DELETE /domains/:id).

claim_domainA

Claim a domain already verified elsewhere (POST /domains/claim). Returns a TXT record to add.

detect_domain_dnsA

Detect a domain's DNS provider and the one-click apply methods available (GET /domains/:id/dns/detect).

apply_domain_dns_cloudflareA

Apply a domain's DNS records via the Cloudflare API, then auto-verify (POST /domains/:id/dns/cloudflare). Requires a scoped Zone.DNS:Edit token.

apply_domain_dns_godaddyB

Apply a domain's DNS records via the GoDaddy API, then auto-verify (POST /domains/:id/dns/godaddy).

apply_domain_dns_namecheapA

Apply a domain's DNS records via the Namecheap API, then auto-verify (POST /domains/:id/dns/namecheap). Namecheap requires the calling server's IP to be whitelisted on the account.

get_domain_claimA

Retrieve the current claim (and its TXT verification record) for a placeholder domain (GET /domains/:id/claim).

verify_domain_claimA

Trigger DNS verification for a pending domain claim (POST /domains/:id/claim/verify).

get_audienceA

Retrieve an audience by id (GET /audiences/:id).

update_audienceB

Rename an audience (PATCH /audiences/:id).

delete_audienceA

Delete an audience and its contacts (DELETE /audiences/:id).

get_contactA

Retrieve a contact (GET /contacts/:id). A contact id is exact; an EMAIL can exist in several domains' pools, so pass domain to pick the pool.

update_contactA

Update a contact by id or email (PATCH /contacts/:id). Pass domain when addressing by EMAIL (picks the pool).

delete_contactA

Delete a contact by id or email (DELETE /contacts/:id). Pass domain when addressing by EMAIL (picks the pool).

add_contact_to_segmentA

Add a contact to a segment (POST /contacts/:id/segments/:segmentId).

list_contact_segmentsA

List the segments a contact belongs to (GET /contacts/:id/segments).

remove_contact_from_segmentA

Remove a contact from a segment (DELETE /contacts/:id/segments/:segmentId).

get_contact_topicsA

Get a contact's topic subscriptions (GET /contacts/:id/topics).

update_contact_topicsA

Update a contact's topic subscriptions (PATCH /contacts/:id/topics). Provide topics as an array of { id, subscription: 'opt_in' | 'opt_out' }.

create_contact_propertyA

Create a custom contact property / merge tag (POST /contact-properties). type is 'string' or 'number'. Idempotent on key: if a property with the same key already exists, returns that property (with already_existed: true) instead of an error.

reply_received_emailA

Reply to a received email's sender, threaded into the same conversation (POST /emails/receiving/:id/reply). from must be on a verified domain.

import_sheet_contactsA

Import contacts from a link-shared Google Sheet (POST /audiences/:id/contacts/import-sheet). Sheet headers become contact properties usable as {{merge_tags}}; rows land in a fresh segment.

import_contacts_batchA

Bulk-import contacts from a JSON array (POST /audiences/:id/contacts/batch). Upserts by email; max 10,000 per call. Each contact: { email, first_name?, last_name?, unsubscribed?, properties? }.

import_contacts_csvB

Bulk-import contacts from CSV text (POST /audiences/:id/contacts/import). Header row optional; the email column is required. Non-builtin columns auto-register as custom properties unless create_properties is false. Max 5 MB / 10,000 rows.

list_pollsC

List emails that have in-email poll responses, with per-email counts (GET /polls).

get_poll_resultsA

Get the aggregated answer breakdown for one email's poll (GET /polls/:emailId).

list_contact_propertiesC

List contact properties (GET /contact-properties).

get_contact_propertyA

Retrieve a contact property by id (GET /contact-properties/:id).

update_contact_propertyA

Update a contact property's fallback value (PATCH /contact-properties/:id). key/type are immutable.

delete_contact_propertyA

Delete a contact property (DELETE /contact-properties/:id).

create_segmentA

Create a segment on a sending domain (POST /segments, domain-first). Segment names are unique WITHIN a domain but reusable across domains. filter supports { status, email_contains, property_filters }.

list_segmentsB

List a sending domain's segments (GET /segments?domain=...). Every domain includes an auto-created "General" (all contacts) segment.

get_segmentA

Retrieve a segment by id (GET /segments/:id).

list_segment_contactsA

Preview the contacts a segment currently resolves to (GET /segments/:id/contacts).

update_segmentA

Update a segment's name or filter (PATCH /segments/:id).

delete_segmentA

Delete a segment (DELETE /segments/:id).

create_topicB

Create a subscription topic on a sending domain (POST /topics, domain-first). default_subscription is 'opt_in' or 'opt_out'; visibility is 'public' or 'private'.

list_topicsA

List a sending domain's subscription topics (GET /topics?domain=...).

get_topicA

Retrieve a topic by id (GET /topics/:id).

update_topicC

Update a topic (PATCH /topics/:id).

delete_topicA

Delete a topic (DELETE /topics/:id).

get_campaignA

Retrieve a campaign by id (GET /campaigns/:id).

get_campaign_statsB

Per-campaign analytics — counts, engagement rates, and top clicked links (GET /campaigns/:id/stats).

get_campaign_abA

A/B winner evaluation for an A/B-test campaign (GET /campaigns/:id/ab).

list_campaignsC

List campaigns (GET /campaigns).

update_campaignB

Update a draft campaign's content or targeting (PATCH /campaigns/:id).

cancel_campaignA

Cancel a scheduled campaign, returning it to draft (POST /campaigns/:id/cancel).

delete_campaignA

Delete a campaign (DELETE /campaigns/:id).

create_templateA

Create a reusable email template (POST /templates). Supports subject/html/text with {{ variables }} and optional variable definitions.

list_templatesC

List templates (GET /templates).

get_templateA

Retrieve a template by id (GET /templates/:id).

update_templateC

Update a template (PATCH /templates/:id).

duplicate_templateA

Duplicate a template (POST /templates/:id/duplicate).

publish_templateA

Publish a template, making its latest draft live (POST /templates/:id/publish).

delete_templateB

Delete a template (DELETE /templates/:id).

create_automationA

Create an automation triggered by an event (POST /automations). Every automation belongs to one sending domain — only send_event calls with the same domain trigger it. Optionally pass an inline step graph (steps + connections).

list_automationsC

List automations (GET /automations).

get_automationA

Retrieve an automation, including its step graph (GET /automations/:id).

add_automation_stepA

Append a step to an automation (POST /automations/:id/steps).

update_automation_stepA

Update a step in place (PATCH /automations/:id/steps/:stepId). The graph key stays stable, so connections keep pointing at it. Disable the automation first if it is enabled.

delete_automation_stepA

Delete a step from an automation (DELETE /automations/:id/steps/:stepId). Stop (disable) the automation first if it is enabled.

update_automationA

Update an automation's name, status, domain, or connection graph (PATCH /automations/:id). Enabling requires at least one step; editing connections or the domain requires the automation to be disabled.

list_automation_runsA

List an automation's runs (GET /automations/:id/runs). Filter with status (comma-separated: running,completed,failed,cancelled,skipped).

get_automation_runA

Retrieve a single automation run, including its step-by-step trace (GET /automations/:id/runs/:runId).

stop_automationA

Stop an automation — prevents new runs; in-progress runs finish (POST /automations/:id/stop).

delete_automationA

Delete an automation (DELETE /automations/:id).

create_webhookA

Create a webhook endpoint (POST /webhooks). The signing secret is returned ONCE on create — store it.

list_webhooksC

List webhooks (GET /webhooks).

get_webhookA

Retrieve a webhook by id (GET /webhooks/:id).

update_webhookB

Update a webhook's endpoint, events, or status (PATCH /webhooks/:id).

delete_webhookB

Delete a webhook (DELETE /webhooks/:id).

rotate_webhook_secretA

Rotate a webhook signing secret (POST /webhooks/:id/rotate). The new secret is returned ONCE; the old secret stops verifying immediately.

test_webhookA

Send a synchronous test delivery and return the endpoint's live result (POST /webhooks/:id/test).

verify_webhook_signatureA

Locally verify a webhook delivery's Svix-style signature (no API call). Provide the exact raw request body, the svix-id/svix-timestamp/svix-signature headers, and your endpoint signing secret. Returns { valid, reason? }.

list_logsC

List API request logs (GET /logs).

get_logA

Retrieve a single API log entry, including request/response bodies (GET /logs/:id).

send_eventA

Send a custom event that automations can trigger on (POST /events/send). domain is required — only automations belonging to that sending domain are triggered. Identify the contact by contact_id OR email.

create_eventA

Create a custom-event definition (POST /events). Optional flat schema (key → 'string'|'number'|'boolean'|'date') validates /events/send payloads (422 on mismatch).

list_eventsB

List custom-event definitions (GET /events).

update_eventA

Update a custom-event definition's payload schema (PATCH /events/:id). The event NAME is immutable (renaming would detach automations that reference it) — create a new event to rename. Pass schema as a flat key→type map, or null to clear it.

delete_eventA

Delete a custom-event definition (DELETE /events/:id). Existing automations keep their trigger names; this only removes the definition + its payload validation.

create_api_keyA

Create an API key (POST /api-keys). The token is returned ONCE. permission is 'full_access' or 'sending_access'.

list_api_keysA

List API keys (GET /api-keys).

delete_api_keyA

Delete (revoke) an API key (DELETE /api-keys/:id).

Prompts

Interactive templates invoked by user choice

NameDescription

No prompts

Resources

Contextual data attached and managed by the client

NameDescription

No resources

TDQS

B3.3/5.0

Scored across 111 tools

Disambiguation4/5

Almost every tool maps to a distinct resource+action, and the descriptions are specific. A few pairs could be confused—create_event (definition) vs send_event, and get_email_attachment vs get_received_email_attachment—but the names plus descriptions largely disambiguate them.

Naming Consistency4/5

Tools overwhelmingly follow a snake_case verb_noun pattern (create_domain, list_contacts, update_campaign). Minor inconsistency: retrieve_email instead of get_email, and several synonyms for similar actions (stop/cancel/delete, verify/check) slightly soften the pattern.

Tool Count1/5

111 tools is an extreme count; even if each maps to a distinct endpoint, the set is far beyond the well-scoped range and will burden an agent's selection. This aligns with the 50+ overgrown category.

Completeness5/5

The surface covers full lifecycles for domains, audiences, contacts, properties, segments, topics, templates, campaigns, sent/received emails, automations, events, webhooks, API keys, logs, and polls. There are no obvious dead ends or missing CRUD operations for the apparent email-platform domain.

Maintenance

ActivityMaintained
ResponsivenessNo issues