Package org.eclipse.egit.ui.internal.push

Source Code of org.eclipse.egit.ui.internal.push.PushBranchWizard

/*******************************************************************************
* Copyright (c) 2013, 2014 Robin Stocker <robin@nibor.org> 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
*******************************************************************************/
package org.eclipse.egit.ui.internal.push;

import java.io.IOException;
import java.net.URISyntaxException;
import java.text.MessageFormat;
import java.util.Arrays;
import java.util.List;
import java.util.Set;

import org.eclipse.egit.core.op.PushOperationResult;
import org.eclipse.egit.core.op.PushOperationSpecification;
import org.eclipse.egit.ui.internal.SecureStoreUtils;
import org.eclipse.egit.ui.internal.UIIcons;
import org.eclipse.egit.ui.internal.UIText;
import org.eclipse.egit.ui.internal.components.RepositorySelection;
import org.eclipse.egit.ui.internal.credentials.EGitCredentialsProvider;
import org.eclipse.jface.wizard.Wizard;
import org.eclipse.jgit.lib.ConfigConstants;
import org.eclipse.jgit.lib.Constants;
import org.eclipse.jgit.lib.ObjectId;
import org.eclipse.jgit.lib.Ref;
import org.eclipse.jgit.lib.Repository;
import org.eclipse.jgit.lib.StoredConfig;
import org.eclipse.jgit.transport.RefSpec;
import org.eclipse.jgit.transport.RemoteConfig;
import org.eclipse.jgit.transport.URIish;

/**
* A wizard dedicated to pushing a commit.
*/
public class PushBranchWizard extends Wizard {

  private final Repository repository;

  private final ObjectId commitToPush;

  /**
   * In case of detached HEAD, reference is null.
   */
  private final Ref ref;

  private AddRemotePage addRemotePage;
  private PushBranchPage pushBranchPage;
  private ConfirmationPage confirmationPage;


  /**
   * @param repository
   *            the repository the ref belongs to
   * @param ref
   */
  public PushBranchWizard(final Repository repository, Ref ref) {
    this(repository, ref.getObjectId(), ref);
  }

  /**
   * @param repository
   *            the repository commit belongs to
   * @param commitToPush
   */
  public PushBranchWizard(final Repository repository, ObjectId commitToPush) {
    this(repository, commitToPush, null);
  }

  private PushBranchWizard(final Repository repository, ObjectId commitToPush, Ref ref) {
    this.repository = repository;
    this.commitToPush = commitToPush;
    this.ref = ref;
    assert (this.repository != null);
    assert (this.commitToPush != null);

    Set<String> remoteNames = repository.getConfig().getSubsections(ConfigConstants.CONFIG_REMOTE_SECTION);
    if (remoteNames.isEmpty())
      addRemotePage = new AddRemotePage(repository);

    pushBranchPage = new PushBranchPage(repository, commitToPush, ref) {
      @Override
      public void setVisible(boolean visible) {
        if (visible && addRemotePage != null) {
          setSelectedRemote(addRemotePage.getRemoteName(),
              addRemotePage.getSelection().getURI());
        }
        super.setVisible(visible);
      }
    };
    // Don't show button if we're configuring a remote in the first step
    pushBranchPage.setShowNewRemoteButton(addRemotePage == null);

    confirmationPage = new ConfirmationPage(repository) {
      @Override
      public void setVisible(boolean visible) {
        setSelection(getRepositorySelection(), getRefSpecs());
        AddRemotePage remotePage = getAddRemotePage();
        if (remotePage != null)
          setCredentials(remotePage.getCredentials());
        super.setVisible(visible);
      }
    };

    setDefaultPageImageDescriptor(UIIcons.WIZBAN_PUSH);
  }

  @Override
  public void addPages() {
    if (addRemotePage != null)
      addPage(addRemotePage);
    addPage(pushBranchPage);
    addPage(confirmationPage);
  }

  @Override
  public String getWindowTitle() {
    if (ref != null)
      return MessageFormat.format(UIText.PushBranchWizard_WindowTitle,
          Repository.shortenRefName(this.ref.getName()));
    else
      return UIText.PushCommitHandler_pushCommitTitle;
  }

  @Override
  public boolean canFinish() {
    return getContainer().getCurrentPage() == confirmationPage;
  }

