[file-history] create api for log file history and use it inside standard action

This commit is contained in:
Julia Beliaeva
2017-01-26 22:03:52 +03:00
parent f6396cb0cf
commit dbe06aa671
11 changed files with 123 additions and 203 deletions

View File

@@ -16,6 +16,7 @@
package com.intellij.openapi.vcs.actions;
import com.intellij.openapi.actionSystem.Presentation;
import com.intellij.openapi.components.ServiceManager;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Pair;
import com.intellij.openapi.vcs.AbstractVcs;
@@ -26,6 +27,7 @@ import com.intellij.openapi.vcs.changes.ChangesUtil;
import com.intellij.openapi.vcs.history.VcsHistoryProvider;
import com.intellij.openapi.vfs.LocalFileSystem;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.vcs.log.VcsLogFileHistoryProvider;
import com.intellij.vcsUtil.VcsUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -61,19 +63,25 @@ public class TabbedShowHistoryAction extends AbstractVcsAction {
}
private static boolean isEnabled(@NotNull Project project, @NotNull FilePath path, @NotNull VirtualFile fileOrParent) {
boolean result = false;
boolean fileInVcs = AbstractVcs.fileInVcsByFileStatus(project, fileOrParent);
if (!fileInVcs) return false;
AbstractVcs vcs = ChangesUtil.getVcsForFile(fileOrParent, project);
if (vcs == null) return false;
if (vcs != null) {
VcsHistoryProvider provider = vcs.getVcsHistoryProvider();
return canShowNewFileHistory(project, path) || canShowOldFileHistory(vcs, path, fileOrParent);
}
result = provider != null &&
(provider.supportsHistoryForDirectories() || !path.isDirectory()) &&
AbstractVcs.fileInVcsByFileStatus(project, fileOrParent) &&
provider.canShowHistoryFor(fileOrParent);
}
private static boolean canShowOldFileHistory(@NotNull AbstractVcs vcs, @NotNull FilePath path, @NotNull VirtualFile fileOrParent) {
VcsHistoryProvider provider = vcs.getVcsHistoryProvider();
return provider != null &&
(provider.supportsHistoryForDirectories() || !path.isDirectory()) &&
provider.canShowHistoryFor(fileOrParent);
}
return result;
private static boolean canShowNewFileHistory(@NotNull Project project, @NotNull FilePath path) {
VcsLogFileHistoryProvider historyProvider = ServiceManager.getService(VcsLogFileHistoryProvider.class);
return historyProvider != null && historyProvider.canShowFileHistory(project, path);
}
@NotNull
@@ -102,13 +110,27 @@ public class TabbedShowHistoryAction extends AbstractVcsAction {
@Override
protected void actionPerformed(@NotNull VcsContext context) {
Project project = context.getProject();
Project project = assertNotNull(context.getProject());
Pair<FilePath, VirtualFile> pair = getPathAndParentFile(context);
FilePath path = assertNotNull(pair.first);
VirtualFile fileOrParent = assertNotNull(pair.second);
AbstractVcs vcs = assertNotNull(ChangesUtil.getVcsForFile(fileOrParent, project));
VcsHistoryProvider provider = assertNotNull(vcs.getVcsHistoryProvider());
if (canShowNewFileHistory(project, path)) {
showNewFileHistory(project, path);
}
else {
showOldFileHistory(project, vcs, path);
}
}
private static void showNewFileHistory(@NotNull Project project, @NotNull FilePath path) {
VcsLogFileHistoryProvider historyProvider = ServiceManager.getService(VcsLogFileHistoryProvider.class);
historyProvider.showFileHistory(project, path, null);
}
private static void showOldFileHistory(@NotNull Project project, @NotNull AbstractVcs vcs, @NotNull FilePath path) {
VcsHistoryProvider provider = assertNotNull(vcs.getVcsHistoryProvider());
AbstractVcsHelper.getInstance(project).showFileHistory(provider, vcs.getAnnotationProvider(), path, null, vcs);
}
}

View File

