面试题手册

梳理高频技术问题,帮助你按主题复习和查漏补缺。

前端阅读 05月27日 21:56

whistle 代理工具有哪些应用场景?

答案Whistle 是基于 Node.js 的跨平台 Web 调试代理工具,通过规则文本拦截和修改 HTTP/HTTPS 请求与响应。相比直接改代码或配 hosts,核心优势是不改代码、不切环境、规则可复用且仅对本地生效。前端开发中最常用的五个场景:本地联调将线上域名指向本地开发服务,省去切环境或改代码:api.example.com host 127.0.0.1:3000联调只影响你自己,其他同事访问线上不受干扰。多个后端服务可同时指向不同本地端口:api.example.com host 127.0.0.1:3000pay.example.com host 127.0.0.1:4000需要同时联调 WebSocket 时也没问题,whistle 默认支持 ws/wss 协议代理。接口 Mock后端接口未就绪时,用本地 JSON 文件返回模拟数据:api.example.com/user resBody://{mock-user.json}在 Whistle 的 Values 面板中创建 mock-user.json,写入模拟响应体即可。也可以直接指定状态码:api.example.com/error resStatus://500用 resDelay://3000 模拟接口超时,验证前端的 loading 和兜底逻辑。需要按条件 Mock 时,用 resScript 编写动态逻辑:// timeout.js — 支付接口模拟 5 秒超时if (rules.requestHeaders.referer && rules.requestHeaders.referer.indexOf('/pay') !== -1) { rules.responseDelay = 5000; rules.responseStatus = 504;}跨域处理开发阶段给响应注入 CORS 头,绕过浏览器同源限制:api.example.com resHeaders://{cors.json}cors.json 内容示例:{ "access-control-allow-origin": "*", "access-control-allow-methods": "GET,POST,PUT,DELETE,OPTIONS", "access-allow-headers": "Content-Type,Authorization"}比后端加跨域配置更安全——只有你自己生效,不会影响线上环境。移动端抓包与调试手机配代理指向电脑 IP:8899,安装根证书后可捕获 HTTPS 请求:手机 Wi-Fi 设置中配置 HTTP 代理,服务器填电脑 IP,端口填 8899手机浏览器访问 ip:8899,下载并安装根证书iOS 需在"设置 → 通用 → 关于本机 → 证书信任设置"中手动启用信任Android 7+ 默认不信任用户证书,需用 whistle.startProxy(8899, true) 开启全局代理或 root 后安装到系统证书目录配合内置 weinre 远程调试移动端页面 DOM 和控制台:m.example.com weinre://debug也可以安装 whistle.inspect 插件注入 vConsole/Eruda,在 App 内直接查看调试面板:npm i -g whistle.inspectm.example.com whistle.inspect://vconsole异常场景模拟用规则快速构造边界条件,测试前端兜底逻辑:# 模拟接口延迟 3 秒api.example.com/api resDelay://3000# 模拟 500 错误api.example.com/api resStatus://500# 模拟弱网(限速 30kb/s)api.example.com/api reqSpeed://30复杂条件用 resScript 处理,简单场景一条规则就够。规则管理建议用 # 注释 标记每条规则的用途,方便团队协作JSON 数据统一放在 Values 面板管理,别直接内联在规则里调试完及时关闭代理并移除证书,防止隐私泄露和证书风险善用 ignore://* 跳过不需要代理的请求,减少干扰追问whistle 和 Charles/Fiddler 的区别? —— whistle 免费开源、基于规则文本配置(可版本管理)、支持 Node 插件扩展;Charles/Fiddler 偏 GUI 操作,Charles 收费且仅 macOS/Windows,Fiddler 仅 Windows。whistle 天然跨平台且规则可团队共享。如何让 whistle 代理 HTTPS 请求? —— 需要安装并信任 whistle 的根证书:在 Whistle 界面点击 HTTPS → 安装根证书,桌面端安装到系统钥匙串/iOS 信任设置中并启用信任,Android 7+ 用户证书默认不被信任需特殊处理。浏览器和系统层面都需要配置信任。SwitchyOmega 和 whistle 是什么关系? —— SwitchyOmega 是浏览器代理切换插件,负责把浏览器流量导向 whistle 所在的地址和端口;whistle 负责具体的规则匹配和请求处理。两者配合:SwitchyOmega 控制哪些流量走代理,whistle 决定代理后怎么处理。whistle 规则的优先级是什么? —— 默认从上到下匹配,先匹配到的规则优先。可用 enable://proxyFirst 改为代理优先模式。ignore:// 规则会跳过所有其他规则,优先级最高。同名规则后写的会覆盖前面的。whistle 插件有什么用? —— 通过 Node 模块扩展功能,如 whistle.inspect 注入 vConsole/Eruda、whistle.vase 做接口录制回放、whistle.autocoder 自动生成规则。安装后 w2 restart 即可使用。
前端阅读 05月27日 21:46

