Quay lại blog

API & SDKHướng dẫn

Yêu cầu đầu tiên bằng C# với openai-dotnet: endpoint, key, câu trả lời

Gửi chat completion đầu tiên từ ứng dụng console C#: đặt Endpoint trong thư viện OpenAI .NET chính thức, đọc key từ env, in câu trả lời và lý do kết thúc.

Bởi CheapTokens TeamĐã xuất bản 5 phút đọc

Ảnh bìa: C# và thư viện OpenAI .NET kết nối đến endpoint CheapTokens
Trên trang này
  1. Bạn cần gì
  2. Xây dựng ứng dụng console
  3. Mã, từng dòng một
  4. Bạn sẽ thấy gì
  5. Chuyển đổi một dịch vụ hiện có
  6. Một yêu cầu tốn bao nhiêu
  7. Nếu nó không hoạt động

Để gửi một yêu cầu từ C# đến CheapTokens, hãy giữ thư viện OpenAI chính thức cho .NET và đặt OpenAIClientOptions.Endpoint thành https://api.cheaptokens.dev/v1. Truyền id model đầy đủ, ví dụ deepseek-ai/DeepSeek-V4-Flash-0731, và đọc key từ biến môi trường. Các lệnh gọi ChatClient và CompleteChat giữ nguyên như trong các ví dụ của OpenAI.

Giả sử bạn đã có một dịch vụ ASP.NET đang nói chuyện với OpenAI, và bạn muốn thử một endpoint và model khác mà không động đến phần còn lại của mã. Trước khi nối bất cứ thứ gì vào đó, hãy kiểm tra ba thứ thường gây lỗi (key, endpoint, id model) trong một ứng dụng console nhỏ. Đó là thứ chúng ta xây dựng ở đây. Các chi tiết bên dưới lấy từ README của thư viện trên GitHub (openai/openai-dotnet, kiểm tra ngày 5 tháng 11 năm 2026) và từ tài liệu CheapTokens: trang tài liệu có cùng base URL.

Bạn cần gì#

Gói này có tên là OpenAI trên NuGet. Phiên bản ổn định mới nhất tính đến ngày 5 tháng 11 năm 2026 là 2.15.0 (mục changelog của nó ghi ngày 4 tháng 11). Nó nhắm đến .NET 8 và .NET Standard 2.0, và README nói nó hoạt động với mọi ứng dụng .NET Standard 2.0, nên một dự án cũ hơn cũng ổn.

Ba giá trị được đưa vào ứng dụng:

  • base URL: https://api.cheaptokens.dev/v1 (tương thích OpenAI Chat Completions);
  • id model: deepseek-ai/DeepSeek-V4-Flash-0731. Dùng id đầy đủ, tên viết tắt từ bảng giá sẽ không được chấp nhận. DeepSeek-V4-Flash có cửa sổ ngữ cảnh 380K và tối đa 32.768 token đầu ra mỗi câu trả lời, một mức giá bất kể thời điểm nào trong ngày;
  • một API key từ tài khoản CheapTokens của bạn, được giữ trong biến môi trường. Nếu bạn không chắc cách lưu nó, hãy đọc cách lưu trữ API key an toàn.

Xây dựng ứng dụng console#

Từng bước một

Tạo dự án và chạy nó

Tạo dự án console

bash
dotnet new console -o FirstRequest
cd FirstRequest

Thêm gói

bash
dotnet add package OpenAI

Đặt key vào biến môi trường

Trong bash hoặc zsh:

bash
export CHEAPTOKENS_API_KEY=your-key

Trong Windows PowerShell:

powershell
$env:CHEAPTOKENS_API_KEY = "your-key"

Dán mã và chạy

Thay nội dung của Program.cs bằng mã ở phần tiếp theo, sau đó chạy dotnet run.

Terminal với năm lệnh tạo và chạy ứng dụng console
Năm lệnh: tạo dự án, vào thư mục, thêm gói, đặt key, chạy.

Mã, từng dòng một#

csharp
using System.ClientModel;
using OpenAI;
using OpenAI.Chat;

string? apiKey = Environment.GetEnvironmentVariable("CHEAPTOKENS_API_KEY");
if (string.IsNullOrEmpty(apiKey))
{
    Console.WriteLine("Set CHEAPTOKENS_API_KEY first.");
    return;
}

ChatClient client = new(
    model: "deepseek-ai/DeepSeek-V4-Flash-0731",
    credential: new ApiKeyCredential(apiKey),
    options: new OpenAIClientOptions
    {
        Endpoint = new Uri("https://api.cheaptokens.dev/v1")
    });

ChatCompletion completion = client.CompleteChat("Explain in two sentences what a token is.");

Console.WriteLine(completion.Content[0].Text);
Console.WriteLine($"finish_reason: {completion.FinishReason}");

