Official PHP library for the DeepL language translation API.

Overview

deepl-php

Latest Stable Version Minimum PHP version License: MIT

Official PHP client library for the DeepL API.

The DeepL API is a language translation API that allows other computer programs to send texts and documents to DeepL's servers and receive high-quality translations. This opens a whole universe of opportunities for developers: any translation product you can imagine can now be built on top of DeepL's best-in-class translation technology.

The DeepL PHP library offers a convenient way for applications written for PHP to interact with the DeepL API. Currently, the library only supports text and document translation; we intend to add support for glossary management soon.

Getting an authentication key

To use deepl-php, you'll need an API authentication key. To get a key, please create an account here. With a DeepL API Free account you can translate up to 500,000 characters/month for free.

Installation

To use this library in your project, install it using Composer:

composer require deeplcom/deepl-php

Requirements

The library officially supports PHP 7.3 and later.

Usage

Construct a Translator object. The first argument is a string containing your API authentication key as found in your DeepL Pro Account.

Be careful not to expose your key, for example when sharing source code.

$authKey = "f63c02c5-f056-..."; // Replace with your key
$translator = new \DeepL\Translator($authKey);

$result = $translator->translateText('Hello, world!', null, 'fr');
echo $result->text; // Bonjour, le monde!

Translator accepts options as the second argument, see Configuration for more information.

Translating text

To translate text, call translateText(). The first argument is a string containing the text you want to translate, or an array of strings if you want to translate multiple texts.

The second and third arguments are the source and target language codes. Language codes are case-insensitive strings according to ISO 639-1, for example 'de', 'fr', 'ja''. Some target languages also include the regional variant according to ISO 3166-1, for example 'en-US', or 'pt-BR'. The source language also accepts null, to enable auto-detection of the source language.

The last argument to translateText() is optional, and specifies extra translation options, see Text translation options below.

translateText() returns a TextResult, or an array of TextResults corresponding to your input text(s). TextResult has two properties: text is the translated text, and detectedSourceLang is the detected source language code.

// Translate text into a target language, in this case, French:
$translationResult = $translator->translateText('Hello, world!', 'en', 'fr');
echo $translationResult->text; // 'Bonjour, le monde !'

// Translate multiple texts into British English:
$translations = $translator->translateText(
    ['お元気ですか?', '¿Cómo estás?'],
    null,
    'en-GB',
);
echo $translations[0]->text; // 'How are you?'
echo $translations[0]->detectedSourceLang; // 'ja'
echo $translations[1]->text; // 'How are you?'
echo $translations[1]->detectedSourceLang; // 'es'

// Translate into German with less and more Formality:
echo $translator->translateText('How are you?', null, 'de', ['formality' => 'less']); // 'Wie geht es dir?'
echo $translator->translateText('How are you?', null, 'de', ['formality' => 'more']); // 'Wie geht es Ihnen?'

Text translation options

Provide options to the translateText function as an associative array, using the following keys:

  • split_sentences: specify how input text should be split into sentences, default: 'on'.
    • 'on': input text will be split into sentences using both newlines and punctuation.
    • 'off': input text will not be split into sentences. Use this for applications where each input text contains only one sentence.
    • 'nonewlines': input text will be split into sentences using punctuation but not newlines.
  • preserve_formatting: controls automatic-formatting-correction. Set to true to prevent automatic-correction of formatting, default: false.
  • formality: controls whether translations should lean toward informal or formal language. This option is only available for some target languages, see Listing available languages.
    • 'less': use informal language.
    • 'more': use formal, more polite language.
  • tag_handling: type of tags to parse before translation, options are 'html' and 'xml'.
  • glossary: glossary ID of glossary to use for translation.

The following options are only used if tag_handling is 'xml':

  • outline_detection: specify false to disable automatic tag detection, default is true.
  • splitting_tags: list of XML tags that should be used to split text into sentences. Tags may be specified as an array of strings (['tag1', 'tag2']), or a comma-separated list of strings ('tag1,tag2'). The default is an empty list.
  • non_splitting_tags: list of XML tags that should not be used to split text into sentences. Format and default are the same as for splitting_tags.
  • ignore_tags: list of XML tags that containing content that should not be translated. Format and default are the same as for splitting_tags.

