🔀

AI Social Media Automation

Medium6 tools

Automated social media content creation, scheduling, and publishing across platforms.

ClaudeDALL-E 3Twitter API v2LinkedIn APIInstagram Graph APIBuffer API

Workflow Steps

  1. 1

    Content Source Processor extracts key points from blog posts or videos

  2. 2

    Platform Content Generator creates platform-optimized posts

  3. 3

    Visual Generator creates engaging images and graphics

  4. 4

    Scheduling Agent determines optimal posting times

  5. 5

    Publisher Agent schedules and publishes to all platforms

Download

Documentation

AI Social Media Automation

Overview

A comprehensive workflow for automating social media content creation, scheduling, and publishing across multiple platforms. This pipeline generates platform-optimized content from a single source (blog post, video, or idea), creates engaging visuals, writes captions, and schedules posts — enabling consistent social media presence with minimal manual effort.

The workflow supports Twitter/X, LinkedIn, Instagram, Threads, and Facebook, automatically adapting content format and style for each platform's audience and best practices.

Difficulty

Medium — Requires API access to social platforms and content generation tools.

Tools Required

ToolPurpose
Claude / GPT-4Content writing and adaptation
DALL-E 3 / MidjourneyVisual content generation
Buffer / Hootsuite APIScheduling and publishing
Twitter API v2Direct posting to X
LinkedIn APIDirect posting to LinkedIn
Instagram Graph APIDirect posting to Instagram

Workflow Steps

Step 1: Content Source Processing

import anthropic
import requests

client = anthropic.Anthropic()

def process_content_source(source_type: str, source_url: str) -> dict:
    """Extract and summarize content from various sources."""
    
    if source_type == "blog":
        # Fetch blog post
        response = requests.get(source_url)
        content = response.text
        
        # Extract key points
        summary = client.messages.create(
            model="claude-3-5-sonnet-latest",
            max_tokens=1000,
            messages=[{
                "role": "user",
                "content": f"""Extract the key points from this blog post:

{content[:5000]}

Return a JSON object with:
- title: catchy headline
- key_points: list of 5-7 main takeaways
- hook: attention-grabbing opening line
- call_to_action: what should readers do next
- target_audience: who would find this valuable"""
            }]
        )
        
        return parse_json(summary.content[0].text)
    
    elif source_type == "video":
        # Use video transcript or description
        transcript = get_video_transcript(source_url)
        summary = client.messages.create(
            model="claude-3-5-sonnet-latest",
            max_tokens=1000,
            messages=[{
                "role": "user",
                "content": f"""Create social media content from this video transcript:

{transcript[:3000]}

Return JSON with: title, key_points, hook, call_to_action, target_audience"""
            }]
        )
        return parse_json(summary.content[0].text)
    
    elif source_type == "idea":
        # Generate from a simple idea
        summary = client.messages.create(
            model="claude-3-5-sonnet-latest",
            max_tokens=1000,
            messages=[{
                "role": "user",
                "content": f"""Expand this idea into social media content:

Idea: {source_url}

Return JSON with: title, key_points, hook, call_to_action, target_audience"""
            }]
        )
        return parse_json(summary.content[0].text)

def parse_json(text: str) -> dict:
    """Parse JSON from AI response."""
    import json
    # Extract JSON block
    start = text.find("{")
    end = text.rfind("}") + 1
    return json.loads(text[start:end])

Step 2: Platform-Specific Content Generation