README trình bày mẫu này cho "một proxy hoặc một LLM tự lưu trữ tương thích OpenAI": endpoint được đưa vào OpenAIClientOptions, key vào một ApiKeyCredential (nó nằm trong System.ClientModel, do đó có using đầu tiên). Phần kiểm tra ở đầu là của chúng ta: nó đưa ra thông báo rõ ràng nếu biến chưa được đặt.

CompleteChat với một chuỗi thuần gửi một tin nhắn người dùng và chờ toàn bộ câu trả lời. Văn bản trả lời nằm trong completion.Content[0].Text. Lý do kết thúc nằm trong completion.FinishReason.

Luồng: key từ env, ChatClient với Endpoint, CompleteChat, văn bản và FinishReason
Điều gì xảy ra trong chương trình từ key đến câu trả lời được in ra.

Bạn sẽ thấy gì#

Bạn sẽ nhận được một lời giải thích ngắn về token và một dòng với lý do kết thúc; sau một kết thúc bình thường nó là Stop (README so sánh FinishReason với ChatFinishReason.Stop). Cách diễn đạt của câu trả lời thay đổi theo từng lần chạy.

Dòng thứ hai là dòng đáng đọc. README so sánh FinishReason với ChatFinishReason.Stop (model tự kết thúc) và ChatFinishReason.ToolCalls (model muốn gọi một công cụ). Bất cứ thứ gì khác Stop trong một cuộc trò chuyện thông thường có nghĩa là câu trả lời kết thúc vì lý do khác, và nghi phạm thường gặp là giới hạn độ dài. Nếu bạn thấy một câu trả lời dừng giữa câu, bài viết này giải thích finish_reason và max_tokens.

Chuyển đổi một dịch vụ hiện có#

Nếu dịch vụ của bạn đã tạo một ChatClient cho OpenAI, bạn thay đổi hai thứ: chuỗi model và các tùy chọn. Phần còn lại của các lệnh gọi vẫn hoạt động.

So sánh

Cùng client, hai dòng thay đổi

Trước

csharp
ChatClient client = new(
    model: "your-current-model",
    credential: new ApiKeyCredential(apiKey));

Sau

csharp
ChatClient client = new(
    model: "deepseek-ai/DeepSeek-V4-Flash-0731",
    credential: new ApiKeyCredential(apiKey),
    options: new OpenAIClientOptions
    {
        Endpoint = new Uri("https://api.cheaptokens.dev/v1")
    });

Với các yêu cầu ngắn có một lựa chọn thứ hai: zai-org/GLM-5.3-Flash (ngữ cảnh 390K, tối đa 8.192 token đầu ra). Bạn chỉ thay đổi chuỗi model. Danh sách các id mà key của bạn có thể dùng chỉ cách một yêu cầu, xem Liệt kê model với GET /v1/models.

Một yêu cầu tốn bao nhiêu#

Giả sử một dịch vụ xử lý 1.000 yêu cầu mỗi ngày, mỗi yêu cầu khoảng 300 token vào và 400 token ra. Một yêu cầu như vậy tốn $0.000045 trên DeepSeek-V4-Flash. Bảng bên dưới hiển thị cùng 1.000 yêu cầu trên cả ba model bên cạnh OpenRouter. Tổng cộng, khi tính cả đầu vào và đầu ra, DeepSeek-V4-Flash rẻ hơn OpenRouter. Giá hiện tại nằm trên trang giá, và trang DeepSeek liệt kê những gì model cung cấp.

Mô hình Mỗi yêu cầu 1.000 yêu cầu OpenRouter, 1.000 yêu cầu
GLM-5.3-Flash $0.000022 $0.022 $0.0433
DeepSeek-V4-Flash $0.000045 $0.0445 $0.077
MiniMax-M2.7 $0.000075 $0.075 $0.90

300 token đầu vào và 400 token đầu ra mỗi yêu cầu. Giá trên 1 triệu token là giá hiện hành và thay đổi cùng với biểu phí của chúng tôi; cột OpenRouter hiển thị giá tham chiếu cho cùng khối lượng công việc.

Nếu nó không hoạt động#

  • 401. Key bị thiếu hoặc sai. In ra xem biến có được đặt không (phần kiểm tra trong mã làm việc này) và đảm bảo dotnet run được khởi động trong cùng terminal nơi bạn đã chạy export (hoặc $env:): biến chỉ tồn tại trong phiên đó.
  • 404. Thường gặp nhất là id model: một tên viết tắt thay vì deepseek-ai/DeepSeek-V4-Flash-0731 đầy đủ, hoặc một endpoint không có /v1 (cũng kiểm tra rằng OpenAIClientOptions thực sự được truyền vào ChatClient). Chi tiết có trong API 401 hoặc 404: sai key, base URL hoặc id model.
  • lỗi CS0246: Không tìm thấy kiểu hoặc tên không gian tên 'ApiKeyCredential'. Dòng using System.ClientModel; bị thiếu ở đầu Program.cs.

Cùng ý tưởng trong ngôn ngữ khác: phiên bản Go với openai-go.