whistle 如何支持 WebSocket 代理和调试?

核心答案Whistle 基于代理机制自动拦截 WebSocket 连接,在 Network 面板的 Frames 标签中实时展示收发消息,配合规则可以实现暂停、忽略、Mock 等调试操作。具体分三步:1. 抓包查看消息设置代理后,Whistle 自动捕获 ws/wss 请求。在 Network 面板选中该请求,切换到 Frames 标签即可看到实时消息流,JSON 消息会自动格式化。2. 用规则控制连接行为# 暂停接收服务端消息ws://example.com enable://pauseReceive# 暂停发送客户端消息ws://example.com enable://pauseSend# 忽略收发(不转发)ws://example.com enable://ignoreReceivews://example.com enable://ignoreSend3. 用 Composer 构造和发送消息在 Frames 面板底部有 Composer 区域,可以直接向服务端或客户端发送自定义文本/JSON 数据,用于模拟服务端推送或异常响应。追问一:如何修改 WebSocket 消息内容?Whistle 原生不支持直接改写 WebSocket 消息体,需要借助 frameScript 规则或插件:frameScript:在 Rules 面板配置 ws://example.com frameScript://{wsModify.js},脚本中监听 onframe 事件对帧数据做替换插件方式:安装 whistle.script 插件,配置 ws://example.com script://handleWS,在脚本中拦截并修改 message追问二:Whistle 如何处理 wss 连接?和 HTTPS 一样需要安装 Whistle 的根证书。证书装好后,Whistle 通过 MITM 方式解密 wss 流量,抓包和调试方式与 ws 完全一致。追问三:如何 Mock WebSocket 服务端?用 Composer 手动发消息是最快的方式。如需自动化,可以写插件监听 upgrade 事件,在 server.on('connection') 回调中按业务逻辑返回 Mock 数据,配置规则指向该插件即可。
前端阅读 05月27日 21:43

whistle 和 Charles 有什么区别,如何选择使用?

核心结论Whistle 开源免费、规则灵活、扩展性强,适合日常高频调试的前端开发者;Charles 图形界面友好、开箱即用,适合偶尔抓包或不熟悉命令行的用户。两者都是 HTTP/HTTPS 调试代理,但设计理念不同:Whistle 靠规则配置驱动,Charles 靠可视化操作驱动。关键差异| 维度 | Whistle | Charles ||------|---------|---------|| 开源与费用 | 完全开源免费 | 商业软件,$50/许可证 || 技术栈 | Node.js,npm 安装 | Java,独立安装包 || 配置方式 | 规则语法(类似 hosts),可脚本化 | 图形界面点选操作 || 协议支持 | HTTP/HTTPS/WebSocket/TCP | HTTP/HTTPS || 插件生态 | npm 插件,可注入 JS/CSS/vConsole | 内置功能为主,扩展有限 || 移动端抓包 | 需手动配代理+装证书,规则可共享 | 同样需配代理,界面操作更直观 || Mock 能力 | 规则指定接口固定返回,不会超时 | Map Local/Rewrite 实现,配置稍繁琐 |选 Whistle 的典型场景团队协作:规则文件可纳入 Git 版本控制,新人拉取即用频繁 Mock:前端联调时给接口固定回参,避免后端未就绪导致阻塞注入调试:通过插件往页面注入 vConsole、eruda 等移动端调试工具预算有限:个人项目或小团队不想付费选 Charles 的典型场景临时抓包:偶尔排查一个接口问题,打开就能用带宽限速测试:内置 Throttle 功能,模拟弱网环境更方便AJAX 调试:请求/响应结构化展示清晰,搜索匹配可定位到具体字段非技术背景:产品或测试人员更习惯图形界面追问:能不能两个都用?可以。日常开发用 Whistle 处理规则和 Mock,遇到需要弱网测试或快速排查时切 Charles。注意两者不能同时监听同一端口,需错开代理端口配置。
前端阅读 05月27日 21:43

