Jump to content

[TOPIC: topicViewTemplate]
[GLOBAL: userSmallPhoto]
Photo

Who's using what for Push Notifications?
Started by jen.looper Jun 05 2013 09:22 AM

80 replies to this topic
push notifications
[TOPIC CONTROLS]
Page 1 of 4 1 2 3 »
This topic has been archived. This means that you cannot reply to this topic.
[/TOPIC CONTROLS]
[modOptionsDropdown]
[/modOptionsDropdown]
[reputationFilter]
[TOPIC: post.html]
#1

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

hi, all. I wonder what you are using currently for your push notification needs. I did a lot of research into push services that would work for both Android and iOs and had a really difficult time meeting my use case, which is to allow clients to schedule push from their device. I can do it using Parse.com on iOs, so that is what I went with, but Parse doesn't work for Android builds as you can't register a device id the way they want you to (via the Manifest) and Parse uses its own Push service, not GCM.

 

I tested Urban Airship (solid, but can't schedule push from client), Parse (works well for iOs), PushSwoosh (couldn't make it work at all), and maybe some others with varied success. As long as they had a REST API I could tap into, I tried it! :)

 

This is all prior to CoronaCloud, but CC won't work for the above use case (yet...Mohamed, where's that scheduled push from client capability? :))

 

So I'd like to know, what are you using, what's your use case for which you found success, what works for you for cross-platform push?

 

thanks,

Jen



[TOPIC: post.html]
#2

emmanuel.ahkouen

[GLOBAL: userInfoPane.html]
emmanuel.ahkouen
  • Observer

  • 21 posts
  • Corona SDK

Hello,

 

Sorry if I do not anwser your question but I have one about Parse / Android.

I'm developping a game with Corona SDK and Parse. After reading your remarks about Parse / Push on android, I'm confused.

The problem is to register for push notifications, we need the installationid of the device which can be retrieved only by calling a native function. So if we don't have enterprise license, we are stuck, right ?



[TOPIC: post.html]
#3

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

According to my painful experience, your above statement is correct. I was forced to use local notifications for Android. It's not ideal for my use case. Wish I had a different answer. Corona engineer-gurus, please prove me wrong?



[TOPIC: post.html]
#4

jonjonsson

[GLOBAL: userInfoPane.html]
jonjonsson
  • Corona Geek

  • 1,051 posts
  • Corona SDK

I just researched this for my game.

 

Parse.com => No go on Android

Urban Airship => No go on Android

Pushwoosh => Works on Android

 

I got Pushwoosh to work fine using their example. I tried registering device and send notification from their site.  But you need to pay to use remote API. I know that if you contact them they will give you free trial while you test it out. If you are pushing more than the free limit on Urban and Parse it is a good price compared to the competitors.

 

I really hope we can get plugins for UA and Parse though.



[TOPIC: post.html]
#5

emmanuel.ahkouen

[GLOBAL: userInfoPane.html]
emmanuel.ahkouen
  • Observer

  • 21 posts
  • Corona SDK

I can see that we (me, jonjonsson and jen.looper) are still looking for a way to push on Android ;P
 

I have found something interesting :

http://www.coronalabs.com/blog/2012/12/25/corona-holiday-gifts-android-push-and-more/

 

So we can use GCM and depends on what we need :

- we can directly send a push from our mobile application

- we can setup our own server (in Google App Engine for example) to perform scheduled tasks / pushs



[TOPIC: post.html]
#6

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

hi, Emmanuel, and welcome to the "Oh.My.God.Why.Is.Push.So.Darn.Hard" club :) for Android. Yeah, we can definitely send pushes to Android devices as long as we use GCM directly or use a service that leverages GCM such as PushSwoosh. 

 

Interestingly, Urban Airship is now using GCM rather than their homegrown 'Helium' service (see below). This means that we ought to be able to use them for basic push needs. 

 

- I just took another look at UA and see that they seem to support Scheduled Notifications. It would be worth testing for iOs and Android. UA is a solid push service that I know works using Corona for iOs at least. It has some more robust capability in that you can also have your clients subscribe to channels. 

 

 

What UA service should I be using for Google Android?

 

