Skip to content

Instantly share code, notes, and snippets.

@bitsmuggler
Last active August 29, 2015 14:23
Show Gist options
  • Save bitsmuggler/570a2c0c5575243f6366 to your computer and use it in GitHub Desktop.
Save bitsmuggler/570a2c0c5575243f6366 to your computer and use it in GitHub Desktop.
AmazoneSNSClientWrapper for Mobile Push Notifications
/*
* Copyright 2014 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License").
* You may not use this file except in compliance with the License.
* A copy of the License is located at
*
* http://aws.amazon.com/apache2.0
*
* or in the "license" file accompanying this file. This file is distributed
* on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
* express or implied. See the License for the specific language governing
* permissions and limitations under the License.
*/
import java.util.HashMap;
import java.util.Map;
import com.amazonaws.services.sns.AmazonSNS;
import com.amazonaws.services.sns.model.CreatePlatformApplicationRequest;
import com.amazonaws.services.sns.model.CreatePlatformApplicationResult;
import com.amazonaws.services.sns.model.CreatePlatformEndpointRequest;
import com.amazonaws.services.sns.model.CreatePlatformEndpointResult;
import com.amazonaws.services.sns.model.DeletePlatformApplicationRequest;
import com.amazonaws.services.sns.model.MessageAttributeValue;
import com.amazonaws.services.sns.model.PublishRequest;
import com.amazonaws.services.sns.model.PublishResult;
public class AmazonSNSClientWrapper {
private final AmazonSNS snsClient;
public AmazonSNSClientWrapper(AmazonSNS client) {
this.snsClient = client;
}
private CreatePlatformApplicationResult createPlatformApplication(
String applicationName, Platform platform, String principal,
String credential) {
CreatePlatformApplicationRequest platformApplicationRequest = new CreatePlatformApplicationRequest();
Map<String, String> attributes = new HashMap<String, String>();
attributes.put("PlatformPrincipal", principal);
attributes.put("PlatformCredential", credential);
platformApplicationRequest.setAttributes(attributes);
platformApplicationRequest.setName(applicationName);
platformApplicationRequest.setPlatform(platform.name());
return snsClient.createPlatformApplication(platformApplicationRequest);
}
private CreatePlatformEndpointResult createPlatformEndpoint(
Platform platform, String customData, String platformToken,
String applicationArn) {
CreatePlatformEndpointRequest platformEndpointRequest = new CreatePlatformEndpointRequest();
platformEndpointRequest.setCustomUserData(customData);
String token = platformToken;
String userId = null;
if (platform == Platform.BAIDU) {
String[] tokenBits = platformToken.split("\\|");
token = tokenBits[0];
userId = tokenBits[1];
Map<String, String> endpointAttributes = new HashMap<String, String>();
endpointAttributes.put("UserId", userId);
endpointAttributes.put("ChannelId", token);
platformEndpointRequest.setAttributes(endpointAttributes);
}
platformEndpointRequest.setToken(token);
platformEndpointRequest.setPlatformApplicationArn(applicationArn);
return snsClient.createPlatformEndpoint(platformEndpointRequest);
}
private void deletePlatformApplication(String applicationArn) {
DeletePlatformApplicationRequest request = new DeletePlatformApplicationRequest();
request.setPlatformApplicationArn(applicationArn);
snsClient.deletePlatformApplication(request);
}
private PublishResult publish(String endpointArn, Platform platform,
Map<Platform, Map<String, MessageAttributeValue>> attributesMap) {
PublishRequest publishRequest = new PublishRequest();
Map<String, MessageAttributeValue> notificationAttributes = getValidNotificationAttributes(attributesMap
.get(platform));
if (notificationAttributes != null && !notificationAttributes.isEmpty()) {
publishRequest.setMessageAttributes(notificationAttributes);
}
publishRequest.setMessageStructure("json");
// If the message attributes are not set in the requisite method,
// notification is sent with default attributes
String message = getPlatformSampleMessage(platform);
Map<String, String> messageMap = new HashMap<String, String>();
messageMap.put(platform.name(), message);
message = SampleMessageGenerator.jsonify(messageMap);
// For direct publish to mobile end points, topicArn is not relevant.
publishRequest.setTargetArn(endpointArn);
// Display the message that will be sent to the endpoint/
System.out.println("{Message Body: " + message + "}");
StringBuilder builder = new StringBuilder();
builder.append("{Message Attributes: ");
for (Map.Entry<String, MessageAttributeValue> entry : notificationAttributes
.entrySet()) {
builder.append("(\"" + entry.getKey() + "\": \""
+ entry.getValue().getStringValue() + "\"),");
}
builder.deleteCharAt(builder.length() - 1);
builder.append("}");
System.out.println(builder.toString());
publishRequest.setMessage(message);
return snsClient.publish(publishRequest);
}
public void demoNotification(Platform platform, String principal,
String credential, String platformToken, String applicationName,
Map<Platform, Map<String, MessageAttributeValue>> attrsMap) {
// Create Platform Application. This corresponds to an app on a
// platform.
CreatePlatformApplicationResult platformApplicationResult = createPlatformApplication(
applicationName, platform, principal, credential);
System.out.println(platformApplicationResult);
// The Platform Application Arn can be used to uniquely identify the
// Platform Application.
String platformApplicationArn = platformApplicationResult
.getPlatformApplicationArn();
// Create an Endpoint. This corresponds to an app on a device.
CreatePlatformEndpointResult platformEndpointResult = createPlatformEndpoint(
platform,
"CustomData - Useful to store endpoint specific data",
platformToken, platformApplicationArn);
System.out.println(platformEndpointResult);
// Publish a push notification to an Endpoint.
PublishResult publishResult = publish(
platformEndpointResult.getEndpointArn(), platform, attrsMap);
System.out.println("Published! \n{MessageId="
+ publishResult.getMessageId() + "}");
// Delete the Platform Application since we will no longer be using it.
deletePlatformApplication(platformApplicationArn);
}
private String getPlatformSampleMessage(Platform platform) {
switch (platform) {
case APNS:
return SampleMessageGenerator.getSampleAppleMessage();
case APNS_SANDBOX:
return SampleMessageGenerator.getSampleAppleMessage();
case GCM:
return SampleMessageGenerator.getSampleAndroidMessage();
case ADM:
return SampleMessageGenerator.getSampleKindleMessage();
case BAIDU:
return SampleMessageGenerator.getSampleBaiduMessage();
case WNS:
return SampleMessageGenerator.getSampleWNSMessage();
case MPNS:
return SampleMessageGenerator.getSampleMPNSMessage();
default:
throw new IllegalArgumentException("Platform not supported : "
+ platform.name());
}
}
public static Map<String, MessageAttributeValue> getValidNotificationAttributes(
Map<String, MessageAttributeValue> notificationAttributes) {
Map<String, MessageAttributeValue> validAttributes = new HashMap<String, MessageAttributeValue>();
if (notificationAttributes == null) return validAttributes;
for (Map.Entry<String, MessageAttributeValue> entry : notificationAttributes
.entrySet()) {
if (!StringUtils.isBlank(entry.getValue().getStringValue())) {
validAttributes.put(entry.getKey(), entry.getValue());
}
}
return validAttributes;
}
}
public class SampleMessageGenerator {
/*
* This message is delivered if a platform specific message is not specified
* for the end point. It must be set. It is received by the device as the
* value of the key "default".
*/
public static final String defaultMessage = "This is the default message";
private static final ObjectMapper objectMapper = new ObjectMapper();
public static enum Platform {
// Apple Push Notification Service
APNS,
// Sandbox version of Apple Push Notification Service
APNS_SANDBOX,
// Amazon Device Messaging
ADM,
// Google Cloud Messaging
GCM,
// Baidu CloudMessaging Service
BAIDU,
// Windows Notification Service
WNS,
// Microsoft Push Notificaion Service
MPNS;
}
public static String jsonify(Object message) {
try {
return objectMapper.writeValueAsString(message);
} catch (Exception e) {
e.printStackTrace();
throw (RuntimeException) e;
}
}
private static Map<String, String> getData() {
Map<String, String> payload = new HashMap<String, String>();
payload.put("message", "Hello World!");
return payload;
}
public static String getSampleAppleMessage() {
Map<String, Object> appleMessageMap = new HashMap<String, Object>();
Map<String, Object> appMessageMap = new HashMap<String, Object>();
appMessageMap.put("alert", "You have got email.");
appMessageMap.put("badge", 9);
appMessageMap.put("sound", "default");
appleMessageMap.put("aps", appMessageMap);
return jsonify(appleMessageMap);
}
public static String getSampleKindleMessage() {
Map<String, Object> kindleMessageMap = new HashMap<String, Object>();
kindleMessageMap.put("data", getData());
kindleMessageMap.put("consolidationKey", "Welcome");
kindleMessageMap.put("expiresAfter", 1000);
return jsonify(kindleMessageMap);
}
public static String getSampleAndroidMessage() {
Map<String, Object> androidMessageMap = new HashMap<String, Object>();
androidMessageMap.put("collapse_key", "Welcome");
androidMessageMap.put("data", getData());
androidMessageMap.put("delay_while_idle", true);
androidMessageMap.put("time_to_live", 125);
androidMessageMap.put("dry_run", false);
return jsonify(androidMessageMap);
}
public static String getSampleBaiduMessage() {
Map<String, Object> baiduMessageMap = new HashMap<String, Object>();
baiduMessageMap.put("title", "New Notification Received from SNS");
baiduMessageMap.put("description", "Hello World!");
return jsonify(baiduMessageMap);
}
public static String getSampleWNSMessage() {
Map<String, Object> wnsMessageMap = new HashMap<String, Object>();
wnsMessageMap.put("version", "1");
wnsMessageMap.put("value", "23");
return "<badge version=\"" + wnsMessageMap.get("version")
+ "\" value=\"" + wnsMessageMap.get("value") + "\"/>";
}
public static String getSampleMPNSMessage() {
Map<String, String> mpnsMessageMap = new HashMap<String, String>();
mpnsMessageMap.put("count", "23");
mpnsMessageMap.put("payload", "This is a tile notification");
return "<?xml version=\"1.0\" encoding=\"utf-8\"?><wp:Notification xmlns:wp=\"WPNotification\"><wp:Tile><wp:Count>"
+ mpnsMessageMap.get("count")
+ "</wp:Count><wp:Title>"
+ mpnsMessageMap.get("payload")
+ "</wp:Title></wp:Tile></wp:Notification>";
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment