Merge tag 'v0.3.0' into chore/sync-gemini-cli-v0.3.0

This commit is contained in:
mingholy.lmh
2025-09-10 21:01:40 +08:00
583 changed files with 30160 additions and 10770 deletions

View File

@@ -4,30 +4,27 @@
* SPDX-License-Identifier: Apache-2.0
*/
import type { Credentials } from 'google-auth-library';
import {
OAuth2Client,
Credentials,
Compute,
CodeChallengeMethod,
Compute,
OAuth2Client,
} from 'google-auth-library';
import * as http from 'http';
import url from 'url';
import crypto from 'crypto';
import * as net from 'net';
import open from 'open';
import path from 'node:path';
import crypto from 'node:crypto';
import { promises as fs } from 'node:fs';
import * as os from 'os';
import { Config } from '../config/config.js';
import { getErrorMessage } from '../utils/errors.js';
import {
cacheGoogleAccount,
getCachedGoogleAccount,
clearCachedGoogleAccount,
} from '../utils/user_account.js';
import { AuthType } from '../core/contentGenerator.js';
import * as http from 'node:http';
import * as net from 'node:net';
import path from 'node:path';
import readline from 'node:readline';
import { QWEN_DIR } from '../utils/paths.js';
import url from 'node:url';
import open from 'open';
import type { Config } from '../config/config.js';
import { Storage } from '../config/storage.js';
import { AuthType } from '../core/contentGenerator.js';
import { FatalAuthenticationError, getErrorMessage } from '../utils/errors.js';
import { UserAccountManager } from '../utils/userAccountManager.js';
const userAccountManager = new UserAccountManager();
// OAuth Client ID used to initiate OAuth2Client class.
const OAUTH_CLIENT_ID =
@@ -54,8 +51,6 @@ const SIGN_IN_SUCCESS_URL =
const SIGN_IN_FAILURE_URL =
'https://developers.google.com/gemini-code-assist/auth_failure_gemini';
const CREDENTIAL_FILENAME = 'oauth_creds.json';
/**
* An Authentication URL for updating the credentials of a Oauth2Client
* as well as a promise that will resolve when the credentials have
@@ -99,7 +94,7 @@ async function initOauthClient(
if (await loadCachedCredentials(client)) {
// Found valid cached credentials.
// Check if we need to retrieve Google Account ID or Email
if (!getCachedGoogleAccount()) {
if (!userAccountManager.getCachedGoogleAccount()) {
try {
await fetchAndCacheUserInfo(client);
} catch {
@@ -147,7 +142,9 @@ async function initOauthClient(
}
}
if (!success) {
process.exit(1);
throw new FatalAuthenticationError(
'Failed to authenticate with user code.',
);
}
} else {
const webLogin = await authWithWeb(client);
@@ -171,7 +168,7 @@ async function initOauthClient(
console.error(
'Failed to open browser automatically. Please try running again with NO_BROWSER=true set.',
);
process.exit(1);
throw new FatalAuthenticationError('Failed to open browser.');
});
} catch (err) {
console.error(
@@ -179,7 +176,7 @@ async function initOauthClient(
err,
'\nPlease try running again with NO_BROWSER=true set.',
);
process.exit(1);
throw new FatalAuthenticationError('Failed to open browser.');
}
console.log('Waiting for authentication...');
@@ -352,7 +349,7 @@ export function getAvailablePort(): Promise<number> {
async function loadCachedCredentials(client: OAuth2Client): Promise<boolean> {
const pathsToTry = [
getCachedCredentialPath(),
Storage.getOAuthCredsPath(),
process.env['GOOGLE_APPLICATION_CREDENTIALS'],
].filter((p): p is string => !!p);
@@ -380,26 +377,22 @@ async function loadCachedCredentials(client: OAuth2Client): Promise<boolean> {
}
async function cacheCredentials(credentials: Credentials) {
const filePath = getCachedCredentialPath();
const filePath = Storage.getOAuthCredsPath();
await fs.mkdir(path.dirname(filePath), { recursive: true });
const credString = JSON.stringify(credentials, null, 2);
await fs.writeFile(filePath, credString, { mode: 0o600 });
}
function getCachedCredentialPath(): string {
return path.join(os.homedir(), QWEN_DIR, CREDENTIAL_FILENAME);
}
export function clearOauthClientCache() {
oauthClientPromises.clear();
}
export async function clearCachedCredentialFile() {
try {
await fs.rm(getCachedCredentialPath(), { force: true });
await fs.rm(Storage.getOAuthCredsPath(), { force: true });
// Clear the Google Account ID cache when credentials are cleared
await clearCachedGoogleAccount();
await userAccountManager.clearCachedGoogleAccount();
// Clear the in-memory OAuth client cache to force re-authentication
clearOauthClientCache();
} catch (e) {
@@ -433,9 +426,7 @@ async function fetchAndCacheUserInfo(client: OAuth2Client): Promise<void> {
}
const userInfo = await response.json();
if (userInfo.email) {
await cacheGoogleAccount(userInfo.email);
}
await userAccountManager.cacheGoogleAccount(userInfo.email);
} catch (error) {
console.error('Error retrieving user info:', error);
}