@@ -18,13 +18,20 @@ class EngineConfig(BaseModel):
1818 """Configuration for the LingoDotDevEngine"""
1919
2020 api_key : str
21+ engine_id : Optional [str ] = None
2122 api_url : str = "https://engine.lingo.dev"
2223 batch_size : int = Field (default = 25 , ge = 1 , le = 250 )
2324 ideal_batch_item_size : int = Field (default = 250 , ge = 1 , le = 2500 )
2425
25- @validator ("api_url" )
26+ @validator ("api_url" , pre = True , always = True )
2627 @classmethod
27- def validate_api_url (cls , v : str ) -> str :
28+ def validate_api_url (cls , v : Optional [str ], values : Dict [str , Any ]) -> str :
29+ if v is None or v == "https://engine.lingo.dev" :
30+ engine_id = values .get ("engine_id" )
31+ if engine_id :
32+ return "https://api.lingo.dev"
33+ if v is None :
34+ return "https://engine.lingo.dev"
2835 if not v .startswith (("http://" , "https://" )):
2936 raise ValueError ("API URL must be a valid HTTP/HTTPS URL" )
3037 return v
@@ -55,6 +62,11 @@ def __init__(self, config: Dict[str, Any]):
5562 """
5663 self .config = EngineConfig (** config )
5764 self ._client : Optional [httpx .AsyncClient ] = None
65+ self ._session_id : str = generate ()
66+
67+ @property
68+ def _is_vnext (self ) -> bool :
69+ return self .config .engine_id is not None
5870
5971 async def __aenter__ (self ):
6072 """Async context manager entry"""
@@ -68,10 +80,14 @@ async def __aexit__(self, exc_type, exc_val, exc_tb):
6880 async def _ensure_client (self ):
6981 """Ensure the httpx client is initialized"""
7082 if self ._client is None or self ._client .is_closed :
83+ if self ._is_vnext :
84+ auth_header = {"X-API-Key" : self .config .api_key }
85+ else :
86+ auth_header = {"Authorization" : f"Bearer { self .config .api_key } " }
7187 self ._client = httpx .AsyncClient (
7288 headers = {
7389 "Content-Type" : "application/json; charset=utf-8" ,
74- "Authorization" : f"Bearer { self . config . api_key } " ,
90+ ** auth_header ,
7591 },
7692 timeout = 60.0 ,
7793 )
@@ -200,16 +216,27 @@ async def _localize_chunk(
200216 """
201217 await self ._ensure_client ()
202218 assert self ._client is not None # Type guard for mypy
203- url = urljoin (self .config .api_url , "/i18n" )
204-
205- request_data = {
206- "params" : {"workflowId" : workflow_id , "fast" : fast },
207- "locale" : {"source" : source_locale , "target" : target_locale },
208- "data" : payload ["data" ],
209- }
210219
211- if payload .get ("reference" ):
212- request_data ["reference" ] = payload ["reference" ]
220+ if self ._is_vnext :
221+ url = f"{ self .config .api_url } /process/{ self .config .engine_id } /localize"
222+ request_data : Dict [str , Any ] = {
223+ "params" : {"fast" : fast },
224+ "sourceLocale" : source_locale ,
225+ "targetLocale" : target_locale ,
226+ "data" : payload ["data" ],
227+ "sessionId" : self ._session_id ,
228+ }
229+ if payload .get ("reference" ):
230+ request_data ["reference" ] = payload ["reference" ]
231+ else :
232+ url = urljoin (self .config .api_url , "/i18n" )
233+ request_data = {
234+ "params" : {"workflowId" : workflow_id , "fast" : fast },
235+ "locale" : {"source" : source_locale , "target" : target_locale },
236+ "data" : payload ["data" ],
237+ }
238+ if payload .get ("reference" ):
239+ request_data ["reference" ] = payload ["reference" ]
213240
214241 try :
215242 response = await self ._client .post (url , json = request_data )
@@ -455,7 +482,11 @@ async def recognize_locale(self, text: str) -> str:
455482
456483 await self ._ensure_client ()
457484 assert self ._client is not None # Type guard for mypy
458- url = urljoin (self .config .api_url , "/recognize" )
485+
486+ if self ._is_vnext :
487+ url = f"{ self .config .api_url } /process/recognize"
488+ else :
489+ url = urljoin (self .config .api_url , "/recognize" )
459490
460491 try :
461492 response = await self ._client .post (url , json = {"text" : text })
@@ -487,10 +518,17 @@ async def whoami(self) -> Optional[Dict[str, str]]:
487518 """
488519 await self ._ensure_client ()
489520 assert self ._client is not None # Type guard for mypy
490- url = urljoin (self .config .api_url , "/whoami" )
521+
522+ if self ._is_vnext :
523+ url = f"{ self .config .api_url } /users/me"
524+ else :
525+ url = urljoin (self .config .api_url , "/whoami" )
491526
492527 try :
493- response = await self ._client .post (url )
528+ if self ._is_vnext :
529+ response = await self ._client .get (url )
530+ else :
531+ response = await self ._client .post (url )
494532
495533 if response .is_success :
496534 payload = self ._safe_parse_json (response )
@@ -541,6 +579,7 @@ async def quick_translate(
541579 source_locale : Optional [str ] = None ,
542580 api_url : str = "https://engine.lingo.dev" ,
543581 fast : bool = True ,
582+ engine_id : Optional [str ] = None ,
544583 ) -> Any :
545584 """
546585 Quick one-off translation without manual context management.
@@ -572,10 +611,12 @@ async def quick_translate(
572611 "es"
573612 )
574613 """
575- config = {
614+ config : Dict [ str , Any ] = {
576615 "api_key" : api_key ,
577616 "api_url" : api_url ,
578617 }
618+ if engine_id :
619+ config ["engine_id" ] = engine_id
579620
580621 async with cls (config ) as engine :
581622 params = {
@@ -600,6 +641,7 @@ async def quick_batch_translate(
600641 source_locale : Optional [str ] = None ,
601642 api_url : str = "https://engine.lingo.dev" ,
602643 fast : bool = True ,
644+ engine_id : Optional [str ] = None ,
603645 ) -> List [Any ]:
604646 """
605647 Quick batch translation to multiple target locales.
@@ -624,10 +666,12 @@ async def quick_batch_translate(
624666 )
625667 # Results: ["Hola mundo", "Bonjour le monde", "Hallo Welt"]
626668 """
627- config = {
669+ config : Dict [ str , Any ] = {
628670 "api_key" : api_key ,
629671 "api_url" : api_url ,
630672 }
673+ if engine_id :
674+ config ["engine_id" ] = engine_id
631675
632676 async with cls (config ) as engine :
633677 if isinstance (content , str ):
0 commit comments