Skip to content

Commit 842015c

Browse files
committed
docs: Update changelog and README with the Write API
1 parent 505c8d2 commit 842015c

File tree

2 files changed

+110
-43
lines changed

2 files changed

+110
-43
lines changed

CHANGELOG.md

+12
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,17 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
55
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
66

77

8+
## Unreleased
9+
### Added
10+
* Added support for the Write API in the client library, the implementation
11+
can be found in the `DeepLClient` class. Please refer to the README for usage
12+
instructions.
13+
### Changed
14+
* The main functionality of the library is now also exposed via the `DeepLClient`
15+
class. Please change your code to use this over the `Translator` class whenever
16+
convenient.
17+
18+
819
## [1.20.0] - 2024-11-15
920
### Added
1021
* Added `model_type` option to `translate_text()` to use models with higher
@@ -314,6 +325,7 @@ Version increased to avoid conflicts with old packages on PyPI.
314325
Initial version.
315326

316327

328+
[Unreleased]: https://github.com/DeepLcom/deepl-python/compare/v1.20.0...HEAD
317329
[1.20.0]: https://github.com/DeepLcom/deepl-python/compare/v1.19.1...v1.20.0
318330
[1.19.1]: https://github.com/DeepLcom/deepl-python/compare/v1.19.0...v1.19.1
319331
[1.19.0]: https://github.com/DeepLcom/deepl-python/compare/v1.18.0...v1.19.0

README.md

