尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

移动应用安全实践指南:基于OWASP MASVS的存储、加密与认证

移动应用安全实践指南:基于OWASP MASVS的存储、加密与认证 1. 项目概述为什么移动应用安全需要一个“标准答案”在移动互联网时代我们开发的每一个App无论是金融、社交还是工具类本质上都在处理用户的“数字资产”。这些资产可能是银行账户、私密聊天记录也可能是健康数据或家庭住址。作为开发者我们常常面临一个灵魂拷问我做的这个App真的安全吗这个问题的答案过去往往依赖于开发团队的安全意识、经验甚至是“感觉”。直到OWASP MASVS的出现它就像一份权威的“安全体检清单”为移动应用安全提供了清晰、可验证的“标准答案”。OWASP MASVS全称是移动应用安全验证标准。它不是一份枯燥的规范文档而是一套由全球安全专家共同维护的、用于衡量移动应用安全防护水平的“标尺”。简单来说它回答了“一个安全的移动App应该做到哪些事”这个问题。今天我们聚焦于MASVS中三个最核心、也最容易出问题的领域数据存储、加密和认证。这不仅仅是技术选型更是构建用户信任的基石。一个在本地明文存储用户密码的App无论功能多么炫酷都像是一座没有大门的金库随时可能崩塌。我见过太多因为忽视这些基础安全控制而引发的安全事故用户数据被恶意应用读取、传输过程中的敏感信息被截获、认证机制被绕过导致账户被盗。这些问题的根源往往不是开发者技术不行而是缺乏一套系统性的安全实践指南。MASVS正是为此而生。接下来我将结合自己多年的移动安全审计经验为你拆解MASVS在存储、加密和认证方面的具体要求并分享从理论到落地的最佳实践与避坑指南。无论你是刚入门的安全工程师还是希望提升产品安全性的开发负责人这份详解都能让你对移动应用“内功”的修炼有一个清晰的方向。2. MASVS安全控制框架深度解析2.1 MASVS的架构与安全要求层级要理解MASVS的具体控制项必须先看懂它的整体架构。MASVS并非一个“一刀切”的标准它采用了分层设计以适应不同安全级别的应用需求。整个标准主要分为三个层级L1标准安全级这是所有面向公众的移动应用必须达到的基线要求。它主要防范那些利用公开工具和常见技术就能发起的攻击比如通过逆向工程分析应用逻辑、拦截未加密的网络流量、利用常见的注入漏洞等。L1的要求是“合理的”意味着在不过度增加开发复杂度和成本的前提下能够抵御大多数自动化扫描和低技能攻击者的威胁。例如要求敏感数据不能明文存储在本地、通信必须使用TLS、应用必须具备基本的抗篡改能力等。L2深度防御级这一层级适用于处理敏感数据如医疗信息、财务详情或提供高价值功能如移动支付、企业数据访问的应用。L2在L1的基础上增加了针对更专业、更有针对性的攻击的防护措施。它要求应用具备“深度防御”能力即即使某一层防护被突破还有其他机制能够阻止或延缓攻击。例如要求实现证书绑定Certificate Pinning以防止中间人攻击、使用白盒加密技术保护密钥、具备高级的运行时完整性检测等。L3抵御逆向工程与篡改级这是最高级别通常用于对安全有极端要求的场景比如金融交易核心App、政府机密应用、高价值游戏防外挂等。L3的要求聚焦于让应用本身变得“难以分析”和“难以修改”。它要求应用具备强大的代码混淆、反调试、防篡改和防逆向工程能力。攻击者即使拿到了应用安装包也很难理解其内部逻辑或对其进行恶意修改。达到L3级别通常需要集成专业的应用保护RASP或代码混淆工具。理解这三个层级至关重要。在项目初期你就应该根据应用处理的数据敏感性和面临的威胁模型确定需要满足哪个层级通常是L1或L2。这直接决定了后续技术方案的选择和投入的成本。盲目追求L3可能会带来巨大的性能和开发体验负担而只满足L1对于一款银行App来说则是远远不够的。2.2 存储、加密与认证在MASVS中的核心地位在MASVS的众多控制项中存储V2、加密V3和认证V4构成了移动应用安全最核心的“铁三角”。它们分别对应了数据生命周期的三个关键状态静态、传输中和使用中。存储静态数据安全数据安静地躺在设备的文件系统、数据库或偏好设置里。这是攻击者最容易直接访问的“宝藏”。MASVS V2系列控制项的核心思想是“不该存的别存必须存的好好存”。它强制要求开发者审视哪些数据真的需要本地持久化并对必须存储的敏感数据如令牌、个人身份信息提供强有力的保护防止通过文件浏览器、备份或恶意应用进行窃取。加密传输与存储安全加密是安全的“翻译官”它将明文数据转换为攻击者无法理解的密文。MASVS V3系列控制项涵盖了传输加密TLS和静态加密。它不仅仅要求“使用加密”更对加密的实现质量提出了要求比如密钥管理、算法强度和随机数生成。一个常见的误区是使用了AES加密就万事大吉但如果密钥硬编码在代码里加密形同虚设。认证会话与访问安全认证是系统的“门卫”负责确认“你是谁”。MASVS V4系列控制项关注移动端特有的认证场景如生物识别集成、本地认证PIN/图案、与远程服务的认证交互以及会话管理。移动设备的丢失和被盗风险很高因此认证机制必须平衡安全性与用户体验例如在设备解锁后提供短暂的免认证窗口但敏感操作仍需重新认证。这三者环环相扣。一个脆弱的认证机制会导致攻击者合法登录进而访问未加密的存储数据而糟糕的存储实践可能会泄露用于加密或认证的密钥。因此MASVS将它们作为独立的验证目标要求我们必须进行系统性的设计和实现。3. 存储安全最佳实践从“存什么”到“怎么存”3.1 数据分类与敏感数据最小化原则安全存储的第一步不是急着选择SQLite还是Realm而是进行彻底的数据分类。你需要像整理房间一样审视应用产生的所有数据并给它们贴上标签。我通常建议团队建立一份《数据资产清单》至少包含以下字段数据名称如“用户登录令牌”、数据类型字符串、二进制、存储位置Keychain、SharedPreferences、数据库文件、敏感级别高、中、低、加密状态、生命周期何时创建、何时销毁。敏感级别的划分至关重要高敏感数据一旦泄露会造成严重法律后果或用户财产损失。例如登录密码应只存哈希值而非明文、生物特征模板绝对不可恢复、支付密码、完整的身份证号、私钥。中敏感数据泄露会侵犯用户隐私但未必直接导致财产损失。例如手机号、邮箱、姓名、地址、会话令牌Token。低敏感数据公开或半公开信息。例如用户昵称、应用偏好设置主题、语言。MASVS的核心原则是敏感数据最小化。这意味着能不存就不存这是最高原则。例如用户的密码永远不应该存储在客户端。认证成功后服务器下发的访问令牌Access Token和刷新令牌Refresh Token需要存储但应将其视为高敏感数据处理。能少存就少存如果只需要用户手机号的后四位用于显示就不要存储完整的手机号。如果需要身份证信息考虑是否只存储哈希值或部分脱敏后的信息用于验证。能短存就短存为数据设定明确的生命周期。会话令牌应有合理的过期时间并在用户登出或应用卸载时立即将其从所有存储位置清除。不要让数据“长生不老”。实操心得在代码评审中我习惯用一个简单的“数据流白板”来追溯敏感数据。从用户输入开始画出一条线追踪它经过的每一个函数、每一个变量、最终写入的每一个文件或数据库字段。这条线越长、分支越多风险点就越多。这个可视化过程能帮助团队快速发现不必要的数据持久化点。3.2 安全存储位置与API的正确使用确定了要存什么接下来就是选择“保险箱”。不同的操作系统提供了不同安全级别的存储API。iOS平台Keychain ServicesKeychain是苹果提供的安全存储容器是存储高敏感数据的首选。它的核心优势是硬件级保护当设备锁定时Keychain中的数据受Secure Enclave安全隔区保护即使设备被越狱提取Keychain数据也极其困难。访问控制可以为Keychain项设置访问控制列表ACL例如要求设备解锁、用户存在生物识别或两者同时满足才能访问。数据隔离Keychain数据以应用为边界隔离但也可以通过共享钥匙串Shared Keychain在开发团队的应用间安全共享数据。使用要点使用kSecAttrAccessible属性明确数据可访问性。对于最敏感的数据如加密密钥使用kSecAttrAccessibleWhenUnlockedThisDeviceOnly这意味着数据仅在设备解锁时可访问且不会备份到iCloud。避免使用kSecAttrAccessibleAlways这相当于把保险箱钥匙放在门口的地毯下。将Keychain视为“密钥/令牌存储库”而不是通用数据库。不要用它来存储大量结构化数据。Android平台Keystore System EncryptedSharedPreferencesAndroid的情况稍复杂因为设备碎片化严重但核心原则是使用系统提供的硬件级安全存储。Android Keystore系统这是存储加密密钥和证书的黄金标准。它能在可信执行环境TEE或安全硬件如StrongBox中生成和存储密钥确保私钥材料永远不会出现在应用进程的内存中。你应该使用Keystore来生成和存储用于加密本地数据的AES密钥。// 示例生成一个受Keystore保护的AES密钥 val keyGenerator KeyGenerator.getInstance(KeyProperties.KEY_ALGORITHM_AES, AndroidKeyStore) val keySpec KeyGenParameterSpec.Builder( my_app_secret_key, KeyProperties.PURPOSE_ENCRYPT or KeyProperties.PURPOSE_DECRYPT ) .setBlockModes(KeyProperties.BLOCK_MODE_GCM) // 使用GCM模式提供认证加密 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) .setKeySize(256) .build() keyGenerator.init(keySpec) val secretKey keyGenerator.generateKey() // 此后你可以用这个secretKey去加密你的数据但secretKey本身由系统安全保管。EncryptedSharedPreferences对于需要存储的简单键值对数据如用户设置、令牌这是比普通SharedPreferences安全得多的选择。它是Jetpack Security库的一部分底层使用上述Keystore管理的密钥来自动加密数据。val masterKey MasterKey.Builder(applicationContext) .setKeyScheme(MasterKey.KeyScheme.AES256_GCM) .build() val sharedPreferences EncryptedSharedPreferences.create( applicationContext, secret_shared_prefs, masterKey, EncryptedSharedPreferences.PrefKeyEncryptionScheme.AES256_SIV, EncryptedSharedPreferences.PrefValueEncryptionScheme.AES256_GCM ) sharedPreferences.edit().putString(api_token, eyJhbG...).apply()跨平台与数据库加密对于使用SQLite等本地数据库的应用如果数据库中含有敏感数据必须对数据库文件进行整体加密。可以使用SQLCipher一个开源的SQLite扩展来实现透明的加密解密。关键点是用于加密数据库的密码或密钥必须来自上述的安全存储如Keychain/Keystore而不是硬编码或简单派生。常见问题很多开发者问既然有了Keychain/Keystore为什么还要加密数据库因为Keychain/Keystore的存储空间和访问性能不适合大量数据。最佳实践是用Keystore生成一个强密钥用这个密钥通过SQLCipher加密整个数据库文件。这样密钥安全数据也安全。3.3 日志、缓存与备份中的敏感信息泄露这是最容易被忽视的“泄密后门”。开发者为了方便调试常常会在日志中打印完整的请求响应、用户ID甚至令牌。这些日志可能被其他恶意应用读取如果权限设置不当或者在将日志发送到远程服务器进行分析时发生泄露。最佳实践生产环境禁用调试日志使用构建变体或配置开关确保在Release版本中所有调试日志Log.d, NSLog被彻底关闭或重定向到空输出。对日志内容进行脱敏如果某些信息必须记录如错误追踪务必进行脱敏。例如将用户手机号13800138000记录为138****8000将令牌eyJhbGciOiJIUzI1NiIs...记录为Token[前10位]...。清理缓存应用缓存如图片、网络响应缓存可能包含敏感信息。确保缓存有合理的过期策略并在用户执行“清除缓存”或登出操作时主动清理所有缓存目录。处理应用备份Android和iOS都支持应用数据备份。你必须明确哪些数据可以备份哪些不行。对于包含高敏感数据的文件或数据库必须通过设置android:allowBackupfalseAndroid或在文件属性中设置NSFileProtectionComplete且不包含在iCloud备份中iOS来禁止备份。否则用户备份到云端的数据可能成为攻击目标。4. 加密机制的实施与密钥管理4.1 传输层安全TLS配置的魔鬼细节几乎所有移动应用都需要与服务器通信TLS是这条通信通道的“防盗门”。但仅仅启用TLS是不够的错误的配置会让这扇门形同虚设。1. 证书验证必须严格禁用所有不安全的协议明确禁用SSLv3, TLSv1.0, TLSv1.1。最低应使用TLSv1.2并优先支持TLSv1.3。在Android网络配置和iOS的NSAppTransportSecurity中明确指定。正确实现证书锁定这是MASVS L2的要求。证书锁定有两种方式公钥锁定在应用包中预置服务器证书的公钥哈希。连接时对比服务器证书公钥的哈希值与预置值是否一致。即使证书到期续签只要公钥不变应用仍可连接。证书锁定预置整个证书的哈希。证书到期更换后必须更新应用。注意证书锁定会增加运维复杂性证书更新需发版。通常建议在L2级应用中使用并配合可靠的证书更新机制。可以使用TrustKit等成熟库来简化实现。2. 正确处理自签名证书或私有CA 对于企业内网应用可能会使用私有CA签发的证书。客户端必须正确地将私有CA的根证书导入到信任库中。绝对禁止为了图方便而实现一个接受所有证书的X509TrustManager或NSURLSession的didReceiveChallenge回调这完全破坏了TLS的安全性。3. 使用强密码套件 确保服务器和客户端协商使用强密码套件。优先使用ECDHE密钥交换和AES-GCM加密算法。可以通过在线工具如SSL Labs的SSL Test测试服务器配置并在客户端代码中如果平台允许指定优先的密码套件列表。4.2 静态数据加密算法选择与模式运用对于必须本地存储的敏感数据我们需要对其进行加密。这里有两个关键决策用什么算法以及用什么模式。算法选择对称加密用于加密大量数据。AES是唯一的选择。密钥长度应使用256位。非对称加密用于密钥交换或数字签名。使用RSA密钥长度至少2048位或ECC椭圆曲线密码学如ECDSA更高效。加密模式与填充 这是最容易出错的地方。绝对禁止使用ECB模式它会暴露数据的模式。推荐使用认证加密模式它同时提供机密性和完整性校验。AES-GCM目前的首选。它将加密和认证通过GMAC结合效率高且能防止密文被篡改。AES-CBC HMAC如果平台不支持GCM可以使用CBC模式但必须结合HMAC使用独立的密钥对密文进行完整性验证。顺序必须是先加密然后对密文计算HMAC。验证时先验证HMAC通过后再解密。一个完整的本地数据加密流程示例应用启动时尝试从Android Keystore/iOS Keychain中获取一个唯一的AES密钥Key_A。如果不存在则通过Keystore/Keychain API在安全硬件内生成一个新的Key_A。当需要存储用户令牌时使用Key_A和AES-GCM模式加密令牌明文得到一个密文Ciphertext和一个认证标签TagGCM生成。将Ciphertext Tag GCM使用的IV一起存储到文件或数据库中。当需要读取时用Key_A解密并验证Tag。踩坑实录我曾审计一个应用它使用了AES-CBC加密但把IV初始化向量固定写死在代码里。这是一个严重错误。IV必须是随机且不可预测的对于相同的密钥和明文每次加密都必须使用不同的IV否则会泄露信息。GCM模式内部会处理IV通常称为Nonce但也必须保证其唯一性。4.3 密钥管理的生命周期的核心加密的安全性完全依赖于密钥。密钥管理是加密体系中最脆弱的一环。MASVS对此有严格要求。1. 密钥的生成与存储永远不要硬编码密钥这是最低级的错误。任何出现在代码中的字符串常量都能被轻易逆向出来。使用安全的随机源生成密钥或IV时必须使用密码学安全的随机数生成器CSPRNG如SecureRandom(Java/Kotlin),SecRandomCopyBytes(iOS)。密钥必须存储在安全硬件中如前所述使用Android Keystore或iOS Keychain来生成和存储主密钥。确保密钥标记为不可导出这样即使拥有root权限也无法直接提取密钥明文。2. 密钥的轮换与销毁密钥轮换长期使用同一个密钥会增加风险。应制定密钥轮换策略。例如可以为每个用户或每个会话生成一个数据加密密钥DEK而这个DEK本身又被一个更高层级的密钥加密密钥KEK保护。轮换时只需更换KEK并重新加密所有DEK即可无需重新加密全部数据。密钥销毁当用户注销、数据需要永久删除时不仅要删除加密数据更要安全地销毁解密密钥。在Keystore/Keychain中删除密钥条目是有效的方法。确保密钥材料从内存中被清除。3. 白盒加密的考量 对于L3级别或面临高级威胁的应用如防止游戏外挂可能需要考虑白盒加密。传统加密假设攻击者看不到密钥运算过程但在移动端应用可能被逆向。白盒加密技术将密钥与加密算法混淆使得即使攻击者能观察整个加密过程也难以提取出密钥。但这会显著增加性能开销和实现复杂度通常需要采购专业的商业SDK。5. 认证与会话安全设计5.1 移动端特有的认证挑战与设计原则移动设备的认证与Web端有很大不同。设备可能丢失、被共用用户期望更便捷的体验如生物识别。MASVS V4针对这些特点提出了要求。设计原则本地认证与远程认证分离设备解锁密码/PIN/生物识别是本地认证用于解锁设备本地存储的密钥或令牌。访问远程服务器需要远程认证通常使用令牌。两者目的不同不要混淆。渐进式认证根据操作的敏感度动态要求认证。例如查看余额只需设备已解锁而转账则需要再次输入密码或进行生物识别验证。短会话与长令牌结合访问令牌Access Token生命周期应较短如15分钟以减少被盗用的风险。刷新令牌Refresh Token生命周期可以较长用于获取新的访问令牌但其存储必须极其安全且服务端应有吊销机制。5.2 生物识别集成与本地认证的安全实现集成生物识别Touch ID, Face ID, 指纹可以极大提升用户体验和安全性。但实现时需注意iOS (LocalAuthentication Keychain)使用LAContext评估生物识别策略.deviceOwnerAuthenticationWithBiometrics。关键点生物识别成功后的结果不应该直接是一个密码或令牌而应该是一个“授权”用于访问Keychain中受ACL保护的项。例如将加密密钥的kSecAttrAccessible设置为.whenPasscodeSetThisDeviceOnly并关联.touchIDAny这样只有生物识别成功后才能从Keychain中取出该密钥进而解密数据。提供回退机制允许用户使用设备密码Passcode作为备选方案。Android (BiometricPrompt)使用BiometricPromptAPI它提供了标准化的对话框和生命周期管理。结合CryptoObjectBiometricPrompt的强大之处在于可以与CryptoObject绑定。你可以将一个Cipher或Signature对象传给BiometricPrompt只有在生物识别成功后这个加解密或签名操作才会被授权执行。这意味着密钥材料本身不需要离开Keystore。val cipher getCipherFromKeystore() // 从Keystore获取一个已初始化的Cipher对象 val biometricPrompt BiometricPrompt(...) val promptInfo BiometricPrompt.PromptInfo.Builder()...build() biometricPrompt.authenticate(promptInfo, BiometricPrompt.CryptoObject(cipher))本地认证的替代方案 对于不支持生物识别的设备或场景可以使用设备PIN/图案或自定义的应用级PIN。注意自定义PIN应具备防暴力破解机制如尝试次数限制、延迟递增并且其哈希值加盐应存储在安全区域如Keychain/Keystore保护下的文件而不是简单的SharedPreferences。5.3 令牌管理、会话安全与防重放攻击移动应用通常使用令牌Token来维持与服务器的会话。安全地管理令牌是认证环节的重中之重。1. 令牌的存储与传输存储访问令牌和刷新令牌都应视为高敏感数据。必须使用前面章节所述的安全存储机制EncryptedSharedPreferences/Keychain进行加密存储。传输令牌应放在HTTP请求的Authorization头部如Bearer token而不是URL参数或Cookie中以防止日志记录泄露。2. 令牌的刷新与过期实现自动且安全的令牌刷新逻辑。当访问令牌过期时使用刷新令牌向认证服务器获取新的访问令牌。刷新令牌轮换最佳实践是每次使用刷新令牌获取新访问令牌时服务端都颁发一组全新的刷新令牌和访问令牌并使旧的刷新令牌立即失效。这可以防止刷新令牌被重复使用。客户端需要处理刷新令牌也过期的情况此时应引导用户重新登录。3. 防重放攻击 即使令牌是加密的攻击者也可能截获一个有效的请求并重复发送重放攻击。 mitigation措施包括使用短期令牌缩短访问令牌有效期。在令牌或请求中引入一次性标识如JWT中可以包含jtiJWT ID声明服务端维护一个已使用jti的短期黑名单。请求签名对于特别敏感的操作如支付可以对整个请求包含时间戳、随机数用客户端私钥签名服务端验证签名和时间戳的有效性。这通常与双向TLSmTLS结合使用达到L2的安全要求。4. 登出与令牌吊销客户端登出时必须立即删除本地存储的所有令牌和会话状态。应调用服务器的令牌吊销端点使该刷新令牌在服务端立即失效。这需要网络请求因此要做好错误处理但本地删除必须无条件执行。6. 从合规到实践安全控制集成与测试验证6.1 将MASVS要求集成到开发流程中安全不是最后一个阶段才贴上的“膏药”而应贯穿整个软件开发生命周期SDLC。需求与设计阶段在编写第一行代码前就根据应用类型确定需要满足的MASVS层级L1/L2。在技术方案评审时针对存储、加密、认证等模块对照MASVS检查清单进行设计评审。编码阶段将MASVS的关键控制点转化为团队的安全编码规范。例如“所有敏感数据必须使用EncryptedSharedPreferences或Keychain存储”、“网络请求必须使用TLS 1.2并验证证书”、“禁止在任何日志中输出令牌、密码等敏感信息”。可以利用静态代码分析工具SAST的规则来部分自动化检查。测试阶段建立动态安全测试DAST和手动测试流程。使用OWASP ZAP、MobSF等工具进行自动化扫描。手动测试应包含逆向工程测试使用工具如jadx, hopper反编译APK/IPA检查是否有硬编码密钥、敏感字符串。本地存储检查在Root/Jailbreak设备上使用文件浏览器或adb检查应用数据目录确认敏感数据是否被加密存储。网络抓包测试使用Burp Suite或Charles验证TLS配置是否安全、传输数据是否加密、证书锁定是否生效。认证与会话测试测试令牌过期逻辑、登出功能、会话并发控制等。6.2 自动化安全测试与工具链推荐手动测试效率低应尽可能自动化。静态应用安全测试MobSF移动安全框架可对APK/IPA文件进行静态分析能快速发现硬编码密钥、不安全的权限、泄露的敏感信息等并部分覆盖MASVS检查点。SonarQube安全插件集成到CI/CD流水线中每次提交代码都进行扫描。Android Lint / iOS 分析器配置自定义规则检查是否有使用不安全的API如HttpURLConnection。动态应用安全测试OWASP ZAP可以配置为自动化代理对应用进行主动和被动扫描发现网络层面的漏洞。Frida / Objection动态插桩工具可用于在运行时测试认证绕过、修改内存数据、绕过证书锁定等是高级安全测试的利器。依赖项检查OWASP Dependency-Check检查项目依赖的第三方库是否存在已知的公开漏洞CVE。6.3 常见安全漏洞场景与修复方案实录根据我的审计经验以下是一些高频出现的问题及解决方案场景一日志中的敏感信息泄露问题在Release版本的日志中打印了完整的HTTP请求/响应其中包含Authorization: Bearer eyJ...。修复使用ProGuard/R8混淆代码并移除所有调试日志。或者实现一个自定义的日志工具在Release构建时自动过滤或替换掉令牌、密码等模式字符串。场景二不安全的本地数据存储问题将用户登录状态以isLoggedIntrue的形式存储在SharedPreferences中且文件权限为全局可读。修复登录状态应由令牌的存在与否来判断。令牌本身必须使用EncryptedSharedPreferences存储。检查AndroidManifest.xml中android:allowBackup设置并确保敏感文件不被包含在备份中。场景三弱加密实现问题使用自定义的“加密”算法如字节异或循环或者使用AES-ECB模式。修复立即改用标准算法。使用Android Keystore系统生成密钥并采用AES-GCM模式进行加密。对于遗留数据需要设计一个安全的数据迁移方案。场景四证书验证被禁用问题在代码中重写了TrustManager接受所有证书以便在测试环境中使用自签名证书。修复为开发和测试环境配置独立的构建变体Build Variant或配置文件。在Debug版本中可以配置信任特定的自签名证书将证书打包到Asset中并创建自定义TrustManager但在Release版本中必须使用严格的证书验证并考虑实现证书锁定。场景五生物识别集成逻辑缺陷问题应用使用生物识别仅仅是为了进入应用主界面认证成功后将用户凭证密码明文存储在内存中供后续API调用使用。修复生物识别应作为访问安全存储Keychain/Keystore的“钥匙”。认证成功后从安全存储中取出加密的令牌来访问API。凭证本身不应长期驻留在应用内存中。安全是一个持续的过程而非一劳永逸的状态。将OWASP MASVS作为移动应用安全的蓝图将其控制项融入到需求、设计、编码、测试和运维的每一个环节才能构建出真正值得用户信赖的移动应用。记住每一次安全的代码提交都是对用户隐私和资产的一份郑重承诺。
返回列表