检查动态IP更改的最简单方法


12

如果我的IP地址已更改,用脚本查找最简单的方法是什么?


背景信息:

我有一个标准的家用电缆调制解调器连接,我的ISP为我分配了一个动态IP。它不时更改,DHCP租用时间似乎不规律。

基本上,我正在做自己的动态DNS事务,并且可以单击一下来更新指向我的家庭服务器的DNS记录。剩下的唯一事情就是检测IP更改,以便我可以完全自动化该过程。

现在这里有几个网站可以返回您的IP地址,我可以使用cron作业访问wget这些页面之一,并返回其中grep的IP地址...但是就CPU /带宽使用而言,这似乎有些过头了,而且不是很吻。

我是否缺少一些简单而优雅的方法来检索我的公共IP并检查它是否已更改?

额外信息:我的调制解调器/路由器是便宜的砖头,在这方面没有任何有趣的事情。我的服务器与Centos 6一起运行。

Answers:


6

假设您落后于NAT,我能想到的最优雅的方法是在路由器本身上运行cron作业,定期检查ifconfig其当前的WAN地址。如果您能够安装自定义固件,甚至可以在“便宜的砖”上实现。然而优雅,几乎不简单。

作为讨论在这里,在Windows上,但参数是为CentOS同样有效,在轮询WAN IP从后面NAT,您遇到的问题是,你没有在技术上有一个外部地址。取而代之的是,您将自行决定是否通过路由器路由您。显然,只要路由器在您的控制之下,您仍然可以访问此信息,但是没有通用的方法可以将此IP地址传递给本地网络上的主机。结果,您的服务器不能简单地向路由器询问它将使用的外部IP。

最有效的选择是让路由器发挥作用,并实际上与外部服务器建立连接,然后要求路由器返回请求所源自的地址。为此专门设置了许多Web服务器。对于脚本编写,我可以推荐http://icanhazip.com/,因为它不需要您进一步解析(仅以纯文本形式返回IP)。

如有必要,与之前相关的问题的答案应提供大量的实施技巧。


好主意和链接。+1(如果仅适用于我不知道的icanhazip网站),则无需下载额外的HTML和进行解析。
Silver Quettier 2013年

1
或checkip.net-me.net/plain
Alex


6

您可以查询显示此任务IP的任何网站。使用checkip.dyndns.com,因为它只有文本。

例:

wget -q -O - checkip.dyndns.com | grep -Po "[\d\.]+"

0

我今天也遇到了同样的问题,我对在这里或在Google上看到的答案不满意,因此我编写了一个PowerShell脚本,每当我的IP地址发生变化时,我都会向我发送Slack通知

如果您希望接收电子邮件,则可以单击脚本中的链接以查看支持Outlook电子邮件的其他版本。

我希望这可以帮助某人并赢得投票。:-)

将以下文本保存到.ps1文件中。使用您自己的Slack webhook URL对其进行适当的编辑。救。右键单击该文件以“使用PowerShell运行”。

或者,您可以安排它每天或经常运行。

#Script to compare current IP with old IP and sends Slack notification if different (and do nothing if there was no change).
#We can put this as a scheduled task to run daily.
#ScriptName: IP_change_detection_notification.ps1

$slackWebhookUrl = "XXXXXXXXXX" #put yours here
$ipDetectionUrl = "https://wtfismyip.com/text"
$IPAddFile = "C:\code\IP_change_detection_notification.dat" #absolute path to file that stores the old IP record
$slackOutputFile = "C:\code\IP_change_detection_notification_Slack.txt"
$optionalDebuggingFile = "C:\code\IP_change_detection_notification_debugging.txt"

$Request = Invoke-WebRequest $ipDetectionUrl
$IP_new = ($Request.Content.Trim())
Write-Host "Current IP address: [$IP_new]"

#Check if old IP record exists
If(Test-Path "$IPAddFile")
{
#Get old IP
$IP_old = Get-Content "$IPAddFile"
    #Compare IPs
    if(-not($IP_new -eq $IP_old))
    {
        Write-Host "Old IP address: [$IP_old]"
        $msg = "Your WAN IP has changed to $IP_new (was $IP_old)!"
        Write-Host "$msg"               
        $body = $("{""text"":""$msg""}")
        Write-Host "$body"
        Invoke-RestMethod -Uri $slackWebhookUrl -Method Post -ContentType 'application/json' -Body $body -OutFile $slackOutputFile

        "Notification Sent"     

        #Overwrite and update new IP
        $IP_new |  Out-File $IPAddFile

    }
    else
    {"No change, no notification"}

}
else
{
#Create new, as file not found
$IP_new |  Out-File $IPAddFile
"File created"
}
$(get-date -f yyyy-MM-dd_HH_mm_ss)  |  Out-File $optionalDebuggingFile
#Read-Host -Prompt "Press Enter to exit" #Comment out this line if this script will be run by a cron job. Otherwise, uncomment it so that you can see the results of the script in the console.

