Using An Oauth 2.0 Service With IonicFramework

Many APIs such as Google, Twitter, and Facebook require Oauth in order to use.  This can get tricky when it comes to mobile because authorization must happen externally in a web browser.  To our advantage, we can handle Oauth 2.0 using the InAppBrowser plugin for Apache Cordova.

Basic instructions on using the InAppBrowser with IonicFramework can be found in one of my earlier blog posts.  If you’re looking to use Oauth in an Ionic 2 application, visit here, otherwise proceed with Ionic Framework 1.

Start by picking an API you’d like to use.  For this example let’s use Google.  If you haven’t already, you need to create a new project using the Google Developer Console.  In the credentials section you’ll need to choose Oauth 2.0 and create a client id for a web application.  The most important part in this process is to set the redirect / callback url as http://localhost/callback.  If your API console doesn’t allow localhost for the callback, choose some other dummy URL.

Now for the fun part.  Assuming you’ve installed the InAppBrowser plugin like described in my previous tutorial, crack open your app.js file as we’re going to add some token logic.

Google’s Oauth 2.0 consists of acquiring a request token and an access token.  Your users will get a request token when authorizing the app login, and then the request token will be exchanged for an access token.

The above code will open an InAppBrowser with a callback triggered for the load of each page.  In particular we will be looking to see if the loaded page is our callback page registered on the Google website.  If it is, extract the request token from the URL.  You may be wondering what startsWith is.  It is a function that must be created for checking the start of strings.  Code for this function can be found below:

With the request token in hand, it must be exchanged for an access token in order to use the Google APIs.  The code for getting an access token is as follows:

A thing to note about the Google APIs though.  The post requests must have a content type of application/x-www-form-urlencoded rather than the default AngularJS JSON content type.  You can change the default POST content type by running:

If you’re not using jQuery, you’ll have to format the POST manually by doing param1=value&param2=value.

So let’s look at a more working example.  The example will consist of two screens, protected and an unprotected screen.  The unprotected screen will have a button for initiating the token request / exchange:

The protected screen will display our access token which is used for all Google API requests:

Oauth Unprotected Oauth Login Oauth Authorize Oauth Secure

An example app.js can be found below which will be responsible for driving the two screens:

Some things to note about the example.  The Google scope is for the URL Shortener API.  You’ll want to use the correct scope for the API you want to use.  For other APIs like Twitter, you may not have a scope to worry about.  The InAppBrowser plugin does not work in a PC browser.  The callbacks will only trigger on a device.

Nic Raboy

