mac自動(dòng)連接wifi

文字描述比較少建钥,有遇到問題可以V本人。

公司wifi需要登錄認(rèn)證網(wǎng)頁(yè)虐沥,手動(dòng)輸入賬號(hào)和密碼熊经,驗(yàn)證完成后,才能開始上網(wǎng)欲险。如果電腦合蓋镐依,或者睡眠。再次打開需要重新在打開網(wǎng)頁(yè)天试,輸入賬號(hào)密碼槐壳,連接。就和我們?cè)贙FC或者是機(jī)場(chǎng)秋秤、酒店宏粤,連接了wifi會(huì)彈出一個(gè)認(rèn)證的窗口。

image.png
  • 首先想到的是把url的請(qǐng)求地址拿出來灼卢,通過curl的請(qǐng)求去完成認(rèn)證绍哎。
    這個(gè)有一個(gè)問題是當(dāng)Captive Network Assistant彈出的時(shí)候,網(wǎng)絡(luò)會(huì)被攔截鞋真,這個(gè)英語翻譯成中文的意思強(qiáng)制網(wǎng)絡(luò)助理崇堰。只要有這個(gè)彈窗在,網(wǎng)絡(luò)都會(huì)被終止(沒有實(shí)際性的原理,親測(cè)是網(wǎng)絡(luò)被攔截)

  • 最早是使用sleepwatcher來執(zhí)行海诲,當(dāng)mac喚醒的時(shí)候繁莹,執(zhí)行腳本。
    有個(gè)問題就是當(dāng)切換網(wǎng)絡(luò)的時(shí)候特幔,就沒辦法執(zhí)行腳本了咨演。只能在喚起的時(shí)候使用

解決方案

使用hammerspoon+lua+applescript來解決

思路

  • 監(jiān)聽網(wǎng)絡(luò)切換和電腦的喚醒、解鎖
  • 監(jiān)聽到事件蚯斯,查找是否有目標(biāo)wifi在薄风,如果有,強(qiáng)制連接目標(biāo)wifi
  • 監(jiān)聽Captive Network Assistant的彈窗拍嵌,如果彈窗存在遭赂,執(zhí)行applescript的腳本,自動(dòng)輸入賬號(hào)密碼

安裝hammerspoon

  • 使用brew安裝
沒有安裝過brew的話可以先執(zhí)行
/usr/bin/ruby -e "$(curl -fsSL https://cdn.jsdelivr.net/gh/ineo6/homebrew-install/install)"
然后安裝
brew install hammerspoon --cask
  • 下載app横辆,自行百度或者官網(wǎng)下載撇他。這邊就不做更多的說明
  • 安裝完成后,頂部會(huì)有一個(gè)錘子的圖標(biāo)狈蚤,點(diǎn)擊紅框部分給到權(quán)限困肩。可以開機(jī)的時(shí)候就啟動(dòng)hammerspoon
image.png
  • 小技巧炫惩,可以把圖標(biāo)也隱藏僻弹。通過command + 空格,喚起搜索他嚷,搜索ha開頭蹋绽,可以再打開設(shè)置界面。


    image.png

    image.png
  • 在~目錄下可以看到有這個(gè)文件筋蓖。hammerspoon會(huì)先執(zhí)行init.lua


    image.png

開發(fā)環(huán)境

init.lua 判斷了如果是自己的mac卸耘,才會(huì)執(zhí)行自動(dòng)更新腳本。這樣只要有修改粘咖,hammerspoon的控制臺(tái)就會(huì)有l(wèi)og蚣抗,方便做調(diào)試

require "wifi.wifi"

if (hs.host.localizedName() == 'Radish') then
    
local pathwatcher = require "hs.pathwatcher"  
local alert = require "hs.alert"
-- 開啟自動(dòng)重載配置文件
function autoReload()  
  function reloadConfig(files)
      doReload = false
      for _, file in pairs(files) do
          if file:sub(-4) == ".lua" then
              doReload = true
          end
      end
      if doReload then
          hs.reload()
      end
  end
  pathwatcher.new(os.getenv("HOME") .. "/.hammerspoon", reloadConfig):start()
end

autoReload()  
end

wifi

