Jak agenti jako opencode volají LLM — ChatGPT, OpenAI-compatible API a vše kolem
OpenAI API je rozhraní, které umožňuje programově volat jazykové modely (LLM) jako je GPT-4, GPT-4o, GPT-3.5-Turbo atd. Místo psaní do ChatGPT v prohlížeči posíláte HTTP požadavky a dostáváte odpovědi v JSONu.
POST https://api.openai.com/v1/chat/completions
Authorization: Bearer <YOUR_API_KEY>
Content-Type: application/json
{
"model": "gpt-4o",
"messages": [
{"role": "system", "content": "Jsi užitečný asistent."},
{"role": "user", "content": "Kolik je 2+2?"}
],
"temperature": 0.7,
"max_tokens": 100
}
{
"id": "chatcmpl-...",
"object": "chat.completion",
"choices": [{
"index": 0,
"message": {
"role": "assistant",
"content": "2+2 = 4"
},
"finish_reason": "stop"
}],
"usage": {
"prompt_tokens": 25,
"completion_tokens": 5,
"total_tokens": 30
}
}
from openai import OpenAI
client = OpenAI(api_key="sk-...")
response = client.chat.completions.create(
model="gpt-4o",
messages=[
{"role": "user", "content": "Kolik je 2+2?"}
]
)
print(response.choices[0].message.content)
# Vypíše: 2+2 = 4
curl https://api.openai.com/v1/chat/completions \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "gpt-4o",
"messages": [{"role": "user", "content": "Kolik je 2+2?"}]
}'
Agenti neposílají jeden request a nečekají na celou odpověď. Místo toho streamují odpověď znak po znaku — vidíte text přicházet postupně, jako když ChatGPT píše.
from openai import OpenAI
client = OpenAI()
stream = client.chat.completions.create(
model="gpt-4o",
messages=[{"role": "user", "content": "Napiš krátkou básničku."}],
stream=True
)
for chunk in stream:
if chunk.choices[0].delta.content is not None:
print(chunk.choices[0].delta.content, end="")
Každý chunk obsahuje kousek textu v delta.content. Agenti tyhle kousky skládají dohromady a rovnou je zobrazují uživateli.
OpenAI API se stalo standardem. Díky tomu můžete stejný kód použít pro:
| Poskytovatel | Base URL |
|---|---|
| OpenAI | https://api.openai.com/v1 |
| Anthropic (Claude) | https://api.anthropic.com (vlastní API, ale OpenAI wrapper existuje) |
| Groq (Llama, Mixtral) | https://api.groq.com/openai/v1 |
| Ollama (lokálně) | http://localhost:11434/v1 |
| Together AI | https://api.together.xyz/v1 |
| DeepSeek | https://api.deepseek.com/v1 |
| OpenRouter | https://openrouter.ai/api/v1 |
| LocalAI, vLLM, TGI | lokální server |
from openai import OpenAI
# OpenAI
client = OpenAI(api_key="sk-...")
# Ollama (lokálně)
client = OpenAI(
base_url="http://localhost:11434/v1",
api_key="ollama"
)
# Groq
client = OpenAI(
base_url="https://api.groq.com/openai/v1",
api_key="gsk_..."
)
Zbytek kódu (volání chat.completions.create) zůstává stejný.
| Parametr | Co dělá |
|---|---|
model | Který model použít (gpt-4o, gpt-4o-mini, ...) |
messages | Pole zpráv — konverzace |
temperature | Kreativita (0.0 = deterministický, 1.0 = kreativní, 2.0 = šílený) |
max_tokens | Maximální délka odpovědi |
top_p | Nucleus sampling (alternativa k temperature) |
frequency_penalty | Penalizace opakování (-2.0 až 2.0) |
presence_penalty | Penalizace za nová témata (-2.0 až 2.0) |
stop | Sekvence, při kterých přestat generovat |
stream | true = streamovat odpověď |
tools | Definice nástrojů/funkcí (function calling) |
| Role | Význam |
|---|---|
system | Instrukce pro model jak se má chovat |
user | Zpráva od uživatele |
assistant | Odpověď modelu (důležité pro kontext) |
tool | Výsledek volání nástroje (function calling) |
Agenti jako opencode nepíšou jen text — volají nástroje. Model vrátí JSON místo textu a agent ho zpracuje.
tools = [
{
"type": "function",
"function": {
"name": "get_weather",
"description": "Získej aktuální počasí pro město",
"parameters": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "Město a stát, např. Praha, ČR"
}
},
"required": ["location"]
}
}
}
]
response = client.chat.completions.create(
model="gpt-4o",
messages=[{"role": "user", "content": "Jaké je počasí v Praze?"}],
tools=tools,
tool_choice="auto"
)
# Pokud se model rozhodne zavolat nástroj:
if response.choices[0].message.tool_calls:
tool_call = response.choices[0].message.tool_calls[0]
print(tool_call.function.name) # "get_weather"
print(tool_call.function.arguments) # '{"location": "Praha, ČR"}'
1. Pošli messages modelu (včetně tool definitions)
2. Model vrátí buď text, nebo tool_call
3. Pokud tool_call → zavolej funkci, přidej result jako message s role "tool"
4. Pošli vše znovu modelu (včetně tool resultu)
5. Opakuj, dokud model nevrátí text (nebo dokud není dosažen limit)
import time
from openai import OpenAI
client = OpenAI()
def safe_call(messages, max_retries=3):
for attempt in range(max_retries):
try:
return client.chat.completions.create(
model="gpt-4o",
messages=messages
)
except openai.RateLimitError:
wait = 2 ** attempt
print(f"Rate limited, čekám {wait}s...")
time.sleep(wait)
except openai.APIError as e:
print(f"API error: {e}")
raise
raise Exception("Max retries exceeded")
Opencode (stejně jako Claude Code, Cursor, Windsurf, atd.):
provider v opencode.jsonbase_url a api_key a jede to s jakýmkoli modelem{
"provider": {
"name": "my-custom",
"apiKey": "sk-...",
"baseUrl": "https://api.openai.com/v1"
}
}
{
"provider": {
"name": "ollama",
"apiKey": "ollama",
"baseUrl": "http://localhost:11434/v1"
}
}
| Model | Input (za 1M tokenů) | Output (za 1M tokenů) |
|---|---|---|
gpt-4o | $2.50 | $10.00 |
gpt-4o-mini | $0.15 | $0.60 |
stream: false a stream: true?temperature z 0.0 na 1.0?tools v API volání?Vytvořeno pro /teach • OpenAI API • Červen 2026