# LinkedIn API Setup Guide

This guide provides step-by-step instructions for setting up LinkedIn API integration for the Social Media Management System.

---

## Table of Contents

1. [Overview](#overview)
2. [Prerequisites](#prerequisites)
3. [LinkedIn Developer Portal Setup](#linkedin-developer-portal-setup)
4. [Environment Configuration](#environment-configuration)
5. [OAuth Redirect URI Configuration](#oauth-redirect-uri-configuration)
6. [Permissions & Scopes](#permissions--scopes)
7. [Webhook Configuration (Optional)](#webhook-configuration-optional)
8. [Development vs Production](#development-vs-production)
9. [Troubleshooting](#troubleshooting)

---

## Overview

**API Version:** RestLi 2.0 (Version 202411)
**Base URL:** `https://api.linkedin.com/rest`
**Auth URL:** `https://www.linkedin.com/oauth/v2/authorization`
**Token URL:** `https://www.linkedin.com/oauth/v2/accessToken`

### Features Supported
- Fetch organization posts
- Read and manage comments on organization posts
- Reply to comments as the organization
- Webhook support for real-time comment notifications

---

## Prerequisites

- A LinkedIn account with admin access to a LinkedIn Company/Organization Page
- Access to [LinkedIn Developer Portal](https://www.linkedin.com/developers/)
- HTTPS-enabled server for production (required for redirect URIs)

---

## LinkedIn Developer Portal Setup

### Step 1: Create a New App

1. Navigate to [LinkedIn Developer Portal](https://www.linkedin.com/developers/)
2. Click **"Create App"**
3. Fill in the required details:
   - **App Name:** Your application name (e.g., "PX360 Social Manager")
   - **LinkedIn Page:** Select your company/organization page
   - **Privacy Policy URL:** Your privacy policy URL
   - **App Logo:** Upload your app logo (required for review)
4. Click **"Create App"**

### Step 2: Request API Products

1. In your app dashboard, go to **"Products"** tab
2. Request access to the following products:
   - **Marketing API** (for posts and comments management)
   - **Share on LinkedIn** (for posting content)
   - **Sign In with LinkedIn** (optional, for user authentication)

3. Some products require LinkedIn approval. Submit a detailed use case explaining:
   > "We are building a Social Media Management Tool that allows organizations to manage and respond to comments on their LinkedIn posts from a centralized dashboard. This helps community managers respond faster and maintain engagement with their audience."

### Step 3: Get Credentials

1. Go to **"Auth"** tab in your app dashboard
2. Copy the following values:
   - **Client ID** → This is your `LINKEDIN_CLIENT_ID`
   - **Client Secret** → Click "Show" to reveal → This is your `LINKEDIN_CLIENT_SECRET`

---

## Environment Configuration

Add the following to your `settings.py` or `.env` file:

### Django Settings (settings.py)

```python
# LinkedIn API Configuration
LINKEDIN_CLIENT_ID = 'your_client_id_here'
LINKEDIN_CLIENT_SECRET = 'your_client_secret_here'
LINKEDIN_REDIRECT_URI = 'https://yourdomain.com/social/callback/LI/'
LINKEDIN_WEBHOOK_VERIFY_TOKEN = 'your_random_secret_string_123'
```

### Environment Variables (.env)

```env
LINKEDIN_CLIENT_ID=your_client_id_here
LINKEDIN_CLIENT_SECRET=your_client_secret_here
LINKEDIN_REDIRECT_URI=https://yourdomain.com/social/callback/LI/
LINKEDIN_WEBHOOK_VERIFY_TOKEN=your_random_secret_string_123
```

---

## OAuth Redirect URI Configuration

### Step 1: Add Redirect URI in LinkedIn App

1. Go to **"Auth"** tab → **"OAuth 2.0 settings"**
2. Click **"Add redirect URL"**
3. Add your callback URL:

**Development:**
```
http://127.0.0.1:8000/social/callback/LI/
http://localhost:8000/social/callback/LI/
```

**Production:**
```
https://yourdomain.com/social/callback/LI/
```

> ⚠️ **Important:** LinkedIn only accepts HTTPS URLs in production. For local development, `http://127.0.0.1` or `http://localhost` is allowed.

---

## Permissions & Scopes

The application requests the following OAuth scopes:

| Scope | Description | Required |
|-------|-------------|----------|
| `r_organization_social` | Read organization posts and comments | ✅ Yes |
| `w_organization_social` | Post content and reply to comments as organization | ✅ Yes |
| `rw_organization_admin` | Manage organization account settings | ✅ Yes |

### Code Reference

```python
# apps/social/utils/linkedin.py
SCOPES = [
    "r_organization_social",
    "w_organization_social",
    "rw_organization_admin"
]
```

---

## Webhook Configuration (Optional)

Webhooks allow real-time notifications when new comments are posted.

### Step 1: Create Webhook Endpoint

Your application should have an endpoint to receive LinkedIn webhooks:

```
POST /social/webhooks/linkedin/
```

### Step 2: Register Webhook

1. In LinkedIn Developer Portal, go to **"Products"** → **"Marketing API"**
2. Configure webhook subscriptions for:
   - `socialActions` (comments and reactions)

### Step 3: Verify Webhook

LinkedIn sends a verification request with a challenge. Your server must respond with the challenge:

```python
# Webhook verification handler
def verify_webhook(request):
    challenge = request.GET.get('challenge')
    verify_token = request.GET.get('verifyToken')
    
    if verify_token == settings.LINKEDIN_WEBHOOK_VERIFY_TOKEN:
        return HttpResponse(challenge, status=200)
    return HttpResponse(status=403)
```

---

## Development vs Production

### Development Setup

| Setting | Value |
|---------|-------|
| `LINKEDIN_REDIRECT_URI` | `http://127.0.0.1:8000/social/callback/LI/` |
| Protocol | HTTP allowed |
| App Review | Not required for testing |

### Production Setup

| Setting | Value |
|---------|-------|
| `LINKEDIN_REDIRECT_URI` | `https://yourdomain.com/social/callback/LI/` |
| Protocol | **HTTPS required** |
| App Review | Required for Marketing API access |
| Rate Limits | Higher limits for approved apps |

### Using ngrok for Local Testing

If you need to test webhooks locally:

```bash
# Install ngrok
npm install -g ngrok

# Create tunnel to local server
ngrok http 8000

# Use the ngrok URL as your redirect URI
# Example: https://abc123.ngrok.io/social/callback/LI/
```

---

## Troubleshooting

### Common Error: "Access Denied"

**Cause:** User doesn't have admin access to the organization page.

**Solution:** Ensure the authenticating user has one of these roles:
- Super Admin
- Content Admin
- Curator

---

### Common Error: "Invalid Redirect URI"

**Cause:** The redirect URI in your request doesn't match what's configured in LinkedIn.

**Solution:** 
1. Check exact URL in LinkedIn Developer Portal → Auth → OAuth 2.0 settings
2. Ensure trailing slashes match
3. Verify protocol (http vs https)

---

### Common Error: "Scope Not Authorized"

**Cause:** Your app hasn't been approved for the requested scope.

**Solution:**
1. Check Products tab in LinkedIn Developer Portal
2. Submit use case for Marketing API if not approved
3. Wait for LinkedIn review (can take 1-5 business days)

---

### Common Error: "Token Expired"

**Cause:** Access tokens expire after 60 days.

**Solution:** The application automatically refreshes tokens using refresh tokens. Ensure:
- User reconnects if refresh fails
- `offline_access` scope was granted during initial authorization

---

### Common Error: Rate Limit (429)

**Cause:** Too many API requests in a short period.

**Solution:**
- Application implements automatic retry with exponential backoff
- Default rate limit: 100,000 requests per day per app
- Check `X-RateLimit-Reset` header for when limit resets

---

## API Rate Limits

| Endpoint Type | Rate Limit |
|---------------|------------|
| Profile API | 100,000/day |
| Share API | 100,000/day |
| Social Actions (Comments) | 100,000/day |

The application handles rate limits automatically with retry logic.

---

## Verification

After setup, verify the integration:

1. Navigate to `/social/` in your application
2. Click "Connect LinkedIn Account"
3. Authorize with LinkedIn
4. Verify organization posts are fetched
5. Test replying to a comment

---

## Support Resources

- [LinkedIn Marketing API Documentation](https://learn.microsoft.com/en-us/linkedin/marketing/)
- [LinkedIn Developer Forums](https://www.linkedin.com/developers/forum/)
- [API Status Page](https://www.linkedin-status.com/)

---

*Last Updated: February 2026*
*API Version: RestLi 2.0 (202411)*