1. 程式人生 > >sshxcute --java遠端執行linux/unix命令的工具類

sshxcute --java遠端執行linux/unix命令的工具類

原文地址:https://www.ibm.com/developerworks/cn/opensource/os-sshxcute/

-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

通常的使用場景

JSch 是 SSH2 的一個純 Java 實現。它可以連線到一個 sshd 伺服器,使用埠轉發,X11 轉發,檔案傳輸等等。但是這個類庫畢竟偏向底層,上手與實際執行起來不太方便,sshxcute 框架正是基於 JSch 封裝的,提供了更為便捷的 API 藉口,更加靈活實用的功能,從而可以讓開發與測試人員更加得心應手的使用。sshxcute 是一個框架,它允許工程師利用 Java 程式碼通過 SSH 連線遠端執行 Linux/UNIX 系統上的命令或者指令碼,這種方式不管是針對軟體測試還是系統部署,都簡化了自動化測試與系統環境部署的步驟。

SSHXCUTE 的設計旨在:

  • 最小的系統需求 – 僅僅開啟 SSH 連線即可。
  • 易用性 – 工程師利用 Java 程式碼執行命令或指令碼。
  • 內建命令 / 指令碼任務執行功能。
  • 易擴充套件 – 使用者可以自定義任務型別並集成於 sshxcute 框架。

下面的章節分別介紹瞭如何使用 sshxcute 框架,如何配置它的執行時引數選項以及如何利用該框架的 Java API 進行擴充套件從而從容應用到自己的專案中。

sshxcute 框架使用指南

配置

首先,必須確保 JDK 版本在 5.0 以上,然後需要確認 sshxcute.jar 已經在環境變數中的 $CLASSPATH 中,然後才可以開始。如果是用整合開發環境(IDE)下,必須將 sshxcute.jar 加入專案構建路徑下,接下來展示的是如何在 Eclipse IDE 中配置 Java Build Path。右鍵單擊專案 > 屬性 > Java 構建路徑。更多的配置步驟請在網際網路上搜索。

圖 1. Eclipse 中配置 Java 構建路徑步驟
圖 1. Eclipse 中配置 Java 構建路徑步驟

初始化準備工作

通常通過 SSH 協議在遠端 Linux/UNIX 系統上執行命令時,以下是必須的步驟:

  1. 開啟 SSH 連線客戶端(例如 Putty,SSHClient 等)
  2. 輸入 IP
  3. 輸入使用者名稱、密碼登入
  4. 登入成功後輸入執行命令
  5. 斷開登入

前三個步驟可以通過 sshxcute 的 Java API 模擬實現:

清單 1. 登入遠端主機
1 2 3 4 5 6 // 新建一個 ConnBean 物件,三個引數依次是 ip 地址、使用者名稱、密碼 ConnBean cb = new ConnBean("ip ", "username","password");
// 將上面新建的 ConnBean 作為引數傳遞給 SSHExec 的靜態單例方法,得到一個 SSHExec 的例項 ssh = SSHExec.getInstance(cb); // 利用上面得到的 SSHExec 例項連線主機 ssh.connect();

第五步斷開登入的實現如下:

清單 2. 斷開遠端主機
1 ssh.disconnect();

第四步是 sshxcute 框架的核心所在——自動執行命令或者指令碼。接下來的部分將主要介紹這個主題。

遠端執行命令

這是 sshxcute 框架內自帶的任務型別,接下來 3.4 小節講到的遠端執行 shell 指令碼也是自帶的任務型別。先來看一段程式碼再來詳細解釋。如果讀者已經具備了面向物件程式設計經驗,那麼下面的內容將會被發現如此熟悉與簡單。

清單 3. 遠端執行命令
1 2 CustomTask sampleTask = new ExecCommand("echo 123"); ssh.exec(sampleTask);

ExecCommand 類繼承了 CustomTask 類,我們新建一個 ExecCommand 物件,他的引用型別是 CustomTask。下圖展示了 ExecCommand、ExecShellScript 和 CustomTask 的類圖,從中可以看出他們的關係,ExecCommand、ExecShellScript 是 CustomTask 的子類。