The TranslateTextOptions class defines constants for the options above, for example TranslateTextOptions::FORMALITY is defined as 'formality'.

Translating documents

To translate documents, call translateDocument(). The first and second arguments are the input and output file paths.

The third and fourth arguments are the source and target language codes, and they work exactly the same as when translating text with translateText().

The last argument to translateDocument() is optional, and specifies extra translation options, see Document translation options below.

// Translate a formal document from English to German:
try {
    $translator->translateDocument(
        'Instruction Manual.docx',
        'Bedienungsanleitung.docx',
        'en',
        'de',
        ['formality' => 'more'],
    );
} catch (\DeepL\DocumentTranslationException $error) {
    // If the error occurs after the document was already uploaded,
    // documentHandle will contain the document ID and key
    echo 'Error occurred while translating document: ' . ($error->getMessage() ?? 'unknown error');
    if ($error->documentHandle) {
        $handle = $error->documentHandle;
        echo "Document ID: {$handle->documentId}, document key: {$handle->documentKey}";
    } else {
        echo 'Unknown document handle';
    }
}

translateDocument() wraps multiple API calls: uploading, polling status until the translation is complete, and downloading. If your application needs to execute these steps individually, you can instead use the following functions directly:

  • uploadDocument(),
  • getDocumentStatus() (or waitUntilDocumentTranslationComplete()), and
  • downloadDocument()

Document translation options

Provide options to the translateDocument function as an associative array, using the following keys:

The uploadDocument function also supports these options.

The TranslateDocumentOptions class defines constants for the options above, for example TranslateDocumentOptions::FORMALITY is defined as 'formality'.

Checking account usage

To check account usage, use the getUsage() function.

The returned Usage object contains up to three usage subtypes, depending on your account type: character, document and teamDocument. For API accounts character will be set, the others null.

Each usage subtypes (if set) have count and limit properties giving the amount used and maximum amount respectively, and the limitReached() function that checks if the usage has reached the limit. The top level Usage object has the anyLimitReached() function to check all usage subtypes.

$usage = $translator->getUsage();
if ($usage->anyLimitReached()) {
    echo 'Translation limit exceeded.';
}
if ($usage->character) {
    echo 'Characters: ' . $usage->character->count . ' of ' . $usage->character->limit;
}
if ($usage->document) {
    echo 'Documents: ' . $usage->document->count . ' of ' . $usage->document->limit;
}

Listing available languages

You can request the list of languages supported by DeepL Translator for text and documents using the getSourceLanguages() and getTargetLanguages() functions. They both return an array of Language objects.

The name property gives the name of the language in English, and the code property gives the language code. The supportsFormality property only appears for target languages, and is a bool indicating whether the target language supports the optional formality parameter.

$sourceLanguages = $translator->getSourceLanguages();
foreach ($sourceLanguages as $sourceLanguage) {
    echo $sourceLanguage->name . ' (' . $sourceLanguage->code . ')'; // Example: 'English (en)'
}

$targetLanguages = $translator->getTargetLanguages();
foreach ($targetLanguages as $targetLanguage) {
    if ($targetLanguage->supportsFormality) {
        echo $targetLanguage->name . ' (' . $targetLanguage->code . ') supports formality';
        // Example: 'German (de) supports formality'
    }
}

Configuration

The Translator constructor accepts configuration options as a second argument, for example:

$options = [ 'max_retries' => 5, 'timeout' => 10.0 ];
$translator = new \DeepL\Translator('YOUR_AUTH_KEY', $options);

Provide the options as an associative array with the following keys:

  • max_retries: the maximum number of failed HTTP requests to retry, per function call. By default, 5 retries are made. See Request retries.
  • timeout: the number of seconds used as connection timeout for each HTTP request retry. The default value is 10.0 (10 seconds).
  • server_url: string containing the URL of the DeepL API, can be overridden for example for testing purposes. By default, the URL is selected based on the user account type (free or paid).
  • headers: extra HTTP headers attached to every HTTP request. By default, no extra headers are used. Note that Authorization and User-Agent headers are added automatically but may be overridden by this option.
  • logger: specify a PSR-3 compatible logger that the library should log messages to.

The TranslatorOptions class defines constants for the options above.

Logging

