@belocal/js-sdk 0.1.8 → 0.1.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,7 +1,78 @@
1
1
  # @belocal/js-sdk
2
2
 
3
- Runtime JS SDK for on-demand translation (browser + node).
3
+ Runtime JS SDK for on-demand translation with platform-specific builds.
4
4
 
5
5
  ## Install
6
6
  ```bash
7
- npm i @belocal/js-sdk
7
+ npm i @belocal/js-sdk
8
+ ```
9
+
10
+ ## Usage
11
+
12
+ The SDK automatically selects the optimal build for your environment:
13
+
14
+ ```javascript
15
+ import { BelocalEngine } from '@belocal/js-sdk';
16
+
17
+ const engine = new BelocalEngine({
18
+ apiKey: 'your-api-key'
19
+ });
20
+
21
+ const translated = await engine.t('Hello world', 'es');
22
+ console.log(translated); // "Hola mundo"
23
+ ```
24
+
25
+ ### Options
26
+
27
+ ```javascript
28
+ const engine = new BelocalEngine({
29
+ apiKey: 'your-api-key', // Required: Your BeLocal API key
30
+ debug: false // Optional: Enable debug logging
31
+ });
32
+ ```
33
+
34
+ ### Translation with Context
35
+ ```javascript
36
+ const translated = await engine.t(
37
+ 'Hello {name}!',
38
+ 'es',
39
+ { name: 'María' }
40
+ );
41
+ console.log(translated); // "¡Hola María!"
42
+ ```
43
+
44
+ ## Automatic Environment Detection
45
+
46
+ The SDK uses conditional exports to automatically load the optimal build:
47
+
48
+ - **Browser environments**: Uses `fetch` API with optimized bundle size (~1.3KB)
49
+ - **Node.js environments**: Uses HTTP/2 with connection pooling and automatic retries (~4.3KB)
50
+ - **CommonJS**: Supported in both environments
51
+
52
+ ## Build Outputs
53
+
54
+ | File | Environment | Format | Size | Features |
55
+ |------|-------------|--------|------|----------|
56
+ | `browser.mjs` | Browser | ESM | ~1.3KB | Fetch API, minified |
57
+ | `browser.cjs` | Browser | CJS | ~1.3KB | Fetch API, minified |
58
+ | `node.mjs` | Node.js | ESM | ~4.3KB | HTTP/2, retries |
59
+ | `node.cjs` | Node.js | CJS | ~4.8KB | HTTP/2, retries |
60
+
61
+ ## TypeScript Support
62
+
63
+ Full TypeScript support with exported types:
64
+
65
+ ```typescript
66
+ import { BelocalEngine, type BelocalEngineOptions, type Lang, type KV } from '@belocal/js-sdk';
67
+
68
+ const options: BelocalEngineOptions = {
69
+ apiKey: 'your-api-key',
70
+ debug: true
71
+ };
72
+
73
+ const engine = new BelocalEngine(options);
74
+ ```
75
+
76
+ ## License
77
+
78
+ MIT
@@ -0,0 +1,3 @@
1
+ 'use strict';function p(r){return async({text:t,lang:e,ctx:o})=>{let n=`${r.baseUrl}${r.path}`,a=new AbortController,i=r.timeoutMs?setTimeout(()=>a.abort(),r.timeoutMs):null;r.debug&&console.log(`[BeLocal Browser Transport] Translating "${t}" to ${e} with url ${n}`);try{let s=await fetch(n,{method:"POST",headers:{"Content-Type":"application/json",...r.headers},body:JSON.stringify({text:t,lang:e,ctx:o}),signal:a.signal});if(!s.ok){let u=`HTTP ${s.status}: ${s.statusText}`;throw r.debug&&console.error("[BeLocal Browser Transport] Request failed:",u),new Error(u)}let l=await s.json();return r.debug&&console.log(`[BeLocal Browser Transport] Translation successful: "${l.text||t}"`),l.text||t}finally{i&&clearTimeout(i);}}}var c=class{constructor(t){let{apiKey:e,baseUrl:o="https://dynamic.belocal.dev",path:n="/v1/translate",timeoutMs:a=1e4,debug:i=false}=t;this.debug=i;let s={Authorization:`Bearer ${e}`};this.transport=p({baseUrl:o,path:n,headers:s,timeoutMs:a,debug:this.debug}),this.debug&&console.log("[BeLocal Engine] Browser transport created with config:",{baseUrl:o,path:n,timeoutMs:a});}async t(t,e,o){return this.transport({text:t,lang:e,ctx:o})}};
2
+ exports.BelocalEngine=c;exports.createBrowserTransport=p;//# sourceMappingURL=browser.cjs.map
3
+ //# sourceMappingURL=browser.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/transports/browser.ts","../src/core/engine/browser.ts"],"names":["createBrowserTransport","config","text","lang","ctx","url","controller","timeoutId","response","errorMsg","result","BelocalEngine","options","apiKey","baseUrl","path","timeoutMs","debug","authHeaders"],"mappings":"aAUO,SAASA,CAAAA,CAAuBC,CAAAA,CAA2C,CAChF,OAAO,MAAO,CAAE,IAAA,CAAAC,CAAAA,CAAM,IAAA,CAAAC,CAAAA,CAAM,GAAA,CAAAC,CAAI,IAAM,CACpC,IAAMC,CAAAA,CAAM,CAAA,EAAGJ,CAAAA,CAAO,OAAO,GAAGA,CAAAA,CAAO,IAAI,CAAA,CAAA,CACrCK,CAAAA,CAAa,IAAI,eAAA,CACjBC,EAAYN,CAAAA,CAAO,SAAA,CAAY,UAAA,CAAW,IAAMK,CAAAA,CAAW,KAAA,GAASL,CAAAA,CAAO,SAAS,CAAA,CAAI,IAAA,CAE1FA,CAAAA,CAAO,KAAA,EACT,QAAQ,GAAA,CAAI,CAAA,yCAAA,EAA4CC,CAAI,CAAA,KAAA,EAAQC,CAAI,CAAA,UAAA,EAAaE,CAAG,CAAA,CAAE,CAAA,CAG5F,GAAI,CACF,IAAMG,CAAAA,CAAW,MAAM,MAAMH,CAAAA,CAAK,CAChC,MAAA,CAAQ,MAAA,CACR,OAAA,CAAS,CACP,eAAgB,kBAAA,CAChB,GAAGJ,CAAAA,CAAO,OACZ,CAAA,CACA,IAAA,CAAM,KAAK,SAAA,CAAU,CAAE,IAAA,CAAAC,CAAAA,CAAM,IAAA,CAAAC,CAAAA,CAAM,GAAA,CAAAC,CAAI,CAAC,CAAA,CACxC,MAAA,CAAQE,CAAAA,CAAW,MACrB,CAAC,EAED,GAAI,CAACE,CAAAA,CAAS,EAAA,CAAI,CAChB,IAAMC,EAAW,CAAA,KAAA,EAAQD,CAAAA,CAAS,MAAM,CAAA,EAAA,EAAKA,CAAAA,CAAS,UAAU,GAChE,MAAIP,CAAAA,CAAO,KAAA,EACT,OAAA,CAAQ,KAAA,CAAM,6CAAA,CAA+CQ,CAAQ,CAAA,CAEjE,IAAI,KAAA,CAAMA,CAAQ,CAC1B,CAEA,IAAMC,EAAS,MAAMF,CAAAA,CAAS,IAAA,EAAK,CACnC,OAAIP,CAAAA,CAAO,OACT,OAAA,CAAQ,GAAA,CAAI,CAAA,qDAAA,EAAwDS,CAAAA,CAAO,IAAA,EAAQR,CAAI,GAAG,CAAA,CAErFQ,CAAAA,CAAO,IAAA,EAAQR,CACxB,CAAA,OAAE,CACIK,CAAAA,EACF,YAAA,CAAaA,CAAS,EAE1B,CACF,CACF,CC/CO,IAAMI,EAAN,KAAoB,CAIzB,WAAA,CAAYC,CAAAA,CAA+B,CACzC,GAAM,CACJ,MAAA,CAAAC,CAAAA,CACA,OAAA,CAAAC,CAAAA,CAAU,6BAAA,CACV,IAAA,CAAAC,EAAO,eAAA,CACP,SAAA,CAAAC,CAAAA,CAAY,GAAA,CACZ,KAAA,CAAAC,CAAAA,CAAQ,KACV,CAAA,CAAIL,CAAAA,CAEJ,IAAA,CAAK,KAAA,CAAQK,CAAAA,CAEb,IAAMC,CAAAA,CAAc,CAClB,aAAA,CAAiB,CAAA,OAAA,EAAUL,CAAM,CAAA,CACnC,CAAA,CAEA,IAAA,CAAK,UAAYb,CAAAA,CAAuB,CACtC,OAAA,CAAAc,CAAAA,CACA,IAAA,CAAAC,CAAAA,CACA,QAASG,CAAAA,CACT,SAAA,CAAAF,CAAAA,CACA,KAAA,CAAO,IAAA,CAAK,KACd,CAAC,CAAA,CAEG,IAAA,CAAK,KAAA,EACP,OAAA,CAAQ,GAAA,CAAI,yDAAA,CAA2D,CACrE,QAAAF,CAAAA,CACA,IAAA,CAAAC,CAAAA,CACA,SAAA,CAAAC,CACF,CAAC,EAEL,CAEA,MAAM,CAAA,CAAEd,CAAAA,CAAcC,CAAAA,CAAYC,CAAAA,CAA2B,CAC3D,OAAO,IAAA,CAAK,SAAA,CAAU,CAAE,IAAA,CAAAF,CAAAA,CAAM,IAAA,CAAAC,CAAAA,CAAM,GAAA,CAAAC,CAAI,CAAC,CAC3C,CACF","file":"browser.cjs","sourcesContent":["import type { Transport } from '../core/types';\n\nexport interface BrowserTransportConfig {\n baseUrl: string;\n path?: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n debug?: boolean;\n}\n\nexport function createBrowserTransport(config: BrowserTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const url = `${config.baseUrl}${config.path}`;\n const controller = new AbortController();\n const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;\n\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translating \"${text}\" to ${lang} with url ${url}`);\n }\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...config.headers,\n },\n body: JSON.stringify({ text, lang, ctx }),\n signal: controller.signal,\n });\n\n if (!response.ok) {\n const errorMsg = `HTTP ${response.status}: ${response.statusText}`;\n if (config.debug) {\n console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);\n }\n throw new Error(errorMsg);\n }\n\n const result = await response.json();\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } finally {\n if (timeoutId) {\n clearTimeout(timeoutId);\n }\n }\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from '../types';\nimport { createBrowserTransport } from '../../transports/browser';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n timeoutMs = 10000,\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`\n };\n\n this.transport = createBrowserTransport({\n baseUrl,\n path,\n headers: authHeaders,\n timeoutMs,\n debug: this.debug\n });\n\n if (this.debug) {\n console.log('[BeLocal Engine] Browser transport created with config:', {\n baseUrl,\n path,\n timeoutMs\n });\n }\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n}\n\n// Re-export types and transport\nexport type { BelocalEngineOptions, Lang, KV } from '../types';\nexport { createBrowserTransport } from '../../transports/browser';\n"]}
@@ -1,27 +1,33 @@
1
1
  type Lang = string;