Since Helium is being sunset (see our FAQ)You should be using our Google Cloud Messaging (GCM) service.  All new customers default to GCM, and we are actively working with customers currently using our Helium platform for Android to help them migrate to GCM.

 

Are there any limitations to UA's support of Google Cloud Messaging (GCM)?

 

Urban Airship provides full support for the GCM API.  You can use our service to send push notifications to any device running Android 2.2 or higher (97% of the market).  



[TOPIC: post.html]
#7

jonjonsson

[GLOBAL: userInfoPane.html]
jonjonsson
  • Corona Geek

  • 1,051 posts
  • Corona SDK

Regarding UA, even though they use GCM you still have to require their .jar as far as I could tell.

 

This page has sample device registration with Curl for iOS but for Android they just say "Android APID registration should always happen from our client library. See our docs here for more information."



[TOPIC: post.html]
#8

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

I think we really ought to write a Parse or UA push plugin. I've emailed plugins@coronalabs.com to see what they think. Jon, maybe you and I can collaborate to get something working. We really need this.

 

Another plugin I'd like to see is Kiip! That's a cool thing for 'real rewards'. 

 

thanks, let's keep trying

Jen



[TOPIC: post.html]
#9

emmanuel.ahkouen

[GLOBAL: userInfoPane.html]
emmanuel.ahkouen
  • Observer

  • 21 posts
  • Corona SDK

Thanks Jen for letting me join the "Oh.My.God.Why.Is.Push.So.Darn.Hard" club ;)

 

If you have more information about Corona SDK + Push (Parse, UA ...) for Android, let me know ! (Hope if there is a solution, it won't be a "pro" feature only ;P).

 

I'm going to try when I have time to setup a server (PHP or Python) with Google App Engine for pushing.

 

Good luck for your projects !



[TOPIC: post.html]
#10

ebookren

[GLOBAL: userInfoPane.html]
ebookren
  • Enthusiast

  • 52 posts
  • Enterprise

I had a soo much trouble trying to get push to work on android. I ended up putting together a rails app, set up on heroku, that I post the android' s device Id to. From there I post to gcm and the push goes through. This way I can use rails to send notification to specific users. The corona app just registers the device Id upon launch. I still can't read launchargs but that's another thread.

[TOPIC: post.html]
#11

jonjonsson

[GLOBAL: userInfoPane.html]
jonjonsson
  • Corona Geek

  • 1,051 posts
  • Corona SDK

I'm doing the same but with Tornado (Python). When I send ID to server I register if its and android or an ios device. If iOS I use UA. Just sucks to have to use 2 different methods on the server.



[TOPIC: post.html]
#12

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

I actually just recently made a little bit of progress using Parse's cloud code. It is sort of like using Heroku in that you write locally and then post it up to your servers. You then call the cloud code via the regular network request. The cloud code can call GCM. I have it working for one element in my app, and I'm hoping I can make it work for Android push... I'll let you know! Thanks for the input!



[TOPIC: post.html]
#13

ksan

[GLOBAL: userInfoPane.html]
ksan
  • Corona Geek

  • 2,795 posts
  • Corona SDK

I would love to hear more on this. I recently started using Parse for IOS and implemented their REST API on my small web app that my client will see to send their push messages so its all happy happy. Now I need to deliver on Android. I'm ok to use a totally separate service if it comes to that. Anything that works for Android with the ease of Parse on IOS?

 

Thanks!!!



[TOPIC: post.html]
#14

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

Hang tight, ksan, I'm working on it. I love Parse and use it for almost everything I need server-side so if I can make the cloud code solution work I'll post here. :)



[TOPIC: post.html]
#15

ksan

[GLOBAL: userInfoPane.html]
ksan
  • Corona Geek

  • 2,795 posts
  • Corona SDK

This is great!!! Thanks much for persevering with this effort. Cheers!!!



[TOPIC: post.html]
#16

ksan

[GLOBAL: userInfoPane.html]
ksan
  • Corona Geek

  • 2,795 posts
  • Corona SDK

Just read this thread once again. So if I understand this right, PushWoosh works on both platforms without much fuss but the downside is the monthly $ that needs to be paid for remote API right? With Parse if you stay under the threshold its all free which is great! 