圖 2. sshxcute 框架類圖
圖 2. sshxcute 框架類圖

ExecCommand 的建構函式只接收一個字串型別變數。注意 ExecCommand 可以執行多個命令,只需要用分隔符“,”分隔各個命令即可。例如:

清單 4. 遠端順序執行多個命令
1 CustomTask sampleTask = new ExecCommand("echo 123", "echo 456, "echo 789");

ExecCommand 的建構函式是:

public ExecCommand(String...args)

把 ExecCommand 物件作為引數傳入 SSHExec.exec(CustomTask) 方法,這樣就可以直接執行命令了。

遠端執行 shell 指令碼

遠端執行 shell 指令碼幾乎與 3.3 小節的遠端執行命令一致。例如,如果想執行 /home/tsadmin 路徑下的 sshxcute_test.sh 指令碼,並且帶兩個引數“hello world”,可以這樣呼叫:

清單 5. 遠端執行 shell 指令碼
1 2 3 CustomTask ct1 = \ new ExecShellScript("/home/tsadmin","./sshxcute_test.sh","hello world"); ssh.exec(ct1);

ExecShellScript 的建構函式是:

public ExecShellScript(String workingDir, String shellPath, String args)

public ExecShellScript(String shellPath, String args)

public ExecShellScript(String shellPath)

其中 workingDir 代表執行前先切換到路徑,shellPath 代表指令碼執行路徑,args 代表引數列表。

上傳檔案到遠端主機

通常會遇到一種情況,要執行的指令碼是存在於本地的,必須先把其上傳到遠端的主機上。這項工作 sshxcute 同樣可以為完成,例如,想要把 c:/data2/data 目錄下的所有檔案上傳到遠端機器上的 /home/tsadmin 目錄下,可以

清單 6. 上傳資料夾下全部檔案到遠端主機
1 ssh.uploadAllDataToServer("c:/data2/data", "/home/tsadmin");

如果想只上傳單一檔案,例如只上傳路徑下的 c:/data/sshxcute_test.sh 到 /home/tsadmin,可以這樣

清單 7. 上傳單一檔案到遠端主機
1 ssh.uploadSingleDataToServer("c:/data/sshxcute_test.sh","/home/tsadmin");

這裡要注意下,必須把順序搞清楚,上傳的步驟必須在執行前,連線成功後。例如:

清單 8. 執行順序注意,上傳指令碼後才能執行成功
1 2 3 4 CustomTask ct1 = new ExecShellScript("/home/tsadmin","./sshxcute_test.sh","hello world"); ssh.connect();  // 連線成功後 ssh.uploadSingleDataToServer("data/sshxcute_test.sh", "/home/tsadmin"); ssh.exec(ct1);  // 執行前

當然這裡不僅僅限於必須執行指令碼,如果你只想上傳檔案可以單獨執行 uploadSingleDataToServer() 或者 uploadSingleDataToServer() 方法。

結果物件

所有的任務型別,包括上面已經講解過的 ExecCommand、ExecShellScript 還有接下來會說明的自定義類任務,在執行完畢後,都會返回一個結果物件(Result)。這個結果物件包含了命令或者指令碼的返回程式碼(return code)、標準輸入、錯誤輸出。還有它會提供一個布林型別的 isSuccess 變數供程式設計師判斷是否任務執行成功,在 4.1 章節判定任務成功與否的過濾關鍵字,將會詳細介紹 sshxcute 是如何判斷任務執行成功與否的,這個判斷的條件也是可以配置的。

例如,SSHExec.exec(CustomTask) 總會返回一個結果物件,可以利用自己的邏輯程式碼列印一些有用的資訊。程式碼相見清單 9

清單 9. 根據結果物件列印輸出或者錯誤資訊
1 2 3 4 5 6 7 8 9 10 11 Result res = ssh.exec(task); if (res.isSuccess) { System.out.println("Return code: " + res.rc); System.out.println("sysout: " + res.sysout); } else { System.out.println("Return code: " + res.rc); System.out.println("error message: " + res.error_msg); }

小結

下面的例子囊括上面所有的技術話題,做個小結。假設需求是在遠端的 Linux 伺服器(ip 是 9.125.71.115)上執行一個 shell 指令碼—— sshxcute_test.sh。它的內容見清單 10。

清單 10. sshxcute_test.sh 指令碼內容
1 2 3 4 5 6 7 8 9 10 11 12 13 #!/bin/bash if [ $# -ne 2 ];then echo "usage: sshxcute_test.sh username password" exit 1 fi export USERNAME=$1 export PASSWORD=$2 if [ "$USERNAME" = "hello" -a "$PASSWORD" = "world" ];then echo "Login success" exit 0 fi echo "Login falied" exit 2

實現程式碼見清單 11。

清單 11. 一個具體例項的實現程式碼
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 // 新建一個 SSHExec 引用 SSHExec ssh = null; // 下面所有的程式碼都放在 try-catch 塊中 try { // 例項化一個 ConnBean 物件,引數依次是 IP 地址、使用者名稱和密碼 ConnBean cb = new ConnBean("9.125.71.115", "username","password"); // 將剛剛例項化的 ConnBean 物件作為引數傳遞給 SSHExec 的單例方法得到一個 SSHExec 物件 ssh = SSHExec.getInstance(cb); // 新建一個 ExecCommand 物件,引用必須是其繼承的 CustomTask 類 CustomTask ct1 = new ExecCommand("chmod 755 /home/tsadmin/sshxcute_test.sh"); // 新建一個 ExecShellScript 物件,引用必須是其繼承的 CustomTask 類 CustomTask ct2 = new ExecShellScript("/home/tsadmin","./sshxcute_test.sh" ,"hello world"); // 連線伺服器 ssh.connect(); // 上傳 shell 指令碼到 /home/tsadmin 目錄 ssh.uploadSingleDataToServer("data/sshxcute_test.sh", "/home/tsadmin"); // 執行命令 ssh.exec(ct1); // 執行指令碼並且返回一個 Result 物件 Result res = ssh.exec(ct2); // 檢查執行結果,如果執行成功列印輸出,如果執行失敗,列印錯誤資訊 if (res.isSuccess) { System.out.println("Return code: " + res.rc); System.out.println("sysout: " + res.sysout); } else { System.out.println("Return code: " + res.rc); System.out.println("error message: " + res.error_msg); } } catch (TaskExecFailException e) { System.out.println(e.getMessage()); e.printStackTrace(); } catch (Exception e) { System.out.println(e.getMessage()); e.printStackTrace(); } finally { ssh.disconnect();  }

相關推薦

sshxcute --java遠端執行linux/unix命令工具

原文地址:https://www.ibm.com/developerworks/cn/opensource/os-sshxcute/ ----------------------------------------------------------------------

java 遠端執行 linux 命令

Maven: <!-- https://mvnrepository.com/artifact/ch.ethz.ganymed/ganymed-ssh2 --> <dependency> <groupId>ch.e

SSH遠端執行Linux Shell命令

使用強大的paramiko Linux伺服器需要注意防火牆設定和SSH的開啟 注意執行的shell命令前提是Linux系統上有的 #!/usr/bin/python #coding=utf-8 import paramiko import threading import

java遠端呼叫linux命令或者指令碼

   Java通過SSH2協議執行遠端Shell指令碼(ganymed-ssh2-build210.jar)   使用步驟如下: 1.導包 官網下載: http://www.ganymed.ethz.ch/ssh2/ maven座標: [java] view plain copy print?

JAVA百科---執行緒池建立工具

一、前言 在《阿里巴巴Java開發手冊》中提到: 建立執行緒或執行緒池時請指定有意義的執行緒名稱,方便出錯時回溯。 執行緒資源必須通過執行緒池提供,不允許在應用中自行顯式建立執行緒。 執行緒池不允許使用 Executors 去建立,而是通過 ThreadPoolExe

Java執行緒之併發工具

一、總論:在JDK中提供了幾種併發工具類 1)CountDownLatch(同步倒數計數器:等待多執行緒(或者多步驟)完成) 2)CyclicBarrier(迴圈屏障:同步屏障) 3)Semaphore(訊號量:控制併發程序數) 主要參考資料

