Retrieving creation date of file (FTP)
I'm using the System.Net.FtpWebRequest
class and my code is as follows:
FtpWebRequest request = (FtpWebRequest)WebRequest.Create("ftp://example.com/folder");
request.Method = WebRequestMethods.Ftp.ListDirectory;
request.Credentials = new NetworkCredential("username", "password");
FtpWebResponse response = (FtpWebResponse)request.GetResponse();
Stream responseStream = response.GetResponseStream();
StreamReader reader = new StreamReader(responseStream);
string names = reader.ReadToEnd();
reader.Close();
response.Close();
This is based off of the examples provided on MSDN but I couldn't find anything more detailed.
I'm storing all the filenames in the folder in names
but how can I now iterate through each of those and retrieve their dates? I want to retrieve the dates so I can find the newest files. Thanks.
Solution 1:
This seems to work just fine http://msdn.microsoft.com/en-us/library/system.net.ftpwebresponse.lastmodified(v=VS.90).aspx
FtpWebRequest request = (FtpWebRequest)WebRequest.Create (serverUri);
request.Method = WebRequestMethods.Ftp.GetDateTimestamp;
FtpWebResponse response = (FtpWebResponse)request.GetResponse ();
Console.WriteLine ("{0} {1}",serverUri,response.LastModified);
Solution 2:
Unfortunately, there's no really reliable and efficient way to retrieve timestamps using features offered by .NET framework, as it does not support the FTP MLSD
command. The MLSD
command provides a listing of remote directory in a standardized machine-readable format. The command and the format is standardized by RFC 3659.
Alternatives you can use, that are supported by .NET framework:
-
ListDirectoryDetails
method (the FTPLIST
command) to retrieve details of all files in a directory and then you deal with FTP server specific format of the details (*nix format similar to thels
*nix command is the most common, a drawback is that the format may change over time, as for newer files "May 8 17:48" format is used and for older files "Oct 18 2009" format is used).DOS/Windows format: C# class to parse WebRequestMethods.Ftp.ListDirectoryDetails FTP response
*nix format: Parsing FtpWebRequest ListDirectoryDetails line -
GetDateTimestamp
method (the FTPMDTM
command) to individually retrieve timestamps for each file. An advantage is that the response is standardized by RFC 3659 toYYYYMMDDHHMMSS[.sss]
. A disadvantage is that you have to send a separate request for each file, what can be quite inefficient.const string uri = "ftp://example.com/remote/path/file.txt"; FtpWebRequest request = (FtpWebRequest)WebRequest.Create(uri); request.Method = WebRequestMethods.Ftp.GetDateTimestamp; FtpWebResponse response = (FtpWebResponse)request.GetResponse(); Console.WriteLine("{0} {1}", uri, response.LastModified);
Alternatively you can use a 3rd party FTP client implementation that supports the modern MLSD
command.
For example WinSCP .NET assembly supports that.
There's even an example for your specific task: Downloading the most recent file.
The example is for PowerShell and the SFTP, but translates to C# and the FTP easily:
// Setup session options
SessionOptions sessionOptions = new SessionOptions
{
Protocol = Protocol.Ftp,
HostName = "example.com",
UserName = "username",
Password = "password",
};
using (Session session = new Session())
{
// Connect
session.Open(sessionOptions);
// Get list of files in the directory
string remotePath = "/remote/path/";
RemoteDirectoryInfo directoryInfo = session.ListDirectory(remotePath);
// Select the most recent file
RemoteFileInfo latest =
directoryInfo.Files
.OrderByDescending(file => file.LastWriteTime)
.First();
// Download the selected file
string localPath = @"C:\local\path\";
string sourcePath = RemotePath.EscapeFileMask(remotePath + latest.Name);
session.GetFiles(sourcePath, localPath).Check();
}
(I'm the author of WinSCP)
Solution 3:
WebRequestMethods.Ftp.ListDirectory
returns a "short listing" of all the files in an FTP directory. This type of listing is only going to provide file names - not additional details on the file (like permissions or last modified date).
Use WebRequestMethods.Ftp.ListDirectoryDetails
instead. This method will return a long listing of files on the FTP server. Once you've retrieved this list into the names
variable, you can split the names
variable into an array based on an end of line character. This will result in each array element being a file (or directory) name listing that includes the permissions, last modified date owner, etc...
At this point, you can iterate over this array, examine the last modified date for each file, and decide whether to download the file.
I hope this helps!!