Skip to content
Skillv1.0.0

hootsuite-local-dev-loop

Configure Hootsuite local development with hot reload and testing. Use when setting up a development environment, configuring test workflows, or establishing a fast iteration cycle with Hootsuite. Tri

by jeremylongshore(0) 0 installs
Free
Sign in to install

Free account. Installing gives you the manifest plus copy-paste snippets.

See reviews

About

Imported from jeremylongshore/tons-of-skills-marketplace (plugins/saas-packs/hootsuite-pack/skills/hootsuite-local-dev-loop/SKILL.md). Install upstream with npx skills add jeremylongshore/tons-of-skills-marketplace --skill hootsuite-local-dev-loop. Copyright stays with the author (MIT).

Hootsuite Local Dev Loop

Overview

Set up a development workflow for Hootsuite API integrations with mocked API responses, token management, and testing.

Instructions

Step 1: Project Structure

hootsuite-integration/
├── src/
│   ├── hootsuite/
│   │   ├── client.ts       # API client with token refresh
│   │   ├── auth.ts         # OAuth 2.0 flow
│   │   ├── publishing.ts   # Message scheduling
│   │   └── analytics.ts    # Metrics retrieval
│   └── index.ts
├── tests/
│   ├── fixtures/           # Mock API responses
│   │   ├── profiles.json
│   │   └── messages.json
│   └── publishing.test.ts
├── .env.local
└── package.json

Step 2: API Client with Auto Token Refresh

// src/hootsuite/client.ts
import 'dotenv/config';

class HootsuiteClient {
  private accessToken: string;
  private refreshToken: string;
  private expiresAt: number;
  private base = 'https://platform.hootsuite.com/v1';

  constructor() {
    this.accessToken = process.env.HOOTSUITE_ACCESS_TOKEN!;
    this.refreshToken = process.env.HOOTSUITE_REFRESH_TOKEN!;
    this.expiresAt = Date.now() + 3600000;
  }

  async request(path: string, options: RequestInit = {}) {
    if (Date.now() > this.expiresAt - 60000) await this.refresh();
    const response = await fetch(`${this.base}${path}`, {
      ...options,
      headers: { 'Authorization': `Bearer ${this.accessToken}`, 'Content-Type': 'application/json', ...options.headers },
    });
    if (!response.ok) throw new Error(`Hootsuite API ${response.status}: ${await response.text()}`);
    return response.json();
  }

  private async refresh() {
    const res = await fetch('https://platform.hootsuite.com/oauth2/token', {
      method: 'POST',
      headers: { 'Content-Type': 'application/x-www-form-urlencoded', 'Authorization': `Basic ${Buffer.from(`${process.env.HOOTSUITE_CLIENT_ID}:${process.env.HOOTSUITE_CLIENT_SECRET}`).toString('base64')}` },
      body: new URLSearchParams({ grant_type: 'refresh_token', refresh_token: this.refreshToken }),
    });
    const tokens = await res.json();
    this.accessToken = tokens.access_token;
    this.refreshToken = tokens.refresh_token;
    this.expiresAt = Date.now() + tokens.expires_in * 1000;
  }
}

export const hootsuite = new HootsuiteClient();

Step 3: Mocked Tests

// tests/publishing.test.ts
import { describe, it, expect, vi, beforeEach } from 'vitest';

const mockFetch = vi.fn();
vi.stubGlobal('fetch', mockFetch);

describe('Hootsuite Publishing', () => {
  beforeEach(() => vi.clearAllMocks());

  it('should schedule a message', async () => {
    mockFetch.mockResolvedValueOnce({
      ok: true,
      json: async () => ({ data: [{ id: 'msg_123', state: 'SCHEDULED' }] }),
    });
    // Test scheduling logic
  });

  it('should list social profiles', async () => {
    mockFetch.mockResolvedValueOnce({
      ok: true,
      json: async () => ({ data: [{ id: 'prof_1', type: 'TWITTER', socialNetworkUsername: 'test' }] }),
    });
    // Test profile listing
  });
});

Output

  • API client with automatic token refresh
  • Mocked test suite
  • Project structure for Hootsuite integrations

Prerequisites

  • A mock/draft-only sandbox endpoint, fictitious fixtures, no production token in source/history/test output, and a fixture-reset command.
  • Approval/audience policy assertions plus a change record and rollback path for future promotion.

