publish_twitter_post
Publish text posts to Twitter by specifying the tweet content. Automate your social media updates.
Instructions
Publish a text post (tweet) to Twitter.
Input Schema
| Name | Required | Description | Default |
|---|---|---|---|
| post_text | Yes | The text content of the tweet (maximum 280 characters). |
Implementation Reference
- cli.js:354-442 (handler)The handler for the 'publish_twitter_post' tool. Extracts the API key from env, validates the 'post_text' argument, sends a POST request to the backend Twitter API (https://ligosocial.com/api/mcp/publish-twitter-post), and returns success/failure responses.
} else if (name === 'publish_twitter_post') { console.error(`${packageName}: Received call for publish_twitter_post tool.`); const apiKey = process.env.LINKEDIN_MCP_API_KEY; const postText = args?.post_text; if (!apiKey) { sendResponse({ jsonrpc: "2.0", error: { code: -32001, message: "Server Configuration Error: API Key not set." }, id }); return; } if (typeof postText !== 'string' || postText.trim() === '') { sendResponse({ jsonrpc: "2.0", error: { code: -32602, message: "Invalid arguments: 'post_text' (string) required." }, id }); return; } try { const headers = { "Authorization": `Bearer ${apiKey}`, "Content-Type": "application/json", "Accept": "application/json" }; const payload = { "post_text": postText }; console.error(`${packageName}: Calling Twitter API: ${backendTwitterApiUrl} with payload:`, JSON.stringify(payload, null, 2)); const apiResponse = await axios.post(backendTwitterApiUrl, payload, { headers, timeout: 60000 }); console.error(`${packageName}: Twitter API response status: ${apiResponse.status}`); console.error(`${packageName}: Twitter API response data:`, JSON.stringify(apiResponse.data, null, 2)); if (apiResponse.data && apiResponse.data.success) { // Include tweet_id from backend if available const tweetDetails = apiResponse.data.tweet_id ? ` (Tweet ID: ${apiResponse.data.tweet_id})` : ''; sendResponse({ jsonrpc: "2.0", result: { content: [ { type: "text", text: `✅ Successfully published tweet to Twitter${tweetDetails}.` } ], isError: false }, id }); } else { const errorMessage = apiResponse.data?.error || "Backend API Error (no detail)"; console.error(`${packageName}: Twitter API Error: ${errorMessage}`); // Report error within the result object sendResponse({ jsonrpc: "2.0", result: { content: [ { type: "text", text: `Failed to publish tweet to Twitter: ${errorMessage}` } ], isError: true }, id }); } } catch (error) { let errorMessage = `Failed to call Twitter API: ${error.message}`; // Determine a user-facing error message based on the error type if (error.response) { // Extract the error message directly from the backend response const backendError = error.response.data?.error || error.response.data?.message; errorMessage = backendError || `Twitter API Error (Status ${error.response.status})`; console.error(`${packageName}: Twitter API Error Response:`, error.response.data); } else if (error.request) { errorMessage = "No response received from Twitter API."; } console.error(`${packageName}: ${errorMessage}`); // Report error within the result object sendResponse({ jsonrpc: "2.0", result: { content: [ { type: "text", text: `Failed to publish tweet to Twitter: ${errorMessage}` } ], isError: true }, id }); } - cli.js:1276-1288 (schema)Schema/tool definition for 'publish_twitter_post' returned in the 'tools/list' response. Defines the name, description, and input schema (requiring a 'post_text' string).
name: "publish_twitter_post", description: "Publish a text post (tweet) to Twitter.", inputSchema: { type: "object", properties: { post_text: { type: "string", description: "The text content of the tweet (maximum 280 characters)." } }, required: ["post_text"] } }, - cli.js:1200-1392 (registration)Registration of 'publish_twitter_post' via the MCP 'tools/list' response. The tool is listed among the available tools.
if (method === 'tools/list') { console.error(`${packageName}: Received tools/list request, sending known tool.`); sendResponse({ jsonrpc: "2.0", id: id, result: { tools: [ { name: "publish_linkedin_post", description: "Publish a text post to LinkedIn, optionally including media (images/videos) specified by URL.", inputSchema: { type: "object", properties: { post_text: { type: "string", description: "The text content of the LinkedIn post." }, media: { type: "array", description: "Optional. A list of media items to attach to the post. Each item must have a 'file_url' pointing to a direct image or video URL and a 'filename'.", items: { type: "object", properties: { file_url: { type: "string", description: "A direct URL to the image or video file (e.g., ending in .jpg, .png, .mp4)." }, filename: { type: "string", description: "A filename for the media item (e.g., 'promo_video.mp4')." } }, required: ["file_url", "filename"] } } }, required: ["post_text"] } }, { name: "schedule_linkedin_post", description: "Schedule a text post for LinkedIn at a specific future date and time, optionally including media (images/videos) specified by URL.", inputSchema: { type: "object", properties: { post_text: { type: "string", description: "The text content of the LinkedIn post to be scheduled." }, scheduled_date: { type: "string", description: "The date and time to publish the post, in ISO 8601 format (e.g., '2025-12-31T10:00:00Z' or '2025-12-31T15:30:00+05:30'). Must be in the future." }, media: { type: "array", description: "Optional. A list of media items to attach to the post. Each item must have a 'file_url' pointing to a direct image or video URL and a 'filename'.", items: { type: "object", properties: { file_url: { type: "string", description: "A direct URL to the image or video file (e.g., ending in .jpg, .png, .mp4)." }, filename: { type: "string", description: "A filename for the media item (e.g., 'meeting_notes.mp4')." } }, required: ["file_url", "filename"] } } }, required: ["post_text", "scheduled_date"] } }, { name: "publish_twitter_post", description: "Publish a text post (tweet) to Twitter.", inputSchema: { type: "object", properties: { post_text: { type: "string", description: "The text content of the tweet (maximum 280 characters)." } }, required: ["post_text"] } }, { name: "analyze_linkedin_chat", description: "Ask questions about the user's LinkedIn profile, content, or network, with support for multi-turn conversations.", inputSchema: { type: "object", properties: { query: { type: "string", description: "The question or request about LinkedIn data to be analyzed." }, conversation_history: { type: "array", description: "Optional. Previous messages in the conversation for context. Each message must have 'role' (user/assistant) and 'content' (text).", items: { type: "object", properties: { role: { type: "string", description: "The sender of the message: 'user' or 'assistant'." }, content: { type: "string", description: "The text content of the message." } }, required: ["role", "content"] } } }, required: ["query"] } }, { name: "generate_linkedin_post", description: "Generate three LinkedIn post variants from any content (article, newsletter, notes, etc.) to optimize engagement.", inputSchema: { type: "object", properties: { content: { type: "string", description: "The source content to transform into LinkedIn posts. Can be articles, emails, newsletters, notes, etc." }, content_type: { type: "string", description: "Optional. A short description of the content type (e.g., 'article', 'newsletter', 'notes'). Defaults to 'article'." } }, required: ["content"] } }, { name: "get_linkedin_posts", description: "Retrieve the user's recent LinkedIn posts with engagement metrics.", inputSchema: { type: "object", properties: { limit: { type: "number", description: "Optional. Number of posts to retrieve (1-20). Defaults to 5." } } } }, { name: "get_linkedin_profile", description: "Retrieve the user's LinkedIn profile information including headline, summary, experience, and education.", inputSchema: { type: "object", properties: {} } }, { name: "set_linkedin_url", description: "Set or update the LinkedIn profile URL to analyze. Required before using profile/posts retrieval tools if not set previously.", inputSchema: { type: "object", properties: { linkedin_url: { type: "string", description: "The full LinkedIn profile URL (e.g., https://www.linkedin.com/in/username/)" } }, required: ["linkedin_url"] } }, { name: "refresh_linkedin_profile", description: "Force a refresh of the LinkedIn profile data to update any recent changes.", inputSchema: { type: "object", properties: {} } }, { name: "refresh_linkedin_posts", description: "Force a refresh of LinkedIn posts data to capture recently published content.", inputSchema: { type: "object", properties: {} } } ] } });