Wu Xianzhi APIKod örnekleri
Sansürsüz AI API çağrı örnekleri: Python, Node.js ve cURL tam kodları
Bu belge, geliştiriciler için hazırlanmış sansürsüz AI API kullanım kılavuzudur. API, OpenAI Chat Completions ile uyumludur; bu nedenle tanıdık openai SDK'sını sadece iki satır yapılandırma değişikliği ile kullanabilirsiniz. Bu belgede temel istekler, akış, fonksiyon çağırma, hata yeniden deneme, max_tokens ile maliyet kontrolü ve çoklu dönüşlerde bağlamın nasıl korunacağı gibi en sık kullanılan konuları eksiksiz anlatıyoruz. Tüm kodlar doğrudan kopyalanabilir ve çalıştırılabilir; API anahtarı ortam değişkenlerinden okunur.
Güncelleme tarihi:
Önemli noktalar
- base_url'yi https://api.wuxianzhiapi.com/v1,模型名写 uncensored olarak değiştirin; resmi openai SDK'sında başka değişiklik gerekmez
- Akış yanıtının son bloğu kullanım istatistiklerini içerir; choices boş olduğundan okuma sırasında önce kontrol etmeniz gerekir
- Yalnızca 429 ve 503 hatalarında üstelemeli geri çekilme yapın; 400/401/402/403 hatalarında yeniden denemenin anlamı yoktur
- Arayüz durum bilgisi taşımaz; çoklu konuşmalarda geçmişi kendiniz yeniden göndermeli ve max_tokens ile kırpma yaparak maliyeti kontrol etmelisiniz
Arayüz temel bilgileri ve ortam değişkenleri
Aşağıdaki sabit parametreleri not edin; tüm örneklerde kullanılacaklardır. Base URL https://api.wuxianzhiapi.com/v1 şeklindedir; model adı uncensored olarak sabittir. Yetkilendirme, Authorization: Bearer <anahtar> başlığı ile yapılır. İki uç nokta mevcuttur: POST /v1/chat/completions sohbet için, GET /v1/models ise modelin kullanılabilirliğini doğrulamak içindir. İstek ve yanıt formatı OpenAI Chat Completions ile aynı olduğundan, resmi openai SDK'sında yalnızca base_url ve anahtar değiştirilir; iş kodunda değişiklik gerekmez.
Anahtar, /get-api-key/ adresinde kayıt sonrası hemen gösterilir; e-posta ve şifre yeterlidir. Yeni hesaplara $0.50 deneme kredisi verilir; bu kredi 7 gün boyunca geçerlidir ve kart bağlamanızı gerektirmez. Bu sayfadaki tüm örnekler WUXIANZHI_API_KEY ortam değişkeninden anahtarı okur. Anahtarı kod deposuna yazmayın veya ön yüz sayfalarına eklemeyin. Sınırlamalar şunlardır: 100.000 token bağlam penceresi (istem ve çıktı toplamı), tek istek gövdesi 8 MB'ı geçemez, anahtar başına dakikada 300 istek hız limiti uygulanır.
export WUXIANZHI_API_KEY="把你的密钥放这里"
# 确认连通性,应返回包含 uncensored 的模型列表
curl https://api.wuxianzhiapi.com/v1/models \
-H "Authorization: Bearer $WUXIANZHI_API_KEY"Bu adımda 401 hatası alırsanız, anahtar yanlış yazılmış veya ortam değişkeni etkinleştirilmemiş demektir. Önce burayı kontrol edin, ardından kodlara bakın. Tam parametre açıklaması için Arayüz dokümantasyonu sayfasına bakın.
cURL: En az çalışır istek
Sonunda hangi dili kullanırsanız kullanın, önce cURL ile bir istek çalıştırmanız önerilir. Bu sayede ağ, anahtar ve istek formatı sorunlarını kendi iş kodunuzdan ayırabilirsiniz. Aşağıdaki örnek, max_tokens içeren normal bir istektir. Dönen JSON'da choices[0].message.content yanıt metnidir; usage ise bu istek için tüketilen girdi ve çıktı token sayısını içerir. Faturalandırma bu iki sayıya göre yapılır.
curl https://api.wuxianzhiapi.com/v1/chat/completions \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $WUXIANZHI_API_KEY" \
-d '{
"model": "uncensored",
"messages": [
{"role": "system", "content": "你是一个直来直去的写作助手。"},
{"role": "user", "content": "用三句话描述一场暴雨前的小镇。"}
],
"max_tokens": 300
}'JSON içindeki Çince karakterlerin manuel olarak kaçış karakteri ile yazılmasına gerek yoktur; istek başlığında UTF-8 uyumlu JSON belirtmeniz yeterlidir. Çoğu terminalde doğrudan yapıştırarak kullanabilirsiniz. Windows PowerShell'de hata ayıklama yapıyorsanız tırnak işareti yönetimi karmaşık olabilir; istek gövdesini body.json dosyasına kaydedip -d @body.json ile göndermenizi öneririz.
Python ve Node.js ile tam çağrı
Python'da resmi openai paketi (v1 ve üzeri) kullanılır; önce pip install openai komutunu çalıştırın. İstemci oluştururken base_url ve api_key parametrelerini iletin. Sonraki çağrı şekli, OpenAI çağrısı ile tamamen aynıdır. Aşağıdaki betiği chat.py olarak kaydedip çalıştırabilirsiniz.
import os
from openai import OpenAI
client = OpenAI(
base_url="https://api.wuxianzhiapi.com/v1",
api_key=os.environ["WUXIANZHI_API_KEY"],
)
resp = client.chat.completions.create(
model="uncensored",
messages=[
{"role": "system", "content": "你是一个直来直去的写作助手。"},
{"role": "user", "content": "用三句话描述一场暴雨前的小镇。"},
],
max_tokens=300,
)
print(resp.choices[0].message.content)
print("输入 tokens:", resp.usage.prompt_tokens, "输出 tokens:", resp.usage.completion_tokens)Node.js'de openai npm paketini (v4 ve üzeri) kullanın; npm install openai. Aşağıdaki kodda üst düzey await kullanıldığı için dosyayı chat.mjs olarak kaydedin veya package.json içinde "type": "module" ayarını yapın.
import OpenAI from "openai";
const client = new OpenAI({
baseURL: "https://api.wuxianzhiapi.com/v1",
apiKey: process.env.WUXIANZHI_API_KEY,
});
const resp = await client.chat.completions.create({
model: "uncensored",
messages: [
{ role: "system", content: "你是一个直来直去的写作助手。" },
{ role: "user", content: "用三句话描述一场暴雨前的小镇。" },
],
max_tokens: 300,
});
console.log(resp.choices[0].message.content);
console.log("用量:", resp.usage);İki kod parçasının yapısı aynıdır; fark yalnızca sözdizimindedir. Projenizde zaten OpenAI çağrısı varsa, genellikle istemci başlatma satırlarını değiştirip model adını uncensored olarak güncellemeniz yeterlidir. Başka bir arayüzden toplu geçiş için Geçiş kılavuzu sayfasına bakın.
Akış (SSE) nasıl okunur
Uzun metin yazarken veya sohbet arayüzü geliştirirken akış kullanmanız gerekir; yoksa kullanıcılar ilk karakteri görene kadar beklemek zorunda kalır. stream: true ayarlandığında sunucu SSE (Server-Sent Events) ile bloklar halinde veri gönderir; her blok data: {...} satırıdır ve data: [DONE] ile biter. Resmi SDK bu veriyi zaten çözmüştür; siz yalnızca döngü kurmanız yeterlidir.
Akışın sonunda usage bloğu gelir; choices boş dizidir. Parametre gerekmez ama chunk.choices[0] almadan önce boş olup olmadığını kontrol edin.
import os
from openai import OpenAI
client = OpenAI(
base_url="https://api.wuxianzhiapi.com/v1",
api_key=os.environ["WUXIANZHI_API_KEY"],
)
stream = client.chat.completions.create(
model="uncensored",
messages=[{"role": "user", "content": "写一段 200 字左右的悬疑小说开头。"}],
max_tokens=600,
stream=True,
)
usage = None
for chunk in stream:
if chunk.usage: # 最后一块:用量统计
usage = chunk.usage
if not chunk.choices: # 用量块没有 choices
continue
delta = chunk.choices[0].delta.content
if delta:
print(delta, end="", flush=True)
print()
if usage:
print("输入", usage.prompt_tokens, "输出", usage.completion_tokens)import OpenAI from "openai";
const client = new OpenAI({
baseURL: "https://api.wuxianzhiapi.com/v1",
apiKey: process.env.WUXIANZHI_API_KEY,
});
const stream = await client.chat.completions.create({
model: "uncensored",
messages: [{ role: "user", content: "写一段 200 字左右的悬疑小说开头。" }],
max_tokens: 600,
stream: true,
});
let usage = null;
for await (const chunk of stream) {
if (chunk.usage) usage = chunk.usage;
const delta = chunk.choices?.[0]?.delta?.content;
if (delta) process.stdout.write(delta);
}
console.log("\n用量:", usage);Ham SSE verilerini görmek için cURL'de -N parametresi ile çıktı tamponlamasını kapatın; böylece her blok geldiğinde hemen yazdırılır. Vekil sunucu veya ağ geçidinin akış yanıtını yutup yutmadığını hata ayıklarken faydalı olur.
curl -N https://api.wuxianzhiapi.com/v1/chat/completions \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $WUXIANZHI_API_KEY" \
-d '{"model":"uncensored","stream":true,"max_tokens":100,
"messages":[{"role":"user","content":"数到五。"}]}'Nginx gibi ters vekil sunucular arkasında akış yanıtını yönlendiriyorsanız, bu yol için yanıt tamponlamasını kapatmayı unutmayın; yoksa ön yüz tek seferde veri görür, karakter karakter değil.
Fonksiyon çağırma: tools ve araç sonuçlarının döndürülmesi
Fonksiyon çağırma, OpenAI formatını kullanır: İstekte tools ile fonksiyonun adını, açıklamasını ve JSON şema parametrelerini belirtin. Model çağrı yapmaya karar verdiğinde, yanıtın message.tool_calls alanında fonksiyon adını ve parametreleri JSON dizgesi olarak verir. Kodunuz fonksiyonu gerçekten çalıştırmalı ve sonucu role: "tool" mesajı olarak geri göndermelidir. Ardından bir kez daha istek yapın; model sonucu temel alarak nihai cevabı yazar.
tool_choice varsayılan olarak "auto" şeklindedir; model kendi kararını verir. Belirli bir fonksiyonu zorlamak için {"type": "function", "function": {"name": "get_weather"}} iletin. "none" ile çağrıyı tamamen engelleyebilirsiniz. Aşağıdaki örnek tam döngüyü gösterir: İlk istekte tool_calls alınır, yerel fonksiyon çalıştırılır, ikinci istekte araç sonuçları iletilir.
import json, os
from openai import OpenAI
client = OpenAI(
base_url="https://api.wuxianzhiapi.com/v1",
api_key=os.environ["WUXIANZHI_API_KEY"],
)
def get_weather(city: str) -> dict:
# 这里用假数据代替真实的天气接口
return {"city": city, "temp_c": 18, "condition": "多云"}
tools = [{
"type": "function",
"function": {
"name": "get_weather",
"description": "查询指定城市的当前天气",
"parameters": {
"type": "object",
"properties": {"city": {"type": "string", "description": "城市名"}},
"required": ["city"],
},
},
}]
messages = [{"role": "user", "content": "杭州现在天气怎么样?"}]
first = client.chat.completions.create(
model="uncensored", messages=messages, tools=tools, tool_choice="auto", max_tokens=500
)
msg = first.choices[0].message
if msg.tool_calls:
messages.append(msg) # 必须把带 tool_calls 的 assistant 消息原样放回历史
for call in msg.tool_calls:
args = json.loads(call.function.arguments)
result = get_weather(**args)
messages.append({
"role": "tool",
"tool_call_id": call.id,
"content": json.dumps(result, ensure_ascii=False),
})
final = client.chat.completions.create(
model="uncensored", messages=messages, tools=tools, max_tokens=500
)
print(final.choices[0].message.content)
else:
print(msg.content)Üç yaygın hata şunlardır: Birincisi, asistanın tool_calls mesajlarını geçmişe eklemeyi unutup tool mesajını doğrudan eklemek; bu istek formatını geçersiz kılar. İkincisi, tool_call_id eşleşmez. Üçüncüsü, modelin döndürdüğü parametreler dizge olduğundan önce json.loads ile ayrıştırılmalı ve hata durumları için yedek mekanizma kurulmalıdır; model çıktısını doğrudan komut veya SQL'e eklemeyin. Node.js akışı tamamen aynıdır; aşağıda eşdeğer kod yer almaktadır.
import OpenAI from "openai";
const client = new OpenAI({
baseURL: "https://api.wuxianzhiapi.com/v1",
apiKey: process.env.WUXIANZHI_API_KEY,
});
const getWeather = (city) => ({ city, temp_c: 18, condition: "多云" });
const tools = [{
type: "function",
function: {
name: "get_weather",
description: "查询指定城市的当前天气",
parameters: {
type: "object",
properties: { city: { type: "string", description: "城市名" } },
required: ["city"],
},
},
}];
const messages = [{ role: "user", content: "杭州现在天气怎么样?" }];
const first = await client.chat.completions.create({
model: "uncensored", messages, tools, tool_choice: "auto", max_tokens: 500,
});
const msg = first.choices[0].message;
if (msg.tool_calls?.length) {
messages.push(msg);
for (const call of msg.tool_calls) {
const args = JSON.parse(call.function.arguments);
messages.push({
role: "tool",
tool_call_id: call.id,
content: JSON.stringify(getWeather(args.city)),
});
}
const final = await client.chat.completions.create({
model: "uncensored", messages, tools, max_tokens: 500,
});
console.log(final.choices[0].message.content);
} else {
console.log(msg.content);
}
Hata işleme ve yeniden deneme: 429 ve 503 nasıl üstelemeli geri çekilir
Hata yanıtı her zaman standart JSON şeklindedir: {"error":{"code":...,"message":...}}. Programınızda yeniden deneme yapmanız gereken yalnızca iki hata türü vardır: 429 (dakikada 300 istek sınırını aşma) ve 503 (upstream_busy, model geçişli olarak meşul, birkaç saniye sonra tekrar deneyin). Ağ katmanı bağlantı zaman aşımı da yeniden denemeye değerdir. Diğer hatalarda yeniden denemenin anlamı yoktur: 400 istek kendisiyle ilgilidir (örneğin isteme max_tokens eklenerek 100k'ı aşmak), 401 anahtarın geçersiz olduğunu, 402 no_credit bakiyenin bittiğini veya denemenin süresinin dolduğunu, 403 content_blocked içeriğin engellendiğini gösterir; yüz kez yeniden göndermek sonucu değiştirmez.
Geri çekilme stratejisi olarak üstelemeli artış ve rastgele titreşim kullanın: 1. denemede yaklaşık 1 saniye, 2. denemede 2 saniye, 3. denemede 4 saniye bekleyin; bir üst sınır ve maksimum deneme sayısı belirleyin. Bu, eşzamanlı birden fazla görevin aynı anda yeniden denemesini ve hız limitini aşmasını engeller. Resmi SDK'da max_retries vardır; varsayılan olarak 429 ve 5xx için birkaç kez yeniden dener. Basit senaryolarda bu değeri artırmak yeterlidir; günlük kaydı, devre kesme veya özel bekleme süreleri gerekiyorsa kendi döngünüzü yazın.
import os, random, time
import openai
from openai import OpenAI
# max_retries=0:关闭 SDK 自带重试,完全由下面的函数控制
client = OpenAI(
base_url="https://api.wuxianzhiapi.com/v1",
api_key=os.environ["WUXIANZHI_API_KEY"],
max_retries=0,
timeout=60,
)
def chat_with_retry(messages, max_attempts=5, **kwargs):
for attempt in range(max_attempts):
try:
return client.chat.completions.create(
model="uncensored", messages=messages, **kwargs
)
except (openai.RateLimitError, openai.InternalServerError,
openai.APIConnectionError, openai.APITimeoutError) as e:
if attempt == max_attempts - 1:
raise
wait = min(30, 2 ** attempt) + random.uniform(0, 1)
print(f"{type(e).__name__},{wait:.1f} 秒后重试(第 {attempt + 1} 次)")
time.sleep(wait)
except openai.APIStatusError as e:
# 400 / 401 / 402 / 403 / 404:重试无效,直接交给上层处理
print("不可重试:", e.status_code, e.response.text)
raise
resp = chat_with_retry([{"role": "user", "content": "你好"}], max_tokens=100)
print(resp.choices[0].message.content)Node.js'de de doğrudan maxRetries değerini artırabilirsiniz; SDK 429 ve 5xx hatalarını geri çekilme stratejisine göre işler. Hataları ayırt etmeniz gerekiyorsa error.status ile kontrol yapabilirsiniz.
import OpenAI from "openai";
const client = new OpenAI({
baseURL: "https://api.wuxianzhiapi.com/v1",
apiKey: process.env.WUXIANZHI_API_KEY,
maxRetries: 5,
timeout: 60_000,
});
try {
const resp = await client.chat.completions.create({
model: "uncensored",
messages: [{ role: "user", content: "你好" }],
max_tokens: 100,
});
console.log(resp.choices[0].message.content);
} catch (err) {
if (err instanceof OpenAI.APIError) {
if (err.status === 402) console.error("余额不足,请充值后再试");
else if (err.status === 403) console.error("内容被拦截:", err.message);
else console.error("请求失败:", err.status, err.message);
} else {
throw err;
}
}Bir uyarı daha: Akış istekleri sırasında bağlantı koparsa, zaten alınan verileri kendiniz saklayın. Yeniden deneme baştan başlayacak ve yeniden faturalandırılacaktır. Bu nedenle uzun metin üretimi için tek seferde büyük bir istek yerine bölümler halinde istek göndermeniz önerilir.
Maliyeti ve uzunluğu max_tokens ile kontrol etme
Faturalandırma kuralları basittir: Giriş $0.25 / milyon token, Çıkış $1.00 / milyon token. Ön ödemeli bakiye kullanılır, aylık ücret yoktur; bakiye never expires. Çıkış birimi giriş biriminin 4 katı olduğundan, tasarruf etmek için çıkışta tasarruf etmelisiniz. max_tokens varsayılan olarak 2048'dir; tek bir istekte maksimum 32,000'e kadar ayarlanabilir. Sadece kısa yanıtlar gerekiyorsa bunu 200 veya 300 olarak belirterek modelin gereğinden fazla konuşmasını önleyin ve tek bir istek için maliyet sınırını belirleyin.
Bir hesap yapalım: Bir istekte max_tokens 1.000 olarak ayarlanırsa, en kötü durumda çıktı maliyeti $0.001 olur; üst sınıra, 32.000'e ayarlanırsa en kötü durum $0.016'dır. $0.50 deneme kredisi yaklaşık 500.000 çıktı token veya 2.000.000 girdi token'a denk gelir; bu sayfadaki tüm örnekleri birçok kez çalıştırmak için yeterlidir. İstem ile max_tokens toplamının 100.000'i geçmemesi gerektiğini unutmayın; aksi halde doğrudan 400 hatası döner. Bu nedenle girdi uzunsa çıktı üst sınırını düşürün. Detaylı fiyatlandırma Fiyatlandırma sayfasında yer almaktadır.
Başka bir detay: Yanıt kesilirse, yanıtta finish_reason alanı "length" olarak döner; bu, modelin bitirmediğini, aksine max_tokens yetersiz kaldığını gösterir. Uzun metin yazarken bu alanı kontrol edip devam edip etmeyeceğinize karar verebilirsiniz.
Çoklu konuşma: Bağlamı kendiniz yönetme
Arayüz durum bilgisi taşımaz; sunucu önceki isteği hatırlamaz. Modelin konuşmaya devam etmesini sağlamak için her seferinde tüm geçmiş mesajları sırayla yeniden göndermeniz gerekir: önce system, ardından user ve assistant sırayla. Bu, her eklenen konuşma döngüsünde girdi token sayısının artacağı ve maliyetin kümülatif olarak artacağı anlamına gelir. Konuşma ilerledikçe her döngünün girdi maliyeti öncekilere göre daha yüksek olacaktır.
Bağlam toplamı 100.000 token ile sınırlıdır (bu istek için çıkış dahil). Bu nedenle uzun diyaloglar kesilmelidir. En basit yöntem system mesajını ve son birkaç dönüşü korumaktır. Daha karmaşık bir yaklaşımda, daha eski içerikler bir istek kullanılarak özetlenip system mesajına eklenebilir. Aşağıdaki sınıf, geçmişi kaydetmek ve mesaj sayısına göre kesmek için gereken mantığı kapsar; doğrudan sohbet hizmetinize ekleyebilirsiniz.
import os
from openai import OpenAI
client = OpenAI(
base_url="https://api.wuxianzhiapi.com/v1",
api_key=os.environ["WUXIANZHI_API_KEY"],
)
class Chat:
def __init__(self, system: str, keep_last: int = 20):
self.system = {"role": "system", "content": system}
self.history = [] # 只存 user / assistant 消息
self.keep_last = keep_last
def say(self, text: str, max_tokens: int = 500) -> str:
self.history.append({"role": "user", "content": text})
recent = self.history[-self.keep_last:]
resp = client.chat.completions.create(
model="uncensored",
messages=[self.system] + recent,
max_tokens=max_tokens,
)
reply = resp.choices[0].message.content
self.history.append({"role": "assistant", "content": reply})
return reply
bot = Chat("你是一位说话简短的旅行顾问。")
print(bot.say("我想去云南玩五天,有什么建议?"))
print(bot.say("刚才说的第二个地方,适合带老人吗?")) # 能接上上一轮Mesaj sayısına göre kırpma yetersizdir. usage.prompt_tokens ile takip edin; 50.000'e yaklaştığında geçmiş mesajları proaktif olarak sıkıştırın. use cases.
Sıkça Sorulan Sorular
Son akış veri bloğu neden boş?
Bu, otomatik olarak eklenen kullanım istatistikleri bloğudur; choices boş bir dizi içerir ve usage token sayısını içerir. Okurken choices'un boş olup olmadığını kontrol edin, ardından delta'yı alın; ek parametre göndermenize gerek yoktur.
429 ve 503 hatalarında yeniden deneme yapılmalı mı? Ne kadar beklenmeli?
Yeniden denemeye değer hatalar şunlardır: 429 dakikada 300 istek sınırını aşma anlamına gelir; 503'ün upstream_busy hatası modelin geç olarak meşgul olduğunu gösterir. 1 saniye başlangıç süresiyle üssel geri çekilme ve rastgele gürültü önerilir. Maksimum deneme sayısını belirleyin ve sonsuz denemeden kaçının.
Fonksiyon çağırma sırasında model tool_calls döndürmüyorsa ne yapmalı?
Bu, modelin çağrı yapmaya gerek olmadığını düşündüğü anlamına gelir; bu durumda message.content nihai cevaptır. Zorunlu olarak çağrı yapmak istiyorsanız, tool_choice'u belirli bir fonksiyon olarak ayarlayın ve fonksiyon açıklaması ile parametre şemasının net yazılıp yazılmadığını kontrol edin.
Çoklu konuşma döngüleri maliyeti artırır mı?
Evet. API stateless (durumsuz) olduğu için her seferinde tüm geçmiş yeniden gönderilir; bu nedenle girdi tokenları döngü sayısıyla artar. Sadece son birkaç döngüyü koruyabilir veya eski içerikleri özetleyerek sıkıştırabilirsiniz. Ayrıca çıktıyı max_tokens ile sınırlayın.
Anahtarınızı almak için formu doldurun
Hesap oluşturun, anahtarınızı kopyalayın ve Base URL'i değiştirin. Yapılandırma bu kadar kolay.
API anahtarını al