Session.Item("Hello") vs Session("Hello") - asp.net

Are there any advantages of using one over the other besides readability?

Nope, they do the same thing. Session["item"] is the same as Session.Item["item"].

You will be accessing the same collection with either.
Its just a hang over from classic ASP, where the session object is implement as a COM object. COM could nominate one property as the default property (which typically would take an indexing parameter). In the case of Session the Item property is the default property.
In an effort to allow classic ASPers to port code to .NET the Session, Server, Request, Response and Application classes were crafted to be similar between classic and .NET ASP.

Personally, I think referencing a property explicitly (Session.Item("Hello")) is always more readable than relying on that property's being the default (Session("Item")), but the readability is at the expense of more typing. If typing is a problem for you, switch to Ruby-on-Rails.

Related

How increase the performance of asp.net application?

Hi
I want to increase the performance of asp.net application when multiple user access my application about 5000 users.
Can we do this
Your ASP.NET application performance depends on various things. You can improve your site's performance by doing various stuff. Your questions is very subjective and of course the answer would be some best practices about improving ASP.NET applications' performance.
I have gathered some tips from the net. Unfortunately, I cannot remember where. Search on any item and you will find many resources that can help you implement it:
Use Cache:
Page output caching.
Page fragment caching.
Data caching.
Avoid frequent trips to database.
Use DB-level paging. Don't retrieve unnecessary data that's not going to be shown in the current page.
Be careful with Session variables. Usually, you should avoid session variables because each ASP page runs in a different thread and session calls will be serialized one by one. So, this will slow down the application. Instead of session variables you can use the QueryString collection or hidden variables in the form which holds the values.
Select the Release mode before making the final Build for your application.
Set debug=false under compilation: <compilation default Language="c#" debug="false">
Avoid Inline JavaScript and CSS
Use Finally Method to kill resources. (But not in the case of using)
Avoid Exceptions: Use If condition (if it is check proper condition)
Check “Page.IsPostBack”. To avoid repetition code execution.
Use single css file instead of multiple css file.
Use Client-Side Validation. (but not all the time you have to validate even on the server side).
Turn off Tracing unless until required.
Turn off Session State, if not required.
Disable ViewState when not required.
Try to use StringBuilder instead of string.
It is nice to use Stringbuilder instead of String when string are Amended. Strings occupy different memory location in every time of amended where stringbuilder use single memory location.
Never use object value directly; first get object value in local variable and then use. It takes more time then variable reading.
Avoid using code like x = x +1; it is always better to use x+=1.
Data Access Techniques: DataReaders provide a fast and efficient method of data retrieval. DataReader is much faster than DataSets as far as performance is concerned. But that depends on you deciding to balance between features/performance.
Use Repeater control instead of DataGrid , DataList, Because It is efficient, customizable, and programmable.
Reduce cookie size.
Compress CSS, JavaScript and Images.
Use server side compression software such as Port80s
Make your page files as light as possible. That is try to avoid unnecessary markups, e.g. use div elements instead of tables.
Write static messages in div and make it visible when necessary. This is faster than letting server set Text property of your label or div.
Retrieve necessary data from database at once, if possible. Don't add up to database trip as far as possible. For this, combine the datafields from different tables and select them.
Remove blank spaces from your html it will increase your kb. You can use regular expression to remove white spaces. I will post the code for removing white spaces next posts.
For asp.net 2.0 and higher version use master pages. It will increase your performance.
Use ADO.NET asynchronous calls for ado.net methods. asp.net 2.0 or higher version is supporting your performance. If you are using same procedure or command multiple time then use ADO.NET Prepare command it will increase your performance.
Do IIS performance tuning as per your requirement.
Disable view state for your controls if possible. If you are using asp.net 2.0 or higher version then use asp.net control state instead of view state. Store view state in session or database by overriding the default methods for storing view state
Use Ajax for your application wisely. Lots of Ajax calls for a page will also decrease your performance.
Call web service from java script instead of server side. Use asynchronous calls to call a web method from web service.

Does ParseControl do any caching?

We use Page.ParseControl to interpret a string of XML into controls. Does it use some kind of caching mechanism? If not - is there a way to cache its result?
Page.LoadControl seems to support some sort of caching.
There does not seem to be any caching involved.
As a Control is a reference types, caching wouldn't be recommended in this case. (You want a new instance of the control each time you call the ParseControl function)
LoadControl doesn't perform caching per say, but the difference is rather that ParseControl will parse the input string every time to create the control dynamically, while LoadControl will re-use the parsed control template and class type when creating new instances, making it an order of magnitude faster.

