自从 ubuntu 14.04 LTS 以来,我一直遇到这个问题,我的无线连接“混乱” - 更具体地说,我有时会失去连接。
我目前正在通过断开连接然后重新连接来解决这个问题。我可以通过点击右上角的统一栏图标,或者通过发出rfkill block wifi
命令来rfkill unblock wifi
解决这个问题
我还没有找到读取问题的解决方案,但我有这样的想法,如果我可以使用在断开连接时触发的脚本以编程方式处理这种情况,那就没问题了。
我也不想创建一个不断轮询 wifi 状态的脚本,我想听针对这一特定事件,并在收到通知后采取行动。
这可能吗?
答案1
首先:
您期望的答案是什么是你实际上称之为:我也不想创建一个不断轮询的脚本。Inotify 还用于持续循环以“监听”当前状态的变化。换句话说:如果没有某种循环,您认为存在的其他选项就不存在。
我还认为你对循环的描述太过沉重。在每个系统上,在每个应用程序中,都有大量循环处于活动状态以等待触发。它应该不会对你的资源产生明显的影响。
这种“解剖学”针对事件采取行动机制基本上是:
在一段时间循环中:
check the current status;
if a is True:
take action A
if a is False:
do nothing
wait a few seconds
在 Bash 脚本中
整合这脚本(检查您的连接)在 while 循环中(进行一些小改动)应该执行您描述的操作:重新建立您的连接并发送通知。
#!/bin/bash
while :
do
wget -q --tries=10 --timeout=20 --spider http://google.com
if [[ $? -eq 0 ]]; then
:
else
rfkill block wifi
rfkill unblock wifi
notify-send "connection re-established"
fi
sleep 4
done
在 Python 脚本中
函数check()
返回真的或者错误的。 如果真的(连接已建立),则不会发生任何事情。如果错误的,你的rfkill block wifi
/rfkill ublock wifi
被执行。
#!/usr/bin/env python3
import socket
import time
import subprocess
def check():
try:
host = socket.gethostbyname("www.google.com")
s = socket.create_connection((host, 80), 2)
return True
except Exception:
return False
while True:
if check() == True:
pass
else:
subprocess.call(["/bin/bash", "-c", "rfkill", "block", "wifi"])
subprocess.call(["/bin/bash", "-c", "rfkill", "unblock", "wifi"])
subprocess.Popen(["/bin/bash", "-c", "notify-send 'conncection re-established'"])
time.sleep(4)
答案2
我的脚本用于处理免费 WIFI 登录/注销和无线连接重新连接和修复。
它连接到免费的 wifi,登录,获取剩余连接时间并等待时间到并检查 wifi 和登录状态和互联网连接,注销并重复。
要向桌面环境发送通知,请使用
notify-send "YOUR MESSAGE HERE"
函数中处理 Wifi 连接修复重新连接()
#!/bin/bash
WIFI_DEVICE="wlp3s2"
USER_PC="T-00%3AC0%3AA8%3AC7%3AF0%3AF1"
USER_USB="T-00%3AE0%3A4C%3A84%3AD2%3A5C"
USER_NAME="$USER_PC"
LOGIN_URL="http://starse.hotspot/login?username="
LOGOUT_URL="http://starse.hotspot/logout"
STATUS_URL="http://starse.hotspot/status"
WIFI_NETWORK="starse.WiFiPoint"
WIFI_PROFILE_FILE_SEARCH="starse"
PORT=5555
LOGIN_RETRY=5
REPEAT_HOURS=10000
SECONDS_LEFT="0"
ONE_MINUTE=15
MINUTES=0
START=0
END=0
ONE=1
ZERO=0
function CleanConnections()
{
MYDIR=$(pwd)
#remove all connections from network manager
cd /etc/NetworkManager/system-connections/ &> /dev/null
rm "$WIFI_PROFILE_FILE_SEARCH.*" &> /dev/null
cd $MYDIR &> /dev/null
}
function ReConnect()
{
# check if WIFI_DEVICE is connected to WIFI_NETWORK
WIFI_OK=$(iwconfig $WIFI_DEVICE | grep -c $WIFI_NETWORK)
# while not connected, try to repair connection
while [ $WIFI_OK = "0" ]
do
# check if wifi radio is on / turn it on
RADIO=$(nmcli radio wifi)
sleep 1
if [ "$RADIO" = "onemogočeno" ]
then
nmcli radio wifi on
echo "$(date), WIFI RADIO OMOGOČEN!"
fi
sleep 1
# check if WIFI_DEVICE is connected to WIFI_NETWORK again
WIFI_OK=$(iwconfig $WIFI_DEVICE | grep -c $WIFI_NETWORK)
if [ $WIFI_OK = "0" ]
then
# if not connected, connect to WIFI_NETWORK
echo "$(date), POVEZAVA WIFI PREKINJENA!"
nmcli d wifi connect "$WIFI_NETWORK" &> /dev/null
sleep 1
# check if WIFI_DEVICE is connected to WIFI_NETWORK again
WIFI_OK=$(iwconfig $WIFI_DEVICE | grep -c $WIFI_NETWORK)
sleep 1
# if connection is still not established, restart network-manager and check connection
if [ $WIFI_OK = "0" ]
then
service network-manager restart
sleep 2
WIFI_OK=$(iwconfig $WIFI_DEVICE | grep -c $WIFI_NETWORK)
echo "$(date), NETWORK MANAGER PONOVNO ZAGNAN!"
else
echo "$(date), POVEZAVA WIFI VZPOSTAVLJENA!"
sleep 2
fi
fi
done
}
function Login()
{
RETRY_COUNT=0
LOGIN_OK=0
# while not logged in
while [ $LOGIN_OK = "0" ]
do
# try to login
LOGIN_OK=$(curl -s -m 2 "$LOGIN_URL$USER_NAME" | grep -c "You are logged in")
if [ $LOGIN_OK = "1" ]
then
echo "$(date), PRIJAVA USPEŠNA."
break
else
# if could not login, try for RETRY_COUN
echo "$(date), PRIJAVA NEUSPEŠNA! Ponavljam $RETRY_COUNT od $LOGIN_RETRY"
RETRY_COUNT=$((RETRY_COUNT+1))
sleep 1
fi
# if RETRY_COUNT expired then ReConnect and continue
if [ $RETRY_COUNT -gt $LOGIN_RETRY ]
then
ReConnect
RETRY_COUNT=0
continue
fi
done
}
function GetSecondsLeft()
{
STATUS_PAGE=$(wget -T 2 -q -O - "$@" "$STATUS_URL")
sleep 10
MIN1=$(echo $STATUS_PAGE | grep -o '[0-9| ][0-9]m' | tail -1 | tr -d 'm' | tr -d ' ')
sleep 1
SEC1=$((MIN1*60))
echo "$(date), ČAS PRIDOBLJEN. NA VOLJO: $((SEC1))s"
eval "$1"="$SEC1"
}
#ReConnect
LOGIN_NR=1
while [ "$LOGIN_NR" -lt "$REPEAT_HOURS" ]
do
# try to login first
Login
#set counters
START=$(date +%s)
# get time left from status page
GetSecondsLeft SECONDS_LEFT
# clean wifi profiles dir
CleanConnections
# get first ELPASED_SEC
END=$(date +%s)
ELPASED_SEC=$((END-START))
# count till next login
while [ $ELPASED_SEC -lt $SECONDS_LEFT ]
do
# display info
echo "$(date), LOGIN: $LOGIN_NR, PRETEKLO: $((ELPASED_SEC))s, NA VOLJO ŠE: $((SECONDS_LEFT-ELPASED_SEC))s"
# wait ONE_MINUTE and periodicaly check for wifi and internet connection every two/three seconds
ELPASED_MINUTE_SEC=0
while [ $ELPASED_MINUTE_SEC -lt $ONE_MINUTE ]
do
# start timer
S=$(date +%s)
# check for wifi connection
WIFI_OK=$(iwconfig $WIFI_DEVICE | grep -c $WIFI_NETWORK)
if [ $WIFI_OK = "1" ]
then
# if wifi connection OK, check for internet connection
PING="0"
PING=$(ping -c 1 -w 2000 -s 1 www.google.si | grep -c "9 bytes")
sleep 2
if [ "$PING" = "0" ]
then
echo "$(date), INTERNETNA POVEZAVA PREKINJENA! Vzpostavljam ..."
# if no internet connection then Login()
Login
# on reconnect caculate SECONDS_LEFT and reset ELPASED_SEC
GetSecondsLeft SECONDS_LEFT
ELPASED_SEC=0
else
sleep 1
fi
else
# if wifi connection is lost ReConnect()
ReConnect
fi
# check if whole time is up and break
END=$(date +%s)
ELPASED_SEC=$((END-START))
if [ $SECONDS_LEFT -le $ELPASED_SEC ]
then
break
fi
# add used seconds to ELPASED MINUTE
E=$(date +%s)
ELPASED_MINUTE_SEC=$((ELPASED_MINUTE_SEC+(E-S)))
done
END=$(date +%s)
ELPASED_SEC=$((END-START))
done
# TIME IS UP
# logout and increase LOGIN_NR
curl -s -m 2 "$LOGOUT_URL" &> /dev/null
LOGIN_NR=$((LOGIN_NR+1))
done