JSONP and sharing cookies from one server to another? - asp.net

I'm working on an intranet system (.NET 3.5); the main pages are served up from a standard ASP.NET server. I would like to use Ajax on those pages to contact a WCF service running on a different machine, to retrieve data, do CRUD operations - the usual Ajax stuff.
The problem I'm trying to resolve is: can I take cookies which were set by the ASP.NET server, and include them on requests to the WCF service? If so, how?
My understanding is that JSONP bypasses XSS restrictions by "wrapping" the Ajax request within a standard <script src="MyAjaxCall?SomeData=SomeValue"> tag. With that in mind, it would seem I'm at the mercy of the browser as to which cookies (if any) will be included in MyAjaxCall. Since the cookies originate from the ASP.NET server, the browser likely won't include them in the call to WCF.
Since this is an intranet application, I cannot necessarily rely on domain wildcarding (*.mydomain.com) to make sure the cookies are shared across multiple machines - the client may well be accessing machines by their simple network name or even IP address directly.
edit: accepting Julian's answer, since using JS to manually grab a cookie's payload and jam it onto the URL seems like the only way to work-around the restriction (tho it feels somewhat inelegant :)

You're perfectly right in assuming you'll have problems with cookies.
The only workaround is to actually pass the values of interest into the query string of the JSONP request. Which means you'll have to inspect cookies client-side, extract the data you need from them and then append it to the url "by hand".

Related

HTTP out-of-order responses and Async processing in Servlet 3.0

I have multiple AJAX requests going out of my browser.
My UI is comprised of multiple views and the AJAX requests are trying to populate those views simultaneously. In some cases I require more than 10 simultaneous requests to be sent from client and processed concurrently at the server.
But due to browser limitations on max concurrent requests to a single domain and because of HTTP's "A server MUST send its responses to requests in the same order that the requests were received" constraint, I am not deriving as much concurrency in request processing as I would want.
From my application's standpoint, I dont need responses to come in the order in which I sent the request. I am ok if view8 gets populated before view1, for example.
Async processing using Servlet 3.0 constructs seems to address only one-side of the problem (the Server-side) and hence cannot be fully exploited for maximizing application concurrency.
My question is:
Am I missing out on some proper constructs ? ('proper' in contrast to workarounds like "host your images from a different sub domain") that can yield me more concurrency ?
This seems like something many web UIs would need ! If not, then I am designing my UI the wrong way. In either case, I would appreciate your inputs.
Edit1: To my advantage, I dont have to support a huge number of concurrent clients. The maximum number of concurrent clients accessing the app would be < 100. Given that fact, basically am trying to enhance the experience of these clients when I have the processing power available aplenty on my server-side.
Edit2: Our application/API is not for 'public' consumption. For ex: It is like my company's webmail app. It is hosted on the internet but it is not meant for everyone's consumption. Only meant for consumption by the relevant few.
The reason why am giving that info, is to differentiate my app from SO/Twitter, which seem to differentiate their (REST) API users from their normal website users. In our case, we think we should not differentiate that way and want to provide single-set of REST endpoints for both.
The reason behind the limitation in the spec (RFC2616) seems to be : "These guidelines are intended to improve HTTP response and avoid congestion.". However, intranet web apps have more luxuries and should not have to be so constrained !?
The server is exposing REST API and hence the UI makes specific GETs
for various resource catogories (ex: blogs, videos, news, articles).
Since each resource catogory has its exclusive view it all fits in
nicely. It feels wrong to collate requests to get blogs and videos
together in one request. Isnt it ?
Well, IMHO being pragmatic is more important. Sure, it makes sense for a service to expose RESTful API but it's not always necessary to expose the entire API to the browser. Your API can be separate from your server side web app. You can always make those multiple API requests on the server side, collate the results and send them back to the client. For e.g. look at the SO home page. The StackOverflow API does expose a RESTful API but when loading the home page the browser doesn't send across multiple requests just to populate the tags, thread listing etc.
Thanks Sanjay for the suggestion. But we wanted to have a single-API
for both REST clients and Browser clients. Interestingly, the root URI
"stackoverflow.com" is not mentioned in SO's REST API, but the browser
client uses it. I suppose if they had exposed the root URI, their
response would be difficult to process (as it would be a mixture of
data). Their REST API is granular (as is in my application), but their
javascript code uses some other doors(APIs) to decrease no. of
round-trips to the server! Somehow that doesnt feel right (Am a novice
in this field though). Feel free to correct me
SO doesn't use any "other doors". It's just that they simply don't send across 10 concurrent requests for populating something on the page. They make XHR request when you vote, mark thread as favorite, comment etc. For loading the page itself, there are no multiple requests. If you want to directly hit your RESTful API from the browser, you'll have to honor the limitations. Either that or go the desktop way which allows you virtually unlimited connections to your server but I guess you don't want to go that route...

