最佳实践的实践 - API 不应将 HTTP 重定向到 HTTPS
原文:jviide - 2024.05.23
TL;DR: 与其将 API 调用从 HTTP 重定向到 HTTPS,不如让失败显而易见。要么完全禁用 HTTP 接口,要么返回明确的 HTTP 错误响应,并撤销通过未加密连接发送的 API 密钥。遗憾的是,许多知名的 API 提供商目前并没有这样做。
背景
当用户将网络浏览器指向 HTTP URL 时,服务通常会将请求重定向到相应的 HTTPS 页面。通信流的这一未加密部分有其缺陷。共享网络中的第三方和网络中介可以从最初的 HTTP 流量中嗅探密码和其他机密,甚至通过 MITM 中间人攻击冒充网络服务器。尽管如此,重定向技术在从基本不加密的早期网络向大部分加密的当今网络过渡的过程中,迈出了有用的第一步。
后来的技术进一步加强了安全性。现在,服务器可以在发送 HTTP 到 HTTPS 的初始重定向响应的同时发送 HSTS(HTTP Strict-Transport-Security
),告诉用户的浏览器从此只能在该域使用 HTTPS。这就将琐碎的嗅探和 MITM 中间人攻击的机会窗口限制在了第一次请求。随后,浏览器增加了 HSTS 预加载列表和 HTTPS-Only 模式,允许完全跳过初始未加密请求。
从可用性和安全性权衡的角度来看,这一切对于面向用户的网站都是合理的。但有趣的是,重定向方法似乎也被 API 广泛采用。API 主要由其他软件使用,因此同样的可用性论点在这里并不适用。此外,许多 API 客户端往往不会像浏览器一样保留他们所看到的 HSTS 标头状态。
本文认为,由于这些因素,应重新考虑将 API 调用从 HTTP 重定向到 HTTPS 的常见做法。虽然本文主要针对 REST API,但其观点也适用于使用 HTTP(S) 作为传输机制的其他类型的 API。
一个简单的拼写错误就足够了
在工作中,我们正在针对第三方 API 构建一个新的集成。初始代码提交中包含了一个拼写错误的 API 基础 URL,写成了 "http://..."
而不是 "https://..."
。这是一个相当容易犯的错误。
这个错误在运行时基本上被掩盖了:第三方 API 对每个请求都会响应 301 重定向到其 HTTPS 端。Node.js 内置的 fetch 功能会愉快且悄悄地 跟随访问这些重定向到 HTTPS 端点。
(注:Go 语言默认的 http.Client
也会自动请求重定向后的端点,除非自定义 CheckRedirect
属性。)
现在,这样的 API 请求都将 API 密钥以明文形式发送到网络上,然后再将其发送到加密端点。一个字母的遗漏可能会在我们不知情的情况下将使用的 API 密钥暴露给第三方。随着集成的进行,代码很有可能会在数年之间,泄露 API 调用中的任何机密。从长远来看,恶意的可能性会不断累积。
幸运的是,我们在代码审查期间发现了这个错误,避免了错误扩散到生产甚至测试中。我们还意识到,我们自己的 API 也进行了类似的 HTTP 到 HTTPS 重定向。
快速失败原则
当 API 将 HTTP 请求重定向到 HTTPS,而 API 客户端默默地跟随访问这些重定向时,它往往会隐藏像上述案例中的拼写错误。一个简单的字母遗漏很容易被忽略,最终进入生产环境,危及整个系统的机密性。
在大多数情况下,最好遵循快速失败原则:未加密的 API 调用应以明显可见的方式失败,这样开发人员可以在开发过程中尽早发现并修复拼写错误。
快速失败最好的解决方案是完全禁用 API 服务器的 HTTP 接口,不再响应对 80 端口的连接尝试。如果初始的未加密连接从未建立,那么就不会发送 API 密钥,从而减轻嗅探攻击的风险,并将 MITM 中间人攻击的机会窗口限制在极小的时间范围内。这种方法适用于以自己的域名(如 api.example.com
)托管的 API。
我们自己的 API 位于 /api
路径下,与我们服务的 Web UI 在同一个域名下。因此,我们对完全禁用 HTTP 接口没有信心,所以选择了第二种方案:所有在 /api
路径下的未加密 HTTP 请求,现在都返回描述性错误信息和 HTTP 状态码 403。在开发过程中可能会出现一些初始明文请求,但开发人员更容易注意到它们。
还有谁?
这解决了我们自己的 API 问题。我们还联系了第三方 API 提供商和几个朋友,让他们检查一下自己的 API。谁知道呢,也许有一些常用的 API 接受 API 密钥(或其他凭证),并且也从 HTTP 重定向到 HTTPS?
我从脑海中列出了一些知名的 API,并做了一个小调查。其中有几个返回 HTTP 错误或完全拒绝连接。这里列出了它们的 cURL 命令,以便查看它们的详细响应:
- Stripe API:返回 403 (“Forbidden”) 和一个描述性错误信息。
curl -i http://api.stripe.com
- NPM Registry API:返回 426 (“Upgrade Required”) 和一个描述性错误信息。
curl -i -X PUT -H 'content-type: application/json' -d '{}' 'http://registry.npmjs.org/-/user/org.couchdb.user:npm'
- Fastmail JMAP API:整个 HTTP 接口似乎已被禁用。
curl -i -H 'Authorization: Bearer foo' http://api.fastmail.com/jmap/session
- …
然而,以下 API 确实 响应了 HTTP 到 HTTPS 的重定向:
- Facebook Graph API
curl -i 'http://graph.facebook.com/me?access_token=foo'
- IBM Cloud API
curl -i "http://iam.cloud.ibm.com/identity/token" -d "apikey=YOUR_API_KEY_HERE&grant_type=urn%3Aibm%3Aparams%3Aoauth%3Agrant-type%3Aapikey" -H "Content-Type: application/x-www-form-urlencoded" -H "Authorization: Basic Yng6Yng="
- OpenAI API — 更新于 2024-05-28,已返回错误。
curl -i -H "Content-Type: application/json" -H "Authorization: Bearer 123" -d '{}' http://api.openai.com/v1/chat/completions
- …
我没有单独向所有这些 API 提供商报告这些发现。有一些未列出的异常,我确实联系了它们,但结果各不相同。
请谨慎对待每个结果:我不得不在没有有效凭证的情况下测试其中一些 API,或者使用文档示例中的凭证。但总体模式表明,API 将 HTTP 请求重定向到 HTTPS 的习惯非常普遍。为什么会这样呢?
最佳实践也需要实践
当与他人谈论这个话题时,许多人都指出,API 从 HTTP 重定向到 HTTPS 的缺点是显而易见的——事后看来是这样。
面向用户的应用程序的重定向经常在最佳实践列表和备忘录中被提及,例如由 OWASP(开放网络应用安全项目)发布的那些。相反,专门针对 API 的建议似乎很少。我只在 OWASP 网站的深处发现了几处提及,例如一个出色的 PDF 幻灯片集,由 Philippe De Ryck 编写,名为"常见 API 安全陷阱":
“常见 API 安全陷阱”的第 8 张幻灯片,重点强调了相关部分。
我的 Google 搜索技巧可能不够好。不过,也许每个建议面向用户的网站进行 HTTP 到 HTTPS 重定向的最佳实践项目,都应该附加明确的注意事项,在显著位置建议不要对 API 进行此类重定向。因此,我在 OWASP 的 GitHub 页面上发起了一个议题,建议相应修改 OWASP 的传输层安全备忘单。
额外内容:以明文响应的流行 API
在审查 API 列表时,我碰到了一些既不重定向也不拒绝未加密请求的流行 API。它们只是以未加密的 HTTP 响应回应未加密的 HTTP 请求,没有在任何阶段强制使用 HTTPS。
也许它们有自己的原因,或者只是意外地错误配置了它们的反向代理。不管怎样,考虑到它们都处理潜在的敏感数据,我通过各自的安全渠道联系了这些 API 提供商,并解释了这个问题。
结论
由于 API 的性质,将 HTTP 重定向到 HTTPS 可能弊大于利。与面向用户的网页不同,API 主要由其他软件使用。API 客户端通常会自动跟随重定向,并且不会维护状态或支持诸如 HSTS 之类的安全标头。这可能导致静默故障,即每个 API 请求中的敏感数据最初都是以明文形式在网络上传输的,没有经过加密。
让我们采用“快速失败”的方法,完全禁用 HTTP 接口或对未加密请求返回明确的错误响应。这可以确保开发人员能够快速注意并修复意外的 http://
URL 为 https://
。我们应将通过未加密连接发送的 API 凭证视为泄露,并立即自动撤销。
在撰写本文时,一些知名且流行的 API 确实将 HTTP 请求重定向到 HTTPS。这种行为似乎很普遍,也许是时候修改最佳实践,明确建议 API 拒绝处理未加密的请求了。
相关文章:
最佳实践的实践 - API 不应将 HTTP 重定向到 HTTPS
原文:jviide - 2024.05.23 TL;DR: 与其将 API 调用从 HTTP 重定向到 HTTPS,不如让失败显而易见。要么完全禁用 HTTP 接口,要么返回明确的 HTTP 错误响应,并撤销通过未加密连接发送的 API 密钥。遗憾的是,许多知名的 A…...
四种跨域解决方案
文章目录 1.引出跨域1.基本介绍2.具体演示1.启动之前学习过的springboot-furn项目2.浏览器直接访问 [localhost:8081/furns](http://localhost:8081/furns) 可以显示信息3.启动前端项目,取消请求拦截器,这样设置,就会出现跨域4.跨域原因 2.跨…...
移动端投屏到大屏幕的操作详解
如果你懒得折腾电脑、电视或其他大屏设备上的影视软件安装及配置,可以选择直接在手机端上将影片投屏到电脑、电视或其他大屏设备上,这里给大家分享三种手机投屏的方法。 系统自带的投屏功能 不管是安卓、鸿蒙还是苹果操作系统,都自带了无线…...
【环境搭建】3.阿里云ECS服务器 安装Redis
在阿里云的 Alibaba Cloud Linux 3.2104 LTS 64位系统上安装 Redis 可以通过以下步骤完成: 1.更新系统软件包: 首先,更新系统软件包以确保所有软件包都是最新的: sudo yum update -y2.安装编译工具和依赖项: Redis…...
动态语言的开源编译器汇总
对于动态语言而言,我们通常不会使用传统意义上的“编译器”,因为动态语言往往是在运行时解释执行的,或者被转换为中间形式(如字节码),再由虚拟机执行。不过,为了性能考虑,现代动态语…...
Linux防火墙配置001
Linux防火墙主要用于控制网络流量,保护系统安全。在Linux中,有几种不同的防火墙管理工具,其中最常见的是iptables和firewalld。本章主要讲述如何关闭防火墙。 操作系统: CentOS Stream 9 操作步骤: 关闭防火墙&…...
Tomcat概述及部署
目录 一.Tomcat概述 1.介绍 2.使用场景 3.组件构成 4.组件结构 5.请求过程 二.Tomcat部署 1.关闭防火墙 2.下载安装JDK 3.安装启动tomcat 4.部署虚拟主机 4.1.创建 xy101 和 xy102 项目目录和文件 4.2.修改 Tomcat 主配置文件 server.xml 一.Tomcat概述 1.介绍 …...
[Vue3:Vite构建项目]:安装router实现登录页面路由跳转
文章目录 一:前置依赖查看依赖安装vite npm create vitelatest sys-instruction-0607 --template vue-ts安装路由:npm install vue-router4安装elementUI:npm install element-plus --save 二:配置文件:viewsÿ…...
概率论与数理统计,重要知识点——全部公式总结
二、一维随机变量及其分布 五个分布参考另外一篇文章 四、随机变量的数字特征 大数定理以及中心极限定理 六、数理统计...
Spring系列-SpringMvc父子容器启动原理解析
1、Spring整合SpringMVC 特性: 说到Spring整合SpringMVC唯一的体现就是父子容器: 通常我们会设置父容器(Spring)管理Service、Dao层的Bean, 子容器(SpringMVC)管理Controller的Bean .子容器可以访问父容器的Bean, 父容器无法访…...
[ssi-uploader插件]解决如何接收服务器返回数据+修改参数名称
前言 ssi-uploader是一款非常好用的多文件上传插件,源码是开源的,在github上面即可下载: https://github.com/ssbeefeater/ssi-uploader 但是源码有些微小的不足,今天我们解决两点问题: 上传文件完成后,…...
InfiniGate自研网关实现思路七
25.网关Nginx负载模型配置 通过模拟多个HTTP服务配置到 Nginx 做负载均衡,以学习API网关负载的配置和使用 API 网关是用于支撑分布式 RPC 接口协议转换提供 HTTP 调用的一套服务,那么 API 网关系统就需要可横向扩展来满足系统的吞吐量诉求。所以这里需…...
277 基于MATLAB GUI火灾检测系统
基于MATLAB GUI火灾检测系统,可以实现图片和视频的火苗检测。火焰识别的三个特征:1个颜色特征,2个几何特征颜色特征:HSV颜色空间下,对三个通道值进行阈值滤波,几何特征1:长宽比,几何…...
【西瓜书】4.决策树
1 递归返回情况 (1)结点包含样本全为同一类别 (2)属性集为空,没有属性可供划分了 或 有属性,但是在属性上划分的结果都一样 (3)结点为空结点 **结束时判定该结点的类别遵循如下规则&…...
区块链--Ubuntu上搭建以太坊私有链
1、搭建私链所需环境 操作系统:ubuntu16.04,开虚拟机的话要至少4G,否则会影响测试挖矿时的速度 软件: geth客户端 Mist和Ethereum Wallet:Releases ethereum/mist GitHub 2、安装geth客户端 sudo apt-get update …...
菜品信息分页查询——后端SpringBoot
1.分页查询的逻辑: 页面发送ajax请求,将分页查询参数(page,pageSize, name)提交到服务端,获取分页数据; 页面发送请求,请求服务端进行图片下载,用于页面图片展示。 开发菜品信息分页查询功能&a…...
利用GPT和PlantUML快速生成UML图用于设计
在软件开发中,设计阶段可是关键的一步。UML(统一建模语言)图能帮我们更清晰地理解和规划系统结构,但手动画UML图有时会很费时费力。好消息是,通过结合使用ChatGPT和PlantUML,我们可以高效地生成UML图&#…...
web-上传项目文件夹到Git远程仓库
Git初识 概念:一个免费开源,分布式的代码版本控制系统,帮助开发团队维护代码 作用:记录代码内容,切换代码版本,多人开发时高效合并代码内容 检验成功 打开bash终端(git专用)命令…...
使用OpenPCDet训练与测试Transformer模型:如何加载自己的数据集
引言 Transformer架构因其强大的序列处理能力和长距离依赖捕捉能力,在自然语言处理领域取得了巨大成功。近年来,这一架构也被引入3D物体检测领域,如Voxel Transformer等,显著提升了模型在复杂场景下的检测性能。OpenPCDet整合了多…...
四舍五入问题
单纯输出四舍五入可以用 printf("%.nf",num); 但是这个方法有时候会出错 代表输出n位四舍五入小数 而将数四舍五入赋值给变量可以用round()函数 a round(num); 表示将num四舍五入赋值给a 但是这么些只能转换位四舍五入的整数 可以改…...
零基础入门学用Arduino 第一部分(三)
重要的内容写在前面: 该系列是以up主太极创客的零基础入门学用Arduino教程为基础制作的学习笔记。个人把这个教程学完之后,整体感觉是很好的,如果有条件的可以先学习一些相关课程,学起来会更加轻松,相关课程有数字电路…...
C++标准库random
random 完整文档看这里 三步走: 选择一种随机数种子选择一个随机数引擎选择一个随机数分布输出 随机数种子 //生成随机数种子,在Linux的实现中,是读取/dev/urandom设备 std::random_device rd; unsigned seed1 rd();// 获取当前时间点作为随机数种子 unsigned seed2 std:…...
电子电气架构——车载诊断DTC一文通
我是穿拖鞋的汉子,魔都中坚持长期主义的汽车电子工程师。 老规矩,分享一段喜欢的文字,避免自己成为高知识低文化的工程师: 没有人关注你。也无需有人关注你。你必须承认自己的价值,你不能站在他人的角度来反对自己。人生在世,最怕的就是把别人的眼光当成自己生活的唯一标…...
Golang | Leetcode Golang题解之第129题求根节点到叶节点数字之和
题目: 题解: type pair struct {node *TreeNodenum int }func sumNumbers(root *TreeNode) (sum int) {if root nil {return}queue : []pair{{root, root.Val}}for len(queue) > 0 {p : queue[0]queue queue[1:]left, right, num : p.node.Left, …...
工业信息化SCI期刊,中科院1区TOP,IF=12.3,收稿范围广泛
一、期刊名称 IEEE Transactions on Industrial Informatics 二、期刊简介概况 期刊类型:SCI 学科领域:工程工业 影响因子:12.3 中科院分区:1区TOP 三、期刊征稿范围 IEEE工业信息学汇刊是一本多学科期刊,发表技…...
Spring Boot整合Redis
Spring Boot整合Redis Spring Boot 整合 Redis 是一种常见的做法,用于在 Spring Boot 应用程序中添加缓存、会话管理分布式锁等功能。 浅谈Redis Redis用于存储数据,且在内存当中进行存储。 但是在日常编写代码时,定义一个变量也就是属于在内…...
kafka的leader和follower
leader和follower kafka的leader和follower是相对于分区有意义的,不是相对于broker。 因为每个分区都有leader和follower, leader负责读写数据。 follower负责复制leader的数据保存到自己的日志数据中,并在leader挂掉后重新选举出leader。 kafka会再…...
git 空仓库笔记
标识身份,建议先完成 Git 全局设置 git config --global user.name “账号” git config --global user.email “email” 方式一:克隆仓库 git clone https://url/your.git cd your_path touch README.md git add README.md git commit -m "add …...
字母异位词分组(charyw)
字母异位词分组 题目描述 给定一个字符串数组,将字母异位词组合在一起。字母异位词指字母相同,但排列不同的字符串。 输入格式 第一行正整数n,表示有n个字符串(1<n<1000) 第二行n个字符串,空格隔开 输出格式 多组字母…...
力扣 41.缺少的第一个正整数
题目描述: 给你一个未排序的整数数组 nums ,请你找出其中没有出现的最小的正整数。 请你实现时间复杂度为 O(n) 并且只使用常数级别额外空间的解决方案。 示例 1: 输入:nums [1,2,0] 输出:3 解释:范围 …...
论坛网站开发平台/网络推广方法有哪些
DTOJ3489 可怜与超市(supermarket)题目题目描述输入格式输出格式样例样例输入1样例输出1样例输入2样例输出2数据范围与提示题解题目 题目描述 九条可怜有bbb块钱,她准备去超市买东西 超市有nnn样商品,其中第iii个商品的价格是ci…...
wordpress缩略图模糊/工具大全
在VMware里克隆出来的CentOS Linux,ifconfig...没有看到eth0,然后重启网卡又报下面错误。 故障现象: service network restartShutting down loopback insterface: …...
域名解析记录值填什么/一个网站可以优化多少关键词
4 案例4:部署Multipath多路径环境 4.1 问题 通过Multipath,实现以下目标: 在共享存储服务器上配置iSCSI,为应用服务器共享存储空间 应用服务器上配置iSCSI,发现远程共享存储 应用服务器上配置Multipath,将相…...
做策划的网站推广/seo美式
假设下面是你的视频网站链接列表,如果别人想爬取你的数据十分轻松,看规则就知道数据库是序列自增的 http://www.xxxx.com/video/1 http://www.xxxx.com/video/2 http://www.xxxx.com/video/3 那么解决这一问题,我们可以使用短地址,…...
如何查看网站用什么代码做的/深圳市企业网站seo
今天早上还是和往常一样,一杯豆奶,可不知怎么地,感觉今天的豆奶有点儿甜呀!难道这就是传说中的甘尽苦来?我这好几斤的小心脏。还是说一下最近的想法吧。虽然有点儿过分,但还是值得记录一下,毕竟…...
南京手机网站制作公司/网站制作设计
先扯两句 经过了漫长的时间,六大设计原则终于结束了,也终于进入到了23中设计模式的学习了。不过设计原则只有六条都写了这么久,设计模式有足足23种,希望这次不要再懒惰了吧。 厚着脸皮激励一下自己《设计模式》——目录&#…...