Read session or cookie on CallBack - asp.net-mvc

We have ASP.NET MVC 3 application which is integrated with Google Checkout API. Is there a way to access Session or Cookie of the Site on Google Checkout CallBack?
Suppose, I have logged into my site with UserID: ramiz and Password: r#miz. After I provided my credentials on Login it collects more details about me and put them in session (like, First and Last Name). Once I get in, I see a list of (used) iPhone. There, I see a cheap deal offering iPhone 3G only $150. There is a button of "Buy Now" in front of that deal. I click on this it ask me some more data and finally take me to the Google Checkout to do the transaction and place the order. I did and it shows me a "Thanks" message which means the transaction is completed successfully.
When we checkout Google calls our defined CallBack URL where we can collect the Nofitication XML which has Order Details. We are getting that Notification XML and happy to see all details is in there which we required. Here, we need to access the user Session or Cookie to get his First/Last Name and UserID. We have tried to access the Session/Cookie but it seems fail.
How do we have access Session or Cookie here? Or is there any good way of doing this?
Thanks.

Cookies (including session cookies) can only be accessed if the client (browser) actually goes back to your web site (if they do).
You can look into storing the data in:
merchant-private-data (order level)
merchant-private-item-data (item level)
instead of cookies. These will be echoed back to your handler in new-order-notification.

Related

Rails app Query params and Cookie based login

