Java工具jsch.jar实现上传下载

在做运维的时候,我们一般使用shell脚本实现文件的服务器之间定时传输,那么对于一些不会shell脚本的童鞋,就得使用万能的编程语言了,这里我们介绍一款Java操作ftp的工具,那就是jsch.jar。工具已经写好,可以根据实际情况做调整,注释很清晰。大家按需阅读:

package com.wdy.tools.utils.sftputil;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Arrays;
import java.util.Collections;
import java.util.Properties;
import java.util.Vector;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.jcraft.jsch.Channel;
import com.jcraft.jsch.ChannelSftp;
import com.jcraft.jsch.JSch;
import com.jcraft.jsch.Session;

/**
 * 利用jsch.jar针对sftp的上传和下载
 * 需要jar包:
 * commons-lang3-3.2.1.jar
 * commons-logging.jar
 * jsch-0.1.53.jar
 * log4j-1.2.17.jar
 * @author wangdy
 *
 */
public class JschSftpUtils {

 private static final Log log = LogFactory.getLog(JschSftpUtils.class);

 /**
 * 利用JSch包实现SFTP下载文件
 * (这里是将serverPath下的指定扩展名的文件,全部下载到localPath下)
 * @param ip 主机IP
 * @param user 主机登陆用户名
 * @param psw 主机登陆密码
 * @param port 主机ssh2登陆端口,如果取默认值,传<=0的值,如-1
 * @param localPath 下载的本地目录的路径
 * @param serverPath 服务器目录
 * @param fileExetension 文件扩展名,格式如:'.txt'
 * @param isDelete 是否删除该路径下扩展名为fileExetension的远程文件
 * @throws Exception
 */
 public static void sshSftpDownload(String ip, String user, String psw, int port, String serverPath, String localPath, String fileExtension, boolean isDelete) throws Exception {
 Session session = null;
 Channel channel = null;
 JSch jsch = new JSch();
 if (port <= 0) {
 // 连接服务器,采用默认端口
 session = jsch.getSession(user, ip);
 } else {
 // 采用指定的端口连接服务器
 session = jsch.getSession(user, ip, port);
 }
 // 如果服务器连接不上,则抛出异常
 if (session == null) {
 throw new Exception("session is null");
 }
 // 设置登陆主机的密码
 session.setPassword(psw);// 设置密码
 // 设置第一次登陆的时候提示,可选值:(ask | yes | no)
// session.setConfig("StrictHostKeyChecking", "no");
 Properties sshConfig = new Properties();
 sshConfig.put("StrictHostKeyChecking", "no");
 session.setConfig(sshConfig);
 // 设置登陆超时时间ms
// session.connect(640);
 session.connect();
 log.info("Session connected.");
 log.info("Opening Channel.");
 try {
 // 创建sftp通信通道
 channel = (Channel) session.openChannel("sftp");
 channel.connect();
// channel.connect(1000);
 ChannelSftp sftp = (ChannelSftp) channel;
 log.info("Connected to " + ip + ".");
 // 进入服务器指定的文件夹
 sftp.cd(serverPath);
 /**
 * 列出服务器指定的文件列表(可以加参数,指明要下载的文件类型)
 * 说明:如果fileExtension不为空,则下载指定扩展名的文件集;
 * 如果fileExtension为"",则下载该目录下所有类型的文件,如果是文件夹的话,会报错,如果您路径下有以.连接的文件夹,请注意,这是不可以的,程序会在过滤到该文件夹时中断
 */
 Vector<?> v = null;
 if (fileExtension != null && !"".equals(fileExtension)) {
 v = sftp.ls("*"+fileExtension);
 }else {
 try {
  v = sftp.ls("*.*");//ls -al | grep \"^-\"只显示文件---// ls -al | grep "^d"只显示目录包括.和..
 } catch (Exception e) {
  log.info("您操作的是一个文件夹!");
 }
 }

 for (int i = 0; i < v.size(); i++) {
// log.info("fileInfos: "+v.get(i));
 String[] fileInfos = v.get(i).toString().replaceAll("\t", " ").split(" ");
 String fileName = fileInfos[fileInfos.length-1];
 log.info("fileName is: "+fileName);
 // 以下代码实现从服务器下载一个文件到 本地
 InputStream instream = sftp.get(fileName);
 OutputStream outstream = new FileOutputStream(new File(localPath+"/"+fileName));
 byte b[] = new byte[1024];
 int n;
 while ((n = instream.read(b)) != -1) {
  outstream.write(b, 0, n);
 }
 outstream.flush();
 outstream.close();
 instream.close();
 log.info("文件["+fileName+"]下载成功!---->>>>下载到目录["+localPath+"]中.");
 //下载成功后,删除文件
 if (isDelete) {
  deleteOneFile(serverPath, fileName, sftp);
  log.info("文件["+fileName+"]删除成功!");
 }
 }
 } catch (Exception e) {
 e.printStackTrace();
 } finally {
 session.disconnect();
 channel.disconnect();
 }
 }