whistle 常见问题有哪些,如何排查和解决?

核心排查思路Whistle 常见问题集中在四个环节:安装启动 → 代理连通 → HTTPS 证书 → 规则生效。逐层排查即可定位大多数问题。安装启动失败怎么办安装报 EACCES 权限错误,用 sudo npm i -g whistle 或改用 nvm 管理 Node 版本。启动报端口占用,先 w2 stop 再 w2 start,或用 -p 指定端口:w2 start -p 8080。启动成功但无法访问 127.0.0.1:8899,运行 w2 status 确认进程存活,再检查防火墙是否放行了对应端口。手机连不上代理怎么排查确保手机和电脑在同一 Wi-Fi 下,手机代理地址填电脑局域网 IP(不是 127.0.0.1),端口填 whistle 监听端口。电脑防火墙需允许该端口入站连接。仍不通时,用 curl -x http://电脑IP:端口 http://example.com 在另一设备验证代理是否可达。HTTPS 抓包失败如何解决这是最高频问题,分两步走:启用 HTTPS 拦截:whistle 面板点击 HTTPS → 勾选 Capture HTTPS安装根证书:浏览器访问 rootca.pro 下载证书,安装到系统"受信任的根证书颁发机构"iOS 额外步骤:安装描述文件后,还需在"设置 → 通用 → 关于本机 → 证书信任设置"中手动开启信任。Android 7+ 默认不信任用户证书,需 root 或配置 networksecurityconfig。Firefox 使用独立证书库,需单独导入。规则不生效怎么排查按以下顺序检查:规则语法是否正确 → 是否被注释或被更靠前的规则覆盖 → 是否需要 w2 restart 重载 → 浏览器缓存是否干扰(用隐身模式验证)。在 Network 面板查看请求是否经 whistle 转发,未转发则代理配置有误。性能问题如何优化规则过多或正则过复杂会拖慢响应。精简规则、避免贪婪匹配,必要时 w2 restart 释放内存。日志积累过多时清空:Network → Tools → Server 清理即可。 追问:应用使用了 SSL Pinning 怎么办?— 用 域名 disable://capture 跳过该域名的解密,或借助 Frida/Xposed 绕过证书校验。多实例共存?用不同端口和 --dirname 指定独立数据目录启动。
前端阅读 05月27日 21:38

whistle 的规则语法是什么,常用的操作符有哪些?

规则语法Whistle 规则的基本格式为 pattern operation [lineProps] [filters],即"匹配模式 + 操作 + 可选配置"。当请求 URL 匹配 pattern 时,whistle 对其执行 operation 定义的操作。常用操作符修改请求/响应:reqHeaders:修改请求头,如 www.test.com reqHeaders://x-token=abcresHeaders:修改响应头,如 www.test.com resHeaders://{cors.json}resBody / resReplace:替换响应体或响应内容映射与代理:file:映射到本地文件,如 www.test.com/api file://{mock.json}host:修改 Host 指向,如 www.test.com host 127.0.0.1:8080proxy / forward:通过代理或指定地址转发请求脚本与延迟:reqScript / resScript:用脚本动态处理请求或响应resDelay:模拟响应延迟,如 www.test.com resDelay://3000匹配模式按模糊程度从精确到宽泛:精确匹配:$www.test.com/api — 加 $ 前缀,仅匹配该 URL路径匹配:www.test.com/api — 匹配该路径下所有请求通配符匹配:*.test.com 或 ^https://**.test.com/**正则匹配:/api\/v2/i — 用正则灵活匹配 URL规则优先级与合并相同 pattern 不同 operation 会合并生效,如 www.test.com resDelay://3000 file://{data.json} 同时延迟并返回本地数据相同 pattern 相同 operation 取最前面的规则用 lineProps://important 提升单行优先级用 excludeFilter / includeFilter 对匹配结果二次过滤追问Whistle 如何实现只对 POST 请求生效?用 includeFilter://m:post 过滤请求方法多条规则冲突时如何排查?看 Rules 面板的匹配日志,或用 lineProps://important 调整优先级Whistle 和 Charles 的核心区别?Whistle 基于规则文件配置、支持脚本和插件,Charles 偏 GUI 操作
前端阅读 05月27日 21:36