2
2
  type KV = Record<string, unknown>;
3
+ type Transport = (params: {
4
+ text: string;
5
+ lang: Lang;
6
+ ctx?: KV;
7
+ }) => Promise<string>;
3
8
  interface BelocalEngineOptions {
4
9
  apiKey: string;
5
10
  baseUrl?: string;
6
11
  path?: string;
7
- transport?: 'browser' | 'node' | 'auto';
8
12
  timeoutMs?: number;
9
13
  retries?: number;
10
- credentials?: RequestCredentials;
14
+ debug?: boolean;
15
+ }
16
+
17
+ interface BrowserTransportConfig {
18
+ baseUrl: string;
19
+ path?: string;
11
20
  headers?: Record<string, string>;
21
+ timeoutMs?: number;
12
22
  debug?: boolean;
13
23
  }
24
+ declare function createBrowserTransport(config: BrowserTransportConfig): Transport;
14
25
 
15
26
  declare class BelocalEngine {
16
27
  private transport;
17
28
  private debug;
18
29
  constructor(options: BelocalEngineOptions);
19
30
  t(text: string, lang: Lang, ctx?: KV): Promise<string>;
20
- private createTransport;
21
- /**
22
- * Автоматически определяет среду выполнения
23
- */
24
- private detectEnvironment;
25
31
  }
26
32
 
27
- export { BelocalEngine, type BelocalEngineOptions, type KV, type Lang };
33
+ export { BelocalEngine, type BelocalEngineOptions, type KV, type Lang, createBrowserTransport };
@@ -0,0 +1,3 @@
1
+ function p(r){return async({text:t,lang:e,ctx:o})=>{let n=`${r.baseUrl}${r.path}`,a=new AbortController,i=r.timeoutMs?setTimeout(()=>a.abort(),r.timeoutMs):null;r.debug&&console.log(`[BeLocal Browser Transport] Translating "${t}" to ${e} with url ${n}`);try{let s=await fetch(n,{method:"POST",headers:{"Content-Type":"application/json",...r.headers},body:JSON.stringify({text:t,lang:e,ctx:o}),signal:a.signal});if(!s.ok){let u=`HTTP ${s.status}: ${s.statusText}`;throw r.debug&&console.error("[BeLocal Browser Transport] Request failed:",u),new Error(u)}let l=await s.json();return r.debug&&console.log(`[BeLocal Browser Transport] Translation successful: "${l.text||t}"`),l.text||t}finally{i&&clearTimeout(i);}}}var c=class{constructor(t){let{apiKey:e,baseUrl:o="https://dynamic.belocal.dev",path:n="/v1/translate",timeoutMs:a=1e4,debug:i=false}=t;this.debug=i;let s={Authorization:`Bearer ${e}`};this.transport=p({baseUrl:o,path:n,headers:s,timeoutMs:a,debug:this.debug}),this.debug&&console.log("[BeLocal Engine] Browser transport created with config:",{baseUrl:o,path:n,timeoutMs:a});}async t(t,e,o){return this.transport({text:t,lang:e,ctx:o})}};
2
+ export{c as BelocalEngine,p as createBrowserTransport};//# sourceMappingURL=browser.mjs.map
3
+ //# sourceMappingURL=browser.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/transports/browser.ts","../src/core/engine/browser.ts"],"names":["createBrowserTransport","config","text","lang","ctx","url","controller","timeoutId","response","errorMsg","result","BelocalEngine","options","apiKey","baseUrl","path","timeoutMs","debug","authHeaders"],"mappings":"AAUO,SAASA,CAAAA,CAAuBC,CAAAA,CAA2C,CAChF,OAAO,MAAO,CAAE,IAAA,CAAAC,CAAAA,CAAM,IAAA,CAAAC,CAAAA,CAAM,GAAA,CAAAC,CAAI,IAAM,CACpC,IAAMC,CAAAA,CAAM,CAAA,EAAGJ,CAAAA,CAAO,OAAO,GAAGA,CAAAA,CAAO,IAAI,CAAA,CAAA,CACrCK,CAAAA,CAAa,IAAI,eAAA,CACjBC,EAAYN,CAAAA,CAAO,SAAA,CAAY,UAAA,CAAW,IAAMK,CAAAA,CAAW,KAAA,GAASL,CAAAA,CAAO,SAAS,CAAA,CAAI,IAAA,CAE1FA,CAAAA,CAAO,KAAA,EACT,QAAQ,GAAA,CAAI,CAAA,yCAAA,EAA4CC,CAAI,CAAA,KAAA,EAAQC,CAAI,CAAA,UAAA,EAAaE,CAAG,CAAA,CAAE,CAAA,CAG5F,GAAI,CACF,IAAMG,CAAAA,CAAW,MAAM,MAAMH,CAAAA,CAAK,CAChC,MAAA,CAAQ,MAAA,CACR,OAAA,CAAS,CACP,eAAgB,kBAAA,CAChB,GAAGJ,CAAAA,CAAO,OACZ,CAAA,CACA,IAAA,CAAM,KAAK,SAAA,CAAU,CAAE,IAAA,CAAAC,CAAAA,CAAM,IAAA,CAAAC,CAAAA,CAAM,GAAA,CAAAC,CAAI,CAAC,CAAA,CACxC,MAAA,CAAQE,CAAAA,CAAW,MACrB,CAAC,EAED,GAAI,CAACE,CAAAA,CAAS,EAAA,CAAI,CAChB,IAAMC,EAAW,CAAA,KAAA,EAAQD,CAAAA,CAAS,MAAM,CAAA,EAAA,EAAKA,CAAAA,CAAS,UAAU,GAChE,MAAIP,CAAAA,CAAO,KAAA,EACT,OAAA,CAAQ,KAAA,CAAM,6CAAA,CAA+CQ,CAAQ,CAAA,CAEjE,IAAI,KAAA,CAAMA,CAAQ,CAC1B,CAEA,IAAMC,EAAS,MAAMF,CAAAA,CAAS,IAAA,EAAK,CACnC,OAAIP,CAAAA,CAAO,OACT,OAAA,CAAQ,GAAA,CAAI,CAAA,qDAAA,EAAwDS,CAAAA,CAAO,IAAA,EAAQR,CAAI,GAAG,CAAA,CAErFQ,CAAAA,CAAO,IAAA,EAAQR,CACxB,CAAA,OAAE,CACIK,CAAAA,EACF,YAAA,CAAaA,CAAS,EAE1B,CACF,CACF,CC/CO,IAAMI,EAAN,KAAoB,CAIzB,WAAA,CAAYC,CAAAA,CAA+B,CACzC,GAAM,CACJ,MAAA,CAAAC,CAAAA,CACA,OAAA,CAAAC,CAAAA,CAAU,6BAAA,CACV,IAAA,CAAAC,EAAO,eAAA,CACP,SAAA,CAAAC,CAAAA,CAAY,GAAA,CACZ,KAAA,CAAAC,CAAAA,CAAQ,KACV,CAAA,CAAIL,CAAAA,CAEJ,IAAA,CAAK,KAAA,CAAQK,CAAAA,CAEb,IAAMC,CAAAA,CAAc,CAClB,aAAA,CAAiB,CAAA,OAAA,EAAUL,CAAM,CAAA,CACnC,CAAA,CAEA,IAAA,CAAK,UAAYb,CAAAA,CAAuB,CACtC,OAAA,CAAAc,CAAAA,CACA,IAAA,CAAAC,CAAAA,CACA,QAASG,CAAAA,CACT,SAAA,CAAAF,CAAAA,CACA,KAAA,CAAO,IAAA,CAAK,KACd,CAAC,CAAA,CAEG,IAAA,CAAK,KAAA,EACP,OAAA,CAAQ,GAAA,CAAI,yDAAA,CAA2D,CACrE,QAAAF,CAAAA,CACA,IAAA,CAAAC,CAAAA,CACA,SAAA,CAAAC,CACF,CAAC,EAEL,CAEA,MAAM,CAAA,CAAEd,CAAAA,CAAcC,CAAAA,CAAYC,CAAAA,CAA2B,CAC3D,OAAO,IAAA,CAAK,SAAA,CAAU,CAAE,IAAA,CAAAF,CAAAA,CAAM,IAAA,CAAAC,CAAAA,CAAM,GAAA,CAAAC,CAAI,CAAC,CAC3C,CACF","file":"browser.mjs","sourcesContent":["import type { Transport } from '../core/types';\n\nexport interface BrowserTransportConfig {\n baseUrl: string;\n path?: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n debug?: boolean;\n}\n\nexport function createBrowserTransport(config: BrowserTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const url = `${config.baseUrl}${config.path}`;\n const controller = new AbortController();\n const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;\n\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translating \"${text}\" to ${lang} with url ${url}`);\n }\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...config.headers,\n },\n body: JSON.stringify({ text, lang, ctx }),\n signal: controller.signal,\n });\n\n if (!response.ok) {\n const errorMsg = `HTTP ${response.status}: ${response.statusText}`;\n if (config.debug) {\n console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);\n }\n throw new Error(errorMsg);\n }\n\n const result = await response.json();\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } finally {\n if (timeoutId) {\n clearTimeout(timeoutId);\n }\n }\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from '../types';\nimport { createBrowserTransport } from '../../transports/browser';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n timeoutMs = 10000,\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`\n };\n\n this.transport = createBrowserTransport({\n baseUrl,\n path,\n headers: authHeaders,\n timeoutMs,\n debug: this.debug\n });\n\n if (this.debug) {\n console.log('[BeLocal Engine] Browser transport created with config:', {\n baseUrl,\n path,\n timeoutMs\n });\n }\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n}\n\n// Re-export types and transport\nexport type { BelocalEngineOptions, Lang, KV } from '../types';\nexport { createBrowserTransport } from '../../transports/browser';\n"]}
@@ -23,45 +23,7 @@ function _interopNamespace(e) {
23
23
 
24
24
  var http2__namespace = /*#__PURE__*/_interopNamespace(http2);
25
25
 
26
- // src/transports/browser.ts
27
- function createBrowserTransport(config) {
28
- return async ({ text, lang, ctx }) => {
29
- const url = `${config.baseUrl}${config.path}`;
30
- const controller = new AbortController();
31
- const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;
32
- if (config.debug) {
33
- console.log(`[BeLocal Browser Transport] Translating "${text}" to ${lang} with url ${url}`);
34
- }
35
- try {
36
- const response = await fetch(url, {
37
- method: "POST",
38
- headers: {
39
- "Content-Type": "application/json",
40
- ...config.headers
41
- },
42
- body: JSON.stringify({ text, lang, ctx }),
43
- credentials: config.credentials,
44
- signal: controller.signal
45
- });
46
- if (!response.ok) {
47
- const errorMsg = `HTTP ${response.status}: ${response.statusText}`;
48
- if (config.debug) {
49
- console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);
50
- }
51
- throw new Error(errorMsg);
52
- }
53
- const result = await response.json();
54
- if (config.debug) {
55
- console.log(`[BeLocal Browser Transport] Translation successful: "${result.text || text}"`);
56
- }
57
- return result.text || text;
58
- } finally {
59
- if (timeoutId) {
60
- clearTimeout(timeoutId);
61
- }
62
- }
63
- };
64
- }
26
+ // src/transports/node.ts
65
27
  var sessionCache = /* @__PURE__ */ new Map();
