|
@@ -1,26 +1,14 @@
|
|
|
package com.chelvc.framework.jpush;
|
|
|
|
|
|
-import java.lang.reflect.Field;
|
|
|
-import java.security.GeneralSecurityException;
|
|
|
-import java.security.KeyFactory;
|
|
|
-import java.security.PrivateKey;
|
|
|
-import java.security.spec.PKCS8EncodedKeySpec;
|
|
|
import java.util.Arrays;
|
|
|
-import java.util.Base64;
|
|
|
import java.util.Collection;
|
|
|
import java.util.Collections;
|
|
|
-import java.util.Comparator;
|
|
|
import java.util.List;
|
|
|
import java.util.Map;
|
|
|
import java.util.Objects;
|
|
|
import java.util.stream.Collectors;
|
|
|
-import javax.annotation.PostConstruct;
|
|
|
-import javax.crypto.Cipher;
|
|
|
|
|
|
-import cn.jiguang.common.ClientConfig;
|
|
|
import cn.jiguang.common.ServiceHelper;
|
|
|
-import cn.jiguang.common.connection.ApacheHttpClient;
|
|
|
-import cn.jiguang.common.resp.APIConnectionException;
|
|
|
import cn.jiguang.common.resp.APIRequestException;
|
|
|
import cn.jmessage.api.JMessageClient;
|
|
|
import cn.jmessage.api.common.model.RegisterInfo;
|
|
@@ -28,14 +16,13 @@ import cn.jmessage.api.user.UserInfoResult;
|
|
|
import cn.jmessage.api.user.UserStateListResult;
|
|
|
import cn.jmessage.api.user.UserStateResult;
|
|
|
import cn.jpush.api.JPushClient;
|
|
|
-import cn.jpush.api.push.CIDResult;
|
|
|
-import cn.jpush.api.push.PushClient;
|
|
|
import cn.jpush.api.push.PushResult;
|
|
|
import cn.jpush.api.push.model.BatchPushResult;
|
|
|
import cn.jpush.api.push.model.Message;
|
|
|
import cn.jpush.api.push.model.PushPayload;
|
|
|
import cn.jpush.api.push.model.notification.Notification;
|
|
|
import cn.jpush.api.report.ReceivedsResult;
|
|
|
+import com.chelvc.framework.base.context.ApplicationContextHolder;
|
|
|
import com.chelvc.framework.base.context.LoggingContextHolder;
|
|
|
import com.chelvc.framework.common.model.Period;
|
|
|
import com.chelvc.framework.common.model.Platform;
|
|
@@ -45,7 +32,6 @@ import com.chelvc.framework.common.util.ObjectUtils;
|
|
|
import com.chelvc.framework.common.util.StringUtils;
|
|
|
import com.chelvc.framework.jpush.config.JPushProperties;
|
|
|
import com.chelvc.framework.jpush.context.JPushContextHolder;
|
|
|
-import com.google.common.collect.ImmutableMap;
|
|
|
import lombok.NonNull;
|
|
|
import lombok.RequiredArgsConstructor;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
@@ -68,11 +54,6 @@ import org.springframework.web.client.RestTemplate;
|
|
|
@Component
|
|
|
@RequiredArgsConstructor(onConstructor = @__(@Autowired))
|
|
|
public class DefaultJPushHandler implements JPushHandler {
|
|
|
- /**
|
|
|
- * 极光令牌验证地址
|
|
|
- */
|
|
|
- private static final String TOKEN2MOBILE_URL = "https://api.verification.jpush.cn/v1/web/loginTokenVerify";
|
|
|
-
|
|
|
/**
|
|
|
* 获取消息地址
|
|
|
*/
|
|
@@ -95,72 +76,10 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
*/
|
|
|
private static final String GET_HISTORY_MESSAGE_URL = "https://report.im.jpush.cn/v2/users/%s/messages?cursor=%s";
|
|
|
|
|
|
+ private final JPushClient pushClient;
|
|
|
+ private final JMessageClient messageClient;
|
|
|
private final RestTemplate restTemplate;
|
|
|
private final JPushProperties properties;
|
|
|
- private PrivateKey privateKey;
|
|
|
- private JPushClient pushClient;
|
|
|
- private JMessageClient messageClient;
|
|
|
-
|
|
|
- @PostConstruct
|
|
|
- public void initialize() throws GeneralSecurityException {
|
|
|
- // 初始化登录认证配置
|
|
|
- JPushProperties.Login login = this.properties.getLogin();
|
|
|
- if (login != null && StringUtils.notEmpty(login.getSecret())) {
|
|
|
- // 初始化私钥
|
|
|
- byte[] secret = Base64.getDecoder().decode(login.getSecret());
|
|
|
- PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(secret);
|
|
|
- this.privateKey = KeyFactory.getInstance("RSA").generatePrivate(keySpec);
|
|
|
- }
|
|
|
-
|
|
|
- // 初始化消息推送配置
|
|
|
- JPushProperties.Push push = this.properties.getPush();
|
|
|
- if (push != null && StringUtils.notEmpty(push.getAppkey()) && StringUtils.notEmpty(push.getSecret())) {
|
|
|
- // 初始化推送客户端实例
|
|
|
- this.pushClient = new JPushClient(push.getSecret(), push.getAppkey()) {
|
|
|
- {
|
|
|
- Field field = ObjectUtils.getField(JPushClient.class, "_pushClient");
|
|
|
- ObjectUtils.setValue(this, field, new PushClient(push.getSecret(), push.getAppkey()) {
|
|
|
- @Override
|
|
|
- public CIDResult getCidList(int count, String type) throws APIConnectionException,
|
|
|
- APIRequestException {
|
|
|
- // 对批量推送CID排序,确保推送结果顺序与发送数据顺序一致
|
|
|
- CIDResult result = super.getCidList(count, type);
|
|
|
- if (result != null && !CollectionUtils.isEmpty(result.cidlist)) {
|
|
|
- result.cidlist.sort(Comparator.naturalOrder());
|
|
|
- }
|
|
|
- return result;
|
|
|
- }
|
|
|
- });
|
|
|
- }
|
|
|
- };
|
|
|
-
|
|
|
- // 初始化消息客户端实例
|
|
|
- this.messageClient = new JMessageClient(push.getAppkey(), push.getSecret());
|
|
|
- this.messageClient.setHttpClient(new ApacheHttpClient(
|
|
|
- ServiceHelper.getBasicAuthorization(push.getAppkey(), push.getSecret()),
|
|
|
- null,
|
|
|
- ClientConfig.getInstance()
|
|
|
- ));
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- /**
|
|
|
- * 获取推送客户端实例
|
|
|
- *
|
|
|
- * @return 推送客户端实例
|
|
|
- */
|
|
|
- private JPushClient getPushClient() {
|
|
|
- return AssertUtils.nonnull(this.pushClient, () -> "JPush client has not been initialized");
|
|
|
- }
|
|
|
-
|
|
|
- /**
|
|
|
- * 获取消息客户端实例
|
|
|
- *
|
|
|
- * @return 消息客户端实例
|
|
|
- */
|
|
|
- private JMessageClient getMessageClient() {
|
|
|
- return AssertUtils.nonnull(this.messageClient, () -> "JMessage client has not been initialized");
|
|
|
- }
|
|
|
|
|
|
/**
|
|
|
* 获取聊天消息
|
|
@@ -169,10 +88,10 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
* @return 聊天消息
|
|
|
*/
|
|
|
private ChatMessage getChatMessages(String url) {
|
|
|
- String appkey = ObjectUtils.ifNull(this.properties.getPush(), JPushProperties.Push::getAppkey);
|
|
|
- String secret = ObjectUtils.ifNull(this.properties.getPush(), JPushProperties.Push::getSecret);
|
|
|
HttpHeaders headers = new HttpHeaders();
|
|
|
- headers.add("Authorization", ServiceHelper.getBasicAuthorization(appkey, secret));
|
|
|
+ headers.add("Authorization", ServiceHelper.getBasicAuthorization(
|
|
|
+ this.properties.getId(), this.properties.getSecret()
|
|
|
+ ));
|
|
|
headers.setContentType(MediaType.APPLICATION_JSON);
|
|
|
HttpEntity<?> entity = new HttpEntity<>(headers);
|
|
|
try {
|
|
@@ -183,48 +102,13 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- @Override
|
|
|
- public String token2mobile(@NonNull String token) {
|
|
|
- PrivateKey key = AssertUtils.nonnull(this.privateKey, () -> "Private key has not been initialized");
|
|
|
-
|
|
|
- // 根据令牌获取手机号密文
|
|
|
- Map<String, String> parameters = ImmutableMap.of("loginToken", token);
|
|
|
- String authorization = ObjectUtils.ifNull(this.properties.getLogin(), JPushProperties.Login::getAuthorization);
|
|
|
- HttpHeaders headers = new HttpHeaders();
|
|
|
- headers.add("Authorization", authorization);
|
|
|
- headers.setContentType(MediaType.APPLICATION_JSON);
|
|
|
- HttpEntity<?> entity = new HttpEntity<>(parameters, headers);
|
|
|
- JPushMobile response;
|
|
|
- try {
|
|
|
- response = this.restTemplate.exchange(
|
|
|
- TOKEN2MOBILE_URL, HttpMethod.POST, entity, JPushMobile.class
|
|
|
- ).getBody();
|
|
|
- } catch (Exception e) {
|
|
|
- LoggingContextHolder.warn(log, e);
|
|
|
- return null;
|
|
|
- }
|
|
|
- if (response == null || response.getCode() == null || response.getCode() != 8000) {
|
|
|
- LoggingContextHolder.warn(log, response);
|
|
|
- return null;
|
|
|
- }
|
|
|
-
|
|
|
- // 解码手机号
|
|
|
- try {
|
|
|
- Cipher cipher = Cipher.getInstance("RSA");
|
|
|
- cipher.init(Cipher.DECRYPT_MODE, key);
|
|
|
- return new String(cipher.doFinal(Base64.getDecoder().decode(response.getPhone())));
|
|
|
- } catch (GeneralSecurityException e) {
|
|
|
- throw new RuntimeException(e);
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
@Override
|
|
|
public boolean register(@NonNull RegisterInfo... registrations) {
|
|
|
if (registrations.length == 0) {
|
|
|
return false;
|
|
|
}
|
|
|
try {
|
|
|
- this.getMessageClient().registerUsers(registrations);
|
|
|
+ this.messageClient.registerUsers(registrations);
|
|
|
} catch (Exception e) {
|
|
|
int code;
|
|
|
if (e instanceof APIRequestException
|
|
@@ -245,12 +129,12 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
@Override
|
|
|
public long push(@NonNull PushPayload payload) {
|
|
|
// 针对生产环境IOS推送,需要设置apnsProduction为true
|
|
|
- if (JPushContextHolder.isProduction()) {
|
|
|
+ if (ApplicationContextHolder.isProduction()) {
|
|
|
payload.resetOptionsApnsProduction(true);
|
|
|
}
|
|
|
PushResult result;
|
|
|
try {
|
|
|
- result = this.getPushClient().sendPush(payload);
|
|
|
+ result = this.pushClient.sendPush(payload);
|
|
|
} catch (Exception e) {
|
|
|
LoggingContextHolder.warn(log, e);
|
|
|
return 0;
|
|
@@ -321,13 +205,13 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
public BatchPushResult push(@NonNull List<PushPayload> payloads) {
|
|
|
AssertUtils.nonempty(payloads, () -> "payloads must not be empty");
|
|
|
// 针对生产环境IOS推送,需要设置apnsProduction为true
|
|
|
- if (JPushContextHolder.isProduction()) {
|
|
|
+ if (ApplicationContextHolder.isProduction()) {
|
|
|
payloads.forEach(payload -> payload.resetOptionsApnsProduction(true));
|
|
|
}
|
|
|
|
|
|
// 批量推送消息
|
|
|
try {
|
|
|
- return this.getPushClient().batchSendPushByAlias(payloads);
|
|
|
+ return this.pushClient.batchSendPushByAlias(payloads);
|
|
|
} catch (Exception e) {
|
|
|
LoggingContextHolder.warn(log, e);
|
|
|
return null;
|
|
@@ -346,7 +230,7 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
}
|
|
|
ReceivedsResult result;
|
|
|
try {
|
|
|
- result = this.getPushClient().getReceivedsDetail(ids);
|
|
|
+ result = this.pushClient.getReceivedsDetail(ids);
|
|
|
} catch (Exception e) {
|
|
|
LoggingContextHolder.warn(log, e);
|
|
|
return Collections.emptyList();
|
|
@@ -375,7 +259,7 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
@Override
|
|
|
public UserInfoResult getUserInfo(@NonNull String username) {
|
|
|
try {
|
|
|
- return this.getMessageClient().getUserInfo(username);
|
|
|
+ return this.messageClient.getUserInfo(username);
|
|
|
} catch (Exception e) {
|
|
|
LoggingContextHolder.warn(log, e);
|
|
|
return null;
|
|
@@ -385,7 +269,7 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
@Override
|
|
|
public UserStateResult getUserState(@NonNull String username) {
|
|
|
try {
|
|
|
- return this.getMessageClient().getUserState(username);
|
|
|
+ return this.messageClient.getUserState(username);
|
|
|
} catch (Exception e) {
|
|
|
LoggingContextHolder.warn(log, e);
|
|
|
return null;
|
|
@@ -398,7 +282,7 @@ public class DefaultJPushHandler implements JPushHandler {
|
|
|
return new UserStateListResult[0];
|
|
|
}
|
|
|
try {
|
|
|
- return this.getMessageClient().getUsersState(usernames);
|
|
|
+ return this.messageClient.getUsersState(usernames);
|
|
|
} catch (Exception e) {
|
|
|
LoggingContextHolder.warn(log, e);
|
|
|
return new UserStateListResult[0];
|