/******************************************************************************* * Copyright (c) 2010, 2013 SAP AG and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Mathias Kinzler (SAP AG) - initial implementation * Laurent Goubet <laurent.goubet@obeo.fr - 404121 *******************************************************************************/ package org.eclipse.egit.ui.view.repositories; import static org.eclipse.swtbot.swt.finder.waits.Conditions.widgetIsEnabled; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import java.io.File; import org.eclipse.core.runtime.IPath; import org.eclipse.core.runtime.Path; import org.eclipse.egit.ui.Activator; import org.eclipse.egit.ui.JobFamilies; import org.eclipse.egit.ui.internal.UIText; import org.eclipse.egit.ui.test.ContextMenuHelper; import org.eclipse.egit.ui.test.TestUtil; import org.eclipse.jface.dialogs.IDialogConstants; import org.eclipse.jface.operation.ModalContext; import org.eclipse.jgit.api.Git; import org.eclipse.jgit.lib.Constants; import org.eclipse.jgit.lib.RepositoryCache.FileKey; import org.eclipse.jgit.util.FS; import org.eclipse.swt.dnd.Clipboard; import org.eclipse.swt.dnd.TextTransfer; import org.eclipse.swt.dnd.Transfer; import org.eclipse.swt.widgets.Display; import org.eclipse.swtbot.eclipse.finder.widgets.SWTBotView; import org.eclipse.swtbot.swt.finder.junit.SWTBotJunit4ClassRunner; import org.eclipse.swtbot.swt.finder.utils.TableCollection; import org.eclipse.swtbot.swt.finder.widgets.SWTBotLabel; import org.eclipse.swtbot.swt.finder.widgets.SWTBotShell; import org.eclipse.swtbot.swt.finder.widgets.SWTBotText; import org.eclipse.swtbot.swt.finder.widgets.SWTBotTree; import org.eclipse.swtbot.swt.finder.widgets.SWTBotTreeItem; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; /** * SWTBot Tests for the Git Repositories View (repository handling) */ @RunWith(SWTBotJunit4ClassRunner.class) public class GitRepositoriesViewRepoHandlingTest extends GitRepositoriesViewTestBase { private static final String REMOVE_REPOSITORY_CONTEXT_MENU_LABEL = "RepoViewRemove.label"; private File repositoryFile; @Before public void before() throws Exception { repositoryFile = createProjectAndCommitToRepository(); } @Test public void testCopyPathToClipboard() throws Exception { clearView(); Activator.getDefault().getRepositoryUtil().addConfiguredRepository( repositoryFile); refreshAndWait(); final SWTBotTree tree = getOrOpenView().bot().tree(); tree.getAllItems()[0].select(); waitInUI(); Display.getDefault().syncExec(new Runnable() { @Override public void run() { Clipboard clp = new Clipboard(Display.getCurrent()); clp.clearContents(); clp.setContents(new Object[] { "x" }, new TextTransfer[] { TextTransfer.getInstance() }); String value = (String) clp.getContents(TextTransfer .getInstance()); assertEquals("Clipboard content should be x", "x", value); ContextMenuHelper.clickContextMenuSync(tree, myUtil .getPluginLocalizedValue("CopyPathCommand")); value = (String) clp.getContents(TextTransfer.getInstance()); assertTrue("Clipboard content (" + value + ")should be a repository path", FileKey .isGitRepository(new File(value), FS.DETECTED)); clp.dispose(); } }); } @Test public void testPasteRepoPath() throws Exception { clearView(); refreshAndWait(); final Exception[] exceptions = new Exception[1]; final SWTBotLabel label = getOrOpenView().bot().label( UIText.RepositoriesView_messsageEmpty); Display.getDefault().syncExec(new Runnable() { @Override public void run() { Clipboard clip = null; try { clip = new Clipboard(Display.getDefault()); clip.setContents(new Object[] { repositoryFile.getPath() }, new Transfer[] { TextTransfer.getInstance() }); ContextMenuHelper.clickContextMenuSync(label, myUtil.getPluginLocalizedValue("PastePathCommand")); } catch (Exception e) { exceptions[0] = e; } finally { if (clip != null) clip.dispose(); } } }); if (exceptions[0] != null) throw exceptions[0]; refreshAndWait(); assertHasRepo(repositoryFile); } @Test public void testRemoveRepositoryWithoutProjects() throws Exception { deleteAllProjects(); clearView(); Activator.getDefault().getRepositoryUtil().addConfiguredRepository( repositoryFile); refreshAndWait(); assertHasRepo(repositoryFile); SWTBotTree tree = getOrOpenView().bot().tree(); tree.getAllItems()[0].select(); ContextMenuHelper.clickContextMenuSync(tree, myUtil .getPluginLocalizedValue(REMOVE_REPOSITORY_CONTEXT_MENU_LABEL)); refreshAndWait(); assertEmpty(); } @Test public void testRemoveRepositoryWithProjectsYes() throws Exception { deleteAllProjects(); assertProjectExistence(PROJ1, false); clearView(); Activator.getDefault().getRepositoryUtil().addConfiguredRepository( repositoryFile); shareProjects(repositoryFile); assertProjectExistence(PROJ1, true); refreshAndWait(); assertHasRepo(repositoryFile); SWTBotTree tree = getOrOpenView().bot().tree(); tree.getAllItems()[0].select(); ContextMenuHelper.clickContextMenu(tree, myUtil .getPluginLocalizedValue(REMOVE_REPOSITORY_CONTEXT_MENU_LABEL)); SWTBotShell shell = bot .shell(UIText.RepositoriesView_ConfirmProjectDeletion_WindowTitle); shell.bot().button(IDialogConstants.YES_LABEL).click(); refreshAndWait(); assertEmpty(); assertProjectExistence(PROJ1, false); } @Test public void testRemoveRepositoryWithProjectsNo() throws Exception { deleteAllProjects(); assertProjectExistence(PROJ1, false); clearView(); Activator.getDefault().getRepositoryUtil().addConfiguredRepository( repositoryFile); shareProjects(repositoryFile); assertProjectExistence(PROJ1, true); refreshAndWait(); assertHasRepo(repositoryFile); SWTBotTree tree = getOrOpenView().bot().tree(); tree.getAllItems()[0].select(); ContextMenuHelper.clickContextMenu(tree, myUtil .getPluginLocalizedValue(REMOVE_REPOSITORY_CONTEXT_MENU_LABEL)); SWTBotShell shell = bot .shell(UIText.RepositoriesView_ConfirmProjectDeletion_WindowTitle); shell.bot().button(IDialogConstants.NO_LABEL).click(); refreshAndWait(); assertEmpty(); assertProjectExistence(PROJ1, true); } @Test public void testRemoveRepositoryWithProjectsCancel() throws Exception { deleteAllProjects(); assertProjectExistence(PROJ1, false); clearView(); Activator.getDefault().getRepositoryUtil().addConfiguredRepository( repositoryFile); shareProjects(repositoryFile); assertProjectExistence(PROJ1, true); refreshAndWait(); assertHasRepo(repositoryFile); SWTBotTree tree = getOrOpenView().bot().tree(); tree.getAllItems()[0].select(); ContextMenuHelper.clickContextMenu(tree, myUtil .getPluginLocalizedValue(REMOVE_REPOSITORY_CONTEXT_MENU_LABEL)); SWTBotShell shell = bot .shell(UIText.RepositoriesView_ConfirmProjectDeletion_WindowTitle); shell.bot().button(IDialogConstants.CANCEL_LABEL).click(); refreshAndWait(); assertHasRepo(repositoryFile); assertProjectExistence(PROJ1, true); } @Test public void testShowIn() throws Exception { clearView(); deleteAllProjects(); shareProjects(repositoryFile); refreshAndWait(); assertProjectExistence(PROJ1, true); assertEmpty(); getOrOpenView().show(); SWTBotView view = TestUtil.showExplorerView(); SWTBotTree explorerTree = view.bot().tree(); SWTBotTreeItem projectItem = getProjectItem(explorerTree, PROJ1) .select(); ContextMenuHelper.clickContextMenuSync(explorerTree, "Show In", viewName); refreshAndWait(); assertHasRepo(repositoryFile); SWTBotTree viewerTree = getOrOpenView().bot().tree(); TableCollection selection = viewerTree.selection(); assertEquals("Selection should contain one element: " + selection, 1, selection.rowCount()); String nodeText = selection.get(0).get(0); assertTrue("Node text should contain project name", projectItem .getText().startsWith(nodeText)); view.show(); SWTBotTreeItem item = TestUtil.expandAndWait(projectItem); item = TestUtil.expandAndWait(item.getNode(FOLDER)); item.getNode(FILE1).select(); ContextMenuHelper.clickContextMenuSync(explorerTree, "Show In", viewName); selection = viewerTree.selection(); assertTrue("Selection should contain one eelement", selection.rowCount() == 1); nodeText = selection.get(0).get(0); assertEquals("Node text should contain file name", FILE1, nodeText); } @Test public void testAddRepoButton() throws Exception { deleteAllProjects(); clearView(); refreshAndWait(); assertEmpty(); getOrOpenView() .toolbarButton( myUtil .getPluginLocalizedValue("RepoViewAddRepository.tooltip")) .click(); TestUtil.processUIEvents(); SWTBotShell shell = bot .shell(UIText.RepositorySearchDialog_AddGitRepositories); shell.bot().textWithLabel(UIText.RepositorySearchDialog_directory) .setText(getTestDirectory().getPath()); assertEquals(0, ModalContext.getModalLevel()); shell.bot().button(UIText.RepositorySearchDialog_Search).click(); TestUtil.processUIEvents(500); int max = 5000; int slept = 0; while (ModalContext.getModalLevel() > 0 && slept < max) { TestUtil.processUIEvents(100); slept += 100; } shell.activate(); SWTBotTreeItem item = shell.bot().tree().getAllItems()[0]; item.check(); shell.bot().button(IDialogConstants.FINISH_LABEL).click(); TestUtil.joinJobs(org.eclipse.egit.core.JobFamilies.AUTO_SHARE); refreshAndWait(); assertHasRepo(repositoryFile); } @Test public void testCloneRepoButton() throws Exception { clearView(); refreshAndWait(); assertEmpty(); getOrOpenView() .toolbarButton( myUtil .getPluginLocalizedValue("RepoViewCloneRepository.tooltip")) .click(); SWTBotShell shell = bot.shell(UIText.GitCloneWizard_title); shell.bot().tree().select("Clone URI"); shell.bot().button("Next >").click(); // for some reason, textWithLabel doesn't seem to work shell.bot() .textInGroup(UIText.RepositorySelectionPage_groupLocation, 0) .setText(repositoryFile.getPath()); shell.bot().button(IDialogConstants.NEXT_LABEL).click(); bot.waitUntil(widgetIsEnabled(shell.bot().tree()), 60000); shell.bot().button(IDialogConstants.NEXT_LABEL).click(); waitInUI(); // for some reason textWithLabel doesn't work; 0 is path text SWTBotText pathText = shell.bot().text(0); pathText.setText(pathText.getText() + "Cloned"); shell.bot().button(IDialogConstants.FINISH_LABEL).click(); TestUtil.joinJobs(JobFamilies.CLONE); refreshAndWait(); assertHasClonedRepo(); } @Test public void testCreateRepository() throws Exception { clearView(); refreshAndWait(); assertEmpty(); // create a non-bare repository getOrOpenView() .toolbarButton( myUtil.getPluginLocalizedValue("RepoViewCreateRepository.tooltip")) .click(); SWTBotShell shell = bot.shell(UIText.NewRepositoryWizard_WizardTitle); IPath newPath = new Path(getTestDirectory().getPath()); shell.bot().textWithLabel(UIText.CreateRepositoryPage_DirectoryLabel) .setText(newPath.append("NewRepository").toOSString()); shell.bot().button(IDialogConstants.FINISH_LABEL).click(); refreshAndWait(); File repoFile = new File(newPath.append("NewRepository").toFile(), Constants.DOT_GIT); myRepoViewUtil.getRootItem(getOrOpenView().bot().tree(), repoFile); assertFalse(myRepoViewUtil.lookupRepository(repoFile).isBare()); // create a bare repository getOrOpenView() .toolbarButton( myUtil.getPluginLocalizedValue("RepoViewCreateRepository.tooltip")) .click(); shell = bot.shell(UIText.NewRepositoryWizard_WizardTitle); newPath = new Path(getTestDirectory().getPath()).append("bare").append( "NewBareRepository"); shell.bot().textWithLabel(UIText.CreateRepositoryPage_DirectoryLabel) .setText(newPath.toOSString()); shell.bot().checkBox(UIText.CreateRepositoryPage_BareCheckbox).select(); shell.bot().button(IDialogConstants.FINISH_LABEL).click(); refreshAndWait(); repoFile = newPath.toFile(); myRepoViewUtil.getRootItem(getOrOpenView().bot().tree(), repoFile); assertTrue(myRepoViewUtil.lookupRepository(repoFile).isBare()); } @Test public void testSearchDirectoryWithBareRepos() throws Exception { deleteAllProjects(); shutDownRepositories(); clearView(); refreshAndWait(); assertEmpty(); Git.init().setBare(true) .setDirectory(new File(getTestDirectory(), "BareRepository1")) .call(); Git.init().setBare(true) .setDirectory(new File(getTestDirectory(), "BareRepository2")) .call(); getOrOpenView() .toolbarButton( myUtil.getPluginLocalizedValue("RepoViewAddRepository.tooltip")) .click(); SWTBotShell shell = bot .shell(UIText.RepositorySearchDialog_AddGitRepositories); shell.bot().checkBox(UIText.RepositorySearchDialog_DeepSearch_button) .deselect(); shell.bot().textWithLabel(UIText.RepositorySearchDialog_directory) .setText(getTestDirectory().getPath()); assertEquals(0, ModalContext.getModalLevel()); shell.bot().button(UIText.RepositorySearchDialog_Search).click(); TestUtil.processUIEvents(500); int max = 5000; int slept = 0; while (ModalContext.getModalLevel() > 0 && slept < max) { TestUtil.processUIEvents(100); slept += 100; } shell.activate(); TestUtil.waitUntilTreeHasNodeContainsText(shell.bot(), shell.bot() .tree(), "BareRepository1", 10000); TestUtil.waitUntilTreeHasNodeContainsText(shell.bot(), shell.bot() .tree(), "BareRepository2", 10000); } private void assertHasClonedRepo() throws Exception { final SWTBotTree tree = getOrOpenView().bot().tree(); String text = repositoryFile.getParentFile().getName() + "Cloned"; TestUtil.waitUntilTreeHasNodeContainsText(bot, tree, text, 10000); } }