Nic Raboy is an advocate of modern web and mobile development technologies. He has experience in Java, JavaScript, Golang and a variety of frameworks such as Angular, NativeScript, and Apache Cordova. Nic writes about his development experiences related to making web and mobile development easier to understand.

  • Akseli

    Hi,

    nice project and nice explication. I have only a question.

    Can I integrate it with another application, like twitch?

    Thank you,

    Akseli

  • Oscar

    Hi Nic,

    I am trying to integrate an ionic application with the RallyDev oauth and I have a problem, the EventListener function is not being fired.

    var ref = window.open(‘https://rally1.rallydev.com/login/oauth2/auth………..
    ref.addEventListener(‘loadstart’, function(event) {
    alert (‘loadstart!!! — URL: ‘ + event.url);
    });

    I have already installed inAppBrowser in my project and added the feature in the config.xml.

    The Rallydev oauth process it is well explained in the following URL
    https://github.com/RallySoftware/rally-oauth-examples

    The behavior I get when running the application in my android device is an error which says, error connection to http://localhost/callback?code=XXXXXXXXXXX&state=my_randomstate. I guess the inAppBrowser is trying to redirect me to the callback URL before the eventListener function captures the event, and of course it cannot find the URL so it gives you an error.

    Do you have any clue of what could be the reason of this behavior?.

    Thanks in advance,
    Oscar.

    • Hi Oscar,

      Can you confirm that you are trying to run from a device or simulator? The ref.addEventListener won’t fire in a web browser.

      What are your logs? If it isn’t working, there must be something in the logs saying why. Please run adb logcat to capture the problem when it occurs.

      Regards,

      • Leonardo Lima Ribeiro

        If I want to force fire in a web browser (because I’m testing all my app in web) there’s some way?

        Very thanks and congrats! I’m build a lot of features in my ionic project based on your articles!

        • You’d have to do a few things:

          You’d have to run a localhost server
          You’d have to create a callback page to process Oauth provider responses

          If you’re building mobile apps, I encourage you to stop trying to test in a web browser. You should test in an environment that closest resembles a device by either testing in the iOS or Android simulator or on an actual device.

          Testing a mobile app in a web browser is like test driving a new car in a video game and assuming it is the same as the real thing. Not the best idea.

          Regards,

          • Leonardo Lima Ribeiro

            Thank you very much Nic!

            I really want to publish my app as multiplatform (cross browsers and mobile devices). It’s a best idea?
            I was thinking about to publish it as app on Play Store, App Store and Windows Store, and publish too as a “WebApp” (if I can say that…).
            But maybe for webapp it’s not a good idea to use Ionic, is that true?

            What do you suggest me?

            And to finish, I’m used to test and debug in browser debugging with Chrome Inspector, but I really agree with you. It must be tested in devices that will be published (Yesterday I discovered that my iOS version doesn’t work, sadly…) So, what tools should I use to debug like Chrome Inspector, but for devices? Can I connect my device with WebStorm and use the debug tool? What’s your usual setup?

            Thank you again and congrats for your blog! You’re awesome!

          • Ionic is good for Android and iOS but it doesn’t support Windows Phone. However, the market for Windows Phone is very small so you probably wouldn’t be missing much.

            You can debug your iOS builds in Xcode and you can use ADB to debug your Android builds:

            https://www.thepolyglotdeveloper.com/2014/12/debugging-android-source-code-adb/

            Regards,

    • Oscar

      Solved!!!,
      InAppBrowser does not fire events unless you add “, ‘location=no'” in your window.open.

  • Alessandro Ouatu

    Hi guys, i need i want to store the access_token for gapi. how can i do?

  • Thomas Liu

    Hi Nic,

    This is a great article.

    I have a question.

    If the authorization server does not permit ‘http://localhost/callback’ as redirect_uri, what should I do?

    Can I use arbitrary uri for redeirect_uri?

    Thanks,

    Thomas

    • Just pick any redirect uri on the server and make sure it matches in your JavaScript code. The InAppBrowser just needs to be able to identify when to close the browser window.

      Regards,

      • Thomas Liu

        Hi Nic,

        I appreciate your answer. I have resolved this problem.

        Thomas

      • pixelmike

        Hi, thanks for creating this library, very helpful stuff! When you say “pick any redirect uri on the server”, which server are you talking about?

        • By server I mean the provider that you’re using. If you’re using Google Oauth, make sure the url you set as the redirect uri in the Google dashboard matches what is in your JavaScript.

          Regards,

  • David Oddoye

    Hi Nic,

    Awesome read.

    Question, is it better to use this that Oauth from ngCordova?

    • I’m the one who made the oauth module in ngCordova, so you may want to save yourself the hassle and just use the library.

      You can, however, use the information on this page to add providers that don’t yet exist in ngCordova.

      Regards,

  • David Oddoye

    Thanks Nic. I’ve integrated Facebook and Twitter logins into my app, thanks to your plugin.

    Now for Google. What do i need for “array appScope”? i just want the user’s profile details.

  • Tin Chu

    Hey Nic..! Big fan of your blog!.. A question I’m developing an app, and they have their own Api, where should I started?

  • Hello Nic, thansk for this tutorial. I am trying to implement the same with the Instagram API. I modified your code a bit, and after pressing the button “Authorize” on instagram, I get redirected to a page “http://localhost/callback#access_token=1942489499.1252936.ad8c7fcf694149bab8f050256d0ba59e”. However, it opens a new window… how can I keep in the original window (my Ionic app) and how does that read the data?

    • Oke, so I tried using your ngCordova solution, as it looks more simpel. In the input you require appScope and in the ngCordova.js you set: scope=’ + appScope.join(” “). Shouldnt that be .join(“+”)? As I read on the instagram api: scope=likes+comments

    • Oauth requires a login flow. My method is web based which will always require a browser. There is no way around this without designing a native plugin for the job.

      Regards,

  • SM

    hi ,
    i need to understand this
    with app example and we can download it
    or share it

  • Alpesh Trivedi

    I am getting Webpage not available : The webpage at http://localhost/callback? error

  • Alpesh Trivedi

    and also getting error in alert ERROR : {“error”:”invalid_client”}

    • This isn’t enough information:

      What provider are you trying to connect to?
      What platform are you using (iOS, Android, etc.)?
      Device or simulator?

      You may want to do a Google search for that error based on the provider you’re trying to connect to. My assumption is that you’re missing a parameter in your request.

      Regards,

  • Anil Kumar

    Hi Nic,

    when I am integrating twitter it is showing the error as Chosen SHA variant is not supported , I installed jssha library also. can you please tell me how to rectify this error.

    Regards
    Anil Kumar

    • Put your project on GitHub and I’ll take a quick look.

      Regards,

      • Anil Kumar

        Hi Nic,
        Chosen SHA variant issue is solved but I am unable to get the access token from twitter in latest cordova version(5.0) but when I tried in older version am able to get the access token for twitter and my code in github is : https://github.com/anilkumar007/launcchoauth.git I need an automatic login in twitter or google and also the profile info of the user also.

        Regards
        Anil Kumar

        • Sounds like you are suffering from the Apache Cordova 5.0 whitelist enhancement:

          https://www.thepolyglotdeveloper.com/2015/05/whitelist-external-resources-for-use-in-ionic-framework/

          After signing in, I cannot help you with the APIs because I don’t know them. The scope of my knowledge ends with Oauth.

          Regards,

          • Anil Kumar

            Hi Nic,
            Thanks for the reply, I am able to login now via gmail and twitter in older version of cordova but I want to access the user profile after login from gmail and twitter, can you tell me how can we achieve this.

            Regards
            Anil Kumar

          • Again, I don’t know the APIs. You’d have to consult the provider documentation for obtaining specific data after sign in.

            Regards,

          • Anil Kumar

            Hi Nic,
            How are you? I hope you are doing well, I need a small help am creating a sample projects by using ionic for windows 8 in emulator but i need to debug the app when running in window 8 emulator or mobile. In chrome it is unable to inspect the device

            Regards
            Anil Kumar

          • It is only appropriate to ask a question in the comments section of a post if the question is related to the post. Otherwise you need to reach out to me on Twitter.

            Future readers don’t want to sift through hundreds of unrelated comments to find the answers they need.

            Regards,

  • mrchess

    Thanks for this post. Is there supposed to be a $stateProvider for http://localhost/callback? When I try your example I get an error.. Cannot GET /callback?code={{MYCODE}}

  • Denial Torres

    Hello Nic.

    I finally can sing up and login with gmail and your tutorial on my website app, I’m using ionic framework with cordova on the client side (android) and ruby on rails for the server side.

    the problem is that when i´m login with my social credentials a little pop-up window (inappbrowser plugin) appears but never closes, so i´m navigating my website app on the pop-up window instead of the mobile app,

    and the mobile app does nothing, it still remains in the main window where you are prompted for credentials

    any suggestian with that ??

    regards

    • I’m not truly sure what you’re talking about, the the InAppBrowser won’t close unless you tell it to via a listener event. Are your listeners correct?

      Regards,

  • Prasad Mhatre

    where can i this google plus login example?Repo link?

  • Sindri Sigurjónsson

    Hey Nic, i’m trying to follow the tutorial but when i run it on a iOS device a always get the same errors. When the in app browser is opened i get the error message: webView:didFailLoadWithError – -999: The operation couldn’t be completed. (NSURLErrorDomain error -999.)

    The in app browser still opens and when i press the accept button i get another similar error: webView:didFailLoadWithError – -1004: Could not connect to the server.

    This error message is followed by the code going into the error function of the call and there i get: {“error”:”invalid_request”,”error_description”:”Parameter not allowed for this message type: session_state”}

    Do you have any idea of what this could be ?

    • Well, the error says it all:

      That error message was returned from the service you’re trying to use. It means you’re not using their oauth spec correctly. I suggest you read the documentation for that particular provider.

      Regards,

      • Sindri Sigurjónsson

        Thanks for the response, i found why it wasn’t working and fixed it. Now i get back a access token, does this not return any information about the user ?

        • I have no idea what APIs you’re using. I suggest consulting the documentation to see what it returns.

          Regards,

  • Prasad Mhatre

    Can we get repo for this above app

  • Tim

    Hi Nic,

    Looking to implement oauth2 in my app – I see that you have the client id and secret hard coded in the client, which from what I have read is not recommended. Are you aware of this? what do you think?

    • You’re right, it is not recommended, but people are still going to do it anyways. The best solution is to use implicit grants if available, but for many providers it is not available.

      https://www.thepolyglotdeveloper.com/2014/11/extract-android-apk-view-source-code/

      Best,

      • Tim

        Ok cool, good to know you’re aware. I see some of the auth providers in the ng-cordova-oauth only use a clientId and not the client secret. is this a sign of an implicit grant?

        • In ng-cordova-oauth I used implicit grants wherever possible so if you see a provider without a secret key requirement it is in fact using an implicit grant.

          If you care about security I’d find a native SDK alternative to the providers that don’t offer implicit grants. Ultimately that is up to you though. Many developers (sadly enough) don’t care.

          Let me know if you have any other questions 🙂

  • Richard Moran

    Hi Nic,

    Would it be possible to use this for the WordPress Rest Api?

    Thanks,
    Richard

    • Does the WordPress REST API use Oauth? If yes, then I don’t see why not.

      Regards,

      • Richard Moran

        Hi Nic,

        Thanks so much for taking the time to respond.

        While the WP rest API lets you use oAuth to create a consumer with a key and secret, it can only be done via the command line. There is no UI for it (yet) and as such there is no option to set a callback URL as you can with other API’s such as Google, FaceBook and Twitter and as you do in this example.

        With this in mind is it still possible to tailor this example for the WP Rest API? The lack of a UI at present makes the task seem massively daunting!

        I actually see a lot of people crying out for a proper tutorial on it as it’s earmarked for inclusion in the WordPress core!

        http://wp-api.org/guides/authentication.html

  • Hello Nic, I want to make an app for my rails webapp , my rails app using doorkeeper as the oAuth2 provider. can i use this approach to my rails app?

    Thanx , Sigit

    • I don’t know anything about Rails or DoorKeeper, but if it works as an oauth provider then it should be fine 🙂

  • fabioi

    Hello Nic I am testing google login and I noticed that I am always asked to insert email and password. Am I doing something wrong or is a limitation? If the user has a google account active on the device It would be nice just to ask for the authorization without having to fill data .Thanks!

    • The approach I demonstrated uses a web view, not native application communication. If you want to check device services you’ll need to use the native Google SDK to access them. The InAppBrowser cannot read device services.

      Regards,

  • Federico Bianchi

    Hi Nic,

    I’m working on a Ionic app using AWS cognito to manage access to AWS services.

    I’m having a problem using ngcordova OAuth with the provider google because the access_token received can be sent to a Google API but cannot be used by AWS cognito to assume the role of the person who’s doing the login action. Everytime the response is that the token in invalid.

    In fact you write: “Google’s Oauth 2.0 consists of acquiring a request token and an access token. Your users will get a request token when authorizing the app login, and then the request token will be exchanged for an access token.” this double action is not provided by the ngcordova Oauth, so the question is: do you plan to modify the ngcordova Oauth to solve this issue in the future?

    thanks in advance

    Federico

    • You may have a misunderstanding when it comes to oauth.

      There are two different grant types in oauth. You can work with implicit grants designed for client facing applications such as mobile, or you can work with explicit grants designed for server side applications where the client cannot access source code.

      This particular article demonstrates explicit grants which technically should only be used server side. I wrote it here to show it is possible client side.

      In ng-cordova-oauth, I use implicit grants wherever possible. I say wherever possible because not all providers offer the implicit option. Google, for example, does offer implicit grants.

      I don’t know what AWS Cognito is, but it sounds like there are two problems:

      You’re using ng-cordova-oauth in a way it was not intended to be used
      You have something misconfigured in Cognito

      So moral of the story, there is nothing wrong with ng-cordova-oauth. It follows the spec how it should be, so there is nothing to resolve. I suggestion you read up on oauth 2.0.

      Best,

      • Federico Bianchi

        Thanx for quick reply,

        for sure I must study more about oauth;) but I understood your answer.

        Finally I solved my problem using this tutorial client side but it’s clear is not the correct way, I will study to find a solution server side

        BTW here there is a link to AWS Cognito http://aws.amazon.com/cognito/

        Federico

  • Joti Basi

    Hi Nic, great tutorial. Any tips on how to use Login with Google or FB to register a user via restful service.

    • I don’t believe this is possible. I think that is a security risk for the provider, allowing registrations over REST. My best advice would be to start the Oauth flow and let the user decide that they want to create an account if they don’t have one.

      Best,

      • Joti Basi

        Thanks but think I didn’t explain very well – let me give you a use case. Let’s assume I want to enable fb login on my ExampleApp. The first time user logins with fblogin I would like to create a new account in the ExampleApp using Facebook credentials. ExampleApp communicates with a CMS such as Drupal or WP via a rest api. Then every time this user logs into the app with Facebook, he can access the content created by him in ExampleApp

        • Joti Basi

          Tinder is a good example

        • Ah! That is a completely different scenario. Thanks for clarifying 🙂

          Most Oauth providers return, or have an API that returns, a unique service id. By service id, I just mean an account identifier that they use instead of your username. Why not take that value and send it to your third party server? The value will never change and it can act as your API key to your RESTful server.

          Any holes in that plan?

          Best,

          • Joti Basi

            Actually not a bad idea. With an SSL it can be easily protected from a MIM attack.

          • Let me know how it goes or if you decide to go a different route 🙂

  • Mark S

    I get a 404 on the callback after the signin with google. I added a console.log() to see if the eventHandler() was working and it doesn’t appear to be.

    I am using the browser platform in ionic.

  • Anthony Kumar

    Not getting the login page instead ionic app starter is getting displayed.

    Following is the error message in console

    ncaught Error: [$injector:modulerr] Failed to instantiate module starter due to:

    Error: [$injector:nomod] Module ‘starter’ is not available! You either misspelled the module name or forgot to load it. If registering a module ensure that you specify the dependencies as the second argument.

    http://errors.angularjs.org/1.4.3/$injector/nomod?p0=starter

    http://errors.angularjs.org/1.4.3/$injector/modulerr?p0=starter&p1=Error%3A…F%2F192.168.0.126%3A8100%2Flib%2Fionic%2Fjs%2Fionic.bundle.js%3A10478%3A12)

    • Thanks for the logs. I see a few potential problems here:

      Because I see an IP address in your logs I assume you’re using ionic serve, ionic view, or ionic live-reload. Because of how the InAppBrowser plugin works, those three ionic services are incompatible and may produce strange or non-working results.
      The particular error you received is usually due to a typo in your code. I get it all the time and 99% of the time it is due to me having a typo somewhere. Maybe incorrect capitalization, a stray semi-colon, etc.

      Based on what I said, look through your code and see if anything matches.

      Best,

  • Elham Sarikhani

    ref.close after login, doesn’t close the popup in iOS testing with ionic view as well as iOS emulator but in Android it works fine. I used _blank and installed cordova-plugin-inappbrowser as well. have you ever faced this issue in iOS?

    • Ionic view hardly works with the InAppBrowser plugin or any plugin for that matter. I encourage you to not use it when testing your application.

      With that said, doing oauth in an ionic view application is not supported.

      Regards,

      • Elham Sarikhani

        Thanks Nic! I couldn’t have concluded that the issue is for ionic view specially because the same test passed in Android device, using ionic view.
        But the scenario would be the same in iOS emulator as well and I can’t get the popup window to close even with a timer.
        Just to verify if I got your point or not, so, the only way for me to test the app in iOS is to run it in a real device and not to use ionic view nor emulator right?

        • You can test in a simulator or on a device, it doesn’t matter. What does matter is how you test it. You cannot use ionic serve, ionic view, ionic live-reload, or phonegap build. Sure it may work some times using these services, but I can tell you from all the hundreds of troubleshooting requests that I receive, that the tools are seriously flawed.

          If you want a true testing experience, build a binary and install the binary to your device or simulator.

          Regards,

          • Elham Sarikhani

            Will do. Thanks for the heads up Nic!

  • MaheshKarthu

    (Beginner of ionic)
    How to solve this problem (in apk) and I am using cors also

    Invalid Parameter value for redirect_uri : Missing authority: file:///android_asset/www/index.html

    • You are not using a valid redirect uri, exactly like the error states. You need to use an actual HTTP url, like demonstrated in the article.

      • Joseph Andrews

        to use this Google APi in ionic project, what type project we should select in Google API console, website/installed applications,etc ? what Origin need to be set?

        • It should be a web application and you should leave the origin blank.

  • Suresh Kumar Majhi

    Hi Nic,
    I’ve a doubt. If I’ve already logged into 3 gmail accounts in my mobile through my native gmail app then, at the time of Google Sign-in through this plugin… will it prompt me to “Choose an account” option from existing my existing gmail accounts?

    • There is a parameter that you must pass in to Google that triggers account selection. I encourage you to read the Google API documentation.

      Best,

      • Suresh Kumar Majhi

        But, Nic how Google Server will know with how many accounts I’ve already logged in my mobile. Because, my hybrid app is running inside a browser & gmail app is a native app. So, no way… I think both can communication with each other to build that list.

        Don’t know I’m right or wrong.

        • The InAppBrowser approach is sandboxed and cannot communicate with any other app. You would have to do your own logic for choosing accounts via the API and storing that information.

          • Suresh Kumar Majhi

            Do you know any API like that? I googled a lot but, not getting any API or specific approach to solve this problem.

          • Like I told you the first time. I encourage you to read the Google API documentation:

            Adding the above to the request URL will show a prompt for users to choose which account they want to use if they are signed into more than one account.

            http://stackoverflow.com/questions/31544595/how-to-force-account-login-for-a-single-account-user-with-googles-oauth-2-0

            Here is the Google API documentation:

            https://developers.google.com/identity/protocols/OAuth2?hl=en

            Please read it.

            Regards,

          • Suresh Kumar Majhi

            HI Nic, Thanks for the information. But, I can’t able to understand how Gmail Server will know with how many accounts I’ve already logged in. Because, as you told “InAppBroswer” work inside a sandbox & I believe after doing the job it’s might’ve close the sandbox. So, no way… in mobile has any kind of information regarding my multiple accounts. So, from where Gmail Server will get my multiple account information & build that “account picker” list.

            But, if the app will be a native app then I think, Gmail server can identify the session info from my native gmail app & build the Account Picker list.

          • You’re right, you’re not going to be able to do this with multiple user accounts. I think you need to take a step back and share with me what you’re trying to accomplish as a final result. Then we can go from there.

            Best,

  • Prag

    Hi Nic, I was just curious if you have submitted an app that using OAuth recently? I used the Google/Twitter/Facebook sign in service provided by azure mobile services and Apple rejected it citing 17.2 – Apps that require users to share personal information, such as email address and date of birth, in order to function will be rejected.
    I use the login to manage their user-specific info, but I’m even just confused on how OAuth violates that rule b/c I thought the whole point was to abstract the login and reduce the amount of info the user has to give me? Sorry, I realize this is a bit off topic :/

    • I have not submitted an app that uses oauth recently, but none of my previous apps have received complaints so far. In the reviewer details you should clarify that your app uses oauth to work with public vender APIs, then list the vendors.

      If Apple better understands the use case, they will probably approve it.

      Regards,

  • Ranjoy Sen

    Hey, I followed according to the steps which you provided. It worked as expected in iOS but in android ref.addEventListener(‘loadstart’, function(event) is not calling. hence the browser is not closing. Any idea what can be done

    • What do your logs say?

      • Ranjoy Sen

        it does not go inside addEventListener, where as in iOS it goes

        • What do your logs say?

          Every time you respond without logs, I’m going to ask you for logs FYI. If you don’t know how to check for logs, tell me so I can help you.

          Regards,

  • Rituraj

    Hey Nic

    First of all thanks for your beautiful tutorials they are really helpful for newbies like me

    I followed this tutorial and was able to get access token at end and then when i tried to access basic user profile info by binding access token received with
    https://www.googleapis.com/plus/v1/people/me
    as
    $http.get(“https://www.googleapis.com/plus/v1/people/me?access_token=”+accesstoken)……
    I got errors saying insufficient permission so NIc please tell me how to get basic user info correctly.

    Thank you

    • You have to include the correct application scopes in your request. In my example, I’m only including the urlshortener permission, not profile.

      You’d have to read the Google API docs for this.

      Best,

  • Gopinath K

    This is the error im getting …. what i need to do

    Error: redirect_uri_mismatch

    Application: TaskBean_App

    You can email the developer of this application at:

  • Gopinath K

    Hi Nic Now i am creating node js Project … and also i’m new to this technology , How to run this project as a android application while i m running this app it shows pop up window to sign in google but i need this sign in access in mobile view.

    • A Node.js project is a web application. This post is for Ionic Framework.

      Can you be more clear in what you’re trying to do and the platforms you’re trying to use?

      Thanks,

      • Gopinath K

        Hi Nic …. Thank you for your reply the thing is i just introduced myself that i am learning Node.Js … I am clear that i am working in ionic framework which is going to be converted as a mobile application in future ,

        while running this code following things are happening … i need to know what went wrong …

        1.First It is asking for google login
        2 after login i got the following screens ….after clicking allow the error screen is displaying .

  • Joseph Andrews

    Hi Nic, Im trying to use Calendar Api, but the example provided here https://developers.google.com/google-apps/calendar/quickstart/js does not return a Access token, how to pass the access token to this function ( gapi.client.load(‘calendar’, ‘v3’, listUpcomingEvents); ) as i want to get the list of events from user’s calendar

    • I’m sorry, but I don’t know the Google APIs. You’ll have to read the documentation. This example only gets the access tokens using Google Oauth, nothing more. What you do with the tokens after is up to you.

      Regards,

    • Chris Herselman

      Hi Joseph, did you figure it out? I would like to know how to do it, thanks!

  • Hi Nic
    Thanks for your great article,
    I can get access_token but I don’t know what should I do after that, how can I get user information such as email, name, profile image, it would be great if you continue such thing in the next articles.

  • Sathishkumar Thangaraj

    Hi Nic Really helpful post for the beginners ….

    I’m Getting the following errors after clicking the Allow button …

    and i have converted the ionic app to android app that shows following error after clicking allow button (Screen shot attached )….

    Logs

    TypeError: Cannot read property ‘addEventListener’ of undefined

  • Sathishkumar Thangaraj

    Hi Nic Really helpful post for the beginners ….

    I’m Getting the following errors after clicking the Allow button…

    Screen shot attached (While running as Android app)

    Logs

    TypeError: Cannot read property ‘addEventListener’ of undefined

  • Madhan kumar

    Hi, I am using LinkedIn OAuth and I am able to receive the request token but unfortunately $http.post fails every time with error status of 0. No problem with the request parameters and I have also specified the content type as ‘application/x-www-form-urlencoded’.

  • Victor

    Hello. I used all the code from expample.
    Authorized redirect URIs: http://localhost/callback

    But all the time i get the error
    Cannot GET /callback?code=4/IsboHTU7zX8mJa2p9uDjkCSSrB4LmdwlU93hvsgzQo
    And popup windows not closing.

    It looks like i need to create url /callback in $stateprovider.

    could you help me?

    • What do your actual logs say? Are you trying to use ionic serve, ionic live reload or ionic view? None of those services are compatible.

      Regards,

      • Victor

        Hello.
        Even on my real nexus 5.

      • Victor

        Hello.
        Even on my real nexus 5.

        • Jameesh Moidunny

          i victor you got solution, i am also having the same problem, assume something wrong with the callback url

          • Raúl Cacabelos Bote

            I’m having the same problem. Seems like something’s wrong at the callback, I’ve been debugging the code of ‘ng-cordova-oauth’ library and the response never enters in the IF statement (ng-cordova-oauth/src/oauth.facebook.js):
            (…)
            browserRef.addEventListener(‘loadstart’, function(event)
            { if((event.url).indexOf(redirect_uri) === 0) {
            (…)
            I’ve been fighting against this problem at least 9 hours and cannot revolve the issue…

          • I found a solution. Apache introduced some breaking changes in the InAppBrowser and core framework. It will take me a bit of time to fix it. Localhost / non-existing web pages get piped into the loaderror event now, rather than loadstart. Quickest fix is to host your own callback so it doesn’t fail to load.

          • Pelancho Guerrero

            im getting the same error using facebook login, before update ionic everithing working nice, can you explain with more detail how to fix this issue??

          • Please see this:

            https://github.com/nraboy/ng-cordova-oauth/issues/193

            It is a confirmed bug now.

          • Angel Suarez Fernandez

            Hi, I have had a look at the github issue and I have already upgraded cordova-plugin-inappbrowser to 1.3.0 and my Cordova version is 6.1.1. However I still have the problem with localhost/callback ERR_CONNECTION_REFUSED. Do you have any idea why?. Many thanks in advanced for your time.

          • What provider and what platform? Also can you share the device logs?

          • Angel Suarez Fernandez

            We have developed an internal OAuth provider for our project which works already for quite some time ago. I am trying to use it in an android emulator but I have not succeeded so far. I am sorry but I don’t know which logs I can give you.

          • Angel Suarez Fernandez

            Hi, actually I though you were asking for some other log :s my bad!.

            Whenever I click the button that opens the browser the first connection to my server is done well and then I get back the exchange code, but the redirection does not work as shown in the second picture.

            In the log I am not seeing that much. Probably it gives you an idea.

            Hope it helps.

            Thank you.

          • I see [object Object] in your logs. Can you serialize that and see what it says? I also notice you are using port 8104 in your callback. Why?

          • Angel Suarez Fernandez

            If you have a look to the following code you can see that line 3 prints [object Object] that corresponds to login.js (66): http://pastebin.com/mScLHzED

            I am using port 8104 because it is the port it uses to deploy ionic. Actually, it should not matter which port i am using right?, the listener will capture the redirection and then it will execute the code inside de if statement. Probably I am wrong here?

            Below you can check the log data.

            http://pastebin.com/es0iPHmw

            Hope it works (this is the third time).

          • So this is the error you’re receiving:

            You say it is related to the following line:

            You also mentioned the port exists because you are using Ionic Deploy.

            If I had to guess, your problem is due to how you’re deploying the application. Yes, the port truly doesn’t matter, but how your application runs does. By using services like Ionic Serve, Ionic Live-Reload, Ionic View, Ionic Deploy, etc., you’re going to run into trouble at some point because of how those services handle native plugins. I can’t say I recommend any of them.

            Try the following few things.

            First try building and installing your application locally using the following:

            Check out the logs and see if anything changed.

            If that doesn’t work, try changing the following line in your code:

            Change it to the following:

            Some versions of Apache Cordova and the plugin are wacky and require different things.

            Start there and report back.

            Best,

          • Angel Suarez Fernandez

            I have used build and run to install the app in Android (Genymotion) and I have also tried window.cordova.InAppBrowser.open but the problem remains.

            Regarding the log data I’ve realised that the error occurs before starting the authentication. When I click Log In the first screen it goes to a form to insert the credentials (that’s when the error happens). Once you have entered your credentials you run the login function (open the browser, retrieves the exchange code, redirect to the callback and gives the error). Therefore, I guess the error in the log has nothing to do with my problem.

            Any other alternative?

            Thank you again.

          • I think I’m out of ideas. Try it without a port? Maybe for whatever reason the InAppBrowser is cutting out the port. Are you sure that you’re getting an exchange token? You might want to put a print statement after every line to troubleshoot how far it gets and what data it obtained.

            A part of me wonders if it is your custom implementation for Oauth.

            You can always try my ng-cordova-oauth library with a popular provider and see if that works. If it does maybe alter the code in the library to fit your needs.

          • Angel Suarez Fernandez

            Hi again, finally solved that issue, but I just get blocked in other different one. The problem now is that the request of the access_token failed. Error logs are not really helping: the message of the error is empty and the status is 404. I have tried one of the POST request in POSTMAN (in the browser) to simulate it and I get the access_token back, but in InAppBrowser something goes wrong.

            Any idea or suggestion?

            Here you have the current version of the code: http://pastebin.com/5Ed9ubY2

            Many thanks for your time.

          • What was the original solution for you?

            I notice print statements throughout the code. Where is the point of failure?

          • Angel Suarez Fernandez

            Hey, finally I solved it. It took two days, but now it works perfect. You can have a look at the code here:

            http://pastebin.com/7f611y3U

            Many thanks for you help.

          • Glad you got it. Hopefully I helped contribute to your solution 🙂

        • Until you show me logs, I cannot help you further.

          Regards,

    • Jameesh Moidunny

      i victor you got solution, i am also having the same problem, assume something wrong with the callback url

  • Rituraj

    Hey Nic

    Thanks for solving all my frequent queries and with your consistent support Finally i was able to develop my complete app.
    Really thanks Nic a major credit goes to your blog .

    My App: https://play.google.com/store/apps/details?id=com.foodzee.co&hl=en

    • Thanks for sharing what you made 🙂

    • shash

      Nice one Rituraj….how much time did you take to develop this..?

      • Rituraj

        Hey shash thanks
        it took me around 20 days of 5-6 hours each

  • Valar Mathi

    Hey Nic thanks for the post,Once i install the app it is asking for log in and next time am able to enter without logging in again thats fine.I dono how to make the user log out from his account. Even if i clear the cache and history still am able to enter with the previous access token received.Help me to solve this.

    • You must clear the InAppBrowser with the following options:

      clearsessioncache=yes
      clearcache=yes

      Best,

      • Valar Mathi

        Thanks Rob its working but now location bar is visible,you could see that i have set location=no but still url location bar is visible where i have done mistake.
        window.open(‘https://accounts.google.com/o/oauth2/auth?client_id=’ + clientId +

        • Valar Mathi

          I have found where the error is.Its working once I add toolbar=no option additionally.

  • shash

    Hey Nic….in ionic i.c in android device i can authenticate through google and i’am getting oauth token…is it possible to get access token for particular login…???

    • I’m not sure I understand. Can you be more clear?

  • Jorge Cascante

    I’m trying to get google calendar events. I successfully get the accessToken but then I don’t have it very clear as to how to use it to request the calendar.

    • Chris Herselman

      Hi, did you figure it out? I need some help doing the same and would appreciate some example code 🙂

      • Jorge Cascante

        At the end it was done in the backend side.

  • Hello, I’m trying to connect with strava, but I can’t, when I send the POST to get the access_token, the response is a error with status -1, I can connect with another providers, but strava is impossible. Any idea?

    • You should probably just use my ng-cordova-oauth library to make you life easier. It includes Strava

      • Thank you Nic for your post, I tought that but I need to connect another sports apps that it doesn’t have support in your library.

      • I tested with your library and I have the same problem, it seems that the problem it’s with my integration, I tested adding this meta for the whitelist <meta http-equiv="Content-Security-Policy" content="default-src *; style-src 'self' 'unsafe-inline'; script-src 'self' 'unsafe-inline' 'unsafe-eval'"> but I do not have success, I thought the error might be my Strava App, but this work from the browser

        • It sounds like it is probably a problem with how you configured Strava through their API dashboard.

          • Thank you Nic for your answer. I thought the same, but the same configuration in the browser is working, apparently don’t is a problem with the configuration of Strava, because I have the same problem integration Moves App, I could integrate Runkeeper and Fitbit without problem.

            I find no other reason for the problem

          • I opened an issue ticket here on your behalf:

            https://github.com/nraboy/ng-cordova-oauth/issues/246

            Can you comment on it with a set of client and secret keys. After we are done troubleshooting you should be able to reset your keys. I am a bit doubtful we will get anywhere because the Strava auth documentation has not changed since the last time I looked at it:

            https://strava.github.io/api/v3/oauth/#get-authorize

            Best,

  • Hari Kishan

    Hi Nic, how can we fetch the refresh token for google using ngCordova?

    • Refresh tokens are only returned when using an explicit grant. It is best to use implicit grants whenever possible because explicit grants technically should not be used in client facing applications because the secret keys are exposed.

  • rejinthala manoj

    Hi Nic,
    I am trying to give the redirect URI like http://localhost:8100/#/soft/login it shows error cannot contain a fragment.can you please help me out to solve this problem.I am using Ionic.
    thanks in advance.

    • You cannot use an angular route. You also can’t use ionic serve, which I believe you’re using because of port 8100

      • rejinthala manoj

        what should i give the redirect URI value

        • Sharanagouda K

          Have u got solution

      • Sharanagouda K

        What should we give redirect_uri because http://localhost/ and http://localhost:8100/ , http://localhost/callback is not working in mobile in appbrowser only it shows webpage not found showing above localhost paths

  • Mohamed Nabil

    Hello Nic,
    It’s working perfect and now i’ve the access token.
    But i would like to achieve this
    https://developers.google.com/analytics/devguides/reporting/core/v3/quickstart/web-js
    Could you suggest how to do it after having the access token ?
    Thanks in advance

    • You’d have to read up on how to use their API or APIs in general. In most cases you pass the access token in the header of every request or the URL query.

      • Mohamed Nabil

        Thanks, i managed to find the way if anyone is interested to know how to authenticate after getting the access token,
        gapi.auth.setToken(data)

  • Muhammed Naseer Naseer

    Hi Nic,
    I have encountered with a problem while using this. I am using this with Apache Cordova app with angular client. While sending the oauth request Cross Origin Request error is showing. How to get it working?

    • Am I correct in assuming that you are trying to do this from a web browser, using ionic serve, ionic live-reload, or anything else that isn’t a clean install on a device?

      Devices don’t suffer from CORS issues, which is why I’m making that guess.

      Let me know.

      Best,

      • Sharanagouda K

        I got an error
        {“error”:{“message”:”CORS:the domain wwww.linkedin.com is not allowed”,”status”:403}} I am creating Linkedin Login using ionic2

  • Roney Francis
  • exp team

    Hi Nic,
    I have set up this code. Secure page is accessible without login if we redirect to it directly. How to redirect from secure page to login if not logged in..
    Thanks in advance..

    • You’d have to add your own logic. Maybe on the secure pages, check to make sure an access token exists in storage, otherwise, navigate backwards? There are hundreds of ways this can be accomplished.

  • Sonam Gupta

    Hi nic,
    this post is not working for access token

    • I’m going to need more information than that if you want help. Logs would be a good place to start.

      • Sonam Gupta

        Hi Nic,
        Error is coming, when i want the fetch access token by using refresh token. In error section it is returning null. Nothing else.

      • Juanjo Salvador

        It works, but when the app is going to make a POST request into “https://accounts.google.com/o/oauth2/token”, there is a 404 response.

        Anyway, great tutorial Nic!

  • Manoj Bhardwaj

    event is not fired

  • Manoj Bhardwaj

    ref.addEventListener(‘loadstart’, function(event) {

  • yash

    if we use ‘_system’ to open authentication page in system browser then how do we revert back the authentication token to native app. I mean want will be the redirect uri in-place of ‘http://localhost/callback’.

  • Amarjit Singh

    hello nic
    nice article it’s working. i want more other things like yahoo and hotmail authentication, have u any reference or working code please share with us.

    i used this article https://github.com/sahat/satellizer but it’s return error after logged in. may be we should need to live(app) first because yahoo or hotmail is not find redirect url like localhost or may not.

  • Francisco Vieira

    Definitely did not work for me. I can get the token “4/AsRzYO5Dm4NHXmIZWaJrfD55Of8sjLs8okcndELTNwo#”, but when do the POST to get more data the response is null

    • If you received an access token, then oauth was successful. If you are having problems using the access token, you should consult the API documentation for the API you’re trying to use.

      Best,

  • Yashesh Bharti

    Dear Nic,
    I need help integrating google drive api to ionic, I have been trying to do this from about 2 weeks now and i’m stuck,
    when i try running it locally it works without problems but when i try to run on a physical phone or an emulator it doesnt work, so i’m assuming it is “Authorized JavaScript origins” problem on the google developer console since i can authorise localhost as it runs on http:// but not file:// protocol with which Ionic works.. I would really be grateful if you can help me with a workaround or any other way that is possible.
    I owe you a lot 🙂
    Thank you so much

    • Oauth via hybrid application browsers no longer works for Google. Requests are now blocked by Google. You’ll have to use the native Google SDK if you wish to use the Google APIs in your Cordova based application.

      • Yashesh Bharti

        If you can guide me to a package or some example i’d be grateful..
        Thankyou so much for your reply Nic 🙂

  • Abhijit Vaidya

    Hello Nic,

    Great blog!
    I am using linkedIn plugin in my app. When I click on log in button, LinkedIn login window opens but it does not take credentials of my LinkedIn account (I have LinkedIn app installed on my phone and I have logged in into it) I have to type in username and password each time I try to login. Can you please let me know if this is expected behaviour or I am missing something?

    • This is expected behavior. The InAppBrowser method of oauth is sandboxed from other applications.

      • Abhijit Vaidya

        Hello Nic,

        Thanks for the response. My app worked fine all these days but now I am facing a strange problem. LinkedIn OAuth works fine when user logs in for the first time. When user logs off and tries to log in again using LinkedIn Oauth 401 error is thrown with following response

        {
        “errorCode”: 0,
        “message”: “Unknown authorization header {Basic}”,
        “requestId”: “”,
        “status”: 401,
        “timestamp”: 1494566772288
        }

        can you please put some light on this?

        Thanks

    • Sharanagouda K

      Have you modified the above code for Linkedin?

      • Abhijit Vaidya

        Hi @sharanagoudak:disqus ,

        Here is the code:

        document.addEventListener(“deviceready”, function () {
        $cordovaOauth.linkedin(linkedinClientKey, linkedinSecret, [“r_basicprofile”, “r_emailaddress”], “<>”, {redirect_uri: “http://<>/callback”}).then(function (result) {
        $http.get(“https://api.linkedin.com/v1/people/~:(email-address,first-name,last-name)?format=json&oauth2_access_token=” + result.access_token).then(function (result) {
        }, function(error){});

        • Sharanagouda K

          Still you are using angular 1st version

  • Sharanagouda K

    Do you know how to implement like this for LinkedIn using ionic 2 framework