吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 3097|回复: 39
上一主题 下一主题
收起左侧

[其他原创] [batch] 写了个自动切换内外网的脚本

[复制链接]
跳转到指定楼层
楼主
hoochanlon 发表于 2024-11-28 14:51 回帖奖励

当前状况&优化:经常需要在同一台主机上进行内外网切换,处理生产域控需要进内网,平时浏览网页需要外网,已存在的内网与外网脚本,每次都要分别点一次不方便。

设计思路:判断是否为静态或自动获取,然后根据“自动获取”设置静态IP,如果是静态IP就设置自动获取,以达到自动识别与切换的目的。

源码及地址:

@echo off
cls

:: 定义接口名称
set interface="以太网"

:: 创建一个临时文件存储 netsh 输出
set temp_file=%temp%\dhcp_status_output.txt

:: 获取接口配置信息并保存到文件
netsh interface ip show config name=%interface% > "%temp_file%"

:: 初始化变量
set dhcp_status=

:: 逐行读取文件,查找 "DHCP 已启用"
for /f "tokens=2 delims=:" %%a in ('findstr /c:"DHCP 已启用" "%temp_file%"') do (
    set dhcp_status=%%a
)

:: 清理前导空格
for /f "tokens=* delims= " %%b in ("%dhcp_status%") do set dhcp_status=%%b

:: 显示结果,检查 DHCP 状态
echo 当前 DHCP 状态: "%dhcp_status%"

:: 判断当前模式并执行切换
if /i "%dhcp_status%"=="是" (
    echo 检测到当前为 DHCP 模式,正在切换到静态 IP...
    netsh interface ip set address name=%interface% source=static addr=172.16.1.55 mask=255.255.255.0 gateway=172.16.1.254 >nul 2>nul
    netsh interface ip set dnsservers %interface% static 172.16.1.6 validate=no >nul 2>nul
    echo 已切换到静态 IP 配置。
) else (
    echo 检测到当前为静态 IP 模式,正在切换到 DHCP...
    netsh interface ip set address name=%interface% source=dhcp >nul 2>nul
    @rem netsh interface ip set dnsservers %interface% dhcp >nul 2>nul
    netsh interface ip set dnsservers %interface% static 192.168.1.250 primary >nul 2>nul
    netsh interface ip add dnsservers %interface% 114.114.114.114 index=2 >nul 2>nul
    echo 已切换到 DHCP 配置。
)

:: 删除临时文件
del "%temp_file%"

@REM pause
:: 等待 3 秒后退出
@REM timeout /t 3 /nobreak >nul

代码效果:

静态设置成DHCP

PixPin_2024-11-28_14-09-11.PNG

DHCP设置成静态

PixPin_2024-11-28_14-12-14.PNG

免费评分

参与人数 14吾爱币 +19 热心值 +11 收起 理由
vincent327 + 1 + 1 我很赞同!
ironlea + 1 谢谢@Thanks!
苏紫方璇 + 7 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!
cnmsh + 1 热心回复!
bcmgzht + 1 + 1 谢谢,刚好可以用上
wzzjnb2006 + 1 + 1 这个必须学习一下。
ztz3421 + 1 热心回复!
wuai9991030 + 1 我很赞同!
baihuxianzi + 1 + 1 用心讨论,共获提升!
woyucheng + 1 + 1 谢谢@Thanks!
yanglinman + 1 谢谢@Thanks!
假好人。 + 1 + 1 谢谢@Thanks!
qazwsxon + 1 + 1 感谢发布原创作品,吾爱破解论坛因你更精彩!
debug_cat + 2 + 1 谢谢@Thanks!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

来自 23#
 楼主| hoochanlon 发表于 2024-11-28 22:15 |楼主

经过 @goblack 相关如下等建议

如果切换很频繁的时候,也不是太容易判断当前网络位置,所以后来我还是写了个小软件,常驻图标显示当前网络是红、黄、绿区。。。避免在公网访问了内网资源导致内网DNS信息泄露这些问题。

从 batch 改为 python,新增功能如下:

  • 自定义IP(自己填静态IP),任务栏托盘粉色小圆标。
  • 自动获取,任务栏托盘绿色小圆标。
  • 固定IP(写死IP),任务栏托盘黄色小圆标。

效果图:

自定义(1)

PixPin_2024-11-28_21-39-08.PNG

自定义(2)

PixPin_2024-11-28_21-40-56.PNG

DHCP

PixPin_2024-11-28_21-30-59.PNG

固定IP

PixPin_2024-11-28_21-34-04.PNG

源码及地址:

import subprocess 
import os
import time
from PIL import Image, ImageDraw
import pystray
from pystray import MenuItem as item
import threading
from tkinter import Tk, Label, Entry, Button, messagebox