To enable logging, specify a PSR-3 compatible logger as the 'logger' option in the Translator configuration options.

Request retries

Requests to the DeepL API that fail due to transient conditions (for example, network timeouts or high server-load) will be retried. The maximum number of retries can be configured when constructing the Translator object using the max_retries option. The timeout for each request attempt may be controlled using the timeout option. An exponential-backoff strategy is used, so requests that fail multiple times will incur delays.

Issues

If you experience problems using the library, or would like to request a new feature, please open an issue.

Development

We welcome Pull Requests, please read the contributing guidelines.

Tests

Execute the tests using phpunit. The tests communicate with the DeepL API using the auth key defined by the DEEPL_AUTH_KEY environment variable.

Be aware that the tests make DeepL API requests that contribute toward your API usage.

The test suite may instead be configured to communicate with the mock-server provided by deepl-mock. Although most test cases work for either, some test cases work only with the DeepL API or the mock-server and will be otherwise skipped. The test cases that require the mock-server trigger server errors and test the client error-handling. To execute the tests using deepl-mock, run it in another terminal while executing the tests. Execute the tests using phpunit with the DEEPL_MOCK_SERVER_PORT and DEEPL_SERVER_URL environment variables defined referring to the mock-server.

Comments
  • Error while instaling: Your requirements could not be resolved to an installable set of packages.

    Error while instaling: Your requirements could not be resolved to an installable set of packages.

    Hi, I received that error while installing:

    miguel@miguel-IdeaPad-3-15ITL6:/var/www/html/vmo$ composer require deeplcom/deepl-php
    Warning from https://repo.packagist.org: Support for Composer 1 is deprecated and some packages will not be available. You should upgrade to Composer 2. See https://blog.packagist.com/deprecating-composer-1-support/
    Info from https://repo.packagist.org: #StandWithUkraine
    Using version ^0.4.0 for deeplcom/deepl-php
    ./composer.json has been updated
    Loading composer repositories with package information
    Warning from https://repo.packagist.org: Support for Composer 1 is deprecated and some packages will not be available. You should upgrade to Composer 2. See https://blog.packagist.com/deprecating-composer-1-support/
    Info from https://repo.packagist.org: #StandWithUkraine
    Updating dependencies (including require-dev)
    Your requirements could not be resolved to an installable set of packages.
    
      Problem 1
        - The requested package vendor/package could not be found in any version, there may be a typo in the package name.
      Problem 2
        - The requested package vendor/package2 could not be found in any version, there may be a typo in the package name.
      Problem 3
        - The requested package vendor/package3 could not be found in any version, there may be a typo in the package name.
      Problem 4
        - pelago/emogrifier v2.2.0 requires php ^5.5.0 || ~7.0.0 || ~7.1.0 || ~7.2.0 || ~7.3.0 -> your PHP version (7.4.3) does not satisfy that requirement.
        - pelago/emogrifier v2.2.0 requires php ^5.5.0 || ~7.0.0 || ~7.1.0 || ~7.2.0 || ~7.3.0 -> your PHP version (7.4.3) does not satisfy that requirement.
        - Installation request for pelago/emogrifier (installed at v2.2.0) -> satisfiable by pelago/emogrifier[v2.2.0].
    
    Potential causes:
     - A typo in the package name
     - The package is not available in a stable-enough version according to your minimum-stability setting
       see <https://getcomposer.org/doc/04-schema.md#minimum-stability> for more details.
     - It's a private package and you forgot to add a custom repository to find it
    
    Read <https://getcomposer.org/doc/articles/troubleshooting.md> for further common problems.
    
    Installation failed, reverting ./composer.json to its original content.
    miguel@miguel-IdeaPad-3-15ITL6:/var/www/html/vmo$
    

    Any solution please?

    Thank you, Miguel

    opened by miguelgisbert 3
  • Getting

    Getting "syntax error, unexpected ')' in src/Translator.php" when constructing Translator

    Docker php:7.4-fpm
    

    I get a syntax error when calling:

    $translator = new \DeepL\Translator($authKey);
    

    and if you look into the file deepl-php/src/Translator.php at Line 552 and Line 559 shown as below:

    // Line 552, validateAndAppendTexts()
    throw new DeepLException(
        'texts parameter must be a non-empty string or array of non-empty strings',
    );
    
    // Same as above, Line 559, validateAndAppendTexts()
    throw new DeepLException(
        'texts parameter must be a non-empty string or array of non-empty strings',
    );
    

    Remove the comma right after the message will fix it :

    throw new DeepLException(
        'texts parameter must be a non-empty string or array of non-empty strings'
    );
    

    Just in case anyone has the same issue, so I posted it here :)

    opened by Hardys- 2
  • Problems with

    Problems with "final class Translator in phpunit integration Tests

    Hey, at the moment I try to replace https://github.com/Baby-Markt/deepl-php-lib with your Library. Everything went relatively smooth but I ran into an Issues when it comes to user the Library in integration Tests. Since I am not able to start an API-Mock-Server during our Tests, I want to Mock your Translator classand to manipulate the return value of for example the translateText-Method. At the moment this is not possible because the Translator-Class is final and phpunit uses Class-Extension to create Mockclasses. I tried Mockery but since we use type hinting this fails too.

    Is it possible for you to Change the definition or do you have an other suggestion for this Problem?

    opened by VimS 2
  • fix: make logger option compatible with PSR-3 Logger

    fix: make logger option compatible with PSR-3 Logger

    Contrary to the documentation it's currently not possible to pass a PSR-3 logger implementation (e.g. Monolog) as the logger option, because of the types declared in the constructor of HttpClient.

    According to the constructor you have to pass a DeepL\LoggerInterface. Monolog for example implements Psr\Log\LoggerInterface but of cause not DeepL\LoggerInterface.

    Because of that you''ll get an Exception when you pass a Monolog logger to the logger option of the Translator:

    Argument 5 passed to DeepL\HttpClient::__construct() must be an instance of DeepL\LoggerInterface or null, instance of Monolog\Logger given

    This PR replaces DeepL\LoggerInterface with the Psr\Log\LoggerInterface which Monolog and other Logging Frameworks implement, making it possible to pass them as a logger to Translator.

    opened by Schleuse 1
  • Question about keys in translated arrays

    Question about keys in translated arrays

    Why does the translation function not retain the key, when translating an array of text?

    $to_translate = array('a' => 'Text A', 'b' => 'Text B');
    $translations = $translator->translateText($to_translate, 'en-US', 'de');
    

    The result is return as an array indexed 0, 1 rather than indexed using 'a', 'b'. Is there a reason for this behavior?

    opened by diderich 1
  • Cannot create account / API key

    Cannot create account / API key

    Hi, the following appears on your site when you sign up -- only after providing a credit card...

    image

    I actually tried again with a new account and got the same thing. Doesn't seem to be a way to generate API keys right now. I did contact support, but have not heard anything.

    opened by putnam 1
  • QUESTION: Question/Issue regarding translation speed for Tweet-sized sentences

    QUESTION: Question/Issue regarding translation speed for Tweet-sized sentences

    I am currently benchmarking DeepL against Google Translate for translating photo captions the size of a Tweet with a rather standardized sentence structure from English to German and French. 80% of the translated caption phrases are identical and in the last 20%, DeepL chooses a more appropriate vocabulary, e.g.

    ORIGINAL: Belinda Bencic of Switzerland plays the ball during her third round match against Donna Vekic of Croatia on day two of the 2019 French Open at the Roland Garros stadium in Paris, France on May 31, 2019 (Photo by Claude Diderich / freshfocus)
    DEEPL TRANSLATION:  PARIS, FRANKREICH - 31. MAI: Belinda Bencic aus der Schweiz spielt den Ball während ihres Drittrundenmatches gegen Donna Vekic aus Kroatien am zweiten Tag der French Open 2019 im Roland-Garros-Stadion in Paris, Frankreich am 31. Mai 2019 (Foto: Claude Diderich / freshfocus)
    GOOGLE TRANSLATION: PARIS, FRANKREICH - 31. MAI: Belinda Bencic aus der Schweiz spielt den Ball während ihres Spiels in der dritten Runde gegen Donna Vekic aus Kroatien am zweiten Tag der French Open 2019 im Roland Garros-Stadion in Paris, Frankreich, am 31. Mai 2019 (Foto von Claude Diderich / freshfocus)
    
    

    But I noticed that on the speed/latency side, Google is 2x to 3x faster (0.15s vs 0.31s, 0.13s vs 0.39s, 0.2s vs 0.52s, etc.). I was wondering if that is due to

    1. the fact that I am currently using the free version from DeepL, i.e., the paid version would be much faster, or
    2. the translation at deepl.com taking more time than Google does, due to the complexity of the translation algorithm used, i.e., it's coming from the software side, or
    3. deepl.com having less sophisticated hardware resources in place, i.e., it's coming from the hardware side, or
    4. me being located in Switzerland and my network connection to translate.google.com is faster than to deepl.com?
    opened by diderich 1
  • Adding curl-options

    Adding curl-options

    Hi, is there a way to add curl-options when instantiating the Translator? I need to include verify_peer: false and verify_host: false, otherwise I'll get a "SSL certificate error: unable to get local issuer certificate"-exception.

    I have tried $translator = new \DeepL\Translator('KEY', ['headers' => ['verify_peer' => false, 'verify_host' => false]]); but that doesn't work (same with "0" instead of "false" for both options). I see the options getting added to $curlOptions in HttpClient (line 182), but they don't seem to do anything.

    Thanks

    enhancement 
    opened by Knallcharge 2
  • Word not found

    Word not found

    Hi, as far as I know, when a word is not found, DeepL will try to guess or just return the same entry. Is it possible to know when that happens? or to have the option to avoid it altogether? sometimes it's better to get a 'not found' message/error than a wild guess due to a misspelling. Thank you for this, by the way, it's very useful! Andres

    opened by AndresKolb 0
  • Connection timed out error when calling getUsage

    Connection timed out error when calling getUsage

    $usage = $translator->getUsage();

    DeepL\ConnectionException: Operation timed out after 10001 milliseconds with 0 bytes received in /var/www/vendor/deeplcom/deepl-php/src/HttpClient.php:200

    opened by KaracsonyMarton 2
  • FEATURE REQUEST: Add support for translated error messages using gettext

    FEATURE REQUEST: Add support for translated error messages using gettext

    It would be great if the error messages would be translatable through gettext, eg., _("Error message").'. '._("Language").' '.$lang.' '._("not supported").

    api change 
    opened by diderich 3
