From a911aca471e8791388b37ec7f0588e7089c01dc3 Mon Sep 17 00:00:00 2001 From: Eric Amodio Date: Sun, 15 Jul 2018 00:40:22 -0400 Subject: [PATCH] Closes #316 - Show file history from another branch or tag Renames Show Branches and Tags -> Choose from Branch or Tag History... Changes it to show the revision history rather than immediate executing --- CHANGELOG.md | 3 ++ src/commands/diffWithRevision.ts | 57 +++++++++++++++++----------- src/commands/openFileRevision.ts | 58 +++++++++++++++++++---------- src/commands/showQuickFileHistory.ts | 68 +++++++++++++++++++++++----------- src/quickPicks/commonQuickPicks.ts | 4 +- src/quickPicks/fileHistoryQuickPick.ts | 6 +-- 6 files changed, 128 insertions(+), 68 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6612f54..e01e8ab 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,10 +10,13 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/) and this p - Adds tag annotations to the tag tooltips in the *GitLens* explorer — closes [#431](https://github.com/eamodio/vscode-gitlens/issues/431) - Adds `gitlens.hovers.avatars` setting to specify whether to show avatar images in hovers — closes [#432](https://github.com/eamodio/vscode-gitlens/issues/432) thanks to [PR #441](https://github.com/eamodio/vscode-gitlens/pull/441) by Segev Finer ([@segevfiner](https://github.com/segevfiner)) - Adds `gitlens.hovers.avatars` setting to the interactive settings editor to specify whether to show avatar images in hovers +- Adds *Choose from Branch or Tag History...* to the quick pick menu shown by the *Show File History...* command (`gitlens.showQuickFileHistory`) — closes [#316](https://github.com/eamodio/vscode-gitlens/issues/316) ### Changed - Renames the *GitLens History* explorer to *GitLens File History* explorer for better clarity - Changes the *GitLens File History* explorer to always show the full file history even when reviewing revisions +- Changes the behavior of and renames the *Show Branches and Tags* command and on the quick pick menu shown by the *Compare File with Revision...* command (`gitlens.diffWithRevision`) to *Choose from Branch or Tag History...* +- Changes the behavior of and renames the *Show Branches and Tags* command on the quick pick menu shown by the *Open Revision...* command (`gitlens.openFileRevision`) to *Choose from Branch or Tag History...* ### Removed - Removes `gitlens:activeIsTracked`, `gitlens:activeIsBlameable`, `gitlens:activeIsRevision`, and `gitlens:activeHasRemotes` contexts and consolidates them into `gitlens:activeFileStatus` for better performance and UX diff --git a/src/commands/diffWithRevision.ts b/src/commands/diffWithRevision.ts index 08be1b3..fc65aba 100644 --- a/src/commands/diffWithRevision.ts +++ b/src/commands/diffWithRevision.ts @@ -5,12 +5,13 @@ import { ActiveEditorCommand, Commands, getCommandUri } from './common'; import { GlyphChars } from '../constants'; import { Container } from '../container'; import { DiffWithCommandArgs } from './diffWith'; -import { GitUri } from '../gitService'; +import { GitBranch, GitTag, GitUri } from '../gitService'; import { Logger } from '../logger'; import { Messages } from '../messages'; import { CommandQuickPickItem, FileHistoryQuickPick, ShowBranchesAndTagsQuickPickItem } from '../quickPicks/quickPicks'; export interface DiffWithRevisionCommandArgs { + branchOrTag?: GitBranch | GitTag; maxCount?: number; line?: number; @@ -34,17 +35,20 @@ export class DiffWithRevisionCommand extends ActiveEditorCommand { const gitUri = await GitUri.fromUri(uri); - const placeHolder = `Compare ${gitUri.getFormattedPath()}${ - gitUri.sha ? ` ${Strings.pad(GlyphChars.Dot, 1, 1)} ${gitUri.shortSha}` : '' - } with ${GlyphChars.Ellipsis}`; - const progressCancellation = FileHistoryQuickPick.showProgress(placeHolder); + const placeHolder = `Compare ${gitUri.getFormattedPath( + args.branchOrTag ? ` (${args.branchOrTag.name})${Strings.pad(GlyphChars.Dot, 2, 2)}` : undefined + )}${gitUri.sha ? ` ${Strings.pad(GlyphChars.Dot, 1, 1)} ${gitUri.shortSha}` : ''} with${GlyphChars.Ellipsis}`; + const progressCancellation = FileHistoryQuickPick.showProgress(placeHolder); try { const log = await Container.git.getLogForFile(gitUri.repoPath, gitUri.fsPath, { maxCount: args.maxCount, - ref: gitUri.sha + ref: (args.branchOrTag && args.branchOrTag.name) || gitUri.sha }); if (log === undefined) { + if (args.branchOrTag) { + return window.showWarningMessage(`The file could not be found in ${args.branchOrTag.name}`); + } return Messages.showFileNotUnderSourceControlWarningMessage('Unable to open history compare'); } @@ -75,21 +79,29 @@ export class DiffWithRevisionCommand extends ActiveEditorCommand { } } + const currentCommand = new CommandQuickPickItem( + { + label: `go back ${GlyphChars.ArrowBack}`, + description: `${Strings.pad(GlyphChars.Dash, 2, 3)} to history of ${ + GlyphChars.Space + }$(file-text) ${gitUri.getFormattedPath()}${ + args.branchOrTag + ? ` from ${GlyphChars.Space}${ + args.branchOrTag instanceof GitTag ? '$(tag)' : '$(git-branch)' + } ${args.branchOrTag.name}` + : gitUri.sha + ? ` from ${GlyphChars.Space}$(git-commit) ${gitUri.shortSha}` + : '' + }` + }, + Commands.DiffWithRevision, + [uri, { ...args }] + ); + const pick = await FileHistoryQuickPick.show(log, gitUri, placeHolder, { pickerOnly: true, progressCancellation: progressCancellation, - currentCommand: new CommandQuickPickItem( - { - label: `go back ${GlyphChars.ArrowBack}`, - description: `${Strings.pad(GlyphChars.Dash, 2, 3)} to history of ${ - GlyphChars.Space - }$(file-text) ${gitUri.getFormattedPath()}${ - gitUri.sha ? ` from ${GlyphChars.Space}$(git-commit) ${gitUri.shortSha}` : '' - }` - }, - Commands.DiffWithRevision, - [uri, { ...args }] - ), + currentCommand: currentCommand, nextPageCommand: args.nextPageCommand, previousPageCommand: previousPageCommand, showAllCommand: @@ -100,7 +112,7 @@ export class DiffWithRevisionCommand extends ActiveEditorCommand { description: `${Strings.pad(GlyphChars.Dash, 2, 3)} this may take a while` }, Commands.DiffWithRevision, - [uri, { ...args, maxCount: 0 }] + [uri, { ...args, maxCount: 0 } as DiffWithRevisionCommandArgs] ) : undefined }); @@ -111,10 +123,13 @@ export class DiffWithRevisionCommand extends ActiveEditorCommand { if (pick instanceof ShowBranchesAndTagsQuickPickItem) { const branchOrTag = await pick.execute(); if (branchOrTag === undefined) return undefined; - if (branchOrTag instanceof CommandQuickPickItem) return branchOrTag.execute(); - ref = branchOrTag.name; + return commands.executeCommand(Commands.DiffWithRevision, gitUri, { + ...args, + branchOrTag: branchOrTag.branchOrTag, + goBackCommand: currentCommand + } as DiffWithRevisionCommandArgs); } else { if (pick instanceof CommandQuickPickItem) return pick.execute(); diff --git a/src/commands/openFileRevision.ts b/src/commands/openFileRevision.ts index d72bd5b..52575d9 100644 --- a/src/commands/openFileRevision.ts +++ b/src/commands/openFileRevision.ts @@ -1,16 +1,17 @@ 'use strict'; import { Iterables, Strings } from '../system'; -import { CancellationTokenSource, Range, TextDocumentShowOptions, TextEditor, Uri, window } from 'vscode'; +import { CancellationTokenSource, commands, Range, TextDocumentShowOptions, TextEditor, Uri, window } from 'vscode'; import { ActiveEditorCommand, Commands, getCommandUri, openEditor } from './common'; import { FileAnnotationType } from '../configuration'; import { GlyphChars } from '../constants'; import { Container } from '../container'; -import { GitUri } from '../gitService'; +import { GitBranch, GitTag, GitUri } from '../gitService'; import { Logger } from '../logger'; import { Messages } from '../messages'; import { CommandQuickPickItem, FileHistoryQuickPick, ShowBranchesAndTagsQuickPickItem } from '../quickPicks/quickPicks'; export interface OpenFileRevisionCommandArgs { + branchOrTag?: GitBranch | GitTag; uri?: Uri; maxCount?: number; @@ -64,16 +65,22 @@ export class OpenFileRevisionCommand extends ActiveEditorCommand { const gitUri = await GitUri.fromUri(uri); - const placeHolder = `Open ${gitUri.getFormattedPath()}${ - gitUri.sha ? ` ${Strings.pad(GlyphChars.Dot, 1, 1)} ${gitUri.shortSha}` : '' - } in revision ${GlyphChars.Ellipsis}`; + const placeHolder = `Open revision of ${gitUri.getFormattedPath( + args.branchOrTag ? ` (${args.branchOrTag.name})${Strings.pad(GlyphChars.Dot, 2, 2)}` : undefined + )}${gitUri.sha ? ` ${Strings.pad(GlyphChars.Dot, 1, 1)} ${gitUri.shortSha}` : ''}${ + GlyphChars.Ellipsis + }`; + progressCancellation = FileHistoryQuickPick.showProgress(placeHolder); const log = await Container.git.getLogForFile(gitUri.repoPath, gitUri.fsPath, { maxCount: args.maxCount, - ref: gitUri.sha + ref: (args.branchOrTag && args.branchOrTag.name) || gitUri.sha }); if (log === undefined) { + if (args.branchOrTag) { + return window.showWarningMessage(`The file could not be found in ${args.branchOrTag.name}`); + } return Messages.showFileNotUnderSourceControlWarningMessage('Unable to open history compare'); } @@ -104,21 +111,29 @@ export class OpenFileRevisionCommand extends ActiveEditorCommand { } } + const currentCommand = new CommandQuickPickItem( + { + label: `go back ${GlyphChars.ArrowBack}`, + description: `${Strings.pad(GlyphChars.Dash, 2, 3)} to history of ${ + GlyphChars.Space + }$(file-text) ${gitUri.getFormattedPath()}${ + args.branchOrTag + ? ` from ${GlyphChars.Space}${ + args.branchOrTag instanceof GitTag ? '$(tag)' : '$(git-branch)' + } ${args.branchOrTag.name}` + : gitUri.sha + ? ` from ${GlyphChars.Space}$(git-commit) ${gitUri.shortSha}` + : '' + }` + }, + Commands.OpenFileRevision, + [uri, { ...args }] + ); + const pick = await FileHistoryQuickPick.show(log, gitUri, placeHolder, { pickerOnly: true, progressCancellation: progressCancellation, - currentCommand: new CommandQuickPickItem( - { - label: `go back ${GlyphChars.ArrowBack}`, - description: `${Strings.pad(GlyphChars.Dash, 2, 3)} to history of ${ - GlyphChars.Space - }$(file-text) ${gitUri.getFormattedPath()}${ - gitUri.sha ? ` from ${GlyphChars.Space}$(git-commit) ${gitUri.shortSha}` : '' - }` - }, - Commands.OpenFileRevision, - [uri, { ...args }] - ), + currentCommand: currentCommand, nextPageCommand: args.nextPageCommand, previousPageCommand: previousPageCommand, showAllCommand: @@ -138,10 +153,13 @@ export class OpenFileRevisionCommand extends ActiveEditorCommand { if (pick instanceof ShowBranchesAndTagsQuickPickItem) { const branchOrTag = await pick.execute(); if (branchOrTag === undefined) return undefined; - if (branchOrTag instanceof CommandQuickPickItem) return branchOrTag.execute(); - args.uri = GitUri.toRevisionUri(branchOrTag.name, gitUri.fsPath, gitUri.repoPath!); + return commands.executeCommand(Commands.OpenFileRevision, gitUri, { + ...args, + branchOrTag: branchOrTag.branchOrTag, + goBackCommand: currentCommand + } as OpenFileRevisionCommandArgs); } else { if (pick instanceof CommandQuickPickItem) return pick.execute(); diff --git a/src/commands/showQuickFileHistory.ts b/src/commands/showQuickFileHistory.ts index 15a484c..7f66c42 100644 --- a/src/commands/showQuickFileHistory.ts +++ b/src/commands/showQuickFileHistory.ts @@ -1,14 +1,15 @@ 'use strict'; -import { Iterables, Strings } from '../system'; import { commands, Range, TextEditor, Uri, window } from 'vscode'; +import { Iterables, Strings } from '../system'; import { ActiveEditorCachedCommand, Commands, getCommandUri } from './common'; import { GlyphChars } from '../constants'; import { Container } from '../container'; -import { GitLog, GitUri } from '../gitService'; +import { GitBranch, GitLog, GitTag, GitUri } from '../gitService'; import { Logger } from '../logger'; import { CommandQuickPickItem, FileHistoryQuickPick, + ShowBranchesAndTagsQuickPickItem, ShowCommitsInResultsQuickPickItem } from '../quickPicks/quickPicks'; import { ShowQuickCommitFileDetailsCommandArgs } from './showQuickCommitFileDetails'; @@ -16,6 +17,7 @@ import { Messages } from '../messages'; import * as path from 'path'; export interface ShowQuickFileHistoryCommandArgs { + branchOrTag?: GitBranch | GitTag; log?: GitLog; maxCount?: number; range?: Range; @@ -37,9 +39,9 @@ export class ShowQuickFileHistoryCommand extends ActiveEditorCachedCommand { args = { ...args }; - const placeHolder = `${gitUri.getFormattedPath()}${ - gitUri.sha ? ` ${Strings.pad(GlyphChars.Dot, 1, 1)} ${gitUri.shortSha}` : '' - }`; + const placeHolder = `${gitUri.getFormattedPath( + args.branchOrTag ? ` (${args.branchOrTag.name})${Strings.pad(GlyphChars.Dot, 2, 2)}` : undefined + )}${gitUri.sha ? ` ${Strings.pad(GlyphChars.Dot, 1, 1)} ${gitUri.shortSha}` : ''}`; const progressCancellation = FileHistoryQuickPick.showProgress(placeHolder); try { @@ -47,9 +49,12 @@ export class ShowQuickFileHistoryCommand extends ActiveEditorCachedCommand { args.log = await Container.git.getLogForFile(gitUri.repoPath, gitUri.fsPath, { maxCount: args.maxCount, range: args.range, - ref: gitUri.sha + ref: (args.branchOrTag && args.branchOrTag.name) || gitUri.sha }); if (args.log === undefined) { + if (args.branchOrTag) { + return window.showWarningMessage(`The file could not be found in ${args.branchOrTag.name}`); + } return Messages.showFileNotUnderSourceControlWarningMessage('Unable to show file history'); } } @@ -86,8 +91,29 @@ export class ShowQuickFileHistoryCommand extends ActiveEditorCachedCommand { } } + // Create a command to get back to where we are right now + const currentCommand = new CommandQuickPickItem( + { + label: `go back ${GlyphChars.ArrowBack}`, + description: `${Strings.pad(GlyphChars.Dash, 2, 3)} to history of ${ + GlyphChars.Space + }$(file-text) ${path.basename(gitUri.fsPath)}${ + args.branchOrTag + ? ` from ${GlyphChars.Space}${ + args.branchOrTag instanceof GitTag ? '$(tag)' : '$(git-branch)' + } ${args.branchOrTag.name}` + : gitUri.sha + ? ` from ${GlyphChars.Space}$(git-commit) ${gitUri.shortSha}` + : '' + }` + }, + Commands.ShowQuickFileHistory, + [uri, args] + ); + const pick = await FileHistoryQuickPick.show(args.log, gitUri, placeHolder, { progressCancellation: progressCancellation, + currentCommand: currentCommand, goBackCommand: args.goBackCommand, nextPageCommand: args.nextPageCommand, previousPageCommand: previousPageCommand, @@ -112,21 +138,21 @@ export class ShowQuickFileHistoryCommand extends ActiveEditorCachedCommand { }); if (pick === undefined) return undefined; - if (pick instanceof CommandQuickPickItem) return pick.execute(); - - // Create a command to get back to where we are right now - const currentCommand = new CommandQuickPickItem( - { - label: `go back ${GlyphChars.ArrowBack}`, - description: `${Strings.pad(GlyphChars.Dash, 2, 3)} to history of ${ - GlyphChars.Space - }$(file-text) ${path.basename(pick.commit.fileName)}${ - gitUri.sha ? ` from ${GlyphChars.Space}$(git-commit) ${gitUri.shortSha}` : '' - }` - }, - Commands.ShowQuickFileHistory, - [uri, args] - ); + if (pick instanceof ShowBranchesAndTagsQuickPickItem) { + const branchOrTag = await pick.execute(); + if (branchOrTag === undefined) return undefined; + if (branchOrTag instanceof CommandQuickPickItem) return branchOrTag.execute(); + + return commands.executeCommand(Commands.ShowQuickFileHistory, gitUri, { + ...args, + log: undefined, + branchOrTag: branchOrTag.branchOrTag, + goBackCommand: currentCommand + } as ShowQuickFileHistoryCommandArgs); + } + else { + if (pick instanceof CommandQuickPickItem) return pick.execute(); + } return commands.executeCommand(Commands.ShowQuickCommitFileDetails, pick.commit.toGitUri(), { commit: pick.commit, diff --git a/src/quickPicks/commonQuickPicks.ts b/src/quickPicks/commonQuickPicks.ts index 11a2fc8..da7be0a 100644 --- a/src/quickPicks/commonQuickPicks.ts +++ b/src/quickPicks/commonQuickPicks.ts @@ -250,8 +250,8 @@ export class ShowBranchesAndTagsQuickPickItem extends CommandQuickPickItem { private readonly placeHolder: string, private readonly goBackCommand?: CommandQuickPickItem, item: QuickPickItem = { - label: 'Show Branches and Tags', - description: `${Strings.pad(GlyphChars.Dash, 2, 2)} displays branches and tags` + label: 'Choose from Branch or Tag History...', + description: `${Strings.pad(GlyphChars.Dash, 2, 2)} shows list of branches and tags` } ) { super(item, undefined, undefined); diff --git a/src/quickPicks/fileHistoryQuickPick.ts b/src/quickPicks/fileHistoryQuickPick.ts index 8790bd0..ae418a3 100644 --- a/src/quickPicks/fileHistoryQuickPick.ts +++ b/src/quickPicks/fileHistoryQuickPick.ts @@ -48,10 +48,8 @@ export class FileHistoryQuickPick { let index = 0; - if (options.pickerOnly) { - index++; - items.splice(0, 0, new ShowBranchesAndTagsQuickPickItem(log.repoPath, placeHolder, options.currentCommand)); - } + index++; + items.splice(0, 0, new ShowBranchesAndTagsQuickPickItem(log.repoPath, placeHolder, options.currentCommand)); if (options.showInResultsExplorerCommand !== undefined) { index++;