機器人助手 - Hubot

2017/10/24 學習筆記 Node.js bot

機器人助手 - Hubot

Hubot是GitHub開源的一個小程序,是一個可以互動的框架,並且可以非常方便簡單的實施擴充功能。他是基於node.js所開發的,可以幫助下達指令與查找資源,可串接LINE、Messenger等通訊軟體,實現一個ChatBot。因為他具有很大的彈性,程式碼可以用Javascript或Coffee開發,目前我主要利用Hubot幫助我部署程式與各種新技術測試。

輕鬆架設

要使用Hubot首先需要有Node.js跟npm,如果沒有可以參考這篇NPM 套件管理工具,可以用以下指令測試是否安裝成功

# 查看 Node.js 版本
node -v

# 查看 npm 版本
npm -v

接下來就直接安裝Hubot

npm install -g yo generator-hubot

再來創建一個你的Hubot機器人專屬的資料夾,並生成機器人

mkdir bot
cd bot
yo hubot

下完指令後會出現下圖 底下會出現一些設定,把Owner、Bot Name、Description填好,Bot adapter這邊先填campfire。接下來,只要下一個指令,我們的Hubot就會啟動了

.\bin\hubot

開啟後會出現一個問答的介面,但不管你輸入甚麼他都不會回答你,因為預設只有幾個關鍵詞他才會回應。比如你要喊他的名字跟說”PING”,他才會回你”PONG”

# 前面名字請改成你的Bot Name
botname ping
botname > PONG

擴充功能

請開啟Script資料夾並新增一個Hello.js,並貼上以下coffee程式碼

module.exports = (robot) ->
  robot.respond /hello/i, (res) ->
    res.send "你好"

再重新啟動Hubot,並下”BotName hello”指令,他就會回”你好”囉

# 前面名字請改成你的Bot Name
botname hello
botname > 你好

非常簡單吧,對Javascript比較熟的也可以用JS寫

module.exports = function(robot){	
 robot.respond(/(hello)/, function(response){ 
    	response.send("你好");  
    });   
}

兩個是做一樣的事,另外如果覺得前面需要叫他名字很煩,可以把respond改成hear,這樣只要聽到hello,他就會回”你好”。

所以會寫Script很重要,如果你之前有寫過Node.js的專案或是相關的技巧,只要是Node.js能做到的事Hubot都可以做到,很方便吧。

利用Adapter與Slack介接

在bot資料夾執行指令

npm install hubot-slack --save

然後去Slack網頁新增App,選擇Hubot,並複製他給你的Token,之後執行這段指令,Token替換成你剛剛複製那個

HUBOT_SLACK_TOKEN=xoxb-119873885123-yXyhtfbW4XJTZb5ZMaFFaxm3 ./bin/hubot --adapter slack

之後就可以跟本機的Hubot透過Slack互動了喔

透過Hubot下CommandLine指令

技術上是利用Node.js裡面的Child Process下CommandLine指令。Child Process可以串接很多功能,把指令一個一串起來,有點像Batch的感覺。Child Process的詳細功能可以參考Node.js v8.7.0 Documentation。以下是我的Deploy Script,用來編譯Grails專案”kgi”並部屬到JBOSS

Deploy.js

exec = require("child_process").exec;
spawn = require("child_process").spawn;
kgi = 'grails clean-all && grails ref-dep && grails war'

module.exports = function(robot){	    
    robot.respond(/(deploy kgi)/i, function(response){
    			cwd_front = process.env.EBILL_FRONT;
    			cwd_target1 = process.env.EFRONT_TARGET;
    			cwd_deploy = process.env.EBILL_WILDFLY_DEPLOYMENTS;

    			response.send("ok,just wait a second^^");   							
					execkgi= exec(kgi,{cwd:cwd_front},function(err,res,body){
    				if(!err){
    					response.send("Build efront.war finished,deploying to wildfly");
    					del = exec('del efront.*',{cwd:cwd_deploy},function(err,res,body){
    					 		  execopy = spawn('xcopy',['efront.war',cwd_deploy,'/Y'],{cwd:cwd_target1});
    						  	response.send("deploy efront successfully,congratulation^^");
    							});
    					}else{
    						 console.log(err+body);  					
    					}
    			});   				
    }); 
     robot.hear(/(kill)/, function(response){     	
    			  execkgi.kill();
    				execopy.kill();
    				del.kill();
    				response.send("OK");  
    });
}
process.on('exit', function () {
    execopy.kill();
    execkgi.kill();
    del.kill();
});

一開始先定義Child Process跟一條Grails在CommandLine下的編譯指令,接下來在module寫當Hubot聽到deploy kgi所執行的功能與回應。respond中首先是執行CommandLine的工作目錄設定,這邊我自行定義三個環境變數

  • EBILL_FRONT:專案資料夾,執行編譯指令的目錄
  • EFRONT_TARGET:編譯完成後生成.WAR檔的資料夾
  • EBILL_WILDFLY_DEPLOYMENTS:JBOSS佈署.WAR檔的資料夾

我讓Hubot先回應”ok,just wait a second^^”,再執行編譯Grails的Child Process,程式碼結構大概是這樣

exec(CommandLine指令,{cwd:執行的工作資料夾},function(err,res,body){
  # callback function
});
# ascync function

因為JavaScript是ascync的,所以需要把成功後你才要做的事寫到callback function中。如果寫在ascync function這邊,則不等待CommandLine指令跑完,這邊的ascync function就會開始跑。所以我在callback function中寫入另一個Child Process,等到編譯完成後,複製我生成在TARGET資料夾的.WAR檔到JBOSS deployment的資料夾,這樣完成JBoss的佈署。

成果

結合Slack Adapter與Deploy Script,只要手機下載Slack APP並加入Hubot好友,就可以利用手機對他說”BotName deploy kgi”,他就會幫我在本機編譯程式碼並部署至Jboss,實現遠端遙控部署。

總結

Child Process實行任何你需要在本機上下的指令,搭配adapter讓你從LINE上或Skype上對Hubot說話,這兩者結合就可以讓你實現遠端遙控電腦的功能,而且非常彈性化好編寫。我現在在發現可能可以互相串連的技術時,都會嘗試利用Hubot去實現測試。






Search

    Post Directory