Releases(v1.2.0)
  • v1.2.0(Dec 1, 2022)

    Changed

    • Added dependency on psr/log. As this package forms a PHP Standard Recommendation, we don't consider it to break backward-compatibility.

    Fixed

    • Change the type of the TranslatorOptions::LOGGER option to Psr\Log\LoggerInterface, to correctly support PSR-3 loggers.
    Source code(tar.gz)
    Source code(zip)
  • v1.1.0(Sep 29, 2022)

    Added

    • Add new formality options: 'prefer_less' and 'prefer_more'.

    Changed

    • Requests resulting in 503 Service Unavailable errors are now retried. Attempting to download a document before translation is completed will now wait and retry (up to 5 times by default), rather than throwing an exception.
    Source code(tar.gz)
    Source code(zip)
  • v0.4.1(Sep 20, 2022)

  • v1.0.0(Sep 20, 2022)

    Stable release.

    Added

    • Add glossary management support.

    • New language available: Ukrainian ('uk'). Add language code constant and tests.

      Note: older library versions also support new languages, this update only adds new code constant.

    • Add proxy support.

    Source code(tar.gz)
    Source code(zip)
  • v0.4.0(May 24, 2022)

  • v0.3.0(May 18, 2022)

    Added

    • New languages available: Indonesian ('id') and Turkish ('tr'). Add language code constants and tests.

      Note: older library versions also support the new languages, this update only adds new code constants.

    Source code(tar.gz)
    Source code(zip)
  • v0.2.0(May 2, 2022)

  • v0.1.1(Apr 28, 2022)

    Fixed

    • Added minimum supported PHP version to composer.json.
    • Fix cURL client issue: do not round timeouts to whole seconds.
    • Fix cURL client issue: consider empty response a retryable-error.
    • Check for and reject invalid server_url option.
    Source code(tar.gz)
    Source code(zip)
  • v0.1.0(Apr 25, 2022)

