DirectorySync - Verzeichnisse Synchronisieren

Nero90

Mitglied
Erstmal Hallo an alle! Das ist mein erster Beitrag bei euch. ;)

So nun zu dem Programm an dem Ich seit 'ner Woche arbeite.
Das Programm heist DirectorySync und soll zwei Verzeichnisse synchronisieren. Man wählt ein Quellverzeichnis a und ein Zielverzeichnis b. Dann werden alle Ordner und Dateien von a nach b kopiert. Während des Kopiervorgangs wird jedes File von a mit jedem File im selben unterverzeichnis von b verglichen. Wenn ein File mit dem selben Namen vorhanden ist, wird zum nächsten gegangen. Ansonsten wird es kopiert.

Damit auch Unterordner eingeschlossen werden, verwende ich eine Rekursion. Das funktioniert soweit auch ganz gut. Jedoch sobald die Ordnerstruckturen etwas komplizierter sind, "vergisst" er einige Ordner und Dateien zu kopieren. Ich weis jetzt nicht so recht wo ich nach dem Fehler suchen soll. ???:L

Klasse CopyData:
Java:
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.channels.FileChannel;

import com.sun.jmx.snmp.tasks.Task;

/**
 * @author Jens Uwe Becker
 *
 */
public class CopyData {
	
	private static File[] fileArrayIn,fileArrayOut;
	private static int counter=0;
	public static int c=0;
	static Task task;
	private static boolean progress=false;
	private static boolean recursive=false;
	
	/**
	 * 
	 * @param fileIn file with the source path
	 * @param fileOut file with the target path
	 * @throws IOException
	 * @throws InterruptedException 
	 */
	public static void startCopying(File fileIn, File fileOut) throws IOException, InterruptedException{
		fileArrayIn = fileIn.listFiles();
		fileArrayOut = fileOut.listFiles();
		progress=true;
		
		
		if(fileArrayIn!=null)
		for(int i=counter;i<fileArrayIn.length;i++){
			if(!recursive)c=i;
			boolean fileFound=false;
			File file = null;
			counter=i;
			if(fileArrayIn[i].isFile()) c+=(int) fileArrayIn[i].length();
			//if(Main.debugMode)Main.gui.appendTaInfo("[debugInfo]: actual file space: "+c+"\n");
			Main.gui.progressBar.setValue(c);
			Main.gui.panelSouth.repaint();
			Main.gui.repaint();
			Thread.sleep(5);
			
			/*
			 * recursive function call
			 * 
			 */
			if(fileArrayIn[i].isDirectory()){
				file = new File(fileOut.getAbsolutePath()+"\\"+fileArrayIn[i].getAbsoluteFile().getName());
				recursive=true;
				if(file.mkdir()){
					Main.gui.appendTaInfo("[info]: create directory: "+file.getPath()+"\n");
					if(Main.debugMode)Main.gui.appendTaInfo("[debugInfo]: recursive function call: new function instance opened.\n");
					startCopying(fileArrayIn[i],file);
					counter++;
					startCopying(fileIn,fileOut);
				}
				else if(file.exists()){
					if(Main.debugMode)Main.gui.appendTaInfo("[debugInfo]: recursive function call: new function instance opened.\n");
					startCopying(fileArrayIn[i],file);
					counter++;
					startCopying(fileIn,fileOut);
				}
				else{
					Main.gui.attribute = Main.gui.orange;
					Main.gui.appendTaInfo("[warning]: could not create directory "+file.getPath()+"\n");
					Main.gui.attribute = Main.gui.black;
				}
				recursive=false;
			}
			
			//continues here, if fileArrayIn[i] is no directory
			if(fileArrayOut!=null)
			for(int j=0;j<fileArrayOut.length;j++){
				//Check if fileArrayIn[i] equals fileArrayOut[j]. If not: Copy fileIn to output folder
				if(fileArrayOut[j].canRead())
				if(fileArrayIn[i].getAbsoluteFile().getName().equals(fileArrayOut[j].getAbsoluteFile().getName())){
					j=fileArrayOut.length;
					fileFound=true;
				}
			}
			
			
			//create and copy file, if not found
			if(!fileFound){
				if(fileArrayIn[i].canRead())
				if(fileArrayIn[i].getAbsoluteFile().isFile()){
					file = new File(fileOut.getAbsolutePath()+"\\"+fileArrayIn[i].getAbsoluteFile().getName());
					Main.gui.appendTaInfo("[info]: file \""+fileArrayIn[i].getAbsoluteFile().getName()+"\" not found in target folder\n");
					Main.gui.appendTaInfo("[info]: copy file \""+file.getAbsoluteFile().getName()+"\" \n");
					
					if(fileArrayIn[i].exists()){
						file.createNewFile();
						copyFile(fileArrayIn[i],file);
						
					}
					else{
						Main.gui.attribute=Main.gui.orange;
						Main.gui.appendTaInfo("[warning]: file does not exist!\n");
						Main.gui.attribute=Main.gui.black;
					}
				}
			}
		}
		else Main.gui.appendTaInfo("[info]: No files found in selected directory");
		if(counter<fileArrayIn.length){counter++; startCopying(fileIn,fileOut);}
	}
	