wifi的腳本思路和上面所述的一樣。主要監(jiān)聽了監(jiān)聽電腦休眠和喚醒wifi發(fā)生改變創(chuàng)建應(yīng)用程序監(jiān)控器瓮下。喚醒的時(shí)候翰铡,去掃描后臺(tái)有沒有目標(biāo)WIFINAME,有的話讽坏,就連接目標(biāo)wifi锭魔,執(zhí)行applescript腳本



local WIFINAME = "Dianei";
-- local USERNAME = "1111"
-- local PASSWORD = "2222"

-- 異步執(zhí)行shell
function asyncSheel(cmd, callback)
  hs.task.new("/bin/sh", function(exitCode, stdOut, stdErr)
    if exitCode ~= 0 then
      print("Error executing command: " .. stdErr)
      callback()
    else
      print("Command output: " .. stdOut)
      callback(stdOut)
    end
  end, {"-c", cmd}):start()
end

-- 執(zhí)行shell腳本
function shell(cmd)
  local success,obj,descriptor = hs.osascript.applescript(string.format('do shell script "%s"', cmd))
  return success,obj,descriptor
end

-- 判斷網(wǎng)絡(luò)是否連接
function isNet()
  local success,obj,descriptor = shell("ping -o -t 1 baidu.com")
  if (success and obj ~= nil and string.find(descriptor, '1 packets received')~= nil) then
    return true
  else
    return false
  end
end


function wifiCallback(watcher, message, interface)
  local ssid = hs.wifi.currentNetwork(interface)
    if (ssid ~= nil and ssid == WIFINAME) then
      print("當(dāng)前wifi列表中存在"..ssid)
      -- scan()
    end
end


function caffeinateCallback(event)
  if event == hs.caffeinate.watcher.screensDidSleep then
    -- 屏幕休眠(屏保開啟)
    print("screensDidSleep")
  elseif event == hs.caffeinate.watcher.screensDidWake then
    -- 屏幕喚醒
    print("screensDidWake")
  elseif event == hs.caffeinate.watcher.screensDidLock then
    print("screensDidLock")
  elseif event == hs.caffeinate.watcher.screensDidUnlock then
    -- 屏幕解鎖
    print("screensDidUnlock")
    -- 強(qiáng)制開啟wifi的按鈕
    asyncSheel("networksetup -setairportpower en0 on", function()
      print('強(qiáng)制開啟了wifi按鈕')
      -- 后臺(tái)掃描WiFi熱點(diǎn)
      hs.wifi.backgroundScan(function(networks)
        -- 處理掃描結(jié)果
        print("wifi 掃描完成")
        for i, network in ipairs(networks) do
            if (network.ssid == WIFINAME or network.bssid == WIFINAME) then
              print("找到 wifi名字了")
              -- 連接wifi 等待cna的彈窗
              hs.wifi.associate(WIFINAME, "")
              break
            end
        end
      end)
    end)
  elseif event == hs.caffeinate.watcher.systemWillSleep then    
    print("systemWillSleep")
  elseif event == hs.caffeinate.watcher.systemDidWake then
    print("systemDidWake")
  elseif event == hs.caffeinate.watcher.systemWillPowerOff then
    print("systemWillPowerOff")
  elseif event == hs.caffeinate.watcher.systemDidPowerOn then
    print("systemDidPowerOn")
  end
end

-- 應(yīng)用程序激活事件處理
function applicationCallback(name, event, app)
  -- and event == hs.application.watcher.launched
  if name == "Captive Network Assistant" or name == "強(qiáng)制網(wǎng)絡(luò)助理"  then
    -- 啟動(dòng)
    -- print(hs.application.watcher.launched)
    -- -- 激活
    -- print(hs.application.watcher.activated)
    -- 在 Captive Network Assistant 打開時(shí)自動(dòng)輸入賬號(hào)密碼
    if event == hs.application.watcher.activated then
      print("激活cna了 ~ ")
      asyncSheel("osascript ~/.hammerspoon/wifi/cna.applescript", function(e)
        print("執(zhí)行完畢")
        local haveNet = isNet()
        if (haveNet == true) then
          hs.alert.show(WIFINAME.."網(wǎng)絡(luò)已連接")
        end
      end)
    end
  end