Strategy for developing a multi function asp.net web application

I'm about to start a new project and want some advice on how to implement.
I need a web application which contains a booking module for reserving timeslots, and a time management module which will enable employees to clock in / clock out.
If I am writing an update to the time managment module, I don't want to disrupt the booking engine availability by releasing a new solution containing both modules.
to make things more difficult, there is some shared functionality like common users, roles and security.
Here's a suggestion I've gotten, which sounds a bit cruddy, but may be functional.
Write a 'container' web application which consists of basically a frame, and authentication / security features. This then has links which, will load the 2 independantly built and released web applications into the frame.
I can see that say, if I wanted to update the time management module, I would only need to build and release this separately, and the rest of the solution would be 'untouched'
Any better alternatives?
Unless I am missing something, if you run ASPX.net (v2, 3, whatever) you can replace the ASPX files (including any CLASS Files) on the fly and the WEB SERVER will automagically "do the right thing."
So if you wrap your "modules" in classes, you can replace those files on a whim without harming the functionality of other classes (not modified.)
As I re-read this am I getting convinced that I am misunderstanding your goal...
Sounds like you what you want is to have some thing along the lines of the Composite Application Block but for a web application (the CAB is for a smart client application).
One of the main things you would want to do is reduce and abstract the coupling between the modules as much as possible.
Keeping the session in the database would go a long way help your ability to dynamically load modules into the application.
This would allow you to have the time management in one server and the booking engine in another. When you update the functionality of one you simply update one server while the other keeps on serving the user.
Add two class library to your web application. one for "booking module" and one for "time management" module.
After compiling you will have one DLL for each module and put them in bin folder of web app (Visual Studio will do) then you can replace them separately when you need.
Maybe you know this already :
Sessions are the heart of problems in web if misunderstood.
Http is a connection-less protocol which means both sides of connection don't care about the flow of the communication. Simply a request has a single response. Without tracking a client how web applications can work ? assume we login to Yahoo mail. Single request (filled login page) is sent to server and a single response (inbox page) returns, then what if we want to see "Draft" folder ?
To inspire state to HTTP a simple solution added which we know as "cookies".
cookies are simple texts send with each request to a specified server. So on login page Yahoo server sends the response with some other text (cookie) which forces client (browser) to remember it and sent with every new request. This way Yahoo server (web application) can keep track of sequence of requests. This is why we should not simply close the browser window when we are done with yahoo and should logout. With logout yahoo server will forget about that cookie and any subsequent requests with that cookie are not accepted. So because Yahoo can't find out we closed the browser "connectionless" is a good name.
How asp.net handle this ?
simply asp.net uses a "session cookie" for any new request (requests without cookie) and let's you put your variables in "Session" object on server side. As long as we are at the same application we can use same session variables. What asp.net is doing behind is creating a table for "session Id" cookies and you "session variables". This is transparent to asp.net programmer. We just simply put a value in a session variable like this : session("Age") = 19; and read it when we need. ASP.NET take care of the rest with session cookies this way: you create a session variable (here "Age") so asp.net should track of this request; whatever is the response, asp.net adds a "session cookie" to it. "Session cookie" is a unique text which should be send by that client on consequent request till it expires (usually 20 minutes in asp.net). Use Firefox with "web developer" add-on to see and manipulate cookies.
Related concepts: session cookies vs permanent cookies, cookie properties (domain, expiration date, ...)
how server deals with cookies (keeping in memory, storing in database, ...)

Stop Direct Page Calls to Ajax Pages

