views:

3454

answers:

5

I am creating a Silverlight with WCF connectivity. I would like to create and maintain a session after user login in Silverlight and do the following.

  • On successful login, create a session object and store session id, user id, user name, session status
  • On further calls with WCF, the session information needs to be passed from Silverlight to WCF

One solution would be to create a session object and pass it as parameter to all methods.

Is there any other way of passing the info in all web service calls without passing a member variable?

Something similar to persistent Session object in ASP.NET.

A: 

Depending on the binding you are using WCF has builtin support for sessions/session management and it simply becomes a matter of configuration to get the behaviour you would like.

Have a look here for info on per-session services.

EDIT: I suppose I should also note that because you are using Silverlight, you have the ability to maintain a reference to the WCF service client (as opposed to traditional web-apps over HTTP where the reference will be lost on each request), which allows you to make use of the WCF support for sessions.

Simon Fox
The main problem with Silverlight is that it uses BasicHttpBinding which doesn't support WCF sessions...
Yuval Peled
A: 

Okay first of, silverlight is not asp.net, WCF by design is stateless, unless otherwise constructed to keep state.

Then if you want to keep state in silverlight 3, you could just create a static class with static properties and maintain these values across pages. But this is not an elegant solution. This is possible since SL is a clientside runtime, and your app exists within a xap assembly that is downloaded when you navigate to the url, so basically its like having a windows desktop app downloaded then running in a restricted security context. I dont want to get into the implications of this now, but its important you know this exists.

A better way to solve your problem is to use the IsolatedStorage like so

        IsolatedStorageSettings.ApplicationSettings.Remove("UserName");
        IsolatedStorageSettings.ApplicationSettings.Add("UserName", UserName);
        IsolatedStorageSettings.ApplicationSettings.Remove("Password");
        IsolatedStorageSettings.ApplicationSettings.Add("Password", UserPassword);

By doing this you could actually save data to the applicationsettings and re-use it on the next time the application is started. Remember everything stored in the IsolatedStorage is basically cleartext, accessible only from the same domain/site.

You must secure your WCF service using one of the many security schemes available otherwise, the information SL3 transfers to the WCF service will be in cleartext and readable by anyone who puts in a little effort, and anyone can call your wcf service bypassing your SL app completely, so remember to properly secure everything.

Neil
Isolated storage isn't encrypted so make you secure that data before you save it.
James Cadd
A: 

WCF authentication in silverlight is performed via SOAP headers which you don't have access to - you can't pass authentication information from Silverlight to WCF as requested. Assuming you're using ASP.NET Application Services to perform user authentication (it's the only tech I know of that'll work here) your basic strategy could be to call the ValidateUser method, which will perform a login and instruct the Silverlight control to include that user session info in the SOAP headers, then make calls to WCF services. You can either periodically refresh the session by logging the user in behind the scenes or wait for a WCF call to fail based on credentials and then validate the user again. I don't know if there's some keep alive aspect to calling WCF services that may make the need to re-authenticate less pressing.

You can store the user's login and password in isolated storage as suggested by another poster, but make sure you encrypt that data first, it's stored in plain text in an obscure location and is not safe.

James Cadd
A: 

The end goal is just to temporarily store the user's variable as long as their browser is open. Regardless of elegence, if it's not megabytes of data, I just temporarily store them in a variable or Resource in memory in the app or class so you don't have to worry about it showing up locally on their machine. It will be gone when the browser session is over.

App.Current.Resource.Add("MySessionItem", item)

For the WCF call, try to let ASP.net do the authenication for you with ASP.net Application Services (i.e My.User.Identity), don't authenticate in your WCF methods based on those passed parameters your storing in the temp variable and/or resource.

Paully
This assumes that you WANT to use ASP.Net. That is a foolish assumption. While the main client may be Silverlight, there may also be other kinds of clients that are not browsers. Especially for automation or data import/export.
Christopher
Dude what are smoking? FAIL. He's using WCF so it's not far to think he's using ASP.net. Anyway, my method doesn't require ASP.net, it's using internal resource variable in Silverlight to hold a global value.
Paully
+2  A: 

Why would you want to pass the session information each time?

If you're using ASP.NET to host your WCF service in ASP compatibility mode, you can set the instanciation mode to Session to then store all that in your WCF service instance variables. Or in your ASP session object.

I can't see what your point is in sending all this data for each request.

A good thing to do when using SL with ASP.NET is to login using the ASP.NET built-in authentication Like here and then you can just call the WCF service and check that HttpContext.Current.User.Identity.IsAuthenticated is true.

R4cOON
The thing with Silverlight is that it only supports BasicHttpBinding, which doesn't allow you to set the instantiation mode to Session.
Phil
You sure about that? I do get session GUIDs on the server side. I actually haven't tried the "create a new instance per session" behaviour because I do all the object locking "by hand".
R4cOON