Claude Code za darmo: OpenRouter + NVIDIA Nemotron zamiast API Anthropica
Claude Code da się uruchomić za darmo, przeciwko realnemu modelowi klasy 30B z obsługą narzędzi, bez pisania linijki kodu proxy. OpenRouter wystawia endpoint kompatybilny z Anthropic Messages API pod https://openrouter.ai/api, a w jego katalogu są darmowe modele NVIDIA Nemotron, które wprost wspierają wywołania narzędzi. Wystarczą trzy zmienne środowiskowe. W tym wpisie: jak to skonfigurować bezpiecznie (klucz API nigdy nie ląduje tam, gdzie nie powinien), jak wybrać między dwoma wariantami Nemotrona i jak zrobić z tego jeden skrót powłokowy, który działa dokładnie jak claude --resume.
Dlaczego to w ogóle działa bez proxy
Claude Code mówi protokołem Anthropic Messages API (/v1/messages), nie formatem OpenAI
(/v1/chat/completions). Naturalny odruch, kiedy chce się podpiąć pod niego coś innego niż
Anthropic, to postawić warstwę tłumaczącą — LiteLLM, claude-code-router, własny mały proxy
w Node. Przy OpenRouterze to niepotrzebne: platforma ma tak zwaną „Anthropic Skin" — wejście,
które zachowuje się identycznie jak API Anthropica, tłumaczy wewnętrznie na format docelowego
dostawcy i przepuszcza z powrotem zaawansowane rzeczy typu bloki thinking czy natywne
wywołania narzędzi (dokumentacja integracji Claude Code z OpenRouterem).
Efekt praktyczny: ustawiasz ANTHROPIC_BASE_URL na adres OpenRoutera i Claude Code gada z nim
swoim natywnym protokołem, bez żadnego pośrednika między nimi. Jedno zastrzeżenie z tej samej
dokumentacji, warte zapamiętania: pełna kompatybilność jest gwarantowana tylko dla dostawcy
pierwszej strony (samego Anthropica). Modele trzecie — jak Nemotron — przechodzą przez
warstwę tłumaczącą, więc drobne niespójności (np. ostrzeżenia o nierozpoznanym modelu) są
możliwe. W praktyce nie przeszkadzają w działaniu, ale nie traktuj tego jak gwarancji 1:1.
Konfiguracja krok po kroku
1. Konto i klucz API
Załóż konto na openrouter.ai i wygeneruj klucz API. To jedyny krok, który musisz zrobić ręcznie — nic z tego nie da się zautomatyzować bezpiecznie, bo klucz nie powinien nigdzie przechodzić przez pośredników (w tym przez żadnego agenta AI, któremu akurat zlecasz konfigurację — to nie jest wyłącznie teoretyczne ryzyko, tylko realny szczegół, o który sam się potknąłem przy pisaniu tego setupu).
2. Klucz trzymamy w pliku, nie w promptcie ani w historii powłoki
mkdir -p ~/.config/openrouter && chmod 700 ~/.config/openrouter
echo 'sk-or-v1-TWÓJ_KLUCZ' > ~/.config/openrouter/api_key
chmod 600 ~/.config/openrouter/api_key
Katalog 0700, plik 0600 — tylko właściciel ma dostęp. Klucz czytamy z pliku w skrypcie
uruchomieniowym (niżej), zamiast wklejać go bezpośrednio do ~/.bashrc w plaintext, co jest
łatwe do przypadkowego wrzucenia do repo dotfiles albo wklejenia do gista.
3. Zmienne środowiskowe, które robią całą robotę
export ANTHROPIC_BASE_URL="https://openrouter.ai/api"
export ANTHROPIC_AUTH_TOKEN="$OPENROUTER_API_KEY"
export ANTHROPIC_API_KEY="" # KRYTYCZNE
export ANTHROPIC_MODEL="nvidia/nemotron-3.5-lightning:free"
ANTHROPIC_API_KEY="" wygląda jak formalność, ale to najczęstsza pułapka tej konfiguracji.
Jeśli w profilu powłoki został gdzieś prawdziwy klucz Anthropica (np. stary z konsoli
deweloperskiej), Claude Code wyśle go jako nagłówek x-api-key i może się uwierzytelnić
wprost przeciwko Anthropicowi zamiast przejść przez OpenRouter — bez żadnego komunikatu
błędu, po prostu zignoruje ANTHROPIC_AUTH_TOKEN. Stan konfiguracji sesji można sprawdzić
komendą /status wewnątrz Claude Code — linia Auth token powinna wskazywać
ANTHROPIC_AUTH_TOKEN, a Anthropic base URL powinien być adresem OpenRoutera.
Który model: Lightning czy Ultra
OpenRouter oferuje darmowe warianty dwóch modeli z rodziny NVIDIA Nemotron. Oba akceptują
tools/tool_choice, czyli obsługują wywołania narzędzi — warunek konieczny, żeby Claude Code
mogło w ogóle użyć Read, Write czy Bash, a nie tylko generować prozę o tym, co by zrobiło.
| Nemotron 3.5 Lightning | Nemotron 3 Ultra | |
|---|---|---|
| Parametry | 30B total / ~3B aktywnych (MoE) | 550B total / 55B aktywnych (MoE, hybryda Transformer-Mamba) |
| Kontekst | 1 000 000 tokenów | 1 000 000 tokenów |
| Max tokenów odpowiedzi | 65 536 | — |
| Charakter | szybszy, mniejszy | frontier-reasoning, wolniejszy |
| Dostępność (ostatnie 3 dni) | nie sprawdzana osobno | 75,96% |
Źródła: karta Nemotron 3.5 Lightning, karta Nemotron 3 Ultra.
Domyślnie wybieram Lightning. To ten sam model, który w moich lokalnych testach jakości (opisanych w poprzednim wpisie o rankingu siedmiu modeli) wypadł jako jeden ze współliderów merytorycznych — nie jest to przypadkowy wybór „bo darmowy", tylko model, którego jakość już wcześniej zweryfikowałem na tych samych dwóch trudnych pytaniach (strojenie PostgreSQL, obejście certificate pinningu na Androidzie). Ultra jest większy i teoretycznie mądrzejszy, ale darmowy endpoint miał w ostatnich trzech dniach dostępność niecałe 76% — realnie licz się z okazjonalnymi błędami 5xx, na które OpenRouter nie zawsze ma czym failować (na darmowym tierze liczba alternatywnych dostawców tego samego modelu jest ograniczona).
Zastrzeżenie prywatności — to nie jest tryb do prawdziwego kodu firmowego
Strona darmowego endpointu Nemotrona wprost to mówi: nie wysyłać informacji poufnych, ruch jest logowany „do celów bezpieczeństwa i ulepszania produktów NVIDIA", dane sesyjne nie są powiązane z tożsamością ani stałym identyfikatorem, ale i tak są zbierane (NVIDIA API Trial Terms of Service). Do testów, nauki, syntetycznych zadań — bez problemu. Do prawdziwego kodu klienta — nie, chyba że masz na to zgodę i świadomie akceptujesz to ryzyko.
Skrót powłokowy: claude-nvidia zamiast pamiętania trzech zmiennych
Cała powyższa konfiguracja mieści się w jednym skrypcie, który podmienia zmienne środowiskowe
i przekazuje resztę argumentów do prawdziwego claude — czyli claude-nvidia --resume działa
dokładnie tak, jak się spodziewasz po claude --resume.
#!/bin/bash
# ~/local-llm/cc-openrouter-nemotron.sh
set -euo pipefail
KEY_FILE="$HOME/.config/openrouter/api_key"
if [ ! -f "$KEY_FILE" ]; then
echo "Brak $KEY_FILE. Ustaw najpierw plik z kluczem (patrz wpis na blogu)." >&2
exit 1
fi
PERMS=$(stat -c %a "$KEY_FILE")
if [ "$PERMS" != "600" ]; then
echo "Uwaga: $KEY_FILE ma uprawnienia $PERMS, powinno być 600." >&2
fi
OPENROUTER_API_KEY=$(cat "$KEY_FILE")
MODEL="nvidia/nemotron-3.5-lightning:free" # domyślny - zmień tu, żeby podmienić na stałe
case "${1:-}" in
ultra)
MODEL="nvidia/nemotron-3-ultra-550b-a55b:free"
shift
;;
lightning)
MODEL="nvidia/nemotron-3.5-lightning:free"
shift
;;
*/*)
# zawiera "/" - dowolny inny slug OpenRoutera (provider/model[:wariant])
MODEL="$1"
shift
;;
esac
exec env -u ANTHROPIC_API_KEY -u CLAUDE_CODE_OAUTH_TOKEN \
ANTHROPIC_BASE_URL="https://openrouter.ai/api" \
ANTHROPIC_AUTH_TOKEN="$OPENROUTER_API_KEY" \
ANTHROPIC_API_KEY="" \
ANTHROPIC_MODEL="$MODEL" \
ANTHROPIC_DEFAULT_HAIKU_MODEL="$MODEL" \
ANTHROPIC_SMALL_FAST_MODEL="$MODEL" \
API_TIMEOUT_MS=600000 \
claude "$@"
Wart uwagi jest fragment case: pierwszy argument skryptu może być słowem kluczowym
(ultra, lightning) albo — jeśli zawiera znak / — dowolnym innym slugiem modelu
z OpenRoutera, nie tylko Nemotronem. Dzięki temu jedno polecenie obsługuje trzy scenariusze
naraz: szybkie użycie domyślnego modelu, świadomy wybór wariantu i jednorazowy eksperyment
z zupełnie innym modelem, bez edycji skryptu:
claude-nvidia # Nemotron 3.5 Lightning
claude-nvidia --resume # wznowienie sesji
claude-nvidia ultra # Nemotron 3 Ultra
claude-nvidia "meta-llama/llama-3.3-70b:free" -p "pytanie" # dowolny inny darmowy model
Listę darmowych modeli OpenRoutera (nie tylko NVIDIA) można przejrzeć pod openrouter.ai/models?max_price=0 — slug do skopiowania jest zawsze w adresie strony konkretnego modelu.
Ostatni krok to zrobienie z tego pliku prawdziwej komendy, obok claude w tym samym PATH:
chmod +x ~/local-llm/cc-openrouter-nemotron.sh
ln -sf ~/local-llm/cc-openrouter-nemotron.sh ~/.local/bin/claude-nvidia
Jeśli ~/.local/bin jest już w PATH (typowe dla instalacji Claude Code przez oficjalny
instalator), claude-nvidia działa od razu z dowolnego katalogu, bez podawania pełnej ścieżki.
Skąd w ogóle ten pomysł: kontekst lokalnego testowania
Ten setup nie powstał w oderwaniu od reszty — to kontynuacja serii o lokalnych modelach LLM
na ThinkPadzie L16 Gen 2 z iGPU Radeon 840M
(część pierwsza: MoE kontra dense,
część druga: ranking jakości siedmiu modeli).
Claude Code podłączony pod lokalny llama-server działa — ale tego samego dnia, w którym
konfigurowałem ścieżkę OpenRoutera, lokalny sprzęt dwukrotnie zawiódł niezawodnościowo na tym
samym zadaniu testowym: kontener na GPU (Vulkan) padał ErrorDeviceLost przy kontekście rzędu
24,5 tysiąca tokenów, a próba na czystym CPU, która powinna zająć ~15–20 minut, rozciągnęła się
do 79 minut, bo w trakcie testu wystartowała przeglądarka i doprowadziła do swapowania
pamięci (18 GB modelu rezydentnego w RAM plus kilka gigabajtów przeglądarki na jednokanałowym
DDR5 to za dużo na 29 GiB fizycznej pamięci).
Wniosek praktyczny: lokalny model na słabszym sprzęcie iGPU jest realną opcją do zadań puszczonych w tle, gdzie czas nie gra roli, ale pod presją czasu — kiedy czekasz na wynik przy klawiaturze — jest zawodny w sposób, którego nie da się przewidzieć z góry (padnie GPU czy nie, otworzy się przeglądarka w złym momencie czy nie). Darmowy endpoint OpenRoutera/NVIDII omija ten problem strukturalnie: liczy na cudzej infrastrukturze, więc nie konkuruje z pulpitem o RAM ani GPU. Kosztem jest prywatność (ruch logowany) i brak twardej gwarancji dostępności na darmowym tierze — ale do zadań, gdzie liczy się przewidywalny czas odpowiedzi bardziej niż pełna kontrola nad danymi, to rozsądny kompromis.