def generate_platform_content(content: dict, platform: str) -> dict:
    """Generate platform-optimized content from source material."""
    
    platform_configs = {
        "twitter": {
            "max_length": 280,
            "style": "punchy, conversational, use threads for longer content",
            "hashtag_count": 2,
            "visual_style": "quote cards, infographics"
        },
        "linkedin": {
            "max_length": 3000,
            "style": "professional, thought leadership, storytelling",
            "hashtag_count": 3,
            "visual_style": "professional images, carousels"
        },
        "instagram": {
            "max_length": 2200,
            "style": "visual-first, engaging, personal",
            "hashtag_count": 10,
            "visual_style": "high-quality photos, reels, carousels"
        },
        "threads": {
            "max_length": 500,
            "style": "casual, conversational, engaging",
            "hashtag_count": 2,
            "visual_style": "simple images, memes"
        }
    }
    
    config = platform_configs[platform]
    
    response = client.messages.create(
        model="claude-3-5-sonnet-latest",
        max_tokens=1500,
        messages=[{
            "role": "user",
            "content": f"""Create social media content for {platform} based on:

Title: {content['title']}
Key Points: {content['key_points']}
Hook: {content['hook']}
Call to Action: {content['call_to_action']}

Platform requirements:
- Max length: {config['max_length']} characters
- Style: {config['style']}
- Hashtags: {config['hashtag_count']} relevant hashtags
- Visual suggestion: {config['visual_style']}

Return JSON with:
- caption: the post text (within character limit)
- hashtags: list of hashtags
- visual_prompt: description for generating the visual
- posting_time: recommended time to post (considering timezone)"""
        }]
    )
    
    return parse_json(response.content[0].text)

Step 3: Visual Generation

def generate_visual(prompt: str, platform: str) -> str:
    """Generate visual content for the post."""
    
    # Adapt prompt for platform
    visual_styles = {
        "twitter": "minimalist quote card, clean typography, brand colors",
        "linkedin": "professional business illustration, clean and modern",
        "instagram": "aesthetic, vibrant, Instagram-worthy design",
        "threads": "fun, casual, engaging visual"
    }
    
    full_prompt = f"{prompt}. Style: {visual_styles[platform]}, 1200x628 pixels"
    
    # Using DALL-E 3
    response = requests.post(
        "https://api.openai.com/v1/images/generations",
        headers={"Authorization": f"Bearer {OPENAI_API_KEY}"},
        json={
            "model": "dall-e-3",
            "prompt": full_prompt,
            "n": 1,
            "size": "1792x1024"
        }
    )
    
    image_url = response.json()["data"][0]["url"]
    return image_url

Step 4: Scheduling and Publishing

def schedule_post(platform: str, content: dict, image_url: str, schedule_time: str):
    """Schedule or publish post to platform."""
    
    if platform == "twitter":
        return post_to_twitter(content, image_url, schedule_time)
    elif platform == "linkedin":
        return post_to_linkedin(content, image_url, schedule_time)
    elif platform == "instagram":
        return post_to_instagram(content, image_url, schedule_time)
    elif platform == "threads":
        return post_to_threads(content, image_url, schedule_time)

def post_to_twitter(content: dict, image_url: str, schedule_time: str) -> str:
    """Post to Twitter/X using API v2."""
    
    # Download image
    image_data = requests.get(image_url).content
    image_id = upload_media(image_data)
    
    # Create tweet
    response = requests.post(
        "https://api.twitter.com/2/tweets",
        headers={
            "Authorization": f"Bearer {TWITTER_BEARER_TOKEN}",
            "Content-Type": "application/json"
        },
        json={
            "text": content["caption"],
            "media": {"media_ids": [image_id]}
        }
    )
    
    return response.json()["data"]["id"]

def post_to_linkedin(content: dict, image_url: str, schedule_time: str) -> str:
    """Post to LinkedIn using API."""
    
    # Upload image to LinkedIn
    upload_response = requests.post(
        "https://api.linkedin.com/v2/assets",
        headers={"Authorization": f"Bearer {LINKEDIN_TOKEN}"},
        json={
            "registerUploadRequest": {
                "recipes": ["urn:li:digitalmediaRecipe:feedshare-image"],
                "owner": "urn:li:person:YOUR_PERSON_URN",
                "serviceRelationships": [{
                    "relationshipType": "OWNER",
                    "identifier": "urn:li:generationJob:YOUR_GENERATION_JOB"
                }]
            }
        }
    )
    
    # Create post
    response = requests.post(
        "https://api.linkedin.com/v2/ugcPosts",
        headers={"Authorization": f"Bearer {LINKEDIN_TOKEN}"},
        json={
            "author": "urn:li:person:YOUR_PERSON_URN",
            "lifecycleState": "PUBLISHED",
            "specificContent": {
                "com.linkedin.ugc.ShareContent": {
                    "shareCommentary": {
                        "text": content["caption"]
                    },
                    "shareMediaCategory": "IMAGE",
                    "media": [{
                        "status": "READY",
                        "description": {"text": content["caption"][:900]},
                        "originalUrl": image_url,
                        "title": {"text": content.get("title", "")}
                    }]
                }
            },
            "visibility": {"memberships": ["PUBLIC"]}
        }
    )
    
    return response.json()["id"]

