苹果授权登陆 服务端验证(java)
需要的jar包:
jose4j-0.6.4.jar;jwks-rsa-0.9.0.jar;jjwt-0.9.1.jar;
jar包下载地址:https://download.csdn.net/download/loveLF1314/12270178
package com.cctin.platform.util;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.ExpiredJwtException;
import io.jsonwebtoken.Jws;
import io.jsonwebtoken.JwtParser;
import io.jsonwebtoken.Jwts;
import java.security.PublicKey;
import java.util.Base64;
import java.util.List;
import java.util.Map;
import org.jose4j.jws.JsonWebSignature;
import org.jose4j.lang.JoseException;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.util.StringUtils;
import org.springframework.web.client.RestTemplate;
import com.alibaba.fastjson.JSON;
import com.auth0.jwk.InvalidPublicKeyException;
import com.auth0.jwk.Jwk;
public class JwtUtils {
private static String getAppleIdPublicKeyFromRemote() {
ResponseEntity<String> responseEntity = new RestTemplate().getForEntity("https://appleid.apple.com/auth/keys", String.class);
if (responseEntity == null || responseEntity.getStatusCode() != HttpStatus.OK) {
return null;
}
return responseEntity.getBody();
}
private static PublicKey getAppleIdPublicKey(String kid) {
String publicKeyStr = getAppleIdPublicKeyFromRemote();
return publicKeyAdapter(publicKeyStr, kid);
}
/**
* 将appleServer返回的publicKey转换成PublicKey对象
*
* @param publicKeyStr
* @return
*/
private static PublicKey publicKeyAdapter(String publicKeyStr, String kid) {
if (!StringUtils.hasText(publicKeyStr)) {
return null;
}
Map maps = (Map) JSON.parse(publicKeyStr);
List<Map> keys = (List<Map>) maps.get("keys");
Map o = null;
for (Map key : keys) {
if (kid.equals(key.get("kid"))) {
o = key;
break;
}
}
if(null != o){
Jwk jwa = Jwk.fromValues(o);
try {
PublicKey publicKey = jwa.getPublicKey();
return publicKey;
} catch (InvalidPublicKeyException e) {
e.printStackTrace();
return null;
}
}else{
return null;
}
}
public static boolean verify2(PublicKey key, String jwt, String audience, String subject) {
JwtParser jwtParser = Jwts.parser().setSigningKey(key);
jwtParser.requireIssuer("https://appleid.apple.com");
jwtParser.requireAudience(audience);
jwtParser.requireSubject(subject);
try {
Jws<Claims> claim = jwtParser.parseClaimsJws(jwt);
if (claim != null && claim.getBody().containsKey("auth_time")) {
return true;
}
return false;
} catch (ExpiredJwtException e) {
return false;
} catch (Exception e) {
return false;
}
}
/**
*
* @Title: isValid
* @Description: TODO(校验基本信息:nonce,iss,aud,exp)
* @param accessToken
* @return
* boolean
*/
public static boolean isValid(String accessToken) {
CusJws cusJws = getJws(accessToken);
if (cusJws == null) {
return false;
}
// iss
long curTime = System.currentTimeMillis();
if (cusJws.getJwsPayload().getExp() * 1000 < curTime) {
return false;
}
if (!JwsPayload.ISS.equals(cusJws.getJwsPayload().getIss())) {
return false;
}
// 校验签名
PublicKey publicKey = getAppleIdPublicKey(cusJws.getJwsHeader().getKid());
if (!verifySignature(accessToken, publicKey)) {
return false;
}
if(!verify2(publicKey, accessToken, cusJws.getJwsPayload().getAud(), cusJws.getJwsPayload().getSub())){
return false;
}
return true;
}
/**
* verify signature
*
* @param accessToken
* @return
*/
private static boolean verifySignature(String accessToken, PublicKey publicKey) {
JsonWebSignature jsonWebSignature = new JsonWebSignature();
jsonWebSignature.setKey(publicKey);
try {
jsonWebSignature.setCompactSerialization(accessToken);
return jsonWebSignature.verifySignature();
} catch (JoseException e) {
return false;
}
}
private static CusJws getJws(String identityToken) {
String[] arrToken = identityToken.split("\\.");
if (arrToken == null || arrToken.length != 3) {
return null;
}
Base64.Decoder decoder = Base64.getDecoder();
JwsHeader jwsHeader = JSON.parseObject(new String(decoder.decode(arrToken[0])), JwsHeader.class);
JwsPayload jwsPayload = JSON.parseObject(new String(decoder.decode(arrToken[1])), JwsPayload.class);
return new CusJws(jwsHeader, jwsPayload, arrToken[2]);
}
static class CusJws {
private JwsHeader jwsHeader;
private JwsPayload jwsPayload;
private String signature;
public CusJws(JwsHeader jwsHeader, JwsPayload jwsPayload, String signature) {
this.jwsHeader = jwsHeader;
this.jwsPayload = jwsPayload;
this.signature = signature;
}
public JwsHeader getJwsHeader() {
return jwsHeader;
}
public void setJwsHeader(JwsHeader jwsHeader) {
this.jwsHeader = jwsHeader;
}
public JwsPayload getJwsPayload() {
return jwsPayload;
}
public void setJwsPayload(JwsPayload jwsPayload) {
this.jwsPayload = jwsPayload;
}
public String getSignature() {
return signature;
}
public void setSignature(String signature) {
this.signature = signature;
}
}
static class JwsHeader {
private String kid;
private String alg;
public String getKid() {
return kid;
}
public void setKid(String kid) {
this.kid = kid;
}
public String getAlg() {
return alg;
}
public void setAlg(String alg) {
this.alg = alg;
}
}
static class JwsPayload {
private String iss;
private String sub;
private String aud;
private long exp;
private long iat;
private String nonce;
private String email;
private boolean email_verified;
public final static String ISS = "https://appleid.apple.com";
public String getIss() {
return iss;
}
public void setIss(String iss) {
this.iss = iss;
}
public String getSub() {
return sub;
}
public void setSub(String sub) {
this.sub = sub;
}
public String getAud() {
return aud;
}
public void setAud(String aud) {
this.aud = aud;
}
public long getExp() {
return exp;
}
public void setExp(long exp) {
this.exp = exp;
}
public long getIat() {
return iat;
}
public void setIat(long iat) {
this.iat = iat;
}
public String getNonce() {
return nonce;
}
public void setNonce(String nonce) {
this.nonce = nonce;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public boolean isEmail_verified() {
return email_verified;
}
public void setEmail_verified(boolean email_verified) {
this.email_verified = email_verified;
}
}
}
苹果授权登陆 服务端验证(java)相关推荐
- postman关闭ssl验证_【第5期】springboot:苹果内购服务端验证
苹果内购: 只要你在苹果系统购买APP中虚拟物品(虚拟货币,VIP充值等),必须通过内购方式进行支付,苹果和商家进行三七开 验证模式有两种: Validating Receipts With the ...
- golang 苹果登录,服务端验证identityToken(真实有效)
介绍 2019年之后,对于Apple App来说,如果要支持第三方登录,则必须同时支持苹果的第三方登录,即Sign in With Apple, 本文主要介绍如何使用Go语言实现Sign in Wit ...
- Sign in with Apple(苹果授权登陆) java jwt方式验证
本文章借鉴的原文链接:https://blog.csdn.net/wpf199402076118/article/details/99677412 苹果授权登陆方式 PC/M端授权登陆,采用协议类似于 ...
- Sign in with Apple(苹果授权登陆)
苹果授权登陆方式 1. PC/M端授权登陆,采用协议类似于oauth2协议 2. App端授权登陆,提供两种后端验证方式 开发者后台配置 详细配置参考该文档,手把手教学 https://develop ...
- Sign in with Apple(苹果授权登陆)服务端验证-测试通过版
Sign in with Apple(苹果授权登陆)服务端验证-测试通过版 1.先引用2个jwt用到的jar包 2.算法的工具类 三方登录调用验证工具类 苹果登录方式有2种,这里介绍基于JWT算法验证 ...
- java服务端验证谷歌支付Google Pay
翻阅大半个谷歌,对服务器验证账单,讲的少之又少,还TM没有看懂 查阅整个百度,发现几乎所有demo都是用世界上最好的语言php写的,这我 在此坐下记录希望能帮到有需要的人 支付流程 前端支付完成,谷歌 ...
- Sign in with Apple(object-c) 从开发者后台到服务端验证
Sign in with Apple 前言 准备工作 开发工作(object-c编写) 基本流程 添加依赖库 创建Apple登录Button 向Apple发起请求 接收Apple的回调 注意: 用户注 ...
- JSR-303 Bean Validation 介绍及 Spring MVC 服务端验证最佳实践
任何时候,当要处理一个应用程序的业务逻辑,数据校验是你必须要考虑和面对的事情. 应用程序必须通过某种手段来确保输入参数在上下文来说是正确的. 分层的应用在很多时候,同样的数据验证逻辑会出现在不同的层, ...
- ios 自己服务器 苹果支付_苹果支付 PHP 服务端处理
因为上周末连续加班 2 天(产品非要周一上线新版本),因此断更公众号一段时间,今天继续补上. 之前有了微信和支付宝支付后,产品要加上苹果支付,于是有了这篇文章. 一.ios 端流程 itunnes 相 ...
最新文章
- 【深度学习】U型的Transfomer网络(Swin-Unet)和Swin-Transformer分类
- marin 初学LINUX之路
- python读取sqlserver数据库方法_SQLServer数据库之Python读取配置文件,并连接数据库SQL Server...
- 教师节,老师们最大的愿望竟然是。。 | 今日最佳
- Android studio的Activity详解
- php怎么引入外部css文件,js如何引入css外部文件
- [转]提高PR值的具体方法
- 基于二进制粒子群算法的背包问题求解- 附代码
- mysql中文乱码--存入mysql里的中文变成问号的解决办法
- 公司网站的访问量突破了每天PV1.5亿
- c++缺省值 缺省参数
- 用Python实现一个商场管理系统(附源码)
- 机器人学笔记之——操作臂运动学:驱动器空间、关节空间和笛卡尔空间
- c语言程序小时工资计算,C语言入门之工资计算
- Web——HTML常见标签及用法
- 2019JDATA店铺购买预测大赛复盘(冠军方案)
- Ubuntu下gcc的静态库与动态库的生成与使用
- 神经网络分类器的原理图,神经网络分类器是什么
- c语言镶嵌循环,讲解C++的do while循环和循环语句的嵌套使用方法
- anaconda安装包百度云下载