 /**
  * 利用JSch包实现SFTP上传文件
  * @param ip 主机IP
  * @param user 主机登陆用户名
  * @param psw 主机登陆密码
  * @param port 主机ssh2登陆端口,如果取默认值,传<=0的值,如-1
  * @param localPath 本地目录
  * @param serverPath 服务器目录
  * @param fileExtension 上传文件的扩展名 格式如:'.txt'
  */
 public static void sshSftpUpload(String ip, String user, String psw, int port,String localPath, String serverPath, String fileExtension) throws Exception {
 Session session = null;
 Channel channel = null;
 JSch jsch = new JSch();
 if (port <= 0) {
 // 连接服务器,采用默认端口
 session = jsch.getSession(user, ip);
 } else {
 // 采用指定的端口连接服务器
 session = jsch.getSession(user, ip, port);
 }
 // 如果服务器连接不上,则抛出异常
 if (session == null) {
 log.info("session is null,服务器连接失败");
 throw new Exception("session is null,服务器连接失败");
 }else {
 log.info("Connected Success, ip is ["+ip+"]");
 }
 // 设置登陆主机的密码
 session.setPassword(psw);// 设置密码
 // 设置第一次登陆的时候提示,可选值:(ask | yes | no)
 session.setConfig("StrictHostKeyChecking", "no");
 // 设置登陆超时时间ms
 session.connect(960);
 try {
 // 创建sftp通信通道
 channel = (Channel) session.openChannel("sftp");
 channel.connect(1000);
 ChannelSftp sftp = (ChannelSftp) channel;
 // 进入服务器指定的文件夹
 sftp.cd(serverPath);
 // 列出服务器指定的文件列表
// Vector v = sftp.ls("*.sh");
// for (int i = 0; i < v.size(); i++) {
// System.out.println(v.get(i));
// }
 // 以下代码实现从本地上传一个文件到服务器,如果要实现下载,对换一下流就可以了
 String[] files = getLocalFileNameArray(localPath);//获取所有文件名数组
 for (int i = 0; i < files.length; i++) {
 String fileName = files[i];
 if (fileExtension != null && !"".equals(fileExtension)) {//如果扩展名不为空,则上传该路径下指定扩展名的文件
  if (fileName.endsWith(fileExtension)) {
  OutputStream outstream = sftp.put(fileName);//要上传到服务器的文件,可以另外设个名字,也可以用本地的名称
  InputStream instream = new FileInputStream(new File(localPath+"/"+fileName));//读取本地文件
  byte b[] = new byte[1024];
  int n;
  while ((n = instream.read(b)) != -1) {
  outstream.write(b, 0, n);
  }
  outstream.flush();
  outstream.close();
  instream.close();
  log.info("文件["+localPath+"/"+fileName+"]上传成功!---->>>>上传到目录["+serverPath+"]中.");
  }else {
  log.info("警告:文件["+fileName+"]不是指定类型["+fileExtension+"]的文件");
  }
 }else {//如果扩展名为空,则上传该路径下的所有文件
  OutputStream outstream = sftp.put(fileName);//要上传到服务器的文件,可以另外设个名字,也可以用本地的名称
  InputStream instream = new FileInputStream(new File(localPath+"/"+fileName));//本地文件
  byte b[] = new byte[1024];
  int n;
  while ((n = instream.read(b)) != -1) {
  outstream.write(b, 0, n);
  }
  outstream.flush();
  outstream.close();
  instream.close();
  log.info("文件["+fileName+"]上传成功!---->>>>上传到目录["+serverPath+"]中.");
 }
 }
 } catch (Exception e) {
 e.printStackTrace();
 } finally {
 session.disconnect();
 channel.disconnect();
 }
 }