# 定义接口名称
interface = "以太网"

# 固定静态 IP 配置(写死的 IP、子网掩码、网关和 DNS)
static_ip = "172.16.1.55"
static_mask = "255.255.255.0"
static_gateway = "172.16.1.254"
static_dns1 = "172.16.1.1"
static_dns2 = "114.114.114.114"

# 创建透明背景的圆形图标
def create_icon(color):
    size = (64, 64)
    image = Image.new('RGBA', size, (0, 0, 0, 0))
    draw = ImageDraw.Draw(image)

    if color == 'green':
        fill_color = (0, 255, 0, 255)
    elif color == 'yellow':
        fill_color = (255, 255, 0, 255)
    elif color == 'pink':
        fill_color = (255, 105, 180, 255)  # 粉色
    else:
        fill_color = (128, 128, 128, 255)  # 默认灰色

    draw.ellipse([0, 0, size[0], size[1]], fill=fill_color)
    return image

# 检查网络是否启用 DHCP
def check_dhcp():
    temp_file = os.path.join(os.getenv('TEMP'), 'display_dhcp_status_output.txt')
    subprocess.run(f'netsh interface ip show config name={interface} > "{temp_file}"', shell=True)
    dhcp_status = None
    with open(temp_file, 'r', encoding='gbk') as file:
        for line in file:
            if "DHCP 已启用" in line:
                dhcp_status = line.split(":")[1].strip()
    os.remove(temp_file)
    return dhcp_status

# 获取当前的 IP 配置
def get_current_ip_config():
    command = f'netsh interface ip show config name="{interface}"'
    result = subprocess.run(command, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE, encoding='gbk')
    output = result.stdout

    ip, mask, gateway, dns1, dns2 = None, None, None, None, None

    for line in output.splitlines():
        if "IP 地址" in line and not ip:
            ip = line.split(":")[1].strip()  # 去掉前后空格
        if "子网掩码" in line and not mask:
            mask = line.split(":")[1].strip()  # 去掉前后空格
        if "默认网关" in line and not gateway:
            gateway = line.split(":")[1].strip()  # 去掉前后空格
        if "DNS 服务器" in line:
            if not dns1:
                dns1 = line.split(":")[1].strip()  # 去掉前后空格
            elif not dns2:
                dns2 = line.strip()

    return ip, mask, gateway, dns1, dns2

# 更新托盘图标状态
def update_icon(icon):
    dhcp_status = check_dhcp()
    ip, mask, gateway, dns1, dns2 = get_current_ip_config()

    # 判断是否为 DHCP
    if dhcp_status == "是":
        icon.icon = create_icon('green')  # DHCP -> 绿色
    # 判断是否为固定静态 IP
    elif (ip == "172.16.1.55"):
        icon.icon = create_icon('yellow')  # 固定静态 IP -> 黄色
    # 否则为自定义静态 IP
    else:
        icon.icon = create_icon('pink')  # 自定义静态 IP -> 粉色

# 切换到 DHCP
def switch_to_dhcp(icon, item):
    subprocess.run(f'netsh interface ip set address name={interface} source=dhcp', shell=True)
    subprocess.run(f'netsh interface ip set dns name={interface} source=dhcp', shell=True)
    update_icon(icon)

# 切换到固定静态 IP
def switch_to_fixed_static(icon, item):
    subprocess.run(f'netsh interface ip set address name={interface} source=static addr={static_ip} mask={static_mask} gateway={static_gateway}', shell=True)
    subprocess.run(f'netsh interface ip set dns name={interface} source=static addr={static_dns1}', shell=True)
    subprocess.run(f'netsh interface ip add dns name={interface} addr={static_dns2} index=2', shell=True)
    update_icon(icon)

