I've successfully completed account linking on api.ai, and now I'm trying to execute a webhook. The problem here is that I need the token that was generated during the linking process to go into the authentication field. Otherwise I will always get a "403" error back. How can you change the auth token in the webhook header field dynamically for each user that issues a Google Home voice command?
For all I know that's not currently possible. I pretty much had the same issue, and I resorted to connecting to an intermediate server that handles the webhook, extracts the access token (available via the actions-on-google node.js API as getUser().access_token), and then forwards the request in the right format to the original host.
Related
What are the keys of username/ password in webhook connect header response? I tried with username/ password/ X-DocuSign-Password/ X-DocuSign-UserName but is not
webhook connect response is sent from DocuSign to your web server following events that occured and based on your configuraiton.
No password is ever going to be sent from DocuSign.
You may be referring to the header that was used in the past to make API calls before OAuth 2.0 was implemented. That is an insecure way to authenticate and therefor no longer allowed for new applications that are under development.
I am building a webapp using nodeJS as the server-side framework and reactJS as the client-side framework.
My issue is the following:
I'm trying to create an account registration mechanism, which is working fine. I do receive an email with a specifc token in order to active an account. The issue that I am facing is that the API which will consume is on the nodeJS side, and I can't figure out how I can force a page to being rendered from the client side as a result of the success, since the API is located on the server on a different port?
Am I approaching this wrongly, and as such I am facing this specific issue?
It's simple you just handle it on both sides,
meaning that you send a verification link in the email so it redirects the user to your application and then on the client app extract the toke (the verification code needed on the verification link from the email) and send it to the server(API) depending on the request status you will take an action, if its verified successfully you will redirect the user to home (or to log in again, or it does not show an error message!
I've been studying the OAuth 2.0 authorization code flow and am trying to write a React application with an Express backend that displays what a user would see on their own Instagram profile. I'm trying to do so with minimal external libraries (i.e. not using passport-js) and without bringing a database into the mix.
This is my flow as of now:
Resource owner clicks an <a> tag on the React application (port 3000) which redirects them to the /auth/instagram endpoint of my Express server (port 8000)
res.redirect(AUTHORIZATON_URL) sends them to Instagram's authorization server
Resource owner consents and the authorization code is sent back to the predefined redirect-url /auth/instagram/callback with the authorization code set as a query parameter
I strip the authorization code off the url and make a POST request to https://api.instagram.com/oauth/access_token to grab the access token
Now that I have the access token, how do I reach out to the React frontend to let them know that everything worked and that the user was successfully authenticated?
From what I've read, this is where the idea of sessions and cookies come into play, but I haven't had luck finding documentation on how to achieve what I want without bringing in third party libraries.
In the end, I would like for my app to support multiple users viewing their profiles simultaneously. Since I imagine passing the access token to the frontend defeats the purpose of securely retrieving it on the backend, I'm guessing I will somehow need to pass a session id between the frontend and backend that is somehow linked to an access token.
Any ideas as to what my next steps should be are greatly appreciated, as well as any articles or documentation you see fit. Thanks!
Since you're doing the OAuth authentication on the server side, you have to pass some parameter to the redirect_uri, identifying the user session (see: Adding a query parameter to the Instagram auth redirect_uri doesn't work? );
When the redirect uri is called from the authority server, you will know which user was authorized. To notify the browser there are two options: 1) Notify the client using web sockets; 2) Pull the state from the client using a timer triggered function;
I'm getting started with Google Cloud Platform.
I'm developing an Android App that will collect information and store it in a Firebase App. The idea is that a Google Assistant function can query this information and read it back- eg
OK Google, Talk To Simons App, Tell me the last time XYZ was done
The problem I've got however, is to get this being multi user.
I've got the Android App collecting data and putting it into the cloud. I'm using the FirebaseUser and using getUid() in the Android app to get a unique id which is a 28 character string like uVHkia8RRgWD8GGPVvW4AUDUK2.
I've setup Actions on Google, got it hooked into API.AI with Web Fulfilment and got Node.js working in firebase functions.
Unfortunately, the UserID I get back looks more like:HTge48H0CF2FC5jJQCigFBc-UCQ
The problem is that this UserID is not the same as the UserUID I got from Filebase User.
Im using
let ApiAiApp = require('actions-on-google').ApiAiApp;
const app = new ApiAiApp({request: request, response: response});
and
const userId = app.getUser().userId;
What am I missing? I see references to OAuth2, Account Linking etc. I'm not entirely sure what to do at this point. All I need to do at the moment, is get the User UID like I get from FirebaseUser.getUID() in order to look the data up in the Firebase Database.
I think the rest should be straight forward.
There's loads of documentation on linking to Firebase from the Assistant, but very little on actually authenticating. So far I've not setup an flows, like Authorization Code Flows, Implicit Flows, or set a username/password against API.AI and the Fulfilment option. Quite frankly Im not sure what needs to go where at this point.
The user provided by app.getUser().userId is designed as a persistent anonymous identifier. It is roughly the equivalent of a cookie that one sets in a web server - you can use it to determine if you've seen this user before, and what else they've done in your Action, but it does not inheriently relate to any outside account.
Unfortunately, the best solution you have at this point is to use Account Linking which requires you to setup an OAuth2 server. As part of this setup, you will need to create three components:
A login web page for your service. You'll provide the URL for this page to Google as part of Account Linking. When the user accesses your Action, and your action indicates they need to log in, they'll be redirected to this URL on their mobile device. On this page the user will log in - once logged in, you now know their Firebase ID and will create an auth code for this user. You'll then redirect them back to a different URL and pass this auth code (along with some other info) as a parameter.
A token exchange endpoint. Google will call this URL with the auth code above. You'll verify this code, determine who the user is, and send back a unique access token. (You'll also send back a refresh token that Google will use in the same way to get an updated access token.)
An auth token handler in your webhook. When API.AI calls your webhook, it will include the access token as one of the fields in the request. You can use this access token to get the Firebase ID for the user.
One thing to note for the auth code, the access token, and the refresh token is that you'll need to have some way to map from these codes/tokens to the Firebase ID. There are two good ways to do this:
The code/token can be a JSON Web Token (JWT). This takes the Firebase ID, and other information you wish to retain about the user, and puts it in a standard format. It then creates a cryptographic signature, to make sure it hasn't been tampered with, and encodes it in a standard format. When you need to determine the ID from the JWT, you can decode it, verify the signature is valid, and read the value.
Generate a random string and store this in your database against the Firebase ID. When you get the token, you can then look up in your database the ID that this string was assigned to.
There are many additional details about an OAuth implementation and about each of these steps. See https://developers.google.com/actions/identity/oauth2-code-flow for more details.
I am making a Twilio app. Twilio can send a request to the server after a call is over, but it isn't able to be associated with the logged in user of my website because Twilio is making an independent request. If I were to tell Twilio to post something at
example.com/response.html?token=ba38pgab38g4agdusoehle8qihxs&data=somedata
and then use this token as a way of verifying that this Twilio request is associated with a user, is that secure?
I have seen this technique used before on password reset forms. An email will contain a link, and the user's identity is confirmed only using the token.
Is doing this in my Twilio app secure? Are there any gotchas to note?
It's as secure as any other request to your server from a remote HTTP client (like a browser). If you want to make sure that no one between Twilio's servers and yours can read the request, you should use HTTPS/SSL.
For this use case, it's probably better to associate the CallSid value that's sent with every request to your server with the user in your system. When the StatusCallback for a completed call fires, look up the user associated with that call and act accordingly.
A few of the browser-based single sign on protocols like OpenID and SAML use a similar technique to track state when redirecting between the site you're trying to authenticate to and the site doing the authentication. I think the technique is good enough for what you want to achieve.
I'm not familiar with Twilio, but I'd be careful about using to identify a user though. Generating a unique code (aka nonce) for every request and having Twilio pass that nonce back in the response would be more secure, as it only identifies a particular request. It might be overkill though.