[TOPIC: post.html]
#17

jonjonsson

[GLOBAL: userInfoPane.html]
jonjonsson
  • Corona Geek

  • 1,051 posts
  • Corona SDK

Just read this thread once again. So if I understand this right, PushWoosh works on both platforms without much fuss but the downside is the monthly $ that needs to be paid for remote API right? With Parse if you stay under the threshold its all free which is great! 

 

Yes that pretty much sums it up.

 

Soldier on Jen! :)



[TOPIC: post.html]
#18

mpappas

[GLOBAL: userInfoPane.html]
mpappas
  • Contributor

  • 527 posts
  • Enterprise

Hello,

 

Sorry if I do not anwser your question but I have one about Parse / Android.

I'm developping a game with Corona SDK and Parse. After reading your remarks about Parse / Push on android, I'm confused.

The problem is to register for push notifications, we need the installationid of the device which can be retrieved only by calling a native function. So if we don't have enterprise license, we are stuck, right ?

I'm using GCM and that is not how you get the installation ID. It is passed through to the app when it is installed using something like this:

 

 
function onNotification(event)
    print(" -- main - onNotification(event)")
    
    if event.type == "remoteRegistration" then
        mojoData.PTOKEN = event.token    -- Save off the installation token (push id)
--        native.showAlert( "remoteRegistration", event.token, { "OK" } )
        print(" -- saved token info: ", event.token)  
    elseif event.type == "remote" then
--        native.showAlert( "localNet Notification", Json.encode( event ), { "OK" } )
        print(" -- localNet Notification", Json.encode( event ) )               
        if( event.applicationState == "active" ) then
            native.setProperty("applicationIconBadgeNumber", 0)             -- clear out list of notifications from notification center....
 
            native.showAlert( "localNet Notification", Json.encode( event.alert ), { "OK" } )           
        end        
    end
    
    return true
end
--
-- Tried adding the listener in systemListener(), but no go, so initializing right in main, like corona docs show -- works here :/
--
Runtime:addEventListener( "notification", onNotification ) 
 

 

Argh... The website never likes my code blocks :/  Using Decoda editor, and mebbe it doesn't use cr/lf or something :/



[TOPIC: post.html]
#19

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

hi, mpappas, I actually got a little hung up on this last night and today. Are you able to get your Android's installation id using the onNotification listener? Somehow, I'm not able to. Would you be able to share your config and settings file with Android permissions? I thought I had this working a while ago but on my Samsung II it's not. The sample GooglePushNotification app doesn't register either. 

 

thanks,

Jen



[TOPIC: post.html]
#20

mpappas

[GLOBAL: userInfoPane.html]
mpappas
  • Contributor

  • 527 posts
  • Enterprise

