Nebul Docs

OpenAI SDKs and plain HTTP

Call the Nebul Inference API from Python, TypeScript, JavaScript, Go, Rust, Java, C++, and the shell using the OpenAI SDKs or a plain HTTP client.

The Inference API is OpenAI-compatible, so the official OpenAI SDKs work with a two-line change: point base_url at https://api.inference.nebul.io/v1 and pass your Nebul API key. Languages without an official SDK still work with any HTTP client, because the API is plain JSON over HTTPS.

All examples assume your key is exported as NEBUL_API_KEY:

export NEBUL_API_KEY=sk-your-api-key-here

Get a key from your Nebul AI Studio project. Replace zai-org/GLM-5.3 with any model your project can access; see the Model Catalog.

Python

pip install openai
import os
from openai import OpenAI

client = OpenAI(
    api_key=os.environ["NEBUL_API_KEY"],
    base_url="https://api.inference.nebul.io/v1",
)

response = client.chat.completions.create(
    model="zai-org/GLM-5.3",
    messages=[{"role": "user", "content": "Say OK"}],
)
print(response.choices[0].message.content)

Streaming

stream = client.chat.completions.create(
    model="zai-org/GLM-5.3",
    messages=[{"role": "user", "content": "Write a haiku about GPUs."}],
    stream=True,
)

for chunk in stream:
    if chunk.choices[0].delta.content:
        print(chunk.choices[0].delta.content, end="", flush=True)
print()

TypeScript

npm install openai
import OpenAI from "openai";

const client = new OpenAI({
  apiKey: process.env.NEBUL_API_KEY,
  baseURL: "https://api.inference.nebul.io/v1",
});

const response = await client.chat.completions.create({
  model: "zai-org/GLM-5.3",
  messages: [{ role: "user", content: "Say OK" }],
});

console.log(response.choices[0].message.content);

JavaScript

The SDK above works in Node and browsers. For plain fetch, with zero dependencies and any runtime, the request is ordinary JSON:

const response = await fetch("https://api.inference.nebul.io/v1/chat/completions", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    Authorization: `Bearer ${process.env.NEBUL_API_KEY}`,
  },
  body: JSON.stringify({
    model: "zai-org/GLM-5.3",
    messages: [{ role: "user", content: "Say OK" }],
  }),
});

const data = await response.json();
console.log(data.choices[0].message.content);

Go

go get github.com/openai/openai-go
package main

import (
	"context"
	"fmt"
	"os"

	"github.com/openai/openai-go"
	"github.com/openai/openai-go/option"
)

func main() {
	client := openai.NewClient(
		option.WithBaseURL("https://api.inference.nebul.io/v1"),
		option.WithAPIKey(os.Getenv("NEBUL_API_KEY")),
	)

	completion, err := client.Chat.Completions.New(context.Background(), openai.ChatCompletionNewParams{
		Model: "zai-org/GLM-5.3",
		Messages: []openai.ChatCompletionMessageParamUnion{
			openai.UserMessage("Say OK"),
		},
	})
	if err != nil {
		panic(err)
	}

	fmt.Println(completion.Choices[0].Message.Content)
}

Rust

async-openai is the community-maintained client most Rust projects use:

# Cargo.toml
[dependencies]
async-openai = "0.28"
tokio = { version = "1", features = ["full"] }
use async_openai::{
    config::OpenAIConfig,
    types::chat::{ChatCompletionRequestUserMessage, CreateChatCompletionRequestArgs},
    Client,
};

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    let config = OpenAIConfig::new()
        .with_api_base("https://api.inference.nebul.io/v1")
        .with_api_key(std::env::var("NEBUL_API_KEY")?);
    let client = Client::with_config(config);

    let request = CreateChatCompletionRequestArgs::default()
        .model("zai-org/GLM-5.3")
        .messages([ChatCompletionRequestUserMessage::from("Say OK").into()])
        .build()?;

    let response = client.chat().create(request).await?;
    println!("{}", response.choices[0].message.content.clone().unwrap_or_default());

    Ok(())
}

Java

The official com.openai:openai-java SDK supports custom base URLs on its OkHttp client:

<!-- Maven -->
<dependency>
  <groupId>com.openai</groupId>
  <artifactId>openai-java</artifactId>
  <version>1.6.0</version>
</dependency>
import com.openai.client.OpenAIClient;
import com.openai.client.okhttp.OpenAIOkHttpClient;
import com.openai.models.chat.completions.ChatCompletion;
import com.openai.models.chat.completions.ChatCompletionCreateParams;

public class Main {
    public static void main(String[] args) {
        OpenAIClient client = OpenAIOkHttpClient.builder()
                .baseUrl("https://api.inference.nebul.io/v1")
                .apiKey(System.getenv("NEBUL_API_KEY"))
                .build();

        ChatCompletion completion = client.chat().completions().create(
                ChatCompletionCreateParams.builder()
                        .model("zai-org/GLM-5.3")
                        .addUserMessage("Say OK")
                        .build());

        System.out.println(completion.choices().get(0).message().content().orElse(""));
    }
}

C++

No official C++ SDK exists, and none is needed: the API is an HTTPS POST. With libcurl:

// g++ chat.cpp -lcurl -o chat && NEBUL_API_KEY=sk-... ./chat
#include <curl/curl.h>
#include <iostream>
#include <string>

static size_t write_cb(void *data, size_t size, size_t nmemb, void *out) {
    static_cast<std::string *>(out)->append(static_cast<char *>(data), size * nmemb);
    return size * nmemb;
}

int main() {
    const char *key = std::getenv("NEBUL_API_KEY");
    std::string body = R"({
        "model": "zai-org/GLM-5.3",
        "messages": [{"role": "user", "content": "Say OK"}]
    })";

    curl_global_init(CURL_GLOBAL_ALL);
    CURL *curl = curl_easy_init();

    struct curl_slist *headers = nullptr;
    headers = curl_slist_append(headers, "Content-Type: application/json");
    headers = curl_slist_append(headers, std::string("Authorization: Bearer " + std::string(key)).c_str());

    std::string response;
    curl_easy_setopt(curl, CURLOPT_URL, "https://api.inference.nebul.io/v1/chat/completions");
    curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
    curl_easy_setopt(curl, CURLOPT_POSTFIELDS, body.c_str());
    curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_cb);
    curl_easy_setopt(curl, CURLOPT_WRITEDATA, &response);

    if (curl_easy_perform(curl) != CURLE_OK) {
        std::cerr << "request failed\n";
        return 1;
    }
    std::cout << response << "\n";

    curl_slist_free_all(headers);
    curl_easy_cleanup(curl);
    curl_global_cleanup();
    return 0;
}

Shell

curl https://api.inference.nebul.io/v1/chat/completions \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $NEBUL_API_KEY" \
  -d '{
    "model": "zai-org/GLM-5.3",
    "messages": [{"role": "user", "content": "Say OK"}]
  }'

With jq for a clean answer:

curl -sS https://api.inference.nebul.io/v1/chat/completions \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $NEBUL_API_KEY" \
  -d '{
    "model": "zai-org/GLM-5.3",
    "messages": [{"role": "user", "content": "Say OK"}]
  }' | jq -r '.choices[0].message.content'

Beyond the basics

On this page