托管代理
托管代理让只接受代理设置的应用经由 URnetwork 发送流量:curl、脚本、爬虫,或者 Shadowrocket 这样的手机应用。这份指南说明在 ur.io 上哪里能找到代理的 URL,以及如何把它填进常见的客户端。
一条适用范围说明:托管代理没有密封会话。你的客户端设备运行在运营方内部,由运营方把代理的协议翻译成网络自己的协议。站在运营方和你的流量之间的,是威胁模型里描述的代理不记日志的设计,而不是密封。提供者仍然不知道你是谁。如果应用本身能运行 URnetwork,那么 URnetwork 应用和 SDK 是更私密的途径。
两种代理
ur.io 能创建两种可供第三方客户端使用的代理:
| HTTPS 代理 | SOCKS5 代理 | |
|---|---|---|
| 套餐 | 所有套餐 | UR Pro |
| ur.io 上的 URL | https:// | socks5h:// |
| 令牌放在哪里 | 放在主机名里,不需要用户名和密码 | 作为用户名;从不检查密码 |
| 客户端必须支持 | HTTPS 代理,即与代理之间使用 TLS | 带用户名和密码的 SOCKS5 |
| 承载内容 | 网页流量:HTTP,以及经 CONNECT 的 HTTPS | TCP 连接,以及经 UDP associate 的 UDP |
SOCKS5 代理不支持 BIND,并会丢弃超过 2 KiB 的 UDP 数据报。ur.io 还能在 UR Pro 上创建 WireGuard 配置文件。把下载的 .conf 文件导入 WireGuard 应用即可;本指南其余部分讲 HTTPS 和 SOCKS5。
获取代理的 URL
- 在 ur.io 登录,打开代理(Proxies)(ur.io/app/proxies)。
- 选择创建代理(Create proxy)。
- 选择代理类型:HTTPS、SOCKS5 或 WireGuard。SOCKS5 和 WireGuard 带有 Pro 标记。在免费档上,创建按钮会先提供 Pro。
- 选择位置。搜索国家、地区或城市,或者保留最佳可用(Best available),它使用网络上的任意提供者。每个位置都会显示它有多少提供者。
- 选择 Create HTTPS proxy 或 Create SOCKS5 proxy。新代理会连同它的 URL 一起出现。
列表中的每个 HTTPS 和 SOCKS5 代理都有复制URL(Copy URL),它会复制带令牌的完整 URL;还有 ×,用于删除这个代理。
读懂 URL
https:// <token>. <host>: <port>
socks5h:// <token>: x@<host>: <port><token>是代理的令牌,一长串字母和数字。它是代理唯一的凭据,字母大小写无关紧要。- 在 HTTPS URL 里,令牌是主机名的第一段。把
<token>.原样填作代理主机,与 ur.io 显示的完全一致:主机名里的令牌就是你的登录凭据。<host> - 在 SOCKS5 URL 里,令牌位于
socks5h://和:x@之间。<host>在@之后,<port>在最后一个:之后。 - 其中的
x是占位密码。SOCKS5 代理从不检查密码,所以填什么都可以;但有些客户端只有在同时设置了密码时才会发送用户名,Python 的requests就是其中之一,所以 ur.io 的 URL 带上了这个x。如果客户端要求分别填写用户名和密码,用户名填令牌,密码随便填。 - 保留
socks5h里的h。它让代理去解析主机名,于是域名查询经由提供者发出,而不是从你的机器发出。如果用不带 h 的socks5,curl 会先在你的机器上解析域名。
把 URL 当作密码对待。 任何拿到它的人都能使用这个代理,而代理的流量消耗的是你账户的数据。如果 URL 泄露了,在 ur.io 上删除那个代理,代理就不再接受它的令牌。然后再创建一个新的。
用 curl 检查是否可用
# HTTPS proxy, on every plan
curl -x 'https:// <token>. <host>: <port>' https:// api. bringyour.com/ my-ip-info
# SOCKS5 proxy, on UR Pro
curl -x 'socks5h:// <token>: x@<host>: <port>' https:// api. bringyour.com/ my-ip-info/my-ip-info 会返回你的请求来自哪个地址,以及这个地址位于何处。经过代理时,那就是你所选位置中某个提供者的地址。HTTPS 代理需要 curl 7.52 或更新版本。
浏览器
给浏览器加代理最简单的办法是 URnetwork 扩展,它会创建并管理自己的托管代理。见浏览器入门。
如果要改用你在 ur.io 上创建的代理,请用它的 HTTPS URL。Chrome 根本无法发送 SOCKS5 用户名。操作系统的代理设置和 Firefox 的手动代理设置通常都无法描述 HTTPS 代理。
Chrome、Edge 及其他 Chromium 系浏览器。 在命令行上带着代理启动浏览器。单独的配置文件目录能让这个参数生效,即使你平时用的浏览器窗口还开着:
# macOS
open -na "Google Chrome" --args --user-data-dir= "$HOME/ urnetwork-proxy-profile" --proxy-server= "https:// <token>. <host>: <port>"
# Linux
google-chrome --user-data-dir= "$HOME/ urnetwork-proxy-profile" --proxy-server= "https:// <token>. <host>: <port>"
# Windows, in Command Prompt (Edge: msedge instead of chrome)
start chrome --user-data-dir= "%USERPROFILE%\urnetwork-proxy-profile" --proxy-server= "https:// <token>. <host>: <port>"Firefox。 Firefox 的手动设置里没有 SOCKS 的用户名栏,也没有 HTTPS 代理类型,所以改用一个只有一行的代理自动配置(PAC)文件。把下面的内容存为 urnetwork.pac:
function FindProxyForURL(url, host) {
return "HTTPS <token>.<host>:<port>";
}然后打开设置 → 常规 → 网络设置 → 设置…(Settings → General → Network Settings → Settings…),选择自动代理配置 URL(Automatic proxy configuration URL),填入该文件的地址,例如 file:/// 或 file:///,再选择确定(OK)。要停用时,在同一个对话框里选择不使用代理(No proxy)。
手机应用:Shadowrocket 等
手机上的代理应用,比如 iOS 上的 Shadowrocket,用几个字段来设置一台 SOCKS5 服务器。在 ur.io 上创建一个 SOCKS5 代理(UR Pro)并复制它的 URL。在应用里添加一台服务器,按 URL 填写:
| 字段 | 值 |
|---|---|
| 类型(Type) | SOCKS5 |
| 地址、服务器或主机(Address) | <host>:@ 与最后一个 : 之间的部分 |
| 端口(Port) | <port>:最后一个 : 之后的数字 |
| 用户或用户名(User) | <token>:socks5h:// 与 :x@ 之间的部分 |
| 密码(Password) | 任意值,例如 x |
保存服务器,选中它,然后打开连接。如果要覆盖整部手机,iOS 或 Android 上的 URnetwork 应用不需要代理,而且是更私密的途径。
Python
requests 两种代理都能用。SOCKS5 需要 socks 附加组件(pip install "requests[socks]"),而且它的 URL 需要一个占位密码:
import requests
proxy = "https:// <token>. <host>: <port>" # HTTPS proxy, every plan
# proxy = "socks5h:// <token>: x@<host>: <port>" # SOCKS5 proxy, UR Pro
r = requests.get(
"https:// api. bringyour.com/ my-ip-info",
proxies={"http": proxy, "https": proxy},
timeout=30,
)
print(r.json()["info"]["ip"])httpx 接受同样的 URL;SOCKS5 需要 pip install "httpx[socks]"。aiohttp 接受 HTTPS 代理:
import asyncio
import aiohttp
import httpx
with httpx. Client(proxy= "https:// <token>. <host>: <port>") as client:
print(client.get("https:// api. bringyour.com/ my-ip-info").json())
async def main():
async with aiohttp. ClientSession() as session:
async with session.get("https:// api. bringyour.com/ my-ip-info", proxy= "https:// <token>. <host>: <port>") as r:
print(await r.json())
asyncio.run(main())Scrapy 的默认下载处理器无法经 HTTPS 代理抓取 https:// 页面:它会停下并报错 "HTTPS proxies for HTTPS destinations are not supported"。请改用上面的某个库来抓取这些页面。
Node.js
对于 fetch,把 HTTPS 代理交给 undici 的 ProxyAgent:
import { fetch, ProxyAgent } from "undici";
const dispatcher = new ProxyAgent("https:// <token>. <host>: <port>");
const res = await fetch("https:// api. bringyour.com/ my-ip-info", { dispatcher });
console.log(await res.json());对于 node:https 以及接受 agent 的库,使用 https-proxy-agent;SOCKS5 则用 socks-proxy-agent:
import https from "node:https";
import { HttpsProxyAgent } from "https-proxy-agent";
// import { SocksProxyAgent } from "socks-proxy-agent";
const agent = new HttpsProxyAgent("https:// <token>. <host>: <port>");
// const agent = new SocksProxyAgent("socks5h:// <token>: x@<host>: <port>");
https.get("https:// api. bringyour.com/ my-ip-info", { agent }, (res) => res.pipe(process. stdout));其他程序:proxychains
在 Linux 上,proxychains-ng 能让一个程序的连接经由 SOCKS5 代理(UR Pro)发出,即使这个程序本身没有代理设置。它靠预加载一个库来工作,所以管不到静态链接的程序,其中包括大多数 Go 程序。它的第一个代理必须是 IP 地址,而不能是主机名,所以先查出地址:
dig +short <host>把这个地址写进配置文件 urnetwork.conf:
strict_chain
proxy_dns
[ProxyList]
socks5 <ip> <port> <token> x然后通过它运行程序:
proxychains4 -f urnetwork.conf curl https:// api. bringyour.com/ my-ip-infoproxy_dns 让 proxychains 经由代理解析域名。如果之后连接不再可用,重新查一次地址。
限制
| 免费档 | UR Pro | |
|---|---|---|
| 活跃代理 | 5 | 1,000 |
| 每分钟新建代理 | 5 | 20 |
浏览器扩展创建的代理也计算在内。限制只阻止新建代理:你已有的代理照常工作,删除一个就能腾出位置再建一个。代理会一直保留,直到你删除它;闲置约 30 天未用的代理会被自动删除。
独立出口 IP
托管代理通常会把连接分散到多个提供者上,所以你的两个代理可能从同一个地址出网。开启独立出口 IP(UR Pro)后,每个代理只经由一个提供者出网,而这个提供者的地址不会被你的其他代理使用。只要该提供者保持健康,代理就一直使用这个出口。
- 开启方式: 在代理页面创建代理时,勾选独立出口 IP。把代理数量设为最多 20,可以一次创建多个。在 API 里,在
proxy_config中加入"unique_。exit": true - 限制: 独立出口代理和其他代理计入同样的限制:1,000 个活跃代理,每分钟新建 20 个。
- 你能看到什么: 每个代理会显示它的出口所在的位置(城市、地区和国家)以及开始使用的时间。出口的 IP 地址不会显示。想看 IP,可以通过代理访问一个 IP 查询地址,例如用上面的 curl 命令。
- 提供者出故障时: 代理会自动换一个新的独立出口,期间显示正在更换出口…。每小时的自动更换次数有限制;超过限制后,代理会等待并稍后再试。在 API 里,
"unique_会让代理改为等你处理:它会显示出口已失效,直到你手动更换。exit_ replace": "manual" - 更换出口: 给代理换一个新的独立出口。每个代理的出口每分钟可更换一次,每天最多 60 次。如果该位置没有其他空闲的独立出口,代理会保留当前的出口。
- 没有可用的独立出口: 当该位置所有健康的出口都已被你的其他代理占用时,ur.io 会提示你,并且不会创建代理;这次尝试不计入你的限制。请换一个位置,或者选最佳可用。
故障排查
ur.io 拒绝创建代理。 它会显示原因(消息为英文)。在免费档上:
- "Your plan's limit of 5 active proxies is reached. Remove a proxy to create another, or upgrade to UR Pro for more."(你的套餐已达到 5 个活跃代理的上限。)删除不再使用的代理,或者升级。
- "Your plan allows 5 new proxies a minute. Try again in a minute, or upgrade to UR Pro for more."(你的套餐每分钟只允许新建 5 个代理。)等一分钟再试。
在 UR Pro 上,同样的消息会给出 Pro 的限制,并且不提升级。
SOCKS5 代理拒绝登录。 curl 会报下面其中一条,其他客户端各有各的措辞:
User was rejected by the SOCKS5 server (1 1).令牌错误或不完整,或者代理已被删除。从 ur.io 重新复制 URL。No authentication method was acceptable.客户端没有发送用户名。把用户名设为令牌,并填一个占位密码,比如x。
HTTPS 代理拒绝连接。 curl 会报 CONNECT tunnel failed, response N,其中 N 是:
- 407:代理没有找到有效的令牌。从 ur.io 重新复制 URL,并把完整的
<token>.填作代理主机。<host> - 502:代理已不存在,例如你删除了它;或者无法连到目标。
- 403:调用方的地址不在代理的 IP 锁定范围内。只有通过 API 创建并设置了 IP 锁定的代理才有这种锁定。
如果客户端收到空回复,或者连接立刻被关闭,它多半是在用明文 HTTP 和代理通信。请在支持 HTTPS 代理的客户端里使用 https:// URL。
页面很慢或超时。 试试最佳可用,或者提供者更多的位置。代理的流量消耗你账户的数据,所以数据用完的账户无法建立新连接。
出口 IP 会变。 和应用一样,托管代理会把它的连接分散到所在位置的多个提供者上。网站看到的地址可能每次连接都不一样。如果想让每个代理固定一个出口 IP,请在 UR Pro 上用独立出口 IP 创建它。
代理位置不对。 最佳可用可能从任何国家出网。创建代理时选好国家、地区或城市。ur.io 无法移动你已有的代理:在你想要的位置新建一个,然后删除旧的。
用 API 自动化
代理页面调用的是运营方 API:带 proxy_config 的 POST /network/,其中 initial_ 选择位置。返回的 proxy_ 里有 https_、socks_ 和 auth_token。API 返回的 socks_ 不含用户名:像 ur.io 那样,把 auth_token 加作用户名。由 IP 地址或子网组成的 lock_ip_list 可以限制谁能使用代理。上面的限制同样适用于 API。
如需独立出口 IP,在 proxy_config 中加入 unique_exit:
{
"proxy_config": {
"unique_exit": true,
"initial_ device_ state": {
"location": { "connect_ location_ id": { "best_available": true } }
}
}
}加入 "unique_ 后,代理的提供者出故障时会保持在原出口上,直到你手动更换;默认值为 "auto"。
返回的 proxy_ 给出出口的 exit_id、country_code、region、city、exit_since、state(assigned、replacing 或 no_supply)、有原因时的 state_reason,以及 replace_mode。GET /network/ 会在每个代理的 exit 中报告同样的信息,与它的 proxy_client 并列。带 no_ 的拒绝表示该位置已没有你的代理尚未使用的出口。用代理的 client_id 调用 POST /network/,可以把它换到一个新的独立出口,返回新的 exit;超过更换频率时会以 rate_limited 拒绝,没有其他空闲出口时以 no_ 拒绝。调用它需要你网络的登录凭证或 API 密钥。