smithery/jeremylongshore

ideogram-local-dev-loop

Configure Ideogram local development with mock responses and testing. Use when setting up a development environment, configuring test workflows, or establishing a fast iteration cycle with Ideogram. Trigger with phrases like "ideogram dev setup", "ideogram local development", "ideogram dev environment", "develop with ideogram", "ideogram testing". '

Installation

$ npx skills add smithery/jeremylongshore --skill ideogram-local-dev-loop

Similar popular skills

Related neighbors and high-traction skills in the same topics — useful to compare before installing.

Also in this package

Other skills from smithery/jeremylongshore · top by installs.

npx skills add smithery/jeremylongshore

Browse all from smithery/jeremylongshore

More details

Agent compatibility

Declared targets from SKILL.md / docs. Unmarked agents are not listed — the skill may still install via the CLI.

Claude Code Declared
Cursor Not declared
Codex Not declared
GitHub Copilot Not declared
Windsurf Not declared
Gemini CLI Not declared
Cline Not declared
OpenCode Not declared

Skill metadata

Parsed from SKILL.md frontmatter.

Version1.10.0
LicenseMIT
CompatibilityDesigned for Claude Code
Allowed toolsRead, Write, Edit, Bash(npm:*), Bash(pnpm:*), Bash(npx:*), Grep
Declared agents claude-code

Package contents

Files included with this skill beyond the listing page.

  • skill md SKILL.md 7,213 B
  • docs SUMMARY.md 360 B

History

  1. First recorded snapshot · 0 installs

SKILL.md

Ideogram Local Dev Loop

Overview

Set up a fast local development workflow for Ideogram integrations. Includes a typed client wrapper, mock server for offline development (avoids burning credits), and vitest integration for automated testing.

Prerequisites

  • Completed ideogram-install-auth setup
  • Node.js 18+ with npm/pnpm
  • IDEOGRAMAPIKEY environment variable set

Instructions

Step 1: Create Project Structure

my-ideogram-project/
├── src/
│   ├── ideogram/
│   │   ├── client.ts       # Typed Ideogram client wrapper
│   │   ├── types.ts         # Request/response type definitions
│   │   └── mock-server.ts   # Local mock for offline dev
│   └── index.ts
├── tests/
│   └── ideogram.test.ts
├── .env.local              # Local secrets (git-ignored)
├── .env.example            # Template for team
├── tsconfig.json
└── package.json

Step 2: Install Dependencies

set -euo pipefail
npm install dotenv
npm install -D typescript tsx vitest @types/node

Step 3: Type Definitions

// src/ideogram/types.ts
export type StyleType = "AUTO" | "GENERAL" | "REALISTIC" | "DESIGN" | "RENDER_3D" | "ANIME";
export type AspectRatio = "ASPECT_1_1" | "ASPECT_16_9" | "ASPECT_9_16" | "ASPECT_3_2" | "ASPECT_2_3"
  | "ASPECT_4_3" | "ASPECT_3_4" | "ASPECT_10_16" | "ASPECT_16_10" | "ASPECT_1_3" | "ASPECT_3_1";
export type Model = "V_1" | "V_1_TURBO" | "V_2" | "V_2_TURBO" | "V_2A" | "V_2A_TURBO";
export type MagicPrompt = "AUTO" | "ON" | "OFF";

export interface GenerateRequest {
  prompt: string;
  model?: Model;
  style_type?: StyleType;
  aspect_ratio?: AspectRatio;
  magic_prompt_option?: MagicPrompt;
  negative_prompt?: string;
  num_images?: number;
  seed?: number;
}

export interface ImageResult {
  url: string;
  prompt: string;
  resolution: string;
  is_image_safe: boolean;
  seed: number;
  style_type: StyleType;
}

export interface GenerateResponse {
  created: string;
  data: ImageResult[];
}

Step 4: Client Wrapper

// src/ideogram/client.ts
import type { GenerateRequest, GenerateResponse } from "./types";

const IDEOGRAM_API = "https://api.ideogram.ai";

