|
Try to replace the Directories.Add() with this:
public void Add(string sUnparsedDirectory)
{
sUnparsedDirectory = sUnparsedDirectory.Replace("\r", string.Empty);
string sDirectoryName = string.Empty;
DateTime dtDirectoryDate;
//parse line
Match m = GetMatchingRegex(sUnparsedDirectory);
if (m == null)
{
//failed
throw (new ApplicationException("Unable to parse line: " + sUnparsedDirectory));
}
else
{
sDirectoryName = m.Groups["name"].Value;
if (DateTime.TryParse(m.Groups["timestamp"].Value, out dtDirectoryDate) == false)
{
dtDirectoryDate = DateTime.MinValue;
}
}
Add(sDirectoryName, dtDirectoryDate);
}
private static Match GetMatchingRegex(string line)
{
Regex rx;
Match m;
for (int i = 0; i <= _ParseFormats.Length - 1; i++)
{
rx = new Regex(_ParseFormats[i]);
m = rx.Match(line);
if (m.Success)
{
return m;
}
}
return null;
}
private static string[] _ParseFormats = new string[] {
"(?<dir>[\\-d])(?<permission>([\\-r][\\-w][\\-xs]){3})\\s+\\d+\\s+\\w+\\s+\\w+\\s+(?<size>\\d+)\\s+(?<timestamp>\\w+\\s+\\d+\\s+\\d{4})\\s+(?<name>.+)",
"(?<dir>[\\-d])(?<permission>([\\-r][\\-w][\\-xs]){3})\\s+\\d+\\s+\\d+\\s+(?<size>\\d+)\\s+(?<timestamp>\\w+\\s+\\d+\\s+\\d{4})\\s+(?<name>.+)",
"(?<dir>[\\-d])(?<permission>([\\-r][\\-w][\\-xs]){3})\\s+\\d+\\s+\\d+\\s+(?<size>\\d+)\\s+(?<timestamp>\\w+\\s+\\d+\\s+\\d{1,2}:\\d{2})\\s+(?<name>.+)",
"(?<dir>[\\-d])(?<permission>([\\-r][\\-w][\\-xs]){3})\\s+\\d+\\s+\\w+\\s+\\w+\\s+(?<size>\\d+)\\s+(?<timestamp>\\w+\\s+\\d+\\s+\\d{1,2}:\\d{2})\\s+(?<name>.+)",
"(?<dir>[\\-d])(?<permission>([\\-r][\\-w][\\-xs]){3})(\\s+)(?<size>(\\d+))(\\s+)(?<ctbit>(\\w+\\s\\w+))(\\s+)(?<size2>(\\d+))\\s+(?<timestamp>\\w+\\s+\\d+\\s+\\d{2}:\\d{2})\\s+(?<name>.+)",
"(?<timestamp>\\d{2}\\-\\d{2}\\-\\d{2}\\s+\\d{2}:\\d{2}[Aa|Pp][mM])\\s+(?<dir>\\<\\w+\\>){0,1}(?<size>\\d+){0,1}\\s+(?<name>.+)" };
<div class="ForumMod">modified on Saturday, November 8, 2008 9:00 AM</div>
|
|
|
|
|
|
The same problem exists in the Files.Add() method...
|
|
|
|
|
yes, it does. Your code also fixed that one too. Thanks
|
|
|
|
|
Hi.
When using this method the FTP.RebuildDirectoryList, the "else" in order to add a file should be changed to "else if ( f [ 0 ] != 'l' )". This should be done because the _ParseFormats variable doesn't have regex to handle unix links and if you get one in the directory list an exception will be thrown.
My RebuildDirectoryList now looks like the following:
public void RebuildDirectoryList()
{
StringBuilder sbDirectoryList = FTPPlumbing.GetDirectoryList();
Directories.Clear();
Files.Clear();
foreach (string f in sbDirectoryList.ToString().Split('\n'))
{
if (f.Length > 0 && !Regex.Match(f, "^total").Success)
{
if ((f[0] == 'd') || (f.ToUpper().IndexOf("<DIR>") >= 0))
{
Directories.Add(f);
}
else if ( f [ 0 ] != 'l' )
{
Files.Add ( f );
}
}
}
}
|
|
|
|
|
In the Add method (both for Directories and Files) when the returned timestamp is, for example, Apr 30 10:00 the DateTime.TryParse fails and the dtDirectoryDate or dtFileDate is assigned the value DateTime.MinValue . This only happens if the timestamp relates to the current year, for other years everything works fine.
In order to solve this problem, at least in my case, I had to add the current year inline. The resulting Add method is the following:
public void Add ( string sUnparsedDirectory )
{
sUnparsedDirectory = sUnparsedDirectory.Replace ( "\r", string.Empty );
string sDirectoryName = string.Empty;
DateTime dtDirectoryDate;
Match m = RegexUtils.GetMatchingRegex ( sUnparsedDirectory );
if ( m == null )
{
throw ( new ApplicationException ( "Unable to parse line: " + sUnparsedDirectory ) );
}
else
{
sDirectoryName = m.Groups [ "name" ].Value;
string _ts = m.Groups [ "timestamp" ].Value;
if ( Regex.IsMatch ( _ts, "^\\w+\\s+\\d{2}\\s+\\d{2}:\\d{2}([Aa|Pp][mM])?$" ) )
{
_ts = _ts.Insert ( 7, DateTime.Now.Year.ToString ( ) + " " );
}
if ( DateTime.TryParse ( _ts, out dtDirectoryDate ) == false )
{
dtDirectoryDate = DateTime.MinValue;
}
}
Add ( sDirectoryName, dtDirectoryDate );
}
|
|
|
|
|
i am using the above code and dll,
but it is not working..
erroris coming like this :An existing connection was forcibly closed by remote host.
my server has firewall settings.
i know the valid credentials.
is first enter to firewall and then server.
i dont know how to connect.
Plz send me the code my mailid :addala.venkat16@gmail.com
|
|
|
|
|
hi,
I use this library everyday, so I know it works.. but its apparent it may be sensitive to different FTP and firewall configurations. My current setting is using a username and password with port 21, I have not tested it outside of this configuation.
If you are using different ports, secure-FTP or other types of things its possible it may not work and you may need to adjust the code as desired.
James
Jmers
|
|
|
|
|
Hi
How do you change directory when uploading without using the backslashes as in the documentation?
so for example : f.ChangeDirectory("api.hoseasons.co.uk/tradedoubler");
Throws an exception about datetime when slashes are used.
Regards
Danny
|
|
|
|
|
My guess is its looking for a directory named "api.hoseasons.co.uk/tradedoubler", instead of navigating into api.hoseasons.co.uk, and then subsequently into tradedoubler.
The obvious work around would be to issue two ChangeDirectory commands. If I recall correctly the previous version of this control didn't handle that sort of directory navigation and since what I was doing served my needs I didn't see to extend it in that regard.
It would not be difficult though to create a "ChangeDirectories" method, have it parse the "/" out, call ChangeDirectory, Re-build the directory list and do it again for each parsed directory.
Jmers
|
|
|
|
|
Hi,
first of all, thanks for your last reply jmers.
Now, I would like to download all the files in some directory on my FTP server.
I tried to do that with "FTP.fileinfo" and then foreach file name do the download, but I got an error says something wrong with the parameter "line".
So I'll realy appreciate it if you could help me.
Thanks, Idan.
|
|
|
|
|
Hi Idan,
You're welcome. I can tell you how to do what you need to do, I'm not quite sure what you are doing to generate your error but I can't find anything labeled "fileinfo" in the code.
Essentially, to download all files in a directory, you could connect to your FTP server, change to the specified directory, then loop through the files collection downloading each file. Here's how the code would look (note the while loop w/the console.writeline would only be useful in a console app, its here for demonstration purposes):
OpenFTP.FTP f = new OpenFTP.FTP();
f.Connect("127.0.0.1", "username_here", "password_here");
f.ChangeDirectory("somedirectory");
for(int i = 0; i <f.files.count; i++)
{
="" f.files.download(f.files[i].filename,="" @"localpath="" "="" +="" path.getfilename(f.files[i].filename));
="" while="" (!f.files.downloadcomplete)
="" {
="" console.writeline("downloading:="" totalbytes:="" f.files.totalbytes.tostring()="" ",="" :="" percentcomplete:="" f.files.percentcomplete.tostring());
="" }
}
hope="" the="" helps...=""
<div="" class="ForumSig">Jmers
|
|
|
|
|
I don't know why, but it downloads only the first file.
I tried to change your "for" statement to:
for (int i = 0; i < f.Files.Count; i++)
because you wrote an invalid statement (you forgot the ")" and to do something with the last "i").
Thanks for your help.
|
|
|
|
|
Oops yeh.. the for loop was incorrect. As far as I know it should re-build the directories collection and file collection on change of directory, you can of course confirm that as I am not w/o error.
Jmers
|
|
|
|
|
OpenFTP.FTP f = new OpenFTP.FTP();
f.Connect("server", "username", "password");
f.ChangeDirectory("");
// Console.Write("{0}", f.Files.Count);
for(int i = 0; i < f.Files.Count; i++)
{
f.Files.Download(f.Files[i].FileName, "C:\\Test\\" + f.Files[i].FileName);
while (!f.Files.DownloadComplete)
{
Console.WriteLine("Downloading: TotalBytes: " + f.Files.TotalBytes.ToString() + ", : PercentComplete: " + f.Files.PercentComplete.ToString());
}
}
Here is my code.
Right now it's downloading only the first file.
There is some way to do the download with foreach statement?
Something like
:
foreach (file in GetFiles)
{
file.download;
}
Thanks.
|
|
|
|
|
hey .. hmmm, I'd start w/checking that f.Files.Count is actually greater than 1.. perhaps the file count is not getting correctly set, or the directory/file collection is not being properly built, that would definitely cause the error you are encountering.
In my limited testing and use it worked, but, I basically use this library to upload files to an FTP server and I am not looping through a collection.
I wish I could be more specific. I can say, if you are using the library in a console app (as I am) try outputing enough information to the console to help you determine where the breakdown is occuring.
Jmers
|
|
|
|
|
Thanks for the lib Jmers but
has someone fixed this please?
I can get only one file copied...
<this.Count> egal 0 for the 2nd file in the <public File this[string sIndex]>
Thanks!
|
|
|
|
|
Just change the inner conditional in RebuildFileList():
if ((f[0] != 'd') && (f.ToUpper().IndexOf("<DIR>") <= 0))
{
this.Add(f);
}
The IndexOf("DIR") returns -1 instead of zero.
|
|
|
|
|
Yes, this is the fix. Open the project, make the above change and recompile. I'm sure I'll run up against this again in the future so: Hey Jeff, this works - make the change and redeploy the dll.
|
|
|
|
|
Hi,
Can you explain to me how to get the directories listing?
When I tried to do that, the input I got was "System.String[]".
So how can I display the directoy's name?
Thanks.
|
|
|
|
|
Hi,
Sorry for the delay in responding, work has been busy.
You want to access the Directories object which is a collection of all of the directories. Its built automatically for you, when you access a directory, so in the example above (you could):
OpenFTP.FTP f = new OpenFTP.FTP();
f.Connect("127.0.0.1", "username_here", "password_here");
f.ChangeDirectory("somedirectory");
string sSomeDirName = "";
for(int i = 0; i <f.directories.count; i++)
{
="" ssomedirname="f.Directories[i].DirectoryName;
}
Hope" that="" helps,
james=""
<div="" class="ForumSig">Jmers
|
|
|
|
|
|
Thanks for the article, everything seems to work fine so far.
To be able to upload Read-only-files, I had to change this line of code in "public void Upload(string sRemoteFilename, string sLocalFilename, bool bResume)" though :
FTPPlumbing.file = new FileStream(sLocalFilename, FileMode.Open, FileAccess.Read);
instead of
FTPPlumbing.file = new FileStream(sLocalFilename, FileMode.Open);
regards,
|
|
|
|
|
Cool.. didn't even try it w/read-only files, very interesting. Thanx for the post.
Jmers
|
|
|
|
|
Is there some way to connect via Proxy
Thnx
|
|
|
|