Ubuntu/RDK 开发环境代理配置:自动开关与局域网代理
整理 Ubuntu 与 RDK 开发环境中的局域网代理配置,包含自动检测、手动开关、sudo 环境继承以及 apt、Git、curl 和 ROS 的排障方法。
在 Ubuntu 和 RDK 开发环境中,代理通常同时服务于 apt、Git、curl、ROS 软件包和 Python 依赖。局域网代理设备可能随网络环境变化,固定写入 Shell 的代理变量会让离线开发、局域网通信和设备调试互相干扰。
这篇文章把 Ubuntu Shell 自动代理脚本与 RDK 局域网代理变量合并为一套配置:启动终端时检测代理端口,端口可用时自动启用;局域网设备地址加入 NO_PROXY,让 SSH、ROS 节点和 WebSocket 通信保持直连。示例中的主机、端口和 RDK 地址全部使用占位符,部署时按实际网络填写。
- Ubuntu 桌面或 RDK 板端的 Bash Shell。
- 代理服务运行在同一局域网的另一台电脑或网关上。
- 需要让 apt、Git、curl 或 ROS 工具读取代理环境变量。
- 需要在代理网络与普通网络之间切换。
先确认当前 Shell:
echo "$SHELL"ps -p "$$" -o comm=本文配置写入 ~/.bashrc。RDK 镜像使用其他 Shell 时,将同一段函数放入对应的启动文件,并按 Shell 语法检查。
| 变量 | 作用 |
|---|---|
| HTTP_PROXY、HTTPS_PROXY | 为 HTTP/HTTPS 客户端提供代理 |
| ALL_PROXY | 为支持该变量的程序提供 SOCKS5 代理 |
| NO_PROXY | 指定本地地址、局域网地址和 RDK 地址直连 |
| PROXY_HOST | 局域网代理设备地址 |
| HTTP_PORT、SOCKS5_PORT | 代理服务的 HTTP 与 SOCKS5 端口 |
同时设置大小写变量可以兼容不同程序。apt、Git、curl 和 ROS 相关进程会继承当前 Shell 导出的环境。
自动检测依赖 netcat-openbsd 提供的 nc:
sudo apt updatesudo apt install netcat-openbsdnc -h初次安装没有代理时,可以临时使用可访问的软件源,或者先在系统网络设置中配置代理。
默认情况下,sudo 会清理一部分环境变量。创建 /etc/sudoers.d/proxy:
sudoedit /etc/sudoers.d/proxy写入:
Defaults env_keep += "http_proxy https_proxy HTTP_PROXY HTTPS_PROXY all_proxy ALL_PROXY no_proxy NO_PROXY"设置文件属主和权限,再检查 sudoers 语法:
sudo chown root:root /etc/sudoers.d/proxysudo chmod 0440 /etc/sudoers.d/proxysudo visudo -c正常结果应包含:
/etc/sudoers: parsed OK/etc/sudoers.d/proxy: parsed OK/etc/sudoers.d/ 下的配置文件需要保持 root:root 和 0440,否则 sudo 可能拒绝读取。
编辑 ~/.bashrc:
nano ~/.bashrc追加以下代码。先替换 PROXY_HOST、HTTP_PORT、SOCKS5_PORT 和 RDK_HOST;这些值也可以先保留占位符,用于检查脚本结构。
# =========================# Ubuntu/RDK 网络代理# =========================
PROXY_SCHEME="http"PROXY_HOST="<PROXY_HOST>"HTTP_PORT="<HTTP_PORT>"SOCKS5_PORT="<SOCKS5_PORT>"RDK_HOST="<RDK_IP>"
# auto: 检测代理端口、系统代理或 TUN;port: 只检测代理端口# system: 检测系统代理后使用上面的代理;tun: 检测 TUN 后使用上面的代理# off: 不在读取 ~/.bashrc 时自动修改代理变量PROXY_AUTO_MODE="auto"
proxy_configured() { [ -n "$PROXY_HOST" ] && [ "$PROXY_HOST" != "<PROXY_HOST>" ] && [ -n "$HTTP_PORT" ] && [ "$HTTP_PORT" != "<HTTP_PORT>" ]}
proxy_port_available() { proxy_configured || return 1 command -v nc >/dev/null 2>&1 || return 1 nc -z -w1 "$PROXY_HOST" "$HTTP_PORT" >/dev/null 2>&1}
proxy_system_enabled() { command -v gsettings >/dev/null 2>&1 || return 1 local mode mode=$(gsettings get org.gnome.system.proxy mode 2>/dev/null) case "$mode" in ""|*none*) return 1 ;; *) return 0 ;; esac}
proxy_tun_enabled() { command -v ip >/dev/null 2>&1 || return 1 ip -o link show 2>/dev/null | awk -F': ' '{print $2}' | cut -d@ -f1 | grep -Eq '^(tun|tap|wg|tailscale|zt)'}
proxy_network_enabled() { proxy_port_available || proxy_system_enabled || proxy_tun_enabled}
proxy_on() { if ! proxy_configured; then [ "${1:-}" = "--quiet" ] || echo "Please configure PROXY_HOST and HTTP_PORT first." return 1 fi
export http_proxy="$PROXY_SCHEME://$PROXY_HOST:$HTTP_PORT" export https_proxy="$PROXY_SCHEME://$PROXY_HOST:$HTTP_PORT" export HTTP_PROXY="$PROXY_SCHEME://$PROXY_HOST:$HTTP_PORT" export HTTPS_PROXY="$PROXY_SCHEME://$PROXY_HOST:$HTTP_PORT"
if [ -n "$SOCKS5_PORT" ] && [ "$SOCKS5_PORT" != "<SOCKS5_PORT>" ]; then export all_proxy="socks5h://$PROXY_HOST:$SOCKS5_PORT" export ALL_PROXY="socks5h://$PROXY_HOST:$SOCKS5_PORT" else unset all_proxy ALL_PROXY fi
# NO_PROXY 的通配符支持取决于客户端;RDK_HOST 用于确保设备地址明确直连。 export no_proxy="localhost,127.0.0.1,::1,$RDK_HOST,10.*,192.168.*,172.*" export NO_PROXY="$no_proxy"
if [ "${1:-}" != "--quiet" ]; then echo "Proxy enabled" echo "HTTP proxy: $http_proxy" if [ -n "$all_proxy" ]; then echo "SOCKS5 proxy: $all_proxy" else echo "SOCKS5 proxy: disabled" fi fi}
proxy_off() { unset http_proxy https_proxy HTTP_PROXY HTTPS_PROXY unset all_proxy ALL_PROXY no_proxy NO_PROXY if [ "${1:-}" != "--quiet" ]; then echo "Proxy disabled" fi}
proxy_status() { if proxy_system_enabled; then echo "System proxy: ON" else echo "System proxy: OFF" fi
if proxy_tun_enabled; then echo "TUN route : ON" else echo "TUN route : OFF" fi
if proxy_port_available; then echo "Proxy port : ON ($PROXY_HOST:$HTTP_PORT)" else echo "Proxy port : OFF ($PROXY_HOST:$HTTP_PORT)" fi
if [ -n "$http_proxy" ]; then echo "Shell proxy : ON" echo "HTTP proxy : $http_proxy" echo "HTTPS proxy : $https_proxy" if [ -n "$all_proxy" ]; then echo "SOCKS5 proxy: $all_proxy" else echo "SOCKS5 proxy: disabled" fi else echo "Shell proxy : OFF" fi}
case "$PROXY_AUTO_MODE" in auto) if proxy_network_enabled && proxy_port_available; then proxy_on --quiet else proxy_off --quiet fi ;; port) if proxy_port_available; then proxy_on --quiet else proxy_off --quiet fi ;; system) if proxy_system_enabled && proxy_port_available; then proxy_on --quiet else proxy_off --quiet fi ;; tun) if proxy_tun_enabled && proxy_port_available; then proxy_on --quiet else proxy_off --quiet fi ;; off) ;; *) echo "Unknown PROXY_AUTO_MODE: $PROXY_AUTO_MODE" ;;esac重新加载:
source ~/.bashrcproxy_status手动控制:
proxy_onproxy_offproxy_statusproxy_on 和 proxy_off 只影响当前 Shell 及其子进程。重新打开终端后,自动逻辑会再次运行。
env | grep -i proxycurl -I --max-time 10 https://example.com使用 -v 可以观察 CONNECT 或 SOCKS5 连接过程:
curl -vI --max-time 10 https://example.comsudo env | grep -i proxysudo apt updatecurl --noproxy '*' -I --max-time 5 http://$RDK_HOST:8000ssh <RDK_USER>@$RDK_HOSTROS、SSH、相机网页和 rosbridge WebSocket 使用的设备地址应放入 NO_PROXY。局域网服务的连通性可以用 curl –noproxy ‘*’ 单独验证,排除代理规则的影响。
代理主要服务于公网依赖下载:
- apt update 和 apt install 获取 Ubuntu、ROS 或 RDK 软件包。
- Git 克隆和拉取远程仓库。
- curl、wget 和 Python 包管理器访问外部地址。
RDK 的 SSH、相机网页、rosbridge WebSocket 和局域网 ROS 通信需要直连。RDK_HOST 与局域网网段写入 NO_PROXY 后,代理变量可以继续保留给公网请求。
nc 只能证明 TCP 端口可以连接,代理服务还需要确认协议类型。HTTP 代理使用 http://,SOCKS5 代理使用 socks5h://。检查代理软件的监听地址、端口和访问控制。
依次检查:
proxy_statussudo env | grep -i proxysudo visudo -csudo apt -o Debug::Acquire::http=true update不同版本 apt 还可以通过 /etc/apt/apt.conf.d/ 单独设置代理;当前配置先使用环境变量,便于 proxy_on 和 proxy_off 统一控制。
检查 NO_PROXY 是否包含 RDK 的实际 IP、主机名和本地网段。不同客户端对通配符和 CIDR 的支持存在差异,最稳定的做法是把 RDK 的实际 IP 单独写入 RDK_HOST。