whistle 如何进行性能监控和分析,有哪些优化建议?

答案Whistle 的性能监控和分析主要依赖 Network 面板和规则配置,核心思路是:抓包看耗时,规则模拟瓶颈,对比验证优化效果。Network 面板分析请求耗时Whistle 的 Network 面板类似 Chrome DevTools,展示所有经过代理的 HTTP/HTTPS 请求。选中某条请求后,右侧详情面板可查看请求头、响应头、Cookie、耗时等完整信息。通过点击 Timeline 列可切换为时间线视图,直观看到每个请求的起止时间和并发关系,快速定位慢请求。实际操作中,先按耗时排序找出 Top 慢请求,再逐个分析是 DNS 解析慢、服务端响应慢(TTFB 高),还是资源体积大导致下载慢,针对性优化。弱网模拟测试性能下限用 reqDelay 和 reqSpeed 规则模拟弱网:# 延迟 3 秒www.example.com reqDelay://3000# 限速 50kb/swww.example.com reqSpeed://50移动端场景必须做弱网测试。Whistle 的优势在于手机配代理后直接生效,比 Chrome DevTools 的弱网模拟更贴近真实移动环境。规则辅助性能优化验证压缩验证:用 enable://gzip 或 enable://br 强制开启压缩,对比响应体积变化:www.example.com enable://gzip缓存测试:用 cache:// 规则控制缓存策略,验证缓存头是否生效:www.example.com/static cache://86400www.example.com/api cache://no-store资源替换:用 resReplace 替换线上资源为本地优化版本,快速验证优化效果:www.example.com resReplace://old.js local-optimized.js实战优化流程用 Network 面板抓包,按耗时排序找瓶颈弱网模拟验证最差体验规则注入压缩/缓存/替换,对比优化前后数据用 Composer 重放请求,确认优化稳定Whistle 不是性能监控平台,而是开发阶段的性能诊断工具,适合在上线前发现和验证问题,线上监控仍需 RUM 方案。追问Q: Whistle 和 Chrome DevTools 的 Network 面板有什么区别?Whistle 是独立代理,能抓取手机 App、小程序等非浏览器场景的请求,这是浏览器内嵌工具做不到的。Q: 如何用 Whistle 持续监控性能?Whistle 本身不支持持续监控,但可以导出 HAR 文件,结合脚本定期采集后做趋势分析。
前端阅读 05月27日 21:34

whistle 如何解决跨域问题,有哪些常见的跨域场景?

答案Whistle 通过 resCors 协议一行规则即可解决跨域,无需手写脚本或配置 JSON 文件。最常用的三种写法:# 允许所有源(开发环境推荐)api.example.com resCors://*# 仅允许指定源api.example.com resCors://https://www.myapp.com# 启用 CORS 并自动回显请求中的 Originapi.example.com resCors://enableresCors://enable 会把响应头 Access-Control-Allow-Origin 设为请求携带的 Origin 值,适合需要携带 Cookie 的场景。resCors://* 直接设置 Access-Control-Allow-Origin: *,浏览器不会发送凭证但足够覆盖大多数调试需求。如果需要额外控制允许的方法或头部,用 resHeaders 补充:api.example.com resCors://* resHeaders://{cors-extra.json}另一种思路是代理到同源:通过 whistle 将前端和 API 映射到同一域名下,从根源消除跨域:my.app.com/api api.example.commy.app.com 127.0.0.1:3000常见跨域场景本地调试: 前端跑在 localhost:3000,后端在 api.example.com,加一条 resCors://* 即可。多子域名: www.example.com 访问 api.example.com,用 resCors://https://www.example.com 限定来源。携带凭证: 需要带 Cookie 时必须指定具体源,用 resCors://enable 或 resCors://https://www.myapp.com,不能使用 *。线上排查: 结合 SwitchyOmega 将流量导到 whistle,用 resCors://enable 临时放开,抓完即关。追问resCors 和 resHeaders 手动加 CORS 头有什么区别? resCors 是 whistle 内置协议,会同时处理预检请求(OPTIONS)的响应;手动加头容易遗漏 Access-Control-Max-Age 等字段,导致频繁预检。生产环境能用 whistle 解决跨域吗? 不能。whistle 是开发调试工具,生产环境应由 Nginx 或后端服务配置 CORS 策略。Cookie 跨域为什么不能用 *? 浏览器规范要求 Access-Control-Allow-Credentials: true 时 Origin 不能为 *,否则请求直接失败。
前端阅读 05月27日 21:33

