diff --git a/extensions/git/src/github.ts b/extensions/git/src/github.ts new file mode 100644 index 00000000000..478a83326ca --- /dev/null +++ b/extensions/git/src/github.ts @@ -0,0 +1,29 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ + +import * as vscode from 'vscode'; +import { CredentialsProvider, Credentials } from './api/git'; + +export class GitHubCredentialProvider implements CredentialsProvider { + + async getCredentials(host: vscode.Uri): Promise { + if (!/github\.com/i.test(host.authority)) { + return; + } + + const session = await this.getSession(); + return { username: session.account.id, password: await session.getAccessToken() }; + } + + private async getSession(): Promise { + const authenticationSessions = await vscode.authentication.getSessions('github', ['repo']); + + if (authenticationSessions.length) { + return await authenticationSessions[0]; + } else { + return await vscode.authentication.login('github', ['repo']); + } + } +} diff --git a/extensions/git/src/main.ts b/extensions/git/src/main.ts index dd50fa8e39a..5d6a67c2595 100644 --- a/extensions/git/src/main.ts +++ b/extensions/git/src/main.ts @@ -22,6 +22,7 @@ import * as path from 'path'; import * as fs from 'fs'; import { GitTimelineProvider } from './timelineProvider'; import { registerAPICommands } from './api/api1'; +import { GitHubCredentialProvider } from './github'; const deactivateTasks: { (): Promise; }[] = []; @@ -37,6 +38,7 @@ async function createModel(context: ExtensionContext, outputChannel: OutputChann const askpass = await Askpass.create(outputChannel); disposables.push(askpass); + context.subscriptions.push(askpass.registerCredentialsProvider(new GitHubCredentialProvider())); const git = new Git({ gitPath: info.path, version: info.version, env: askpass.getEnv() }); const model = new Model(git, askpass, context.globalState, outputChannel); diff --git a/extensions/github-authentication/package.json b/extensions/github-authentication/package.json index 79ce9cbe49b..54d30a027f2 100644 --- a/extensions/github-authentication/package.json +++ b/extensions/github-authentication/package.json @@ -14,9 +14,6 @@ "activationEvents": [ "*" ], - "extensionDependencies": [ - "vscode.git" - ], "aiKey": "AIF-d9b70cd4-b9f9-4d70-929b-a071c400b217", "main": "./out/extension.js", "scripts": { diff --git a/extensions/github-authentication/src/extension.ts b/extensions/github-authentication/src/extension.ts index ba4f5991f2e..aa2ecb54209 100644 --- a/extensions/github-authentication/src/extension.ts +++ b/extensions/github-authentication/src/extension.ts @@ -8,29 +8,6 @@ import { GitHubAuthenticationProvider, onDidChangeSessions } from './github'; import { uriHandler } from './githubServer'; import Logger from './common/logger'; import TelemetryReporter from 'vscode-extension-telemetry'; -import { GitExtension, CredentialsProvider, Credentials } from './typings/git'; - -class GitHubCredentialProvider implements CredentialsProvider { - - async getCredentials(host: vscode.Uri): Promise { - if (!/github\.com/i.test(host.authority)) { - return; - } - - const session = await this.getSession(); - return { username: session.account.id, password: await session.getAccessToken() }; - } - - private async getSession(): Promise { - const authenticationSessions = await vscode.authentication.getSessions('github', ['repo']); - - if (authenticationSessions.length) { - return await authenticationSessions[0]; - } else { - return await vscode.authentication.login('github', ['repo']); - } - } -} export async function activate(context: vscode.ExtensionContext) { const { name, version, aiKey } = require('../package.json') as { name: string, version: string, aiKey: string }; @@ -74,9 +51,7 @@ export async function activate(context: vscode.ExtensionContext) { } }); - const gitExtension = vscode.extensions.getExtension('vscode.git')!.exports; - const gitAPI = gitExtension.getAPI(1); - context.subscriptions.push(gitAPI.registerCredentialsProvider(new GitHubCredentialProvider())); + return; } // this method is called when your extension is deactivated diff --git a/extensions/github-authentication/src/typings/git.d.ts b/extensions/github-authentication/src/typings/git.d.ts deleted file mode 100644 index 46e8217ce6f..00000000000 --- a/extensions/github-authentication/src/typings/git.d.ts +++ /dev/null @@ -1,287 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ - -import { Uri, Event, Disposable, ProviderResult } from 'vscode'; -export { ProviderResult } from 'vscode'; - -export interface Git { - readonly path: string; -} - -export interface InputBox { - value: string; -} - -export const enum RefType { - Head, - RemoteHead, - Tag -} - -export interface Ref { - readonly type: RefType; - readonly name?: string; - readonly commit?: string; - readonly remote?: string; -} - -export interface UpstreamRef { - readonly remote: string; - readonly name: string; -} - -export interface Branch extends Ref { - readonly upstream?: UpstreamRef; - readonly ahead?: number; - readonly behind?: number; -} - -export interface Commit { - readonly hash: string; - readonly message: string; - readonly parents: string[]; - readonly authorDate?: Date; - readonly authorName?: string; - readonly authorEmail?: string; - readonly commitDate?: Date; -} - -export interface Submodule { - readonly name: string; - readonly path: string; - readonly url: string; -} - -export interface Remote { - readonly name: string; - readonly fetchUrl?: string; - readonly pushUrl?: string; - readonly isReadOnly: boolean; -} - -export const enum Status { - INDEX_MODIFIED, - INDEX_ADDED, - INDEX_DELETED, - INDEX_RENAMED, - INDEX_COPIED, - - MODIFIED, - DELETED, - UNTRACKED, - IGNORED, - INTENT_TO_ADD, - - ADDED_BY_US, - ADDED_BY_THEM, - DELETED_BY_US, - DELETED_BY_THEM, - BOTH_ADDED, - BOTH_DELETED, - BOTH_MODIFIED -} - -export interface Change { - - /** - * Returns either `originalUri` or `renameUri`, depending - * on whether this change is a rename change. When - * in doubt always use `uri` over the other two alternatives. - */ - readonly uri: Uri; - readonly originalUri: Uri; - readonly renameUri: Uri | undefined; - readonly status: Status; -} - -export interface RepositoryState { - readonly HEAD: Branch | undefined; - readonly refs: Ref[]; - readonly remotes: Remote[]; - readonly submodules: Submodule[]; - readonly rebaseCommit: Commit | undefined; - - readonly mergeChanges: Change[]; - readonly indexChanges: Change[]; - readonly workingTreeChanges: Change[]; - - readonly onDidChange: Event; -} - -export interface RepositoryUIState { - readonly selected: boolean; - readonly onDidChange: Event; -} - -/** - * Log options. - */ -export interface LogOptions { - /** Max number of log entries to retrieve. If not specified, the default is 32. */ - readonly maxEntries?: number; -} - -export interface CommitOptions { - all?: boolean | 'tracked'; - amend?: boolean; - signoff?: boolean; - signCommit?: boolean; - empty?: boolean; -} - -export interface Repository { - - readonly rootUri: Uri; - readonly inputBox: InputBox; - readonly state: RepositoryState; - readonly ui: RepositoryUIState; - - getConfigs(): Promise<{ key: string; value: string; }[]>; - getConfig(key: string): Promise; - setConfig(key: string, value: string): Promise; - getGlobalConfig(key: string): Promise; - - getObjectDetails(treeish: string, path: string): Promise<{ mode: string, object: string, size: number }>; - detectObjectType(object: string): Promise<{ mimetype: string, encoding?: string }>; - buffer(ref: string, path: string): Promise; - show(ref: string, path: string): Promise; - getCommit(ref: string): Promise; - - clean(paths: string[]): Promise; - - apply(patch: string, reverse?: boolean): Promise; - diff(cached?: boolean): Promise; - diffWithHEAD(): Promise; - diffWithHEAD(path: string): Promise; - diffWith(ref: string): Promise; - diffWith(ref: string, path: string): Promise; - diffIndexWithHEAD(): Promise; - diffIndexWithHEAD(path: string): Promise; - diffIndexWith(ref: string): Promise; - diffIndexWith(ref: string, path: string): Promise; - diffBlobs(object1: string, object2: string): Promise; - diffBetween(ref1: string, ref2: string): Promise; - diffBetween(ref1: string, ref2: string, path: string): Promise; - - hashObject(data: string): Promise; - - createBranch(name: string, checkout: boolean, ref?: string): Promise; - deleteBranch(name: string, force?: boolean): Promise; - getBranch(name: string): Promise; - setBranchUpstream(name: string, upstream: string): Promise; - - getMergeBase(ref1: string, ref2: string): Promise; - - status(): Promise; - checkout(treeish: string): Promise; - - addRemote(name: string, url: string): Promise; - removeRemote(name: string): Promise; - renameRemote(name: string, newName: string): Promise; - - fetch(remote?: string, ref?: string, depth?: number): Promise; - pull(unshallow?: boolean): Promise; - push(remoteName?: string, branchName?: string, setUpstream?: boolean): Promise; - - blame(path: string): Promise; - log(options?: LogOptions): Promise; - - commit(message: string, opts?: CommitOptions): Promise; -} - -export interface RemoteSource { - readonly name: string; - readonly description?: string; - readonly url: string | string[]; -} - -export interface RemoteSourceProvider { - readonly name: string; - readonly icon?: string; // codicon name - readonly supportsQuery?: boolean; - getRemoteSources(query?: string): ProviderResult; -} - -export interface Credentials { - readonly username: string; - readonly password: string; -} - -export interface CredentialsProvider { - getCredentials(host: Uri): ProviderResult; -} - -export type APIState = 'uninitialized' | 'initialized'; - -export interface API { - readonly state: APIState; - readonly onDidChangeState: Event; - readonly git: Git; - readonly repositories: Repository[]; - readonly onDidOpenRepository: Event; - readonly onDidCloseRepository: Event; - - toGitUri(uri: Uri, ref: string): Uri; - getRepository(uri: Uri): Repository | null; - init(root: Uri): Promise; - - registerRemoteSourceProvider(provider: RemoteSourceProvider): Disposable; - registerCredentialsProvider(provider: CredentialsProvider): Disposable; -} - -export interface GitExtension { - - readonly enabled: boolean; - readonly onDidChangeEnablement: Event; - - /** - * Returns a specific API version. - * - * Throws error if git extension is disabled. You can listed to the - * [GitExtension.onDidChangeEnablement](#GitExtension.onDidChangeEnablement) event - * to know when the extension becomes enabled/disabled. - * - * @param version Version number. - * @returns API instance - */ - getAPI(version: 1): API; -} - -export const enum GitErrorCodes { - BadConfigFile = 'BadConfigFile', - AuthenticationFailed = 'AuthenticationFailed', - NoUserNameConfigured = 'NoUserNameConfigured', - NoUserEmailConfigured = 'NoUserEmailConfigured', - NoRemoteRepositorySpecified = 'NoRemoteRepositorySpecified', - NotAGitRepository = 'NotAGitRepository', - NotAtRepositoryRoot = 'NotAtRepositoryRoot', - Conflict = 'Conflict', - StashConflict = 'StashConflict', - UnmergedChanges = 'UnmergedChanges', - PushRejected = 'PushRejected', - RemoteConnectionError = 'RemoteConnectionError', - DirtyWorkTree = 'DirtyWorkTree', - CantOpenResource = 'CantOpenResource', - GitNotFound = 'GitNotFound', - CantCreatePipe = 'CantCreatePipe', - CantAccessRemote = 'CantAccessRemote', - RepositoryNotFound = 'RepositoryNotFound', - RepositoryIsLocked = 'RepositoryIsLocked', - BranchNotFullyMerged = 'BranchNotFullyMerged', - NoRemoteReference = 'NoRemoteReference', - InvalidBranchName = 'InvalidBranchName', - BranchAlreadyExists = 'BranchAlreadyExists', - NoLocalChanges = 'NoLocalChanges', - NoStashFound = 'NoStashFound', - LocalChangesOverwritten = 'LocalChangesOverwritten', - NoUpstreamBranch = 'NoUpstreamBranch', - IsInSubmodule = 'IsInSubmodule', - WrongCase = 'WrongCase', - CantLockRef = 'CantLockRef', - CantRebaseMultipleBranches = 'CantRebaseMultipleBranches', - PatchDoesNotApply = 'PatchDoesNotApply', - NoPathFound = 'NoPathFound', - UnknownPath = 'UnknownPath', -}