Java tutorial
/******************************************************************************* * Copyright (c) 2012 SAP 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: * Sascha Scholz (SAP) - initial API and implementation *******************************************************************************/ package org.eclipse.mylyn.internal.gerrit.ui.egit; import java.lang.reflect.InvocationTargetException; import java.net.URISyntaxException; import java.util.HashMap; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.egit.ui.internal.provisional.wizards.GitRepositoryInfo; import org.eclipse.egit.ui.internal.provisional.wizards.IRepositorySearchResult; import org.eclipse.jface.layout.GridDataFactory; import org.eclipse.jface.layout.GridLayoutFactory; import org.eclipse.jface.operation.IRunnableWithProgress; import org.eclipse.jface.viewers.DoubleClickEvent; import org.eclipse.jface.viewers.IDoubleClickListener; import org.eclipse.jface.viewers.ISelectionChangedListener; import org.eclipse.jface.viewers.ITreeSelection; import org.eclipse.jface.viewers.SelectionChangedEvent; import org.eclipse.jface.viewers.TreePath; import org.eclipse.jface.viewers.TreeViewer; import org.eclipse.jface.wizard.WizardPage; import org.eclipse.jgit.lib.ConfigConstants; import org.eclipse.jgit.lib.Constants; import org.eclipse.mylyn.commons.workbench.SubstringPatternFilter; import org.eclipse.mylyn.internal.gerrit.core.GerritConnector; import org.eclipse.mylyn.internal.gerrit.core.GerritCorePlugin; import org.eclipse.mylyn.internal.gerrit.core.GerritUtil; import org.eclipse.mylyn.internal.gerrit.core.client.GerritClient; import org.eclipse.mylyn.internal.gerrit.core.client.GerritConfiguration; import org.eclipse.mylyn.internal.gerrit.core.client.GerritException; import org.eclipse.mylyn.internal.tasks.ui.actions.AddRepositoryAction; import org.eclipse.mylyn.tasks.core.TaskRepository; import org.eclipse.osgi.util.NLS; import org.eclipse.swt.SWT; import org.eclipse.swt.events.KeyAdapter; import org.eclipse.swt.events.KeyEvent; import org.eclipse.swt.events.SelectionAdapter; import org.eclipse.swt.events.SelectionEvent; import org.eclipse.swt.layout.GridData; import org.eclipse.swt.layout.GridLayout; import org.eclipse.swt.widgets.Button; import org.eclipse.swt.widgets.Combo; import org.eclipse.swt.widgets.Composite; import org.eclipse.swt.widgets.Group; import org.eclipse.swt.widgets.Label; import org.eclipse.swt.widgets.Shell; import org.eclipse.ui.dialogs.FilteredTree; import com.google.gerrit.reviewdb.AccountGeneralPreferences.DownloadScheme; import com.google.gerrit.reviewdb.Project; /** * @author Sascha Scholz */ public class GerritRepositorySearchPage extends WizardPage implements IRepositorySearchResult { private Combo cloneUriCombo; private Button refreshButton; public GerritRepositorySearchPage() { super(GerritRepositorySearchPage.class.getName()); setTitle("Source Git Repository"); setMessage("Select the Gerrit project"); } @Override public void createControl(Composite parent) { Composite container = new Composite(parent, SWT.NONE); GridLayoutFactory.fillDefaults().numColumns(2).applyTo(container); GridDataFactory.fillDefaults().grab(true, true).applyTo(container); Composite composite = new Composite(container, SWT.NONE); GridLayoutFactory.fillDefaults().numColumns(1).applyTo(composite); GridDataFactory.fillDefaults().grab(true, true).applyTo(composite); FilteredTree tree = new FilteredTree(composite, SWT.SINGLE | SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL, new SubstringPatternFilter(), true); final TreeViewer tv = tree.getViewer(); GridDataFactory.fillDefaults().grab(true, true).applyTo(tree); tv.setContentProvider(new GerritRepositorySearchPageContentProvider()); tv.setLabelProvider(new GerritRepositorySearchPageLabelProvider()); tv.setInput(this); tv.addSelectionChangedListener(new ISelectionChangedListener() { @Override public void selectionChanged(SelectionChangedEvent event) { ITreeSelection selection = (ITreeSelection) event.getSelection(); GerritRepositorySearchPage.this.selectionChanged(tv, selection); } }); tv.addDoubleClickListener(new IDoubleClickListener() { @Override public void doubleClick(DoubleClickEvent event) { ITreeSelection selection = (ITreeSelection) event.getSelection(); GerritRepositorySearchPage.this.doubleClick(tv, selection); } }); tv.getTree().addKeyListener(new KeyAdapter() { @Override public void keyPressed(KeyEvent event) { if (event.keyCode == SWT.F5) { refreshConfigIfTaskRepositoryIsSelected(tv); } } }); final Composite buttonsComposite = new Composite(composite, SWT.NONE); GridLayoutFactory.fillDefaults().numColumns(2).applyTo(buttonsComposite); buttonsComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL | GridData.GRAB_HORIZONTAL)); buttonsComposite.setLayout(new GridLayout(2, false)); Button addButton = new Button(buttonsComposite, SWT.NONE); addButton.setText("Add..."); addButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { Shell shell = getShell(); if (shell != null && !shell.isDisposed()) { AddRepositoryAction addRepositoryAction = new AddRepositoryAction(); addRepositoryAction.setPromptToAddQuery(false); TaskRepository addedRepository = addRepositoryAction.showWizard(shell, GerritConnector.CONNECTOR_KIND); if (addedRepository != null) { tv.refresh(); refreshConfig(tv, addedRepository); } } } }); refreshButton = new Button(buttonsComposite, SWT.NONE); refreshButton.setText("Refresh"); refreshButton.setEnabled(false); refreshButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { refreshConfigIfTaskRepositoryIsSelected(tv); } }); final Group repositoryGroup = new Group(composite, SWT.NONE); repositoryGroup.setText("Git Repository"); GridLayoutFactory.fillDefaults().numColumns(2).applyTo(repositoryGroup); repositoryGroup.setLayoutData(new GridData(GridData.FILL_HORIZONTAL | GridData.GRAB_HORIZONTAL)); repositoryGroup.setLayout(new GridLayout(2, false)); new Label(repositoryGroup, SWT.NULL).setText("URI:"); cloneUriCombo = new Combo(repositoryGroup, SWT.DROP_DOWN); GridDataFactory.fillDefaults().grab(true, false).applyTo(cloneUriCombo); clearCloneUris(); setControl(container); } private void selectionChanged(final TreeViewer tv, ITreeSelection selection) { clearError(); if (selection.size() == 1) { refreshButton.setEnabled(true); if (selection.getFirstElement() instanceof Project) { TreePath path = selection.getPaths()[0]; TaskRepository repository = (TaskRepository) path.getSegment(0); Project project = (Project) path.getSegment(1); try { GerritConfiguration config = GerritCorePlugin.getGerritClient(repository).getConfiguration(); setCloneUris(GerritUtil.getCloneUris(config, repository, project)); } catch (URISyntaxException e) { String message = NLS.bind("Unable to compute Git clone URI for Gerrit project {0}", project.getName()); showError(e, message); clearCloneUris(); } } else if (selection.getFirstElement() instanceof TaskRepository) { clearCloneUris(); } } else { refreshButton.setEnabled(false); clearCloneUris(); } } private void showError(Exception e, String message) { GerritCorePlugin.logError(message, e); setErrorMessage(message); } private void clearError() { setErrorMessage(null); } private void setCloneUris(HashMap<DownloadScheme, String> uriMap) { cloneUriCombo.removeAll(); addCloneUriIfNotNull(uriMap, DownloadScheme.SSH); addCloneUriIfNotNull(uriMap, DownloadScheme.HTTP); addCloneUriIfNotNull(uriMap, DownloadScheme.ANON_HTTP); addCloneUriIfNotNull(uriMap, DownloadScheme.ANON_GIT); if (cloneUriCombo.getItemCount() > 0) { cloneUriCombo.select(0); cloneUriCombo.setEnabled(true); setPageComplete(true); } else { clearCloneUris(); showError(null, "No download scheme is offered. Additional schemes may be available after a refresh of the repository configuration."); } } private void addCloneUriIfNotNull(HashMap<DownloadScheme, String> uriMap, DownloadScheme scheme) { String uri = uriMap.get(scheme); if (uri != null) { cloneUriCombo.add(uri); } } private void clearCloneUris() { cloneUriCombo.removeAll(); cloneUriCombo.setText(""); //$NON-NLS-1$ cloneUriCombo.setEnabled(false); setPageComplete(false); } private void doubleClick(TreeViewer tv, ITreeSelection selection) { clearError(); GerritRepositorySearchPage.this.selectionChanged(tv, selection); if (selection.size() == 1 && selection.getFirstElement() instanceof TaskRepository) { Object element = selection.getFirstElement(); if (tv.getExpandedState(element)) { tv.collapseToLevel(element, 1); } else { tv.expandToLevel(element, 1); } } if (isPageComplete()) { getContainer().showPage(getNextPage()); } } private void refreshConfig(TreeViewer tv, final TaskRepository repository) { clearError(); try { final GerritClient client = GerritCorePlugin.getGerritClient(repository); getContainer().run(true, true, new IRunnableWithProgress() { public void run(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException { monitor.beginTask("Refreshing " + repository.getRepositoryLabel(), IProgressMonitor.UNKNOWN); try { client.refreshConfig(monitor); } catch (GerritException e) { throw new InvocationTargetException(e, e.getMessage()); } monitor.done(); } }); tv.refresh(repository); } catch (InvocationTargetException e) { showError(e, e.getMessage()); } catch (InterruptedException e) { } } private void refreshConfigIfTaskRepositoryIsSelected(final TreeViewer tv) { ITreeSelection selection = (ITreeSelection) tv.getSelection(); Object element = selection.getFirstElement(); if (element instanceof TaskRepository) { refreshConfig(tv, (TaskRepository) element); } else if (element instanceof Project) { TreePath path = selection.getPaths()[0]; refreshConfig(tv, (TaskRepository) path.getSegment(0)); } } @Override public GitRepositoryInfo getGitRepositoryInfo() { GitRepositoryInfo gitRepositoryInfo = new GitRepositoryInfo(cloneUriCombo.getText()); addFetchReviewNotesRefSpec(gitRepositoryInfo); addPushToGerritRefSpec(gitRepositoryInfo); addCreateGerritChangeIdConfig(gitRepositoryInfo); return gitRepositoryInfo; } private void addFetchReviewNotesRefSpec(GitRepositoryInfo gitRepositoryInfo) { String notesRef = Constants.R_NOTES + "*"; //$NON-NLS-1$ gitRepositoryInfo.addFetchRefSpec("+" + notesRef + ":" + notesRef); } private void addPushToGerritRefSpec(GitRepositoryInfo gitRepositoryInfo) { gitRepositoryInfo.addPushInfo("HEAD:refs/for/master", null); //$NON-NLS-1$ } private void addCreateGerritChangeIdConfig(GitRepositoryInfo gitRepositoryInfo) { gitRepositoryInfo.addRepositoryConfigProperty(ConfigConstants.CONFIG_GERRIT_SECTION, null, ConfigConstants.CONFIG_KEY_CREATECHANGEID, ConfigConstants.CONFIG_KEY_TRUE); } }