我在搜索并发现了其他问题,但没有一个能解决我的问题。我正在尝试使用示例MSDN代码通过FTP上传文件。我得到远程服务器返回错误:(550)此行上的文件不可用(例如,找不到文件,没有访问权限)错误:ftpstream.Close();
string inputfilepath = @"C:\DWF\test.txt";
string ftpfilepath = "/abc/def/hij/klm/nop/test.txt";
string ftphost = "my-ser-ver1:2121";
//here correct hostname or IP of the ftp server to be given
string ftpfullpath = "ftp://" + ftphost + ftpfilepath;
FtpWebRequest ftp = (FtpWebRequest)FtpWebRequest.Create(ftpfullpath);
ftp.Credentials = new NetworkCredential("user", "pass");
//userid and password for the ftp server to given
ftp.KeepAlive = true;
ftp.UseBinary = true;
ftp.Method = WebRequestMethods.Ftp.UploadFile;
FileStream fs = File.OpenRead(inputfilepath);
byte[] buffer = new byte[fs.Length];
fs.Read(buffer, 0, buffer.Length);
fs.Close();
Stream ftpstream = ftp.GetRequestStream();
ftpstream.Write(buffer, 0, buffer.Length);
ftpstream.Close();
我已经仔细检查了空格的URI,但没有。我能够使用具有相同用户登录名的filezilla完成此任务。没有古怪的默认目录已经是我的URI的一部分。有一点可以肯定的是,我正在连接到unix服务器,所以可能有一个我缺少的设置?
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [220 Oracle Content Services FTP Server ready.]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [USER myuser]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [331 Password required for myuser.]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [PASS ********]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [230 Login successful.]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [OPTS utf8 on]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [500 Command not supported: OPTS]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [PWD]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [257 "/"]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [TYPE I]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [200 TYPE set to I.]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [PASV]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [227 Entering Passive Mode (10,8,9,50,77,53)]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Sending command [STOR abc/def/hij/klm/nop/test.txt]
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [150 Ok to send data.]
System.Net Verbose: 0 : [7584] Exiting FtpWebRequest#10964107::GetRequestStream()
System.Net Information: 0 : [7584] FtpControlStream#62182359 - Received response [550 Access denied.]
System.Net Information: 0 : [7584] FtpWebRequest#10964107::(Releasing FTP connection#62182359.)
答案 0 :(得分:6)
答案 1 :(得分:2)
如果没有关于错误的详细信息很难说,但似乎很可能在你的路径中的某个地方缺少一个目录。如果您在FTP文件路径中使用任何非标准字符,请尝试使用HttpUtility.UrlPathEncode,然后再将其添加到Url中。
要获取详细的故障排除信息,我在应用程序的.config文件的配置元素中添加以下内容:
<system.diagnostics>
<sources>
<source name="System.Net">
<listeners>
<add name="TraceFile"/>
</listeners>
</source>
<source name="System.Net.Sockets" maxdatasize="1024">
<listeners>
<add name="TraceFile"/>
</listeners>
</source>
</sources>
<sharedListeners>
<add name="TraceFile" type="System.Diagnostics.TextWriterTraceListener" initializeData="System.Net.trace.log" traceOutputOptions="DateTime"/>
</sharedListeners>
<switches>
<add name="System.Net" value="Verbose"/>
<!--<add name="System.Net.Sockets" value="Verbose"/>-->
</switches>
<trace autoflush="true" />
</system.diagnostics>
另外,仅供参考,这是我用于上传的代码:
private static FtpWebRequest CreateFtpWebRequest(string ftpUrl, string userName, string password, bool useSsl, bool allowInvalidCertificate, bool useActiveFtp)
{
FtpWebRequest request = (FtpWebRequest)WebRequest.Create(ftpUrl);
request.Credentials = new NetworkCredential(userName, password);
if (useSsl)
{
request.EnableSsl = true;
if (allowInvalidCertificate)
{
ServicePointManager.ServerCertificateValidationCallback = ServicePointManager_ServerCertificateValidationCallback;
}
else
{
ServicePointManager.ServerCertificateValidationCallback = null;
}
}
request.UsePassive = !useActiveFtp;
return request;
}
private static void UploadFileToServer(string ftpUrl, string userName, string password, bool useSsl, bool allowInvalidCertificate, bool useActiveFtp, string filePath)
{
FtpWebRequest request = CreateFtpWebRequest(ftpUrl, userName, password, useSsl, allowInvalidCertificate, useActiveFtp);
request.Method = WebRequestMethods.Ftp.UploadFile;
long bytesReceived = 0;
long bytesSent = 0;
using (Stream requestStream = request.GetRequestStream())
using (FileStream uploadFileStream = File.OpenRead(filePath))
{
// Note that this method call requires .NET 4.0 or higher. If using an earlier version it will need to be replaced.
uploadFileStream.CopyTo(requestStream);
bytesSent = uploadFileStream.Position;
}
using (FtpWebResponse response = (FtpWebResponse)request.GetResponse())
{
bytesReceived = response.ContentLength;
}
}
答案 2 :(得分:2)
我最近才遇到这个问题。它刚刚出现在我多年来一直使用的代码上。 事实证明,我一直在与许多ftp站点合作,并将相同的文件发送到所有这些ftp站点。好吧,当我去一些ftp网站时,我被留在了根,但在其他人,我立即被放在一个子目录。 在此最近的更改之前,我可以使用请求流并将文件直接放在我放置的子目录上。截至上周,我需要完全确定路径。
希望这有助于某人......
答案 3 :(得分:0)
这个答案适用于Steen,包含一个与下面http://support.microsoft.com/kb/2134299中的代码等效的PowerShell。我没有一个系统具有不合规的行为进行测试,因此您需要自己尝试。
function SetMethodRequiresCWD() {
[Type] $requestType = [System.Net.FtpWebRequest]
[System.Reflection.FieldInfo] $methodInfoField = $requestType.GetField("m_MethodInfo", [System.Reflection.BindingFlags]::NonPublic -bor [System.Reflection.BindingFlags]::Instance)
[Type] $methodInfoType = $methodInfoField.FieldType
[System.Reflection.FieldInfo] $knownMethodsField = $methodInfoType.GetField("KnownMethodInfo", [System.Reflection.BindingFlags]::Static -bor [System.Reflection.BindingFlags]::NonPublic)
[Array] $knownMethodsArray = [Array]$knownMethodsField.GetValue($null);
[System.Reflection.FieldInfo] $flagsField = $methodInfoType.GetField("Flags", [System.Reflection.BindingFlags]::NonPublic -bor [System.Reflection.BindingFlags]::Instance)
[int] $MustChangeWorkingDirectoryToPath = 0x100
ForEach ($knownMethod In $knownMethodsArray) {
[int] $flags = [int]$flagsField.GetValue($knownMethod)
$flags = $flags -bor $MustChangeWorkingDirectoryToPath
$flagsField.SetValue($knownMethod, $flags)
}
}