I am trying to find a way to distribute a Ruby on Rails app selectively by sending them an email with the link that logs them in. This should be the only way to get to the page hosted at a unique subdomain. Additionally, we don't plan on having a login wall so the access would need to be guarded by using Cookies or the Query URL params.
A couple of questions regarding this:
Is it possible to leverage cookies exclusively to achieve this? I.e Any way to embed cookies within the URL sent in the email itself?
An approach I felt that might work is to embed the user ID (encrypted) in the URL in the email. In order for the users to not need to bookmark this URL or go back to the email to access this link, I was planning to store their session ID via a browser cookie. Any issues with this approach?
How to avoid wandering users(i.e users who haven't received this email) to access this page (i.e a nice way to raise a 404 error)?
Any other cleaner ways to accomplish this task?
Is it possible to leverage cookies exclusively to achieve this? I.e
Any way to embed cookies within the URL sent in the email itself?
No. You cannot "embed cookes in a URL". Cookies are set via the SET-COOKIE header in a response or through JavaScript.
An approach I felt that might work is to embed the user ID (encrypted)
in the URL in the email. In order for the users to not need to
bookmark this URL or go back to the email to access this link, I was
planning to store their session ID via a browser cookie. Any issues
with this approach?
Yes. You should generate a random token thats not tied the users id.
How to avoid wandering users(i.e users who haven't received this
email) to access this page (i.e a nice way to raise a 404 error)?
Create time limited access tokens that can only be used once by the user. There really is no other way for you to actually know that the person requesting the URL is the recipient of the email.
What you are describing can be accomplished with Devise Invitable which is a pretty good community tested point of reference if you want to reinvent the wheel.
When you invite a user Invitable creates invitation tokens which are stored in the users table. This is just a random string. There are also timestamp columns that expire invitations automatically.
The token is included in the URL in the invitation email as a query parameters.
When the user clicks the link the controller looks up the user based on the token and nulls users.invitation_token so that it cannot be used again. This stores the user id in the session and takes the user to a screen where they edit and finalize their account by setting a password.

How do I add a token to my request in Rails 4?

I have an upload application that will be accessible by multiple other applications. I want user security from those applications to be federated to this upload hub. I'm doing it with HTTP tokens that are shared between the applications.
I have read 5 different articles on how to secure an API in Rails. I have everything set up properly in the upload hub app. I have keys set up in my User table, and I have shared this key with the user table in the other apps. I have the code in place to check for this key, and to locate the appropriate subscription. Upon failure, the user is redirected to the login page of the source application.
There's just one thing. I can't find anywhere how to create the actual request! I want the users in the other applications to click an "upload" link that will take them to this application. No problem creating the link, of course. The problem is, how do I add the token to the request?
See, I'm not making programmatic requests to an API... The user is actually going from one app to another. I want the upload hub app to check the request and say "Oh, there's this big long key. Let me see if I can find a user associated with that. I'm obviously not going to put it in a query string.
The only thing I've come up with on my own is to have a bit of jQuery code that constructs a form with a hidden item containing the key in it, which it would get from a hidden field on the current page, then do a POST against the upload hub app. That's not really a token, but it's doable. Surely there's a better way?
UPDATE
I went the jQuery "postGo" route where I construct a form with a hidden field and send it as a parameter to the other app. I had forgotten about protect_from_forgery though. However, even after turning protect_from_forgery off, Rails somehow still strips all parameters except for controller and action from outside requests. Undocumented feature? Or maybe I missed the documentation.
Really, I just want SSO on a couple of apps. It looks like I'm going to have to create an Oath provider. Sure are a lot of hoops to jump through to federate a simple session on some apps that I own.
Here's a possible way of doing this.
In the upload controller method of the app, instead of redirecting the user directly, make a request to the upload hub app.
In the upload hub app, add a controller method and generate a token, store it and a user's credential in redis, or other storage of your choice, then response the app with the token.
Your app's upload controller method receive the response from upload hub, then give 302 response back to the client, with the token included in the redirect url.
The client redirects to the upload hub
The upload hub router accepts this format, the token can be in a query string.
Check in redis and find it by the token and match the user's credential

How do I get the ID of the currently authenticated Twitter user in a web application without using OAuth?

*Apologies in advance for the long background but I think it is necessary and helpful to other devs once this is answered.
Background
I am building a very social web-application in which there are several events that trigger social actions such as updating the user's Twitter status.
Currently, I use a library called "TweetMoaSharp" (.NET) to handle the Oauth workflows and events that trigger a status update or follow action work brilliantly as long as the user is briefly redirected to the Twitter authentication page.
To clarify, the user is not asked to re-authorize my app each time, but there is an unsightly flicker that lasts for 1-2 seconds while the user is directed to Twitter and then back to my app. This will annoy the end user as there are frequent Twitter interactions.
So--to relieve the situation, I use TweetMoaSharp to obtain an OAuth Access Token via the server and then store that token along with the user id returned from Twitter in my database. I then set a cookie on the client that contains the user's Twitter Id so that for future requests I can simply pass that ID to the server, grab the OAuth token form the database and do my business. No redirect required!
Problem Solved, Right?
Well, no. Stupidly, I overlooked the fact that this can cause a collision with multiple Twitter Accounts being used on the same page and ended up tweeting test-tweets to a second twitter account I own because I had changed Twitter sessions. This could happen to any user(s) who access multiple Twitter accounts from the same browser; a husband and wife for example.
Back to the Drawing Board
I thought to myself, "The Facebook JavaScript API" makes it super easy to get the id of the currently logged in user without going through a bunch of server-side token steps so I am sure Twitter offers the same approach." Ha! I haven't found one yet.
Bottom Line / Question
How do I get the ID of the currently authenticated Twitter user without redirecting them to Twitter (even for just a second)? If I can do this, then I can compare the returned ID to the one in my cookie and know if it is valid for my application's current session or if I need to have that (new) user authenticate as well so that I avoid "Tweeting" under the wrong account.
Thanks in advance.
Use your app tokens to do a verify credentials call
https://api.twitter.com/1.1/account/verify_credentials.json
The returned info is the logged in user.
Unfortunately limited to 15 calls per 15 minute window!

Twitterizer: what is the workflow in order to publish messages on user's profile?

as I started to work with Twitterizer in order to publish on someone's wall I am in confusing time.
There is a page, my case, DefaultTwitter.aspx where is link to authenticate on twitter with token provided. Goes on Twitter and comes back to CallbackTwitter.aspx with outh_token and secret. And so the user is identified. On twitterizer example says:
Step 5 - Store the results
You should now store the access token and the user details. Keep in mind that the
only way an access token will become invalid is if the user revokes access by logging
into Twitter. Otherwise, those values will grant you access to that user's data
forever.
My questions are: - should I store any data in SQL datatable and what exactly(however I hope that is not the case to do so)
somebody said that I should save in a cookie(I thought in session); however then if another user comes then how should I create a button to logout or something like that?
-how will user revoke application access if he would like so?
A live example will be much appreciated as I could not found any on internet how exactly twitter api works.
When your application finishes getting authorization to access the user's data, the result is the access token (represented by 2 values, a key and a secret). Those values are, in effect, the username/password you can use in requests to the API on behalf of that user.* Save those values in your SQL database. You'll also be given the user id and screen name. It's probably a good idea to keep those handy, too.
The user can revoke access to an application by going to http://twitter.com/settings/applications, finding the application and clicking the revoke access button next to it. Your application cannot revoke access for the user.
You asked for an example, but you're citing the example application. Just look at the source code in that sample.
* - That's a simplification for explanation sake. Please don't crucify me, OAuth experts.

"Remember Me" Login for website - Problem with different browsers/computers

I'm trying to implement a "Remember Me" login functionality for an ASP.NET MVC site I'm building. I'm trying to use this approach http://jaspan.com/improved_persistent_login_cookie_best_practice (see 'Miller's Design' near top) and have it working to a degree.
Thus the work-flow is:
User logs in and is issued a cryptographically secure random string + their database ID as a persistent cookie (lasting about 30 days). Secure string is stored in the database next to their user account record.
User later comes back to site where browser presents the login cookie, the ID and secure key is looked up in the database and if match is found, the user is automatically authenticated.
Once authenticated a new secure key is generated, stored in the database and new cookie issued.
I have this working fine, however, it doesn't work very well if the user logs in from multiple browsers or computers. Obviously different browsers will end up with a different secure key stored as a cookie, thus the work-flow becomes:
User logs in from browser A, is issued a secure key as cookie, key is stored in database.
User logs in from browser B, is issued a different secure key as cookie. Key is also stored in database, but overwrites the key generated from browser A.
User visits site from browser A again, browser presents cookie issued from step 1. but it no longer matches because secure key was replaced in step 2. so user has to log in again. Another new key is generated and overwrites the key issued to browser B.
Users visits from browser B again, key doesn't match, has to log in again etc. etc.
How do I solve this? Do I need to store and maintain multiple keys in the database? Am I even going about this the right way? I've noticed StackOverflow seems to manage this and remembers me from different browsers and computers.
From reading the article you linked, it seems to me like Miller's design is to store the random string and the username as a pair in a different table than the user-table. By using the random string as the index, you can have multiple simultaneous logins from the same user-name while still being reasonably well-protected from session hijacking.
Your description indicate that you store the random string inside the user-table, which would only allow one login at the time.
You need a third item in your cookie, a 'series' token. This will represent a login event. Everytime the user logs into your system, it creates a new series, that doesn't change until they logout, or login again. You still have your token, ie Secured Key, that is updating on every request.
Here's some links to help with this implementation:
Database problems when allowing multiple browser persistent log ins
The definitive guide to form-based website authentication

Resources