java遠端連線linux執行指令碼命令

1.maven的POM.xml需要配置包 <dependency> <groupId>ch.ethz.ganymed</groupId> <artifactId>ganymed-ssh2</artifac

Java 執行系統命令工具

row com enc log tostring mha comm span onf 依賴jar <!-- 可以在JVM中可靠地執行外部進程的庫。 --> <dependency> <

java 執行linux 本地命令

public static String executeCMD(final String[] cmdStrArr) { StringBuffer resBuf = new StringBuffer(); Runtime rt = Ru

Java程式執行Linux命令

java程式中要執行linux命令主要依賴2個類:Process和Runtime 首先看一下Process類: ProcessBuilder.start() 和 Runtime.exec 方法建立一個本機程序,並返回 Process 子類的一個例項,   該例項可

java遠端執行shell命令

1、連線伺服器,執行shell的方法package com.shishike.susie.utility; import java.io.BufferedReader; import java.io.InputStreamReader; import java.util.P

大技霸教你遠端執行Linux指令碼和命令

如果現在需要在 Linux 伺服器上執行一系列命令(比如搭建 LNMP 環境)我應該會第一時間想到想辦法寫個 Shell 指令碼,然後扔上去執行以下看看結果。 然而一貫懶惰的我並不想這麼去執行 Shell 和一些重複命令。所以俺尋思可以有個方法本地直接在伺服器端執行指令碼,尋思生異端,這時候有某大技霸告訴我

Linux常用命令工具安裝

1、wget:下載工具 yum -y install wget 2、vim:文字編輯 yum -y install wget 3、ifconfig:顯示或設定網路裝置 yum -y install net-tools 4、 git:Git工具 yum -

Linux/Unix 命令列選項前的一橫(-)、兩橫(--)和沒橫

在使用 Linux/Unix 命令的時候,我們可能會對其五花八門的選項表示形式感到困惑,比如: ls -l ls --size ps aux 我們可以發現,這三個命令的選項都有不同的風格,有的是一個

Python執行Linux系統命令的4種方法

http://www.jb51.net/article/56490.htm (1) os.system 僅僅在一個子終端執行系統命令,而不能獲取命令執行後的返回資訊 複製程式碼程式碼如下: system(command) -> exit_status  Exe

ssh 遠端執行多個命令,有萬用字元要使用雙引號,沒有則可以不用

#!/bin/sh  for i in {2..25}  do         ip=10.161.21.$i         echo $ip         t=`ssh [email protected]$ip    "ls /home/unicom

Macbook Pro 安裝 Java JDK8 9 10 11 命令工具

Macbook 安裝 Java JDK8 9 10 11。Macbook 安裝 Java JDK8 9 10 11,新手第一次買蘋果Macbook需要配置Java開發環境,安裝JDK。步驟:1、安裝命令工具homebrew,在蘋果終端裡完成:命令直接複製到終端視窗,回車/usr/bin/ruby -e "$(

Runtime exec 執行linux find 命令時 引號問題

環境: Distributor ID: CentOS、java linux 中使用find 命令 find /opt/test -name '*abc' 假設在這個命令在終端中可以找到 123abc 但是用java程式中  String str="find /opt/tes

java遠端操控linux,windows,三層交換機。對其進行關機和重啟

最近有幾個需求,對linux,windows伺服器和三層交換機進行重啟和關機。 Linux: 首先說原理:對linux是通過ssh協議,賬號密碼登陸後使用命令。直接上程式碼。使用jsch-0.1.48.jar包 import java.io.BufferedReader;

java遠端呼叫linux上jar包

首先在遠端伺服器上編寫一個測試指令碼test.sh,並賦予可執行許可權:chmod +x test.sh#!/bin/bash echo $1$1是指令碼傳進來的第一個引數,現在列印一下傳進來的第一個引數。在pom中新增依賴<dependency>    <