@@ -20,5 +20,6 @@
<orderEntry type="module" module-name="testFramework" scope="TEST" />
<orderEntry type="library" name="gson" level="project" />
<orderEntry type="module" module-name="diff-impl" exported="" />
<orderEntry type="module" module-name="vcs-log-api" />
</component>
</module>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2000-2016 JetBrains s.r.o.
* Copyright 2000-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -13,14 +13,15 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package git4idea.actions;
package com.intellij.vcs.log;
import com.intellij.vcs.log.ui.actions.NewShowHistoryAction;
import git4idea.log.GitLogProvider;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.vcs.FilePath;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public class GitShowHistoryAction extends NewShowHistoryAction {
@Override
protected boolean useMainAction() {
return super.useMainAction() && GitLogProvider.isIndexingOn();
}
public interface VcsLogFileHistoryProvider {
boolean canShowFileHistory(@NotNull Project project, @NotNull FilePath path);
void showFileHistory(@NotNull Project project, @NotNull FilePath path, @Nullable String revisionNumber);
}

View File

@@ -30,6 +30,9 @@
<postStartupActivity implementation="com.intellij.vcs.log.impl.VcsProjectLog$InitLogStartupActivity"/>
<cachesInvalidator implementation="com.intellij.vcs.log.impl.VcsLogCachesInvalidator"/>
<applicationService serviceInterface="com.intellij.vcs.log.VcsLogFileHistoryProvider"
serviceImplementation="com.intellij.vcs.log.ui.history.VcsLogFileHistoryProviderImpl"/>
</extensions>
<actions>
@@ -63,8 +66,6 @@
<action class="com.intellij.vcs.log.ui.actions.RefreshLogAction" id="Vcs.Log.Refresh" use-shortcut-of="Refresh"/>
<action class="com.intellij.vcs.log.ui.actions.ShowGraphHistoryAction" id="Vcs.Show.Graph.History"
text="Show History as Graph" description="Show History as Graph" internal="true"/>
<action class="com.intellij.vcs.log.ui.actions.ShowHistoryAction" id="Vcs.Show.History"
text="Show History" description="Show History"/>
<action class="com.intellij.vcs.log.ui.actions.ShowCommitTooltipAction" id="Vcs.Log.ShowTooltip"
text="Show Commit Tooltip" description="Show tooltip for currently selected commit in the Log"
use-shortcut-of="QuickJavaDoc"/>

View File

@@ -29,5 +29,4 @@ public class VcsLogActionPlaces {
public static final String VCS_LOG_TEXT_FILTER_SETTINGS_ACTION = "Vcs.Log.QuickTextFilterSettings";
public static final String VCS_LOG_FOCUS_TEXT_FILTER = "Vcs.Log.FocusTextFilter";
public static final String VCS_LOG_SHOW_DETAILS_ACTION = "Vcs.Log.ShowDetailsAction";
public static final String VCS_SHOW_HISTORY_ACTION = "Vcs.Show.History";
}

View File

@@ -26,6 +26,7 @@ import com.intellij.ui.content.ContentManager;
import com.intellij.util.ContentUtilEx;
import com.intellij.util.ContentsUtil;
import com.intellij.vcs.log.impl.VcsLogContentProvider;
import com.intellij.vcs.log.ui.history.VcsLogFileHistoryProviderImpl;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -62,7 +63,7 @@ public class CloseLogTabAction extends CloseTabToolbarAction {
Content content = contentManager.getSelectedContent();
if (content != null) {
if (ContentUtilEx.isContentTab(content, VcsLogContentProvider.TAB_NAME) ||
ContentUtilEx.isContentTab(content, ShowHistoryAction.TAB_NAME)) {
ContentUtilEx.isContentTab(content, VcsLogFileHistoryProviderImpl.TAB_NAME)) {
return content;
}
}

View File

@@ -1,27 +0,0 @@
/*
* Copyright 2000-2016 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.vcs.log.ui.actions;
import com.intellij.openapi.actionSystem.ActionManager;
import com.intellij.vcs.log.ui.VcsLogActionPlaces;
public class NewShowHistoryAction extends SwitchableDelegateAction {
public NewShowHistoryAction() {
super(ActionManager.getInstance().getAction(VcsLogActionPlaces.VCS_SHOW_HISTORY_ACTION),
ActionManager.getInstance().getAction("Vcs.ShowTabbedFileHistory"),
"vcs.new.history");
}
}

View File

@@ -1,76 +0,0 @@
/*
* Copyright 2000-2016 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.vcs.log.ui.actions;
import com.intellij.openapi.actionSystem.AnActionEvent;
import com.intellij.openapi.actionSystem.CommonDataKeys;
import com.intellij.openapi.actionSystem.Presentation;
import com.intellij.openapi.project.DumbAwareAction;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.registry.Registry;
import com.intellij.openapi.vcs.FilePath;
import com.intellij.openapi.vcs.ProjectLevelVcsManager;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.vcs.log.data.VcsLogData;
import com.intellij.vcs.log.impl.VcsLogContentProvider;
import com.intellij.vcs.log.impl.VcsLogManager;
import com.intellij.vcs.log.impl.VcsProjectLog;
import com.intellij.vcs.log.ui.history.FileHistoryUi;
import com.intellij.vcs.log.ui.history.FileHistoryUiFactory;
import com.intellij.vcsUtil.VcsUtil;
import org.jetbrains.annotations.NotNull;
public class ShowHistoryAction extends DumbAwareAction {
@NotNull
public static final String TAB_NAME = "History";
@Override
public void actionPerformed(AnActionEvent e) {
Project project = e.getProject();
assert project != null;
VirtualFile file = e.getRequiredData(CommonDataKeys.VIRTUAL_FILE);
FilePath path = VcsUtil.getFilePath(file);
if (!VcsLogContentProvider.findAndSelectContent(project, FileHistoryUi.class, ui -> ui.getPath().equals(path))) {
VcsLogManager logManager = VcsProjectLog.getInstance(project).getLogManager();
assert logManager != null;
VcsLogContentProvider.openLogTab(project, logManager, TAB_NAME, file.getName(), new FileHistoryUiFactory(path));
}
}
@Override
public void update(AnActionEvent e) {
Presentation presentation = e.getPresentation();
if (!Registry.is("vcs.log.graph.history")) {
presentation.setEnabledAndVisible(false);
return;
}
VirtualFile file = e.getData(CommonDataKeys.VIRTUAL_FILE);
Project project = e.getProject();
if (file == null || project == null) {
presentation.setEnabledAndVisible(false);
return;
}
VirtualFile root = ProjectLevelVcsManager.getInstance(project).getVcsRootFor(file);
VcsLogData dataManager = VcsProjectLog.getInstance(project).getDataManager();
presentation.setEnabledAndVisible(root != null &&
dataManager != null &&
dataManager.getRoots().contains(root) &&
dataManager.getIndex().getDataGetter() != null);
}
}

View File

@@ -1,73 +0,0 @@
/*
* Copyright 2000-2016 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.vcs.log.ui.actions;
import com.intellij.openapi.actionSystem.AnAction;
import com.intellij.openapi.actionSystem.AnActionEvent;
import com.intellij.openapi.util.registry.Registry;
import org.jetbrains.annotations.NotNull;
public class SwitchableDelegateAction extends AnAction {
@NotNull private final AnAction myMainDelegate;
@NotNull private final AnAction myAlternateDelegate;
@NotNull private final String myRegistryKey;
public SwitchableDelegateAction(@NotNull AnAction mainAction, @NotNull AnAction alternateAction, @NotNull String registryKey) {
myMainDelegate = mainAction;
myAlternateDelegate = alternateAction;
myRegistryKey = registryKey;
copyFrom(mainAction);
setEnabledInModalContext(mainAction.isEnabledInModalContext());
}
@NotNull
private AnAction getDelegateAction() {
if (useMainAction()) {
return myMainDelegate;
}
return myAlternateDelegate;
}
protected boolean useMainAction() {
return Registry.is(myRegistryKey);
}
@Override
public void update(final AnActionEvent e) {
getDelegateAction().update(e);
}
@Override
public void actionPerformed(final AnActionEvent e) {
getDelegateAction().actionPerformed(e);
}
@Override
public boolean isDumbAware() {
return getDelegateAction().isDumbAware();
}
@Override
public boolean isTransparentUpdate() {
return getDelegateAction().isTransparentUpdate();
}
@Override
public boolean isInInjectedContext() {
return getDelegateAction().isInInjectedContext();
}
}

View File

@@ -0,0 +1,73 @@
/*
* Copyright 2000-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.vcs.log.ui.history;
import com.intellij.openapi.extensions.Extensions;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.registry.Registry;
import com.intellij.openapi.vcs.AbstractVcs;
import com.intellij.openapi.vcs.FilePath;
import com.intellij.openapi.vcs.ProjectLevelVcsManager;
import com.intellij.openapi.vcs.VcsRoot;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.util.containers.ContainerUtil;
import com.intellij.vcs.log.VcsLogFileHistoryProvider;
import com.intellij.vcs.log.VcsLogProperties;
import com.intellij.vcs.log.VcsLogProvider;
import com.intellij.vcs.log.data.VcsLogData;
import com.intellij.vcs.log.impl.VcsLogContentProvider;
import com.intellij.vcs.log.impl.VcsLogManager;
import com.intellij.vcs.log.impl.VcsProjectLog;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Arrays;
import java.util.List;
public class VcsLogFileHistoryProviderImpl implements VcsLogFileHistoryProvider {
@NotNull
public static final String TAB_NAME = "History";
@Override
public boolean canShowFileHistory(@NotNull Project project, @NotNull FilePath path) {
if (!Registry.is("vcs.new.history")) return false;
VcsRoot rootObject = ProjectLevelVcsManager.getInstance(project).getVcsRootObjectFor(path);
if (rootObject == null) return false;
VirtualFile root = rootObject.getPath();
AbstractVcs vcs = rootObject.getVcs();
if (vcs == null || root == null) return false;
VcsLogData dataManager = VcsProjectLog.getInstance(project).getDataManager();
if (dataManager == null || !dataManager.getRoots().contains(root) || dataManager.getIndex().getDataGetter() == null) return false;
List<VcsLogProvider> allLogProviders = Arrays.asList(Extensions.getExtensions(VcsLogProvider.LOG_PROVIDER_EP, project));
VcsLogProvider provider = ContainerUtil.find(allLogProviders, p -> p.getSupportedVcs().equals(vcs.getKeyInstanceMethod()));
if (provider == null) return false;
return VcsLogProperties.get(provider, VcsLogProperties.SUPPORTS_INDEXING);
}
@Override
public void showFileHistory(@NotNull Project project, @NotNull FilePath path, @Nullable String revisionNumber) {
if (!VcsLogContentProvider.findAndSelectContent(project, FileHistoryUi.class, ui -> ui.getPath().equals(path))) {
VcsLogManager logManager = VcsProjectLog.getInstance(project).getLogManager();
assert logManager != null;
VcsLogContentProvider.openLogTab(project, logManager, TAB_NAME, path.getName(), new FileHistoryUiFactory(path));
}
}
}

View File

@@ -38,8 +38,6 @@
</action>
<action class="git4idea.log.GitShowCommitInLogAction" id="Git.SelectInGitLog"/>
<action class="git4idea.actions.GitShowHistoryAction" id="Git.New.Show.History"
text="Show History" description="Show History"/>
<group id="GitFileActions">
<reference ref="CheckinFiles"/>
@@ -51,7 +49,7 @@
<reference ref="Compare.LastVersion"/>
<reference ref="Compare.Selected"/>
<action id="Git.CompareWithBranch" class="git4idea.actions.GitCompareWithBranchAction" text="Compare with Branch..." />
<reference id="Git.New.Show.History"/>
<reference ref="Vcs.ShowTabbedFileHistory"/>
<reference id="Vcs.ShowHistoryForBlock"/>
<reference id="Vcs.Show.Graph.History"/>
<separator/>