66
28
  function getOrCreateSession(baseUrl, debug) {
67
29
  if (sessionCache.has(baseUrl)) {
@@ -173,83 +135,44 @@ function createNodeTransport(config) {
173
135
  };
174
136
  }
175
137
 
176
- // src/core/engine.ts
138
+ // src/core/engine/node.ts
177
139
  var BelocalEngine = class {
178
140
  constructor(options) {
179
141
  const {
180
142
  apiKey,
181
143
  baseUrl = "https://dynamic.belocal.dev",
182
144
  path = "/v1/translate",
183
- transport = "auto",
184
145
  timeoutMs = 1e4,
185
146
  retries = 3,
186
- credentials,
187
- headers = {},
188
147
  debug = false
189
148
  } = options;
190
149
  this.debug = debug;
191
150
  const authHeaders = {
192
- "Authorization": `Bearer ${apiKey}`,
193
- ...headers
151
+ "Authorization": `Bearer ${apiKey}`
194
152
  };
195
- this.transport = this.createTransport(transport, {
153
+ this.transport = createNodeTransport({
196
154
  baseUrl,
197
155
  path,
156
+ headers: authHeaders,
198
157
  timeoutMs,
199
158
  retries,
200
- credentials,
201
- headers: authHeaders,
202
159
  debug: this.debug
203
160
  });
204
- }
205
- async t(text, lang, ctx) {
206
- return this.transport({ text, lang, ctx });
207
- }
208
- createTransport(transportType, config) {
209
- const actualTransport = transportType === "auto" ? this.detectEnvironment() : transportType;
210
- if (config.debug) {
211
- console.log(`[BeLocal Engine] Creating ${actualTransport} transport with config:`, {
212
- baseUrl: config.baseUrl,
213
- path: config.path,
214
- timeoutMs: config.timeoutMs,
215
- ...actualTransport === "browser" && { credentials: config.credentials },
216
- ...actualTransport === "node" && { retries: config.retries }
217
- });
218
- }
219
- if (actualTransport === "browser") {
220
- return createBrowserTransport({
221
- baseUrl: config.baseUrl,
222
- path: config.path,
223
- credentials: config.credentials,
224
- headers: config.headers,
225
- timeoutMs: config.timeoutMs,
226
- debug: config.debug
227
- });
228
- } else {
229
- return createNodeTransport({
230
- baseUrl: config.baseUrl,
231
- path: config.path,
232
- headers: config.headers,
233
- timeoutMs: config.timeoutMs,
234
- retries: config.retries,
235
- debug: config.debug
161
+ if (this.debug) {
162
+ console.log("[BeLocal Engine] Node transport created with config:", {
163
+ baseUrl,
164
+ path,
165
+ timeoutMs,
166
+ retries
236
167
  });
237
168
  }
238
169
  }
239
- /**
240
- * Автоматически определяет среду выполнения
241
- */
242
- detectEnvironment() {
243
- if (typeof window !== "undefined" && typeof window.document !== "undefined") {
244
- return "browser";
245
- }
246
- if (typeof process !== "undefined" && process.versions && process.versions.node) {
247
- return "node";
248
- }
249
- return "node";
170
+ async t(text, lang, ctx) {
171
+ return this.transport({ text, lang, ctx });
250
172
  }
251
173
  };
252
174
 
253
175
  exports.BelocalEngine = BelocalEngine;
254
- //# sourceMappingURL=index.cjs.map
255
- //# sourceMappingURL=index.cjs.map
176
+ exports.createNodeTransport = createNodeTransport;
177
+ //# sourceMappingURL=node.cjs.map
178
+ //# sourceMappingURL=node.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/transports/node.ts","../src/core/engine/node.ts"],"names":["session","URL","http2","headers"],"mappings":"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","file":"node.cjs","sourcesContent":["import * as http2 from 'node:http2';\nimport { URL } from 'node:url';\nimport type { Transport } from '../core/types';\n\nexport interface NodeTransportConfig {\n baseUrl: string;\n path: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n retries?: number;\n debug?: boolean;\n}\n\n// Global session cache for HTTP/2 connections\nconst sessionCache = new Map<string, http2.ClientHttp2Session>();\n\nfunction getOrCreateSession(baseUrl: string, debug?: boolean): http2.ClientHttp2Session {\n if (sessionCache.has(baseUrl)) {\n const session = sessionCache.get(baseUrl)!;\n if (!session.destroyed) {\n return session;\n }\n sessionCache.delete(baseUrl);\n }\n\n const parsedUrl = new URL(baseUrl);\n const session = http2.connect(parsedUrl.origin);\n\n session.socket?.unref();\n \n // Set up session cleanup\n session.on('error', () => {\n sessionCache.delete(baseUrl);\n });\n \n session.on('close', () => {\n sessionCache.delete(baseUrl);\n });\n\n // Add debug logging if enabled\n if (debug) {\n session.on('connect', () => console.log('[H2] new session connected'));\n session.on('goaway', (code, lastStreamID, opaque) =>\n console.log('[H2] goaway', code, lastStreamID)\n );\n }\n \n sessionCache.set(baseUrl, session);\n return session;\n}\n\nfunction makeHttp2Request(\n session: http2.ClientHttp2Session,\n path: string,\n headers: Record<string, string>,\n body: string,\n timeoutMs?: number\n): Promise<{ statusCode: number; headers: Record<string, string>; body: string }> {\n return new Promise((resolve, reject) => {\n const req = session.request({\n ':method': 'POST',\n ':path': path,\n 'content-type': 'application/json',\n 'content-length': Buffer.byteLength(body),\n ...headers,\n });\n\n let timeout: NodeJS.Timeout | null = null;\n if (timeoutMs) {\n timeout = setTimeout(() => {\n req.destroy();\n reject(new Error(`Request timeout after ${timeoutMs}ms`));\n }, timeoutMs);\n }\n\n let responseData = '';\n let statusCode = 0;\n let responseHeaders: Record<string, string> = {};\n\n req.on('response', (headers) => {\n statusCode = headers[':status'] as number;\n responseHeaders = headers as Record<string, string>;\n });\n\n req.on('data', (chunk) => {\n responseData += chunk;\n });\n\n req.on('end', () => {\n if (timeout) clearTimeout(timeout);\n resolve({\n statusCode,\n headers: responseHeaders,\n body: responseData,\n });\n });\n\n req.on('error', (error) => {\n if (timeout) clearTimeout(timeout);\n reject(error);\n });\n\n req.write(body);\n req.end();\n });\n}\n\nexport function createNodeTransport(config: NodeTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const maxRetries = config.retries || 0;\n let attempt = 0;\n\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translating \"${text}\" to ${lang} with url ${config.baseUrl}${config.path}`);\n }\n\n while (attempt <= maxRetries) {\n try {\n const session = getOrCreateSession(config.baseUrl, config.debug);\n const body = JSON.stringify({ text, lang, ctx });\n \n const response = await makeHttp2Request(\n session,\n config.path,\n config.headers || {},\n body,\n config.timeoutMs\n );\n\n if (response.statusCode < 200 || response.statusCode >= 300) {\n throw new Error(`HTTP ${response.statusCode}: Request failed`);\n }\n\n const result = JSON.parse(response.body);\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } catch (error) {\n attempt++;\n if (config.debug) {\n console.error(`[BeLocal Node Transport] Attempt ${attempt} failed:`, error instanceof Error ? error.message : String(error));\n }\n if (attempt > maxRetries) {\n throw error;\n }\n\n await new Promise(resolve => setTimeout(resolve, Math.pow(2, attempt) * 1000));\n }\n }\n\n return text;\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from '../types';\nimport { createNodeTransport } from '../../transports/node';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n timeoutMs = 10000,\n retries = 3,\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`\n };\n\n this.transport = createNodeTransport({\n baseUrl,\n path,\n headers: authHeaders,\n timeoutMs,\n retries,\n debug: this.debug\n });\n\n if (this.debug) {\n console.log('[BeLocal Engine] Node transport created with config:', {\n baseUrl,\n path,\n timeoutMs,\n retries\n });\n }\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n}\n\n// Re-export types and transport\nexport type { BelocalEngineOptions, Lang, KV } from '../types';\nexport { createNodeTransport } from '../../transports/node';\n"]}
package/dist/node.d.ts ADDED
@@ -0,0 +1,34 @@
1
+ type Lang = string;
2
+ type KV = Record<string, unknown>;
3
+ type Transport = (params: {
4
+ text: string;
5
+ lang: Lang;
6
+ ctx?: KV;
7
+ }) => Promise<string>;
8
+ interface BelocalEngineOptions {
9
+ apiKey: string;
10
+ baseUrl?: string;
11
+ path?: string;
12
+ timeoutMs?: number;
13
+ retries?: number;
14
+ debug?: boolean;
15
+ }
16
+
17
+ interface NodeTransportConfig {
18
+ baseUrl: string;
19
+ path: string;
20
+ headers?: Record<string, string>;
21
+ timeoutMs?: number;
22
+ retries?: number;
23
+ debug?: boolean;
24
+ }
25
+ declare function createNodeTransport(config: NodeTransportConfig): Transport;
26
+
27
+ declare class BelocalEngine {
28
+ private transport;
29
+ private debug;
30
+ constructor(options: BelocalEngineOptions);
31
+ t(text: string, lang: Lang, ctx?: KV): Promise<string>;
32
+ }
33
+
34
+ export { BelocalEngine, type BelocalEngineOptions, type KV, type Lang, createNodeTransport };
@@ -1,45 +1,7 @@
1
1
  import * as http2 from 'http2';
2
2
  import { URL } from 'url';
3
3
 
4
- // src/transports/browser.ts
5
- function createBrowserTransport(config) {
6
- return async ({ text, lang, ctx }) => {
7
- const url = `${config.baseUrl}${config.path}`;
8
- const controller = new AbortController();
9
- const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;
10
- if (config.debug) {
11
- console.log(`[BeLocal Browser Transport] Translating "${text}" to ${lang} with url ${url}`);
12
- }
13
- try {
14
- const response = await fetch(url, {
15
- method: "POST",
16
- headers: {
17
- "Content-Type": "application/json",
18
- ...config.headers
19
- },
20
- body: JSON.stringify({ text, lang, ctx }),
21
- credentials: config.credentials,
22
- signal: controller.signal
23
- });
24
- if (!response.ok) {
25
- const errorMsg = `HTTP ${response.status}: ${response.statusText}`;
26
- if (config.debug) {
27
- console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);
28
- }
29
- throw new Error(errorMsg);
30
- }
31
- const result = await response.json();
32
- if (config.debug) {
33
- console.log(`[BeLocal Browser Transport] Translation successful: "${result.text || text}"`);
34
- }
35
- return result.text || text;
36
- } finally {
37
- if (timeoutId) {
38
- clearTimeout(timeoutId);
39
- }
40
- }
41
- };
42
- }
4
+ // src/transports/node.ts
43
5
  var sessionCache = /* @__PURE__ */ new Map();
44
6
  function getOrCreateSession(baseUrl, debug) {
45
7
  if (sessionCache.has(baseUrl)) {
@@ -151,83 +113,43 @@ function createNodeTransport(config) {
151
113
  };
152
114
  }
153
115
 
154
- // src/core/engine.ts
116
+ // src/core/engine/node.ts
155
117
  var BelocalEngine = class {
156
118
  constructor(options) {
157
119
  const {
158
120
  apiKey,
159
121
  baseUrl = "https://dynamic.belocal.dev",
160
122
  path = "/v1/translate",
161
- transport = "auto",
162
123
  timeoutMs = 1e4,
163
124
  retries = 3,
164
- credentials,
165
- headers = {},
166
125
  debug = false
167
126
  } = options;
168
127
  this.debug = debug;
169
128
  const authHeaders = {
170
- "Authorization": `Bearer ${apiKey}`,
171
- ...headers
129
+ "Authorization": `Bearer ${apiKey}`
172
130
  };
173
- this.transport = this.createTransport(transport, {
131
+ this.transport = createNodeTransport({
174
132
  baseUrl,
175
133
  path,
134
+ headers: authHeaders,
176
135
  timeoutMs,
177
136
  retries,
178
- credentials,
179
- headers: authHeaders,
180
137
  debug: this.debug
181
138
  });
182
- }
183
- async t(text, lang, ctx) {
184
- return this.transport({ text, lang, ctx });
185
- }
186
- createTransport(transportType, config) {
187
- const actualTransport = transportType === "auto" ? this.detectEnvironment() : transportType;
188
- if (config.debug) {
189
- console.log(`[BeLocal Engine] Creating ${actualTransport} transport with config:`, {
190
- baseUrl: config.baseUrl,
191
- path: config.path,
192
- timeoutMs: config.timeoutMs,
193
- ...actualTransport === "browser" && { credentials: config.credentials },
194
- ...actualTransport === "node" && { retries: config.retries }
195
- });
196
- }
197
- if (actualTransport === "browser") {
198
- return createBrowserTransport({
199
- baseUrl: config.baseUrl,
200
- path: config.path,
201
- credentials: config.credentials,
202
- headers: config.headers,
203
- timeoutMs: config.timeoutMs,
204
- debug: config.debug
205
- });
206
- } else {
207
- return createNodeTransport({
208
- baseUrl: config.baseUrl,
209
- path: config.path,
210
- headers: config.headers,
211
- timeoutMs: config.timeoutMs,
212
- retries: config.retries,
213
- debug: config.debug
139
+ if (this.debug) {
140
+ console.log("[BeLocal Engine] Node transport created with config:", {
141
+ baseUrl,
142
+ path,
143
+ timeoutMs,
144
+ retries
214
145
  });
215
146
  }
216
147
  }
217
- /**
218
- * Автоматически определяет среду выполнения
219
- */
220
- detectEnvironment() {
221
- if (typeof window !== "undefined" && typeof window.document !== "undefined") {
222
- return "browser";
223
- }
224
- if (typeof process !== "undefined" && process.versions && process.versions.node) {
225
- return "node";
226
- }
227
- return "node";
148
+ async t(text, lang, ctx) {
149
+ return this.transport({ text, lang, ctx });
228
150
  }
229
151
  };
230
152
 
231
- export { BelocalEngine };
232
- //# sourceMappingURL=index.js.map
233
- //# sourceMappingURL=index.js.map
153
+ export { BelocalEngine, createNodeTransport };
154
+ //# sourceMappingURL=node.mjs.map
155
+ //# sourceMappingURL=node.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/transports/node.ts","../src/core/engine/node.ts"],"names":["session","headers"],"mappings":"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","file":"node.mjs","sourcesContent":["import * as http2 from 'node:http2';\nimport { URL } from 'node:url';\nimport type { Transport } from '../core/types';\n\nexport interface NodeTransportConfig {\n baseUrl: string;\n path: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n retries?: number;\n debug?: boolean;\n}\n\n// Global session cache for HTTP/2 connections\nconst sessionCache = new Map<string, http2.ClientHttp2Session>();\n\nfunction getOrCreateSession(baseUrl: string, debug?: boolean): http2.ClientHttp2Session {\n if (sessionCache.has(baseUrl)) {\n const session = sessionCache.get(baseUrl)!;\n if (!session.destroyed) {\n return session;\n }\n sessionCache.delete(baseUrl);\n }\n\n const parsedUrl = new URL(baseUrl);\n const session = http2.connect(parsedUrl.origin);\n\n session.socket?.unref();\n \n // Set up session cleanup\n session.on('error', () => {\n sessionCache.delete(baseUrl);\n });\n \n session.on('close', () => {\n sessionCache.delete(baseUrl);\n });\n\n // Add debug logging if enabled\n if (debug) {\n session.on('connect', () => console.log('[H2] new session connected'));\n session.on('goaway', (code, lastStreamID, opaque) =>\n console.log('[H2] goaway', code, lastStreamID)\n );\n }\n \n sessionCache.set(baseUrl, session);\n return session;\n}\n\nfunction makeHttp2Request(\n session: http2.ClientHttp2Session,\n path: string,\n headers: Record<string, string>,\n body: string,\n timeoutMs?: number\n): Promise<{ statusCode: number; headers: Record<string, string>; body: string }> {\n return new Promise((resolve, reject) => {\n const req = session.request({\n ':method': 'POST',\n ':path': path,\n 'content-type': 'application/json',\n 'content-length': Buffer.byteLength(body),\n ...headers,\n });\n\n let timeout: NodeJS.Timeout | null = null;\n if (timeoutMs) {\n timeout = setTimeout(() => {\n req.destroy();\n reject(new Error(`Request timeout after ${timeoutMs}ms`));\n }, timeoutMs);\n }\n\n let responseData = '';\n let statusCode = 0;\n let responseHeaders: Record<string, string> = {};\n\n req.on('response', (headers) => {\n statusCode = headers[':status'] as number;\n responseHeaders = headers as Record<string, string>;\n });\n\n req.on('data', (chunk) => {\n responseData += chunk;\n });\n\n req.on('end', () => {\n if (timeout) clearTimeout(timeout);\n resolve({\n statusCode,\n headers: responseHeaders,\n body: responseData,\n });\n });\n\n req.on('error', (error) => {\n if (timeout) clearTimeout(timeout);\n reject(error);\n });\n\n req.write(body);\n req.end();\n });\n}\n\nexport function createNodeTransport(config: NodeTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const maxRetries = config.retries || 0;\n let attempt = 0;\n\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translating \"${text}\" to ${lang} with url ${config.baseUrl}${config.path}`);\n }\n\n while (attempt <= maxRetries) {\n try {\n const session = getOrCreateSession(config.baseUrl, config.debug);\n const body = JSON.stringify({ text, lang, ctx });\n \n const response = await makeHttp2Request(\n session,\n config.path,\n config.headers || {},\n body,\n config.timeoutMs\n );\n\n if (response.statusCode < 200 || response.statusCode >= 300) {\n throw new Error(`HTTP ${response.statusCode}: Request failed`);\n }\n\n const result = JSON.parse(response.body);\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } catch (error) {\n attempt++;\n if (config.debug) {\n console.error(`[BeLocal Node Transport] Attempt ${attempt} failed:`, error instanceof Error ? error.message : String(error));\n }\n if (attempt > maxRetries) {\n throw error;\n }\n\n await new Promise(resolve => setTimeout(resolve, Math.pow(2, attempt) * 1000));\n }\n }\n\n return text;\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from '../types';\nimport { createNodeTransport } from '../../transports/node';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n timeoutMs = 10000,\n retries = 3,\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`\n };\n\n this.transport = createNodeTransport({\n baseUrl,\n path,\n headers: authHeaders,\n timeoutMs,\n retries,\n debug: this.debug\n });\n\n if (this.debug) {\n console.log('[BeLocal Engine] Node transport created with config:', {\n baseUrl,\n path,\n timeoutMs,\n retries\n });\n }\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n}\n\n// Re-export types and transport\nexport type { BelocalEngineOptions, Lang, KV } from '../types';\nexport { createNodeTransport } from '../../transports/node';\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@belocal/js-sdk",
3
- "version": "0.1.8",
3
+ "version": "0.1.10",
4
4
  "description": "BeLocal runtime JS SDK for on-demand translation (browser + node)",
5
5
  "scripts": {
6
6
  "test": "echo \"Error: no test specified\" && exit 1",
@@ -33,10 +33,20 @@
33
33
  "types": "./dist/index.d.ts",
34
34
  "exports": {
35
35
  ".": {
36
- "types": "./dist/index.d.ts",
37
- "import": "./dist/index.mjs",
38
- "require": "./dist/index.cjs",
39
- "default": "./dist/index.mjs"
36
+ "browser": {
37
+ "types": "./dist/browser.d.ts",
38
+ "import": "./dist/browser.mjs",
39
+ "require": "./dist/browser.cjs"
40
+ },
41
+ "node": {
42
+ "types": "./dist/node.d.ts",
43
+ "import": "./dist/node.mjs",
44
+ "require": "./dist/node.cjs"
45
+ },
46
+ "types": "./dist/browser.d.ts",
47
+ "import": "./dist/browser.mjs",
48
+ "require": "./dist/node.cjs",
49
+ "default": "./dist/browser.mjs"
40
50
  }
41
51
  },
42
52
  "sideEffects": false,
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/transports/browser.ts","../src/transports/node.ts","../src/core/engine.ts"],"names":["session","URL","http2","headers"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;AAWO,SAAS,uBAAuB,MAAA,EAA2C;AAChF,EAAA,OAAO,OAAO,EAAE,IAAA,EAAM,IAAA,EAAM,KAAI,KAAM;AACpC,IAAA,MAAM,MAAM,CAAA,EAAG,MAAA,CAAO,OAAO,CAAA,EAAG,OAAO,IAAI,CAAA,CAAA;AAC3C,IAAA,MAAM,UAAA,GAAa,IAAI,eAAA,EAAgB;AACvC,IAAA,MAAM,SAAA,GAAY,MAAA,CAAO,SAAA,GAAY,UAAA,CAAW,MAAM,WAAW,KAAA,EAAM,EAAG,MAAA,CAAO,SAAS,CAAA,GAAI,IAAA;AAE9F,IAAA,IAAI,OAAO,KAAA,EAAO;AAChB,MAAA,OAAA,CAAQ,IAAI,CAAA,yCAAA,EAA4C,IAAI,QAAQ,IAAI,CAAA,UAAA,EAAa,GAAG,CAAA,CAAE,CAAA;AAAA,IAC5F;AAEA,IAAA,IAAI;AACF,MAAA,MAAM,QAAA,GAAW,MAAM,KAAA,CAAM,GAAA,EAAK;AAAA,QAChC,MAAA,EAAQ,MAAA;AAAA,QACR,OAAA,EAAS;AAAA,UACP,cAAA,EAAgB,kBAAA;AAAA,UAChB,GAAG,MAAA,CAAO;AAAA,SACZ;AAAA,QACA,MAAM,IAAA,CAAK,SAAA,CAAU,EAAE,IAAA,EAAM,IAAA,EAAM,KAAK,CAAA;AAAA,QACxC,aAAa,MAAA,CAAO,WAAA;AAAA,QACpB,QAAQ,UAAA,CAAW;AAAA,OACpB,CAAA;AAED,MAAA,IAAI,CAAC,SAAS,EAAA,EAAI;AAChB,QAAA,MAAM,WAAW,CAAA,KAAA,EAAQ,QAAA,CAAS,MAAM,CAAA,EAAA,EAAK,SAAS,UAAU,CAAA,CAAA;AAChE,QAAA,IAAI,OAAO,KAAA,EAAO;AAChB,UAAA,OAAA,CAAQ,KAAA,CAAM,+CAA+C,QAAQ,CAAA;AAAA,QACvE;AACA,QAAA,MAAM,IAAI,MAAM,QAAQ,CAAA;AAAA,MAC1B;AAEA,MAAA,MAAM,MAAA,GAAS,MAAM,QAAA,CAAS,IAAA,EAAK;AACnC,MAAA,IAAI,OAAO,KAAA,EAAO;AAChB,QAAA,OAAA,CAAQ,GAAA,CAAI,CAAA,qDAAA,EAAwD,MAAA,CAAO,IAAA,IAAQ,IAAI,CAAA,CAAA,CAAG,CAAA;AAAA,MAC5F;AACA,MAAA,OAAO,OAAO,IAAA,IAAQ,IAAA;AAAA,IACxB,CAAA,SAAE;AACA,MAAA,IAAI,SAAA,EAAW;AACb,QAAA,YAAA,CAAa,SAAS,CAAA;AAAA,MACxB;AAAA,IACF;AAAA,EACF,CAAA;AACF;ACtCA,IAAM,YAAA,uBAAmB,GAAA,EAAsC;AAE/D,SAAS,kBAAA,CAAmB,SAAiB,KAAA,EAA2C;AACtF,EAAA,IAAI,YAAA,CAAa,GAAA,CAAI,OAAO,CAAA,EAAG;AAC7B,IAAA,MAAMA,QAAAA,GAAU,YAAA,CAAa,GAAA,CAAI,OAAO,CAAA;AACxC,IAAA,IAAI,CAACA,SAAQ,SAAA,EAAW;AACtB,MAAA,OAAOA,QAAAA;AAAA,IACT;AACA,IAAA,YAAA,CAAa,OAAO,OAAO,CAAA;AAAA,EAC7B;AAEA,EAAA,MAAM,SAAA,GAAY,IAAIC,OAAA,CAAI,OAAO,CAAA;AACjC,EAAA,MAAM,OAAA,GAAgBC,gBAAA,CAAA,OAAA,CAAQ,SAAA,CAAU,MAAM,CAAA;AAE9C,EAAA,OAAA,CAAQ,QAAQ,KAAA,EAAM;AAGtB,EAAA,OAAA,CAAQ,EAAA,CAAG,SAAS,MAAM;AACxB,IAAA,YAAA,CAAa,OAAO,OAAO,CAAA;AAAA,EAC7B,CAAC,CAAA;AAED,EAAA,OAAA,CAAQ,EAAA,CAAG,SAAS,MAAM;AACxB,IAAA,YAAA,CAAa,OAAO,OAAO,CAAA;AAAA,EAC7B,CAAC,CAAA;AAGD,EAAA,IAAI,KAAA,EAAO;AACT,IAAA,OAAA,CAAQ,GAAG,SAAA,EAAW,MAAM,OAAA,CAAQ,GAAA,CAAI,4BAA4B,CAAC,CAAA;AACrE,IAAA,OAAA,CAAQ,EAAA;AAAA,MAAG,QAAA;AAAA,MAAU,CAAC,MAAM,YAAA,EAAc,MAAA,KACxC,QAAQ,GAAA,CAAI,aAAA,EAAe,MAAM,YAAY;AAAA,KAC/C;AAAA,EACF;AAEA,EAAA,YAAA,CAAa,GAAA,CAAI,SAAS,OAAO,CAAA;AACjC,EAAA,OAAO,OAAA;AACT;AAEA,SAAS,gBAAA,CACP,OAAA,EACA,IAAA,EACA,OAAA,EACA,MACA,SAAA,EACgF;AAChF,EAAA,OAAO,IAAI,OAAA,CAAQ,CAAC,OAAA,EAAS,MAAA,KAAW;AACtC,IAAA,MAAM,GAAA,GAAM,QAAQ,OAAA,CAAQ;AAAA,MAC1B,SAAA,EAAW,MAAA;AAAA,MACX,OAAA,EAAS,IAAA;AAAA,MACT,cAAA,EAAgB,kBAAA;AAAA,MAChB,gBAAA,EAAkB,MAAA,CAAO,UAAA,CAAW,IAAI,CAAA;AAAA,MACxC,GAAG;AAAA,KACJ,CAAA;AAED,IAAA,IAAI,OAAA,GAAiC,IAAA;AACrC,IAAA,IAAI,SAAA,EAAW;AACb,MAAA,OAAA,GAAU,WAAW,MAAM;AACzB,QAAA,GAAA,CAAI,OAAA,EAAQ;AACZ,QAAA,MAAA,CAAO,IAAI,KAAA,CAAM,CAAA,sBAAA,EAAyB,SAAS,IAAI,CAAC,CAAA;AAAA,MAC1D,GAAG,SAAS,CAAA;AAAA,IACd;AAEA,IAAA,IAAI,YAAA,GAAe,EAAA;AACnB,IAAA,IAAI,UAAA,GAAa,CAAA;AACjB,IAAA,IAAI,kBAA0C,EAAC;AAE/C,IAAA,GAAA,CAAI,EAAA,CAAG,UAAA,EAAY,CAACC,QAAAA,KAAY;AAC9B,MAAA,UAAA,GAAaA,SAAQ,SAAS,CAAA;AAC9B,MAAA,eAAA,GAAkBA,QAAAA;AAAA,IACpB,CAAC,CAAA;AAED,IAAA,GAAA,CAAI,EAAA,CAAG,MAAA,EAAQ,CAAC,KAAA,KAAU;AACxB,MAAA,YAAA,IAAgB,KAAA;AAAA,IAClB,CAAC,CAAA;AAED,IAAA,GAAA,CAAI,EAAA,CAAG,OAAO,MAAM;AAClB,MAAA,IAAI,OAAA,eAAsB,OAAO,CAAA;AACjC,MAAA,OAAA,CAAQ;AAAA,QACN,UAAA;AAAA,QACA,OAAA,EAAS,eAAA;AAAA,QACT,IAAA,EAAM;AAAA,OACP,CAAA;AAAA,IACH,CAAC,CAAA;AAED,IAAA,GAAA,CAAI,EAAA,CAAG,OAAA,EAAS,CAAC,KAAA,KAAU;AACzB,MAAA,IAAI,OAAA,eAAsB,OAAO,CAAA;AACjC,MAAA,MAAA,CAAO,KAAK,CAAA;AAAA,IACd,CAAC,CAAA;AAED,IAAA,GAAA,CAAI,MAAM,IAAI,CAAA;AACd,IAAA,GAAA,CAAI,GAAA,EAAI;AAAA,EACV,CAAC,CAAA;AACH;AAEO,SAAS,oBAAoB,MAAA,EAAwC;AAC1E,EAAA,OAAO,OAAO,EAAE,IAAA,EAAM,IAAA,EAAM,KAAI,KAAM;AACpC,IAAA,MAAM,UAAA,GAAa,OAAO,OAAA,IAAW,CAAA;AACrC,IAAA,IAAI,OAAA,GAAU,CAAA;AAEd,IAAA,IAAI,OAAO,KAAA,EAAO;AAChB,MAAA,OAAA,CAAQ,GAAA,CAAI,CAAA,sCAAA,EAAyC,IAAI,CAAA,KAAA,EAAQ,IAAI,CAAA,UAAA,EAAa,MAAA,CAAO,OAAO,CAAA,EAAG,MAAA,CAAO,IAAI,CAAA,CAAE,CAAA;AAAA,IAClH;AAEA,IAAA,OAAO,WAAW,UAAA,EAAY;AAC5B,MAAA,IAAI;AACF,QAAA,MAAM,OAAA,GAAU,kBAAA,CAAmB,MAAA,CAAO,OAAA,EAAS,OAAO,KAAK,CAAA;AAC/D,QAAA,MAAM,OAAO,IAAA,CAAK,SAAA,CAAU,EAAE,IAAA,EAAM,IAAA,EAAM,KAAK,CAAA;AAE/C,QAAA,MAAM,WAAW,MAAM,gBAAA;AAAA,UACrB,OAAA;AAAA,UACA,MAAA,CAAO,IAAA;AAAA,UACP,MAAA,CAAO,WAAW,EAAC;AAAA,UACnB,IAAA;AAAA,UACA,MAAA,CAAO;AAAA,SACT;AAEA,QAAA,IAAI,QAAA,CAAS,UAAA,GAAa,GAAA,IAAO,QAAA,CAAS,cAAc,GAAA,EAAK;AAC3D,UAAA,MAAM,IAAI,KAAA,CAAM,CAAA,KAAA,EAAQ,QAAA,CAAS,UAAU,CAAA,gBAAA,CAAkB,CAAA;AAAA,QAC/D;AAEA,QAAA,MAAM,MAAA,GAAS,IAAA,CAAK,KAAA,CAAM,QAAA,CAAS,IAAI,CAAA;AACvC,QAAA,IAAI,OAAO,KAAA,EAAO;AAChB,UAAA,OAAA,CAAQ,GAAA,CAAI,CAAA,kDAAA,EAAqD,MAAA,CAAO,IAAA,IAAQ,IAAI,CAAA,CAAA,CAAG,CAAA;AAAA,QACzF;AACA,QAAA,OAAO,OAAO,IAAA,IAAQ,IAAA;AAAA,MACxB,SAAS,KAAA,EAAO;AACd,QAAA,OAAA,EAAA;AACA,QAAA,IAAI,OAAO,KAAA,EAAO;AAChB,UAAA,OAAA,CAAQ,KAAA,CAAM,CAAA,iCAAA,EAAoC,OAAO,CAAA,QAAA,CAAA,EAAY,KAAA,YAAiB,QAAQ,KAAA,CAAM,OAAA,GAAU,MAAA,CAAO,KAAK,CAAC,CAAA;AAAA,QAC7H;AACA,QAAA,IAAI,UAAU,UAAA,EAAY;AACxB,UAAA,MAAM,KAAA;AAAA,QACR;AAEA,QAAA,MAAM,IAAI,OAAA,CAAQ,CAAA,OAAA,KAAW,UAAA,CAAW,OAAA,EAAS,IAAA,CAAK,GAAA,CAAI,CAAA,EAAG,OAAO,CAAA,GAAI,GAAI,CAAC,CAAA;AAAA,MAC/E;AAAA,IACF;AAEA,IAAA,OAAO,IAAA;AAAA,EACT,CAAA;AACF;;;ACrJO,IAAM,gBAAN,MAAoB;AAAA,EAIzB,YAAY,OAAA,EAA+B;AACzC,IAAA,MAAM;AAAA,MACJ,MAAA;AAAA,MACA,OAAA,GAAU,6BAAA;AAAA,MACV,IAAA,GAAO,eAAA;AAAA,MACP,SAAA,GAAY,MAAA;AAAA,MACZ,SAAA,GAAY,GAAA;AAAA,MACZ,OAAA,GAAU,CAAA;AAAA,MACV,WAAA;AAAA,MACA,UAAU,EAAC;AAAA,MACX,KAAA,GAAQ;AAAA,KACV,GAAI,OAAA;AAEJ,IAAA,IAAA,CAAK,KAAA,GAAQ,KAAA;AAEb,IAAA,MAAM,WAAA,GAAc;AAAA,MAClB,eAAA,EAAiB,UAAU,MAAM,CAAA,CAAA;AAAA,MACjC,GAAG;AAAA,KACL;AAEA,IAAA,IAAA,CAAK,SAAA,GAAY,IAAA,CAAK,eAAA,CAAgB,SAAA,EAAW;AAAA,MAC/C,OAAA;AAAA,MACA,IAAA;AAAA,MACA,SAAA;AAAA,MACA,OAAA;AAAA,MACA,WAAA;AAAA,MACA,OAAA,EAAS,WAAA;AAAA,MACT,OAAO,IAAA,CAAK;AAAA,KACb,CAAA;AAAA,EACH;AAAA,EAEA,MAAM,CAAA,CAAE,IAAA,EAAc,IAAA,EAAY,GAAA,EAA2B;AAC3D,IAAA,OAAO,KAAK,SAAA,CAAU,EAAE,IAAA,EAAM,IAAA,EAAM,KAAK,CAAA;AAAA,EAC3C;AAAA,EAEQ,eAAA,CACN,eACA,MAAA,EASW;AACX,IAAA,MAAM,eAAA,GAAkB,aAAA,KAAkB,MAAA,GAAS,IAAA,CAAK,mBAAkB,GAAI,aAAA;AAE9E,IAAA,IAAI,OAAO,KAAA,EAAO;AAChB,MAAA,OAAA,CAAQ,GAAA,CAAI,CAAA,0BAAA,EAA6B,eAAe,CAAA,uBAAA,CAAA,EAA2B;AAAA,QACjF,SAAS,MAAA,CAAO,OAAA;AAAA,QAChB,MAAM,MAAA,CAAO,IAAA;AAAA,QACb,WAAW,MAAA,CAAO,SAAA;AAAA,QAClB,GAAI,eAAA,KAAoB,SAAA,IAAa,EAAE,WAAA,EAAa,OAAO,WAAA,EAAY;AAAA,QACvE,GAAI,eAAA,KAAoB,MAAA,IAAU,EAAE,OAAA,EAAS,OAAO,OAAA;AAAQ,OAC7D,CAAA;AAAA,IACH;AAEA,IAAA,IAAI,oBAAoB,SAAA,EAAW;AACjC,MAAA,OAAO,sBAAA,CAAuB;AAAA,QAC5B,SAAS,MAAA,CAAO,OAAA;AAAA,QAChB,MAAM,MAAA,CAAO,IAAA;AAAA,QACb,aAAa,MAAA,CAAO,WAAA;AAAA,QACpB,SAAS,MAAA,CAAO,OAAA;AAAA,QAChB,WAAW,MAAA,CAAO,SAAA;AAAA,QAClB,OAAO,MAAA,CAAO;AAAA,OACf,CAAA;AAAA,IACH,CAAA,MAAO;AACL,MAAA,OAAO,mBAAA,CAAoB;AAAA,QACzB,SAAS,MAAA,CAAO,OAAA;AAAA,QAChB,MAAM,MAAA,CAAO,IAAA;AAAA,QACb,SAAS,MAAA,CAAO,OAAA;AAAA,QAChB,WAAW,MAAA,CAAO,SAAA;AAAA,QAClB,SAAS,MAAA,CAAO,OAAA;AAAA,QAChB,OAAO,MAAA,CAAO;AAAA,OACf,CAAA;AAAA,IACH;AAAA,EACF;AAAA;AAAA;AAAA;AAAA,EAKQ,iBAAA,GAAwC;AAC9C,IAAA,IAAI,OAAO,MAAA,KAAW,WAAA,IAAe,OAAO,MAAA,CAAO,aAAa,WAAA,EAAa;AAC3E,MAAA,OAAO,SAAA;AAAA,IACT;AAEA,IAAA,IAAI,OAAO,OAAA,KAAY,WAAA,IAAe,QAAQ,QAAA,IAAY,OAAA,CAAQ,SAAS,IAAA,EAAM;AAC/E,MAAA,OAAO,MAAA;AAAA,IACT;AAEA,IAAA,OAAO,MAAA;AAAA,EACT;AACF","file":"index.cjs","sourcesContent":["import type { Transport } from '../core/types';\n\nexport interface BrowserTransportConfig {\n baseUrl: string;\n path?: string;\n credentials?: RequestCredentials;\n headers?: Record<string, string>;\n timeoutMs?: number;\n debug?: boolean;\n}\n\nexport function createBrowserTransport(config: BrowserTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const url = `${config.baseUrl}${config.path}`;\n const controller = new AbortController();\n const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;\n\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translating \"${text}\" to ${lang} with url ${url}`);\n }\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...config.headers,\n },\n body: JSON.stringify({ text, lang, ctx }),\n credentials: config.credentials,\n signal: controller.signal,\n });\n\n if (!response.ok) {\n const errorMsg = `HTTP ${response.status}: ${response.statusText}`;\n if (config.debug) {\n console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);\n }\n throw new Error(errorMsg);\n }\n\n const result = await response.json();\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } finally {\n if (timeoutId) {\n clearTimeout(timeoutId);\n }\n }\n };\n}","import * as http2 from 'node:http2';\nimport { URL } from 'node:url';\nimport type { Transport } from '../core/types';\n\nexport interface NodeTransportConfig {\n baseUrl: string;\n path: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n retries?: number;\n debug?: boolean;\n}\n\n// Global session cache for HTTP/2 connections\nconst sessionCache = new Map<string, http2.ClientHttp2Session>();\n\nfunction getOrCreateSession(baseUrl: string, debug?: boolean): http2.ClientHttp2Session {\n if (sessionCache.has(baseUrl)) {\n const session = sessionCache.get(baseUrl)!;\n if (!session.destroyed) {\n return session;\n }\n sessionCache.delete(baseUrl);\n }\n\n const parsedUrl = new URL(baseUrl);\n const session = http2.connect(parsedUrl.origin);\n\n session.socket?.unref();\n \n // Set up session cleanup\n session.on('error', () => {\n sessionCache.delete(baseUrl);\n });\n \n session.on('close', () => {\n sessionCache.delete(baseUrl);\n });\n\n // Add debug logging if enabled\n if (debug) {\n session.on('connect', () => console.log('[H2] new session connected'));\n session.on('goaway', (code, lastStreamID, opaque) =>\n console.log('[H2] goaway', code, lastStreamID)\n );\n }\n \n sessionCache.set(baseUrl, session);\n return session;\n}\n\nfunction makeHttp2Request(\n session: http2.ClientHttp2Session,\n path: string,\n headers: Record<string, string>,\n body: string,\n timeoutMs?: number\n): Promise<{ statusCode: number; headers: Record<string, string>; body: string }> {\n return new Promise((resolve, reject) => {\n const req = session.request({\n ':method': 'POST',\n ':path': path,\n 'content-type': 'application/json',\n 'content-length': Buffer.byteLength(body),\n ...headers,\n });\n\n let timeout: NodeJS.Timeout | null = null;\n if (timeoutMs) {\n timeout = setTimeout(() => {\n req.destroy();\n reject(new Error(`Request timeout after ${timeoutMs}ms`));\n }, timeoutMs);\n }\n\n let responseData = '';\n let statusCode = 0;\n let responseHeaders: Record<string, string> = {};\n\n req.on('response', (headers) => {\n statusCode = headers[':status'] as number;\n responseHeaders = headers as Record<string, string>;\n });\n\n req.on('data', (chunk) => {\n responseData += chunk;\n });\n\n req.on('end', () => {\n if (timeout) clearTimeout(timeout);\n resolve({\n statusCode,\n headers: responseHeaders,\n body: responseData,\n });\n });\n\n req.on('error', (error) => {\n if (timeout) clearTimeout(timeout);\n reject(error);\n });\n\n req.write(body);\n req.end();\n });\n}\n\nexport function createNodeTransport(config: NodeTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const maxRetries = config.retries || 0;\n let attempt = 0;\n\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translating \"${text}\" to ${lang} with url ${config.baseUrl}${config.path}`);\n }\n\n while (attempt <= maxRetries) {\n try {\n const session = getOrCreateSession(config.baseUrl, config.debug);\n const body = JSON.stringify({ text, lang, ctx });\n \n const response = await makeHttp2Request(\n session,\n config.path,\n config.headers || {},\n body,\n config.timeoutMs\n );\n\n if (response.statusCode < 200 || response.statusCode >= 300) {\n throw new Error(`HTTP ${response.statusCode}: Request failed`);\n }\n\n const result = JSON.parse(response.body);\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } catch (error) {\n attempt++;\n if (config.debug) {\n console.error(`[BeLocal Node Transport] Attempt ${attempt} failed:`, error instanceof Error ? error.message : String(error));\n }\n if (attempt > maxRetries) {\n throw error;\n }\n\n await new Promise(resolve => setTimeout(resolve, Math.pow(2, attempt) * 1000));\n }\n }\n\n return text;\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from './types';\nimport { createBrowserTransport } from '../transports/browser';\nimport { createNodeTransport } from '../transports/node';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n transport = 'auto',\n timeoutMs = 10000,\n retries = 3,\n credentials,\n headers = {},\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`,\n ...headers\n };\n\n this.transport = this.createTransport(transport, {\n baseUrl,\n path,\n timeoutMs,\n retries,\n credentials,\n headers: authHeaders,\n debug: this.debug\n });\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n\n private createTransport(\n transportType: 'browser' | 'node' | 'auto',\n config: {\n baseUrl: string;\n path: string;\n timeoutMs: number;\n retries: number;\n credentials?: RequestCredentials;\n headers: Record<string, string>;\n debug: boolean;\n }\n ): Transport {\n const actualTransport = transportType === 'auto' ? this.detectEnvironment() : transportType;\n\n if (config.debug) {\n console.log(`[BeLocal Engine] Creating ${actualTransport} transport with config:`, {\n baseUrl: config.baseUrl,\n path: config.path,\n timeoutMs: config.timeoutMs,\n ...(actualTransport === 'browser' && { credentials: config.credentials }),\n ...(actualTransport === 'node' && { retries: config.retries })\n });\n }\n\n if (actualTransport === 'browser') {\n return createBrowserTransport({\n baseUrl: config.baseUrl,\n path: config.path,\n credentials: config.credentials,\n headers: config.headers,\n timeoutMs: config.timeoutMs,\n debug: config.debug,\n });\n } else {\n return createNodeTransport({\n baseUrl: config.baseUrl,\n path: config.path,\n headers: config.headers,\n timeoutMs: config.timeoutMs,\n retries: config.retries,\n debug: config.debug,\n });\n }\n }\n\n /**\n * Автоматически определяет среду выполнения\n */\n private detectEnvironment(): 'browser' | 'node' {\n if (typeof window !== 'undefined' && typeof window.document !== 'undefined') {\n return 'browser';\n }\n \n if (typeof process !== 'undefined' && process.versions && process.versions.node) {\n return 'node';\n }\n\n return 'node';\n }\n}\n"]}
package/dist/index.js.map DELETED
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/transports/browser.ts","../src/transports/node.ts","../src/core/engine.ts"],"names":["session","headers"],"mappings":"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","file":"index.js","sourcesContent":["import type { Transport } from '../core/types';\n\nexport interface BrowserTransportConfig {\n baseUrl: string;\n path?: string;\n credentials?: RequestCredentials;\n headers?: Record<string, string>;\n timeoutMs?: number;\n debug?: boolean;\n}\n\nexport function createBrowserTransport(config: BrowserTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const url = `${config.baseUrl}${config.path}`;\n const controller = new AbortController();\n const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;\n\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translating \"${text}\" to ${lang} with url ${url}`);\n }\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...config.headers,\n },\n body: JSON.stringify({ text, lang, ctx }),\n credentials: config.credentials,\n signal: controller.signal,\n });\n\n if (!response.ok) {\n const errorMsg = `HTTP ${response.status}: ${response.statusText}`;\n if (config.debug) {\n console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);\n }\n throw new Error(errorMsg);\n }\n\n const result = await response.json();\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } finally {\n if (timeoutId) {\n clearTimeout(timeoutId);\n }\n }\n };\n}","import * as http2 from 'node:http2';\nimport { URL } from 'node:url';\nimport type { Transport } from '../core/types';\n\nexport interface NodeTransportConfig {\n baseUrl: string;\n path: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n retries?: number;\n debug?: boolean;\n}\n\n// Global session cache for HTTP/2 connections\nconst sessionCache = new Map<string, http2.ClientHttp2Session>();\n\nfunction getOrCreateSession(baseUrl: string, debug?: boolean): http2.ClientHttp2Session {\n if (sessionCache.has(baseUrl)) {\n const session = sessionCache.get(baseUrl)!;\n if (!session.destroyed) {\n return session;\n }\n sessionCache.delete(baseUrl);\n }\n\n const parsedUrl = new URL(baseUrl);\n const session = http2.connect(parsedUrl.origin);\n\n session.socket?.unref();\n \n // Set up session cleanup\n session.on('error', () => {\n sessionCache.delete(baseUrl);\n });\n \n session.on('close', () => {\n sessionCache.delete(baseUrl);\n });\n\n // Add debug logging if enabled\n if (debug) {\n session.on('connect', () => console.log('[H2] new session connected'));\n session.on('goaway', (code, lastStreamID, opaque) =>\n console.log('[H2] goaway', code, lastStreamID)\n );\n }\n \n sessionCache.set(baseUrl, session);\n return session;\n}\n\nfunction makeHttp2Request(\n session: http2.ClientHttp2Session,\n path: string,\n headers: Record<string, string>,\n body: string,\n timeoutMs?: number\n): Promise<{ statusCode: number; headers: Record<string, string>; body: string }> {\n return new Promise((resolve, reject) => {\n const req = session.request({\n ':method': 'POST',\n ':path': path,\n 'content-type': 'application/json',\n 'content-length': Buffer.byteLength(body),\n ...headers,\n });\n\n let timeout: NodeJS.Timeout | null = null;\n if (timeoutMs) {\n timeout = setTimeout(() => {\n req.destroy();\n reject(new Error(`Request timeout after ${timeoutMs}ms`));\n }, timeoutMs);\n }\n\n let responseData = '';\n let statusCode = 0;\n let responseHeaders: Record<string, string> = {};\n\n req.on('response', (headers) => {\n statusCode = headers[':status'] as number;\n responseHeaders = headers as Record<string, string>;\n });\n\n req.on('data', (chunk) => {\n responseData += chunk;\n });\n\n req.on('end', () => {\n if (timeout) clearTimeout(timeout);\n resolve({\n statusCode,\n headers: responseHeaders,\n body: responseData,\n });\n });\n\n req.on('error', (error) => {\n if (timeout) clearTimeout(timeout);\n reject(error);\n });\n\n req.write(body);\n req.end();\n });\n}\n\nexport function createNodeTransport(config: NodeTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const maxRetries = config.retries || 0;\n let attempt = 0;\n\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translating \"${text}\" to ${lang} with url ${config.baseUrl}${config.path}`);\n }\n\n while (attempt <= maxRetries) {\n try {\n const session = getOrCreateSession(config.baseUrl, config.debug);\n const body = JSON.stringify({ text, lang, ctx });\n \n const response = await makeHttp2Request(\n session,\n config.path,\n config.headers || {},\n body,\n config.timeoutMs\n );\n\n if (response.statusCode < 200 || response.statusCode >= 300) {\n throw new Error(`HTTP ${response.statusCode}: Request failed`);\n }\n\n const result = JSON.parse(response.body);\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } catch (error) {\n attempt++;\n if (config.debug) {\n console.error(`[BeLocal Node Transport] Attempt ${attempt} failed:`, error instanceof Error ? error.message : String(error));\n }\n if (attempt > maxRetries) {\n throw error;\n }\n\n await new Promise(resolve => setTimeout(resolve, Math.pow(2, attempt) * 1000));\n }\n }\n\n return text;\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from './types';\nimport { createBrowserTransport } from '../transports/browser';\nimport { createNodeTransport } from '../transports/node';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n transport = 'auto',\n timeoutMs = 10000,\n retries = 3,\n credentials,\n headers = {},\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`,\n ...headers\n };\n\n this.transport = this.createTransport(transport, {\n baseUrl,\n path,\n timeoutMs,\n retries,\n credentials,\n headers: authHeaders,\n debug: this.debug\n });\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n\n private createTransport(\n transportType: 'browser' | 'node' | 'auto',\n config: {\n baseUrl: string;\n path: string;\n timeoutMs: number;\n retries: number;\n credentials?: RequestCredentials;\n headers: Record<string, string>;\n debug: boolean;\n }\n ): Transport {\n const actualTransport = transportType === 'auto' ? this.detectEnvironment() : transportType;\n\n if (config.debug) {\n console.log(`[BeLocal Engine] Creating ${actualTransport} transport with config:`, {\n baseUrl: config.baseUrl,\n path: config.path,\n timeoutMs: config.timeoutMs,\n ...(actualTransport === 'browser' && { credentials: config.credentials }),\n ...(actualTransport === 'node' && { retries: config.retries })\n });\n }\n\n if (actualTransport === 'browser') {\n return createBrowserTransport({\n baseUrl: config.baseUrl,\n path: config.path,\n credentials: config.credentials,\n headers: config.headers,\n timeoutMs: config.timeoutMs,\n debug: config.debug,\n });\n } else {\n return createNodeTransport({\n baseUrl: config.baseUrl,\n path: config.path,\n headers: config.headers,\n timeoutMs: config.timeoutMs,\n retries: config.retries,\n debug: config.debug,\n });\n }\n }\n\n /**\n * Автоматически определяет среду выполнения\n */\n private detectEnvironment(): 'browser' | 'node' {\n if (typeof window !== 'undefined' && typeof window.document !== 'undefined') {\n return 'browser';\n }\n \n if (typeof process !== 'undefined' && process.versions && process.versions.node) {\n return 'node';\n }\n\n return 'node';\n }\n}\n"]}
package/dist/index.mjs DELETED
@@ -1,3 +0,0 @@
1
- import*as g from'http2';import {URL}from'url';function b(e){return async({text:s,lang:t,ctx:r})=>{let n=`${e.baseUrl}${e.path}`,p=new AbortController,a=e.timeoutMs?setTimeout(()=>p.abort(),e.timeoutMs):null;e.debug&&console.log(`[BeLocal Browser Transport] Translating "${s}" to ${t} with url ${n}`);try{let o=await fetch(n,{method:"POST",headers:{"Content-Type":"application/json",...e.headers},body:JSON.stringify({text:s,lang:t,ctx:r}),credentials:e.credentials,signal:p.signal});if(!o.ok){let u=`HTTP ${o.status}: ${o.statusText}`;throw e.debug&&console.error("[BeLocal Browser Transport] Request failed:",u),new Error(u)}let i=await o.json();return e.debug&&console.log(`[BeLocal Browser Transport] Translation successful: "${i.text||s}"`),i.text||s}finally{a&&clearTimeout(a);}}}var l=new Map;function y(e,s){if(l.has(e)){let n=l.get(e);if(!n.destroyed)return n;l.delete(e);}let t=new URL(e),r=g.connect(t.origin);return r.socket?.unref(),r.on("error",()=>{l.delete(e);}),r.on("close",()=>{l.delete(e);}),s&&(r.on("connect",()=>console.log("[H2] new session connected")),r.on("goaway",(n,p,a)=>console.log("[H2] goaway",n,p))),l.set(e,r),r}function f(e,s,t,r,n){return new Promise((p,a)=>{let o=e.request({":method":"POST",":path":s,"content-type":"application/json","content-length":Buffer.byteLength(r),...t}),i=null;n&&(i=setTimeout(()=>{o.destroy(),a(new Error(`Request timeout after ${n}ms`));},n));let u="",c=0,m={};o.on("response",d=>{c=d[":status"],m=d;}),o.on("data",d=>{u+=d;}),o.on("end",()=>{i&&clearTimeout(i),p({statusCode:c,headers:m,body:u});}),o.on("error",d=>{i&&clearTimeout(i),a(d);}),o.write(r),o.end();})}function T(e){return async({text:s,lang:t,ctx:r})=>{let n=e.retries||0,p=0;for(e.debug&&console.log(`[BeLocal Node Transport] Translating "${s}" to ${t} with url ${e.baseUrl}${e.path}`);p<=n;)try{let a=y(e.baseUrl,e.debug),o=JSON.stringify({text:s,lang:t,ctx:r}),i=await f(a,e.path,e.headers||{},o,e.timeoutMs);if(i.statusCode<200||i.statusCode>=300)throw new Error(`HTTP ${i.statusCode}: Request failed`);let u=JSON.parse(i.body);return e.debug&&console.log(`[BeLocal Node Transport] Translation successful: "${u.text||s}"`),u.text||s}catch(a){if(p++,e.debug&&console.error(`[BeLocal Node Transport] Attempt ${p} failed:`,a instanceof Error?a.message:String(a)),p>n)throw a;await new Promise(o=>setTimeout(o,Math.pow(2,p)*1e3));}return s}}var h=class{constructor(s){let{apiKey:t,baseUrl:r="https://dynamic.belocal.dev",path:n="/v1/translate",transport:p="auto",timeoutMs:a=1e4,retries:o=3,credentials:i,headers:u={},debug:c=false}=s;this.debug=c;let m={Authorization:`Bearer ${t}`,...u};this.transport=this.createTransport(p,{baseUrl:r,path:n,timeoutMs:a,retries:o,credentials:i,headers:m,debug:this.debug});}async t(s,t,r){return this.transport({text:s,lang:t,ctx:r})}createTransport(s,t){let r=s==="auto"?this.detectEnvironment():s;return t.debug&&console.log(`[BeLocal Engine] Creating ${r} transport with config:`,{baseUrl:t.baseUrl,path:t.path,timeoutMs:t.timeoutMs,...r==="browser"&&{credentials:t.credentials},...r==="node"&&{retries:t.retries}}),r==="browser"?b({baseUrl:t.baseUrl,path:t.path,credentials:t.credentials,headers:t.headers,timeoutMs:t.timeoutMs,debug:t.debug}):T({baseUrl:t.baseUrl,path:t.path,headers:t.headers,timeoutMs:t.timeoutMs,retries:t.retries,debug:t.debug})}detectEnvironment(){return typeof window<"u"&&typeof window.document<"u"?"browser":(typeof process<"u"&&process.versions&&process.versions.node,"node")}};
2
- export{h as BelocalEngine};//# sourceMappingURL=index.mjs.map
3
- //# sourceMappingURL=index.mjs.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/transports/browser.ts","../src/transports/node.ts","../src/core/engine.ts"],"names":["createBrowserTransport","config","text","lang","ctx","url","controller","timeoutId","response","errorMsg","result","sessionCache","getOrCreateSession","baseUrl","debug","session","parsedUrl","URL","code","lastStreamID","opaque","makeHttp2Request","path","headers","body","timeoutMs","resolve","reject","req","timeout","responseData","statusCode","responseHeaders","chunk","error","createNodeTransport","maxRetries","attempt","BelocalEngine","options","apiKey","transport","retries","credentials","authHeaders","transportType","actualTransport"],"mappings":"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","file":"index.mjs","sourcesContent":["import type { Transport } from '../core/types';\n\nexport interface BrowserTransportConfig {\n baseUrl: string;\n path?: string;\n credentials?: RequestCredentials;\n headers?: Record<string, string>;\n timeoutMs?: number;\n debug?: boolean;\n}\n\nexport function createBrowserTransport(config: BrowserTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const url = `${config.baseUrl}${config.path}`;\n const controller = new AbortController();\n const timeoutId = config.timeoutMs ? setTimeout(() => controller.abort(), config.timeoutMs) : null;\n\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translating \"${text}\" to ${lang} with url ${url}`);\n }\n\n try {\n const response = await fetch(url, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n ...config.headers,\n },\n body: JSON.stringify({ text, lang, ctx }),\n credentials: config.credentials,\n signal: controller.signal,\n });\n\n if (!response.ok) {\n const errorMsg = `HTTP ${response.status}: ${response.statusText}`;\n if (config.debug) {\n console.error(`[BeLocal Browser Transport] Request failed:`, errorMsg);\n }\n throw new Error(errorMsg);\n }\n\n const result = await response.json();\n if (config.debug) {\n console.log(`[BeLocal Browser Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } finally {\n if (timeoutId) {\n clearTimeout(timeoutId);\n }\n }\n };\n}","import * as http2 from 'node:http2';\nimport { URL } from 'node:url';\nimport type { Transport } from '../core/types';\n\nexport interface NodeTransportConfig {\n baseUrl: string;\n path: string;\n headers?: Record<string, string>;\n timeoutMs?: number;\n retries?: number;\n debug?: boolean;\n}\n\n// Global session cache for HTTP/2 connections\nconst sessionCache = new Map<string, http2.ClientHttp2Session>();\n\nfunction getOrCreateSession(baseUrl: string, debug?: boolean): http2.ClientHttp2Session {\n if (sessionCache.has(baseUrl)) {\n const session = sessionCache.get(baseUrl)!;\n if (!session.destroyed) {\n return session;\n }\n sessionCache.delete(baseUrl);\n }\n\n const parsedUrl = new URL(baseUrl);\n const session = http2.connect(parsedUrl.origin);\n\n session.socket?.unref();\n \n // Set up session cleanup\n session.on('error', () => {\n sessionCache.delete(baseUrl);\n });\n \n session.on('close', () => {\n sessionCache.delete(baseUrl);\n });\n\n // Add debug logging if enabled\n if (debug) {\n session.on('connect', () => console.log('[H2] new session connected'));\n session.on('goaway', (code, lastStreamID, opaque) =>\n console.log('[H2] goaway', code, lastStreamID)\n );\n }\n \n sessionCache.set(baseUrl, session);\n return session;\n}\n\nfunction makeHttp2Request(\n session: http2.ClientHttp2Session,\n path: string,\n headers: Record<string, string>,\n body: string,\n timeoutMs?: number\n): Promise<{ statusCode: number; headers: Record<string, string>; body: string }> {\n return new Promise((resolve, reject) => {\n const req = session.request({\n ':method': 'POST',\n ':path': path,\n 'content-type': 'application/json',\n 'content-length': Buffer.byteLength(body),\n ...headers,\n });\n\n let timeout: NodeJS.Timeout | null = null;\n if (timeoutMs) {\n timeout = setTimeout(() => {\n req.destroy();\n reject(new Error(`Request timeout after ${timeoutMs}ms`));\n }, timeoutMs);\n }\n\n let responseData = '';\n let statusCode = 0;\n let responseHeaders: Record<string, string> = {};\n\n req.on('response', (headers) => {\n statusCode = headers[':status'] as number;\n responseHeaders = headers as Record<string, string>;\n });\n\n req.on('data', (chunk) => {\n responseData += chunk;\n });\n\n req.on('end', () => {\n if (timeout) clearTimeout(timeout);\n resolve({\n statusCode,\n headers: responseHeaders,\n body: responseData,\n });\n });\n\n req.on('error', (error) => {\n if (timeout) clearTimeout(timeout);\n reject(error);\n });\n\n req.write(body);\n req.end();\n });\n}\n\nexport function createNodeTransport(config: NodeTransportConfig): Transport {\n return async ({ text, lang, ctx }) => {\n const maxRetries = config.retries || 0;\n let attempt = 0;\n\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translating \"${text}\" to ${lang} with url ${config.baseUrl}${config.path}`);\n }\n\n while (attempt <= maxRetries) {\n try {\n const session = getOrCreateSession(config.baseUrl, config.debug);\n const body = JSON.stringify({ text, lang, ctx });\n \n const response = await makeHttp2Request(\n session,\n config.path,\n config.headers || {},\n body,\n config.timeoutMs\n );\n\n if (response.statusCode < 200 || response.statusCode >= 300) {\n throw new Error(`HTTP ${response.statusCode}: Request failed`);\n }\n\n const result = JSON.parse(response.body);\n if (config.debug) {\n console.log(`[BeLocal Node Transport] Translation successful: \"${result.text || text}\"`);\n }\n return result.text || text;\n } catch (error) {\n attempt++;\n if (config.debug) {\n console.error(`[BeLocal Node Transport] Attempt ${attempt} failed:`, error instanceof Error ? error.message : String(error));\n }\n if (attempt > maxRetries) {\n throw error;\n }\n\n await new Promise(resolve => setTimeout(resolve, Math.pow(2, attempt) * 1000));\n }\n }\n\n return text;\n };\n}","import type { BelocalEngineOptions, KV, Lang, Transport } from './types';\nimport { createBrowserTransport } from '../transports/browser';\nimport { createNodeTransport } from '../transports/node';\n\nexport class BelocalEngine {\n private transport: Transport;\n private debug: boolean;\n\n constructor(options: BelocalEngineOptions) {\n const {\n apiKey,\n baseUrl = 'https://dynamic.belocal.dev',\n path = '/v1/translate',\n transport = 'auto',\n timeoutMs = 10000,\n retries = 3,\n credentials,\n headers = {},\n debug = false\n } = options;\n\n this.debug = debug;\n\n const authHeaders = {\n 'Authorization': `Bearer ${apiKey}`,\n ...headers\n };\n\n this.transport = this.createTransport(transport, {\n baseUrl,\n path,\n timeoutMs,\n retries,\n credentials,\n headers: authHeaders,\n debug: this.debug\n });\n }\n\n async t(text: string, lang: Lang, ctx?: KV): Promise<string> {\n return this.transport({ text, lang, ctx });\n }\n\n private createTransport(\n transportType: 'browser' | 'node' | 'auto',\n config: {\n baseUrl: string;\n path: string;\n timeoutMs: number;\n retries: number;\n credentials?: RequestCredentials;\n headers: Record<string, string>;\n debug: boolean;\n }\n ): Transport {\n const actualTransport = transportType === 'auto' ? this.detectEnvironment() : transportType;\n\n if (config.debug) {\n console.log(`[BeLocal Engine] Creating ${actualTransport} transport with config:`, {\n baseUrl: config.baseUrl,\n path: config.path,\n timeoutMs: config.timeoutMs,\n ...(actualTransport === 'browser' && { credentials: config.credentials }),\n ...(actualTransport === 'node' && { retries: config.retries })\n });\n }\n\n if (actualTransport === 'browser') {\n return createBrowserTransport({\n baseUrl: config.baseUrl,\n path: config.path,\n credentials: config.credentials,\n headers: config.headers,\n timeoutMs: config.timeoutMs,\n debug: config.debug,\n });\n } else {\n return createNodeTransport({\n baseUrl: config.baseUrl,\n path: config.path,\n headers: config.headers,\n timeoutMs: config.timeoutMs,\n retries: config.retries,\n debug: config.debug,\n });\n }\n }\n\n /**\n * Автоматически определяет среду выполнения\n */\n private detectEnvironment(): 'browser' | 'node' {\n if (typeof window !== 'undefined' && typeof window.document !== 'undefined') {\n return 'browser';\n }\n \n if (typeof process !== 'undefined' && process.versions && process.versions.node) {\n return 'node';\n }\n\n return 'node';\n }\n}\n"]}