Quay lại blog
Maven coordinates for the PolyLingo Java SDK alongside a short Java client setup snippet.

Dịch nội dung có cấu trúc từ Java với PolyLingo SDK

By Robert

Dịch nội dung có cấu trúc từ Java với PolyLingo SDK

PolyLingo Java SDK hiện đã có trên Maven Central. Nó bao phủ toàn bộ PolyLingo API: dịch đồng bộ, yêu cầu theo lô, công việc bất đồng bộ với việc kiểm tra trạng thái, và tất cả các điểm cuối tiện ích. Yêu cầu Java 11 trở lên, sử dụng HTTP client thư viện chuẩn, và chỉ có một phụ thuộc runtime duy nhất: Jackson cho JSON.


Cài đặt

Maven

<dependency>
  <groupId>com.usepolylingo</groupId>
  <artifactId>polylingo</artifactId>
  <version>0.1.0</version>
</dependency>

Gradle

implementation 'com.usepolylingo:polylingo:0.1.0'

Không cần phụ thuộc HTTP client bổ sung. SDK sử dụng java.net.http.HttpClient từ thư viện chuẩn Java 11.


Thiết lập client

import com.usepolylingo.polylingo.PolyLingo;

PolyLingo client = PolyLingo.builder()
    .apiKey(System.getenv("POLYLINGO_API_KEY"))
    .build();

Có hai tham số builder tùy chọn:

PolyLingo client = PolyLingo.builder()
    .apiKey(System.getenv("POLYLINGO_API_KEY"))
    .baseUrl("https://api.usepolylingo.com/v1") // mặc định, ghi đè cho các instance tự lưu trữ
    .timeout(Duration.ofSeconds(30))            // mặc định là 120 giây
    .build();

Giữ khóa API của bạn trong biến môi trường. Không bao giờ mã hóa cứng hoặc commit vào hệ thống kiểm soát phiên bản.

SDK sử dụng pattern builder xuyên suốt. Không có constructor vị trí, không có thứ tự trường bắt buộc. Tất cả các trường tùy chọn đều có giá trị mặc định hợp lý nên bạn chỉ cấu hình những gì thực sự cần thay đổi.


Dịch nội dung

Yêu cầu đơn lẻ

import com.usepolylingo.polylingo.types.TranslateParams;
import com.usepolylingo.polylingo.types.TranslateResult;

TranslateResult result = client.translate(
    TranslateParams.builder()
        .content("Hello, world!")
        .targets(List.of("es", "fr", "de"))
        .build()
);

result.getTranslations().forEach((lang, text) ->
    System.out.println(lang + ": " + text)
);
// es: ¡Hola, mundo!
// fr: Bonjour le monde !
// de: Hallo Welt!

Builder TranslateParams chấp nhận contenttargets là các trường bắt buộc. Các tham số tùy chọn bao gồm format (plain, markdown, json hoặc html — tự động phát hiện nếu bỏ qua), source như gợi ý ngôn ngữ, và modelstandard (mặc định) hoặc advanced.

Việc bảo toàn định dạng hoạt động giống như phần còn lại của PolyLingo API. Với nội dung json, chỉ các giá trị chuỗi được dịch còn khóa, cấu trúc lồng nhau và các kiểu không phải chuỗi được giữ nguyên. Với markdown, các tiêu đề vẫn là tiêu đề và các khối mã được giữ nguyên. Với html, các thẻ và thuộc tính được bảo toàn và chỉ các nút văn bản được dịch.

Dịch file locale JSON

import com.fasterxml.jackson.databind.ObjectMapper;
import java.nio.file.Files;
import java.nio.file.Path;

ObjectMapper mapper = new ObjectMapper();
String sourceJson = Files.readString(Path.of("messages/en.json"));

TranslateResult result = client.translate(
    TranslateParams.builder()
        .content(sourceJson)
        .format("json")
        .targets(List.of("fr", "de", "ja"))
        .build()
);

result.getTranslations().forEach((locale, translated) -> {
    try {
        Object parsed = mapper.readValue(translated, Object.class);
        String pretty = mapper.writerWithDefaultPrettyPrinter().writeValueAsString(parsed);
        Files.writeString(Path.of("messages/" + locale + ".json"), pretty);
        System.out.println("Wrote messages/" + locale + ".json");
    } catch (Exception e) {
        throw new RuntimeException(e);
    }
});

Một yêu cầu xử lý cả ba locale. Các khóa giống hệt với nguồn trong mọi file đầu ra.


Yêu cầu theo lô

Gửi tối đa 100 mục nội dung trong một yêu cầu, mỗi mục có id riêng và format tùy chọn:

import com.usepolylingo.polylingo.types.BatchParams;
import com.usepolylingo.polylingo.types.BatchItem;
import com.usepolylingo.polylingo.types.BatchResult;

BatchResult result = client.batch(
    BatchParams.builder()
        .targets(List.of("es", "ja"))
        .addItem(BatchItem.builder().id("title").content("Welcome").build())
        .addItem(BatchItem.builder().id("body").content("Get started today.").build())
        .build()
);

for (BatchItemResult item : result.getResults()) {
    System.out.println(item.getId() + ": " + item.getTranslations());
}

Tất cả các mục chia sẻ cùng danh sách targets. id bạn gán được giữ nguyên trong phản hồi để bạn có thể ánh xạ kết quả trở lại dữ liệu nguồn mà không phụ thuộc vào thứ tự.


Công việc bất đồng bộ

Đối với tài liệu dài hoặc khối lượng công việc dịch lớn, API công việc nhận yêu cầu, trả về ngay ID công việc và cho phép bạn kiểm tra kết quả. SDK xử lý theo hai cách.