+98-43
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,11 @@
44
[![Supported Python versions](https://img.shields.io/pypi/pyversions/deepl.svg)](https://pypi.org/project/deepl/)
55
[![License: MIT](https://img.shields.io/badge/license-MIT-blueviolet.svg)](https://github.com/DeepLcom/deepl-python/blob/main/LICENSE)
66

7-
The [DeepL API][api-docs] is a language translation API that allows other
8-
computer programs to send texts and documents to DeepL's servers and receive
9-
high-quality translations. This opens a whole universe of opportunities for
10-
developers: any translation product you can imagine can now be built on top of
11-
DeepL's best-in-class translation technology.
7+
The [DeepL API][api-docs] is a language AI API that allows other computer programs
8+
to send texts and documents to DeepL's servers and receive high-quality
9+
translations and improvements to the text. This opens a whole universe of
10+
opportunities for developers: any translation product you can imagine can now
11+
be built on top of DeepL's best-in-class translation technology.
1212

1313
The DeepL Python library offers a convenient way for applications written in
1414
Python to interact with the DeepL API. We intend to support all API functions
@@ -19,7 +19,7 @@ after they’re added to the API.
1919

2020
To use the DeepL Python Library, you'll need an API authentication key. To get a
2121
key, [please create an account here][create-account]. With a DeepL API Free
22-
account you can translate up to 500,000 characters/month for free.
22+
account you can consume up to 500,000 characters/month for free.
2323

2424
## Installation
2525

@@ -53,7 +53,7 @@ To continue using this library, you should update to Python 3.8+.
5353

5454
## Usage
5555

56-
Import the package and construct a `Translator`. The first argument is a string
56+
Import the package and construct a `DeepLClient`. The first argument is a string
5757
containing your API authentication key as found in your
5858
[DeepL Pro Account][pro-account].
5959

@@ -63,17 +63,17 @@ Be careful not to expose your key, for example when sharing source code.
6363
import deepl
6464

6565
auth_key = "f63c02c5-f056-..." # Replace with your key
66-
translator = deepl.Translator(auth_key)
66+
deepl_client = deepl.DeepLClient(auth_key)
6767

68-
result = translator.translate_text("Hello, world!", target_lang="FR")
68+
result = deepl_client.translate_text("Hello, world!", target_lang="FR")
6969
print(result.text) # "Bonjour, le monde !"
7070
```
7171

7272
This example is for demonstration purposes only. In production code, the
7373
authentication key should not be hard-coded, but instead fetched from a
7474
configuration file or environment variable.
7575

76-
`Translator` accepts additional options, see [Configuration](#configuration)
76+
`DeepLClient` accepts additional options, see [Configuration](#configuration)
7777
for more information.
7878

7979
### Translating text
@@ -105,11 +105,11 @@ corresponding to your input text(s). `TextResult` has the following properties:
105105

106106
```python
107107
# Translate text into a target language, in this case, French:
108-
result = translator.translate_text("Hello, world!", target_lang="FR")
108+
result = deepl_client.translate_text("Hello, world!", target_lang="FR")
109109
print(result.text) # "Bonjour, le monde !"
110110

111111
# Translate multiple texts into British English
112-
result = translator.translate_text(
112+
result = deepl_client.translate_text(
113113
["お元気ですか?", "¿Cómo estás?"],
114114
target_lang="EN-GB",
115115
)
@@ -122,12 +122,12 @@ print(result[1].billed_characters) # 12 - the number of characters in the sourc
122122

123123
# Translate into German with less and more Formality:
124124
print(
125-
translator.translate_text(
125+
deepl_client.translate_text(
126126
"How are you?", target_lang="DE", formality="less"
127127
)
128128
) # 'Wie geht es dir?'
129129
print(
130-
translator.translate_text(
130+
deepl_client.translate_text(
131131
"How are you?", target_lang="DE", formality="more"
132132
)
133133
) # 'Wie geht es Ihnen?'
@@ -191,6 +191,61 @@ The following options are only used if `tag_handling` is `'xml'`:
191191
For a detailed explanation of the XML handling options, see the
192192
[API documentation][api-docs-xml-handling].
193193

194+
### Improving text (Write API)
195+
196+
You can use the Write API to improve or rephrase text. This is implemented in
197+
the `rephrase_text()` method. The first argument is a string containing the text
198+
you want to translate, or a list of strings if you want to translate multiple texts.
199+
200+
`target_lang` optionally specifies the target language, e.g. when you want to change
201+
the variant of a text (for example, you can send an english text to the write API and
202+
use `target_lang` to turn it into British or American English). Please note that the
203+
Write API itself does NOT translate. If you wish to translate and improve a text, you
204+
will need to make multiple calls in a chain.
205+
206+
Language codes are the same as for translating text.
207+
208+
Example call:
209+
210+
```python
211+
result = deepl_client.rephrase_text("A rainbouw has seven colours.", target_lang="EN-US")
212+
print(result.text)
213+
```
214+
215+
Additionally, you can optionally specify a style OR a tone (not both at once) that the
216+
improvement should be in. The following styles are supported (`default` will be used if
217+
nothing is selected):
218+
219+
- `academic`
220+
- `business`
221+
- `casual`
222+
- `default`
223+
- `simple`
224+
225+
The following tones are supported (`default` will be used if nothing is selected):
226+
227+
- `confident`
228+
- `default`
229+
- `diplomatic`
230+
- `enthusiastic`
231+
- `friendly`
232+
233+
You can also prefix any non-default style or tone with `prefer_` (`prefer_academic`, etc.),
234+
in which case the style/tone will only be applied if the language supports it. If you do not
235+
use `prefer_`, requests with `target_lang`s or detected languages that do not support
236+
styles and tones will fail. The current list of supported languages can be found in our
237+
[API documentation][api-docs]. We plan to also expose this information via an API endpoint
238+
in the future.
239+
240+
You can use the predefined constants in the library to use a style:
241+
242+
```python
243+
result = deepl_client.rephrase_text(
244+
"A rainbouw has seven colours.", target_lang="EN-US", style=WritingStyle.BUSINESS.value
245+
)
246+
print(result.text)
247+
```
248+
194249
### Translating documents
195250

196251
To translate documents, you may call either `translate_document()` using file IO
@@ -210,7 +265,7 @@ input_path = "/path/to/Instruction Manual.docx"
210265
output_path = "/path/to/Bedienungsanleitung.docx"
211266
try:
212267
# Using translate_document_from_filepath() with file paths
213-
translator.translate_document_from_filepath(
268+
deepl_client.translate_document_from_filepath(
214269
input_path,
215270
output_path,
216271
target_lang="DE",
@@ -219,7 +274,7 @@ try:
219274

220275
# Alternatively you can use translate_document() with file IO objects
221276
with open(input_path, "rb") as in_file, open(output_path, "wb") as out_file:
222-
translator.translate_document(
277+
deepl_client.translate_document(
223278
in_file,
224279
out_file,
225280
target_lang="DE",
@@ -283,7 +338,7 @@ count.
283338
```python
284339
# Create an English to German glossary with two terms:
285340
entries = {"artist": "Maler", "prize": "Gewinn"}
286-
my_glossary = translator.create_glossary(
341+
my_glossary = deepl_client.create_glossary(
287342
"My glossary",
288343
source_lang="EN",
289344
target_lang="DE",
@@ -307,7 +362,7 @@ bytes containing file content:
307362
# consider using encoding='utf-8-sig' instead.
308363
with open('/path/to/glossary_file.csv', 'r', encoding='utf-8') as csv_file:
309364
csv_data = csv_file.read() # Read the file contents as a string
310-
my_csv_glossary = translator.create_glossary_from_csv(
365+
my_csv_glossary = deepl_client.create_glossary_from_csv(
311366
"CSV glossary",
312367
source_lang="EN",
313368
target_lang="DE",
@@ -333,13 +388,13 @@ Functions to get, list, and delete stored glossaries are also provided:
333388
```python
334389
# Retrieve a stored glossary using the ID
335390
glossary_id = "559192ed-8e23-..."
336-
my_glossary = translator.get_glossary(glossary_id)
391+
my_glossary = deepl_client.get_glossary(glossary_id)
337392

338393
# Find and delete glossaries named 'Old glossary'
339-
glossaries = translator.list_glossaries()
394+
glossaries = deepl_client.list_glossaries()
340395
for glossary in glossaries:
341396
if glossary.name == "Old glossary":
342-
translator.delete_glossary(glossary)
397+
deepl_client.delete_glossary(glossary)
343398
```
344399

345400
#### Listing entries in a stored glossary
@@ -352,7 +407,7 @@ To list the entries contained within a stored glossary, use
352407
ID:
353408

354409
```python
355-
entries = translator.get_glossary_entries(my_glossary)
410+
entries = deepl_client.get_glossary_entries(my_glossary)
356411
print(entries) # "{'artist': 'Maler', 'prize': 'Gewinn'}"
357412
```
358413

@@ -364,21 +419,21 @@ specify the `source_lang` argument (it is required when using a glossary):
364419

365420
```python
366421
text = "The artist was awarded a prize."
367-
with_glossary = translator.translate_text(
422+
with_glossary = deepl_client.translate_text(
368423
text, source_lang="EN", target_lang="DE", glossary=my_glossary,
369424
)
370425
print(with_glossary) # "Der Maler wurde mit einem Gewinn ausgezeichnet."
371426

372427
# For comparison, the result without a glossary:
373-
without_glossary = translator.translate_text(text, target_lang="DE")
428+
without_glossary = deepl_client.translate_text(text, target_lang="DE")
374429
print(without_glossary) # "Der Künstler wurde mit einem Preis ausgezeichnet."
375430
```
376431

377432
Using a stored glossary for document translation is the same: set the `glossary`
378433
argument and specify the `source_lang` argument:
379434

380435
```python
381-
translator.translate_document(
436+
deepl_client.translate_document(
382437
in_file, out_file, source_lang="EN", target_lang="DE", glossary=my_glossary,
383438
)
384439
```
@@ -404,7 +459,7 @@ that checks if the usage has reached the limit. The top level `Usage` object has
404459
the `any_limit_reached` property to check all usage subtypes.
405460

406461
```python
407-
usage = translator.get_usage()
462+
usage = deepl_client.get_usage()
408463
if usage.any_limit_reached:
409464
print('Translation limit reached.')
410465
if usage.character.valid:
@@ -427,11 +482,11 @@ optional `formality` parameter.
427482

428483
```python
429484
print("Source languages:")
430-
for language in translator.get_source_languages():
485+
for language in deepl_client.get_source_languages():
431486
print(f"{language.name} ({language.code})") # Example: "German (DE)"
432487

433488
print("Target languages:")
434-
for language in translator.get_target_languages():
489+
for language in deepl_client.get_target_languages():
435490
if language.supports_formality:
436491
print(f"{language.name} ({language.code}) supports formality")
437492
# Example: "Italian (IT) supports formality"
@@ -448,7 +503,7 @@ of `GlossaryLanguagePair` objects. Each has `source_lang` and `target_lang`
448503
properties indicating that that pair of language codes is supported.
449504

450505
```python
451-
glossary_languages = translator.get_glossary_languages()
506+
glossary_languages = deepl_client.get_glossary_languages()
452507
for language_pair in glossary_languages:
453508
print(f"{language_pair.source_lang} to {language_pair.target_lang}")
454509
# Example: "EN to DE", "DE to EN", etc.
@@ -464,10 +519,10 @@ target language English (`"EN"`) supports translations to both American English
464519
### Writing a Plugin
465520

466521
If you use this library in an application, please identify the application with
467-
`deepl.Translator.set_app_info`, which needs the name and version of the app:
522+
`deepl.DeepLClient.set_app_info`, which needs the name and version of the app:
468523

469524
```python
470-
translator = deepl.Translator(...).set_app_info("sample_python_plugin", "1.0.2")
525+
deepl_client = deepl.DeepLClient(...).set_app_info("sample_python_plugin", "1.0.2")
471526
```
472527

473528
This information is passed along when the library makes calls to the DeepL API.
@@ -499,23 +554,23 @@ logging.getLogger('deepl').setLevel(logging.DEBUG)
499554
#### Server URL configuration
500555

501556
You can override the URL of the DeepL API by specifying the `server_url`
502-
argument when constructing a `deepl.Translator`. This may be useful for testing
557+
argument when constructing a `deepl.DeepLClient`. This may be useful for testing
503558
purposes. You **do not** need to specify the URL to distinguish API Free and API
504559
Pro accounts, the library selects the correct URL automatically.
505560

506561
```python
507562
server_url = "http://user:pass@localhost:3000"
508-
translator = deepl.Translator(..., server_url=server_url)
563+
deepl_client = deepl.DeepLClient(..., server_url=server_url)
509564
```
510565

511566
#### Proxy configuration
512567

513568
You can configure a proxy by specifying the `proxy` argument when constructing a
514-
`deepl.Translator`:
569+
`deepl.DeepLClient`:
515570

516571
```python
517572
proxy = "http://user:[email protected]:3128"
518-
translator = deepl.Translator(..., proxy=proxy)
573+
deepl_client = deepl.DeepLClient(..., proxy=proxy)
519574
```
520575

521576
The proxy argument is passed to the underlying `requests` session, see the
@@ -525,11 +580,11 @@ proxy URLs is also accepted.
525580
#### Override SSL verification
526581

527582
You can control how `requests` performs SSL verification by specifying the
528-
`verify_ssl` option when constructing a `deepl.Translator`, for example to
583+
`verify_ssl` option when constructing a `deepl.DeepLClient`, for example to
529584
disable SSL certificate verification:
530585

531586
```python
532-
translator = deepl.Translator(..., verify_ssl=False)
587+
deepl_client = deepl.DeepLClient(..., verify_ssl=False)
533588
```
534589

535590
This option is passed to the underlying `requests` session as the `verify`
@@ -546,26 +601,26 @@ can be changed to 3 as follows:
546601
import deepl
547602

548603
deepl.http_client.max_network_retries = 3
549-
t = deepl.Translator(...)
550-
t.translate_text(...)
604+
c = deepl.DeepLClient(...)
605+
c.translate_text(...)
551606
```
552607

553608
You can configure the timeout `min_connection_timeout` the same way, as well
554609
as set a custom `user_agent`, see the next section.
555610

556611
#### Anonymous platform information
557612

558-
By default, we send some basic information about the platform the client library is running on with each request, see [here for an explanation](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/User-Agent). This data is completely anonymous and only used to improve our product, not track any individual users. If you do not wish to send this data, you can opt-out when creating your `deepl.Translator` object by setting the `send_platform_info` flag like so:
613+
By default, we send some basic information about the platform the client library is running on with each request, see [here for an explanation](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/User-Agent). This data is completely anonymous and only used to improve our product, not track any individual users. If you do not wish to send this data, you can opt-out when creating your `deepl.DeepLClient` object by setting the `send_platform_info` flag like so:
559614

560615
```python
561-
translator = deepl.Translator(..., send_platform_info=False)
616+
deepl_client = deepl.DeepLClient(..., send_platform_info=False)
562617
```
563618

564-
You can also customize the `user_agent` by setting its value explicitly before constructing your `deepl.Translator` object.
619+
You can also customize the `user_agent` by setting its value explicitly before constructing your `deepl.DeepLClient` object.
565620

566621
```python
567622
deepl.http_client.user_agent = 'my custom user agent'
568-
translator = deepl.Translator(os.environ["DEEPL_AUTH_KEY"])
623+
deepl_client = deepl.DeepLClient(os.environ["DEEPL_AUTH_KEY"])
569624
```
570625

571626
## Command Line Interface

0 commit comments

Comments
 (0)