whistle 常用的命令行操作有哪些?

核心命令Whistle 的命令行操作都通过 w2 命令完成,常用命令如下:w2 start — 启动服务,默认监听 8899 端口w2 start -p 8080 — 指定端口启动w2 start -S storageName — 指定存储目录,用于多实例管理w2 start -n user -w pass — 设置管理界面的登录用户名和密码w2 stop — 停止服务w2 restart — 重启服务w2 status — 查看运行状态w2 proxy — 设置系统代理w2 proxy 0 — 关闭系统代理w2 ca — 安装 HTTPS 根证书(抓 HTTPS 请求必须)w2 -h — 查看帮助安装只需 npm i -g whistle,Mac 用户也可用 brew install whistle。多实例管理需要同时运行多个 whistle 实例时,每个实例必须指定独立的端口和存储目录:w2 start -p 8010 -S 8010w2 start -p 8020 -S 8020建议端口和存储目录使用相同编号,便于管理。启动进阶参数--httpsPort 8001 — 启用 HTTPS 代理端口--socksPort 1080 — 启用 SOCKSv5 代理端口-P 8889 — 单独设置管理界面端口--inspect — 开启 Node.js 调试(默认 9229 端口)--config /path/to/config.json — 从配置文件加载参数追问:如何在命令行快速切换代理环境?通过 -S 指定不同存储目录,每个目录维护独立的规则集。脚本化切换:#!/bin/bashw2 stopw2 start -p 8899 -S $1执行 ./switch.sh dev 即可切换到 dev 环境的规则,无需手动编辑配置。
前端阅读 05月27日 21:30

如何使用 whistle 拦截 HTTPS 请求,证书如何配置?

答案whistle 作为本地代理,对 HTTPS 请求执行中间人解密:收到客户端 CONNECT 后,用自签 RootCA 为目标域名动态签发证书,再以该证书与客户端建立 TLS 连接,明文拿到请求内容后转发给真实服务器。要让客户端信任这些动态证书,必须把 whistle 的 RootCA 装进系统或浏览器的信任链。证书配置启动并打开管理界面 npm i -g whistle && w2 start浏览器访问 http://127.0.0.1:8899。下载根证书管理界面点击 HTTPS 标签,下载 RootCA。安装到系统信任链Mac:钥匙串访问 → 导入 → 双击设为"始终信任"Windows:双击证书 → 安装到"本地计算机" → 放入"受信任的根证书颁发机构"Linux:sudo cp rootCA.crt /usr/local/share/ca-certificates/ && sudo update-ca-certificates开启拦截勾选 HTTPS 面板的 "Capture HTTPS CONNECTs";只想拦截特定域名用规则 example.com filter://intercept。移动端手机连同一 Wi-Fi,浏览器访问 http://rootca.pro 下载证书,系统设置中信任该证书,再将手机代理指向电脑 IP:8899。踩坑点Android 7+:应用默认不信任用户证书,需 root 或配置 networksecurityconfigiOS 10.3+:安装后还得到 设置 → 通用 → 关于本机 → 证书信任设置 手动开启Firefox:独立证书库,需在 about:preferences 单独导入 RootCA证书锁定:部分 App 校验服务器证书指纹,代理无法拦截追问whistle 拦截 HTTPS 的原理?——中间人代理 + 动态签发证书如何只拦截特定域名?——filter://intercept 规则Android 高版本为什么抓不到包?——用户证书信任域变更
前端阅读 02月21日 16:26