Is there a "clever" way of stopping direct page calls in ASP.NET? (Page functionality, not the page itself)
By clever, I mean not having to add in hashes between pages to stop AJAX pages being called directly. In a nutshell, this is stopping users from accessing the Ajax pages without it coming from one of your websites pages in a legitimate way. I understand that nothing is impossible to break, I am simply interested in seeing what other interesting methods there are.
If not, is there any way that one could do it without using sessions/cookies?
Have a look at this question: Differentiating Between an AJAX Call / Browser Request
The best answer from the above question is to check for a requested-by or custom header.
Ultimately, your web server is receiving requests (including headers) of what the client sends you - all data that can be spoofed. If a user is determined, then any request can look like an AJAX request.
I can't think of an elegant method to prevent this (there are inelegant and probably non-perfect methods whereby you provide a hash of some sort of request counter between ajax and non-ajax requests).
Can I ask why your application is so sensitive to "ajax" pages being called directly? Could you design around this?
You can check the Request headers to see if the call is initiated by AJAX Usually, you should find that x-requested-with has the value XMLHttpRequest. Or in the case of ASP.NET AJAX, check to see if ScriptMAnager.IsInAsyncPostBack == true. However, I'm not sure about preventing the request in the first place.
Have you looked into header authentication? If you only want your app to be able to make ajax calls to certain pages, you can require authentication for those pages...not sure if that helps you or not?
Basic Access Authentication
or the more secure
Digest Access Authentication
Another option would be to append some sort of identifier to your URL query string in your application before requesting the page, and have some sort of authentication method on the server side.
I don't think there is a way to do it without using a session. Even if you use an Http header, it is trivial for someone to create a request with the exact same headers.
Using session with ASP.NET Ajax requests is easy. You may run into some problems, like session expiration, but you should be able to find a solution.
With sessions you will be able to guarantee that only logged-in users can access the Ajax services. When servicing an Ajax request simply test that there is a valid session associated with it. Of course a logged-in user will be able to access the service directly. There is nothing you can do to avoid this.
If you are concerned that a logged-in user may try to contact the service directly in order to steal data, you can add a time limit to the service. For example do not allow the users to access the service more often than one minute at a time (or whatever rate else is needed for the application to work properly).
See what Google and Amazon are doing for their web services. They allow you to contact them directly (even providing APIs to do this), but they impose limits on how many requests you can make.
I do this in PHP by declaring a variable in a file that's included everywhere, and then check if that variable is set in the ajax call file.
This way, you can't directly call the file ever because that variable will never have been defined.
This is the "non-trivial" way, hence it's not too elegant.
The only real idea I can think of is to keep track of every link. (as in everything does a postback and then a response.redirect). In this way you could keep a static List<> or something of IP addresses(and possible browser ID and such) that say which pages are allowed to be accessed at the moment from that visitor.. along with a time out for them and such to keep them from going straight to a page 3 days from now.
I recommend rethinking your design to be sure that this is really needed though. And also note IPs and such can be spoofed.
Also if you follow this route be sure to read up about when static variables get disposed and such. You wouldn't want one of those annoying "your session has expired" messages when they have been using the site for 10 minutes.

Who is calling my WebService?