	/**
	 * 
	 * @param dir
	 * @return the directory size
	 */
   public static long getDirSize(File dir) {
	    if (dir.isFile())
	    	return dir.length();
	    
	    File[] subFiles = dir.listFiles();
	    long size = 0;
	    for (File file : subFiles) {
		    if (file.isFile())
		    	size += file.length();
		    else
		    	size += getDirSize(file);
	    }
	    return size;
    }
	
	/**
	 * resets the Class CopyData, so that you can call them again for another folder/directory
	 */
	public static void reset(){
		Main.gui.progressBar.setValue(0);
		fileArrayIn=null;
		fileArrayOut=null;
		counter=0;
	}
	
	/**
	 * 
	 * @param in source file to copy
	 * @param out target file to override
	 * @throws IOException
	 */
    public static void copyFile(File in, File out) throws IOException {
    	FileChannel inChannel = null;
    	FileChannel outChannel = null;
    	
        if(in.getAbsoluteFile().isFile()){
        	inChannel = new FileInputStream(in).getChannel();}
        if(out.getAbsoluteFile().isFile()){
        	outChannel = new FileOutputStream(out).getChannel();}
        
        try {
        	if(inChannel!=null && outChannel!=null)
        		inChannel.transferTo(0, inChannel.size(), outChannel);
        } catch (IOException e) {
        	Main.gui.attribute=Main.gui.red;
        	Main.gui.appendTaInfo("[IOException]: "+e.getMessage());
        	Main.gui.attribute=Main.gui.black;
            e.printStackTrace();
        } finally {
            if (inChannel != null)
                inChannel.close();
            if (outChannel != null)
                outChannel.close();
        }
    }

}

Klasse Gui:
Java:
import java.awt.Color;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.File;
import java.io.IOException;

import javax.swing.JButton;
import javax.swing.JEditorPane;
import javax.swing.JFileChooser;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JProgressBar;
import javax.swing.JScrollPane;
import javax.swing.JTextField;
import javax.swing.text.AttributeSet;
import javax.swing.text.BadLocationException;
import javax.swing.text.DefaultCaret;
import javax.swing.text.Document;
import javax.swing.text.MutableAttributeSet;
import javax.swing.text.SimpleAttributeSet;
import javax.swing.text.StyleConstants;
import javax.swing.text.StyledEditorKit;

import data.CopyData;

/**
 * 
 * @author Jens Uwe Becker
 *
 */
public class Gui extends JFrame{
	
	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	private JFileChooser fileChooser = new JFileChooser();
	public JPanel panelSouth = new JPanel();
	public JEditorPane taInfo = new JEditorPane();
	private JButton buttonSource,buttonTarget,buttonClearTa;
	public JButton buttonStart;
	private File pathSource,pathTarget;
	private JScrollPane scroll = new JScrollPane();
	public AttributeSet attribute;
	public MutableAttributeSet black;
    public MutableAttributeSet red;
    public MutableAttributeSet orange;
    private Document doc;
    public JTextField tf;
    public JProgressBar progressBar;
    public Thread thread;
    public DefaultCaret caret;

