11

I have quite a slow Application_Start due to having a lot of IoC stuff happen at start up.

The problem I'm trying to solve is, how do I avoid passing that start up time to the end user?

Assumptions

My apps are hosted on AppHarbor so I have no access to IIS. However even if I did, my understudying is that it's best practice to let the app pool recycle, so there's no way to avoid having the Application_Start run regularly (I think it's every 20 minutes on AppHarbor).

My idea to solve it

Initially I thought I'd hit it every minute or something, but that seems too brute force and it may not even stop a user from experiencing the slow start up.

My current solution is to handle the Application_End event, and then immediately hit the App so that it starts up again, thus hopefully not impacting any users.

Is there a better way to solve this issue?

andy
  • 8,775
  • 13
  • 77
  • 122
  • 1
    Are you sure they recycle every 20 minutes? Out-of-the-box experience on IIS is that they shutdown the application pool when there's been no activity for 20 minutes. Of course, then the first hit will be slower, but it shouldn't be an issue unless you do crazy, crazy stuff in `Application_Start`. – MartinHN Jul 25 '12 at 07:29
  • Hey Martin, yeah it's every 20mins, according to AppHarbor. However you're right, it's a very low use site so it's probably not being hit enough. So potentially I could hit it every 15 mins so it wouldn't go to sleep...? – andy Jul 27 '12 at 02:28
  • I'd look into `Application_Start`. How long does it actually take? Can you optimize it, so that it is not a problem with a slight delay on the first hit? – MartinHN Jul 27 '12 at 08:56
  • hey martin, takes 5 to 10 seconds, and its all windsor IoC stuff. i kind of dont mind that as long as the user doesnt have to experience it. – andy Jul 28 '12 at 03:45
  • Well, if it's no more than 5-10 seconds I wouldn't bother. – MartinHN Jul 28 '12 at 05:09

2 Answers2

5

Unfortunately, a longer session timeout will not prevent an IIS app pool recycle when you're using InProcess session state.

Have you considered lazy loading (some of) your dependencies? SimpleInjector has documentation on how to do this, which should be adaptable to most other IoCs:

Simple Injector \ Documentation \ How To \ Register Factory Delegates \ Working With Lazy Factories

Steven
  • 166,672
  • 24
  • 332
  • 435
Facio Ratio
  • 3,373
  • 1
  • 16
  • 18
  • +1 interesting, I'll check out the lazy loading. what do you mean when you talk about inprocess session state? – andy Jul 28 '12 at 03:46
  • +1 The best way to minimize load time, is to minimize the amount of stuff happening at load by deferring the loading of specific components until the first time they are really needed. – BenSwayne Jul 30 '12 at 01:25
  • Sorry for the late response, andy. Session state can be stored in a variety of ways. The default method is InProcess, which is simply in memory on the IIS server. It is simple and works just fine if your app is only running on one server and if you are sensible about your app pool recycles. An alternate method is to store the session in the database where they will survive an app pool reset or a user bouncing between servers in a load-balanced environment. – Facio Ratio Aug 02 '12 at 15:56
3

In my understanding, to prevent the propagation of startup time to users, you should avoid recycling the App Pool, for which you can use IIS App pool timeout settings,these can be tuned through web.config, not just through IIS console. Additionally you can read more of it here on this SO qurestion. You might not need Application_End hacks to achieve this.

Update : I found another interesting thing that may help you on this, check this IIS Application Initialization Extension that can be used to preload dependencies as soon as worker process starts. It may help you improve customer experience. Check it out.

Community
  • 1
  • 1
Furqan Hameedi
  • 4,372
  • 3
  • 27
  • 34
  • +1 thanks furqan, but doesn't the app pool need to be recycled? Ill check out your links now – andy Jul 28 '12 at 03:52
  • App Pool recycling can be minimized but it should never be eliminated. Also many hosting companies won't allow you 100% control over the app pool recycling parameters (often enforcing app pool recycles for exceeding resource allocations such a memory). This is still fine advice, but not "the best answer" to this question. – BenSwayne Jul 30 '12 at 01:20
  • If you can code without leaking memory (obviously you can!) you should disable the AppPool recycle imo. So I think this is indeed the best answer. – Henrik Jul 30 '12 at 20:51