如何开发 whistle 插件,插件的基本结构是什么?

答案Whistle 支持插件系统,可以通过开发插件来扩展其功能,实现自定义的网络请求处理逻辑。插件开发基础1. 创建插件项目mkdir whistle-plugin-democd whistle-plugin-demonpm init -y2. 创建插件入口文件创建 index.js 文件:module.exports = function(server, options) { // 插件初始化逻辑 console.log('Whistle plugin demo loaded'); // 监听请求事件 server.on('request', function(req, res) { // 处理请求 if (req.url === '/api/plugin-demo') { res.writeHead(200, { 'Content-Type': 'application/json' }); res.end(JSON.stringify({ message: 'Hello from whistle plugin', timestamp: Date.now() })); } }); // 监听响应事件 server.on('response', function(req, res) { // 处理响应 console.log('Response:', req.url, res.statusCode); });};3. 配置 package.json{ "name": "whistle-plugin-demo", "version": "1.0.0", "description": "A demo whistle plugin", "main": "index.js", "whistleConfig": { "name": "demo", "description": "Demo plugin for whistle" }}插件功能实现1. 请求拦截和修改module.exports = function(server, options) { server.on('request', function(req, res) { // 修改请求头 req.headers['X-Custom-Header'] = 'Custom Value'; // 记录请求信息 console.log('Request URL:', req.url); console.log('Request Method:', req.method); console.log('Request Headers:', req.headers); });};2. 响应拦截和修改module.exports = function(server, options) { server.on('response', function(req, res) { // 修改响应头 res.setHeader('X-Response-Header', 'Custom Response'); // 修改响应体 const originalEnd = res.end; res.end = function(chunk, encoding) { if (chunk) { const body = chunk.toString(); const modifiedBody = body.replace(/old/g, 'new'); originalEnd.call(res, modifiedBody, encoding); } else { originalEnd.call(res, chunk, encoding); } }; });};3. 中间件模式module.exports = function(server, options) { // 使用 Express 风格的中间件 server.use(function(req, res, next) { console.log('Middleware:', req.url); next(); }); // 路由处理 server.get('/api/test', function(req, res) { res.json({ success: true }); });};插件配置选项module.exports = function(server, options) { // 获取插件配置 const customConfig = options.customConfig || {}; const port = options.port || 3000; console.log('Plugin options:', options);};安装和使用插件1. 本地安装插件cd whistle-plugin-demonpm linkw2 install demo2. 全局安装插件npm install -g whistle-plugin-demow2 install demo3. 在规则中使用插件www.example.com plugin://demo高级功能1. WebSocket 支持module.exports = function(server, options) { server.on('upgrade', function(req, socket, head) { // 处理 WebSocket 升级请求 console.log('WebSocket upgrade:', req.url); });};2. 文件系统操作const fs = require('fs');const path = require('path');module.exports = function(server, options) { server.on('request', function(req, res) { if (req.url === '/api/file') { const filePath = path.join(__dirname, 'data.json'); const data = fs.readFileSync(filePath, 'utf8'); res.end(data); } });};3. 数据库集成const mysql = require('mysql');module.exports = function(server, options) { const connection = mysql.createConnection({ host: 'localhost', user: 'root', password: 'password', database: 'test' }); server.on('request', function(req, res) { if (req.url === '/api/users') { connection.query('SELECT * FROM users', function(error, results) { if (error) { res.statusCode = 500; res.end(JSON.stringify({ error: error.message })); } else { res.end(JSON.stringify(results)); } }); } });};最佳实践错误处理添加适当的错误处理逻辑记录错误日志提供友好的错误信息性能优化避免阻塞操作使用缓存减少重复计算合理使用异步操作安全性验证输入参数防止注入攻击敏感信息加密存储文档和测试编写清晰的使用文档添加单元测试提供示例代码