	public Gui(){
		super("DirectorySync - v0.031 - Alpha");
		setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		getContentPane().setLayout(new GridLayout(2,1));
		
		setBounds(500,100,600,600);
		setResizable(true);
		
        black = new SimpleAttributeSet();
        StyleConstants.setForeground(black, Color.black);
        red = new SimpleAttributeSet();
        StyleConstants.setForeground(red, Color.red);
        orange = new SimpleAttributeSet();
        StyleConstants.setForeground(orange, Color.orange);
		
		taInfo.setEditable(false);
		taInfo.setBackground(Color.WHITE);
		taInfo.setEditorKit(new StyledEditorKit());
		taInfo.setText("Welcome to DirectorySync!\n");
		scroll = new JScrollPane(taInfo);
		scroll.setAutoscrolls(rootPaneCheckingEnabled);
		scroll.setSize(new Dimension(200,200));
		scroll.setAutoscrolls(true);
		caret = (DefaultCaret)taInfo.getCaret();
		caret.setUpdatePolicy(DefaultCaret.ALWAYS_UPDATE);

        doc = taInfo.getDocument();
		
		fileChooser.setAcceptAllFileFilterUsed(true);
		fileChooser.setFileSelectionMode(JFileChooser.FILES_AND_DIRECTORIES);
		fileChooser.setBounds(0,0,200,200);
		
		buttonSource = new JButton("Source folder");
		buttonSource.setBounds(225,50,150,30);
		buttonTarget = new JButton("Target folder");
		buttonTarget.setBounds(225,100,150,30);
		buttonStart = new JButton("Start");
		buttonStart.setBounds(225,150,150,30);
		buttonClearTa = new JButton("Clear log");
		buttonClearTa.setBounds(225,200,150,30);
		
		progressBar = new JProgressBar();
		progressBar.setBounds(225,10,150,30);
		
		tf = new JTextField();
		tf.setEditable(false);
		tf.setBounds(225,10,150,30);
		
		panelSouth.setLayout(null);		
		
		//init panels
		//panelSouth.add(tf);
		panelSouth.add(progressBar);
		panelSouth.add(buttonSource);
		panelSouth.add(buttonTarget);
		panelSouth.add(buttonStart);
		panelSouth.add(buttonClearTa);
		
		//add panels to layout
		getContentPane().add(scroll);
		getContentPane().add(panelSouth);
		
		setVisible(true);
		

		attribute=red;
		appendTaInfo("[warning]: This program is an alpha version! Long runtimes expected after starting copying!\n");
		attribute=black;
		
		
		/*
		 * ActionListener comes here
		 */
		
		buttonSource.addActionListener(new ActionListener() {
			 
	        public void actionPerformed(ActionEvent e)
	        {
	        	
	        	fileChooser.showOpenDialog(null);
	        	setPathSource(fileChooser.getSelectedFile());
	        	appendTaInfo("[info]: source folder "+getPathSource().getAbsolutePath()+ " selected\n");
	        }
		});
		
		buttonTarget.addActionListener(new ActionListener() {
			 
	        public void actionPerformed(ActionEvent e)
	        {
	        	fileChooser.showOpenDialog(null);
	        	setPathTarget(fileChooser.getSelectedFile());
	        	appendTaInfo("[info]: target folder "+getPathTarget().getAbsolutePath()+ " selected.\n");
	        }
		});
		
		buttonStart.addActionListener(new ActionListener() {
			 
	        public void actionPerformed(ActionEvent e)
	        {
	        	
	        	@SuppressWarnings("unused")
				JProgressBar progress;
	        	thread = new Thread(){
	        		
	        		public void run(){

			        	if(pathSource==null){
			        		attribute=orange;
			        		appendTaInfo("[warning]: please select source path.\n[warning]: copying aborded.\n");
			        		attribute=black;
			        	}
			        	else if(pathTarget==null){
			        		attribute=orange;
			        		appendTaInfo("[warning]: please select target path.\n[warning]: copying aborded.\n");
			        		attribute=black;
			        	}
			        	else{
			        		try {
			        			buttonStart.setEnabled(false);
			        			buttonSource.setEnabled(false);
			        			buttonTarget.setEnabled(false);
			        			int dirSize=(int) CopyData.getDirSize(pathSource);
			        			
			        			CopyData.c=dirSize;
					        	appendTaInfo("[info]: copying started.\n");
					        	appendTaInfo("[info]: dir size:"+dirSize+"\n");
					        	progressBar.setMaximum(dirSize);
			        			
								CopyData.startCopying(pathSource, pathTarget);
								appendTaInfo("[info]: file copying finished!\n");
								JOptionPane.showMessageDialog(null, "File copying successful finished!");
								tf.setText("          Progress: 100%");
							} catch (IOException e1) {
								// TODO Auto-generated catch block
								attribute=red;
								appendTaInfo("[IOException]: "+e1.getMessage());
								JOptionPane.showMessageDialog(null, e1.getMessage());
								attribute=black;
								e1.printStackTrace();
							} catch (InterruptedException e) {
								// TODO Auto-generated catch block
								e.printStackTrace();
							}
			        	}
			        	CopyData.reset();
			        	buttonStart.setEnabled(true);
	        			buttonSource.setEnabled(true);
	        			buttonTarget.setEnabled(true);
	        		}
	        	};
	        	thread.start();
	        }
		});
		
		buttonClearTa.addActionListener(new ActionListener() {
			 
	        public void actionPerformed(ActionEvent e)
	        {
	        	taInfo.setText("");
	        	doc=taInfo.getDocument();
	        	appendTaInfo("[info]: log cleared.");
	        }
		});
	}

