Making this awesome Google Translate Script work for DeepL Topic is solved

Get help with using AutoHotkey (v1.1 and older) and its commands and hotkeys
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

26 Feb 2021, 12:24

If You can do it in browser then You can repeat it with winhttprequest.
But for me this particular case not actual and not interesting.
BoBo
Posts: 6564
Joined: 13 May 2014, 17:15

Re: Making this awesome Google Translate Script work for DeepL

26 Feb 2021, 12:49

Free use. Use is free of charge up to a text length of 5,000 characters. Commercial customers can use a paid application programming interface to embed DeepL in their software, from €5.99 per month for personal use.
Owner: DeepL GmbH
Re: DeepL kicked me today
Postby bedtime » Mon Jun 29, 2020 1:25 pm

I've used DeepL several times to translate 2000 line documents. It will allow for this. Your problem of being banned is not how much but how often.

I know with Google Translate you need to wait at least 10 seconds between translations if you're going to use it consistently. I suspect this is the same with DeepL. So long as I keep the translations 10-20 seconds apart, I could translate as much as I want—I've translated several 2000 line documents in a row.

Remember, it is not how much but how often. It doesn't matter if you're translating 5000 characters per translation or just 5.

Also, Google and DeepL may allow you to get away with translating every 5 seconds or so, but only for a few dozen translations. Doing this is walking a very thin line and I don't recommend it.

I made a program that uses Google Translate to translate epub books. It grabs as close to 5000 characters as possible and throws it to Google every 12 seconds. These epubs are as small as 20 pages to as large as 450, so far. Never a problem. I've kept the program translating for 17+ hours at a time, and wasn't blocked.

But as soon as I go under the minimum of 10 seconds wait time between translations for about a few dozen translations, I'm banned.

So, you might be interested to use a script similar to this: https://www.autohotkey.com/boards/viewtopic.php?f=10&t=86797 ... that is splitting a text block into chunks of 5000 chars (well, how much is up to you), afterward add a timeout of 10+ seconds before the next request and you might be fine, probably. Good luck :)
Iskander
Posts: 23
Joined: 07 Feb 2017, 06:30

Re: Making this awesome Google Translate Script work for DeepL

26 Feb 2021, 13:20

malcev wrote:
26 Feb 2021, 12:24
If You can do it in browser then You can repeat it with winhttprequest.
But for me this particular case not actual and not interesting.
All designs on a guithab based on the winhttprequest with a repeat of the behavior of the browser - stopped working. Apparently, this is the only option - through IE:

Code: Select all

#SingleInstance Force
#NoEnv
SetBatchLines, -1

;----------------------------------------
LangFrom := "EN"
LangTo := "DE"
;----------------------------------------

rtext =
(
Hello, 

World
)

rtext := DeepLTranslate(rtext,LangIn,LangOut)
msgbox % rtext

