详解代理自动配置 PAC
转自知乎
最近一直在做跨域中华局域网的工作,了解了很多代理知识和基础概念,很零散,也很细碎。希望通过一段时间的学习,能够自由地穿梭在国际互联网和中华局域网之间。后续会写一系列文章记录我了解到的知识点,本文要说的是我们平时接触比较多的 PAC,全名为 proxy auto-config。
什么是 PAC
PAC,一个自动代理配置脚本,包含了很多使用 JavaScript 编写的规则,它能够决定网络流量走默认通道还是代理服务器通道,控制的流量类型包括:HTTP、HTTPS 和 FTP。
它是一段 JavaScript 脚本:
function FindProxyForURL(url, host) {
return "DIRECT";
}
上面就是一个最简洁的 PAC 文件,意思是所有流量都直接进入互联网,不走代理。
PAC 语法和函数
上面函数中,url 字段就是我们在浏览器地址栏输入的待访问地址,host 为该地址对应的 hostname,return 语句有三种指令:
DIRECT,表示无代理直接连接
PROXY host:port,表示走host:port 的 proxy 服务
SOCKS host:port,表示走host:port 的 socks 服务
而返回的接口可以是多个代理串联:
return “PROXY 222.20.74.89:8800; SOCKS 222.20.74.89:8899; DIRECT”;
上面代理的意思是,默认走222.20.74.89:8800 的 proxy 服务;如果代理挂了或者超时,则走 222.20.74.89:8899的 socks 代理;如果 socks 也挂了,则无代理直接连接。从这里可以看出 PAC 的一大优势:自动容灾。
PAC 提供了几个内置的函数,下面一一介绍下:
dnsDomainIs
类似于 ==,但是对大小写不敏感,
if (dnsDomainIs(host, "google.com") ||
dnsDomainIs(host, "www.google.com")) {
return "DIRECT";
}
shExpMatch
Shell 正则匹配,* 匹配用的比较多,可以是*.http://example.com,也是可以下面这样,
if (shExpMatch(host, "vpn.domain.com") ||
shExpMatch(url, "http://abcdomain.com/folder/*")) {
return "DIRECT";
}
isInNet
判断是否在网段内容,比如 10.1.0.0 这个网段,10.1.1.0 就在网段中,
if (isInNet(dnsResolve(host), "172.16.0.0", "255.240.0.0")) {
return "DIRECT";
}
myIpAddress
返回主机的 IP,
if (isInNet(myIpAddress(), "10.10.1.0", "255.255.255.0")) {
return "PROXY 10.10.5.1:8080";
}
dnsResolve
通过 DNS 查询主机 ip,
if (isInNet(dnsResolve(host), "10.0.0.0", "255.0.0.0") ||
isInNet(dnsResolve(host), "172.16.0.0", "255.240.0.0") ||
isInNet(dnsResolve(host), "192.168.0.0", "255.255.0.0") ||
isInNet(dnsResolve(host), "127.0.0.0", "255.255.255.0")) {
return "DIRECT";
}
isPlainHostName
判断是否为诸如http://barret/,http://server-name/ 这样的主机名,
if (isPlainHostName(host)) {
return "DIRECT";
}
isResolvable
判断主机是否可访问,
if (isResolvable(host)) {
return "PROXY proxy1.example.com:8080";
}
dnsDomainLevels
返回是几级域名,比如dnsDomainLevels(http://barretlee.com) 返回的结果就是 1,
if (dnsDomainLevels(host) > 0) {
return "PROXY proxy1.example.com:8080";
} else {
return "DIRECT";
}
weekdayRange
周一到周五,
if (weekdayRange("MON", "FRI")) {
return "PROXY proxy1.example.com:8080";
} else {
return "DIRECT";
}
dateRange
一月到五月,
if (dateRange("JAN", "MAR")) {
return "PROXY proxy1.example.com:8080";
} else {
return "DIRECT";
}
timeRange
八点到十八点,
if (timeRange(8, 18)) {
return "PROXY proxy1.example.com:8080";
} else {
return "DIRECT";
}
alert
据说这个函数可以用来调试,不过我在 Chrome 上测试并未生效,
resolved_host = dnsResolve(host);
alert(resolved_host);
PAC 文件的安装和注意事项
在 Windows 系统中,通过「Internet选项 -> 连接 -> 局域网设置 -> 使用自动配置脚本」可以找到配置处,下放的地址栏填写 PAC 文件的 URI,这个 URI 可以是本地资源路径(file:///),也可以是网络资源路径(http://)。
Chrome 中可以在「chrome://settings/ -> 显示高级设置 -> 更改代理服务器设置」中找到 PAC 填写地址。
需要注意的几点:
PAC 文件被访问时,返回的文件类型(Content-Type)应该为:application/x-ns-proxy-autoconfig,当然,如果你不写,一般浏览器也能够自动辨别
FindProxyByUrl(url, host) 中的 host 在上述函数对比时无需转换成小写,对大小写不敏感
没必要对 dnsResolve(host) 的结果做缓存,DNS 在解析的时候会将结果缓存到系统中
详解代理自动配置 PAC的更多相关文章
- 企业IT管理员IE11升级指南【15】—— 代理自动配置脚本
企业IT管理员IE11升级指南 系列: [1]—— Internet Explorer 11增强保护模式 (EPM) 介绍 [2]—— Internet Explorer 11 对Adobe Flas ...
- 代理自动配置文件PAC的使用方法
我通常上网使用两个浏览器,safari用于一般上网:Chrome安装SwitchyOmega插件,在不同的代理中切换,来保证某些网站的上网速度. 但是这种方式到了手机上就有点懵,几乎所有的iPhone ...
- Nginx主配置参数详解,Nginx配置网站
1.Niginx主配置文件参数详解 a.上面博客说了在Linux中安装nginx.博文地址为:http://www.cnblogs.com/hanyinglong/p/5102141.html b.当 ...
- mybatis 代码生成器(IDEA, Maven)及配置详解(部分配置你应该不知道)
目录 1 创建代码生成器 1.1 创建Maven项目 1.2 配置 generator.xml 1.3 配置 pom.xml 1.4 使用及测试 2 XML 配置详解 2.1 优先 2.2 官网没有的 ...
- 详解Tomcat核心配置、http协议
Tomcat服务器 Tomcat配置与部署(IDEA) https://www.cnblogs.com/gonghr/p/14731266.html Tomcat手工创建和打包第一个Web工程 在ap ...
- [C#详解] (1) 自动属性、初始化器、扩展方法
文章来源:Slark.NET-博客园 http://www.cnblogs.com/slark/p/CSharp-focus-1.html 代码下载:点我下载 目录 前言 属性与自动属性 属性 自动属 ...
- spring boot actuator端点高级进阶metris指标详解、git配置详解、自定义扩展详解
https://www.cnblogs.com/duanxz/p/3508267.html 前言 接着上一篇<Springboot Actuator之一:执行器Actuator入门介绍>a ...
- Jenkins进阶系列之——12详解Jenkins节点配置
2014-03-02:修正对于lable标签的理解.(1.532.1版本已经给出了官方解释) 2013-12-22:添加JNLP端口修改,修改了一些错误. Jenkins有个很强大的功能:分布式构建( ...
- 详解webpack-dev-server的配置属性
1.devServer.contentBase 它指定了服务器资源的根目录,如果不写入contentBase的值,那么contentBase默认是项目的目录. 在上面例子中产生错误和后来解决错误的 ...
随机推荐
- UPLOADIFY用法
把下面代码 this.settings.upload_url = SWFUpload.completeURL(this.settings.upload_url); this.settings.but ...
- pod 查看当前源/添加源
1 pod 查看当前源 PeiSongs-iMac:5i5jAPP chenpeisong$ pod repo 0 repos 2 pod repo换源 CocoaPods 镜像使用帮助CocoaPo ...
- flysql 里两种传参的方式
传参的方式,两个标清楚: for lists_bx_goods in out_list: sql = XDO().get_update_sql('init_goods_test', { "一 ...
- C#后台将string="23.00"转换成int类型
在C# 后台将String类型转换成int 有以下几种方法: (1) int.TryParse(string); (2) Convert.Toint32(string); (3) (int)stri ...
- 1.Jmeter 快速入门教程(一) - 认识jmeter和google插件
Jmeter是免费开源的性能测试工具( 同时也可以用作功能测试,http协议debug工具 ). 在如今越来越注重知识产权的今天, 公司越来越不愿意冒着巨大的风险去使用盗版的商业性能测试工具. 但如 ...
- oracle执行计划(转载)
转载自 https://www.cnblogs.com/Dreamer-1/p/6076440.html 一:什么是Oracle执行计划? 执行计划是一条查询语句在Oracle中的执行过程或访问路径的 ...
- ELK+filebeat+redis 日志分析平台
一.简介 ELK Stack是软件集合Elasticsearch.Logstash.Kibana的简称,由这三个软件及其相关的组件可以打造大规模日志实时处理系统. 其中,Elasticsearch 是 ...
- lvm 磁盘扩容
LVM磁盘管理 一.LVM简介 LVM是 Logical Volume Manager(逻辑卷管理)的简写,它由Heinz Mauelshagen在Linux 2.4内核上实现.LVM将一个或多个硬盘 ...
- SQL数据库—<6>存储过程
Transact-SQL中的存储过程,非常类似于Java语言中的方法,它可以重复调用.当存储过程执行一次后,可以将语句缓存中,这样下次执行的时候直接使用缓存中的语句.这样就可以提高存储过程的性能. Ø ...
- Java script-数组与字符串方法
数组: 1.concat() 功能:用于连接两个或多个数组,该方法不会改变现有的数组,而仅仅会返回被连接数组的一个副本. 参数:concat(data1,data2,...);所有参数可选,要合并的数 ...