RecursiveOps.cs

// Copyright (C) 2004 Enterprise Distributed Technologies Ltd
// 
// www.enterprisedt.com
//
// Refer to readme.html in the same directory for instructions.
// 
// Change Log:
// 
// $Log$
// 
using System;
using System.IO;
using System.Threading;
using EnterpriseDT.Util.Debug;
using EnterpriseDT.Net.Ftp;
using EnterpriseDT.Net.Ftp.Pro;

/// <summary>
/// edtFTPnet/PRO Example 7
/// </summary>
/// <author>              
/// Bruce Blackshaw
/// </author>
/// <version>         
/// $Revision: 1.2 $
/// </version>
public class RecursiveOps {
    
private static Logger log = Logger.GetLogger(typeof(RecursiveOps));

    /// <summary>  
    /// Simple test that gets a remote directory, puts it back to another directory,
    /// gets it again, and then deletes the temporary remote directory
    /// </summary>
    public static void Main(string[] args)
    {        
        // we want remote host, user name, password, remote dir to fetch
        if (args.Length != 4) {
            System.Console.Out.WriteLine(
                "Usage: RecursiveOps remote-host username password remote-dir");
            System.Console.Out.WriteLine("See readme.html for instructions.");
            System.Environment.Exit(1);
        }
        
        string host = args[0];
        string user = args[1];
        string password = args[2];
        string remoteDir = args[3];
        
        // set up logger level - change to DEBUG to see all the FTP operations etc
        Logger.CurrentLevel = Level.INFO;
        
        try {
            FTPClient ftp = new FTPClient(host);
            ftp.Login(user, password);
            
            // create a tmp dir name
            int id = new Random().Next();
            string tmpDir1 = remoteDir + "_" + id + "_1";
            
            // test get to tmp dir
            RecursiveOperations recurse = new RecursiveOperations();
            recurse.Get(ftp, tmpDir1, remoteDir, true);
            log.Info("Retrieved remote directory " + remoteDir + " to " + tmpDir1);
                     
            // test putting it back
            recurse.Put(ftp, tmpDir1, tmpDir1, true);
            log.Info("Put local directory " + tmpDir1 + " to " + tmpDir1);
            
            // now get it into another tmp dir
            string tmpDir2 = remoteDir + "_" + id + "_2";
            recurse.Get(ftp, tmpDir2, tmpDir1, true);
            log.Info("Retrieved remote directory " + tmpDir1 + " to " + tmpDir2);
            
            // now delete the new remote
            recurse.Delete(ftp, tmpDir1);
            log.Info("Deleted remote directory " + tmpDir1);
           
            // now compare the 2 local dirs
            CompareAndDeleteDirectories(new DirectoryInfo(tmpDir1), new DirectoryInfo(tmpDir2));
            log.Info("Directories are identical");
            
            // log off
            ftp.Quit();
            
        }
        catch (Exception e) 
        {
            log.Error("Caught exception " + e.GetType().FullName + " " + e.Message, e);
        } 
    }
    
    /// <summary> 
    /// Compare two local directories, checking names and contents
    /// </summary>
    /// <param name="dirname1">first dir</param>
    /// <param name="dirname2">second dir</param>
    private static void CompareAndDeleteDirectories(DirectoryInfo dir1, DirectoryInfo dir2) 
    {
        DirectoryInfo[] dirs1 = dir1.GetDirectories();
        DirectoryInfo[] dirs2 = dir2.GetDirectories();
        if (dirs1.Length != dirs2.Length)
            throw new ApplicationException ("Directory counts do not match");
        
        for (int i = 0; i < dirs1.Length; i++) 
        {
            if (!dirs1[i].Name.Equals(dirs2[i].Name))
                throw new ApplicationException ("Directory names do not match");
            
            CompareAndDeleteDirectories(dirs1[i], dirs2[i]);
        }
        
        FileInfo[] files1 = dir1.GetFiles();
        FileInfo[] files2 = dir2.GetFiles();
        if (files1.Length != files2.Length)
            throw new ApplicationException ("Directory file counts do not match");
        
        for (int i = 0; i < files1.Length; i++) 
        {
            if (!files1[i].Name.Equals(files2[i].Name))
                throw new ApplicationException ("File name do not match");
            
            CompareAndDeleteFiles(files1[i], files2[i]);
        }
        
        log.Debug("Deleting local directory: " + dir1.Name);
        dir1.Delete();
        log.Debug("Deleting local directory: " + dir2.Name);
        dir2.Delete();
    }
    
    /// <summary> 
    /// Test to see if two files are identical, byte for byte
    /// </summary>
    /// <param name="file1">first file</param>
    /// <param name="file2">second file</param>    
    private static void CompareAndDeleteFiles(FileInfo file1, FileInfo file2)
    {            
        BufferedStream is1 = null;
        BufferedStream is2 = null;
        try
        {
            // check lengths first
            if (file1.Length != file2.Length)
                throw new ApplicationException ("File lengths do not match");
            
            // now check each byte
            is1 = new BufferedStream(new FileStream(file1.FullName, FileMode.Open, FileAccess.Read));
            is2 = new BufferedStream(new FileStream(file2.FullName, FileMode.Open, FileAccess.Read));
            int ch1 = 0;
            int ch2 = 0;
            while ((ch1 = is1.ReadByte()) != - 1 && (ch2 = is2.ReadByte()) != - 1)
            {
                if (ch1 != ch2)
                    throw new ApplicationException ("Contents not equal");
            }
        }
        finally
        {
            if (is1 != null)
                is1.Close();
            if (is2 != null)
                is2.Close();
        }
        
        log.Debug("Deleting local file: " + file1.Name);
        file1.Delete();
        log.Debug("Deleting local file: " + file2.Name);
        file2.Delete();
    }

}

Generated on Sat Feb 26 19:17:38 2005 for edtFTPnet/PRO by  doxygen 1.4.1