Owner
DeepL
DeepL
[virion] Language management library for automatic translation

libtranslator :: library for automatic translation ✔️ Multilingual support for plugin messages ✔️ Translation language is set according to the player

PocketMine-MP projects of PresentKim 5 Jul 29, 2022
Composer package providing translation features for PHP apps

PHP translation This is a composer package providing translation support for PHP applications. It is similar to gettext, in usage, with these differen

Sérgio Carvalho 0 Aug 15, 2022
Better translation management for Laravel

Better localization management for Laravel Introduction Keeping a project's translations properly updated is cumbersome. Usually translators do not ha

Waavi 354 Dec 18, 2022
Laravel translation made __('simple').

Translation.io client for Laravel 5.5+/6/7/8 Add this package to localize your Laravel application. Use the official Laravel syntax (with PHP or JSON

Translation.io 109 Dec 29, 2022
🎌 Laravel Localization Helper :: Easily add translation variables from Blade templates.

LocalizationHelper Package for convenient work with Laravel's localization features and fast language files generation. Take a look at contributing.md

Awes.io 36 Jul 18, 2022
Manage Laravel translation files

Laravel 5 Translation Manager For Laravel 4, please use the 0.1 branch! This is a package to manage Laravel translation files. It does not replace the

Barry vd. Heuvel 1.5k Jan 4, 2023
A GUI for managing JSON translation files in your laravel projects.

Laravel Language Manager Langman is a GUI for managing your JSON language files in a Laravel project. Installation Begin by installing the package thr

Mohamed Said 515 Nov 30, 2022
A Gui To Manage Laravel Translation Files

Lingo A file based translation manager, which unlike other Lang managers don't need a database connection to handle the translation. Installation comp

Muah 97 Dec 5, 2022
Provides support for message translation and localization for dates and numbers.

The I18n library provides a I18n service locator that can be used for setting the current locale, building translation bundles and translating messages. Additionally, it provides the Time and Number classes which can be used to output dates, currencies and any numbers in the right format for the specified locale.

CakePHP 26 Oct 22, 2022
Internationalization tools, particularly message translation.

Aura.Intl The Aura.Intl package provides internationalization (I18N) tools, specifically package-oriented per-locale message translation. Installation

Aura for PHP 86 Dec 18, 2022
The Translation component provides tools to internationalize your application.

Translation Component The Translation component provides tools to internationalize your application. Getting Started $ composer require symfony/transl

Symfony 6.4k Jan 6, 2023
Filament Translations - Manage your translation with DB and cache

Filament Translations Manage your translation with DB and cache, you can scan your languages tags like trans(), __(), and get the string inside and tr

Fady Mondy 32 Nov 28, 2022
French-Traduction-Pterodactyl est la traduction française de pterodactyl French-Traduction-Pterodactyl is the French translation of pterodactyl

French-Traduction-Pterodactyl Star French-Traduction-Pterodactyl est la traduction française de pterodactyl French-Traduction-Pterodactyl is the Frenc

null 5 Sep 26, 2022
Translation (i18n) Manager as a virion

TL Translation (i18n) Manager as a virion Translation use hook-like $t = $tl->useTranslation($player->getLocale()); $player->sendMessage($t("message-k

RedMC Network 3 Oct 28, 2022
Geographer is a PHP library that knows how any country, state or city is called in any language

Geographer Geographer is a PHP library that knows how any country, state or city is called in any language. Documentation on the official website Incl

Menara Solutions 757 Nov 24, 2022
A morphological solution for Russian and English language written completely in PHP.

Morphos A morphological solution for Russian and English language written completely in PHP. Tests & Quality: Features [✓] Inflection of Personal name

Sergey 723 Jan 4, 2023
Language files manager in your artisan console.

Laravel Langman Langman is a language files manager in your artisan console, it helps you search, update, add, and remove translation lines with ease.

Mohamed Said 867 Nov 30, 2022
Support multiple language resources for Laravel

Laratrans Support multiple language resources for Laravel. Docs Installation composer require lechihuy/laratrans After you install the package success

Lê Chí Huy 3 Dec 21, 2021
PHP library to collect and manipulate gettext (.po, .mo, .php, .json, etc)

Gettext Note: this is the documentation of the new 5.x version. Go to 4.x branch if you're looking for the old 4.x version Created by Oscar Otero http

Gettext 651 Dec 29, 2022