Comment SpringBoot utilise FTP pour gérer les fichiers
May 12, 2023 pm 07:37 PMIntroduction
Utilisez SpringBoot pour configurer le serveur FTP afin de télécharger, supprimer et télécharger des fichiers.
Configurer FTP
Vérifiez si vsftpd est installé
rpm -qa | grep vsftpd
Vérifiez si vsftpd a été installé et vérifiez le numéro de version.
Installez vsftpd
yum -y install vsftpd
Si une erreur est signalée, utilisez les privilèges d'administrateur pour exécutez
sudo yum -y install vsftpd
sudo yum -y install vsftpd
关闭匿名访问
关闭匿名访问后,想访问里面的文件就需要账号和密码;如果不关,就可以直接访问。
vim /etc/vsftpd/vsftpd.conf
如果提示是只读文件,那么你只需要输入命令:
sudo vim /etc/vsftpd/vsftpd.conf
如下:
# Example config file /etc/vsftpd/vsftpd.conf # # The default compiled in settings are fairly paranoid. This sample file # loosens things up a bit, to make the ftp daemon more usable. # Please see vsftpd.conf.5 for all compiled in defaults. # # READ THIS: This example file is NOT an exhaustive list of vsftpd options. # Please read the vsftpd.conf.5 manual page to get a full idea of vsftpd's # capabilities. # # Allow anonymous FTP? (Beware - allowed by default if you comment this out). anonymous_enable=NO # # Uncomment this to allow local users to log in. local_enable=YES # # Uncomment this to enable any form of FTP write command. write_enable=YES # # Default umask for local users is 077. You may wish to change this to 022, # if your users expect that (022 is used by most other ftpd's) local_umask=022 # # Uncomment this to allow the anonymous FTP user to upload files. This only # has an effect if the above global write enable is activated. Also, you will # obviously need to create a directory writable by the FTP user. # When SELinux is enforcing check for SE bool allow_ftpd_anon_write, allow_ftpd_full_access #anon_upload_enable=YES # # Uncomment this if you want the anonymous FTP user to be able to create # new directories. #anon_mkdir_write_enable=YES # # Activate directory messages - messages given to remote users when they # go into a certain directory. dirmessage_enable=YES # # Activate logging of uploads/downloads. xferlog_enable=YES # # Make sure PORT transfer connections originate from port 20 (ftp-data). connect_from_port_20=YES # # If you want, you can arrange for uploaded anonymous files to be owned by # a different user. Note! Using "root" for uploaded files is not # recommended! #chown_uploads=YES #chown_username=whoever # # You may override where the log file goes if you like. The default is shown # below. #xferlog_file=/var/log/xferlog # # If you want, you can have your log file in standard ftpd xferlog format. # Note that the default log file location is /var/log/xferlog in this case. xferlog_std_format=YES # # You may change the default value for timing out an idle session. #idle_session_timeout=600
关闭匿名访问就是将:anonymous_enable=NO
启动服务
systemctl start vsftpd.service
查看服务状态
systemctl status vsftpd.service
[root@hadoop-master ~]# systemctl status vsftpd.service ● vsftpd.service - Vsftpd ftp daemon Loaded: loaded (/usr/lib/systemd/system/vsftpd.service; disabled; vendor preset: disabled) Active: active (running) since 一 2022-12-19 10:15:39 CST; 58min ago Process: 21702 ExecStart=/usr/sbin/vsftpd /etc/vsftpd/vsftpd.conf (code=exited, status=0/SUCCESS) Main PID: 21703 (vsftpd) CGroup: /system.slice/vsftpd.service └─21703 /usr/sbin/vsftpd /etc/vsftpd/vsftpd.conf 12月 19 10:15:39 hadoop-master systemd[1]: Starting Vsftpd ftp daemon... 12月 19 10:15:39 hadoop-master systemd[1]: Started Vsftpd ftp daemon. [root@hadoop-master ~]#
看到绿色的
active(running)
,代表着启动成功正在运行中。
添加 FTP 用户
因为在 Linux 上,root 用户是不能登陆 FTP 的。如果你输入的是 root 用户,登陆会失败的。
adduser ftpadmin
设置密码:
passwd ftpadmin
输入两次密码就 ok 了。
配置允许root用户登录
将 /etc/vsftpd/user_list
文件和 /etc/vsftpd/ftpusers
文件中的root
这一行注释掉
修改/etc/vsftpd/vsftpd.conf
,在最后一行处添加local_root=/
service vsftpd restart
这样远程就可以root用户身份登录ftp了。
文件存储地址授权
如存储地址为:app/upload/
Après avoir désactivé l'accès anonyme, vous avez besoin d'un compte et d'un mot de passe pour accéder aux fichiers qu'il contient si vous ne l'activez pas ; éteint, vous pouvez y accéder directement.
chmod 777 /app/upload/
Si l'invite est un fichier en lecture seule, il vous suffit alors de saisir la commande : sudo vim /etc/vsftpd/vsftpd.conf
Comme suit :
<dependency> <groupId>com.jcraft</groupId> <artifactId>jsch</artifactId> <version>0.1.55</version> </dependency>
Pour désactivez l'accès anonyme, changez simplement : anonyme_enable =NO
Démarrez le service
package com.demo.utils; import com.jcraft.jsch.*; import com.demo.dto.UploadFileDto; import lombok.extern.slf4j.Slf4j; import java.io.File; import java.io.FileOutputStream; import java.util.Properties; /** * @ClassName: UploadFileUtils.java * @Description: 上传文件 * @Author: tanyp * @Date: 2022/12/19 10:38 **/ @Slf4j public class UploadFileUtils { /** * @MonthName: upload * @Description: 上传文件 * @Author: tanyp * @Date: 2022/12/19 10:38 * @Param: [dto] * @return: boolean **/ public static boolean upload(UploadFileDto dto) throws Exception { log.info("============上传文件开始=============="); Boolean result = false; ChannelSftp sftp = null; Channel channel = null; Session sshSession = null; try { JSch jSch = new JSch(); jSch.getSession(dto.getAccount(), dto.getHost(), dto.getPort()); sshSession = jSch.getSession(dto.getAccount(), dto.getHost(), dto.getPort()); sshSession.setPassword(dto.getPasswd()); Properties sshConfig = new Properties(); sshConfig.put("StrictHostKeyChecking", "no"); sshSession.setConfig(sshConfig); sshSession.connect(); channel = sshSession.openChannel("sftp"); channel.connect(); sftp = (ChannelSftp) channel; sftp.cd(dto.getWorkingDir()); sftp.put(dto.getInputStream(), dto.getFileName()); result = true; log.info("============上传文件结束=============="); } catch (JSchException e) { result = false; log.error("=====上传文件异常:{}", e.getMessage()); e.printStackTrace(); } finally { closeChannel(sftp); closeChannel(channel); closeSession(sshSession); } return result; } /** * @MonthName: delete * @Description: 删除文件 * @Author: tanyp * @Date: 2022/12/19 10:38 * @Param: [dto] * @return: boolean **/ public static boolean delete(UploadFileDto dto) throws Exception { log.info("============删除文件开始=============="); Boolean result = false; ChannelSftp sftp = null; Channel channel = null; Session sshSession = null; try { JSch jSch = new JSch(); jSch.getSession(dto.getAccount(), dto.getHost(), dto.getPort()); sshSession = jSch.getSession(dto.getAccount(), dto.getHost(), dto.getPort()); sshSession.setPassword(dto.getPasswd()); Properties sshConfig = new Properties(); sshConfig.put("StrictHostKeyChecking", "no"); sshSession.setConfig(sshConfig); sshSession.connect(); channel = sshSession.openChannel("sftp"); channel.connect(); sftp = (ChannelSftp) channel; sftp.cd(dto.getWorkingDir()); sftp.rm(dto.getFileName()); result = true; log.info("============删除文件结束=============="); } catch (JSchException e) { result = false; log.error("=====删除文件异常:{}", e.getMessage()); e.printStackTrace(); } finally { closeChannel(sftp); closeChannel(channel); closeSession(sshSession); } return result; } /** * @MonthName: download * @Description: 下载文件 * @Author: tanyp * @Date: 2022/12/19 10:38 * @Param: [dto] * @return: boolean **/ public static boolean download(UploadFileDto dto) throws Exception { log.info("============下载文件开始=============="); Boolean result = false; ChannelSftp sftp = null; Channel channel = null; Session sshSession = null; try { JSch jSch = new JSch(); jSch.getSession(dto.getAccount(), dto.getHost(), dto.getPort()); sshSession = jSch.getSession(dto.getAccount(), dto.getHost(), dto.getPort()); sshSession.setPassword(dto.getPasswd()); Properties sshConfig = new Properties(); sshConfig.put("StrictHostKeyChecking", "no"); sshSession.setConfig(sshConfig); sshSession.connect(); channel = sshSession.openChannel("sftp"); channel.connect(); sftp = (ChannelSftp) channel; sftp.cd(dto.getWorkingDir()); sftp.get(dto.getFileName(), new FileOutputStream(new File(dto.getDownloadPath()))); sftp.disconnect(); sftp.getSession().disconnect(); result = true; log.info("============下载文件结束=============="); } catch (JSchException e) { result = false; log.error("=====下载文件异常:{}", e.getMessage()); e.printStackTrace(); } finally { closeChannel(sftp); closeChannel(channel); closeSession(sshSession); } return result; } private static void closeChannel(Channel channel) { if (channel != null) { if (channel.isConnected()) { channel.disconnect(); } } } private static void closeSession(Session session) { if (session != null) { if (session.isConnected()) { session.disconnect(); } } } }
Vérifiez l'état du service
package com.demo.dto; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.AllArgsConstructor; import lombok.Builder; import lombok.Data; import lombok.NoArgsConstructor; import java.io.InputStream; /** * @ClassName: UploadFileDto.java * @ClassPath: com.demo.dto.UploadFileDto.java * @Description: 上传文件 * @Author: tanyp * @Date: 2022/12/19 10:38 **/ @Data @AllArgsConstructor @NoArgsConstructor @Builder @ApiModel(value = "上传文件Dto") public class UploadFileDto { @ApiModelProperty(value = " ftp 服务器ip地址") private String host; @ApiModelProperty(value = " ftp 服务器port,默认是21") private Integer port; @ApiModelProperty(value = " ftp 服务器用户名") private String account; @ApiModelProperty(value = " ftp 服务器密码") private String passwd; @ApiModelProperty(value = " ftp 服务器存储图片的绝对路径") private String workingDir; @ApiModelProperty(value = "上传到ftp 服务器文件名") private String fileName; @ApiModelProperty(value = " 文件流") private InputStream inputStream; @ApiModelProperty(value = " 下载文件的路径") private String downloadPath; }
package com.demo.vo; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.AllArgsConstructor; import lombok.Builder; import lombok.Data; import lombok.NoArgsConstructor; /** * @ClassName: UploadVo.java * @ClassPath: com.demo.vo.UploadVo.java * @Description: 文件VO * @Author: tanyp * @Date: 2022/12/19 15:18 **/ @Data @AllArgsConstructor @NoArgsConstructor @Builder @ApiModel(value = "文件VO") public class UploadVo { @ApiModelProperty(value = "原始文件名称") private String oldName; @ApiModelProperty(value = "新文件名称") private String newName; @ApiModelProperty(value = "访问路径") private String path; }
Voir le actif (en cours d'exécution)
vert, ce qui signifie le démarrage est réussi et fonctionne.
Ajouter un utilisateur FTP
Car sous Linux, l'utilisateur root ne peut pas se connecter à FTP. Si vous entrez l'utilisateur root, la connexion échouera. package com.demo.controller;
import com.demo.vo.UploadVo;
import com.demo.service.UploadService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
/**
* @ClassName: UploadController.java
* @ClassPath: com.demo.controller.UploadController.java
* @Description: 上传文件
* @Author: tanyp
* @Date: 2022/12/19 15:18
**/
@Slf4j
@RestController
@RequestMapping("/upload")
@Api(value = "upload", tags = "上传文件")
public class UploadController {
@Autowired
private UploadService uploadService;
@ApiOperation(value = "上传图片", notes = "上传图片")
@PostMapping("/uploadImage")
public UploadVo uploadImage(@RequestParam("file") MultipartFile file) {
return uploadService.uploadImage(file);
}
@ApiOperation(value = "删除文件", notes = "删除文件")
@GetMapping("/delFile")
public Boolean delFile(String fileName) {
return uploadService.delFile(fileName);
}
@ApiOperation(value = "下载文件", notes = "下载文件")
@GetMapping("/downloadFile")
public Boolean downloadFile(String fileName, String downloadPath) {
return uploadService.downloadFile(fileName, downloadPath);
}
}
package com.demo.service; import com.demo.vo.UploadVo; import org.springframework.web.multipart.MultipartFile; /** * @ClassName: UploadService.java * @ClassPath: com.demo.service.UploadService.java * @Description:上传文件 * @Author: tanyp * @Date: 2022/12/19 15:18 **/ public interface UploadService { UploadVo uploadImage(MultipartFile file); Boolean delFile(String fileName); Boolean downloadFile(String fileName, String downloadPath); }
Entrez le mot de passe deux fois et c'est OK.
🎜🎜Configurez pour autoriser la connexion de l'utilisateur root🎜🎜🎜Placezroot</code dans le fichier <code>/etc/vsftpd/user_list
et /etc/vsftpd/ftpusers
file >Commentez cette ligne🎜🎜Modifiez /etc/vsftpd/vsftpd.conf
et ajoutez local_root=/
🎜package com.demo.service.impl; import com.demo.dto.UploadFileDto; import com.demo.vo.UploadVo; import com.demo.config.FtpConfig; import com.demo.service.UploadService; import com.demo.utils.UUIDUtils; import com.demo.utils.UploadFileUtils; import com.demo.exception.BusinessException; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.web.multipart.MultipartFile; import java.time.LocalDate; import java.time.format.DateTimeFormatter; import java.util.Objects; /** * @ClassName: UploadServiceImpl.java * @ClassPath: com.demo.service.impl.UploadServiceImpl.java * @Description: 上传文件 * @Author: tanyp * @Date: 2022/12/19 15:18 **/ @Slf4j @Service public class UploadServiceImpl implements UploadService { @Autowired private FtpConfig ftpConfig; @Override public UploadVo uploadImage(MultipartFile file) { log.info("=======上传图片开始,图片名称:{}", file.getOriginalFilename()); try { // 1. 取原始文件名 String oldName = file.getOriginalFilename(); // 2. ftp 服务器的文件名 String newName = LocalDate.now().format(DateTimeFormatter.ofPattern("yyyyMMdd")) + UUIDUtils.getUUID(10) + oldName.substring(oldName.lastIndexOf(".")); // 3.上传图片 Boolean result = UploadFileUtils.upload( UploadFileDto.builder() .host(ftpConfig.host) .port(ftpConfig.post) .account(ftpConfig.username) .passwd(ftpConfig.password) .workingDir(ftpConfig.basePath) .fileName(newName) .inputStream(file.getInputStream()) .build() ); // 4.返回结果 if (!result) { throw new BusinessException("上传图片失败!"); } log.info("=======上传图片结束,新图片名称:{}", newName); return UploadVo.builder() .oldName(oldName) .newName(newName) .path(ftpConfig.imageBaseUrl + "/" + newName) .build(); } catch (Exception e) { log.error("=======上传图片异常,异常信息:{}", e.getMessage()); e.printStackTrace(); } return null; } @Override public Boolean delFile(String fileName) { if (Objects.isNull(fileName)) { throw new BusinessException("文件名称为空,请核实!"); } try { Boolean result = UploadFileUtils.delete( UploadFileDto.builder() .host(ftpConfig.host) .port(ftpConfig.post) .account(ftpConfig.username) .passwd(ftpConfig.password) .workingDir(ftpConfig.basePath) .fileName(fileName) .build() ); return result; } catch (Exception e) { log.error("=======删除文件异常,异常信息:{}", e.getMessage()); e.printStackTrace(); } return null; } @Override public Boolean downloadFile(String fileName, String downloadPath) { if (Objects.isNull(fileName) || Objects.isNull(downloadPath)) { throw new BusinessException("文件名称或下载路径为空,请核实!"); } try { Boolean result = UploadFileUtils.download( UploadFileDto.builder() .host(ftpConfig.host) .port(ftpConfig.post) .account(ftpConfig.username) .passwd(ftpConfig.password) .workingDir(ftpConfig.basePath) .fileName(fileName) .downloadPath(downloadPath) .build() ); return result; } catch (Exception e) { log.error("=======下载文件异常,异常信息:{}", e.getMessage()); e.printStackTrace(); } return null; } }
app/upload/
, définissez l'autorisation sur : 🎜package com.demo.config; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Component; /** * @ClassName: FtpConfig.java * @ClassPath: com.demo.config.FtpConfig.java * @Description: FTP配置 * @Author: tanyp * @Date: 2022/12/19 22:28 **/ @Component public class FtpConfig { // ftp 服务器ip地址 @Value("${ftp.host}") public String host; // ftp 服务器port,默认是21 @Value("${ftp.post}") public Integer post; // ftp 服务器用户名 @Value("${ftp.username}") public String username; // ftp 服务器密码 @Value("${ftp.password}") public String password; // ftp 服务器存储图片的绝对路径 @Value("${ftp.base-path}") public String basePath; // ftp 服务器外网访问图片路径 @Value("${ftp.image-base-url}") public String imageBaseUrl; }
# ftp ftp: host: 127.0.0.1 post: 22 username: ftpadmin password: ftpadmin base-path: /app/upload/images image-base-url: http://127.0.0.1:8080/images
server { listen 8080; server_name localhost; location /images/ { root /app/upload/; autoindex on; } }
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Article chaud

Outils chauds Tags

Article chaud

Tags d'article chaud

Bloc-notes++7.3.1
Éditeur de code facile à utiliser et gratuit

SublimeText3 version chinoise
Version chinoise, très simple à utiliser

Envoyer Studio 13.0.1
Puissant environnement de développement intégré PHP

Dreamweaver CS6
Outils de développement Web visuel

SublimeText3 version Mac
Logiciel d'édition de code au niveau de Dieu (SublimeText3)

Sujets chauds

Utiliser FTP dans Go : un guide complet

Comment utiliser Redis pour implémenter des verrous distribués dans SpringBoot

Comparaison et analyse des différences entre SpringBoot et SpringMVC

Comment résoudre le problème selon lequel Springboot ne peut pas accéder au fichier après l'avoir lu dans un package jar

PHP et FTP : réaliser le partage de fichiers entre plusieurs départements lors du développement de sites Web

Comment SpringBoot personnalise Redis pour implémenter la sérialisation du cache

Comment obtenir la valeur dans application.yml au Springboot

Comment comparer des répertoires et des fichiers sur un serveur FTP via PHP
