qwenproxy-cli 1.3.1 → 1.3.2

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "qwenproxy-cli",
3
- "version": "1.3.1",
3
+ "version": "1.3.2",
4
4
  "description": "High-performance OpenAI & Anthropic compatible API gateway for Qwen with multi-account rotation, interactive TUI, and resilient tool calling.",
5
5
  "main": "src/index.ts",
6
6
  "bin": {
@@ -1889,94 +1889,94 @@ async function loginViaApi(
1889
1889
  .digest("hex");
1890
1890
  const signinUrl = qwenUrl("/api/v2/auths/signin");
1891
1891
 
1892
- const requestId = crypto.randomUUID();
1893
- const result = await page.evaluate(
1894
- async ({ email, password, signinUrl, requestId }) => {
1895
- try {
1896
- const response = await fetch(signinUrl, {
1897
- method: "POST",
1898
- signal: AbortSignal.timeout(10_000),
1899
- credentials: "include",
1900
- headers: {
1901
- accept: "application/json, text/plain, */*",
1902
- "content-type": "application/json",
1903
- source: "web",
1904
- timezone: new Date().toString().split(" (")[0],
1905
- "x-request-id": requestId,
1906
- },
1907
- body: JSON.stringify({ email, password, login_type: "email" }),
1908
- });
1909
- const data = await response.json().catch(() => null);
1910
- const token = data?.data?.token || data?.token;
1911
- if (token) {
1892
+ let signinSuccess = false;
1893
+ let data: any = null;
1894
+
1895
+ if (page.request && typeof page.request.post === "function") {
1896
+ try {
1897
+ const response = await page.request.post(signinUrl, {
1898
+ data: {
1899
+ email,
1900
+ password: hashedPassword,
1901
+ login_type: "email",
1902
+ },
1903
+ headers: {
1904
+ "content-type": "application/json",
1905
+ accept: "application/json, text/plain, */*",
1906
+ referer: qwenUrl("/auth"),
1907
+ origin: qwenOrigin(),
1908
+ },
1909
+ timeout: 10_000,
1910
+ });
1911
+ data = await response.json().catch(() => null);
1912
+ signinSuccess = Boolean(data && (data.success === true || data.token));
1913
+ } catch {}
1914
+ }
1915
+
1916
+ if (!signinSuccess && !data) {
1917
+ // Fallback to in-page evaluate fetch if page.request was unavailable
1918
+ const requestId = crypto.randomUUID();
1919
+ const evalRes = await page
1920
+ .evaluate(
1921
+ async ({ email, password, signinUrl, requestId }) => {
1912
1922
  try {
1913
- localStorage.setItem("token", token);
1914
- document.cookie = `token=${encodeURIComponent(token)}; path=/; domain=.qwen.ai; max-age=31536000`;
1915
- } catch {}
1916
- }
1917
- return { ok: response.ok, status: response.status, data, token };
1918
- } catch (e: any) {
1919
- return { ok: false, error: e.message };
1920
- }
1921
- },
1922
- { email, password: hashedPassword, signinUrl, requestId },
1923
- );
1923
+ const response = await fetch(signinUrl, {
1924
+ method: "POST",
1925
+ signal: AbortSignal.timeout(10_000),
1926
+ credentials: "include",
1927
+ headers: {
1928
+ accept: "application/json, text/plain, */*",
1929
+ "content-type": "application/json",
1930
+ source: "web",
1931
+ timezone: new Date().toString().split(" (")[0],
1932
+ "x-request-id": requestId,
1933
+ },
1934
+ body: JSON.stringify({ email, password, login_type: "email" }),
1935
+ });
1936
+ const json = await response.json().catch(() => null);
1937
+ return { ok: response.ok, status: response.status, data: json };
1938
+ } catch (e: any) {
1939
+ return { ok: false, error: e.message };
1940
+ }
1941
+ },
1942
+ { email, password: hashedPassword, signinUrl, requestId },
1943
+ )
1944
+ .catch(() => null);
1924
1945
 
1925
- if (result.data) {
1926
- if (result.data.success === true || result.token) {
1927
- await page
1928
- .goto(qwenUrl("/"), {
1929
- waitUntil: "domcontentloaded",
1930
- timeout: config.timeouts.navigation,
1931
- })
1932
- .catch(() => {});
1933
- await sleep(1000);
1934
- const url = page.url();
1935
- const isLogged = !(url.includes("/auth") || url.includes("/login"));
1936
- if (isLogged) {
1937
- return { success: true };
1938
- }
1939
- const loggedIn = await isPageLoggedIn(page);
1940
- if (loggedIn) {
1941
- return { success: true };
1942
- }
1943
- } else if (result.data.success === false) {
1944
- const code = result.data?.data?.code || result.data?.code;
1945
- const details =
1946
- result.data?.data?.details ||
1947
- result.data?.details ||
1948
- result.data?.message;
1949
- const classified = classifyQwenAuthError(code, details);
1950
- return {
1951
- success: false,
1952
- permanentFailure: classified.isPermanent,
1953
- reason: classified.reason,
1954
- };
1946
+ if (evalRes?.data) {
1947
+ data = evalRes.data;
1948
+ signinSuccess = Boolean(data && (data.success === true || data.token));
1955
1949
  }
1956
1950
  }
1957
1951
 
1958
- if (result.ok) {
1952
+ if (data?.success === false) {
1953
+ const code = data?.data?.code || data?.code;
1954
+ const details = data?.data?.details || data?.details || data?.message;
1955
+ const classified = classifyQwenAuthError(code, details);
1956
+ return {
1957
+ success: false,
1958
+ permanentFailure: classified.isPermanent,
1959
+ reason: classified.reason,
1960
+ };
1961
+ }
1962
+
1963
+ if (signinSuccess) {
1959
1964
  await page
1960
1965
  .goto(qwenUrl("/"), {
1961
1966
  waitUntil: "domcontentloaded",
1962
1967
  timeout: config.timeouts.navigation,
1963
1968
  })
1964
1969
  .catch(() => {});
1965
- await sleep(1000);
1966
- const url = page.url();
1967
- const isLogged = !(url.includes("/auth") || url.includes("/login"));
1968
- if (isLogged) {
1970
+ await sleep(1500);
1971
+ const loggedIn = await isPageLoggedIn(page, 4_000);
1972
+ if (loggedIn) {
1969
1973
  return { success: true };
1970
1974
  }
1971
- const loggedIn = await isPageLoggedIn(page);
1972
- return {
1973
- success: loggedIn,
1974
- reason: loggedIn ? undefined : "Sessão não autenticada após signin",
1975
- };
1976
1975
  }
1976
+
1977
1977
  return {
1978
1978
  success: false,
1979
- reason: result.error || `HTTP ${result.status || "desconhecido"} sem corpo JSON válido`,
1979
+ reason: "API signin não confirmou sessão autenticada",
1980
1980
  };
1981
1981
  } catch (err: any) {
1982
1982
  const errMsg = err?.message || String(err);
@@ -985,12 +985,12 @@ export async function requestQwenSettingsDirectFetch(
985
985
  // passes the WAF.
986
986
  let json: any = null;
987
987
  let okShape = false;
988
- if (contentType.includes("html")) {
988
+ if (contentType.includes("html") || !response.ok) {
989
989
  okShape = false;
990
990
  } else {
991
991
  try {
992
992
  json = JSON.parse(raw);
993
- okShape = json && typeof json === "object" && "success" in json;
993
+ okShape = json && typeof json === "object" && json.success === true;
994
994
  } catch {
995
995
  okShape = false;
996
996
  }