Một lần gọi kiểm tra đến khi xong

import com.usepolylingo.polylingo.types.JobsTranslateParams;

TranslateResult result = client.jobs().translate(
    JobsTranslateParams.builder()
        .content(longArticleText)
        .targets(List.of("fr", "de", "ja", "zh"))
        .pollInterval(Duration.ofSeconds(3))
        .timeout(Duration.ofMinutes(10))
        .onProgress(queuePosition ->
            System.out.println("Queue position: " + queuePosition))
        .build()
);

result.getTranslations().forEach((lang, text) ->
    System.out.println(lang + ": " + text.substring(0, 100) + "...")
);

Callback onProgress được gọi mỗi lần kiểm tra với vị trí hàng đợi hiện tại dưới dạng số nguyên, hoặc null nếu API không trả về. Dùng để ghi log tiến trình hoặc cập nhật giao diện người dùng.

Đưa vào hàng đợi và kiểm tra thủ công

import com.usepolylingo.polylingo.types.CreateJobParams;
import com.usepolylingo.polylingo.types.Job;

Job job = client.jobs().create(
    CreateJobParams.builder()
        .content("Translate this.")
        .targets(List.of("es"))
        .build()
);

// Tự kiểm tra
Job status = client.jobs().get(job.getJobId());
System.out.println(status.getStatus()); // pending / processing / completed / failed

Điểm cuối tiện ích

// Kiểm tra sức khỏe API (không cần khóa API)
HealthResponse health = client.health();
System.out.println(health.getStatus()); // "ok"

// Liệt kê các ngôn ngữ được hỗ trợ (không cần khóa API)
LanguagesResponse langs = client.languages();
langs.getLanguages().forEach(l ->
    System.out.println(l.getCode() + " — " + l.getName())
);

// Kiểm tra sử dụng token cho tháng thanh toán hiện tại
UsageResponse usage = client.usage();
System.out.println("Tokens used: " + usage.getUsage().getTokensUsed());
System.out.println("Tokens remaining: " + usage.getUsage().getTokensRemaining());

Xử lý lỗi

Tất cả ngoại lệ đều unchecked. Không có khai báo throws bắt buộc, không có chuỗi ngoại lệ checked cần xử lý:

import com.usepolylingo.polylingo.errors.*;

try {
    TranslateResult result = client.translate(
        TranslateParams.builder()
            .content("# Hello")
            .targets(List.of("es", "fr"))
            .format("markdown")
            .build()
    );
} catch (AuthException e) {
    // HTTP 401 — khóa API không hợp lệ, thiếu hoặc bị thu hồi
    System.out.println("Auth failed: " + e.getError());
} catch (RateLimitException e) {
    // HTTP 429 — đạt giới hạn mỗi phút
    e.getRetryAfter().ifPresent(s ->
        System.out.println("Retry after: " + s + "s")
    );
} catch (JobFailedException e) {
    // Công việc bất đồng bộ đạt trạng thái lỗi hoặc hết thời gian kiểm tra
    System.out.println("Job " + e.getJobId() + " failed: " + e.getError());
} catch (PolyLingoException e) {
    // Tất cả lỗi API khác
    System.out.println(e.getStatus() + ": " + e.getMessage());
}

RateLimitException.getRetryAfter() trả về Optional<Integer> — có giá trị là số giây cần chờ nếu API bao gồm giá trị đó, ngược lại là rỗng. JobFailedException.getJobId() cung cấp ID công việc thất bại để ghi log hoặc logic thử lại.


Ghi chú thiết kế

Một vài quyết định đáng biết nếu bạn đang đánh giá SDK:

API đồng bộ. Mỗi phương thức chặn và trả về kết quả trực tiếp. Không có Future, CompletableFuture, hay luồng phản ứng. Việc kiểm tra công việc là câu chuyện bất đồng bộ của SDK cho khối lượng công việc nặng — gửi công việc, SDK kiểm tra trên luồng của bạn và gọi callback onProgress khi vị trí hàng đợi cập nhật.

Pattern builder xuyên suốt. Mỗi đối tượng tham số sử dụng builder. Không có constructor vị trí nghĩa là không phải đoán thứ tự đối số, không bị hoán đổi trường vô tình, và mã rõ ràng tại điểm gọi.

Một phụ thuộc runtime duy nhất. Jackson cho tuần tự hóa JSON. Mọi thứ khác là thư viện chuẩn. Không có OkHttp, Apache HttpClient, Guava.

Java 11+. Sử dụng java.net.http.HttpClient được giới thiệu trong Java 11. Nếu dự án của bạn nhắm tới Java 8 hoặc cũ hơn thì SDK không tương thích.


Tham khảo nhanh

Phương thứcĐiểm cuốiCần xác thực
client.health()GET /healthKhông
client.languages()GET /languagesKhông
client.translate(...)POST /translate
client.batch(...)POST /translate/batch
client.usage()GET /usage
client.jobs().create(...)POST /jobs
client.jobs().get(jobId)GET /jobs/:id
client.jobs().translate(...)POST /jobs + polling

Bắt đầu

SDK có trên Maven Central tại central.sonatype.com/artifact/com.usepolylingo/polylingo. Mã nguồn và Javadoc tại github.com/UsePolyLingo/polylingo-Java. Tài liệu API đầy đủ tại usepolylingo.com/docs/sdk/java.

Gói miễn phí bao gồm 50.000 token mỗi tháng. Không cần thẻ tín dụng.

<dependency>
  <groupId>com.usepolylingo</groupId>
  <artifactId>polylingo</artifactId>
  <version>0.1.0</version>
</dependency>

Nhận khóa API của bạn