API密钥与JWT授权对比介绍
发布时间:2022-06-22 13:36:57 所属栏目:安全 来源:互联网
导读:对于某些用例,API密钥就足够了。但另一些情况下,出于安全和灵活的考虑,还需要JSON Web令牌(JWT)授权。所以要比较API密钥和JWT授权两个方案,具体方案还需具体分析。 所有API调用都需要一定程度的安全性和访问控制 具有合理ACL的API密钥可以在不增加太多开
对于某些用例,API密钥就足够了。但另一些情况下,出于安全和灵活的考虑,还需要JSON Web令牌(JWT)授权。所以要比较API密钥和JWT授权两个方案,具体方案还需具体分析。 所有API调用都需要一定程度的安全性和访问控制 具有合理ACL的API密钥可以在不增加太多开销的情况下提供足够的安全性。但是,随着微服务的使用在各种大小任务中增加,API生态系统可能会需要像JWT授权方案这样更统一、更细粒度、更安全的方案。 适合API密钥的情况 对使用基于云的搜索API的在线企业来说,只要数据的基础索引不包含任何机密信息,通常可以公开只读API密钥,而不会带来很大风险。 事实上,出于性能考虑,客户端应用程序应该直接连接到云搜索引擎,从而公开其API密钥——以避免在进入云之前更长时间地访问后端服务器。 另一方面,索引更新需要限制对API密钥的访问,而这些API密钥不应被公开。 在这两个用例(搜索和索引)中,API密钥通常都很不错,无需在JWT 授权上耗费金钱。 何时该考虑JWT授权 API需要越来越灵活,也越来越需要保护。 JWT授权不仅额外提高了安全级别(详见下文),还提供了一种更易于管理、更简单的方法来协调日常中使用大量的API网络。 JWT通过生成包含用户和应用程序级别信息(加密或散列)的单个共享令牌来集中身份验证和授权,以帮助同一生态系统中的所有API确定允许令牌 持有者执行的操作。 乍一看,API的密钥似乎很简单,你只需要发送正确的API密钥,就可以开始使用,但这好得有点不真实。 当生态系统依赖于许多集成的微服务时,大量API密钥管理将会变得混乱、不可靠甚至几乎无法进行。 它们会有数量增加、更改、过期、被删除、ACL更改等等情况,而不通知依赖这些相同API密钥的应用程序和用户。 使用JWT可为单点登录架构奠定基础,下文将详述这一点。 使用API密钥与JWT授权 使用API密钥 API密钥直接、简单且完全透明。它们不代表任何基础信息,不加密秘密消息,只是不可读的唯一ID。 下面是一个在客户端javascript中公开可用的API密钥的示例: 该代码包括一个App ID(app-id-BBRSSHR),它使用API密钥(temp-search-key-ere452sdaz56qsjh565d)进行搜索。 App ID 是指一个面向用户的应用程序(如在线网站或流媒体服务)。API 密钥是临时的,它在一段时间后就过期,从而具有一定保护作用,能防止不必要的使用或滥用。 复制 import { hitTemplate } from "./helpers"; const search = instantsearch({ appId: "app-id-BBRSSHR", apiKey: "temp-search-key-ere452sdaz56qsjh565d", indexName: "demo_ecommerce" }); 1. 2. 3. 4. 5. 6. 另一个例子是索引,它需要一个更安全的API密钥。它有相同的格式(appId+apiKey),但其秘钥要么在编译代码中,要么在后端的安全数据库中,因而对公众隐藏且为私有。 App ID (YourApplicationID) 是指后台系统。 API 密钥 (YourAdminAPIKey) 可以是一个永久的管理密钥,每年只更改一次以简化维护。 复制 use AlgoliaAlgoliaSearchSearchClient; $client = SearchClient::create( 'YourApplicationID', 'YourAdminAPIKey' ); $index = $client->initIndex('demo_ecommerce'); $index->saveObject( [ 'firstname' => 'Jimmie', 'lastname' => 'Barninger', 'city' => 'New York', 'objectID' => 'myID' ] ); 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 使用 JWT 令牌 JWT令牌是一大串不可读的字符,其中包含的信息已隐藏和编码,被签名或加密算法覆盖。它由三部分组成:头部(header)、主体(body)和签名(signature), 由句点分隔:Header.Body.Signature。 复制 EZPZAAdsqfqfzeezarEUARLEA.sqfdqsTIYfddhtreujhgGSFJ.fkdlsqEgfdsgkerGAFSLEvdslmgIegeVDEzefsqd 1. EZPZAADSQFZEEZAREUARLEA是JWT头,其中包含以下信息: 复制 { "alg": "HS256", "typ": "JWT" } { "sub": "1234567890", "name": "John Doe", "iat": 1516239022 } 1. 2. 3. 4. 5. 6. 7. 8. 9. 我们有不同的算法可用,例如 RS256 和 HS256。 这里我们使用 HS256算法,它需要在生成签名时使用私钥,RS256则使用私钥和公钥组合。 sqfdqsTIYfddhtreujhgGSFJ是 JWT 主体(称为有效负载),其中包含用户的身份,以帮助确立令牌用户的权利。 它还提供过期日期(越短越安全)等其他信息。 复制 { "sub": "1234567890", "name": "John Doe", "iat": 1516239022 } 1. 2. 3. 4. 5. fkdlsqEgfdsgkerGAFSLEvdslmgIegeVDEzefsqd是JWT签名 ,它如头部所示,通过使用 HS256 散列方法组合头部、主体和共享私钥组合生成。 复制 HMACSHA256( base64UrlEncode(header) + "." + base64UrlEncode(payload), secret) 1. 2. 3. 4. 这样你就得到了相应的令牌:Header.Body.Signature: 复制 EZPZAAdsqfqfzeezarEUARLEA.sqfdqsTIYfddhtreujhgGSFJ.fkdlsqEgfdsgkerGAFSLEvdslmgIegeVDEzefsqd 1. 关于身份验证(Authentication)和授权(Authorization) API密钥和JWT都用于身份验证和授权,但方式有所不同。 身份验证(Authentication)允许用户或应用程序使用API的一种或多种方法。 授权(Authorization)则规定了用户或应用程序如何使用这些方法。一些应用程序或用户只能读取数据,一些可以更新,一些则是管理员(角色和权限)。API密钥也是如此,由它们的ACL管理,它们可以是只读、写访问或管理。 进行身份验证和授权时,API密钥使用相同的API密钥,JWT授权则需要在生成授权令牌之前进行初始身份验证。 一旦生成了令牌,它就可以在整个生态系统中使用,以确定令牌持有者能做什么和不能做什么。 此外,API密钥验证的是应用程序而不是用户;而JWT同时对用户和应用程序进行身份验证。当然,你可以使用API密钥进行用户级授权,但它的设计并不完善——生态系统需要为每个用户或会话id生成和管理API密钥,这对系统来说是不必要的负担。 保护和安全提升 在安全方面,API密钥和JWT都容易受到攻击。最好的安全措施是为所有端到端通信实施安全架构。 不过,因为它们需要被隐藏,API密钥在历史上不太安全。 你可以使用SSL/TLS/HTTPS隐藏密钥,或者将密钥的使用限制在后端进程。但是,你不能控制所有API的使用,且API密钥也可能会泄漏,同时HTTPS也并不总是可行方案等等。 在JWT中,由于令牌是散列/加密的,因此它具有更安全的方法,不太可能被公开。 JWT令牌中包含哪些信息? API密钥和JWT令牌之间最显著的区别在于,JWT令牌是自包含的:它们包含API保护交易和确定令牌持有人权利粒度所需的信息。 相反,API密钥使用其唯一性来获得初始访问;但是,API需要在中央表中找到与密钥关联的ACL,以精准确定密钥允许访问的内容。 通常,API密钥只保障应用程序层级的安全,为每个用户提供相同的访问权限;而JWT令牌提供用户级访问。 JWT令牌可以包含过期日期和用户标识符等信息,以确定用户在整个生态系统中的权限。 让我们看一下JWT令牌中可以包含的一些信息: iss(颁发者):标识发布 JWT 的主体。 sub(主题):标识作为 JWT 主题的主体, 必须是唯一的。 aud(受众):标识 JWT 的目标接收者(字符串数组/uri)。 exp(过期时间):标识过期时间(UTC Unix),在此之后你必须不再接受此令牌。 它应该在发布时间之后。 nbf(not before):标识不能接受 JWT 的 UTC Unix 时间 iat(发布时间):标识发布 JWT 的 UTC Unix 时间。 jti(JWT ID):为 JWT 提供唯一标识符。 例子: 复制 { "iss": "stackoverflow", "sub": "joe", "aud": ["all"], "iat": 1300819370, "exp": 1300819380, "jti": "3F2504E0-4F89-11D3-9A0C-0305E82C3301", "context": { "user": { "key": "joe", "displayName": "Joe Smith" }, "roles":["admin","finaluser"] } } JWT授权具有灵活性、可靠性和更高的安全性 下面是一个使用场景: 你有多种应用程序,这些程序可能: 允许我们跟踪所有用户API使用情况; 允许访问账单和客户数据; 允许API用户更改在不同系统上设置; 检索产品数据或业务内容等。 使用API密钥操作 当有很多的API在运行时,就会出现问题。这些访问所需的 100 多个 API 密钥要存储在哪里呢?管理过多的API密钥需要为生态系统中运行的所有应用程序提供一个API密钥表。 因此,生态系统中的每个应用程序都必须了解数据库,都需要连接并读取该密钥表。此外,一些应用程序将被允许生成新密钥或修改现有密钥。 所有这些都是不错的方式,但很难维护。管理这问题的一种方法是创建一个API,API根据该数据库来验证密钥。但为此你需要第二个身份验证系统来连接到这个API。 不仅检索API密钥很繁琐,维护其持续时间和授权级别也是冗长的过程,而且并不是每个应用程序都在应用程序级别运行,它们需要用户级别的权限。 此外,API的使用方式因系统而异。更糟糕的是,不同的应用程序共享API密钥,因此要依赖不同的应用程序来维护对共享API密钥的正确访问级别。 (编辑:开发网_开封站长网) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |