A modern, feature-rich Java client for the LibreTranslate API with advanced capabilities including rate limiting, caching, and comprehensive monitoring. Compatible with JDK-17+.
- Synchronous & Asynchronous Translation - Flexible translation modes to suit different application needs
- Smart Adaptive Rate Limiting - Automatically adjusts request rates based on API responses
- Configurable Translation Cache - Reduces API calls for frequently translated text
- Comprehensive Metrics Monitoring - Track performance with detailed statistics
- Resource Management - Full
AutoCloseable
support for proper cleanup - Command Processing - Process translation commands individually with flexible operation modes
- Modular Architecture - Clean separation of concerns with well-defined interfaces
com.vidigal.code.libretranslate
├── cache - Caching implementation for translations
├── client - Core client implementation
├── config - Configuration classes
├── exception - Translation-specific exceptions
├── http - HTTP request handling
├── language - Language code utilities
├── ratelimit - Rate limiting implementation
├── service - Service interfaces and factories
└── util - Common utility classes
Test - 1
Test - 2
// Create a translator service with API URL and optional key
try (TranslatorService translator = Translators.create("https://libretranslate.com", "your-api-key")) {
// Translate with automatic language detection
String result = translator.translate("Hello world", "pt");
System.out.println("Translated text: " + result);
// Translate with specified source language
String resultWithSource = translator.translate("Hello world", "en", "es");
System.out.println("Translated to Spanish: " + resultWithSource);
}
try (TranslatorService translator = Translators.create("https://libretranslate.com", "your-api-key")) {
// Perform an asynchronous translation
CompletableFuture<String> future = translator.translateAsync("Hello world", "fr");
// Handle the result when it completes
future
.thenAccept(text -> System.out.println("Translation: " + text))
.exceptionally(ex -> {
System.err.println("Translation failed: " + ex.getMessage());
return null;
});
// Wait for completion if needed
future.join();
}
// Create a custom configuration
LibreTranslateConfig config = LibreTranslateConfig.builder()
.apiUrl("https://libretranslate.com")
.apiKey("your-api-key")
.connectionTimeout(5000) // Connection timeout in ms
.socketTimeout(10000) // Socket timeout in ms
.maxRequestsPerSecond(10) // Rate limit
.maxRetries(3) // Retry count for failures
.rateLimitCooldown(5000) // Cooldown after hitting rate limits
.enableRetry(true) // Enable automatic retries
.build();
// Create translator with custom config
TranslatorService translator = Translators.create(config);
The library provides a flexible command processing system for handling translation operations:
// Commands follow a specific format
List<String> commands = List.of(
"m:s;t:Hello;en;es", // Synchronous mode (s)
"m:as;t:World;en;pt", // Asynchronous mode (as)
"t:Thank you;en;ja" // Default mode (implicit synchronous)
);
// Process commands (commands are processed individually)
List<String> results = translator.processCommands(commands, true);
results.forEach(System.out::println);
// Access metrics programmatically
System.out.println("Cache Hits: " + translator.getCacheHits());
System.out.println("Cache Misses: " + translator.getCacheMisses());
// Calculate cache hit ratio
double hitRatio = (double) translator.getCacheHits() / (translator.getCacheHits() + translator.getCacheMisses());
System.out.printf("Cache Hit Ratio: %.2f%%\n", hitRatio * 100);
The library uses TranslationException
for error conditions:
try {
String result = translator.translate("Hello", "invalid-language-code", "es");
} catch (TranslationException e) {
System.err.println("Translation failed: " + e.getMessage());
// Handle specific error conditions
}
public static void main(String[] args) throws Exception {
// Create a TranslatorService instance with the API URL and API Key
TranslatorService translator = Translators.create(API, KEY);
// Define a list of commands for batch processing
List<String> commands = Arrays.asList(
"m:s;t:Hello;en;pt", // Synchronous translation of "Hello" from English (en) to Portuguese (pt)
"t:World;pt", // Translate "World" to Portuguese (pt)
"t:Hello;en;pt", // Translate "Hello" en (English) to Portuguese (pt)
"m:as;t:Goodbye;en;es" // Asynchronous translation of "Goodbye" from English (en) to Spanish (es)
);
// Process the commands and print the results
System.out.println(translator.processCommands(commands, false));
// Perform a simple synchronous translation
String result = translator.translate("Hello world", "pt");
System.out.println("Translated text: " + result);
// Perform a synchronous translation with a specified source language
String resultWithSource = translator.translate("Hello world", "en", "es");
System.out.println("Translated to Spanish: " + resultWithSource);
// Perform an asynchronous translation
CompletableFuture<String> translationFuture = translator.translateAsync("Hello world", "en", "fr");
// Handle the asynchronous result
translationFuture
.thenAccept(text -> {
System.out.println("Translation: " + text);
})
.exceptionally(ex -> {
System.err.println("Translation failed: " + ex.getMessage());
return null;
});
// Wait for the asynchronous operation to complete
translationFuture.join();
translator.close();
}
public static void main(String[] args) throws Exception {
// Step 1: Build a custom configuration using LibreTranslateConfig.Builder
LibreTranslateConfig config = LibreTranslateConfig.builder()
.apiUrl(API) // Set the API URL
.apiKey(KEY) // Set the API Key
.rateLimitCooldown(1000) // Rate limit cooldown (100 and 60000)
.connectionTimeout(10000) // Connection timeout in milliseconds
.socketTimeout(15000) // Socket timeout in milliseconds
.maxRetries(5) // Maximum number of retries for failed requests
.build();
// Step 2: Create a TranslatorService instance with the custom configuration
TranslatorService customTranslator = Translators.create(config);
// Step 3: Define a list of commands for batch processing
List<String> commandsCustom = Arrays.asList(
"m:s;t:Hello;en;pt", // Synchronous translation of "Hello" from English (en) to Portuguese (pt)
"t:World;pt", // Translate "World" to Portuguese (pt)
"t:Hello;en;pt", // Translate "Hello" en (English) to Portuguese (pt)
"m:as;t:Goodbye;en;es" // Asynchronous translation of "Goodbye" from English (en) to Spanish (es)
);
// Step 4: Process the commands and print the results
System.out.println("customTranslator: " + customTranslator.processCommands(commandsCustom, false));
// Step 5: Perform a simple synchronous translation
String resultCustom = customTranslator.translate("Hello world", "pt"); // Translate to Portuguese
System.out.println("customTranslator - Translated text: " + resultCustom);
// Step 6: Perform a synchronous translation with a specified source language
String resultWithSourceCustom = customTranslator.translate("Hello world", "en", "es"); // Translate from English to Spanish
System.out.println("customTranslator - Translated to Spanish: " + resultWithSourceCustom);
// Step 7: Perform an asynchronous translation
CompletableFuture<String> translationFutureCustom = customTranslator.translateAsync("Hello world", "en", "fr");
// Handle the asynchronous result
translationFutureCustom
.thenAccept(text -> {
System.out.println("customTranslator - Translation: " + text);
})
.exceptionally(ex -> {
System.err.println("customTranslator - Translation failed: " + ex.getMessage());
return null;
});
// Wait for the asynchronous operation to complete
translationFutureCustom.join();
customTranslator.close();
}
Parameter | Description | Default | Range |
---|---|---|---|
apiUrl |
LibreTranslate API endpoint URL | (Required) | Valid URL |
apiKey |
Authentication key for the API | "" | Any string |
maxRequestsPerSecond |
Maximum requests per second | 10 | 1-1000 |
connectionTimeout |
Connection establishment timeout (ms) | 5000 | > 0 |
socketTimeout |
Socket read timeout (ms) | 10000 | > 0 |
maxRetries |
Maximum retry attempts for failed requests | 3 | ≥ 0 |
rateLimitCooldown |
Cooldown period after hitting rate limits (ms) | 5000 | 100-60000 |
enableRetry |
Whether to automatically retry failed requests | true | true/false |
The library follows these architectural principles:
- Interface-Based Design - All major components are defined by interfaces
- Factory Pattern - Factories provide convenient instance creation
- Builder Pattern - For fluid configuration construction
- Strategy Pattern - Interchangeable algorithm implementations
- Facade Pattern - Simplified API via the
Translators
class
The core interface for translation operations:
public interface TranslatorService extends AutoCloseable {
// Core translation methods
String translate(String text, String targetLanguage);
String translate(String text, String sourceLanguage, String targetLanguage);
// Asynchronous translation methods
CompletableFuture<String> translateAsync(String text, String targetLanguage);
CompletableFuture<String> translateAsync(String text, String sourceLanguage, String targetLanguage);
// Command processing
List<String> processCommands(List<String> commands, boolean log);
// Metrics
int getCacheHits();
int getCacheMisses();
void clearMetrics();
// Resource management (from AutoCloseable)
void close();
}
Factory facade for creating translator services:
public final class Translators {
// Get factory instance
public static TranslatorServiceFactory factory();
// Create translator service
public static TranslatorService create(String apiUrl, String apiKey);
public static TranslatorService create(LibreTranslateConfig config);
// Test connection
public static boolean testConnection(String apiUrl);
}
Main implementation of the TranslatorService
interface:
public class LibreTranslateClient implements TranslatorService {
// Constants
public static final String DEFAULT_SOURCE_LANGUAGE = Language.AUTO.getCode();
// Constructor
public LibreTranslateClient(LibreTranslateConfig config);
// Translation methods
@Override
public String translate(String text, String targetLanguage);
@Override
public String translate(String text, String sourceLanguage, String targetLanguage);
// Asynchronous methods
@Override
public CompletableFuture<String> translateAsync(String text, String targetLanguage);
@Override
public CompletableFuture<String> translateAsync(String text, String sourceLanguage, String targetLanguage);
// Command processing
@Override
public List<String> processCommands(List<String> commands, boolean log);
// Metrics
@Override
public int getCacheHits();
@Override
public int getCacheMisses();
@Override
public void clearMetrics();
// Resource management
@Override
public void close();
}
Builder-pattern based configuration class:
public class LibreTranslateConfig {
// Create configuration with builder
public static Builder builder();
// Properties
public String getApiUrl();
public String getApiKey();
public int getConnectionTimeout();
public int getSocketTimeout();
public int getMaxRequestsPerSecond();
public int getMaxRetries();
public long getRateLimitCooldown();
public boolean isEnableRetry();
// Builder class
public static class Builder {
public Builder apiUrl(String apiUrl);
public Builder apiKey(String apiKey);
public Builder connectionTimeout(int connectionTimeout);
public Builder socketTimeout(int socketTimeout);
public Builder maxRequestsPerSecond(int maxRequestsPerSecond);
public Builder maxRetries(int maxRetries);
public Builder rateLimitCooldown(long rateLimitCooldown);
public Builder enableRetry(boolean enableRetry);
public LibreTranslateConfig build();
}
}
Enumeration of supported languages:
public enum Language {
// Language constants
ENGLISH("en"), ALBANIAN("sq"), ARABIC("ar"), AZERBAIJANI("az"),
RUSSIAN("ru"), CATALAN("ca"), CHINESE("zh"), CZECH("cs"),
DANISH("da"), DUTCH("nl"), ESPERANTO("eo"), FINNISH("fi"),
FRENCH("fr"), GERMAN("de"), GREEK("el"), HEBREW("he"),
HINDI("hi"), HUNGARIAN("hu"), INDONESIAN("id"), IRISH("ga"),
ITALIAN("it"), JAPANESE("ja"), KOREAN("ko"), PERSIAN("fa"),
POLISH("pl"), PORTUGUESE("pt"), SLOVAK("sk"), SPANISH("es"),
SWEDISH("sv"), TURKISH("tr"), UKRAINIAN("uk"), AUTO("auto");
// Methods
public String getCode();
public static Language fromCode(String code);
public static boolean isValidLanguageCode(String code);
public static List<String> getAllLanguageCodes();
public static boolean isSupportedLanguage(String code);
public static boolean isSupportedLanguage(String... languages);
}
Interface for translation caching:
public interface TranslationCacheService extends AutoCloseable {
// Cache operations
String generateCacheKey(String text, String sourceLanguage, String targetLanguage);
Optional<String> get(String cacheKey);
void put(String cacheKey, String translatedText);
void clear();
// Metrics
int getCacheHits();
int getCacheMisses();
void clearMetrics();
// Resource management
void close();
}
Implementation of the TranslationCacheService
interface:
public class TranslationCache implements TranslationCacheService {
// Enable/disable detailed logging
public static boolean DETAILED_LOGGING = false;
// Constructors
public TranslationCache();
public TranslationCache(int maxCacheSize, long cacheExpirationMs);
public TranslationCache(int maxCacheSize, long cacheExpirationMs, long cleanupIntervalMs);
// Cache operations
@Override
public String generateCacheKey(String text, String sourceLanguage, String targetLanguage);
@Override
public Optional<String> get(String cacheKey);
@Override
public void put(String cacheKey, String translatedText);
@Override
public void clear();
// Metrics
@Override
public int getCacheHits();
@Override
public int getCacheMisses();
@Override
public void clearMetrics();
// Resource management
@Override
public void close();
}
Factory for creating cache services:
public final class CacheFactory {
// Create cache services
public static TranslationCacheService createDefault();
public static TranslationCacheService create(int maxSize, long expirationMs);
public static TranslationCacheService create(int maxSize, long expirationMs, long cleanupIntervalMs);
public static TranslationCacheService createSmall();
public static TranslationCacheService createLarge();
}
Interface for rate limiting:
public interface RateLimiterService extends AutoCloseable {
// Rate limiting operations
boolean acquire() throws InterruptedException;
void notifyRateLimitExceeded(int retryAfterSeconds);
// Metrics and control
RateLimitMetrics getMetrics();
void resetMetrics();
void reset();
// Resource management
void close();
}
Implementation of the RateLimiterService
interface:
public class RateLimiter implements RateLimiterService {
// Enable/disable detailed logging
public static boolean DETAILED_LOGGING = false;
// Constructors
public RateLimiter(int requestsPerSecond);
public RateLimiter(int requestsPerSecond, double burstCapacityMultiplier, long maxWaitTimeNanos);
// Rate limiting operations
@Override
public boolean acquire() throws InterruptedException;
@Override
public void notifyRateLimitExceeded(int retryAfterSeconds);
// Metrics and control
@Override
public RateLimitMetrics getMetrics();
@Override
public void resetMetrics();
@Override
public void reset();
// Resource management
@Override
public void close();
}
Factory for creating rate limiter services:
public final class RateLimiterFactory {
// Create rate limiter services
public static RateLimiterService createDefault();
public static RateLimiterService create(int requestsPerSecond);
public static RateLimiterService create(int requestsPerSecond, double burstCapacityMultiplier, long maxWaitTimeMs);
public static RateLimiterService createLowThroughput();
public static RateLimiterService createHighThroughput();
}
Handler for processing translation commands:
public class LibreTranslateCommands {
// Constructor
public LibreTranslateCommands(TranslatorService translatorService);
// Command processing
public List<String> processCommands(List<String> commands, boolean log);
}
Exception for translation errors:
public class TranslationException extends RuntimeException {
// Constructors
public TranslationException(String message);
public TranslationException(String message, Throwable cause);
}
To enable detailed logging for components:
// Enable detailed cache logging
TranslationCache.DETAILED_LOGGING = true;
// Enable detailed rate limiter logging
RateLimiter.DETAILED_LOGGING = true;
When enabled:
- Cache will log detailed information about hits, misses, and cleanup operations
- Rate limiter will log detailed information about permits, throttling, and backoff behavior
- Always use try-with-resources for proper resource cleanup
- Configure appropriate timeouts for your network environment
- Adjust rate limiting based on the API service's limitations
- Use asynchronous translations for non-blocking operations
- Implement proper error handling for robust applications
<dependency>
<groupId>com.vidigal.code</groupId>
<artifactId>libretranslate-java</artifactId>
<version>1.0.0</version>
</dependency>
implementation 'com.vidigal.code:libretranslate-java:1.0.0'
This project is licensed under the MIT License.
See the LICENSE file for more details.
The LibreTranslate API is also licensed under the MIT License. See the LibreTranslate LICENSE for details.
- Creator: Kauan Vidigal
- Translation API: LibreTranslate
- Contributions: Contributions are welcome! Feel free to fork the repository, open an issue, or submit a pull request.