#This script was adapted from https://gallery.technet.microsoft.com/scriptcenter/Detect-IP-address-change-aeb51118 by Satyajit

要使任务计划程序正常工作:

我必须以管理员身份运行PowerShell,然后运行Get-ExecutionPolicy,然后告诉我当前的ExecutionPolicy为“受限”。

然后我跑了Set-ExecutionPolicy RemoteSigned(如此处所示,但这让我感到紧张:https : //stackoverflow.com/a/26955050/470749)。

然后从基本的Windows命令提示符下,尝试几次运行以下命令:(C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe -ExecutionPolicy ByPass -File "C:\code\IP_change_detection_notification.ps1"一次存储IP,第二次检查它是否已更改)。

(直到您使它起作用,不要再尝试使用Task Scheduler。)

然后,我用C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe程序和-ExecutionPolicy ByPass -File C:\code\IP_change_detection_notification.ps1参数安排了一个任务。


它是一个很好的解决方案,但不幸的是,OP指出他正在使用CentOS,因此从技术上讲这并不能回答问题。
MaQleod

0

前面的答案(不包括PS实现)实际上并没有告诉您IP是否已更改。(我想爱PowerShell。Ryan在确定为什么不这样做方面做得很好:执行安全权限令人讨厌)。

只要在IP不变的情况下任何其他输出都没有变化,就不需要解析IP。例如,checkip.dyndns.com返回类似于“当前IP地址”的内容:ddd.ddd.ddd.ddd。因此,仅比较整个输出就足够了。

另外,如果您使用curl,则可能要使用-s标志隐藏进度。由于已将其写入stderr,因此不会污染stdout。

因此,这是一个简单的.cmd脚本,该脚本使用curl来保存输出。然后,它将使用FC将其与先前的输出(如果有)进行比较。我不需要为Unicode,区分大小写等设置FC选项,因为在IP不变的情况下,输出应为二进制匹配。Unix具有cmp而不是FC。

@REM 12/30/2017 The following work:
@REM                checkip.dyndns.com
@REM                wtfismyip.com/text
@REM                icanhazip.com
@REM                ifconfig.me/ip -- can be slow

curl icanhazip.com > CurrentIp.txt
fc /B LastIp.txt CurrentIp.txt 1> nul: 2>>&1

if ERRORLEVEL 1 (
    ECHO Ip Changed
    REM Remember for next time
    MOVE /Y CurrentIp.txt LastIp.txt 1>nul:
    exit /b 1
) else (
    ECHO Ip not Changed
)

显然,可以将CurrentIp.txt的LastIp.txt更改为适合的名称,例如,前缀为“%TMP%\”的脚本。


0

针对OP:“我是否缺少一种简单而优雅的方法来检索我的公共IP并检查其是否已更改?”

一个真正简单的答案是不。只需定期更新您的IP。

看起来很浪费,但是“更智能”的解决方案更加复杂且可靠性较低,而又不节省CPU,带宽等。每小时发送一次1500字节或更少的字节(一个数据包)非常便宜。整个一年将消耗365 * 24 * 1,500 = 13 Meg Bytes或Netflix上Rifleman的大约3分钟。

获取外部ip并偶尔发布新ip的CPU /带宽成本很可能比定期重复发布ip的CPU /带宽成本更高。多年来,我一直在每小时将我的IP发布到duckdns,没有问题。显然,如果您开始执行此1 /秒操作,则您的域服务可能会发现并烦恼。同样,如果您执行此操作,则用于查找ip的任何服务将不满意。

最后想一想,您提出的问题是您提到的问题的一部分。刷新动态DNS的触发条件可能是您的域名未解析到服务器时。您可以使用ping,但是如果您的旧IP地址被重用,则新的IP租约持有人很可能会响应ping。

考虑到这一点,您可以定期尝试从服务器下载一个小的签名/魔术文件。确实,这可以是任何告诉您找到服务器的静态文件,即使您的主页也可以使用,但是不寻常的名称比default.html好得多。

如果d / l失败,则更新您的IP,清除DNS缓存,然后重试。更新可能需要几分钟的时间才能生效,具体取决于您的DNS服务。这种方法消除了对其他外部ip站点的依赖,并实际测试了您真正想知道的内容:其他人可以访问我的站点吗?


0

作为一种可能对您有所帮助的替代方法,我编写了一个python脚本,旨在监视外部IP地址的更改。我在Linux下使用它,但是由于它是python,因此在设置了适当的Python环境之后,它应该可以在Windows上正常工作。当前,它将“当前”外部IP地址保存到文件中,并在运行时获取一个新IP地址,然后将其与旧IP地址进行比较。如果检测到更改,它可以通过电子邮件发送给您。

它被设计为作为cronjob(Linux)或计划任务(Windows)运行,而不是作为后台守护程序单独运行。

这是github存储库的链接:https : //github.com/begleysm/ipwatch

希望它会有所帮助!


By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.