機器人助手 - 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去實現測試。