package com
.test
;
import java
.io
.ByteArrayOutputStream
;
import java
.io
.DataOutputStream
;
import java
.io
.FileInputStream
;
import java
.io
.IOException
;
import java
.io
.InputStream
;
import java
.io
.UnsupportedEncodingException
;
import java
.net
.Socket
;
import java
.security
.KeyStore
;
import java
.util
.regex
.Pattern
;
import javax
.net
.ssl
.KeyManagerFactory
;
import javax
.net
.ssl
.SSLContext
;
import javax
.net
.ssl
.SSLSocketFactory
;
public class ApnsUtils {
private String keyPath
;
private String keyPassword
;
private String serverHost
;
private Integer serverPort
;
private static ApnsUtils instance
= new ApnsUtils();;
private ApnsUtils(){
keyPath
= this.getClass().getResource("/").getPath()+"file/push.p12";
keyPassword
= "1234";
serverHost
= "gateway.sandbox.push.apple.com";
serverPort
= 2195;
}
public static ApnsUtils
getInstance() {
return instance
;
}
public void pushToIos(String deviceToken
,String text
){
String ksType
= "PKCS12";
String ksAlgorithm
= "SunX509";
try {
InputStream certInput
= new FileInputStream(keyPath
);
KeyStore keyStore
= KeyStore
.getInstance(ksType
);
keyStore
.load(certInput
, keyPassword
.toCharArray());
KeyManagerFactory kmf
= KeyManagerFactory
.getInstance(ksAlgorithm
);
kmf
.init(keyStore
, keyPassword
.toCharArray());
SSLContext sslContext
= SSLContext
.getInstance("TLS");
sslContext
.init(kmf
.getKeyManagers(), null
, null
);
SSLSocketFactory socketFactory
= sslContext
.getSocketFactory();
Socket socket
= socketFactory
.createSocket(serverHost
, serverPort
);
StringBuilder content
= new StringBuilder();
content
.append("{\"aps\":");
content
.append("{\"alert\":\"").append(text
).append("\",\"badge\":0").append(", \"sound\" : \"default\"}");
content
.append(",\"cpn\":{\"t0\":")
.append(System
.currentTimeMillis()).append("}");
content
.append("}");
byte[] msgByte
= makebyte((byte)1, deviceToken
, content
.toString(), 10000001);
socket
.getOutputStream().write(msgByte
);
socket
.getOutputStream().flush();
socket
.close();
} catch (Exception e
) {
e
.printStackTrace();
}
}
private static byte[] makebyte(byte command
, String deviceToken
, String payload
, int identifer
) {
byte[] deviceTokenb
= decodeHex(deviceToken
);
byte[] payloadBytes
= null
;
ByteArrayOutputStream boas
= new ByteArrayOutputStream();
DataOutputStream dos
= new DataOutputStream(boas
);
try {
payloadBytes
= payload
.getBytes("UTF-8");
} catch (UnsupportedEncodingException e
) {
e
.printStackTrace();
return null
;
}
try {
dos
.writeByte(command
);
dos
.writeInt(identifer
);
dos
.writeInt(Integer
.MAX_VALUE
);
dos
.writeShort(deviceTokenb
.length
);
dos
.write(deviceTokenb
);
dos
.writeShort(payloadBytes
.length
);
dos
.write(payloadBytes
);
return boas
.toByteArray();
} catch (IOException e
) {
e
.printStackTrace();
return null
;
}
}
private static final Pattern pattern
= Pattern
.compile("[ -]");
private static byte[] decodeHex(String deviceToken
) {
String hex
= pattern
.matcher(deviceToken
).replaceAll("");
byte[] bts
= new byte[hex
.length() / 2];
for (int i
= 0; i
< bts
.length
; i
++) {
bts
[i
] = (byte) (charval(hex
.charAt(2*i
)) * 16 + charval(hex
.charAt(2*i
+ 1)));
}
return bts
;
}
private static int charval(char a
) {
if ('0' <= a
&& a
<= '9')
return (a
- '0');
else if ('a' <= a
&& a
<= 'f')
return (a
- 'a') + 10;
else if ('A' <= a
&& a
<= 'F')
return (a
- 'A') + 10;
else{
throw new RuntimeException("Invalid hex character: " + a
);
}
}
public static void main(String
[] args
) {
ApnsUtils
.getInstance().pushToIos("7785bd40502060af8b8b156e36896b623d020df4c8acdbb361c871114c9cb6bf", "this is content");
}
}