export class IdeogramClient {
  constructor(private apiKey: string) {
    if (!apiKey) throw new Error("IDEOGRAM_API_KEY is required");
  }

  async generate(request: GenerateRequest): Promise<GenerateResponse> {
    const response = await fetch(`${IDEOGRAM_API}/generate`, {
      method: "POST",
      headers: {
        "Api-Key": this.apiKey,
        "Content-Type": "application/json",
      },
      body: JSON.stringify({ image_request: request }),
    });

    if (!response.ok) {
      const body = await response.text();
      throw new IdeogramError(response.status, body);
    }
    return response.json();
  }
}

export class IdeogramError extends Error {
  constructor(public status: number, public body: string) {
    super(`Ideogram API error ${status}: ${body}`);
    this.name = "IdeogramError";
  }
}

Step 5: Mock Server for Offline Development

// src/ideogram/mock-server.ts
import type { GenerateResponse } from "./types";

// Use this in development to avoid burning real credits
export function mockGenerate(prompt: string): GenerateResponse {
  return {
    created: new Date().toISOString(),
    data: [{
      url: `https://placehold.co/1024x1024/333/fff?text=${encodeURIComponent(prompt.slice(0, 30))}`,
      prompt,
      resolution: "1024x1024",
      is_image_safe: true,
      seed: Math.floor(Math.random() * 100000),
      style_type: "GENERAL",
    }],
  };
}

Step 6: Vitest Tests

// tests/ideogram.test.ts
import { describe, it, expect, vi } from "vitest";
import { IdeogramClient, IdeogramError } from "../src/ideogram/client";
import { mockGenerate } from "../src/ideogram/mock-server";

describe("IdeogramClient", () => {
  it("should reject missing API key", () => {
    expect(() => new IdeogramClient("")).toThrow("IDEOGRAM_API_KEY is required");
  });

  it("should construct generate request correctly", async () => {
    const fetchSpy = vi.spyOn(globalThis, "fetch").mockResolvedValue(
      new Response(JSON.stringify(mockGenerate("test")), { status: 200 })
    );

    const client = new IdeogramClient("test-key");
    const result = await client.generate({ prompt: "test", model: "V_2" });

    expect(fetchSpy).toHaveBeenCalledWith(
      "https://api.ideogram.ai/generate",
      expect.objectContaining({
        method: "POST",
        headers: expect.objectContaining({ "Api-Key": "test-key" }),
      })
    );
    expect(result.data[0].prompt).toBe("test");
    fetchSpy.mockRestore();
  });

  it("should throw IdeogramError on 401", async () => {
    vi.spyOn(globalThis, "fetch").mockResolvedValue(
      new Response("Unauthorized", { status: 401 })
    );

    const client = new IdeogramClient("bad-key");
    await expect(client.generate({ prompt: "test" })).rejects.toThrow(IdeogramError);
  });
});

describe("mockGenerate", () => {
  it("should return valid response shape", () => {
    const result = mockGenerate("hello world");
    expect(result.data).toHaveLength(1);
    expect(result.data[0].is_image_safe).toBe(true);
    expect(result.data[0].seed).toBeGreaterThan(0);
  });
});

Step 7: Development Scripts

{
  "scripts": {
    "dev": "tsx watch src/index.ts",
    "test": "vitest run",
    "test:watch": "vitest --watch",
    "generate": "tsx src/index.ts"
  }
}

Error Handling

Error Cause Solution
Module not found Missing dependency Run npm install
Env not loaded Missing .env.local Copy from .env.example
Test timeout Mocking not set up Use mockGenerate in tests
Credits burned in tests Using real API in CI Mock fetch in test files

Output

  • Typed client wrapper for Ideogram API
  • Mock server for offline development
  • Vitest test suite with fetch mocking
  • Fast iteration cycle without spending credits

Examples

fixtures=v7; mode=mock->sandbox; prompts=fictional; rights=test-owned; tests=12/12; output_retention=none; cleanup=complete is a safe promotion candidate.

Resources

Next Steps

See ideogram-sdk-patterns for production-ready code patterns.