【实现】树莓派开机自动向微信发消息报告ip地址(无第三方代理)
可能不少有樹(shù)莓派的小伙伴都遇到過(guò)這樣一個(gè)問(wèn)題,長(zhǎng)期不用但已經(jīng)配置過(guò)的樹(shù)莓派,剛開(kāi)機(jī)會(huì)自動(dòng)連接已經(jīng)識(shí)別的wifi,如果沒(méi)有wifi的管理密碼,手頭又沒(méi)有可以顯示的設(shè)備,手邊也沒(méi)有能讀tf卡的機(jī)器,就只能面對(duì)默默亮燈的樹(shù)莓派望洋興嘆了。
如果能在每次樹(shù)莓派開(kāi)機(jī)的時(shí)候自動(dòng)獲取連接的ip地址,并發(fā)送到自己的微信上,豈不是快捷又方便?就像這樣 ↓ ↓ ↓ ↓↓↓ ↓↓↓ ?(。???。)?
怎么實(shí)現(xiàn)呢?Please follow me~
文章目錄
- 1. 思路(可行性分析):
- 2. 獲取ip地址
- 3. 注冊(cè)企業(yè)微信號(hào)(無(wú)門(mén)檻)
- 4. 調(diào)用api發(fā)送信息
- 4.1 新建應(yīng)用
- 4.2 記住幾個(gè)關(guān)鍵信息
- 4.3 獲取access_token
- 4.4 發(fā)送信息
- 4.5 賦予文件可執(zhí)行權(quán)限并執(zhí)行編寫(xiě)的腳本
- 5. 設(shè)置開(kāi)機(jī)自動(dòng)運(yùn)行
- 6. 重啟自動(dòng)執(zhí)行不成功?
- 6.1 添加環(huán)境變量,使cron開(kāi)機(jī)能成功執(zhí)行腳本
- 6.2 添加循環(huán)判斷,在未連接時(shí)不斷檢測(cè),連接后發(fā)送消息
- 7. 成功!
- 8. 關(guān)于IP地址獲取的改進(jìn)
- 9.附:完整示例代碼:
1. 思路(可行性分析):
- 通過(guò)樹(shù)莓派shell命令,可以獲取ip地址
- 通過(guò)crontab定時(shí)任務(wù)功能,可實(shí)現(xiàn)開(kāi)機(jī)執(zhí)行特定腳本
- 企業(yè)微信號(hào)注冊(cè)很方便,提供群發(fā)api接口,只需注冊(cè)一個(gè)企業(yè)微信號(hào),成員只有自己一個(gè)人,調(diào)用api接口可以向自己發(fā)送消息
so,完全可以很方便的實(shí)現(xiàn)~
2. 獲取ip地址
這個(gè)應(yīng)該是最簡(jiǎn)單的一步了吧,為了防止后面我忘了,就寫(xiě)在前面吧。
ifconfig命令可以查看網(wǎng)絡(luò)連接狀態(tài),用|grep 192.168篩選其中包含192.168的信息(畢竟我們只需要這個(gè)192.168.x.x的地址),再用|awk -F net '{print $2}'選擇其中第一個(gè)地址,就是我們樹(shù)莓派連接的ip地址了。
即:ifconfig|grep 192.168|awk -F net '{print $2}'
ifconfig命令執(zhí)行后包含192.168.x.x的信息應(yīng)該只有兩處,第一處是我們要用的ip地址inet,第二處則是broadcast。這兩個(gè)信息都是在一行展示,所以用grep篩選后會(huì)是如下形式:
inet 192.168.1.4 netmask 255.255.255.0 broadcast 192.168.1.255
所以我們要再用awk的截取操作,我們發(fā)現(xiàn)要提取的ip地址處于兩個(gè)“net”字符之間,因此我們?cè)O(shè)置截取的分隔符為“net”,則會(huì)將這段信息截成三部分,第一部分是"i",第二部分是"192.168.1.4",第三部分是"mask 255.255…",我們要取的是第二部分,因此print $2
?
- awk使用格式為:|awk -F 分隔符 '{命令}'
- grep使用格式為:|grep 篩選內(nèi)容
3. 注冊(cè)企業(yè)微信號(hào)(無(wú)門(mén)檻)
點(diǎn)擊進(jìn)入→:企業(yè)微信官網(wǎng)
按要求注冊(cè)就行了,沒(méi)有任何門(mén)檻,非常簡(jiǎn)單,略過(guò)不提。
4. 調(diào)用api發(fā)送信息
4.1 新建應(yīng)用
在“應(yīng)用管理>應(yīng)用>自建”一欄中點(diǎn)擊“創(chuàng)建應(yīng)用”,根據(jù)提示創(chuàng)建一個(gè)應(yīng)用即可。如圖:
4.2 記住幾個(gè)關(guān)鍵信息
- 應(yīng)用ID(AgentId)
- 秘鑰(Secret) (以上兩個(gè)均可點(diǎn)進(jìn)剛才創(chuàng)建的應(yīng)用列表里找到)
- 企業(yè)ID(corpID) (在“我的企業(yè)>企業(yè)信息”最下方找到“企業(yè)ID”)
然后我們?cè)跇?shù)莓派上一個(gè)方便的目錄下,創(chuàng)建一個(gè).sh文件,比如叫作 AutoDetectIP.sh
打開(kāi)編輯,首行按規(guī)矩先輸入:
回車(chē)換行,然后我們將上述信息賦值成變量:
AgentId=xxxxx Secret=xxxxx corpId=xxxxx注1: shell賦值時(shí)等號(hào)左右不能空格!
注2: 調(diào)用時(shí)要在變量前面加“$”,如輸出AgentId:echo $AgentId
4.3 獲取access_token
需要用 get 方式請(qǐng)求網(wǎng)址,命令格式如下:
curl https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=ID&corpsecret=SECRET
其中ID和SECRET分別填寫(xiě)上面記住的企業(yè)ID和秘鑰
curl請(qǐng)求時(shí),不加參數(shù)默認(rèn)就是get請(qǐng)求,后面直接跟網(wǎng)址即可。
調(diào)用前面的變量,于是命令為:
curl https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=$corpId&corpsecret=$Secret
如果正確,會(huì)返回一串信息,其中包含我們需要的access_token和其生效時(shí)間。
我們可以把這段信息賦值給一個(gè)變量temp,于是命令又進(jìn)一步改為:
在shell腳本中反引號(hào) ` 括起來(lái)的內(nèi)容表示這是一段命令而不是字符串,也可以用$()括起來(lái),但最好用前者。
- 注意: 要區(qū)分 $(命令) 和 ${變量}
這時(shí)temp中內(nèi)容就包含了我們的access_token,接下來(lái)要截掉多與信息,依然使用前面提到的|awk操作:
觀察所給信息格式,大致如下:
如果錯(cuò)誤,返回格式大致為:
{"errcode":40001,"errmsg":"invalid credential, hint: [16051035.........], from ip: 111...., more info at https://open.work.weixin.qq.com/devtool/query?e=40001"}
如果正確,返回格式大致為:
{"errcode":0,"errmsg":"ok","access_token":".........................","expires_in":7200}
我們可以將連續(xù)的雙引號(hào)、冒號(hào)、雙引號(hào),即 “:” 作為分隔符,如果錯(cuò)誤則只能得到2部分,如果正確則能得到3部分。且第三部分中如果我們?cè)僖?“,” 作為分隔符,則其中的第一部分就是純凈的access_token。因此,我們借助條件語(yǔ)句,代碼如下:
if [ -n `echo $temp|awk -F \":\" '{print $3}'` ];thenaccess_token=`echo $temp|awk -F \":\" '{print $3}'|awk -F \",\" '{print $1}'` fi- 如果上述命令直接在控制臺(tái)或要寫(xiě)成一行輸入,則 fi 前面必須加分號(hào);
- if 后的判斷框[ ]和里面的條件語(yǔ)句必須左右留有一個(gè)空格,即 [ 的右邊和 ] 的左邊必須空一格
- 參數(shù) -n 表示如果參數(shù)長(zhǎng)度不為0,則執(zhí)行then,否則執(zhí)行else(shell中如果else下沒(méi)有命令就不能寫(xiě),不可命令留空);相反,參數(shù) -z 表示如果參數(shù)長(zhǎng)度為0,則執(zhí)行then,否則執(zhí)行else
- 雙引號(hào)前面要加轉(zhuǎn)義符 \
至此,我們得到了access_token并將其存入了變量access_token中。
4.4 發(fā)送信息
需要用post方式請(qǐng)求網(wǎng)址,并用json傳遞結(jié)構(gòu)化參數(shù):
官方文檔給出的參數(shù)示例為:
post地址為:https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=ACCESS_TOKEN
(ACCESS_TOKEN為剛獲取到的內(nèi)容)
將地址賦值給變量(要不然之后的命令太長(zhǎng)了):
用curl進(jìn)行post請(qǐng)求,并以json傳遞參數(shù),格式為:
curl -H "Content-type: application/json" -X POST -d ‘{參數(shù)}’ 網(wǎng)址
其中,參數(shù)內(nèi)容中如果要引用變量,需要先用雙引號(hào),再用單引號(hào),再用雙引號(hào)括起來(lái),然后$變量名,例如:
-X POST -d '{"touser":"@all","msgtype":"text","agentid":"'"$AgentId"'","text",{"content":"IP地址為'"$IP"'"}}'參數(shù)中,msgtype、agetid、text、content是必須包含的參數(shù),touser、toparty、totag三者至少需要包含一個(gè)
(IP變量沒(méi)定義的記得先定義,方法如第2節(jié)所述命令,格式如前述:變量名=$`命令` <反引號(hào)括起來(lái)的都是命令>)
故發(fā)送消息命令為:
curl -H "Content-type: application/json" -X POST -d '{..如上..}' $PostURL保存退出。
4.5 賦予文件可執(zhí)行權(quán)限并執(zhí)行編寫(xiě)的腳本
賦予權(quán)限:
sudo chmod +x AutoDetectIP.sh
+號(hào)代表賦予權(quán)限,-號(hào)代表剝奪權(quán)限,x表示可執(zhí)行權(quán)限,r表示可讀權(quán)限,w表示可寫(xiě)權(quán)限
執(zhí)行腳本文件:
./AutoDetectIP.sh
默認(rèn)用bash執(zhí)行,執(zhí)行時(shí)默認(rèn)檢查的是/etc、/bin等這些文件夾,一般我們用戶操作的文件夾都不再檢查范圍內(nèi),所以要用 ./ 來(lái)強(qiáng)調(diào)從本文件夾中查找文件并執(zhí)行(當(dāng)然,得先進(jìn)入文件夾,或者輸入完整路徑)
出現(xiàn)如下提示且手機(jī)收到消息(需要提前掃描企業(yè)二維碼關(guān)注企業(yè),二維碼在“我的企業(yè)>微信插件>邀請(qǐng)關(guān)注”中),則發(fā)送成功。
% Total % Received % Xferd Average Speed Time Time Time CurrentDload Upload Total Spent Left Speed 100 277 100 277 0 0 601 0 --:--:-- --:--:-- --:--:-- 602 {"errcode":0,"errmsg":"ok","invaliduser":""}5. 設(shè)置開(kāi)機(jī)自動(dòng)運(yùn)行
我們使用crontab定時(shí)任務(wù)功能來(lái)實(shí)現(xiàn)。
在控制臺(tái)終端輸入
crontab -e
即可啟動(dòng)定時(shí)任務(wù)配置文件,第一次配置會(huì)提示選擇編輯器,選擇你習(xí)慣的編輯器或者直接回車(chē)也ok,即可進(jìn)入文件進(jìn)行配置,文件默認(rèn)注釋部分就是說(shuō)明和示例,可以創(chuàng)建每隔多久運(yùn)行一次的任務(wù),只需按規(guī)則在文件后添加即可,且保存后如果機(jī)器重啟,定時(shí)任務(wù)仍然有效。
格式為:
如:
0 0 * * * /home/pi/backup.sh 表示每天00:00運(yùn)行備份程序
*/5 * * * * python /home/pi/test.py 表示每5分鐘用python運(yùn)行一次test.py程序
0 5 * * 1 sudo apt-get update -y; sudo apt-get upgrade -y 表示每周一天05:00時(shí)更新apt軟件包
- 星號(hào)(*):代表所有可能的值,例如month字段如果是星號(hào),則表示在滿足其它字段的制約條件后每月都執(zhí)行該命令操作;
- 逗號(hào)(,):可以用逗號(hào)隔開(kāi)的值指定一個(gè)列表范圍,例如,“1,2,5,7,8,9”;
- 短橫(-):可以用在整數(shù)之間表示一個(gè)范圍,例如“2-6”表示“2,3,4,5,6”;
- 斜線(/):可以用正斜線指定時(shí)間的間隔頻率,例如h位置處填“0-10/2”表示0點(diǎn)到10點(diǎn)間每?jī)尚r(shí)執(zhí)行一次。同時(shí)斜線可以和星號(hào)一起使用,例如*/10,如果用在m位置,表示每十分鐘執(zhí)行一次。
如果想要每次開(kāi)機(jī)執(zhí)行任務(wù),只需在文件最后添加:
@reboot /home/pi/AutoDetectIP.sh
這里面需要根據(jù)你之前創(chuàng)建文件的位置輸入完整路徑,即表示每次開(kāi)機(jī)自動(dòng)運(yùn)行此文件
保存退出即可。
6. 重啟自動(dòng)執(zhí)行不成功?
到這里可以說(shuō)基本已經(jīng)全部完成了??赡苡械男』锇榕d沖沖地重啟樹(shù)莓派,滿心期待的望著手機(jī),結(jié)果卻發(fā)現(xiàn)等了個(gè)寂寞。。。
怎么回事呢?
如果檢查sudo service cron status確定cron計(jì)時(shí)任務(wù)正在運(yùn)行的話,那么主要有兩個(gè)原因:
因此,針對(duì)這兩種情況我們分別進(jìn)行調(diào)整。
6.1 添加環(huán)境變量,使cron開(kāi)機(jī)能成功執(zhí)行腳本
首先我們要確定在當(dāng)前用戶執(zhí)行成功時(shí),腳本所用到的環(huán)境變量。
我們可以在腳本末尾添加一行代碼:(調(diào)試成功后記得刪掉)
echo $PATH
再次運(yùn)行,就可以得到當(dāng)前運(yùn)行所使用的環(huán)境變量,比如我的為:
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/local/games:/usr/games
那么我們只需把這些環(huán)境變量手動(dòng)添加到腳本中即可。
在腳本正文的第一行(在#!/bin/bash之下)添加如下代碼即可:
6.2 添加循環(huán)判斷,在未連接時(shí)不斷檢測(cè),連接后發(fā)送消息
我們使用shell腳本中的while循環(huán)語(yǔ)句:
while true; do (echo `ifconfig|grep 192.168`)&& break;sleep 1;done;如上,表示不斷循環(huán),直到匹配192.168的內(nèi)容非空時(shí),跳出循環(huán),循環(huán)間隔1s。
我們將此句加入腳本文件中合適位置,就可以在運(yùn)行后一直等待連接網(wǎng)絡(luò)成功的第一時(shí)間向微信發(fā)送消息。(此句至少得放在所有使用curl這樣與網(wǎng)絡(luò)相關(guān)的命令之前)
其次,為了保證啟動(dòng)時(shí)程序不影響其他啟動(dòng)內(nèi)容,或不被系統(tǒng)過(guò)快切斷,因此我們將crontab中的命令修改為nohup + 命令+ &這樣的靜默不掛起運(yùn)行方式:
控制臺(tái)輸入crontab -e進(jìn)入編輯定時(shí)任務(wù),將原來(lái)的命令修改為:
7. 成功!
至此,所有步驟都結(jié)束了。我們就可以在每次樹(shù)莓派開(kāi)機(jī)時(shí),通過(guò)微信自動(dòng)收到所連接的ip地址消息提示了。
8. 關(guān)于IP地址獲取的改進(jìn)
上面關(guān)于本機(jī)IP地址的操作主要有兩個(gè),一是通過(guò)是否包含“192.168”字段來(lái)判斷是否連接wifi,二是通過(guò)|grep、|awk等操作截取純凈的ip地址信息。
其中第一個(gè)判斷方式應(yīng)該來(lái)說(shuō)是較為準(zhǔn)確且穩(wěn)定的,符合我們的使用目標(biāo)。
但第二個(gè)提取操作卻有可能因?yàn)榫W(wǎng)絡(luò)環(huán)境的變化,或網(wǎng)絡(luò)設(shè)置的調(diào)整,可能會(huì)有字段的位置或是中間內(nèi)容的調(diào)整,使得截取出來(lái)的不一定再是純凈的ip地址。因此我們可以更換一種更為快捷的獲取IP地址的方式:
hostname -I很簡(jiǎn)單的命令不用任何操作,就可以直接輸出樹(shù)莓派所連接的ip地址。
當(dāng)然,如果你連接的網(wǎng)絡(luò)給你分配了ipv6地址的話,也會(huì)一并展示出來(lái),如果需要再按需提取即可。比如我的輸出如下:
如果只需要提取前面的ipv4地址,那么同上用awk截取:
echo `hostname -I|awk -F ' ' '{print $1}'`如果要賦值給變量$IP,那么用內(nèi)外雙重反引號(hào)會(huì)造成歧義,故可以在外面用$(命令)的方式:
IP=$(echo `hostname -I|awk -F ' ' '{print $1}'`)如此即可提取出純凈的ipv4地址
最終效果如圖:
?
?
?
?
9.附:完整示例代碼:
#!/bin/bash ########################################### ##### created by RichardYann ##### ##### 2020-11-11 ##### ##### EmaiL:yanrichard500@gmail.com ##### ############################################ set PATH export PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/local/games:/usr/games"# Global Variables corpid=CORPID # change to your own corpid AgentId=AGENTID # change to your own agentid Secret=SECRET # change to your own secret getTokenURL="https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=$corpid&corpsecret=$Secret"# check netstat while true; do $(echo `ifconfig|grep 192.168`)&& break;sleep 1;done;# get token temp=`curl $getTokenURL` if [ -n `echo $temp|awk -F \":\" '{print $3}'` ];thenaccess_token=`echo $temp|awk -F \":\" '{print $3}'|awk -F \",\" '{print $1}'` fi# get postURL PostURL="https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=$access_token"# get ip; change $1 to $2 if you wanna get ipv6 addr.(if you had) IP=$(echo `hostname -I|awk -F ' ' '{print $1}'`)# send post curl -H "Content-type: application/json" -X POST -d '{"touser":"@all","msgtype":"text","agentid":"'"$AgentId"'","text":{"content":"樹(shù)莓派已經(jīng)啟動(dòng)啦!!\n\nIP地址是:'"$IP"'\n\n快點(diǎn)連接控制吧~~"},"safe":0}' $PostURL總結(jié)
以上是生活随笔為你收集整理的【实现】树莓派开机自动向微信发消息报告ip地址(无第三方代理)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 深度解析UG二次开发装配的部件事件、部件
- 下一篇: 古诗接力