How can I use jQuery Ajax and PageMethods with instance variables?

One reason we currently use UpdatePanels for doing our AJAX is because our BL and DA layers pass around the Page.User.Identity for authentication.
Is there a way to access this?
Yes, you can get the current user via HttpContext.Current.User. From the MSDN documentation for Page.User:
This property uses the HttpContext
object's User property to determine
where the request originates.
As for your broader question, "How can I use jQuery Ajax and PageMethods with instance variables?" The answer is "not directly."
No instance of your page is created when executing a page method. (Why do ASP.NET AJAX page methods have to be static? is a great conceptual overview of the differences between normal page operations and static page methods).
The only way to access instance variables in page methods is to first put the variables into Session during the initial page request - but this is a rather fragile strategy: you're better off figuring out another way to get the data or values in question.
I agree with Jeff Sternal's answer to this post. On my current project, we frequently use the session as a "scratch pad" to store data for later use by PageMethods and ASMX webservices.
However, if you don't like using session in that fashion, here is another approach that should be a viable alternative:
At page-creation time, you can put instance variable values into javascript vars or hidden fields. From there, they can easily be accessed by javascript/jquery and included as params on calls to webservices. You could then code your webservices (PageMethods, ASMX services or others) to take those values as parameters.

Problems with ASP.NET Session State / NInject / OnePerRequest behavior

