分享

Java发送ios推送消息(APN)的代码示例

 勤奋不止 2014-03-12

实际项目应用中,应该考虑使用开源项目java-apns:https://github.com/notnoop/java-apns
千万不要用一个叫JAVAPNS的项目。这个开源项目的代码非常烂,每次发送消息都重新建立socket连接。在apple的文档中,都明确的说了会把这种行为当作dos攻击行为。性能差就更不用说了。
ios手机上要安装对应的应用。该应用与.p12证书文件应该匹配。
apple官方的,关于APN服务,和apn的feedback的文档在这个地方:https://developer.apple.com/library/ios/#documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/Chapters/CommunicatingWIthAPS.html#//apple_ref/doc/uid/TP40008194-CH101-SW3
java版本发送apn推送代码示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
package 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 TestAPN {
    /**
     * @param args
     */
    public static void main(String[] args) {
         
        String keyPath = "/data/tmp/proj.apns.p12";
        String ksType = "PKCS12";
        String ksPassword = "111111";
        String ksAlgorithm = "SunX509";
         
        String deviceToken = "1404c88dbb0adb92c0a85f4cd09be9707f251ae5bbecdb0a6a3e572aeb337d73";
         
        String serverHost = "gateway.push.apple.com";
        int serverPort = 2195;
         
        try {
            InputStream certInput = new FileInputStream(keyPath);
            KeyStore keyStore = KeyStore.getInstance(ksType);
            keyStore.load(certInput, ksPassword.toCharArray());
             
            KeyManagerFactory kmf = KeyManagerFactory.getInstance(ksAlgorithm);
            kmf.init(keyStore, ksPassword.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();
             
            String text = "this is a test.";
             
            content.append("{\"aps\":");
            content.append("{\"alert\":\"").append(text)
                .append("\",\"badge\":1,\"sound\":\"")
                .append("ping1").append("\"}");
             
            content.append(",\"cpn\":{\"t0\":")
                .append(System.currentTimeMillis()).append("}");
            content.append("}");
             
            byte[] msgByte = makebyte((byte)1, deviceToken, content.toString(), 10000001);
             
            System.out.println(msgByte);
             
            socket.getOutputStream().write(msgByte);
            socket.getOutputStream().flush();
             
            socket.close();
             
        } catch (Exception e) {
            e.printStackTrace();
        }
         
         
         
    }
     
    /**
     * 组装apns规定的字节数组  使用增强型
     *
     * @param command
     * @param deviceToken
     * @param payload
     * @return
     * @throws IOException
     */
    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);//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);
        }
    }
}

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多