I have a web service that is on an internal server. It can be called from any website on our network.
More and more developers are starting to use it. Current probably 20+ pages use this service, and the number is growing fast. I can see a year from now, someone asking what pages are using this service and what methods.
I would like to log the url of the pages that use my web service as the request come in.
It would also be nice to know the method they are calling.I need to do something in such a way, that it does not affect the client web sites.My first thought was that I could write some code in the global.asax.
I have added some code to the Application_BeginRequest to log the request object details, but there does not appear to be anything about the requesting url.
What am I missing? Should I be looking at a different object?
Thanks.
Without disrupting existing users this is going to be difficult. The httpContect.Current.RequestUrl will just return the URL used to call your web service, not which web page called it.
The closest you can do without disrupting existing apps and forcing developers to change them is to grab the HttpContext.Current.Request.UserHostAddress, so you can at least get the IP of the machine calling your service.
Beyond this, what you might want to consider is adding a parameter to your functions for "CallingApp" and then log that in your code. That's pretty much what we did once re realized that we needed to know which apps are calling our service. We actually have an application monitoring service that uses a GUID for every new app we develop, and we pass that GUID to any web service. It[s extra work but to us it was critical because it allows us to know which apps will be affected when we need to perform updates or take the app server down for maintenance.
Edit - added
As a side note, at the point we realized we needed to track this, we had already been using web services for about a year. When faced with the same problem, we created a new set of web services, and included the extra field for the calling app in all of the new services, and then slowly went back and changed the older programs to point to the new services.
IN retrospect, we wish we had known we would need to do this up front because it created a lot of extra work. I'm guessing you'll be facing something similar if you really want to know exactly who is calling your services.
The only thing you can probably retrieve from the consumer is the IP address without changing your interface.
If you can change this you could do this e.g. by adding authentication and logging who is calling what, or by having some simple "token" principle.
However both methods require you to change the interface and therefore break backwards compatibility - which you should never do.
By always ensuring both back and forward compatibility you should not need to know exactly who is calling your service, but only that it is actually used.
#David Stratton
Thanks for your help. I think your suggestions were great. I accually did something very different, after your answer gave me some new ideas.
I should have mentioned that I was generating the web proxy that most of my users were using to make calls against my web service. My client in general do NOT use the proxy that Visual Studio creates.
Here is what did:
I generated my web proxy client again, and added calls to log the httpcontext of the client before every call. Because the proxy is running on the client, he had access to everything I needed. That allowed me to record everything about the client and the specific call they were making. I realize this would not work for most cases. But all of my clients are internal web sites.
It also had the advantage in that the clients did not have to modify their code at all. I just gave them all a new DLL. Problem solved. I get all the tracking data I want, and they did not have to modify their code.
I was stuck trying to solve the problem from the web service's point of view.
I realize that there is still a whole in this implementation, because someone does not have to use my client proxy to call my service. I guess I could force that at some point in the future. For now, they could let Visual Studio genereate a web proxy for my service. However, if they do that I guess I don't care. That is not the recommened way to call my service. I think the only one doing that is an ASP.NET 1.1 web site. When they upgrade, they will probably switch to my generated proxy.
Without implementing some sort of authentication, there isn't a guraenteeted way of knowing exactly who is calling your service - web metrics are the only way you can gauge what volume of traffic is hitting your service.
I'm sure you already know this but the whole point of a web service isn't to know or care who is calling it.
I have successfully used ...
Dim strReferrer As String = HttpContext.Current.Request.UrlReferrer.AbsoluteUri
to get the calling page that called my WEB API 2 Web Service.

Does the word "Webservice" imply a specific format?

When I talk to an developer from the Microsoft ASP.NET world and he uses the word "Webservice", does that word in every case imply a specific data format (XML? SOAP?)?
Or is it just anything you can call via http(s)?
In my view, it can be anything that's over http/https, and intended for calling by an application rather than a user's browser.
In particular, REST and SOAP are quite different about how they pass arguments in and get results back
The term Webservice itself is language-agnostic.
This is a decent overview.
If an Asp.Net developer says WebService, you can pretty much bet that they are talking about XML/SOAP.
However this is not universally true. I think it's just fine to call anything a WebService if 1) the data source is available via the web or 2) it is a web address that can provide back information given a set of inputs.
For example, StackOverflow.com allows for screen scraping of the User pages in order for 3rd party applications to be built. It's not specifically XML/SOAP but I would consider it a Web Service (format #1)
In my experience this completly depends upon who you are talking to. For some ASP.Net developers this is only SOAP for others it includes other things like REST. If you are planning on using the term in a specification it would be a good idea to be a bit more specific.
I can only agree with Paul, anything queried over the web, using the http(s) protocol and not browser oriented. But any web service should also have the functionality of being discovered (WDSL and so on).
Personally I mean any HTTPHandler!
That means under ASP.NET, a page is a webservice that returns HTML.
WCF extends that concept, because by default, WCF service requests in ASP.NET are processed by Modules not Handlers.
So really any web request is a service.
Typically though ASP.NET developers will be refering to SOAP unless they prefix i.e. WCF Webservices,

Resources