This is quite a lengthy post, so bear with me. I'm not sure whether it is primarily about ASP.NET Session State behaviour, NInject, application design, or refactoring. Read on and then you can decide... :-)
Background
First, a bit of background. We are working on trying to refactor a large webshop into a more maintainable , structured design. The webshop is currently running on .NET 3.5, but the design is more of a hangover from the classic ASP days. Obviously we cannot tackle everything in one go, so many of the features / technologies / approaches have to be taken as a given. With that in mind...
The app maintains everything to do with the current session (user profile, cart, session choices, etc.) in a context object which is simply a large XML document that gets serialized to and deserialized from the Session as a string. The XML format is also important because the rendering is done via XSLT.
This has led to a number of problems :
It's a kind of God object with far
too many concerns.
It's loosely typed and relies too much on XML manipulation / XPath.
There is no standard way / pattern for retrieving the session xml document or for writing it back. We have a horrible mixture of methods that take the document in as a parameter, modify it and return it, methods that retrieve it themselves, modify it and save it back to session, etc, etc. This has lead to a lot of hard to trace bugs, over-use of serializing /deserializing from the Session, etc.
Our Solution
What we have done is try to introduce a strongly -typed wrapper around the xml document, which breaks it up into different concerns and to manage the lifecycle transparently to the rest of the app.
What we are aiming for is the following workflow:
Beginning of the request, we populate
the session document from the xml
string stored in the session.
The rest of the app interacts with it
only through the strongly typed
wrapper. The whole app uses the same
instance and does not have to worry
about when to retrieve or save the
state back to session.
At the end of the request, the underlying xml document is serialized back to the Session.
Since we are using NInject(v1) as the IOC of choice, we decided to use this to manage the lifecycle of our context object. The context object was wrapped with the OnePerRequest attribute and the dispose method was hooked up to a method that would save the xml document back to Session as a string.
It doesn't work...
We soon encountered a problem that the NInject OnePerRequest module didn't appear to have access to SessionState. The first thing we tried was a hack that we would keep the Session object in a variable to make sure we could still write to it. This appeared to work on a development machine but it became obvious it didn't when moving to out of process state.
It still doesn't work...
We tried inheriting from the OnePerRequest behaviour / module, and adding the IRequiresSessionState marker interface (OnePerRequestRequiresSessionState). However, this was not enough as the method which NInject uses to release references and clean up gets hooked up to the EndRequest method. Session is available in EndRequest but it has already been serialized to the out of process state server so changing something now is not reflected when the session string is retrieved at the beginning of the next request.
We then decided to change the even t to hook up to. We ditched EndRequest and hooked up our OnePerRequestRequiresSessionState "release all" method to the PostRequestHandlerExecute event, which is BEFORE the session data gets serialized out of process.
It works... then it doesn't...
This seemed to work. On a single server and on a web farm. Then we noticed weird behaviour. There seemed to be two different versions of the context and you would randomly switch between them. Add something to the cart, it's not there. Go to browse to another product and the previous product would show up in the cart.
After some tracing, we discovered the culprit: Response.Redirect. Sprinkled throughout the site in literally hundreds of places is Response.Redirect(url);. With this version of the redirect, the execution of the page is stopped immediately. This means that PostRequestHandlerExecute is not fired and the current version of the Context object is not thrown away by NInject... and everything falls apart. New versions are not created properly, etc. EndRequest is fired which is why the normal NInject OnePerRequest module works fine with it, just not our bastardized version that tries to use session state.
Of course, there is an override to Response.Redirect where you can pass a boolean value in to tell it whether to terminate the existing page or continue to execute - Response.Redirect(url,false). Continuing obviously fires our event and everything works but... it continues to execute the rest of the page! This means executing everything that comes after the call to Redirect and we have absolutely no idea what that means (since the existing site expects it to stop).
What next?
So, any suggestions on what to do? So far we've discussed :
Abstracting our redirect behaviour
and going through a central method
that controls the redirect (perhaps
hacking out a way to call the
PostRequestHandlerExecute even t or
maybe a custom Redirect event that
our NInject module can also
subscribe to and clean up).
Seeing if there is a way we can
force the Session object to save in
EndRequest if it hasn't been saved
previously in
PostRequestHandlerExecute, and do
the ninject clean up in EndRequest
Remove our dependency on Session
completely and use another storage
mechanism: DB, document DB,
distributed HashTable, etc. Any
advice? Suggestions we haven't
thought of? Things you've tried
that have / haven't worked?
I think you're on the right track. Here's some thoughts I had:
in addition to the strongly typed wrapper you have, I'd suggest a facade for accessing the context object that returns your wrapper, something like an IContextProvider. that way you can introduce it piece-meal, and then when it's fully integrated, you can refactor the provider without breaking the things that use it. I can't tell, but you might have already done this. it'll also be easier to change your persistence mechanism if you choose to. if you can do this, I would suggest once you get all the dependencies isolated from the context object, change it to not persist as XML. the SessionState will store a binary object much faster, and you can always serialize to XML if you need to do transforms.
I don't think that Ninject is the correct mechanism for what you're trying to do. it's difficult to signal end of the request in Ninject, since garbage collection can't be depended on. have you considered using an IHttpModule instead? you can use the AcquireRequestState and ReleaseRequestState or EndRequest to handle getting/setting the context in Session. only allow the app to get to the context object through the facade.
if you're on a webfarm, you're probably using a database for your Session storage anyway, so putting your context into a DB won't be much different.
Firstly, while it's good to demonstrate you've put in the work, (and I and others may not have replied if it wasn't clear how much you're interested in a resolution)... that's a massive wall of text! Here's a +1 on your way to investing in a bonus for a complete response that talks about the Ninject ASP.NET extensions and how they apply to each individual element of your issue. Having said that, hopefully someone will come along with a real resolution for you.
Even though it's [very] 2.0 specific, Nate's Cache and Collect Post is required reading. While it seems you're pretty au fait with the tradeoffs involved and have debugged deep in, the article is well worth a few reads.
I'd also consider moving to V2 of Ninject - a lot of this stuff has been revised significantly. It's not magically going to work, but represents a mature rewrite based on a lot of learning from V1. Have you read the (V1 or) V2 unit tests for Ninject? They'll show you the low level tools at your disposal in order to realise your goals.
Bottom line for me is that you need to work out a strategy for your state management independent of DI, and then by all means use the container/DI system as a part of the implementation.

What is the best way to manage Global variable in asp.net?

Currently i have a NotInheritable class in App_Code that hold some variables that need to be access thur-out the application but i don't think it's a good way to manage global variables.
Usually, this kind of thing calls for a Singleton. However, I'd recommend never coding a singleton yourself, and using a Dependency Injection/IoC framework to handle the life-cycle of services.
The other thing you have to remember with ASP.NET is that the ASP.NET process automatically recycles itself every now-and-then, so you'll need to persist changes to permenant storage (such as file-system or database)
You should use the Application Settings. Just go to the Application property window, choose the settings tab and add your variables. Than on the code just use the strong typed class. For instance, if I've created a Global variable named PortalName I just use: Settings.Default.PortalName
I believe the Application object is a built-in way to use global variables where you can store various values in the object as needed.
As an alternative to Application state, consider just making your variable static. It is basically going to amount to the same thing, with the added benefit of being strongly typed.
Personally, I'd go with what David suggested and use a singleton scoped service that is managed by an IoC container.

Resources