views:

76

answers:

3

I've seen several posts that essentially state that UI components shouldn't run as a service. I understand the rational that no one can respond to UI events etc. But the fact remains that are are many automation tasks that are only possible with Windows forms.

Here is a couple of great examples:

  1. I would like to build a url crawler service that makes thumbnails of webpages. Currently the only way I see to achieve this is to try and automate the .Net WebBroswer component.

  2. Automate the printing of MS-Word docs.

Pre-Vista there was some tricks to get around this, but now there is none. My question is why is this the case, and what alternatives does one really have?

+6  A: 

Lookup Shatter Attacks and Session 0 Isolation Feature.

Basically if two processes (of different users) share the same desktop, one process can potentially execute whatever code it wants in the other process by sending windows messages, and this was called a Shatter Attack.

There was a lot of discussion whether this was a design bug or not, and post Vista, Microsoft decided to remove any interactive desktop support for services as that was a potential security hole.

As an alternative, you can consider, running your image generation/printing code as a logged in user, who has access to an interactive desktop.

Moron
+1 nice answer.
James
A: 

Technically, UI components requires started Windows Message Queue to work. You can run it from windows service (may be with allowed Interaction with Desktop, as far as I know this feature is disabled in Windows Vista and higher).

But things you are talking about is not UI components, it is COM components, and you can use it. At least MS Office, but it is not recommended by Microsoft, because memory leaks are possible. Latest MS Office has server edition, that can be used in application without user interface.

STO
+1  A: 

Like Moron said best thing to do is not run it as a service.

But perhaps you're stuck running it from a service anyway, because there is an existing framework of some sort that you're needing to run your code from.

So the workaround to that would be to write a server program that runs as a logged in user. You will hit that server program from your code the must be in a service. The server will do the work and return the results.

You can communicate between the 2 using WCF over named pipes as the transport, or whatever works. If that doesn't, you can use bare named pipes, or, tcp/ip on the localhost. Judging from your website in your userprofile, you should know all about localhost!

FastAl