客户端签名密钥如何存储才能保证安全? - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
szandy6
V2EX    问与答

客户端签名密钥如何存储才能保证安全?

  •  
  •   szandy6 2023-08-22 11:23:53 +08:00 2475 次点击
    这是一个创建于 833 天前的主题,其中的信息可能已经有所发展或是发生改变。

    客户端请求 API 时,一般要带上签名信息,签名参数用的密钥( secret key)怎么存储才能保证安全,还是说有其他更好的方案,比如放在服务端,大家一般是怎么做的。

    第 1 条附言    2023-08-22 18:09:35 +08:00
    在网上也看到很多人说 https 环境下,没必要在对参数进行签名,国外很多大厂的 Open API 都是没有签名的,这种说法很有道理,我也挺赞同的。但在国内,没有几个大厂的 Open API 是不签名的。
    30 条回复    2023-08-23 15:46:42 +08:00
    dzdh
        1
    dzdh  
       2023-08-22 11:31:04 +08:00
    webauthn ?
    EchoAI
        2
    EchoAI  
       2023-08-22 13:56:49 +08:00 via Android
    我们目前是这么做的:Android 使用 so 文件,iOS 使用 a 文件,web 使用 wasm 文件。密钥和算法都在内部实现,同时做了很多防反编译的策略。
    szandy6
        3
    szandy6  
    OP
       2023-08-22 15:34:50 +08:00
    @EchoAI 我们之前也是这么干的,不过安全部门说会被反编译出来。
    EchoAI
        4
    EchoAI  
       2023-08-22 15:40:08 +08:00
    只要是密钥需要存储在客户端,就会被拿出来。只是时间的问题。绝对的安全是不存在的。
    szandy6
        5
    szandy6  
    OP
       2023-08-22 15:49:21 +08:00
    @EchoAI 是的,能做的就是提高一点破解的复杂度,没有绝对安全。
    tool2d
        6
    tool2d  
       2023-08-22 15:50:09 +08:00
    我看到过的版本是密钥和时间强相关,客户端 6 小时就会变动一次,用算法生成的。

    要破解密钥容易,要拿到算法还是有一点难度的。
    0o0O0o0O0o
        7
    0o0O0o0O0o  
       2023-08-22 16:08:10 +08:00 via iPhone
    先说观点:放在客户端的全部都是能够被公开的东西。

    > 安全部门说会被反编译出来

    一些白盒密码方案大约就是为了应付这种情况,说是应付,因为它们和 #2 在一部分攻击者看来没有太多本质区别。
    xiangyuecn
        8
    xiangyuecn  
       2023-08-22 16:08:22 +08:00
    http 时代的遗留产物。
    yinmin
        9
    yinmin  
       2023-08-22 16:29:46 +08:00 via iPhone
    一了百了的方案是改成不对称加密。客户端保存 rsa 公钥(是公开的,没必要保密),客户端用 rsa 公钥加密数据后上传,服务器用 rsa 用私钥解密。

    直接从理论上解决问题。
    edwardhodges
        10
    edwardhodges  
       2023-08-22 16:38:50 +08:00
    客户端不要直接请求这个 API 。客户端请求自己的业务服务器,然后服务器来请求这个 API ,密钥放在服务器就好了。
    tool2d
        11
    tool2d  
       2023-08-22 16:41:16 +08:00
    @yinmin 不行哦,客户端能用 rsa 公钥加密,那么黑客也能用 rsa 公钥加密。

    服务器收到后,都能解密。分不清哪个是黑客签名,哪个是真客户端签名。
    mdn
        12
    mdn  
       2023-08-22 16:49:58 +08:00
    @edwardhodges 业务服务器如何分辨是自己的客户端了
    hsfzxjy
        13
    hsfzxjy  
       2023-08-22 16:51:33 +08:00
    放在系统原生的钥匙串应该安全吧?比如安卓的 https://developer.android.com/reference/android/security/KeyChain
    szandy6
        14
    szandy6  
    OP
       2023-08-22 18:05:19 +08:00
    @yinmin HMAC 与加密需求不一样,如果是数据加密,现在非对称加密是比较成熟的方案。
    SteveRogers
        15
    SteveRogers  
       2023-08-22 18:13:50 +08:00 via iPhone
    密钥本地二次加密、二加密后的密钥分开存储,然后放到多处。
    xiaoke
        16
    xiaoke  
       2023-08-22 18:16:36 +08:00 via Android
    搭车请教,看到一些安卓 APP 直接把证书文件放在 assets 目录下,有风险吗?
    0o0O0o0O0o
        17
    0o0O0o0O0o  
       2023-08-22 18:22:26 +08:00 via iPhone
    @tool2d #11 你说的这是客户端软件层面 **无解** 的事情(包括白盒),客户端的所有混淆都可以被分析所有逻辑都可以被模拟,只是难易度的区别。

    > 分不清哪个是黑客签名,哪个是真客户端签名

    这对应的应该是一个完整的风控系统,而不单纯是客户端该考虑的
    iX8NEGGn
        18
    iX8NEGGn  
       2023-08-22 21:54:43 +08:00 via iPhone
    你没搞明白,国内大厂的 api 签名是为了防止重放攻击,参与签名的参数一般都包含时间,你这个属于 SSL Pinning ,为了提升绕过客户端请求的难度,破解是避免不了的,只是增加破解难度而已。
    rocmax
        19
    rocmax  
       2023-08-22 22:16:38 +08:00 via Android   1
    一般应用加密只是为了防止篡改请求。如果你的应用真的需要用签名核实身份(例如比特币钱包类),请使用 HSM 。如果是手机应用的话内置加密模块有类似功能,可以保证密钥不离开硬件。
    edwardhodges
        20
    edwardhodges  
       2023-08-23 08:34:19 +08:00
    @mdn 已经是业务服务器了,那就可以设置自己的登录等业务了。登录后获取 token ,用 token 来做校验不是常规操作?
    mdn
        21
    mdn  
       2023-08-23 09:45:03 +08:00
    @edwardhodges #20 客户端加签名在没有被破解的情况下都是 信任的客户端,token 无法证明是客户端请求的 API
    edwardhodges
        22
    edwardhodges  
       2023-08-23 10:09:41 +08:00
    @mdn 是不是想复杂了。这个跟客户端没有什么关系吧,举个例子,token 根据手机号登录验证后获取,然后根据当前用户的 token 来请求业务服务器。业务服务器根据这个 token 判断是哪个用户,然后业务服务器再来调用比如 openai 的接口。就是说使用 secret key 调用三方 api 的行为是发生在自己服务器的。 而客户端的验证方式就是传统的验证方式,所有 app 都是这么进行的。 客户端就是被破解了又怎么样,最多知道了 api 接口(客户端里面没有保存三方的 secret key 这些信息),那又怎么样。
    CodeCodeStudy
        23
    CodeCodeStudy  
       2023-08-23 10:15:18 +08:00
    @yinmin #9 非对称加密太慢了,不应直接用非对称加密数据,而是用非对称加密对称加密的密钥,然后用对称加密数据
    mdn
        24
    mdn  
       2023-08-23 11:07:48 +08:00
    @edwardhodges #22 客户端加签名,想要防止某些用户绕过客户端直接请求接口,比如签到等功能,token 用户自己也能看到,签名需要用户破解
    IvanLi127
        25
    IvanLi127  
       2023-08-23 13:43:42 +08:00 via Android
    签名是防谁篡改负载?防非法用户篡改用登录凭据,防网络链路爱咋存咋存,防合法用户那得靠硬件了。
    msg7086
        26
    msg7086  
       2023-08-23 14:16:24 +08:00
    @tool2d #11
    > 分不清哪个是黑客签名,哪个是真客户端签名。

    要不然呢?难道你还能分清你对面的是客户端还是黑客?
    EchoAI
        27
    EchoAI  
       2023-08-23 14:24:34 +08:00 via Android
    @edwardhodges #22 客户端被破解了,不仅知道了 API ,用户的 token 也能被拿到,还省得去破解密钥了,直接使用 token 请求 API 就可以了。
    tool2d
        28
    tool2d  
       2023-08-23 14:31:58 +08:00
    @msg7086 你普通 ssh 连接,服务器可以设置客户端指纹的白名单。就算黑客有密码和密钥,只要客户端指纹不对,服务器也是可以拒绝请求的。

    客户端被挟持发请求,和黑客第三方 IP 发起恶意请求,对服务器来说,还是有区别的。
    edwardhodges
        29
    edwardhodges  
       2023-08-23 14:46:44 +08:00
    又看了下讨论,如果想把请求绝对限制在自己指定的客户端里,理论上只能增加难度,无法绝对的。不清楚大家的需求,感觉这个需求本身意义就不大吧。 使用加固混淆等方式,增加客户端 app 被破解的难度,所有请求必须使用信任机构颁发的证书的 https ,不在客户端存放重要的信息,验证流程通过服务器来校验。这些操作下来,理论上已经很安全了吧。
    msg7086
        30
    msg7086  
       2023-08-23 15:46:42 +08:00
    @tool2d 客户端可以视作开源,黑客直接伪造指纹就行了。
    有些时候是不需要从头开始搞的,拿现成的代码来植入点东西跑可能会更方便。
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     2666 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 27ms UTC 15:05 PVG 23:05 LAX 07:05 JFK 10:05
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86