	/**
	 * @return the pathSource
	 */
	public File getPathSource() {
		return pathSource;
	}

	/**
	 * @param pathSource the pathSource to set
	 */
	public void setPathSource(File pathSource) {
		this.pathSource = pathSource;
	}

	/**
	 * @return the pathTarget
	 */
	public File getPathTarget() {
		return pathTarget;
	}

	/**
	 * @param pathTarget the pathTarget to set
	 */
	public void setPathTarget(File pathTarget) {
		this.pathTarget = pathTarget;
	}

	/**
	 * @return the taInfo
	 */
	public JEditorPane getTaInfo() {
		return taInfo;
	}

	/**
	 * @param taInfo the taInfo to set
	 */
	public void setTaInfo(JEditorPane taInfo) {
		this.taInfo = taInfo;
	}
	
	/**
	 * 
	 * @param arg0 the text to append
	 */
	public void appendTaInfo(String text){
		try {
            doc.insertString(doc.getLength(), text, attribute);
        } catch (BadLocationException ex) {
            ex.printStackTrace();
        }
	}

}


Ich hoffe, dass ihr mir etwas helfen könnt. Falls ihr Fragen zum Quellcode habt: fragt bitte.^^
 

jemandzehage

Aktives Mitglied
Moin,

Hab jetzt zwar nur kurz drüber geschaut, aber ich vermute das liegt daran, dass du in der rekursion auf eine globale Variable zugreifst um die Dateilisten abzuspeichern. Dadurch wird bei jedem rekursiven Aufruf die Liste überschrieben und die Funktion in der die Rekursion aufgerufen wurde arbeitet danach auf falschen Daten weiter. Ich hoffe das wars schon.

Grüße
 

Nero90

Mitglied
Das war es leider nicht. Mir ist bei den debugAusgaben im Textfeld jedoch aufgefallen, dass er weit mehr Verzeichnisse überprüft, als er erstellt. Insgesammt gibt es 130 unterverzeichnisse. Davon hat er nach Abschluss 24 im Zielordner erstellt (teils bis zur "tiefsten" ebene). Das Verwirrende ist, dass er im Quellordner deutlich über 40 überprüft hat. Warum erstellt er die überprüften nicht im Zielordner?
Ein Fehler beim zusammenbauen des Zielpfads?

Ach und noch was: Gibt es eine Möglichkeit die Laufzeit zu verkürzen bzw. das ganze etwas zu beschleunigen? Man merkt deutlich, dass es umso länger dauert je mehr Ordner es gibt. :reflect:


Edit:
Hier mal was er mir im Textfeld postet nach einem zweiten durchlauf:
[info]: source folder D:\TestSourceFolder selected
[info]: target folder D:\TestTargetFolder selected.
[info]: copying started.
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner - Kopie
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (7)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (8)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (9)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (10)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (10)\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (2)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (3)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (4)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (5)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (6)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (7)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (8)
[debugInfo]: checking subDir "D:\TestTargetFolder\Neuer Ordner - Kopie (9)
[info]: file copying finished!

Wenn er eine Datei oder einen Ordner erstellt hätte, würde das ebenfalls da stehen. Er hat immerhin alle Ordner im root verzeichnis abgearbeitet...
 
Zuletzt bearbeitet:

Tobse

Top Contributor
Also ich hab mir deinen Code auch nicht genau angeschaut. Ich habe aber ein änliches Programm in C# schonmal geschrieben, welches auch rekursiv läuft. Vllt findest du da den Unterschied.

Seien A und B die Verzeichnisse, die es zu synchronisieren gilt. Dann geht mein Code durch rekursiv Verzeichnis durch A(Zeile 136-146) und synchronisiert jede Datei (Zeile 89+90, Zeile 94+123-133). Dann wird das Ganze mit B gemacht (Zeile 64-69).

Kleine Hilfe fürs übertragen in Java:
Java's [JAPI]java.io.File#list[/JAPI] entspricht einer kombination aus C#'s
Code:
Directory.getFiles(string)
und
Code:
Directory.getDirectories(string)

Code:
using System;
using System.IO;

namespace syncdir
{
	class MainClass
	{
		private static bool syncSubs=true;
		private static int sourcePathOffset=0;
		private static bool secondDirection = false;
		private static bool verbose;
		public static void Main (string[] args)
		{
			bool singleDirection=false;
			string sourceDirStr=null;
			string destDirStr=null;
			for (int i=0;i<args.Length;i++)
			{
				if (args[i].Equals("--help"))
				{
					printHelp();
					return;
				}
				else if (args[i].Equals("-sd"))
				{
					singleDirection=true;
				}
				else if (args[i].Equals("-nosub"))
				{
					syncSubs=false;
				}
				else if (args[i].Equals("-v") || args[i].Equals("-verbose"))
				{
				     verbose = true;
				} else {
					if (sourceDirStr==null) {
						sourceDirStr=args[i];
					} else if (destDirStr==null) {
						destDirStr=args[i];
					}
				}
			}
			if (sourceDirStr == null) {
				Console.WriteLine("No source directory specified. Use --help to see all options.");
				return;
			}
			if (destDirStr == null) {
				Console.WriteLine("No target directory specified. Use --help to see all options.");
				return;
			}
			if (!Directory.Exists(sourceDirStr)) {
				Console.WriteLine(sourceDirStr+" does not exist or is no directory.");
				return;
			}
			if (!Directory.Exists(destDirStr)) {
				Console.WriteLine(destDirStr+" does not exist or is no directory.");
				return;
			}
			if (!sourceDirStr.EndsWith(Path.DirectorySeparatorChar.ToString()))
				sourceDirStr=sourceDirStr+Path.DirectorySeparatorChar;
			if (!destDirStr.EndsWith(Path.DirectorySeparatorChar.ToString()))
				destDirStr=destDirStr+Path.DirectorySeparatorChar;
			
			syncDirs(sourceDirStr, destDirStr);
			if (!singleDirection) 
			{
				secondDirection = true;
				syncDirs(destDirStr, sourceDirStr);
			}
		}
		private static void syncDirs(string source, string dest) {
			if (!Directory.Exists (dest)) {
				try {
					Directory.CreateDirectory(dest);
				} catch (PathTooLongException ex) {
					Console.WriteLine("Failed to create "+dest+": Path too long");
					return;
				} catch (IOException ex) {
					Console.WriteLine("Failed to create "+dest+": it is a file or the network is not known.");
					return;
				} catch (UnauthorizedAccessException ex) {
					Console.WriteLine("Failed to create "+dest+": Permission denied.");
					return;
				} catch (Exception ex) {
					Console.WriteLine("Failed to create "+dest+":");
					Console.WriteLine(ex.GetType().ToString()+": "+ex.Message);
				}
			}
			string[] files=Directory.GetFiles(source);
			for (int i=0;i<files.Length;i++) {
				string filePre=files[i].Substring(source.Length);
				string sourceFile=source+filePre;
				string destFile=dest+filePre;
				if (File.Exists(destFile)) {
					bool failed=false;
					try {
						if (File.GetLastWriteTime(sourceFile).CompareTo(
							File.GetLastWriteTime(destFile)
						)>0) { // Source is newer
							File.Delete(destFile);
							File.Copy(sourceFile, destFile, true);
							if (verbose)
							{
								Console.WriteLine(
									(secondDirection? "Target > Source" : "Source > Target") + " " + filePre
								);
							}
						}
					} catch (UnauthorizedAccessException ex) {
						Console.WriteLine("Failed to repalce "+destFile+": Permission denied.");
						failed=true;
					} catch (Exception ex) {
						Console.WriteLine("Failed to replace "+destFile+":");
						Console.WriteLine(ex.GetType().ToString()+": "+ex.Message);
						failed=true;
					} finally {
						if (failed) {
							File.Delete(destFile);
							File.Copy(destFile+".backup", destFile);
						}
						File.Delete(destFile+".backup");
					}
				} else {
					try {
						File.Copy(sourceFile, destFile);
					} catch (UnauthorizedAccessException ex) {
						Console.WriteLine ("Failed to write "+dest+": Permission denied.");
						continue;
					} catch (Exception ex) {
						Console.WriteLine("Failed to write "+destFile+":");
						Console.WriteLine(ex.GetType().ToString()+": "+ex.Message);
					}
				}
			}
			if (!syncSubs) return;
			string[] dirs=Directory.GetDirectories(source);
			for (int i=0;i<dirs.Length;i++) {
				string dirPre=dirs[i].Substring(source.Length);
				string sourceDir=source+dirPre;
				string destDir=dest+dirPre;
				if (!sourceDir.EndsWith(Path.DirectorySeparatorChar.ToString()))
					sourceDir=sourceDir+Path.DirectorySeparatorChar;
				if (!destDir.EndsWith(Path.DirectorySeparatorChar.ToString()))
				    destDir=destDir+Path.DirectorySeparatorChar;
				syncDirs(sourceDir, destDir);
			}
		}
		private static void printHelp() {
			Console.WriteLine("Usage: syncdir [options] source target");
			Console.WriteLine("Options:");
			Console.WriteLine("--help         Show this message");
			Console.WriteLine("-sd            Target will be syncronized with source but");
			Console.WriteLine("               not vice versa");
			Console.WriteLine("-nosub         The subdirectories will not be synchroized");
			Console.WriteLine("-v / -verbose  Be verbose: Print all files, that are replaced");
		}
	}
}
[EDIT]
[OT]Man vergebe mir die Todsünde, C#-Code in einem Java-Forum zu posten...[/OT][/EDIT]
 