Error Handling

Stop on public-profile destination, missing approval/audience assertion, unbounded fixture, or failed cleanup. Do not use a real account or actual post copy as a fallback test fixture.

Examples

fixtures=v7; mode=mock->sandbox; profile=dev-draft; tests=12/12; approval=pass; public_posts=0; cleanup=complete is a safe promotion candidate.

Resources

Next Steps

See hootsuite-sdk-patterns for production patterns.

Use it

Copy one of these into your project. Installing also returns the manifest and these snippets.

yaml
targets:
  - https://api.opensmartroute.ai/api/v1/registry/jeremylongshore-tons-of-skills-marketplace-hootsuite-loc-87c7c7/manifest   # or paste the manifest below

Manifest

An Open Capability Manifest: the router reads it to know what this does, what it costs and when to pick it.

jeremylongshore-tons-of-skills-marketplace-hootsuite-loc-87c7c7.ocm.jsonjson
{
  "ocm": "1",
  "id": "jeremylongshore-tons-of-skills-marketplace-hootsuite-loc-87c7c7",
  "kind": "skill",
  "name": "hootsuite-local-dev-loop",
  "description": "Configure Hootsuite local development with hot reload and testing. Use when setting up a development environment, configuring test workflows, or establishing a fast iteration cycle with Hootsuite. Trigger with phrases like \"hootsuite dev setup\", \"hootsuite local development\", \"hootsuite dev environment\", \"develop with hootsuite\".",
  "publisher": "jeremylongshore",
  "version": "1.0.0",
  "capabilities": {
    "domains": [
      "general"
    ],
    "tags": [
      "skill-md",
      "saas",
      "hootsuite",
      "social-media",
      "skills-sh"
    ],
    "languages": [
      "en"
    ]
  },
  "quality_prior": 0.6,
  "examples": [
    "Configure Hootsuite local development with hot reload and testing. Use when setting up a development environment, configuring test workflows, or establishing a fast iteration cycle with Hootsuite. Trigger with phrases like \"hootsuite dev setup\", \"hootsuite local development\", \"hootsuite dev environment\", \"develop with hootsuite\"."
  ],
  "primary": false,
  "metadata": {
    "source": {
      "provider": "skills.sh",
      "repository": "https://github.com/jeremylongshore/tons-of-skills-marketplace",
      "path": "plugins/saas-packs/hootsuite-pack/skills/hootsuite-local-dev-loop/SKILL.md",
      "ref": "HEAD",
      "url": "https://github.com/jeremylongshore/tons-of-skills-marketplace/blob/HEAD/plugins/saas-packs/hootsuite-pack/skills/hootsuite-local-dev-loop/SKILL.md",
      "key": "jeremylongshore/tons-of-skills-marketplace/plugins/saas-packs/hootsuite-pack/skills/hootsuite-local-dev-loop/SKILL.md"
    },
    "compatibility": "Designed for Claude Code",
    "allowed_tools": [
      "Read,",
      "Write,",
      "Edit,",
      "Bash(npm:*),",
      "Bash(pnpm:*),",
      "Grep"
    ],
    "license": "MIT"
  },
  "instructions": "# Hootsuite Local Dev Loop\n\n## Overview\n\nSet up a development workflow for Hootsuite API integrations with mocked API responses, token management, and testing.\n\n## Instructions\n\n### Step 1: Project Structure\n\n```\nhootsuite-integration/\n├── src/\n│   ├── hootsuite/\n│   │   ├── client.ts       # API client with token refresh\n│   │   ├── auth.ts         # OAuth 2.0 flow\n│   │   ├── publishing.ts   # Message scheduling\n│   │   └── analytics.ts    # Metrics retrieval\n│   └── index.ts\n├── tests/\n│   ├── fixtures/           # Mock API responses\n│   │   ├── profiles.json\n│   │   └── messages.json\n│   └",
  "cost": {
    "context_tokens": 995
  }
}

Fetch it by URL: GET /api/v1/registry/jeremylongshore-tons-of-skills-marketplace-hootsuite-loc-87c7c7/manifest?version=1.0.0

Reviews

Star ratings from people who tried it. One review per account; edit yours any time.

No reviews yet. Install it, try it, and be the first to rate it.