 /**
  * 利用JSch包实现SFTP下载、上传文件(该方法暂不适用)
  * @param ip 主机IP
  * @param user 主机登陆用户名
  * @param psw 主机登陆密码
  * @param port 主机ssh2登陆端口,如果取默认值(默认值22),传-1
  * @param privateKey 密钥文件路径
  * @param passphrase 密钥的密码
  *
  */
 public static void sshSftp(String ip, String user, String psw ,int port ,String privateKey ,String passphrase) throws Exception{
  Session session = null;
  Channel channel = null;
  JSch jsch = new JSch();
  //设置密钥和密码
  if (privateKey != null && !"".equals(privateKey)) {
   if (passphrase != null && "".equals(passphrase)) {
    //设置带口令的密钥
    jsch.addIdentity(privateKey, passphrase);
   } else {
    //设置不带口令的密钥
    jsch.addIdentity(privateKey);
   }
  }
  if(port <=0){
   //连接服务器,采用默认端口
   session = jsch.getSession(user, ip);
  }else{
   //采用指定的端口连接服务器
   session = jsch.getSession(user, ip ,port);
  }
  //如果服务器连接不上,则抛出异常
  if (session == null) {
   throw new Exception("session is null");
  }
  //设置登陆主机的密码
  session.setPassword(psw);//设置密码
  //设置第一次登陆的时候提示,可选值:(ask | yes | no)
  session.setConfig("StrictHostKeyChecking", "no");
  //设置登陆超时时间
  session.connect(30000);
  try {
   //创建sftp通信通道
   channel = (Channel) session.openChannel("sftp");
   channel.connect(1000);
   ChannelSftp sftp = (ChannelSftp) channel;
   //进入服务器指定的文件夹
   sftp.cd("domains");
   //列出服务器指定的文件列表
   Vector<?> v = sftp.ls("*.txt");
   for(int i=0;i<v.size();i++){
    log.info(v.get(i));
   }
   //以下代码实现从本地上传一个文件到服务器,如果要实现下载,对换以下流就可以了
   OutputStream outstream = sftp.put("1.txt");
   InputStream instream = new FileInputStream(new File("c:/print.txt"));
   byte b[] = new byte[1024];
   int n;
   while ((n = instream.read(b)) != -1) {
    outstream.write(b, 0, n);
   }
   outstream.flush();
   outstream.close();
   instream.close();
  } catch (Exception e) {
   e.printStackTrace();
  } finally {
   session.disconnect();
   channel.disconnect();
  }
 }

 //***************Utils******************//
 /**
 * 读取指定路径下的所有文件
 * @param localPath 指定路径
 * @return String[] 文件名数组
 */
 public static String[] getLocalFileNameArray(String localPath){
 File diskFile = new File(localPath);
 String[] fileNameList = diskFile.list() ;
 if(fileNameList!=null){
 //按照文件名倒序排序
 Arrays.sort(fileNameList,Collections.reverseOrder());
 }
 return fileNameList ;
 }

 /**
 * 删除指定目录的,指定扩展名的远程文件
 * @param directory 要删除文件的目录
 * @param sftp ChannelSftp实体
 * @param fileExtension 文件扩展名(删除远程文件,扩展名不能为空)
 */
 public void deleteAll(String directory, ChannelSftp sftp, String fileExtension) {
  try {
  sftp.cd(directory);
  Vector<?> v = null;
  if (fileExtension !=null && "".equals(fileExtension)) {
  v=sftp.ls("*"+fileExtension);
 }else {
// v=sftp.ls("");//此处有风险
 log.warn("FileExtension is not null! Please Check");
 }
  for (int i = 0; i < v.size(); i++) {
  String[] fileInfos = v.get(i).toString().replaceAll("\t", " ").split(" ");
 String fileName = fileInfos[fileInfos.length-1];
   sftp.rm(fileName);
  }
  } catch (Exception e) {
  e.printStackTrace();
  }
 }

 /**
 * 删除单个文件
 *
 * @param directory
 *   要删除文件所在目录
 * @param deleteFile
 *   要删除的文件
 * @throws Exception
 */
 public static void deleteOneFile(String directory, String deleteFile, ChannelSftp sftp) throws Exception {
 sftp.cd(directory);
 sftp.rm(deleteFile);
 } 

}

