sftp上傳文件到linux服務器上(ssh驗證)

需求:
以前,手動上傳配置文件到服務器,然後手工複製到另外一臺服務器上,然後登陸SSH Secure File Transfer Client客戶端,執行相關shell命令號
現在這些操作需要一鍵完成,即文件複製到另一臺服務器,登陸ssh客戶端,切換用戶,執行導入命令行
解決辦法:

  1. 獲得應用程序所在的機器用戶名和密碼,然後執行shell腳本完成以上操作
    未採用:因爲運維不提供應用服務器的用戶名和密碼
  2. 直接連接另一臺服務器,執行復制文件,然後執行shell腳本(採取
    要上傳文件到linux服務器上,使用FTP協議,公司linux服務器上需要ftp客戶端需要安全驗證,比較麻煩,所以想到使用sftp來解決,sftp是基於ssh的安全協議的ftp協議,Java中有JSch包來實現連接服務器。

第一步:下載JSch包,請從官網下載它:http://www.jcraft.com/jsch/
第二步:新建FtpsFileList.java文件

//只有上傳方法,也可以有下載文件方法
public class FtpsFileList {
    private static final Logger LOG = LoggerFactory.getLogger(FtpsFileList.class);

    //將本地的dirFile這個文件複製到遠程服務器上的desFile文件夾下
    public static void loadFile(String host, int port, String username, final String password, String dirFile,String desFile) {
        ChannelSftp sftp = null;
        Channel channel = null;
        Session sshSession = null;
        try {
            JSch jsch = new JSch();//創建一個jsch對象
            jsch.getSession(username, host, port);
            // 根據用戶名,主機ip,端口獲取一個Session對象
            sshSession = jsch.getSession(username, host, port);
            //設置密碼
            sshSession.setPassword(password);
            Properties sshConfig = new Properties();
            sshConfig.put("StrictHostKeyChecking", "no");
            // 爲Session對象設置properties
            sshSession.setConfig(sshConfig);
            sshSession.connect();
            LOG.debug("Session connected!");
            // 打開SFTP通道
            channel = sshSession.openChannel("sftp");
            // 建立SFTP通道的連接
            channel.connect();
            LOG.debug("Channel connected!");
            sftp = (ChannelSftp) channel;

            //InputStream is = sftp.get("/ftp/re/20140713.dat");
            InputStream fis = new FileInputStream(new File(dirFile));
            //文件上傳(通過inputstream流來實現)  詳見https://www.cnblogs.com/longyg/archive/2012/06/25/2556576.html
            sftp.put(fis,desFile);
            LOG.info("文件複製到服務器成功!\r");

        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            closeChannel(sftp);
            closeChannel(channel);
            closeSession(sshSession);
        }
    }

    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();
            }
        }
    }
}

調用方式:

FtpsFileList.loadFile("10.31.92.70", 22, "serviceop", "115LbUrAbEsZw","/nfsc/qhcs-ansir-stg1/ansir/HanLP/xiaodai/loan-freebase.ttl","/wls/serviceop/virtuoso_script/loanXD.ttl");
logger.info("ttl文件複製成功");

到這一步,已經完成上傳文件到linux服務器上
第三步:寫好shell腳本(關鍵核心),這一步學習了好多東西,發現shell命令挺好玩的

#!/usr/bin/expect
spawn ssh serviceop@10.31.92.70
set timeout 2
expect "password:"
send "115LbUrAbEsZw\r"
expect "*]#"
set password "wuxin952"
spawn su root
expect "password:"  
send "wuxin952\r" 
expect "#"
send "/wls/serviceop/virtuoso-opensource/home/bin/isql localhost:13002\r" 
send "DB.DBA.TTLP_MT(file_to_string_output('/wls/serviceop/virtuoso_script/loan.ttl'),'','http://www.xiaowei.com');\r"
interact

註釋:因爲需要交互式輸入密碼,所以選擇使用expect命令環境來執行
具體釋義見:

第四步:java代碼調用shell腳本,代碼如下,
Process類是一個抽象類,用於定義一個本地進程,Runtime.getRuntime().exec(sh)返回一個進程對象
具體見:process

//授予權利給shell腳本呢
Process ps1=Runtime.getRuntime().exec("chmod 777 /nfsc/qhcs-ansir-stg1/ansir/HanLP/xiaodai/bash_scp.sh");
//等待當前線程執行完,等待返回process類對象表示的進程結束
ps1.waitFor();
logger.info("chmod命令執行結束");

BufferedReader br1 = new BufferedReader(new InputStreamReader(ps1.getInputStream()));
while ((line = br1.readLine()) != null) {
    logger.info("chmod命令結果:"+line);
}
//實際調用使用expect 文件
Process ps2=Runtime.getRuntime().exec("expect /nfsc/qhcs-ansir-stg1/ansir/HanLP/xiaodai/bash_scp.sh");
ps2.waitFor();
logger.info("expect命令執行結束");

BufferedReader br2 = new BufferedReader(new InputStreamReader(ps2.getInputStream()));
while ((line = br2.readLine()) != null) {
    logger.info("expect命令結果:"+line);
}

String result = sb.toString();
logger.info("expect整理結果爲:"+result);

後續shell命令見下一篇博客

發佈了63 篇原創文章 · 獲贊 17 · 訪問量 4萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章