应用场景:
- 在域名绑定受限制的情况下隐藏原服务器真实地址,
- 没限制直接绑定托管到cf的域名就可以了,
- 比如在境内IDC上部署一个没备案的域名,
- 只支持二级域名的免费空间换成自己的顶级域名
- 家庭宽带没有80 443端口的情况下对外发布应用
- 访问某些被限制访问的网站,例如Google Drive等 注意某些个别网站是不可以用的,还有登录cookie之类的功能会受限制
在cf中找到worker 创建一个部署,部署过程看提示就行,
基本步骤如下,cf后台 右侧点击 workers 概况 创建一个服务 会提示子域什么的哪个按照提示操作
服务名字 我输入 xxx
项目地址 是类似
xxx.你的账户名.workers.dev 的格式,
启动器 我们选择http处理程序
打开后 项目地址 提示 hello word 就是ok了
然后点击快速编辑 在线编辑,删除初始的代码,粘贴下面的 使用js代码格式
//主要配置这个对象 const config = { basic: { //源站的url upstream: 'http://debug.com/', //对于移动端的源站url mobileRedirect: 'http://debug.com/', }, //屏蔽的国家,默认有CN被我删了,否则会返回错误 firewall: { blockedRegion: ['KP', 'SY', 'PK', 'CU'], blockedIPAddress: [], scrapeShield: true, }, //不同地区源站url的特化 routes: { TW: 'https://debug.com/', HK: 'https://debug.com/', FR: 'https://debug.com/', }, //下面是压缩和缓存配置 optimization: { cacheEverything: false, cacheTtl: 5, mirage: true, polish: 'off', minify: { javascript: true, css: true, html: true, }, }, }; //检查是不是手机 async function isMobile(userAgent) { const agents = ['Android', 'iPhone', 'SymbianOS', 'Windows Phone', 'iPad', 'iPod']; return agents.any((agent) => userAgent.indexOf(agent) > 0); } //主函数 async function fetchAndApply(request) { const region = request.headers.get('cf-ipcountry') || ''; const ipAddress = request.headers.get('cf-connecting-ip') || ''; const userAgent = request.headers.get('user-agent') || ''; request.headers.set("user-agent", "mirror"); //根据屏蔽的国家返回错误 if (region !== '' && config.firewall.blockedRegion.includes(region.toUpperCase())) { return new Response( 'Access denied: booster.js is not available in your region.', { status: 403, }, ); } if (ipAddress !== '' && config.firewall.blockedIPAddress.includes(ipAddress)) { return new Response( 'Access denied: Your IP address is blocked by booster.js.', { status: 403, }, ); } const requestURL = new URL(request.url); let upstreamURL = null; //构造请求的url if (userAgent && isMobile(userAgent) === true) { upstreamURL = new URL(config.basic.mobileRedirect); } else if (region && region.toUpperCase() in config.routes) { upstreamURL = new URL(config.routes[region.toUpperCase()]); } else { upstreamURL = new URL(config.basic.upstream); } //假如源站url有路径就都加一起 requestURL.protocol = upstreamURL.protocol; requestURL.host = upstreamURL.host; requestURL.pathname = upstreamURL.pathname + requestURL.pathname; //有请求主体的跟没有请求主体的 let newRequest; if (request.method === 'GET' || request.method === 'HEAD') { newRequest = new Request(requestURL, { cf: { cacheEverything: config.optimization.cacheEverything, cacheTtl: config.optimization.cacheTtl, mirage: config.optimization.mirage, polish: config.optimization.polish, minify: config.optimization.minify, scrapeShield: config.firewall.scrapeShield, }, method: request.method, headers: request.headers, }); } else { const requestBody = await request.text(); newRequest = new Request(requestURL, { cf: { cacheEverything: config.optimization.cacheEverything, cacheTtl: config.optimization.cacheTtl, mirage: config.optimization.mirage, polish: config.optimization.polish, minify: config.optimization.minify, scrapeShield: config.firewall.scrapeShield, }, method: request.method, headers: request.headers, body: requestBody, }); } const fetchedResponse = await fetch(newRequest); const modifiedResponseHeaders = new Headers(fetchedResponse.headers); if (modifiedResponseHeaders.has('x-pjax-url')) { const pjaxURL = new URL(modifiedResponseHeaders.get('x-pjax-url')); pjaxURL.protocol = requestURL.protocol; pjaxURL.host = requestURL.host; pjaxURL.pathname = pjaxURL.path.replace(requestURL.pathname, '/'); modifiedResponseHeaders.set( 'x-pjax-url', pjaxURL.href, ); } return new Response( fetchedResponse.body, { headers: modifiedResponseHeaders, status: fetchedResponse.status, statusText: fetchedResponse.statusText, }, ); } // eslint-disable-next-line no-restricted-globals addEventListener('fetch', (event) => { event.respondWith(fetchAndApply(event.request)); });
另外有一个有意思的代码
#在线浏览器 https://github.com/yangmyc/jsproxy/blob/master/cf-worker/index.js
然后把域名 替换成 我们地址的顶级域名
首先,域名必须托管在cf 并且是dns托管,第三方cname的方式也可以但是更复杂,我这里不在记录。域名增加一条A解析记录,必须是 代理模式 指向的ip随意
下面要注意的是,必须在域名的界面左侧点击 规则 页面规则 ,然后在右侧 再点击 workers
添加
测试后 ok
进阶=》 源站增加密码认证 参考我之前的文章
根据cf请求的heard里面会有 下面五个数据,我们选择 HTTP_CF_WORKER 这个唯一的
HTTP_CF_WORKER: HTTP_CF_CONNECTING_IP: HTTP_CF_EW_VIA: 15 HTTP_CF_VISITOR: HTTP_CF_RAY:
把上文里面的php代码修改一下
// 先判断 if(strpos($My_agent,'mirror') ==false ){
修改为
// 先判断 UA 以及是否是来自cf if(strpos($_SERVER['HTTP_CF_WORKER'],'leiyanhui.com') ==false && strpos($My_agent,'mirror') ==false) {
另外再把 css js img登图片迁移到 github+jsdelivr
值得注意的是,用户登录要用到的cookie session之类的 反向代理 就别想了。