Step 5: Content Calendar Management

def create_content_calendar(content_sources: list, platforms: list, frequency: str) -> list[dict]:
    """Generate a content calendar for the week/month."""
    
    calendar = []
    
    for source in content_sources:
        content = process_content_source(source["type"], source["url"])
        
        for platform in platforms:
            platform_content = generate_platform_content(content, platform)
            
            calendar.append({
                "source": source,
                "platform": platform,
                "content": platform_content,
                "scheduled_for": calculate_post_time(frequency),
                "status": "pending"
            })
    
    return calendar

def calculate_post_time(frequency: str) -> str:
    """Calculate optimal posting time."""
    from datetime import datetime, timedelta
    
    # Best times by platform (simplified)
    best_times = {
        "twitter": ["9:00", "12:00", "15:00", "18:00"],
        "linkedin": ["8:00", "10:00", "12:00"],
        "instagram": ["11:00", "14:00", "19:00"],
        "threads": ["10:00", "13:00", "20:00"]
    }
    
    # Return next optimal time
    now = datetime.now()
    for hour in best_times[frequency]:
        candidate = now.replace(hour=int(hour.split(":")[0]), minute=int(hour.split(":")[1]))
        if candidate > now:
            return candidate.isoformat()
    
    return (now + timedelta(days=1)).isoformat()

Example Usage

def automate_social_media(blog_url: str, platforms: list = ["twitter", "linkedin", "instagram"]):
    # Step 1: Process content source
    content = process_content_source("blog", blog_url)
    print(f"Processed: {content['title']}")
    
    # Step 2: Generate platform-specific content
    all_posts = []
    for platform in platforms:
        platform_content = generate_platform_content(content, platform)
        all_posts.append({
            "platform": platform,
            "content": platform_content
        })
        print(f"Generated {platform} post: {platform_content['caption'][:100]}...")
    
    # Step 3: Generate visuals
    for post in all_posts:
        visual_url = generate_visual(
            post["content"]["visual_prompt"],
            post["platform"]
        )
        post["visual_url"] = visual_url
        print(f"Generated visual for {post['platform']}")
    
    # Step 4: Schedule posts
    for post in all_posts:
        post_id = schedule_post(
            post["platform"],
            post["content"],
            post["visual_url"],
            post["content"]["posting_time"]
        )
        post["post_id"] = post_id
        print(f"Scheduled {post['platform']} post: {post_id}")
    
    return all_posts

# Run it
posts = automate_social_media(
    "https://myblog.com/ai-agents-2026",
    platforms=["twitter", "linkedin", "instagram", "threads"]
)

Pros

  • ✅ Consistent social media presence across platforms
  • ✅ Platform-optimized content for each audience
  • ✅ Significant time savings (hours → minutes)
  • ✅ Data-driven posting times
  • ✅ Visual content included
  • ✅ Scalable for multiple accounts

Cons

  • ❌ AI-generated content may lack authenticity
  • ❌ Visual quality varies
  • ❌ API rate limits on social platforms
  • ❌ Requires API access (some platforms restrictive)
  • ❌ No real-time engagement handling
  • ❌ Platform algorithm changes affect reach

When to Use

  • Consistent posting schedule — Maintain regular presence
  • Content repurposing — One source, multiple platforms
  • Multi-platform management — Handle several accounts
  • Time-constrained creators — Limited manual effort
  • B2B marketing — LinkedIn-focused thought leadership
  • Product launches — Coordinated multi-platform campaigns

Resources