Yes, the installation id (called a token in the docs) comes through just fine. I believe it not only comes to my app on installation, but that the corona sdk send it every launch of my app (I have some code that checks if it was already sent to the server, so I think that's why I added it way back when). Anyways:

 

Dunno if they will appear correctly, but here they are:

 

Config:

application =
{
    content =
    {
            width = 640,
            height = 960,
            scale = "letterbox",
            fps = 60,            
    },
        
    notification =
    {
        iphone =
        {
            types =
            {
                "badge", "sound", "alert"
            }
        },
         google =
        {
            projectNumber = "261275118095",
        },        
    },
        
}

 

build.settings:

 

settings =
{
     android =
     {
        largeHeap = true,
     
         permissions =
        {
        { name = ".permission.C2D_MESSAGE", protectionLevel = "signature" },
        },     
        usesPermissions =
        {
             "android.permission.INTERNET",
             "android.permission.ACCESS_FINE_LOCATION",
             "android.permission.ACCESS_COARSE_LOCATION",
             "android.permission.ACCESS_LOCATION_EXTRA_COMMANDS",
             "android.permission.WRITE_EXTERNAL_STORAGE",
             "com.android.vending.BILLING",                
             "android.permission.CAMERA",  
             "android.permission.CALL_PHONE",
             "android.permission.RECEIVE_BOOT_COMPLETED",          
             "android.permission.GET_ACCOUNTS",
             "com.google.android.c2dm.permission.RECEIVE",
             ".permission.C2D_MESSAGE",
             "android.permission.RECORD_AUDIO",       
        },
        usesFeatures =
        {
            { name = "android.hardware.camera", required = false },
            { name = "android.hardware.camera.front", required = false },                 
            { name = "android.hardware.telephony", required = false },                                        
        },        
    },
    
    iphone =
    {    
        components = {},
        
        plist =
        {
            UIPrerenderedIcon = true,
            UIApplicationExitsOnSuspend = false,
            CFBundleIconFile = "Icon.png",
            CFBundleIconFiles = {
                    "Icon.png" ,
                    "Icon@2x.png" ,
                    "Icon-72.png",
            },
            
            FacebookAppID = "423650107852131",            
            CFBundleURLTypes =
            {
                {
                CFBundleURLSchemes =
                    {
                    "fb424050273855136",
                    }
                }
            },
        },
    },            
}
 



[TOPIC: post.html]
#21

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

hi, in the interest of science, I'll put a theoretical fix up here and see if anyone can make it work. My problem is probably my testing environment. I have an un-activated Samsung II and a loaner Android that's also not on a cell network, and I have a feeling that is stopping me getting the deviceID. That being said, I would think that the following would work (inspired by a post on the Parse forum).

 

1. Install Parse Cloud Code like thus: https://www.parse.com/docs/cloud_code_guide. It will install some files on your local, including one called main.js

 

2. In Main.js, add the following and deploy it up to your app's cloud code:

 

Parse.Cloud.define("sendPush",function(request,response){
 
      Parse.Cloud.httpRequest({
      method: 'POST',
      url: 'https://android.googleapis.com/gcm/send',
      headers: {
        'Authorization': 'key=' + 'my_Google_API_Key',
        'Content-Type': 'application/json'
      },
      body: {
        registration_ids: request.params.deviceId,
        data: "testing push notification on Android"
      },
      success: function(httpResponse) {
        console.log("success");
      },
      error: function(httpResponse) {
        console.log('GCM Request failed' + JSON.stringify(httpResponse));
      }
    
    });
 
});
 
3. When you want to invoke the above code from your app, call it like this (you can use a REST API call to call any Parse cloud code function that you stick in min.'s:
 
--set the globals
APPID = 'my_Parse_API_Key'
RESTAPIKEY = 'my_Parse_REST_API_Key'
 
--pass through the device token you got back from GCM
 
local function sendPush(dt)
 
        local function sendPushListener()
            print("sent")
        end
 
        headers = {}
        headers["X-Parse-Application-Id"] = APPID
        headers["X-Parse-REST-API-Key"] = RESTAPIKEY
        headers["Content-Type"] = "application/json"
 
 
        local params = {}
 
        commands_json =
             {
                ["deviceId"] = dt
             }        
 
        postData = json.encode(commands_json)
        
        local params = {}
        params.headers = headers
        params.body = postData
 
        network.request( "https://api.parse.com/1/functions/sendPush","POST",sendPushListener,params)
       
 
end
 
This is all theoretical as my devices right now can't get to first base (e.g. get the deviceID). But if someone else would like to run with this I think it would work. Look forward to your trials!
 
best,
Jen
 


[TOPIC: post.html]
#22

jonjonsson

[GLOBAL: userInfoPane.html]
jonjonsson
  • Corona Geek

  • 1,051 posts
  • Corona SDK

Hi Jen, I just tested it real quick since its late here. Can look closer at it again in the morning.

 

My main question is where we are registering the device ID with Parse? Seems like the deployed function is registering on GCM only?

 

I got an error, but I will verify my test in the morning though, I was doing this hastily, might have missed something. So please someone else test too.  But I do know it is calling that function in the cloud because before adding that I got a 'no function' error.

 

My result from network request on device:

 

 

I/Corona (19568): Parse_response = {
I/Corona (19568): | responseHeaders = {
I/Corona (19568): | | Access-Control-Allow-Origin = "*",
I/Corona (19568): | | Content-Length = "51",
I/Corona (19568): | | X-UA-Compatible = "IE=Edge,chrome=1",
I/Corona (19568): | | Date = "Thu, 20 Jun 2013 14:19:41 GMT",
I/Corona (19568): | | Set-Cookie = "_parse_session=BAh7BkkiD3Nlc3Npb25faWQGOgZFRiIlMzNlOTJjMjIzYTA3N2VlNmFmM2I3NWE0NWY1OTJjMDk%3D--d043537614b38524d8b9bada3beb9d69c5ec78bf; domain=.parse.com; path=/; expires=Sat, 20-Jul-2013 14:19:41 GMT; secure; HttpOnly",
I/Corona (19568): | | Access-Control-Request-Method = "*",
I/Corona (19568): | | X-Runtime = "0.171536",
I/Corona (19568): | | X-Android-Sent-Millis = "1371737981559",
I/Corona (19568): | | Connection = "keep-alive",
I/Corona (19568): | | Cache-Control = "no-cache",
I/Corona (19568): | | X-Android-Received-Millis = "1371737981952",
I/Corona (19568): | | Status = "400 Bad Request",
I/Corona (19568): | | Content-Type = "application/json; charset=utf-8",
I/Corona (19568): | | HTTP-STATUS-LINE = "HTTP/1.1 400 Bad Request",
I/Corona (19568): | | Server = "nginx/1.2.2",
I/Corona (19568): | },
I/Corona (19568): | responseType = "text",
I/Corona (19568): | phase = "ended",
I/Corona (19568): | bytesEstimated = 51,
I/Corona (19568): | response = "{"code":141,"error":"success/error was not called"}",
I/Corona (19568): | name = "networkRequest",
I/Corona (19568): | bytesTransferred = 51,
I/Corona (19568): | status = 400,
I/Corona (19568): | url = "https://api.parse.com/1/functions/sendPush",
I/Corona (19568): | isError = false,
I/Corona (19568): | requestId = "false",
I/Corona (19568): },


 


[TOPIC: post.html]
#23

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

ah yes, to register your device with parse, I put in the onNotification listener the following:

 

 
if event.token ~= nil then
       registerParseDevice(event.token)
else
       print("no token returned, too bad")
end
 
and that function is:
 
[lua=auto:0]
local function registerParseDevice(deviceToken)
 
    
    local environment = system.getInfo( "platformName" )
    if environment == "Android" then 
        deviceType = "android"
    else
        deviceType = "ios"
    end
     
      dt = deviceToken
 
      print(deviceType)
      print(dt)
 
 
      local function parseNetwork


[TOPIC: post.html]
#24

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

[TOPIC: post.html]
#25

jen.looper

[GLOBAL: userInfoPane.html]
jen.looper
  • Contributor

  • 164 posts
  • Corona SDK

ah yes, to register your device with parse, I put in the onNotification listener the following:

 

 
if event.token ~= nil then
       registerParseDevice(event.token)
else
       print("no token returned, too bad")
end
 
and that function is:
 

local function registerParseDevice(deviceToken)
 
    
    local environment = system.getInfo( "platformName" )
    if environment == "Android" then 
        deviceType = "android"
    else
        deviceType = "ios"
    end
     
      dt = deviceToken
 
      print(deviceType)
      print(dt)
 
 
      local function parseNetworkListener(event)
        print(event.response)        
      end
 
        headers = {}
        headers["X-Parse-Application-Id"] = APPID
        headers["X-Parse-REST-API-Key"] = RESTAPIKEY
        headers["Content-Type"] = "application/json"
 
--[[I always put my user into a channel so that I can target them. Note, if you want scheduled pushes, you also need to send timeZone, formatted like 'America/New_York'. There's a google database you can use to input lat/long to get this info]]--
 
        commands_json =
            {
             ["deviceType"] = deviceType,
             ["deviceToken"] = dt,
             ["channels"] = {"S"..dt}                 
            }        
 
        postData = json.encode(commands_json)
        
        data = ""
        local params = {}
        params.headers = headers
        params.body = postData
        network.request( "https://api.parse.com/1/installations" ,"POST", parseNetworkListener,  params)
    
 
end



[topic_controls]
Page 1 of 4 1 2 3 »
 
[/topic_controls]