/* JMeld is a visual diff and merge tool. Copyright (C) 2007 Kees Kuip This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ package org.jmeld.util.file; import org.jmeld.ui.*; import org.jmeld.util.*; import org.jmeld.util.node.*; import org.jmeld.vc.*; import org.jmeld.vc.util.VcCmd; import java.io.*; import java.util.*; public class VersionControlDiff extends FolderDiff { private File file; private JMDiffNode rootNode; private Map<String, JMDiffNode> nodes; private VersionControlIF versionControl; public VersionControlDiff(File file, Mode mode) { super(mode); setFile(file); setVersionControl(VersionControlUtil.getFirstVersionControl(getFile())); try { setLeftFolderShortName(file.getName()); setRightFolderShortName(""); setLeftFolderName(file.getCanonicalPath()); setRightFolderName(""); } catch (Exception ex) { ex.printStackTrace(); } } public JMDiffNode getRootNode() { return rootNode; } public File getFile() { return file; } public void setFile(File file) { this.file = file; } public VersionControlIF getVersionControl() { return versionControl; } public void setVersionControl(VersionControlIF versionControl) { this.versionControl = versionControl; } public Collection<JMDiffNode> getNodes() { return nodes.values(); } public void diff() { StopWatch stopWatch = new StopWatch(); stopWatch.start(); StatusBar.getInstance().start(); StatusBar.getInstance().setState("Start scanning directories..."); rootNode = new JMDiffNode("<root>", false); nodes = new HashMap<String, JMDiffNode>(); StatusResult statusResult = getVersionControl().executeStatus(getFile()); for (StatusResult.Entry entry : statusResult.getEntryList()) { File file = new File(statusResult.getPath(), entry.getName()); JMDiffNode node = buildNode(entry.getName(), file.isFile()); FileNode fileNode = new FileNode(entry.getName(), file); node.setBufferNodeLeft(new VersionControlBaseNode(getVersionControl(), entry, fileNode, file)); node.setBufferNodeRight(fileNode); switch (entry.getStatus()) { case unmodified: node.setCompareState(JMDiffNode.Compare.Equal); break; case modified: case index_modified: case conflicted: case missing: case dontknow: node.setCompareState(JMDiffNode.Compare.NotEqual); break; case unversioned: case added: case index_added: node.setCompareState(JMDiffNode.Compare.LeftMissing); break; case removed: case index_removed: node.setCompareState(JMDiffNode.Compare.RightMissing); break; case clean: case ignored: node.setCompareState(JMDiffNode.Compare.Equal); break; } } StatusBar.getInstance().setState( "Ready comparing directories (took " + (stopWatch.getElapsedTime() / 1000) + " seconds)"); StatusBar.getInstance().stop(); } private JMDiffNode buildNode(String name, boolean leaf) { JMDiffNode node = nodes.get(name); if (node == null) { node = addNode(name, leaf); } return node; } private JMDiffNode addNode(String name, boolean leaf) { JMDiffNode node = new JMDiffNode(name, leaf); nodes.put(name, node); buildParentNode(node); return node; } private void buildParentNode(JMDiffNode node) { String parentName = node.getParentName(); JMDiffNode parentnode; if (StringUtil.isEmpty(parentName)) { parentnode = rootNode; } else { parentnode = nodes.get(parentName); if (parentnode == null) { parentnode = addNode(parentName, false); FileNode fn = new FileNode(parentName, new File(file, parentName)); parentnode.setBufferNodeRight(fn); parentnode.setBufferNodeLeft(fn); } } parentnode.addChild(node); } public void print() { rootNode.print(""); } public static void main(String[] args) { VersionControlDiff diff; StopWatch stopWatch; File file = VcCmd.parseFile(args); if (file == null) { return; } diff = new VersionControlDiff(file, VersionControlDiff.Mode.TWO_WAY); stopWatch = new StopWatch(); stopWatch.start(); diff.diff(); System.err.println("diff took " + stopWatch.getElapsedTime() + " msec."); diff.print(); } }