Skip to content

Instantly share code, notes, and snippets.

@raviwu
Created June 24, 2016 10:19
Show Gist options
  • Save raviwu/62ebfb203138e4ca9020d04ce3fb3ac2 to your computer and use it in GitHub Desktop.
Save raviwu/62ebfb203138e4ca9020d04ce3fb3ac2 to your computer and use it in GitHub Desktop.
PushServicesWrapper
# In app/services/push_services_wrapper.rb
require 'json/ext'
class PushServicesWrapper
attr_reader :message, :to_email, :channels, :badge, :from_id, :push_time, :addition, :push_uri, :to_id
def initialize(options = {})
@message = options[:message]
@to_email = options[:to_email].kind_of?(Array) ? options[:to_email] : [options[:to_email]]
@to_email.compact!
receiver = User.find_by_email(to_email.first)
@to_id = receiver.id if receiver.present?
push_to_channels = options[:channels].kind_of?(Array) ? options[:channels] : [options[:channels]] if options[:channels].present?
@channels = push_to_channels
@badge = options[:badge]
default_from_id = User.find_by_email("default_user@user.email").id
@from_id = options[:from_id].present? ? options[:from_id] : default_from_id
@to_id ||= @from_id
@push_time = options[:push_time] # this is for parse schedule push
@addition = options[:addition]
@push_uri = options[:push_uri]
end
def send_push(options = {})
push_to_channels = options[:push_to_channels] || false
result = false
if push_to_channels
# push through Parse and SNS, manipulate message for debugging
result = topic_push_by_amazon_sns
result = successfully_push_by_parse?
else
to_users = to_email.map { |email| User.find_by_email(email) }
# Push to user by amazon when user has amazon_sns_infos record
to_users_by_amazon = to_users.select { |user| user.amazon_sns_infos.present? }
begin
to_users_by_amazon.each do |user|
target_push_by_amazon_sns(user)
end
result = true
rescue => e
result = false
end
# deliver the rest notification through Parse
to_users_by_parse = to_users - to_users_by_amazon
@to_email = to_users_by_parse.map { |user| user.email }
if @to_email.present?
result = successfully_push_by_parse?
end
end
result
end
private
def target_push_by_amazon_sns(user)
user.amazon_sns_infos.each do |amazon_sns_info|
AmazonSnsWrapper.push_notification(
amazon_sns_info: amazon_sns_info,
message: self.message,
badge: self.badge,
push_uri: self.push_uri,
from_id: self.from_id
)
end
end
def topic_push_by_amazon_sns
topic_arns = AmazonSnsWrapper.convert_topic_arns_by_env(channels)
topic_arns.each do |topic_arn|
AmazonSnsWrapper.push_notification(
message: self.message,
badge: self.badge,
push_uri: self.push_uri,
topic_arn: topic_arn,
from_id: self.from_id,
push_to_channels: true
)
end
end
def successfully_push_by_parse?
resp_raw_body = push_by_parse
response_body = JSON.parse(resp_raw_body)
# error format from parse response: "{\"result\":true}\n"
# error format from parse response: "{\"error\":\"unauthorized\"}\n"
response_body['result'] == true && response_body['error'].blank?
end
def push_by_parse
data_arr = {
"where" => {
"channels" => {"$all" => channels} },
"data" => {
"alert" => message,
"badge" => badge,
"sound" => "default" }
}
data_arr["where"]["userId"] = {"$in" => to_email} if to_email.present?
data_arr["data"]["uri"] = push_uri if push_uri.present?
data_arr["push_time"] = push_time if push_time.present?
parse_push_api_url = "https://api.parse.com/1/push"
uri = URI.parse(parse_push_api_url)
conn = Faraday.new(:url => uri) do |faraday|
faraday.request :url_encoded # Form-encode POST params.
faraday.response :logger # Log requests to STDOUT.
faraday.adapter :net_http # Make requests with Net::HTTP.
end
resp = conn.post do |req|
req.url parse_push_api_url
req.headers["X-Parse-Application-Id"] = ParseConfig["ApplicationID"]
req.headers["X-Parse-REST-API-Key"] = ParseConfig["RestAPIKey"]
req.headers["Content-Type"] = "application/json"
req.headers["Content-length"] = data_arr.to_json.length.to_s
req.body = data_arr.to_json
end
resp.body
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment