All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.intellij.cvsSupport2.history.CvsHistoryProvider Maven / Gradle / Ivy

Go to download

A packaging of the IntelliJ Community Edition cvs-plugin library. This is release number 1 of trunk branch 142.

The newest version!
/*
 * Copyright 2000-2014 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.cvsSupport2.history;

import com.intellij.CvsBundle;
import com.intellij.cvsSupport2.CvsFilePath;
import com.intellij.cvsSupport2.CvsUtil;
import com.intellij.cvsSupport2.application.CvsEntriesManager;
import com.intellij.cvsSupport2.changeBrowser.CvsChangeList;
import com.intellij.cvsSupport2.changeBrowser.CvsRepositoryLocation;
import com.intellij.cvsSupport2.connections.CvsConnectionSettings;
import com.intellij.cvsSupport2.connections.CvsEnvironment;
import com.intellij.cvsSupport2.cvsExecution.CvsOperationExecutor;
import com.intellij.cvsSupport2.cvsExecution.DefaultCvsOperationExecutorCallback;
import com.intellij.cvsSupport2.cvshandlers.CommandCvsHandler;
import com.intellij.cvsSupport2.cvsoperations.cvsLog.LocalPathIndifferentLogOperation;
import com.intellij.cvsSupport2.cvsoperations.cvsTagOrBranch.ui.TagsPanel;
import com.intellij.cvsSupport2.util.CvsVfsUtil;
import com.intellij.openapi.actionSystem.AnAction;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.vcs.FilePath;
import com.intellij.openapi.vcs.VcsException;
import com.intellij.openapi.vcs.annotate.ShowAllAffectedGenericAction;
import com.intellij.openapi.vcs.history.*;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.util.TreeItem;
import com.intellij.util.ui.AbstractTableCellEditor;
import com.intellij.util.ui.ColumnInfo;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.netbeans.lib.cvsclient.admin.Entry;
import org.netbeans.lib.cvsclient.command.log.LogInformation;
import org.netbeans.lib.cvsclient.command.log.Revision;

import javax.swing.*;
import javax.swing.table.TableCellEditor;
import javax.swing.table.TableCellRenderer;
import java.awt.*;
import java.io.File;
import java.util.*;
import java.util.List;

public class CvsHistoryProvider implements VcsHistoryProvider {
  public static final ColumnInfo STATE = new ColumnInfo(
    CvsBundle.message("file.history.state.column.name")) {
    public String valueOf(VcsFileRevision vcsFileRevision) {
      if (!(vcsFileRevision instanceof CvsFileRevision)) return "";
      return ((CvsFileRevision)vcsFileRevision).getState();
    }

    public Comparator getComparator() {
      return new Comparator() {
        public int compare(VcsFileRevision r1, VcsFileRevision r2) {
          if (!(r1 instanceof CvsFileRevision)) return 1;
          if (!(r2 instanceof CvsFileRevision)) return -1;
          return ((CvsFileRevision)r1).getState().compareTo(((CvsFileRevision)r2).getState());
        }
      };
    }
  };

  abstract class TagOrBranchColumn extends ColumnInfo {
    public TagOrBranchColumn(final String name) {
      super(name);
    }

    public TableCellRenderer getRenderer(Object object) {
      final TableCellRenderer rendererFromSuper = super.getRenderer(object);
      if (!(object instanceof CvsFileRevision)) return rendererFromSuper;
      final Collection tags = getValues((CvsFileRevision)object);
      if (tags.size() < 2) return rendererFromSuper;
      return new TagsPanel(getName());
    }

    public boolean isCellEditable(Object object) {
      if (!(object instanceof CvsFileRevision)) return false;
      return getValues(((CvsFileRevision)object)).size() > 1;
    }

    public TableCellEditor getEditor(final Object object) {
      if (!(object instanceof CvsFileRevision)) return null;
      return new AbstractTableCellEditor() {
        public Object getCellEditorValue() {
          return "";
        }

        public Component getTableCellEditorComponent(JTable table,
                                                     Object value,
                                                     boolean isSelected,
                                                     int row,
                                                     int column) {
          final TagsPanel result = new TagsPanel(getName());
          result.setTags(getValues((CvsFileRevision)object));
          result.setSelected(true, table);
          return result;
        }
      };
    }

    protected abstract Collection getValues(CvsFileRevision revision);

    public Object valueOf(Object object) {
      if (!(object instanceof CvsFileRevision)) return "";
      final Collection values = getValues(((CvsFileRevision)object));
      if (values.isEmpty()) return "";
      if (values.size() == 1) return values.iterator().next().toString();
      return values;
    }


  }

  private final ColumnInfo TAG = new TagOrBranchColumn(CvsBundle.message("file.history.tag.column.name")) {
    protected Collection getValues(CvsFileRevision revision) {
      return revision.getTags();
    }
  };

  public final ColumnInfo BRANCHES = new TagOrBranchColumn(CvsBundle.message("file.history.branches.column.name")) {
    protected Collection getValues(CvsFileRevision revision) {
      return revision.getBranches();
    }
  };


  private final Project myProject;

  public CvsHistoryProvider(Project project) {
    myProject = project;
  }

  public boolean isDateOmittable() {
    return false;
  }

  public VcsDependentHistoryComponents getUICustomization(final VcsHistorySession session, JComponent forShortcutRegistration) {
    return VcsDependentHistoryComponents.createOnlyColumns(new ColumnInfo[]{
      STATE, TAG, BRANCHES
    });
  }

  public String getHelpId() {
    return null;
  }

  @Nullable
  public VcsHistorySession createSessionFor(final FilePath filePath) {
    final List fileRevisionList = createRevisions(filePath);
    if (fileRevisionList == null) return null;
    return new MyHistorySession(fileRevisionList, filePath);
  }

  private static class MyHistorySession extends VcsAbstractHistorySession {
    private final FilePath myFilePath;

    private MyHistorySession(List revisions, FilePath filePath) {
      super(revisions);
      myFilePath = filePath;
    }

    @Nullable
    public VcsRevisionNumber calcCurrentRevisionNumber() {
      return myFilePath == null ? null : getCurrentRevision(myFilePath);
    }

    @Override
    public synchronized boolean shouldBeRefreshed() {
      //noinspection SimplifiableIfStatement
      if (!CvsEntriesManager.getInstance().isActive()) {
        return false;
      }
      return super.shouldBeRefreshed();
    }

    public boolean isContentAvailable(final VcsFileRevision revision) {
      if (revision instanceof CvsFileRevision) {
        final CvsFileRevision cvsFileRevision = (CvsFileRevision)revision;
        return !cvsFileRevision.getState().equals(CvsChangeList.DEAD_STATE);
      }
      return super.isContentAvailable(revision);
    }

    public HistoryAsTreeProvider getHistoryAsTreeProvider() {
      return MyHistoryAsTreeProvider.getInstance();
    }

    @Override
    public VcsHistorySession copy() {
      return new MyHistorySession(getRevisionList(), myFilePath);
    }
  }

  public void reportAppendableHistory(FilePath path, VcsAppendableHistorySessionPartner partner) throws VcsException {
    final VcsHistorySession session;
    if (path instanceof CvsFilePath) {
      final CvsRepositoryLocation location = ((CvsFilePath)path).getRepositoryLocation();
      final List fileRevisionList = createRevisions(location.getEnvironment(), path.getIOFile());
      if (fileRevisionList == null) return;
      session = new MyHistorySession(fileRevisionList, path);
    }
    else {
      session = createSessionFor(path);
    }
    partner.reportCreatedEmptySession((VcsAbstractHistorySession)session);
  }

  private static VcsRevisionNumber getCurrentRevision(FilePath filePath) {
    final Entry entryFor = CvsEntriesManager.getInstance().getEntryFor(filePath.getVirtualFileParent(), filePath.getName());
    if (entryFor == null) {
      return new CvsRevisionNumber("0");
    }
    else {
      return new CvsRevisionNumber(entryFor.getRevision());
    }
  }

  @Nullable
  public List createRevisions(final FilePath filePath) {
    final File file = filePath.getIOFile();
    final VirtualFile root = CvsVfsUtil.refreshAndFindFileByIoFile(file.getParentFile());
    // check if we have a history pane open for a file in a package which has just been deleted
    if (root == null) return null;
    final CvsConnectionSettings env = CvsEntriesManager.getInstance().getCvsConnectionSettingsFor(filePath.getVirtualFileParent());
    final File lightweightFileForFile = CvsUtil.getCvsLightweightFileForFile(file);
    return createRevisions(env, lightweightFileForFile);
  }

  private List createRevisions(final CvsEnvironment connectionSettings, final File lightweightFileForFile) {
    final LocalPathIndifferentLogOperation logOperation = new LocalPathIndifferentLogOperation(connectionSettings);
    logOperation.addFile(lightweightFileForFile);
    final CvsOperationExecutor executor = new CvsOperationExecutor(myProject);
    final ArrayList result = new ArrayList();
    executor.performActionSync(new CommandCvsHandler(CvsBundle.message("operation.name.load.file.content"), logOperation),
                               new DefaultCvsOperationExecutorCallback() {
                                 @Override
                                 public void executionFinishedSuccessfully() {
                                   final LogInformation firstLogInformation = logOperation.getFirstLogInformation();
                                   if (firstLogInformation != null) {
                                     final List revisionList = firstLogInformation.getRevisionList();
                                     for (Revision revision : revisionList) {
                                       result.add(new CvsFileRevisionImpl(revision, lightweightFileForFile,
                                                                          firstLogInformation, connectionSettings, myProject));
                                     }
                                   }
                                 }
                               });
    Collections.sort(result, Collections.reverseOrder(VcsFileRevisionComparator.INSTANCE));
    return result;
  }

  public AnAction[] getAdditionalActions(final Runnable refresher) {
    return new AnAction[]{ ShowAllAffectedGenericAction.getInstance() };
  }

  public boolean supportsHistoryForDirectories() {
    return false;
  }

  @Override
  public DiffFromHistoryHandler getHistoryDiffHandler() {
    return null;
  }

  @Override
  public boolean canShowHistoryFor(@NotNull VirtualFile file) {
    return true;
  }

  private static class MyHistoryAsTreeProvider implements HistoryAsTreeProvider {
    private static final MyHistoryAsTreeProvider ourInstance = new MyHistoryAsTreeProvider();

    public static MyHistoryAsTreeProvider getInstance() {
      return ourInstance;
    }

    public List> createTreeOn(List allRevisions) {
      Collections.sort(allRevisions, VcsFileRevisionComparator.INSTANCE);

      final List> result = new ArrayList>();

      TreeItem prevRevision = null;
      for (final VcsFileRevision sortedRevision : allRevisions) {
        final CvsFileRevisionImpl cvsFileRevision = (CvsFileRevisionImpl)sortedRevision;
        final TreeItem treeItem = new TreeItem(cvsFileRevision);
        final TreeItem commonParent = getCommonParent(prevRevision, treeItem);
        if (commonParent != null) {
          commonParent.addChild(treeItem);
        }
        else {
          result.add(treeItem);
        }
        prevRevision = treeItem;
      }

      return result;
    }

    @Nullable
    private static TreeItem getCommonParent(TreeItem prevRevision, TreeItem cvsFileRevision) {
      if (prevRevision == null) return null;
      while (!isParent(prevRevision, cvsFileRevision)) {
        prevRevision = prevRevision.getParent();
      }
      return prevRevision;
    }

    private static boolean isParent(TreeItem prevRevision, TreeItem cvsFileRevision) {
      if (prevRevision == null) return true;
      final CvsFileRevisionImpl prevData = (CvsFileRevisionImpl)prevRevision.getData();
      final CvsFileRevisionImpl data = (CvsFileRevisionImpl)cvsFileRevision.getData();
      return data.getRevisionNumber().asString().startsWith(prevData.getRevisionNumber().asString());
    }
  }

  private static class VcsFileRevisionComparator implements Comparator {

    public static final VcsFileRevisionComparator INSTANCE = new VcsFileRevisionComparator();

    private VcsFileRevisionComparator() {}

    public int compare(VcsFileRevision rev1, VcsFileRevision rev2) {
      return VcsHistoryUtil.compare(rev1, rev2);
    }
  }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy