rpm -q vsftpd
yum install -y vsftpd
anonymous_enable=YES
anon_upload_enable=YES
anon_mkdir_write_enable=YES
anon_other_write_enable=YES
anon_world_readable_only=NO
anon_root=/home/vsftpd
默认是不能自动创建该文件的,如果要创建需要修改配置文件;
原因一:
修改vsftpd.conf文件中的chroot_local_user=NO,
并重启 systemctl restart vsftpd.service;
原因二:
makeDirectory(path)中path的上一级目录是否存在,如果不存在则创建失败,即makeDirectory只能逐级创建;
//创建用户,myftp为用户名
useradd myftp
//为用户myftp设置密码
passwd myftp
firewall-cmd --add-service=ftp --permanent
firewall-cmd --reload
临时性
//查看当前SELinux模式
getenforce
//更改当前模式为Permissive模式
setenforce 0
永久
vi /etc/selinux/config
SELINUX=enforcing <==调整 enforcing|disabled|permissive
//使用getsebool -a | grep -i ftp查看相关权限,on表示允许,off表示不允许
//开启匿名上传
setsebool -P ftpd_anon_write=1
//开放21端口号
firewall-cmd --zone=public --add-port=21/tcp --permanent
//开放20端口号
firewall-cmd --zone=public --add-port=20/tcp --permanent
//查看已开放的端口号
firewall-cmd --list-ports
//重启防火墙
firewall-cmd --reload
//重启vsftpd服务
systemctl start vsftpd
状态 systemctl status vsftpd.service
启动 systemctl start vsftpd.service
关闭 systemctl enable vsftpd.service
重启 systemctl restart vsftpd.service
开机启动 systemctl enable vsftpd.service
服务器重启需要重启vsftpd服务,或者设置启动加载vsftpd
//重启vsftpd服务
systemctl start vsftpd
commons-net
commons-net
3.3
FTP_ADDRESS=ip地址
FTP_PORT=21
FTP_USERNAME=登陆的用户名
FTP_PASSWORD=登陆的密码
FTP_BASEPATH=用户的根目录
IMG_PATH=上传文件存放的路径
package com.mr.ftp.controller;
import com.mr.ftp.service.FtpService;
import com.mr.utils.MyFtpUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
/**
* Created by LI WAN on 2019/1/21.
*/
@Controller
public class FtpController {
@Autowired
private FtpService ftpService;
@ResponseBody
@RequestMapping("ftpTest")
public String ftpTest(){
return "hei";
}
@RequestMapping("openFtp")
public String openFtp(){
return "ftpList";
}
//获取ip地址
@Value("${FTP_ADDRESS}")
private String FTP_ADDRESS;
//端口号
@Value("${FTP_PORT}")
private int FTP_PORT;
//用户名
@Value("${FTP_USERNAME}")
private String FTP_USERNAME;
//密码
@Value("${FTP_PASSWORD}")
private String FTP_PASSWORD;
//ftp的基本路径
@Value("${FTP_BASEPATH}")
private String FTP_BASEPATH;
//自定义需要上传的文件夹
@Value("${IMG_PATH}")
private String IMG_PATH;
/*//获取ip地址
private String FTP_ADDRESS="地址";
//端口号
private int FTP_PORT=21;
//用户名
private String FTP_USERNAME="zx2";
//密码
private String FTP_PASSWORD="root";
//ftp的基本路径s
private String FTP_BASEPATH="/home/zx2/";
//自定义需要上传的文件夹sss
private String IMG_PATH = "/ccc/imgs";
*/
@RequestMapping("addImgs")
@ResponseBody
public String img(String imgName, MultipartFile imgs){
boolean b = false;
String oldName = imgs.getOriginalFilename();//获取源文件名
String newName = MyFtpUtil.getFileSuffName(oldName);//修改为随机的文件名
String url = "";// 上传成功之后访问的路径
try {
//通过工具类上传,如果上传成功则返回 true, 不成功为false
b = MyFtpUtil.uploadFile(FTP_ADDRESS,FTP_USERNAME,FTP_PASSWORD,FTP_PORT,FTP_BASEPATH+IMG_PATH,newName,imgs.getInputStream());
//ftp的访问路径: ftp://ip:端口号/自定义文件路径/w服务器中的文件名
url = "ftp://"+FTP_ADDRESS+":"+FTP_PORT+"/"+IMG_PATH+"/"+newName;
//将参数添加在map中吗,传递到后台插入数据,注意service层事务管理
Map map = new HashMap<>();
map.put("imgName",imgName);
map.put("url",url);
//新增方法
ftpService.addImg(map);
} catch (IOException e) {
e.printStackTrace();
}
if(b){//如果成功,返回访问路径
return url;
}
return "error";//失败返回error
}
}
package com.mr.ftp.service;
import com.mr.ftp.mapper.FtpMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.Map;
/**
* Created by LI WAN on 2019/1/21.
*/
@Service
public class FtpServiceImpl implements FtpService{
@Autowired
private FtpMapper ftpMapper;
@Override
public void addImg(Map map) {
ftpMapper.addImg(map);
}
}
insert into t_imgs (img_name, img_url) VALUES (#{imgName},#{url})
package com.mr.utils;
import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPReply;
import java.io.*;
import java.net.SocketException;
import java.util.UUID;
/**
* Created by LI WAN on 2019/1/21.
*/
public class MyFtpUtil {
/**
* 获取FTPClient对象
*
* @param ftpHost FTP主机服务器
* @param ftpPassword FTP 登录密码
* @param ftpUserName FTP登录用户名
* @param ftpPort FTP端口 默认为21
* @return
*/
public static FTPClient getFTPClient(String ftpHost, String ftpUserName,
String ftpPassword, int ftpPort) {
FTPClient ftpClient = new FTPClient();
try {
ftpClient = new FTPClient();
ftpClient.connect(ftpHost, ftpPort);// 连接FTP服务器
ftpClient.login(ftpUserName, ftpPassword);// 登陆FTP服务器
if (!FTPReply.isPositiveCompletion(ftpClient.getReplyCode())) {
System.out.println("未连接到FTP,用户名或密码错误。");
ftpClient.disconnect();
} else {
System.out.println("FTP连接成功。");
}
} catch (SocketException e) {
e.printStackTrace();
System.out.println("FTP的IP地址可能错误,请正确配置。");
} catch (IOException e) {
e.printStackTrace();
System.out.println("FTP的端口错误,请正确配置。");
}
return ftpClient;
}
/**
* 从FTP服务器下载文件
* @param ftpHost FTP IP地址
* @param ftpUserName FTP 用户名
* @param ftpPassword FTP用户名密码
* @param ftpPort FTP端口
* @param ftpPath FTP服务器中文件所在路径 格式: ftptest/aa
* @param localPath 下载到本地的位置 格式:H:/download
* @param fileName 文件名称
*/
public static void downloadFtpFile(String ftpHost, String ftpUserName,
String ftpPassword, int ftpPort, String ftpPath, String localPath,
String fileName) {
FTPClient ftpClient = null;
try {
boolean flag = ftpClient.changeWorkingDirectory(ftpPath);
if(!flag){
//创建上传的路径 该方法只能创建一级目录,在这里如果/home/ftpuser存在则可创建image
ftpClient.makeDirectory(ftpPath);
}
//指定上传路径
ftpClient.changeWorkingDirectory(ftpPath);
ftpClient = getFTPClient(ftpHost, ftpUserName, ftpPassword, ftpPort);
ftpClient.setControlEncoding("UTF-8"); // 中文支持
ftpClient.setFileType(FTPClient.BINARY_FILE_TYPE);
ftpClient.enterLocalPassiveMode();
ftpClient.changeWorkingDirectory(ftpPath);
File localFile = new File(localPath + File.separatorChar + fileName);
OutputStream os = new FileOutputStream(localFile);
ftpClient.retrieveFile(fileName, os);
os.close();
ftpClient.logout();
} catch (FileNotFoundException e) {
System.out.println("没有找到" + ftpPath + "文件");
e.printStackTrace();
} catch (SocketException e) {
System.out.println("连接FTP失败.");
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
System.out.println("文件读取错误。");
e.printStackTrace();
}
}
/**
* Description: 向FTP服务器上传文件
* @param ftpHost FTP服务器hostname
* @param ftpUserName 账号
* @param ftpPassword 密码
* @param ftpPort 端口
* @param ftpPath FTP服务器中文件所在路径 格式: ftptest/aa
* @param fileName ftp文件名称
* @param input 文件流
* @return 成功返回true,否则返回false
*/
public static boolean uploadFile(String ftpHost, String ftpUserName,
String ftpPassword, int ftpPort, String ftpPath,
String fileName,InputStream input) {
boolean success = false;
FTPClient ftpClient = null;
try {
int reply;
ftpClient = getFTPClient(ftpHost, ftpUserName, ftpPassword, ftpPort);
reply = ftpClient.getReplyCode();
if (!FTPReply.isPositiveCompletion(reply)) {
ftpClient.disconnect();
return success;
}
ftpClient.setControlEncoding("UTF-8"); // 中文支持
ftpClient.setFileType(FTPClient.BINARY_FILE_TYPE);
ftpClient.enterLocalPassiveMode();
boolean b = ftpClient.makeDirectory(ftpPath);
System.out.println("创建目录:"+ftpPath);
System.out.println(b);
ftpClient.changeWorkingDirectory(ftpPath);
ftpClient.storeFile(fileName, input);
input.close();
ftpClient.logout();
success = true;
} catch (IOException e) {
e.printStackTrace();
} finally {
if (ftpClient.isConnected()) {
try {
ftpClient.disconnect();
} catch (IOException ioe) {
}
}
}
return success;
}
/**
* 修改文件名为uuid开头避免文件名重复
* @param fileName 获取上传的文件名
* @return 新的文件名
*/
public static String getFileSuffName(String fileName){
File file=new File(fileName);
String oldFileName=file.getName();
String suffixFileName=oldFileName.substring(oldFileName.lastIndexOf(".")+1);
String uuid= UUID.randomUUID().toString().replace("-","");
String newFileName=uuid+"."+suffixFileName;
return newFileName;
}
}
先登录再访问