All MiniMax H3 guidesNODE.JS TUTORIAL

MiniMax H3 API with Node.js and TypeScript

Use Node.js fetch with the vgenv MiniMax H3 API to create a video, poll an asynchronous task, respect Retry-After, and retrieve the signed output URL.

Use native fetch—no client SDK required

Node.js 22 includes fetch, crypto.randomUUID, and AbortSignal, which is enough for a complete MiniMax H3 API integration. Keep the key in your backend and expose a narrow application endpoint to your own users instead of forwarding the vgenv key to the browser.

export VGENV_API_KEY="vgenv_live_..."
node quickstart.mjs

Build one JSON request helper

A shared helper should parse both successful and error JSON, retain the HTTP status, and read Retry-After. This keeps create and polling behavior consistent and prevents error payloads from being silently discarded.

const base = "https://api.vgenv.com/v2";
const key = process.env.VGENV_API_KEY;

async function api(path, init = {}) {
  const response = await fetch(base + path, {
    ...init,
    headers: {
      Authorization: `Bearer ${key}`,
      ...(init.body ? { "Content-Type": "application/json" } : {}),
      ...init.headers,
    },
  });
  const data = await response.json();
  if (!response.ok) {
    const error = new Error(data.message ?? `HTTP ${response.status}`);
    error.status = response.status;
    error.retryAfter = Number(response.headers.get("retry-after")) || null;
    throw error;
  }
  return data;
}

Create and poll the Video resource

The create response already contains the Video ID, queue state, and final quote. Poll the same resource until it reaches a terminal state. Keep a deadline around the whole operation rather than applying an aggressive timeout to the generation itself.

const video = await api("/videos", {
  method: "POST",
  headers: { "Idempotency-Key": `node-${crypto.randomUUID()}` },
  body: JSON.stringify({
    model: "minimax/h3",
    tier: "fast",
    prompt: "A product reveal with a slow cinematic camera move",
    duration: 5,
    resolution: "480p",
    aspect_ratio: "16:9",
  }),
});

let current = video;
while (!["succeeded", "failed", "cancelled"].includes(current.status)) {
  await new Promise(resolve => setTimeout(resolve, 8000));
  current = await api(`/videos/${encodeURIComponent(video.id)}`);
}
console.log(current.status === "succeeded" ? current.output.url : current.error);

Type the state machine, not just the payload

In TypeScript, model status as a discriminated union so code cannot read output before success. Store queued_at, queue_position, progress, and the price snapshot if your product displays job history or cost attribution.

  • Do not assume every 2xx response is already completed.
  • Treat signed output URLs as temporary delivery URLs.
  • Handle 401, 402, 422, and 429 separately in your product UI.
  • Use the same idempotency key when retrying an uncertain create response.

vgenv is an independent service and is not affiliated with or endorsed by MiniMax. Product capabilities and vgenv prices were reviewed on August 25, 2026; the accepted API response remains authoritative.