这就是整个工具的内容了。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • Java实现后台发送及接收json数据的方法示例

    本文实例讲述了Java实现后台发送及接收json数据的方法.分享给大家供大家参考,具体如下: 本篇博客试用于编写java后台接口以及两个项目之间的接口对接功能: 具体的内容如下: 1.java后台给指定接口发送json数据 package com.utils; import java.io.BufferedReader; import java.io.InputStreamReader; import java.io.OutputStreamWriter; import java.net.Htt

  • java利用phantomjs进行截图实例教程

    前言 最近工作中遇到一个需求,需要实现截图功能,断断续续查找资料.验证不同的实现方法终于算基本搞定了页面截图,因为中间过程曲折花费较多时间,分享出来帮助大家快速实现截图 为什么选用phantomjs进行截图 截图可以实现的方式有很多,比如: selenium HtmlUnit Html2Image...and so on但是这些实现的截图效果都不好.selenium只能实现截屏,不能截取整个页面,而HtmlUnit.Html2Image对js的支持效果并不好,截下来的图会有很多空白.phanto

  • Java实现的JSONUtil工具类与用法示例

    本文实例讲述了Java实现的JSONUtil工具类与用法.分享给大家供大家参考,具体如下: import java.util.HashMap; import java.util.Map; import com.alibaba.druid.util.StringUtils; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; public class JSONUtils { /** * Bean对象转J

  • java的JsonObject对象提取值方法

    实例如下所示: import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONArray; import com.alibaba.fastjson.JSONObject; import io.swagger.models.auth.In; import java.io.IOException; import java.security.KeyManagementException; import java.security.N

  • Java 把json对象转成map键值对的方法

    工具方法: 本文的目的是把json串转成map键值对存储,而且只存储叶节点的数据 maven 引用jar包版本: <dependency> <groupId>org.json</groupId> <artifactId>json</artifactId> <version>20090211</version> </dependency> 工具类: package com.baofoo.admin.test; /

  • 解决JavaWeb读取本地json文件以及乱码的问题

    最近在开发项目的时候遇到一个问题,在myecilpes上使用googlede gson读取项目中的json文件成功,然后把项目发布到tomcat上再使用同样的方法,会提示"系统找不到指定的路径" 文件放在src/config/下 JsonParser parser = new JsonParser(); JsonObject object = (JsonObject) parser.parse(new FileReader("config/Test.json"));

  • Java读取本地json文件及相应处理方法

    如下所示: //读取json文件地址 /* String path = getClass().getClassLoader().getResource("menu.json").toString(); path = path.replace("\\", "/"); if (path.contains(":")) { path = path.replace("file:/", ""); }

  • java 读取excel文件转换成json格式的实例代码

    需要读取excel数据转换成json数据,写了个测试功能,转换正常: JSON转换:org.json.jar 测试类:  importFile.java: package com.siemens.util; import java.util.ArrayList; import java.util.List; import org.json.JSONException; import org.json.JSONObject; import org.apache.poi.ss.usermodel.R

  • 详解java爬虫jsoup解析多空格class数据

    在使用jsoup爬取其他网站数据的时候,发现class是带空格的多选择,如果直接使用doc.getElementsByClass("class的值"),这种方法获取不到想要的数据. 1.问题描述: 在使用jsoup爬取其他网站数据的时候,发现class是带空格的多选择,如果直接使用doc.getElementsByClass("class的值"),这种方法获取不到想要的数据. 爬取网站页面结构如下: 2.其中文章列表的div为:<div class="

  • Java执行JS脚本工具

    Java 执行 JS 脚本工具 用途:为了便于系统扩展,提供了 JS 脚本的功能,可以通过在系统中执行脚本来获得更复杂的功能. 例如:系统提供了一个接口,这个接口不必非的有实现类,而是可以通过JS来实现这个接口的方法,在运行时载入JS脚本去实现.只要能融会贯通,可用的地方还是很多的. 先看最基础的一个工具类 实际上有这么一个工具类就足够了,后面讲的例子也是基于这个工具类的. 这段代码的原理: 由于在 Java 的 javascript 引擎中,常用的List,Map等复杂对象的 属性值 不能在

随机推荐