Skip to main content
Glama
facebook-mcp

facebook-mcp

by IvanBBaev

Send message

facebook_send_message
Destructive

Send one private Messenger reply to a person as your Page within the 24-hour messaging window, with a dry-run preview by default and support for a single attachment.

Instructions

Send ONE PRIVATE Messenger message as the Page — text, or one attachment (image / audio / video / file by public HTTPS URL or reusable attachment_id) — as a reply inside the 24-hour standard messaging window (messaging_type=RESPONSE). This is not a public comment reply — use the moderation tools for that. Dry run by default: it returns a preview and sends nothing unless apply:true. Pass conversation_id so the messaging window and the recipient can be verified before sending. If the send outcome is ever ambiguous the message may ALREADY have been delivered — verify with facebook_get_conversation instead of resending. Pass reply_to_message_id to quote one message of the thread. No message tags are supported: Outside the 24-hour standard messaging window a plain RESPONSE message is rejected by Facebook: a message tag would be required. Every message tag now hard-fails except HUMAN_AGENT, which needs a separate App Review approval and is NOT supported by this server — so there is no tag this tool can send. Options: (1) wait until the person messages the Page again, which reopens the window; (2) if they commented in the last 7 days, reply privately with facebook_private_reply; (3) answer publicly on the post. Never resend blindly.

Input Schema

NameRequiredDescriptionDefault
applyNoSet true to actually perform the write. Omitted or false ⇒ the server decides from its configured write mode: usually a dry run that returns a plan preview and changes nothing, but a server (or package) configured apply-first performs the write. To be certain nothing happens, read the result: a dry run always reports the plan and says the write was NOT performed.
messageNoThe message text (1–2000 characters). Sent verbatim to a real person; there is no unsend. Exactly one of message / saved_reply_id.
plan_idNoThe `planId` returned by a preceding dry-run preview of this same tool. Required for irreversible and spend-tier writes; plans expire a few minutes after they are created.
profileNoPage profile key (e.g. "brand-a") or a raw Page ID. Omitted ⇒ the default Page (FB_PAGE_ID).
attachmentNoONE attachment instead of text: exactly one of url / attachment_id. A message carries text or one attachment, never both.
recipient_idNoThe recipient's page-scoped ID (PSID). Optional when conversation_id is given (it is derived from the thread); required otherwise, and then the messaging window cannot be verified client-side.
saved_reply_idNoId of a saved reply (facebook_list_saved_replies) to send instead of `message`. Its text is resolved now and bound to the plan, so editing the template after the preview makes the apply diverge.
conversation_idNoConversation id from facebook_list_conversations. Strongly preferred: it identifies the recipient and lets the 24-hour window be checked before the send.
reply_to_message_idNoMessage id (mid, from facebook_get_conversation) this reply quotes. Must belong to the same conversation. Optional.

Schema Changelog

Changes observed during successful MCP inspections.

  1. Changed6 schema fields changedv0.8.0
    • addedInput schema / properties / attachment
      Added value: +{
      +  "additionalProperties": false,
      +  "description": "ONE attachment instead of text: exactly one of url / attachment_id. A message carries text or one attachment, never both.",
      +  "properties": {
      +    "attachment_id": {
      +      "description": "A reusable attachment id from facebook_upload_message_attachment (valid for about 90 days, this Page only).",
      +      "pattern": "^\\d{1,32}$",
      +      "type": "string"
      +    },
      +    "type": {
      +      "description": "Attachment kind: image, audio, video or file (for example a PDF).",
      +      "enum": [
      +        "image",
      +        "audio",
      +        "video",
      +        "file"
      +      ],
      +      "type": "string"
      +    },
      +    "url": {
      +      "description": "A public https:// URL Meta fetches itself (no credentials in it). Meta gives up after about 10 s (75 s for video); images up to 8 MB, other files up to 25 MB.",
      +      "format": "uri",
      +      "maxLength": 2048,
      +      "type": "string"
      +    }
      +  },
      +  "required": [
      +    "type"
      +  ],
      +  "type": "object"
      +}
    • addedInput schema / properties / conversation_id / pattern
      Added value: +"^(?=.*\\w)[\\w.-]+$"
    • changedInput schema / properties / message / description
      Previous value: -"The message text (1–2000 characters). Sent verbatim to a real person; there is no unsend."New value: +"The message text (1–2000 characters). Sent verbatim to a real person; there is no unsend. Exactly one of message / saved_reply_id."
    • addedInput schema / properties / reply_to_message_id
      Added value: +{
      +  "description": "Message id (mid, from facebook_get_conversation) this reply quotes. Must belong to the same conversation. Optional.",
      +  "maxLength": 200,
      +  "pattern": "^[\\w.:\\-+=/]+$",
      +  "type": "string"
      +}
    • addedInput schema / properties / saved_reply_id
      Added value: +{
      +  "description": "Id of a saved reply (facebook_list_saved_replies) to send instead of `message`. Its text is resolved now and bound to the plan, so editing the template after the preview makes the apply diverge.",
      +  "pattern": "^[a-z0-9][a-z0-9-]{0,47}$",
      +  "type": "string"
      +}
    • removedInput schema / required
      Removed value: -[
      -  "message"
      -]
  2. First observedv0.7.0

TDQS

A4.8/5.0
Behavior5/5

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

Annotations declare destructive/openWorld/non-idempotent, and the description adds materially beyond them: dry-run-by-default with apply:true, the hard failure of every message tag except HUMAN_AGENT (unsupported here), Meta-side rejection outside the window, and the risk that an ambiguous outcome means the message was already delivered. That is exactly the context an agent needs before a non-idempotent write.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loads the core action and scope in the first sentence, then layers constraints and fallbacks. The final enumerated options passage is verbose and slightly repetitive, but each clause carries operational information rather than filler.

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

Completeness5/5

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

For a nullable-parameter, nested-object, irreversible write with no output schema, the description supplies the safety profile, window semantics, tag limitations, and recovery path. Nothing needed to invoke it correctly is missing.

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?

Schema coverage is 100%, so the baseline is 3; the description still adds decision-relevant meaning by explaining why conversation_id is strongly preferred (window and recipient verification) and what reply_to_message_id does (quote one message in the same thread). It does not restate attachment size limits or plan_id semantics, which the schema already covers.

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?

States a specific verb and resource with scope: sending ONE private Messenger message as the Page, including supported payloads (text or one attachment). It explicitly separates itself from sibling tools, noting it is 'not a public comment reply — use the moderation tools for that' and later naming facebook_private_reply.

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

Usage Guidelines5/5

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

Names the exact precondition (the 24-hour standard messaging window) and enumerates three concrete alternatives when that precondition fails: wait, use facebook_private_reply, or answer publicly. It also instructs verifying ambiguous outcomes with facebook_get_conversation rather than resending.

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