  @Override
  public boolean performFinish() {
    try {
      AddRemotePage remotePage = getAddRemotePage();
      if (remotePage != null) {
        storeCredentials(remotePage);
        URIish uri = remotePage.getSelection().getURI();
        configureNewRemote(uri);
      }
      if (pushBranchPage.isConfigureUpstreamSelected())
        configureUpstream();
      startPush();
    } catch (IOException e) {
      confirmationPage.setErrorMessage(e.getMessage());
      return false;
    } catch (URISyntaxException e) {
      confirmationPage.setErrorMessage(e.getMessage());
      return false;
    }

    return true;
  }

  private AddRemotePage getAddRemotePage() {
    if (addRemotePage != null)
      return addRemotePage;
    else
      return pushBranchPage.getAddRemotePage();
  }

  private RepositorySelection getRepositorySelection() {
    AddRemotePage remotePage = getAddRemotePage();
    if (remotePage != null)
      return remotePage.getSelection();
    else
      return new RepositorySelection(null,
          pushBranchPage.getRemoteConfig());
  }

  private List<RefSpec> getRefSpecs() {
    String src = this.ref != null ? this.ref.getName() : this.commitToPush.getName();
    String dst = pushBranchPage.getFullRemoteReference();
    RefSpec refSpec = new RefSpec().setSourceDestination(src, dst)
        .setForceUpdate(pushBranchPage.isForceUpdateSelected());
    return Arrays.asList(refSpec);
  }

  private void storeCredentials(AddRemotePage remotePage) {
    if (remotePage.getStoreInSecureStore()) {
      URIish uri = remotePage.getSelection().getURI();
      if (uri != null)
        SecureStoreUtils.storeCredentials(
            remotePage.getCredentials(), uri);
    }
  }

  private void configureNewRemote(URIish uri) throws URISyntaxException,
      IOException {
    StoredConfig config = repository.getConfig();
    String remoteName = getRemoteName();
    RemoteConfig remoteConfig = new RemoteConfig(config, remoteName);
    remoteConfig.addURI(uri);
    RefSpec defaultFetchSpec = new RefSpec().setForceUpdate(true)
        .setSourceDestination(Constants.R_HEADS + "*", //$NON-NLS-1$
            Constants.R_REMOTES + remoteName + "/*"); //$NON-NLS-1$
    remoteConfig.addFetchRefSpec(defaultFetchSpec);
    remoteConfig.update(config);
    config.save();
  }

  private void configureUpstream() throws IOException {
    if (this.ref == null) {
      // Don't configure upstream for detached HEAD
      return;
    }
    String remoteName = getRemoteName();
    String fullRemoteBranchName = pushBranchPage.getFullRemoteReference();
    String localBranchName = Repository.shortenRefName(this.ref.getName());

    StoredConfig config = repository.getConfig();
    config.setString(ConfigConstants.CONFIG_BRANCH_SECTION, localBranchName,
        ConfigConstants.CONFIG_KEY_REMOTE, remoteName);
    config.setString(ConfigConstants.CONFIG_BRANCH_SECTION, localBranchName,
        ConfigConstants.CONFIG_KEY_MERGE, fullRemoteBranchName);
    if (pushBranchPage.isRebaseSelected()) {
      config.setBoolean(ConfigConstants.CONFIG_BRANCH_SECTION,
          localBranchName, ConfigConstants.CONFIG_KEY_REBASE, true);
    } else {
      // Make sure we overwrite any previous configuration
      config.unset(ConfigConstants.CONFIG_BRANCH_SECTION, localBranchName,
          ConfigConstants.CONFIG_KEY_REBASE);
    }

    config.save();
  }

  private void startPush() throws IOException {
    PushOperationResult result = confirmationPage.getConfirmedResult();
    PushOperationSpecification pushSpec = result
        .deriveSpecification(confirmationPage
            .isRequireUnchangedSelected());

    PushOperationUI pushOperationUI = new PushOperationUI(repository,
        pushSpec, false);
    pushOperationUI.setCredentialsProvider(new EGitCredentialsProvider());
    pushOperationUI.setShowConfigureButton(false);
    if (confirmationPage.isShowOnlyIfChangedSelected())
      pushOperationUI.setExpectedResult(result);
    pushOperationUI.start();
  }

  private String getRemoteName() {
    return pushBranchPage.getRemoteConfig().getName();
  }
}
TOP

Related Classes of org.eclipse.egit.ui.internal.push.PushBranchWizard

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.