end

-- 監(jiān)聽電腦休眠和喚醒
hs.caffeinate.watcher.new(caffeinateCallback):start()
-- wifi發(fā)生改變
hs.wifi.watcher.new(wifiCallback):start()
-- 創(chuàng)建應(yīng)用程序監(jiān)控器
hs.application.watcher.new(applicationCallback):start()



function getDianneiWifi()
  return hs.window.filter.new(false):setAppFilter("Captive Network Assistant", { currentSpace = true, allowTitles = "加入“Dianei”" }):getWindows()
end



-- hs.application:getWindow(title)


-- function launchOrNextWindow(name, showName)
--  local findName = showName or name
--  local appName = hs.application.frontmostApplication():name()
--  print("appName")
--  print(appName)
--  if findName ~= appName then
--          hs.application.launchOrFocus(name)
--  else
--          -- local wlist = getWinList(findName)
--          -- local wcount = #wlist
--          -- if wcount > 1 then
--          --      hs.eventtap.keyStroke({'cmd'}, '`')
--          -- else
--          --      local win = wlist[1]
--          --      if win:isMinimized() then win:unminimize() else win:minimize() end
--          -- end
--  end
-- end

-- function mapLaunch(key, name, showName)
--  hs.hotkey.bind({}, key, function()
--          launchOrNextWindow(name, showName)
--  end)
-- end

-- mapLaunch('f1', 'Google Chrome')
-- launchOrNextWindow('iTerm', 'iTerm2')

applescript

需要注意的是,vscode中默認(rèn)是UTF-8的編碼路呜,applescript要設(shè)置為GB2312迷捧。不然有中文的會(huì)識(shí)別不了


global WIFINAME
global USERNAME
global USERPASSWORD
global ROOPNUM
global DELAYTIME
global NOTWIFI
set WIFINAME to "xxxx"
set USERNAME to "xxx"
set USERPASSWORD to "xxxx"
set ROOPNUM to 5
set DELAYTIME to 0.5

set roopCount to 0
repeat while roopCount < ROOPNUM
    if isNet() = true then
        log "net connct success"
        my closeDianei()
        exit repeat
    else
        if my getCNAAlert() = 1 then
            log "find cna"
            -- begin connect
            my connectWIFI()
        end if
        set roopCount to roopCount + 1
    end if
end repeat




on closeDianei()
    tell application "System Events"
        -- 是否存在 CNA 彈窗
        if exists (process "Captive Network Assistant") then
            -- 進(jìn)入CNA的進(jìn)程
            tell process "Captive Network Assistant"
                -- 是否存在dianei的wifi連接彈窗
                if exists (window "加入“Dianei”") then
                    -- 進(jìn)入dianeiwif連接的彈窗
                    tell window "加入“Dianei”"
                        -- 進(jìn)入U(xiǎn)I界面
                        if exists (button "完成") then
                            click button "完成"
                        end if
                        if exists (button "取消") then
                            click button "取消"
                        end if
                    end tell
                end if
            end tell
        end if
    end tell
end closeDianei



on getCNAAlert()
    -- 系統(tǒng)事件
    tell application "System Events"
        if exists (process "Captive Network Assistant") then
            return 1
        else
            return 2
        end if
    end tell
end getCNAAlert


