linux中ftp提示--553 Could not create file (绝对有用)

本文针对FTP客户端在上传文件时出现553错误的问题进行了深入分析,并提供了详细的解决方案,包括调整SELinux设置、验证FTP配置文件及目录权限等。

 


提示553 Could not create file,把这个目录的属主和权限都设置好,还是报这个错误,那仔细在网上查查,问题解决如下:
 
错误提示
 
当前目录是/home
 ftp> !ls -l
 ......
 -rwxr-xr-x   1 root    root       146 Aug 16 03:30 hosts
 -rw-r--r--   1 root    root        46 Aug 16 02:09 host.txt
 -rw-r--r--   1 root    root        51 Aug 15 07:14 logins.txt
 .....
 ftp> put host.txt
 local: host.txt remote: host.txt
 227 Entering Passive Mode (127,0,0,1,62,184)
 150 Ok to send data.
 226 File receive OK.
 46 bytes sent in 0.014 seconds (3.2 Kbytes/s)
 ftp> put hosts
 local: hosts remote: hosts
 227 Entering Passive Mode (127,0,0,1,174,59)
 150 Ok to send data.
 226 File receive OK.
 146 bytes sent in 0.046 seconds (3.1 Kbytes/s)
 ftp> put /home/hosts
 local: /home/hosts remote: /home/hosts
 227 Entering Passive Mode (127,0,0,1,232,15)
 553 Could not create file.
 ftp>
 问题:ftp> put /home/hosts 与 ftp> put hosts (当前目录是/home
 )执行的参数应该是一样的 为什么前一种却不能上传?
 
碰到这种问题我们要先要分析原因,大概如
 
1.考虑是不是selinux的原因 把selinux禁用试试
 2.说不定ftp的文件夹确实没有写权限,确认一下该目录权限
 3.配置文件里有write_enable=YES吗
 
先来尝试:
 


 代码如下

复制代码

 

 
1. setsebool -P ftpd_disable_trans 1
 2. service vsftpd restart
 

如果解决了就不要向下看了,否则往下看另一种方法
 
我们需要把allow_ftpd_full_access 设置为1
 


 代码如下

复制代码

 

 
[root@umboyserver vsftpd]# setsebool allow_ftpd_full_access 1
 
[root@umboyserver vsftpd]# setsebool allow_ftpd_use_cifs 1
 [root@umboyserver vsftpd]# setsebool allow_ftpd_use_nfs 1
 [root@umboyserver vsftpd]# setsebool ftp_home_dir 1
 [root@umboyserver vsftpd]# setsebool httpd_enable_ftp_server 1
 [root@umboyserver vsftpd]# setsebool tftp_anon_write 1
 [root@umboyserver vsftpd]# service vsftpd restart
 Shutting down vsftpd: [ OK ]
 Starting vsftpd for vsftpd: [ OK ]
 [root@umboyserver vsftpd]# getsebool -a|grep ftp
 allow_ftpd_anon_write --> off
 allow_ftpd_full_access --> on
 allow_ftpd_use_cifs --> on
 allow_ftpd_use_nfs --> on
 ftp_home_dir --> on
 httpd_enable_ftp_server --> on
 tftp_anon_write --> on
 


续:
 
为ftp新加用户
 


 代码如下

复制代码

 

useradd ftp-new -s /sbin/nologin -g ftp -d /home/ftp-new
 修改系统配置iptables
 /etc/sysconfig/iptables
 /etc/init.d/iptables restart

 

推荐一种匿名用户
 
1.vsftpd.conf文件中:
 


 代码如下

复制代码

 

 
write_enable=YES
 
anon_mkdir_write_enable=YES
 
anon_other_write_enable=YES
 

2.ftp目录权限:
 
查看ftp目录:
 


 代码如下

复制代码

 

 
> cat /etc/passwd | grep ftp
 
ftp:x:107:65534::/home/ftp:/bin/false
 

ftp目录为/home/ftp
 


 代码如下

复制代码

 

 
chown root:root   /home/ftp
 
chmod -R 755   /home/ftp
 

但这样是不能上传文件的。因为这是匿名用户,当前目录所有者是root用户; 真的要上传文件在该目录下建立一个文件夹如名字是upload,
 


 代码如下

复制代码

 

 
mkdir  /home/ftp/upload
 
chown ftp:root  /home/ftp/upload
 

这个时候可以传文件到upload目录,但根目录还是不能上传文件,这是匿名用户,如果是不是匿名用户就不存在这个问题。

更多详细内容请查看:http://www.111cn.net/sys/linux/45542.htm

<think> 我们正在处理一个关于使用Apache Commons Net FTP客户端时遇到的FTP响应553错误的问题。错误信息“553 Could not create file”通常表示服务器无法创建指定的文件,这通常与权限问题或路径问题有关。 根据提供的引用,我们知道用户已经添加了commons-net-1.4.1包,并且在调用listFiles方法时出现了异常(但注意,用户现在的问题是在创建文件时出现553错误,而不是listFiles)。因此,我们需要关注文件上传或创建时的553错误。 引用[2]提到关于获取隐藏文件的方法,这与当前问题关联不大,但我们可以从中知道FTPClient的一些配置选项。 常见的553错误原因: 1. 目标目录不存在。 2. 用户对目标目录没有写入权限。 3. 尝试创建文件时使用了绝对路径,但FTP服务器配置不允许。 4. 文件名中包含非法字符(如空格、特殊字符等)或路径格式不正确。 解决方案建议: 1. 确保目标目录存在:在写入文件之前,检查目标目录是否存在,如果不存在则创建它(如果允许的话)。注意:创建目录可能需要额外的权限。 2. 检查权限:确认FTP用户有在目标目录下创建文件的权限。 3. 使用相对路径:避免使用绝对路径,尝试将文件写入到当前工作目录(可以使用`printWorkingDirectory()`方法查看当前目录)。 4. 更改文件名:尝试使用一个简单的文件名(如test.txt)来测试,以排除文件名问题。 5. 检查服务器设置:有些FTP服务器对文件名有严格限制(如不允许空格),或者对文件创建有其他限制。 在代码层面,我们可以采取以下步骤: - 在登录后,使用`makeDirectory`和`changeWorkingDirectory`确保目标目录存在并切换到该目录。 - 在上传文件时,只使用文件名(不带路径)作为参数,因为我们已经切换到了目标目录。 代码示例: 假设我们要将本地文件上传到FTP服务器的某个目录,但遇到553错误。我们可以这样处理: ```java FTPClient ftp = new FTPClient(); ftp.connect(server, port); ftp.login(username, password); // 设置文件类型为二进制,防止文件损坏 ftp.setFileType(FTP.BINARY_FILE_TYPE); // 设置被动模式,因为很多服务器位于防火墙后 ftp.enterLocalPassiveMode(); // 假设目标目录为 "/public/upload" String remoteDir = "/public/upload"; // 检查目录是否存在,如果不存在则尝试创建 if (!ftp.changeWorkingDirectory(remoteDir)) { // 目录不存在,尝试创建 if (ftp.makeDirectory(remoteDir)) { System.out.println("Directory created: " + remoteDir); // 切换到新创建的目录 ftp.changeWorkingDirectory(remoteDir); } else { // 创建目录失败,可能是权限问题或路径无效 System.out.println("Failed to create directory: " + remoteDir); // 处理错误,退出 return; } } else { // 目录已存在,切换到该目录 System.out.println("Changed to directory: " + remoteDir); } // 现在上传文件,注意这里使用文件名(不带路径)作为远程文件名 String remoteFile = "test.txt"; File localFile = new File("local.txt"); // 本地文件路径 InputStream inputStream = new FileInputStream(localFile); boolean uploaded = ftp.storeFile(remoteFile, inputStream); inputStream.close(); if (uploaded) { System.out.println("File uploaded successfully."); } else { // 上传失败,可以检查FTP回复码 int replyCode = ftp.getReplyCode(); System.out.println("Upload failed. Reply code: " + replyCode + ", " + ftp.getReplyString()); } ftp.logout(); ftp.disconnect(); ``` 注意:上面的代码中,我们创建目录时使用了`makeDirectory`,但注意如果目录是多级(例如"/public/upload"),而服务器上只有"/public"存在,那么创建"upload"目录是可行的。但如果"/public"也不存在,那么需要逐级创建。Apache Commons Net的`makeDirectory`只能创建单级目录,所以对于多级目录,需要自己拆分路径逐级创建。 另外,如果目标目录结构复杂,可以使用以下方法创建多级目录: ```java // 递归创建目录的方法 public static boolean createDirectory(FTPClient ftpClient, String dirPath) throws IOException { String[] pathElements = dirPath.split("/"); if (pathElements[0].isEmpty()) { // 绝对路径以空字符串开始(因为分割后第一个是空) pathElements[0] = "/"; } StringBuilder pathBuilder = new StringBuilder(); for (String dir : pathElements) { if (dir.isEmpty()) { continue; } pathBuilder.append(dir).append("/"); String currentPath = pathBuilder.toString(); // 尝试切换,如果不能切换则创建 if (!ftpClient.changeWorkingDirectory(currentPath)) { if (ftpClient.makeDirectory(currentPath)) { System.out.println("Created directory: " + currentPath); } else { System.out.println("Failed to create directory: " + currentPath); return false; } } } return true; } ``` 然后在上面的代码中替换为: ```java // 创建目录(支持多级) if (!createDirectory(ftp, remoteDir)) { System.out.println("Failed to create directories: " + remoteDir); return; } // 切换到目标目录 ftp.changeWorkingDirectory(remoteDir); ``` 如果以上方法都不能解决问题,可能需要联系FTP服务器管理员,确认用户权限和服务器配置。 注意:由于FTP服务器可能有不同的配置,例如是否允许创建目录,以及目录权限的设置,所以需要根据实际情况调整。 最后,用户的问题中提到了“553 Could not create file”,在上传文件时(storeFile)可能会返回false,并且通过getReplyCode()会得到553。在代码中,我们应该检查上传操作的返回值,并获取服务器的响应信息,这有助于诊断问题。 因此,我们建议用户按照上述步骤检查目录和权限,并尝试使用简单的文件名上传到当前目录(确保当前目录有写权限)来测试。 </think> ### Java使用Apache Commons Net FTP时出现FTP响应553错误的解决方案 出现`553 Could not create file`错误通常表示FTP服务器拒绝了文件创建请求,主要涉及**权限问题**或**路径问题**。以下是系统性的解决方案: #### 核心解决方法 1. **检查服务器写入权限** - 确认FTP账号对目标目录有写入权限(Linux下使用`ls -ld /path`检查目录权限) - 尝试在目标目录手动创建文件验证权限 - *建议:联系服务器管理员确认账号权限* 2. **验证文件路径格式**(关键步骤) ```java // 错误示例:绝对路径可能导致553错误 ftpClient.storeFile("/absolute/path/file.txt", inputStream); // 正确做法:先切换工作目录再传文件ftpClient.changeWorkingDirectory("/target/directory"); boolean success = ftpClient.storeFile("file.txt", inputStream); ``` - 使用`changeWorkingDirectory()`切换目录后,`storeFile()`只需传入文件名而非完整路径 - 路径分隔符使用`/`而非`\`(Windows服务器也支持`/`) 3. **检查磁盘空间** - 通过`STAT`命令查看服务器磁盘空间: ```java ftpClient.sendCommand("STAT"); System.out.println(ftpClient.getReplyString()); ``` - 若磁盘已满需清理空间 #### 其他排查点 4. **文件名合法性** - 避免特殊字符:`<>:"/\|?*` - 文件名区分大小写(Linux服务器) - 临时使用简单文件名测试:`test123.txt` 5. **配置传输模式** ```java ftpClient.setFileType(FTP.BINARY_FILE_TYPE); // 二进制模式 ftpClient.enterLocalPassiveMode(); // 被动模式避免防火墙问题 ``` 6. **服务器日志分析** - 检查FTP服务器日志(如vsftpd日志路径`/var/log/vsftpd.log`) - 查找553错误的详细原因描述 #### 完整代码示例 ```java FTPClient ftp = new FTPClient(); ftp.connect("ftp.example.com", 21); ftp.login("user", "password"); // 关键配置 ftp.enterLocalPassiveMode(); ftp.setFileType(FTP.BINARY_FILE_TYPE); // 切换工作目录(绝对路径) if (!ftp.changeWorkingDirectory("/uploads/2024")) { System.out.println("目录不存在或不可访问:" + ftp.getReplyString()); return; } // 上传文件(仅文件名) try (InputStream input = new FileInputStream("localfile.txt")) { if (!ftp.storeFile("remotefile.txt", input)) { // 获取详细错误 System.out.println("上传失败: " + ftp.getReplyCode() + " - " + ftp.getReplyString()); } } finally { ftp.logout(); ftp.disconnect(); } ``` > **重要提示**:553错误90%由权限/路径问题引起。测试时可先用FTP客户端(如FileZilla)手动上传相同文件,若同样失败即可确认为服务器端问题[^1][^2]。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值