Java實(shí)現(xiàn)上傳文件到服務(wù)器的示例代碼
更新時(shí)間:2024年04月23日 09:50:06 作者:abc_xian
這篇文章主要為大家詳細(xì)介紹了如何使用Java實(shí)現(xiàn)上傳文件到服務(wù)器,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下
1、使用jsch
<!--sftp文件上傳-->
<dependency>
<groupId>com.jcraft</groupId>
<artifactId>jsch</artifactId>
<version>0.1.55</version>
</dependency>
2、配置類
package com.base.jsch;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
@Data
@Component
@ConfigurationProperties(prefix = "sftp")
public class SFTPConfig {
/**
* SFTP 服務(wù)器地址IP地址
*/
@NotBlank(message = "IP地址不能為空")
private String ip;
/**
* SFTP 端口
*/
@NotNull(message = "端口不能為空")
private int port;
/**
* SFTP 登錄用戶名
*/
@NotBlank(message = "用戶名不能為空")
private String username;
/**
* SFTP 登錄密碼
*/
@NotBlank(message = "密碼不能為空")
private String password;
/**
* SFTP 私鑰
*/
private String privateKey;
/**
* 上傳失敗隔多長(zhǎng)時(shí)間重新上傳
*/
@NotNull(message = "上傳失敗重試間隔不能為空")
private int uploadSleep;
/**
* 重新上傳的次數(shù)
*/
@NotNull(message = "重新上傳次數(shù)不能為空")
private int uploadRetry;
/**
* 服務(wù)器路徑
*/
@NotBlank(message = "服務(wù)器路徑不能為空")
private String serverStorageDir;
@NotNull(message = "文件名是否需要中文編碼")
private Boolean isFileNameGBK;
}
3、獲取連接
package com.base.jsch;
import java.lang.reflect.Field;
import java.util.Properties;
import com.jcraft.jsch.*;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
/**
* SFTP工廠類,用于獲取SFTP的連接和關(guān)閉SFTP的連接
*/
@Slf4j
@Component
public class SFTPConnection {
@Autowired
private SFTPConfig sftpConfig;
private static ChannelSftp client;
private static Session session;
/**
* 建立連接
*
* @return client
*/
public synchronized ChannelSftp makeConnection() {
if (client == null || session == null || !client.isConnected() || !session.isConnected()) {
try {
JSch jsch = new JSch();
if (sftpConfig.getPrivateKey() != null) {
jsch.addIdentity(sftpConfig.getPrivateKey());// 設(shè)置私鑰
}
session = jsch.getSession(sftpConfig.getUsername(), sftpConfig.getIp(), sftpConfig.getPort());
if (sftpConfig.getPassword() != null) {
session.setPassword(sftpConfig.getPassword());
}
Properties config = new Properties();
config.put("StrictHostKeyChecking", "no");
session.setConfig(config);
session.connect();
client = (ChannelSftp)session.openChannel("sftp");
client.connect();
log.info("sftp服務(wù)器連接成功");
// 文件名中文亂碼
if(Boolean.TRUE.equals(sftpConfig.getIsFileNameGBK())){
try{
Class<ChannelSftp> cl = ChannelSftp.class;
Field f1 =cl.getDeclaredField("server_version");
f1.setAccessible(true);
f1.set(client, 2);
client.setFilenameEncoding("gbk");
log.info("設(shè)置中文編碼");
}catch (NoSuchFieldException | SftpException | IllegalAccessException e) {
log.error("設(shè)置中文編碼" + e.getMessage());
throw new RuntimeException(e);
}
}
} catch (JSchException e) {
log.error("主機(jī)sftp登錄失敗,檢測(cè)登錄ip,端口號(hào),用戶名密碼是否正確,錯(cuò)誤信息為" + e.getMessage());
}
}
return client;
}
/**
* 關(guān)閉連接
*/
public void logout() {
if (client != null) {
if (client.isConnected()) {
client.disconnect();
}
}
if (session != null) {
if (session.isConnected()) {
session.disconnect();
}
}
}
}4、上傳工具類
package com.base.jsch;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.concurrent.TimeUnit;
import com.jcraft.jsch.SftpATTRS;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import com.jcraft.jsch.ChannelSftp;
import com.jcraft.jsch.SftpException;
/**
* 工具類
*/
@Slf4j
@Component
public class SFTPClientUtils {
@Autowired
private SFTPConfig sftpConfig;
@Autowired
private SFTPConnection sftpConnection;
public synchronized boolean upload(InputStream fileIs, String fileName) {
boolean result = false;
int i = 0;
while (!result) {
log.info("*****開(kāi)始登陸*****");
ChannelSftp sftp = sftpConnection.makeConnection();
if(null == sftp || !sftp.isConnected() || sftp.isClosed()){
log.info("連接無(wú)效");
return result;
}
log.info("******登陸成功*****");
try {
sftp.cd(sftpConfig.getServerStorageDir());
} catch (SftpException e) {
if(sftp.isConnected()){
log.info("sftp文件上傳,目錄不存在開(kāi)始創(chuàng)建");
try {
sftp.mkdir(sftpConfig.getServerStorageDir());
sftp.cd(sftpConfig.getServerStorageDir());
} catch (SftpException e1) {
log.info("sftp文件上傳,目錄創(chuàng)建失敗,錯(cuò)誤信息:" + e1.fillInStackTrace());
}
}else{
log.info("sftp連接已經(jīng)失效");
return result;
}
}
try {
sftp.put(fileIs, fileName, new FileProgressMonitor(fileIs.available()), ChannelSftp.OVERWRITE);
// 用下面的方法不會(huì)調(diào)用進(jìn)度監(jiān)控
//sftp.put(fileIs, fileName);
if (i > 0) {
log.info("sftp重試文件上傳成功,ftp路徑:" + sftpConfig.getServerStorageDir() + ",文件名稱:" + fileName);
} else {
log.info("sftp文件上傳成功,ftp路徑為" + sftpConfig.getServerStorageDir() + ",文件名稱:" + fileName);
}
result = true;
} catch (Exception e) {
i++;
log.error("sftp文件上傳失敗,重試中。。。第" + i + "次,錯(cuò)誤信息" + e.fillInStackTrace());
if (i > sftpConfig.getUploadRetry()) {
sftpConnection.logout();
log.error("sftp文件上傳失敗,超過(guò)重試次數(shù)結(jié)束重試,錯(cuò)誤信息" + e.fillInStackTrace());
return result;
}
try {
TimeUnit.MILLISECONDS.sleep(sftpConfig.getUploadSleep());
} catch (InterruptedException e1) {
sftpConnection.logout();
e1.printStackTrace();
log.error("sftp文件上傳失敗,系統(tǒng)檢測(cè)出異常:" + e);
}
}
}
sftpConnection.logout();
log.info("sftp上傳:" + result);
try {
fileIs.close();
} catch (IOException e) {
throw new RuntimeException(e);
}
return result;
}
public synchronized void download(String directory, String downloadFile, String localDir) {
log.info("*****開(kāi)始登陸*****");
ChannelSftp sftp = sftpConnection.makeConnection();
log.info("******登陸成功*****");
if (directory != null && !"".equals(directory)) {
try {
sftp.cd(directory);
} catch (SftpException e) {
log.error("sftp文件下載,目錄不存在,錯(cuò)誤信息" + e.fillInStackTrace());
}
}
String src = directory + "/" + downloadFile;
try {
SftpATTRS attr = sftp.stat(src);
long fileSize = attr.getSize();
InputStream inputStream = sftp.get(src, new FileProgressMonitor(fileSize));
// 用下面的方法不會(huì)調(diào)用進(jìn)度監(jiān)控
//InputStream inputStream = sftp.get(src);
String tempFile = localDir + "/" + downloadFile;
File file = new File(tempFile);
File fileParent = file.getParentFile();
if (!fileParent.exists()) {
fileParent.mkdirs();
}
if (!file.exists()) {
writeToLocal(tempFile, inputStream);
}
} catch (SftpException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
sftpConnection.logout();
}
// /**
// * 文件上傳 將文件對(duì)象上傳到sftp作為文件。文件完整路徑=basePath+directory 目錄不存在則會(huì)上傳文件夾
// *
// * @param basePath 服務(wù)器的基礎(chǔ)路徑,服務(wù)器上必須有該目錄,例如 /home
// * @param directory 上傳到的目錄,服務(wù)器上沒(méi)有會(huì)自動(dòng)創(chuàng)建,有則不創(chuàng)建,例如 /test
// * @param fileIs 文件流
// * @param fileName 放到服務(wù)器上要保存的名字,例如 碼海無(wú)際.txt
// * @return
// */
// public synchronized static boolean upload(String basePath, String directory, InputStream fileIs, String fileName) {
// boolean result = false;
// Integer i = 0;
// while (!result) {
// log.info("*****開(kāi)始登陸*****");
// ChannelSftp sftp = SFTPConnectionFactory.makeConnection();
// log.info("******登陸成功*****");
// try {
// sftp.cd(basePath);
// sftp.cd(directory);
// } catch (SftpException e) {
// log.info("sftp文件上傳,目錄不存在開(kāi)始創(chuàng)建");
// String[] dirs = directory.split("/");
// String tempPath = basePath;
// for (String dir : dirs) {
// if (null == dir || "".equals(dir)) {
// continue;
// }
// tempPath += "/" + dir;
// try {
// sftp.cd(tempPath);
// } catch (SftpException ex) {
// try {
// sftp.mkdir(tempPath);
// sftp.cd(tempPath);
// } catch (SftpException e1) {
// log.info("sftp文件上傳,目錄創(chuàng)建失敗,錯(cuò)誤信息:" + e1.fillInStackTrace());
// }
// }
// }
// }
// try {
// sftp.put(fileIs, fileName, new FileProgressMonitor(fileIs.available()), ChannelSftp.OVERWRITE);
// // 用下面的方法不會(huì)調(diào)用進(jìn)度監(jiān)控
// //sftp.put(fileIs, fileName);
// if (i > 0) {
// log.info("sftp重試文件上傳成功,ftp路徑:" + basePath + directory + ",文件名稱:" + fileName);
// } else {
// log.info("sftp文件上傳成功,ftp路徑為" + basePath + directory + ",文件名稱:" + fileName);
// }
// result = true;
// } catch (Exception e) {
// i++;
// log.error("sftp文件上傳失敗,重試中。。。第" + i + "次,錯(cuò)誤信息" + e.fillInStackTrace());
// if (i > uploadRettry) {
// SFTPConnectionFactory.logout();
// log.error("sftp文件上傳失敗,超過(guò)重試次數(shù)結(jié)束重試,錯(cuò)誤信息" + e.fillInStackTrace());
// return result;
// }
// try {
// TimeUnit.MILLISECONDS.sleep(uploadSleep);
// } catch (InterruptedException e1) {
// SFTPConnectionFactory.logout();
// e1.printStackTrace();
// log.error("sftp文件上傳失敗,系統(tǒng)檢測(cè)出異常:" + e);
// }
// }
//
// }
// SFTPConnectionFactory.logout();
// log.info("sftp上傳:" + result);
// try {
// fileIs.close();
// } catch (IOException e) {
// throw new RuntimeException(e);
// }
// return result;
// }
// /**
// * 下載文件至本地
// *
// * @param directory 要下載文件所在目錄,例如 /home
// * @param downloadFile 要下載的文件,例如 碼海無(wú)際.txt
// * @param localDir 本地路徑,例如 D:\\home
// * @return
// */
// public synchronized static void download(String directory, String downloadFile, String localDir) {
// log.info("*****開(kāi)始登陸*****");
// ChannelSftp sftp = SFTPConnectionFactory.makeConnection();
// log.info("******登陸成功*****");
// if (directory != null && !"".equals(directory)) {
// try {
// sftp.cd(directory);
// } catch (SftpException e) {
// log.error("sftp文件下載,目錄不存在,錯(cuò)誤信息" + e.fillInStackTrace());
// }
// }
// String src = directory + "/" + downloadFile;
// try {
// SftpATTRS attr = sftp.stat(src);
// long fileSize = attr.getSize();
// InputStream inputStream = sftp.get(src, new FileProgressMonitor(fileSize));
// // 用下面的方法不會(huì)調(diào)用進(jìn)度監(jiān)控
// //InputStream inputStream = sftp.get(src);
// String tempFile = localDir + "/" + downloadFile;
// File file = new File(tempFile);
// File fileParent = file.getParentFile();
// if (!fileParent.exists()) {
// fileParent.mkdirs();
// }
// if (!file.exists()) {
// writeToLocal(tempFile, inputStream);
// }
// } catch (SftpException e) {
// e.printStackTrace();
// } catch (IOException e) {
// e.printStackTrace();
// }
// SFTPConnectionFactory.logout();
// }
/**
* 將InputStream寫入本地文件
*
* @param destination 寫入本地目錄
* @param input 輸入流
* @throws IOException 異常
*/
public static void writeToLocal(String destination, InputStream input) throws IOException {
int index;
byte[] bytes = new byte[1024];
FileOutputStream downloadFile = new FileOutputStream(destination);
while ((index = input.read(bytes)) != -1) {
downloadFile.write(bytes, 0, index);
downloadFile.flush();
}
downloadFile.close();
input.close();
}
/**
* 刪除文件
*
* @param directory 要?jiǎng)h除文件所在目錄,例如 /home
* @param deleteFile 要?jiǎng)h除的文件,例如 碼海無(wú)際.txt
*/
public synchronized boolean delete(String directory, String deleteFile) {
boolean result = false;
ChannelSftp sftp = sftpConnection.makeConnection();
try {
sftp.cd(directory);
sftp.rm(deleteFile);
} catch (SftpException e) {
e.printStackTrace();
}
result = true;
sftpConnection.logout();
return result;
}
}5、上傳進(jìn)度
package com.base.jsch;
import com.jcraft.jsch.SftpProgressMonitor;
import lombok.extern.slf4j.Slf4j;
import java.text.DecimalFormat;
@Slf4j
public class FileProgressMonitor implements SftpProgressMonitor {
private long fileSize; // 記錄文件總大小
private long transfered; // 記錄已傳輸?shù)臄?shù)據(jù)總大小
public FileProgressMonitor(long fileSize) {
if (fileSize != 0) {
this.fileSize = fileSize;
log.info("數(shù)據(jù)大小: " + fileSize + " bytes");
} else {
log.info("文件錯(cuò)誤");
}
}
@Override
public void init(int op, String src, String dest, long max) {
log.info("開(kāi)始");
}
/**
* 實(shí)現(xiàn)了SftpProgressMonitor接口的count方法
*/
@Override
public boolean count(long count) {
add(count);
return true;
}
/**
* 實(shí)現(xiàn)了SftpProgressMonitor接口的end方法
*/
@Override
public void end() {
log.info("結(jié)束");
}
private synchronized void add(long count) {
transfered = transfered + count;
log.info("已傳輸數(shù)據(jù)大小: " + transfered + " bytes");
double d = ((double) transfered * 100) / (double) fileSize;
DecimalFormat df = new DecimalFormat("#.##");
log.info("已傳輸數(shù)據(jù)占比: " + df.format(d) + "%");
}
}6、配置文件
sftp: ip: 192.168.1.111 port: 22 username: root password: root uploadSleep: 1000 #上傳失敗隔1秒重新上傳 uploadRettry: 1 #重新上傳的次數(shù) serverStorageDir: /opt/zzz #服務(wù)器路徑 isFileNameGBK: true #文件名是否gbk編碼
7、上傳測(cè)試
String src = "D:\\home\\test.xlsx"; // 本地文件名
File file = new File(src);
try (FileInputStream fis = new FileInputStream(file)) {
boolean upload = sftpClientUtils.upload(fis, ele.getName());
} catch (IOException e) {
e.printStackTrace();
}以上就是Java實(shí)現(xiàn)上傳文件到服務(wù)器的示例代碼的詳細(xì)內(nèi)容,更多關(guān)于Java上傳文件到服務(wù)器的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
基于SpringBoot實(shí)現(xiàn)驗(yàn)證碼功能的代碼及思路
SpringBoot技術(shù)是目前市面上從事JavaEE企業(yè)級(jí)開(kāi)發(fā)過(guò)程中使用量最大的技術(shù),下面這篇文章主要給大家介紹了如何基于SpringBoot實(shí)現(xiàn)驗(yàn)證碼功能的相關(guān)資料,文中通過(guò)代碼介紹的非常詳細(xì),需要的朋友可以參考下2024-07-07
詳解SpringMVC中的@RequestMapping注解
這篇文章主要介紹了SpringMVC中@RequestMapping注解,@RequestMapping注解是一個(gè)用來(lái)處理請(qǐng)求地址映射的注解,可用于映射一個(gè)請(qǐng)求或一個(gè)方法,可以用在類或方法上,需要的朋友可以參考下2023-07-07
Java中實(shí)現(xiàn)文件預(yù)覽的功能(實(shí)例代碼)
大家都知道word,Excel,PPT實(shí)現(xiàn)在線預(yù)覽常用的方式就是先轉(zhuǎn)換成pdf,然后在進(jìn)行預(yù)覽,下面給大家介紹Java中如何實(shí)現(xiàn)文件預(yù)覽的功能,需要的朋友可以參考下2023-05-05
Hibernate validator使用以及自定義校驗(yàn)器注解
這篇文章主要介紹了Hibernate validator使用以及自定義校驗(yàn)器注解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2020-01-01
intellij idea14打包apk文件和查看sha1值
這篇文章主要為大家詳細(xì)介紹了intellij idea14打包apk文件和查看sha1值,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2020-10-10
Java集合排序規(guī)則接口Comparator用法解析
這篇文章主要介紹了Java集合排序規(guī)則接口Comparator用法解析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-09-09