DeepLTranslate(Source,LangIn,LangOut)
{
   global LangFrom
   global LangTo
   SetTitleMatchMode, 3

   StringReplace, Source, Source, %A_Space%, `%20, All
   StringReplace, Source, Source, `n, `%0A, All
   LangIn := LangFrom
   LangOut := LangTo
   Base := "www.deepl.com/translator#"
   Path := Base . LangIn . "/" . LangOut . "/" . Source
   IE := ComObjCreate("InternetExplorer.Application")
   IE.Navigate(Path)
   While IE.readyState!=4 || IE.document.readyState!="complete" || IE.busy
      Sleep 50
   While (IE.document.getElementsByClassName("lmt__textarea lmt__target_textarea")[0].innertext = "")
   Sleep 50

   Result := IE.document.getElementsByClassName("lmt__textarea lmt__target_textarea")[0].innertext ; ESTE VALE

   IE.Quit

   Return Result
}
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

26 Feb 2021, 15:07

All designs on a guithab based on the winhttprequest with a repeat of the behavior of the browser - stopped working
Post Your code.
Iskander
Posts: 23
Joined: 07 Feb 2017, 06:30

Re: Making this awesome Google Translate Script work for DeepL

26 Feb 2021, 15:19

Code: Select all

WinHTTP := ComObjCreate("Msxml2.XMLHTTP.6.0")
;WinHTTP := ComObjCreate("WinHTTP.WinHTTPRequest.5.1")

url := "https://www2.deepl.com/jsonrpc"

WinHTTP.Open("POST", url, 0)
If ProxyOrNot
   WinHTTP.SetProxy(2, proxy)
WinHTTP.SetRequestHeader("Pragma", "no-cache")
WinHTTP.SetRequestHeader("Cache-Control", "no-cache, no-store")

WinHTTP.SetRequestHeader("accept", "*/*")
WinHTTP.SetRequestHeader("accept-encoding", "gzip, deflate, br")
WinHTTP.SetRequestHeader("accept-language", "ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7,zh-CN;q=0.6,zh;q=0.5")
WinHTTP.SetRequestHeader("content-length", "737")
WinHTTP.SetRequestHeader("content-type", "application/json")
WinHTTP.SetRequestHeader("cookie", "__cfduid=d54bab8a9ffbb256ed62ed2287d36ffb41613690879; LMTBID=v2|9067e803-f8a5-4191-9ff0-f12f99f524bb|a15d134419ce7ec31b79e4c0ade7194d; privacySettings=%7B%22v%22%3A%221%22%2C%22t%22%3A1614297600%2C%22m%22%3A%22LAX%22%2C%22consent%22%3A%5B%22NECESSARY%22%2C%22PERFORMANCE%22%2C%22COMFORT%22%5D%7D; dapSid=%7B%22sid%22%3A%227b79d2b1-8691-41e1-ab15-2e4da323cd67%22%2C%22lastUpdate%22%3A1614348554%7D; ")
WinHTTP.SetRequestHeader("dnt", "1")
WinHTTP.SetRequestHeader("origin", "https://www.deepl.com ")
WinHTTP.SetRequestHeader("referer", "https://www.deepl.com/ru/translator")
WinHTTP.SetRequestHeader("sec-fetch-mode", "cors")
WinHTTP.SetRequestHeader("sec-fetch-site", "same-site")

WinHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.79 Safari/537.36")
WinHTTP.Send("{""jsonrpc"":""2.0"",""method"": ""LMT_handle_jobs"",""params"":{""jobs"":[{""kind"":""default"",""raw_en_sentence"":""Hello World"",""raw_en_context_before"":[],""raw_en_context_after"":[],""preferred_num_beams"":4,""quality"":""fast""}],""lang"":{""user_preferred_langs"":[""EN"",""RU""],""source_lang_computed"":""EN"",""target_lang"":""RU""},""priority"":-1,""commonJobParams"":{""regionalVariant"":""en-US"",""formality"":null},""timestamp"":1614348558259},""id"":52780804}")

;WinHTTP.WaitForResponse()
ResponseText := WinHTTP.ResponseText
ResponseText := JavaEscapedToHtml(ResponseText)
MsgBox % ResponseText

JavaEscapedToHtml(s) {
    i := 1
    while j := RegExMatch(s, "\\u[A-Fa-f0-9]{1,4}", m, i)
        e .= SubStr(s, i, j-i) Chr("0x" SubStr(m, 3)), i := j + StrLen(m)
    return e . SubStr(s, i)
}
Last edited by BoBo on 26 Feb 2021, 15:36, edited 2 times in total.
Reason: Fixed broken links.
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

26 Feb 2021, 15:41

Your code is the same as from swagfag.
id should not be constant.
Look at c# code from github, or if You dont understand it, look at network requests in browser.
MrHue
Posts: 17
Joined: 01 Oct 2015, 02:51

Re: Making this awesome Google Translate Script work for DeepL

18 Dec 2021, 10:52

Hi Iskander,
It seems DeepL might be monitoring number of attempts of translation coming from a particular IP address.
It doesn't seem to be related to be the id used in the json request or cookies or browser or the interval between attempts.
I was testing the script, each time taking more than 12 seconds before translating and using random id's.
It worked initially but after maybe 20 runs it banned my ip and will not translate even when running manual translations from various web browsers (e.g. Edge, Brave etc)
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

18 Dec 2021, 12:01

Why do You think that id should be random?
MrHue
Posts: 17
Joined: 01 Oct 2015, 02:51

Re: Making this awesome Google Translate Script work for DeepL

22 Dec 2021, 08:49

The github page you pointed to (https://github.com/NightlyRevenger/TataruHelper/tree/master/Translation) initialises the ID to a random number that is then incremented between calls, so that's why I tried random IDs. Not sure if it is truely random though. A fragment of the javascript translator_late.min.$f03af9.js used by the web translator seems to be doing some modulus maths involving timestamp and the length text submitted

Code: Select all

var x = R(n, u).getFunction("LMT_handle_jobs");
                            this._rpc_sendTranslationJobs = function (e, t) {
                                var n = 1,
                                    r = Date.now();
                                return e.jobs && e.jobs.forEach((function (e) {
                                    e.sentences ? e.sentences.forEach((function (e) {
                                        n += ((e.text || "").match(/[i]/g) || []).length
                                    })) : n += ((e.raw_en_sentence || "").match(/[i]/g) || []).length
                                })), i && (e.timestamp = r + (n - r % n)), x(e, t)
                            } 
[Mod edit: [code][/code] tags added.]
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

22 Dec 2021, 14:06

And if You increment this id between calls then You have banned?
When I tried it it worked ok.
MrHue
Posts: 17
Joined: 01 Oct 2015, 02:51

Re: Making this awesome Google Translate Script work for DeepL

23 Dec 2021, 04:22

It works initially but perhaps after twenty tries I got banned. I think after a certain number of non-browser request from an ip, DeepL will ban that ip (I think it's not the time interval between requests, but rather how many times). It should be possible to mimick browser requests but it's rather difficult due to the obscure way that DeepL generates various browser cookies (LMTBID, dapsid, dapuid...) and also some other possible checks involving timestamp and the characteristic/length of the submitted text (see javascript fragment above). The web interface works but for long text DeepL embeds various advertising messages into the translated text which are difficult to remove as the advertising messages are in the translated text language and are variable in length and composition. I tried to register for the free Api but DeepL only allows registration from certain countries (it uses credit card information and it charges 0 Euro to verify the credit card).
Last edited by MrHue on 23 Dec 2021, 04:41, edited 1 time in total.
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

23 Dec 2021, 04:39

You can post Your code and we cat test it.
MrHue
Posts: 17
Joined: 01 Oct 2015, 02:51

Re: Making this awesome Google Translate Script work for DeepL

23 Dec 2021, 04:43

This is the initial code that got banned. The returned text should be translated text in json format.

Code: Select all

DeepL(byref text,source_lang:="ja",target_lang:="zh")		; converts input text to json multisentence format and returns translated text in json format
{
	static DeepLId
	static WinHTTP := ComObjCreate("WinHttp.WinHttpRequest.5.1")
	static lastrun

	if (!waited) || (waited==A_ThisFunc)
		sleep 30000
	waited := A_ThisFunc

	url := "https://www2.deepl.com/jsonrpc"
	if (!DeepLId) || (DeepLId > 83931525)
		Random, DeepLId, 33931525, 53931525

	timestamp := A_NowUTC
	Envsub, timestamp, 19700101, seconds
	timestamp := timestamp*1000 + A_MSec

	WinHTTP.Open("POST", url, 0)
	If ProxyOrNot
		WinHTTP.SetProxy(2, proxy)
	WinHTTP.SetRequestHeader("Pragma", "no-cache")
	WinHTTP.SetRequestHeader("Cache-Control", "no-cache, no-store")

	WinHTTP.SetRequestHeader("accept", "*/*")
	WinHTTP.SetRequestHeader("accept-encoding", "gzip, deflate, br")
	WinHTTP.SetRequestHeader("accept-language", "ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7,zh-CN;q=0.6,zh;q=0.5")
	WinHTTP.SetRequestHeader("content-type", "application/json")
;	WinHTTP.SetRequestHeader("cookie", "__cfduid=d54bab8a9ffbb256ed62ed2287d36ffb41613690879; LMTBID=v2|9067e803-f8a5-4191-9ff0-f12f99f524bb|a15d134419ce7ec31b79e4c0ade7194d; privacySettings=%7B%22v%22%3A%221%22%2C%22t%22%3A1614297600%2C%22m%22%3A%22LAX%22%2C%22consent%22%3A%5B%22NECESSARY%22%2C%22PERFORMANCE%22%2C%22COMFORT%22%5D%7D; dapSid=%7B%22sid%22%3A%227b79d2b1-8691-41e1-ab15-2e4da323cd67%22%2C%22lastUpdate%22%3A1614348554%7D; ")
	WinHTTP.SetRequestHeader("cookie", "LMTBID=v2|0cfec311-37af-46e7-8b16-bab5b604d413|521cd4513eb738de37a0cd52b01eafb3; "
		. "privacySettings=%7B%22v%22%3A%221%22%2C%22t%22%3A1639180800%2C%22m%22%3A%22LAX_AUTO%22%2C%22consent%22%3A%5B%22NECESSARY%22%2C%22PERFORMANCE%22%2C%22COMFORT%22%5D%7D; "
		. "dapSid=%7B%22sid%22%3A%2270804e01-5555-4785-b16e-a7fbabbf7e3a%22%2C%22lastUpdate%22%3A1639841841%7D; "
		. "dapUid=7cd51b65-465a-44c7-8fe8-c7a7e5821ec0; dapVn=2")

	WinHTTP.SetRequestHeader("dnt", "1")
	WinHTTP.SetRequestHeader("origin", "https://www.deepl.com ")
	WinHTTP.SetRequestHeader("referer", "https://www.deepl.com/translator")
	WinHTTP.SetRequestHeader("sec-fetch-mode", "cors")
	WinHTTP.SetRequestHeader("sec-fetch-site", "same-site")
	WinHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.79 Safari/537.36")

	text := StrReplace(text, "`n", "\n")			; convert new lines
	text := StrReplace(text, "`r", "\r")
	WinHTTP.Send("{""jsonrpc"":""2.0"",""method"": ""LMT_split_into_sentences"",""params"":{"
		. """texts"":[""" text """],"
		. """lang"":{""lang_user_selected"":""auto"",""user_preferred_langs"":[""" source_lang """,""" target_lang """],""source_lang_computed"":""" source_lang """,""target_lang"":""" target_lang """},"
		. """priority"":-1,""timestamp"":" timestamp "},""id"":" DeepLId "}")

	text := JavaEscapedToHtml(WinHTTP.ResponseText)		; convert \numeric_codes back to unicode characters for translation
	csv := RegExReplace(text, ".+""splitted_texts"":\[\[")
	csv := RegExReplace(csv, "\]\],""lang"":.+")
	resume := 0

	Loop
	{
		maxlen := 0, jobs:=""
		Loop, Parse, csv, CSV
		{
			if (A_Index<resume)
				continue
			maxlen += StrLen(A_LoopField)
			if (maxlen>5000)		; break if character length > 5000 (limit of translation)
			{
				resume:=A_Index
				break
			}
			if !jobs
			{
				if prev
					jobs := "{""kind"":""default"",""raw_en_sentence"":""" A_LoopField """,""raw_en_context_before"":[""" prev """]"
				else jobs := "{""kind"":""default"",""raw_en_sentence"":""" A_LoopField """"
			}
			else	jobs .= ",""raw_en_context_after"":[""" A_LoopField """]},{""kind"":""default"",""raw_en_sentence"":""" A_LoopField """,""raw_en_context_before"":[""" prev """]"
			prev := A_LoopField
		} 

		if jobs
		{
			timestamp := A_NowUTC
			Envsub, timestamp, 19700101, seconds
			timestamp := timestamp*1000 + A_MSec

			WinHTTP.Open("POST", url, 0)
			If ProxyOrNot
				WinHTTP.SetProxy(2, proxy)
			WinHTTP.SetRequestHeader("Pragma", "no-cache")
			WinHTTP.SetRequestHeader("Cache-Control", "no-cache, no-store")

			WinHTTP.SetRequestHeader("accept", "*/*")
			WinHTTP.SetRequestHeader("accept-encoding", "gzip, deflate, br")
			WinHTTP.SetRequestHeader("accept-language", "ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7,zh-CN;q=0.6,zh;q=0.5")
			WinHTTP.SetRequestHeader("content-type", "application/json")
			WinHTTP.SetRequestHeader("cookie", "__cfduid=d54bab8a9ffbb256ed62ed2287d36ffb41613690879; LMTBID=v2|9067e803-f8a5-4191-9ff0-f12f99f524bb|a15d134419ce7ec31b79e4c0ade7194d; privacySettings=%7B%22v%22%3A%221%22%2C%22t%22%3A1614297600%2C%22m%22%3A%22LAX%22%2C%22consent%22%3A%5B%22NECESSARY%22%2C%22PERFORMANCE%22%2C%22COMFORT%22%5D%7D; dapSid=%7B%22sid%22%3A%227b79d2b1-8691-41e1-ab15-2e4da323cd67%22%2C%22lastUpdate%22%3A1614348554%7D; ")
			WinHTTP.SetRequestHeader("dnt", "1")
			WinHTTP.SetRequestHeader("origin", "https://www.deepl.com ")
			WinHTTP.SetRequestHeader("referer", "https://www.deepl.com/translator")
			WinHTTP.SetRequestHeader("sec-fetch-mode", "cors")
			WinHTTP.SetRequestHeader("sec-fetch-site", "same-site")
			WinHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/79.0.3945.79 Safari/537.36")

			jobs .= ",""raw_en_context_after"":[]}"
			WinHTTP.Send("{""jsonrpc"":""2.0"",""method"": ""LMT_handle_jobs"",""params"":{""jobs"":[" jobs "],""lang"":{""user_preferred_langs"":[""" source_lang """,""" target_lang """],""source_lang_computed"":""" source_lang """,""target_lang"":""" target_lang """},""priority"":-1,""timestamp"":" timestamp "},""id"":" DeepLId "}")
			DeepLId++
		} else break

		; other json options
		; WinHTTP.Send("{""jsonrpc"":""2.0"",""method"": ""LMT_handle_jobs"",""params"":{""jobs"":[{""kind"":""default"",""raw_en_sentence"":""Hello World"",""raw_en_context_before"":[],""raw_en_context_after"":[],""preferred_num_beams"":4,""quality"":""fast""}],""lang"":{""user_preferred_langs"":[""EN"",""RU""],""source_lang_computed"":""EN"",""target_lang"":""RU""},""priority"":-1,""commonJobParams"":{""regionalVariant"":""en-US"",""formality"":null},""timestamp"":" timestamp "},""id"":" DeepLId "}")

		; example multisentence json
		;	WinHTTP.Send("{""jsonrpc"":""2.0"",""method"": ""LMT_handle_jobs"",""params"":{""jobs"":["
		;	. "{""kind"":""default"",""raw_en_sentence"":""" s[1] """,""raw_en_context_before"":[],""raw_en_context_after"":[""" s[2] """],""preferred_num_beams"":4,""quality"":""fast""},"
		;	. "{""kind"":""default"",""raw_en_sentence"":""" s[2] """,""raw_en_context_before"":[""" s[1] """],""raw_en_context_after"":[],""preferred_num_beams"":4,""quality"":""fast""}"
		;	. "],""lang"":{""user_preferred_langs"":[""" source_lang """,""" target_lang """],""source_lang_computed"":""" source_lang """,""target_lang"":""" target_lang """},""priority"":-1,""timestamp"":" timestamp "},""id"":" DeepLId "}")

		;WinHTTP.WaitForResponse()
		Translated .= JavaEscapedToHtml(WinHTTP.ResponseText)
		if resume
		{
			Menu,Tray,Tip,Done segment %A_Index%...`nWaiting 20 secs before next segment.
			sleep 20000		; wait 20 seconds to avoid being banned ("too many requests")
		}
	} until !resume
	lastrun := A_Now
	return Translated
}

JavaEscapedToHtml(s) {
    i := 1
    while j := RegExMatch(s, "\\u[A-Fa-f0-9]{1,4}", m, i)
        e .= SubStr(s, i, j-i) Chr("0x" SubStr(m, 3)), i := j + StrLen(m)
    return e . SubStr(s, i)
}
The code below works by using IE. However, for long text DeepL will embed advertising messages. (Random sentence about contacting DeepL appears due to Japanese punctuation. https://github.com/Artikash/Textractor/issues/547 )

Code: Select all

global waited
DeepLTranslate(byref text,source_lang:="ja",target_lang:="zh")
{
	static ie
	if (!waited) || (waited==A_ThisFunc)
		sleep 30000
	waited := A_ThisFunc
	if !ie
	{
		if WinExist("DeepL Translate: The world's most accurate translator - Internet Explorer")
			IE := WBGet("DeepL Translate: The world's most accurate translator - Internet Explorer")
		if !ie
		{
			Path := "https://www.deepl.com/en/translator/l/" source_lang "/" target_lang
			IE := ComObjCreate("InternetExplorer.Application")
			IE.Navigate(Path)
		}

		While IE.readyState!=4 || IE.document.readyState!="complete" || IE.busy
			Sleep 50
	}

	IE.visible := 1
	sleep 1000
	IE.document.getElementsByClassName("lmt__textarea lmt__source_textarea lmt__textarea_base_style")[0].innertext := text
	sleep 12000
	While (IE.document.getElementsByClassName("lmt__textarea lmt__target_textarea")[0].innertext = "")
		Sleep 50
	translated := IE.document.getElementsByClassName("lmt__textarea lmt__target_textarea")[0].innertext
	return translated
}
This is my most recent attempt, trying to use IE to generate cookies to mimick the browser and then send json requests. I haven't tested it yet because the IE generated cookies is missing the LMTBID cookie. Also browser sends a LMT_handleAdditionalData json request at the end of a translation. It seems to be for stats but not sure if DeepL uses it to check if a request is valid.

Code: Select all

global waited
DeepLJson(byref text, from:="ja", to:="zh")
{
	static ie, cookies, id
	static WinHTTP := ComObjCreate("WinHttp.WinHttpRequest.5.1")
	if (!id) || (id > 83931525)
		Random, id, 33931525, 53931525

	textdata := trim(RegExReplace(text,"[`r`n]+",""","""),",""`r`n`t ")
	data = {"jsonrpc":"2.0","method": "LMT_split_text","params":{"texts":["%textdata%"],"lang":{"lang_user_selected":"%from%","preference":{"weight":{"DE":0.15461,"EN":0.33316,"ES":0.08041,"FR":0.1162,"IT":0.02247,"JA":4.60334,"NL":0.02205,"PL":0.01143,"PT":0.01181,"RU":0.01317,"ZH":1.87751,"BG":0,"CS":0,"DA":0,"EL":0,"ET":0,"FI":0,"HU":0,"LV":0,"LT":0,"RO":0,"SK":0,"SL":0,"SV":0},"default":"default"},"selected":"%from%"}},"id":%id%}

	if (!waited) || (waited==A_ThisFunc)
		sleep 30000
	waited := A_ThisFunc
	if !ie
	{	; DeepL uses jscript to create cookies so run it using IE to get all the cookies
		Path := "https://www.deepl.com/en/translator/l/" source_lang "/" target_lang
		IE := ComObjCreate("InternetExplorer.Application")
		IE.Navigate(Path)

		While IE.readyState!=4 || IE.document.readyState!="complete" || IE.busy
			Sleep 50
		cookies := IE.document.cookie
		IE.visible := True
		msgbox % cookies	; IE.document.parentWindow.dapsid
	}
	WinHTTP.Open("POST", "https://www2.deepl.com/jsonrpc?method=LMT_split_text", 0)
	WinHTTP.SetRequestHeader("content-type", "application/json; charset=utf-8")
	WinHTTP.SetRequestHeader("cookie", cookies)
	WinHTTP.SetRequestHeader("origin", "https://www.deepl.com")
	WinHTTP.SetRequestHeader("referer", "https://www.deepl.com/")
	WinHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; WOW64; Trident/7.0; rv:11.0) like Gecko")
	WinHTTP.SetRequestHeader("sec-fetch-dest", "empty")
	WinHTTP.SetRequestHeader("sec-fetch-mode", "cors")
	WinHTTP.SetRequestHeader("sec-fetch-site", "same-site")
	WinHTTP.SetRequestHeader("sec-gpc", "1")
	WinHTTP.Send(data)
	text := JavaEscapedToHtml(WinHTTP.ResponseText)		; convert \numeric_codes back to unicode characters for translation
	resume := 0, pos:=1, tid:=0
	id++

	Loop
	{
		maxlen := 0, jobs:="", after:=""
		while newpos:=RegExMatch(text,"text"":""\K[^""]+", sentence, pos)
		{
			len := StrLen(sentence)
			maxlen += len
			if (maxlen>1000)		; break if character length > 1000 
			{				; (5000 is limit of translation but web page actually splits the text and does multiple request roughly 1000 chars at a time so we do the same)
				after := sentence
				break
			} 
			if jobs
				jobs .= ",""raw_en_context_after"":[""" sentence """],""preferred_num_beams"":1},"
			jobs .= "{""kind"":""default"",""sentences"":[{""text"":""" sentence """,""id"":" tid ",""prefix"":""""}],""raw_en_context_before"":[""" prev """]"
			tid++
			prev1 := prev2 
			prev2 := prev3
			prev3 := prev4
			prev4 := sentence 
			prev := trim(prev1 "," prev2 "," prev3 "," prev4, ",")
			pos := newpos + len
		} 

		if jobs
		{
			timestamp := A_NowUTC
			Envsub, timestamp, 1970, seconds
			timestamp := timestamp*1000 + A_MSec

			WinHTTP.Open("POST", "https://www2.deepl.com/jsonrpc?method=LMT_handle_jobs", 0)
			WinHTTP.SetRequestHeader("accept", "*/*")
			WinHTTP.SetRequestHeader("accept-encoding", "gzip, deflate, br")
			WinHTTP.SetRequestHeader("accept-language", "ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7,zh-CN;q=0.6,zh;q=0.5")
			WinHTTP.SetRequestHeader("content-type", "application/json")
			WinHTTP.SetRequestHeader("cookie",cookies)
			WinHTTP.SetRequestHeader("origin", "https://www.deepl.com ")
			WinHTTP.SetRequestHeader("referer", "https://www.deepl.com/")
			WinHTTP.SetRequestHeader("sec-fetch-dest", "empty")
			WinHTTP.SetRequestHeader("sec-fetch-mode", "cors")
			WinHTTP.SetRequestHeader("sec-fetch-site", "same-site")
			WinHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; WOW64; Trident/7.0; rv:11.0) like Gecko")

			jobs .= ",""raw_en_context_after"":[""" after """]}"
			StringUpper, from, from
			StringUpper, to, to
			WinHTTP.Send("{""jsonrpc"":""2.0"",""method"": ""LMT_handle_jobs"",""params"":{""jobs"":[" jobs "],"
				. """lang"":{""preference"":{""weight"":{},""default"":""default""},""source_lang_computed"":""" from """,""target_lang"":""" to """},""priority"":1,""commonJobParams"":{""browserType"":1,""formality"":null},""timestamp"":" timestamp "},""id"":" id "}")
			id++
		} else break

		Translated .= JavaEscapedToHtml(WinHTTP.ResponseText)
		if after
		{
			Menu,Tray,Tip,Done segment %A_Index%...`nWaiting 20 secs before next segment.
			sleep 30000		; wait 20 seconds to avoid being banned ("too many requests")
		}
	} until !after

	WinHTTP.Open("POST", "https://www2.deepl.com/jsonrpc?method=LMT_handleAdditionalData", 0)
	WinHTTP.SetRequestHeader("content-type", "application/json")
	WinHTTP.SetRequestHeader("cookie",cookies)
	WinHTTP.SetRequestHeader("origin", "https://www.deepl.com ")
	WinHTTP.SetRequestHeader("referer", "https://www.deepl.com/")
	WinHTTP.SetRequestHeader("sec-fetch-dest", "empty")
	WinHTTP.SetRequestHeader("sec-fetch-mode", "cors")
	WinHTTP.SetRequestHeader("sec-fetch-site", "same-site")
	WinHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; WOW64; Trident/7.0; rv:11.0) like Gecko")
	WinHTTP.Send()
	return Translated
}

JavaEscapedToHtml(s) {
    i := 1
    while j := RegExMatch(s, "\\u[A-Fa-f0-9]{1,4}", m, i)
        e .= SubStr(s, i, j-i) Chr("0x" SubStr(m, 3)), i := j + StrLen(m)
    return e . SubStr(s, i)
}
Note that once I got banned, even my browser requests and translation attempts using the DeepL app got banned, so the ban is probably IP based, so be careful with trying out the code.
Last edited by MrHue on 24 Dec 2021, 02:09, edited 1 time in total.
malcev
Posts: 1769
Joined: 12 Aug 2014, 12:37

Re: Making this awesome Google Translate Script work for DeepL

23 Dec 2021, 20:28

I tested and see that deepl increase their protection.
You can try download and install on virtual machine this software
https://github.com/NightlyRevenger/TataruHelper/releases/latest/download/Setup.exe
(may be it contains some viruses, who knows).
Test deepl engine and if it works, convert source to ahk.
https://github.com/NightlyRevenger/TataruHelper
MrHue
Posts: 17
Joined: 01 Oct 2015, 02:51

Re: Making this awesome Google Translate Script work for DeepL

24 Dec 2021, 00:57

Thank you. I couldn't test the program because I don't have Final Fantasy XIV installed but I see the program source was changed a few days ago. I will change my ID generation to try match the algorithm that it is using.

Code: Select all

Random Rnd;
Rnd = new Random((int)Math.Round(DateTime.Now.TimeOfDay.TotalMilliseconds)); // Seed
...
 long baseIdMult = 10000;
 ...
 _DeepLId = baseIdMult * (long)Math.Round((double)baseIdMult * Rnd.NextDouble());
Converted to ahk should be

Code: Select all

Random,,A_Hour*3600 + A_Min*60 + A_Sec + Round(A_MSec/1000)
Random, Rnd, 0.0, 1.0
id := 10000 * Round(10000 * Rnd)
Changed the json ID generation code, increased the wait between requests to 60 seconds and reduced the length of the text to translate but get "too many requests" error after two translations. So far there's no ip ban but I didn't retry the json requests after getting the "too many requests" error. The only thing that works at the moment is still translation using Internet Explorer.
mickbiden2
Posts: 1
Joined: 28 Dec 2021, 06:45

Re: Making this awesome Google Translate Script work for DeepL

28 Dec 2021, 07:01

I would really appreciate it. Please kindly try to use shortcuts that are not used, such as AltZ or AltX hellodear.in

teatv.ltd
mumulu
Posts: 7
Joined: 17 Mar 2023, 13:41

Re: Making this awesome Google Translate Script work for DeepL

17 Mar 2023, 14:28

As to a working DeepL script (Alt + T), it is possible to get a free API key from DeepL (for developers). You get 500,000 characters per month. I tried a script, it still has errors because I am very bad in scripting. Maybe there are only some silly errors and somebody with more knowledge can make it work:

-----------------------------------------------------------------------------------------------

Code: Select all

; Define the DeepL function at the beginning of the script
DeepL(text,EN,DE) {HERE COMES THE API KEY}

; Define the DeeplTranslate function
DeeplTranslate() {HERE COMES THE API KEY
    ; Call the DeepL function inside the DeeplTranslate function
    DeepL(text,EN,DE)
}



UriEncode(string) { 
; This function encodes a string for a URL request. 
Loop Parse string result .= (A_LoopField = "") ? Chr(A_Index + 31) : UriChar(A_LoopField) return result }

UriChar(char) { static chars = "0123456789ABCDEF" if char is alnum return char else if char = " " return "+" else { code := Ord(char) return "%" . SubStr(chars,(code >> 4)+1 ,1) . SubStr(chars,(code & 15)+1 ,1) } } 


DeepL(text,EN,DE) 
; This function sends a request to deepl.com and returns the translation 
{ static WinHTTP := ComObjCreate("WinHttp.WinHttpRequest.5.1") 
; Create a WinHTTP object 
url := "https://api-free.deepl.com/v2/translate" 
; The URL for the Deepl API 
params := "auth_key=[HERE COMES THE API KEY]&text=" UriEncode(text) "&source_lang=" EN "&target_lang=" DE 
; The parameters for the request 
WinHTTP.Open("POST", url) 
; Open a POST request 
WinHTTP.SetRequestHeader("Content-Type", "application/x-www-form-urlencoded") 
; Set the Content-Type header 
WinHTTP.Send(params) 
; Send the parameters 
WinHTTP.WaitForResponse() 
; Wait for an answer

response := WinHTTP.ResponseText 
; Save the answer as text 
json := JSON.Load(response) 
; Load the response as a JSON object
return json.translations1.text 
; Return the first translated text 
}


!t:: 
ClipSaved := ClipboardAll 
; Save the current content of the clipboard 
Clipboard := "" 
; Empty the clipboard 
Send ^c 
; Copy the selected text 
ClipWait 
; Wait for the text in the clipboard 
Text := Clipboard 
; Save the text in a variable 
Clipboard := ClipSaved 
; Restore the clipboard

Translation := DeepL(Text,"EN","DE") 
; Call the Deepl function to translate the text

Send ^v 
; Insert the translation 
return


Return to “Ask for Help (v1)”

Who is online

Users browsing this forum: Hansielein, Lpanatt and 311 guests