Zuletzt bearbeitet:
Ähnliche Java Themen
  Titel Forum Antworten Datum
A Java Verzeichnisse in Combobox Ausgeben JAVA Allgemeine Java-Themen 3
R Leere Verzeichnisse löschen Allgemeine Java-Themen 11
KrokoDiehl Verzeichnisse via FileVisitor löschen Allgemeine Java-Themen 3
G Mit Batch-Datei verzeichnisse löschen Allgemeine Java-Themen 9
R ANT Jar Task soll leere Verzeichnisse ignorieren..? Allgemeine Java-Themen 3
G Dateien und Verzeichnisse in einem Verzeichnis zählen Allgemeine Java-Themen 9
F mehrere Verzeichnisse als Parameter Allgemeine Java-Themen 15
S In .jar File Verzeichnisse anlegen Allgemeine Java-Themen 2
F Verzeichnisse auslesen / auflisten in einer html Allgemeine Java-Themen 2
M Rekursiv Verzeichnisse ansehen und auf Muster matchen Allgemeine Java-Themen 6
U wie groß sind Verzeichnisse Allgemeine Java-Themen 11
B Abstrakte Datentypen synchronisieren Allgemeine Java-Themen 11
N Best Practice Kontakte synchronisieren Allgemeine Java-Themen 0
M Buffer-Vector einzeln und zusammen synchronisieren Allgemeine Java-Themen 4
S Synchronisieren von Dateien Allgemeine Java-Themen 3
P Buffer - Consumer Producer - Threads synchronisieren Allgemeine Java-Themen 15
Kr0e Synchronisieren: boolean,byte,char ? Allgemeine Java-Themen 2
S Objekt synchronisieren, sodass es nicht von mehreren Threads benutzt wird..? Allgemeine Java-Themen 2
G JTrees synchronisieren Allgemeine Java-Themen 7
M Javaprozess mit Batch-Script synchronisieren Allgemeine Java-Themen 2
N 2 Arrays koppeln (synchronisieren) Allgemeine Java-Themen 25
H Zugriff auf statische Variable synchronisieren Allgemeine Java-Themen 4
L Liste (SWT widget) mit HashSet synchronisieren Allgemeine Java-Themen 5
B Thread synchronisieren Allgemeine Java-Themen 2

Ähnliche Java Themen

Neue Themen


Oben