/// <summary> /// Start FTP Proxy /// </summary> private void StartFtpService() { try { ftpListener = new FtpListener(settings.FtpProxyPort.Value); ftpListener.Start(); } catch (Exception ex) { Log.Write(MethodBase.GetCurrentMethod(), ex); } }
private static void ProcessClientRequest() { Debug.Print("Welcome to the FTP Service."); FtpListener.AuthenticationEvent += (object sender, UserAuthenticatorArgs e) => { if (e.User == "anonymous") { Debug.Print("hi anonymous"); e.Result = UserAuthenticationResult.Approved; } }; // a custom listener will be looking after the "special" directory in the ROOT volumes only FtpListener listener = new FtpListener(); listener.Prefixes.Add(virtualROOT + "special/"); listener.Start(); // all other directories will be handled by the standard listener, on both volumes FtpListener listener_root = new FtpFilesystemListener(virtualROOT, @"\ROOT\"); listener_root.Start(); FtpListener listener_winfs = new FtpFilesystemListener(virtualWINFS, @"\WINFS\"); listener_winfs.Start(); for (; ;) { FtpListenerContext context = listener.GetContext(); Stream stream = context.Response.OutputStream; switch (context.Request.Method) { case WebRequestMethodsEx.Ftp.ChangeDirectory: string path = context.Request.QueryString.Substring(virtualROOT.Length); int markerIdx = path.IndexOf('/'); if (markerIdx != -1) { path = path.Substring(0, markerIdx); string dir = @"\ROOT\" + path; if (Directory.Exists(dir) && monitoredDirectory == dir) { Debug.Print("Changed to the monitored directory"); context.Response.StatusCode = FtpStatusCode.FileActionOK; } else { context.Response.StatusCode = FtpStatusCode.ActionNotTakenFileUnavailable; } } else { Directory.SetCurrentDirectory(@"\ROOT"); context.Response.StatusCode = FtpStatusCode.FileActionOK; } stream.Close(); break; case WebRequestMethods.Ftp.ListDirectory: case WebRequestMethods.Ftp.ListDirectoryDetails: { DirectoryInfo cd = new DirectoryInfo(monitoredDirectory); foreach (FileInfo fi in cd.GetFiles()) { (stream as FtpResponseStream).Write(fi); } foreach (DirectoryInfo di in cd.GetDirectories()) { (stream as FtpResponseStream).Write(di); } context.Response.StatusCode = FtpStatusCode.ClosingData; stream.Close(); } break; case WebRequestMethods.Ftp.DownloadFile: DirectoryInfo info = new DirectoryInfo(monitoredDirectory); string prefix = virtualROOT + info.Name + "/"; string download = context.Request.QueryString.Substring(prefix.Length); string file = monitoredDirectory + @"\" + download; if (!File.Exists(file)) { throw new Exception("File does not exists!"); } using (FileStream fs = new FileStream(file, FileMode.Open)) { (stream as FtpResponseStream).Write(fs); context.Response.StatusCode = FtpStatusCode.ClosingData; stream.Close(); } break; default: context.Response.StatusCode = FtpStatusCode.CommandNotImplemented; stream.Close(); break; } } }