# 切换到自定义静态 IP
def switch_to_custom_static(icon, item):
    def input_window():
        def submit():
            diy_ip = entry_ip.get().strip()
            diy_mask = entry_mask.get().strip()
            diy_gateway = entry_gateway.get().strip()
            diy_dns1 = entry_dns1.get().strip()
            diy_dns2 = entry_dns2.get().strip()

            if diy_ip and diy_mask and diy_gateway and diy_dns1:
                subprocess.run(f'netsh interface ip set address name={interface} source=static addr={diy_ip} mask={diy_mask} gateway={diy_gateway}', shell=True)
                subprocess.run(f'netsh interface ip set dns name={interface} source=static addr={diy_dns1}', shell=True)
                if diy_dns2:
                    subprocess.run(f'netsh interface ip add dns name={interface} addr={diy_dns2} index=2', shell=True)
                update_icon(icon)
                root.destroy()
            else:
                messagebox.showerror("错误", "请填写完整的必填项!")

        root = Tk()
        root.title("输入自定义静态 IP 配置")
        root.geometry("400x250")
        root.resizable(False, False)

        Label(root, text="IP 地址:").grid(row=0, column=0, padx=10, pady=5, sticky='e')
        Label(root, text="子网掩码:").grid(row=1, column=0, padx=10, pady=5, sticky='e')
        Label(root, text="网关地址:").grid(row=2, column=0, padx=10, pady=5, sticky='e')
        Label(root, text="首选 DNS:").grid(row=3, column=0, padx=10, pady=5, sticky='e')
        Label(root, text="备用 DNS (可选):").grid(row=4, column=0, padx=10, pady=5, sticky='e')

        entry_ip = Entry(root, width=30)
        entry_mask = Entry(root, width=30)
        entry_gateway = Entry(root, width=30)
        entry_dns1 = Entry(root, width=30)
        entry_dns2 = Entry(root, width=30)

        entry_ip.grid(row=0, column=1, padx=10, pady=5)
        entry_mask.grid(row=1, column=1, padx=10, pady=5)
        entry_gateway.grid(row=2, column=1, padx=10, pady=5)
        entry_dns1.grid(row=3, column=1, padx=10, pady=5)
        entry_dns2.grid(row=4, column=1, padx=10, pady=5)

        Button(root, text="提交", command=submit).grid(row=5, column=0, columnspan=2, pady=10)
        root.mainloop()

    threading.Thread(target=input_window, daemon=True).start()

# 创建任务栏图标
def on_quit(icon, item):
    icon.stop()

def create_tray_icon():
    icon = pystray.Icon("network_status")
    icon.icon = create_icon('gray')

    # 创建托盘菜单
    icon.menu = pystray.Menu(
        item('切换到 DHCP', lambda icon, item: switch_to_dhcp(icon, item)),
        item('切换到固定静态 IP', lambda icon, item: switch_to_fixed_static(icon, item)),
        item('切换到自定义静态 IP', lambda icon, item: switch_to_custom_static(icon, item)),
        item('退出', on_quit)
    )

    update_icon(icon)

    # 定时更新图标状态
    def periodic_update():
        while True:
            update_icon(icon)
            time.sleep(5)

    threading.Thread(target=periodic_update, daemon=True).start()

    icon.run()

if __name__ == "__main__":
     create_tray_icon()
沙发
baishibukele 发表于 2024-11-28 15:01
3#
dxxiong 发表于 2024-11-28 15:35
4#
goblack 发表于 2024-11-28 15:37
思考!震惊。这玩意儿竟然值得用IDE编写。。。

这是单文件自动判断处理。相当于“自锁开关”,一键处理

我是写了多个文件,运行不同的脚本一键切换为DHCP或者不同网段,或者同时添加多个网段

如果切换很频繁的时候,也不是太容易判断当前网络位置,所以后来我还是写了个小软件,常驻图标显示当前网络是红、黄、绿区。。。避免在公网访问了内网资源导致内网DNS信息泄露这些问题。
5#
goblack 发表于 2024-11-28 15:39
话说我还有个建议。。。。尾部pause之后不一定是结束。毕竟已经pause了没必要再往后面添加timeout。
可以直接goto 开头,反复一键切换
6#
silent117 发表于 2024-11-28 15:55
如果你忘了当前网络环境,不如按数字选择
在选择界面显示当前的网络环境,好做判断。
7#
土鸡炖蘑菇 发表于 2024-11-28 15:58
直接添加两个ip不就好了吗,省的切换了,不过外网dhcp的话 有可能会ip冲突罢了
8#
 楼主| hoochanlon 发表于 2024-11-28 16:15 |楼主
goblack 发表于 2024-11-28 15:37
思考!震惊。这玩意儿竟然值得用IDE编写。。。

这是单文件自动判断处理。相当于“自锁开关”,一键处理
...

常驻图标显示当前网络是红、黄、绿区,是在任务栏加小点图标吗?pause和timeout是做代码调试的时候用了,所以没删,单纯注释。网络位置,工位上有内外网线标识的。
9#
goblack 发表于 2024-11-28 16:18
hoochanlon 发表于 2024-11-28 16:15
常驻图标显示当前网络是红、黄、绿区,是在任务栏加小点图标吗?pause和timeout是做代码调试的时候用了, ...

对的。。。。随意用VB写了个小软件。。不到20KB。upx下就3KB.。。。。

不是怕插网线搞错,是经常切换,在用的时候搞错当前网络
10#
guihai3 发表于 2024-11-28 16:19
学习学习
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2025-5-28 15:02

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表