on connectWIFI()
    -- 系統(tǒng)事件
    tell application "System Events"
        -- 是否存在 CNA 彈窗
        if exists (process "Captive Network Assistant") then
            -- 進(jìn)入CNA的進(jìn)程
            tell process "Captive Network Assistant"
                -- 是否存在dianei的wifi連接彈窗
                if exists (window "加入“Dianei”") then
                    -- 進(jìn)入dianeiwif連接的彈窗
                    tell window "加入“Dianei”"
                        -- 進(jìn)入U(xiǎn)I層級(jí) 從這個(gè)命令去找 entire contents  找到對(duì)應(yīng)想要的名稱织咧。比如用戶名 密碼 注銷等等
                        if exists (UI element 1 of scroll area 1 of group 1 of group 2) then
                            -- UI層架
                            tell UI element 1 of scroll area 1 of group 1 of group 2
                                set groupTag to 0
                                repeat while groupTag < 50
                                    try
                                        if my isNet() = true then
                                            exit repeat
                                        else
                                            if exists (text field 1 of group 1 of group groupTag) then
                                                log "開始自動(dòng)輸入用戶名和密碼"
                                                -- 用戶名
                                                tell group 1 of group groupTag
                                                    set value of attribute "AXFocused" of text field 1 to true
                                                    set value of text field 1 to USERNAME
                                                end tell
                                                -- 密碼
                                                tell group 2 of group groupTag
                                                    set value of attribute "AXFocused" of text field 1 to true
                                                    set value of text field 1 to USERPASSWORD
                                                end tell
                                                -- 勾選框
                                                tell group (groupTag + 1)
                                                    click checkbox 1
                                                end tell
                                                -- 登錄按鈕
                                                tell group (groupTag + 2)
                                                    click button "登錄"
                                                end tell
                                                exit repeat
                                            else
                                                set groupTag to groupTag + 1
                                            end if
                                        end if
                                    end try
                                end repeat
                            end tell
                        end if
                    end tell
                end if
            end tell
        end if
    end tell
end connectWIFI



on isNet()
    try
        set pingResult to do shell script "ping -o -t 1 baidu.com"
        if pingResult contains "1 packets received" then
            return true
        else
            return false
        end if
    on error
        return false
    end try
end isNet

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市漠秋,隨后出現(xiàn)的幾起案子笙蒙,更是在濱河造成了極大的恐慌,老刑警劉巖庆锦,帶你破解...
    沈念sama閱讀 218,941評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件捅位,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡肥荔,警方通過查閱死者的電腦和手機(jī)绿渣,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,397評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門朝群,熙熙樓的掌柜王于貴愁眉苦臉地迎上來燕耿,“玉大人,你說我怎么就攤上這事姜胖∮В” “怎么了?”我有些...
    開封第一講書人閱讀 165,345評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵右莱,是天一觀的道長(zhǎng)蚜锨。 經(jīng)常有香客問我,道長(zhǎng)慢蜓,這世上最難降的妖魔是什么亚再? 我笑而不...
    開封第一講書人閱讀 58,851評(píng)論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮晨抡,結(jié)果婚禮上氛悬,老公的妹妹穿的比我還像新娘。我一直安慰自己耘柱,他們只是感情好如捅,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,868評(píng)論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著调煎,像睡著了一般镜遣。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上士袄,一...
    開封第一講書人閱讀 51,688評(píng)論 1 305
  • 那天悲关,我揣著相機(jī)與錄音,去河邊找鬼娄柳。 笑死寓辱,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的西土。 我是一名探鬼主播讶舰,決...
    沈念sama閱讀 40,414評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來了跳昼?” 一聲冷哼從身側(cè)響起般甲,我...
    開封第一講書人閱讀 39,319評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎鹅颊,沒想到半個(gè)月后敷存,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,775評(píng)論 1 315
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡堪伍,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,945評(píng)論 3 336
  • 正文 我和宋清朗相戀三年锚烦,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片帝雇。...
    茶點(diǎn)故事閱讀 40,096評(píng)論 1 350
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡涮俄,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出尸闸,到底是詐尸還是另有隱情彻亲,我是刑警寧澤,帶...
    沈念sama閱讀 35,789評(píng)論 5 346
  • 正文 年R本政府宣布吮廉,位于F島的核電站苞尝,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏宦芦。R本人自食惡果不足惜宙址,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,437評(píng)論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望调卑。 院中可真熱鬧抡砂,春花似錦、人聲如沸令野。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,993評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽气破。三九已至聊浅,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間现使,已是汗流浹背低匙。 一陣腳步聲響...
    開封第一講書人閱讀 33,107評(píng)論 1 271
  • 我被黑心中介騙來泰國(guó)打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留碳锈,地道東北人顽冶。 一個(gè)月前我還...
    沈念sama閱讀 48,308評(píng)論 3 372
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像售碳,于是被迫代替她去往敵國(guó)和親强重。 傳聞我的和親對(duì)象是個(gè)殘疾皇子绞呈,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,037評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容