/** * Turning credentials on this machine into a usable Google client. * * This is the composition root the connector never had. Every piece existed, * adoption, the token manager, the API client, the refresh call, and nothing * assembled them, so the agent held working credentials it could not reach. * * Precedence is native-first and deliberate: * * 1. The agent's own encrypted secret store. Credentials it owns, can * refresh, and can write back to. * 2. An existing `~/.gmail-mcp` install. Read-only: these belong to another * tool that may still be running, so a refreshed access token is never * written back over them. * * The fallback is what makes the owner's machine work without a setup run. It * is not a substitute for connecting an account, `/google adopt` copies the * credentials into the encrypted store so they survive the other tool being * removed, but it means the capability is genuinely usable rather than * merely explainable. */ import { GoogleApiClient, type GoogleApiFetchPort } from './api-client.js'; import { GoogleTokenManager } from './token-manager.js'; import { type GoogleFetchPort } from './oauth-loopback.js'; import { type GoogleCredentialSummary, type GoogleFilePort, type GoogleOAuthCredentials } from './credential-adoption.js'; /** The paths adoption reads. Exported so the capability index probes the same list. */ export declare function googleCredentialPaths(homeDirectory: string): readonly string[]; export interface GoogleConnectionSources { readonly files: GoogleFilePort; readonly homeDirectory: string; /** Reads a config value. Never used for secret values. */ readonly configGet: (key: string) => unknown; /** Reads a secret. Returns null when absent. */ readonly secretGet: (key: string) => Promise; } /** * Resolve the Google credentials this machine holds. * * The encrypted store, and by default nothing else. This used to fall through * to a scan of `~/.gmail-mcp` on every resolve, which meant an ordinary * capability check went looking through the home directory for another tool's * credential files. That is not something to do unasked: most people have no * such directory, and a connector that quietly picks up credentials it found * lying around is doing something nobody requested. * * Adoption is still fully supported and still works exactly as it did, it is * just user-directed now. Someone names a path (or runs the adopt command), * the credentials are copied into the encrypted store, and the reply says what * was taken up and where it now lives. `readDiskCredentials` exists for those * explicit callers; nothing reaches it by default. */ export declare function resolveGoogleCredentials(sources: GoogleConnectionSources, options?: { readonly includeDiskCredentials?: boolean; }): Promise; /** * Read credentials from the known on-disk layout, for a caller that was * explicitly told to look there. Never called from a default path. */ export declare function readDiskCredentials(sources: Pick): GoogleOAuthCredentials | null; /** Safe-to-display posture. Contains provenance and scopes, never a token. */ export declare function describeGoogleConnection(sources: GoogleConnectionSources, now?: number): Promise; export interface GoogleConnection { readonly client: GoogleApiClient; /** * The same token manager the client calls through. * * Carried because `scopes()` is the only honest answer to "what is this grant * allowed to do", and it is only correct AFTER a refresh: credentials read * from the encrypted secret store are constructed with `scopes: []` (the * store records no scope list), and the real set arrives on the refresh * response. A caller that gates on scopes, `collectHistoryDelta` does, and * refuses with `no-gmail-scope` when it sees none, therefore has to be able * to force that refresh first, or it would read an empty list as a revoked * capability and report a working mailbox as unreadable. * * The SAME instance rather than a second one, for the same reason * `historyDeltaPort` exists: two managers are two access tokens, two refresh * races and two different answers to `scopes()`. */ readonly tokens: GoogleTokenManager; readonly credentials: GoogleOAuthCredentials; readonly summary: GoogleCredentialSummary; } /** * Build a live Google client, or explain why there is not one. * * Adopted credentials get no persist function: they belong to another tool and * are never written back. */ export declare function openGoogleConnection(sources: GoogleConnectionSources, ports: { readonly fetch: GoogleFetchPort & GoogleApiFetchPort; /** * The account this machine is signed in as, when something knows it, * normally gcloud's active account. Supplied so an `invalid_grant` can be * diagnosed as an account mix-up instead of a shrug. */ readonly signedInAccount?: string | null; }, now?: number): Promise; //# sourceMappingURL=connection.d.ts.map