So how do you make an updater be less horrible.
First off, as I suggested for all applets, consider not having one at all. For instance, Collectorz.Com's applications each check for updates periodically when they are started. That way you bury your update functionality with the application, and it alleviates the need to worry about external updaters.
If your application is itself a plugin (think Flash, Quicktime, Java or a driver (of any kind)), then you don't have a convenient application on which to hang your updater. For that case, whatever you do, don't burn a process whose sole purpose is to check for updates once a month. Instead, use the task scheduler functionality built into Windows to schedule your updater. The task scheduler is a remarkably flexible mechanism for scheduling periodic operations. Even using the Task Scheduler 1.0 interfaces (which are available on Windows platforms going back to Windows ME), you can generate triggers that will cause tasks to be run daily, weekly, monthly, monthly on a specific day of the week, logon, idle, etc. For Vista, the list of trigger types is enhanced to include triggers on system events, groups of triggers, etc.
One of the cool things you can do with scheduled tasks is to specify the context in which the job runs - jobs can be scheduled to run in the context of the user at the console, in the system context, the context of an interactively logged on user, to run only if a specific user is logged on, etc.
Using the task scheduler means that you can get your updater to run without consuming any long-term resources.
Once you've decided that you need to update the application, you've got to download the update. For that, you really have two options. The first is that you can assume that the user is going to want the update and pre-download it, the second is that you download it after informing the user about update. For either case Windows has a nifty feature called "BITS" which allows you to download data from the web without interfering with the user - essentially the BITS service is aware of the traffic generated by the interactive user and it throttles its transfers if it detects that the user's using the network. It also supports progressive downloading so it can handle the network dropping out mid transfer. Windows Update's downloader is built on top of BITS, but I'm not aware of any 3rd party apps that use it (which is a shame, because it really is cool). BITS is available on at least Windows XP and later, so it's not "yet another vista-only feature".
Also, whatever you do, don't ever require elevation for your updater - I cannot imagine any scenario that would require that your updater run elevated - it just annoys the user who complains about unnecessary elevation prompts.
Next: Mitigations for notification area handlers.
> Uh, this one lost me. I write my installer to install in Program Files. Surely that means my updater must update files (DLLs, EXEs, say) in Program Files?
Your *installer* might write to program files and require elevation but your *updater*, which checks for an update and then downloads it and runs the installer, shouldn't.
I think Larry's point is that you really don't want to be hassled by a UAC prompt when an updater decides to wake up and do an update check. A couple of posts back he mentioned something which did just that.
>> but I'm not aware of any 3rd party apps that use it
So do we. Our field service folks are mighty happy about it.
davidacoder: I'm not sure why WU is a service, I'll see if I can find out.
"Maybe this is because it wasn't cool enough to be documented..."
Why do people embarrass themselves like this? A little research shows that there is a large amount of information on the Internet on using BITS, including formal documentation. In addition to the link to the documentation Larry provided, there is:
Write Auto-Updating Apps with .NET and the Background Intelligent Transfer Service API:
Background Intelligent Transfer Service (BITS):
Using Windows XP Background Intelligent Transfer Service (BITS) with Visual Studio .NET: http://msdn2.microsoft.com/en-us/library/ms997639.aspx
Managed Wrapper for BITS:
Maybe some of the above isn't applicable to you, maybe it is. Point being, to claim that Microsoft does not document (and support developers using) it's *public* APIs is an outright lie and does a disservice to the men and women of Microsoft who work very hard to try to make sure the documentation is complete:
Shameless plug for an article I wrote that demonstrates how to use BITS to download files:
Somehow I think Larry meant that the application that checks for updates and downloads them should not need elevation, not the actual update itself.
"I'm not sure why WU is a service, I'll see if I can find out."
It is called "Automatic Updates"
> two options. The first is that you can assume that the user
> is going to want the update and pre-download it,
DO NOT DO THIS.
Windows Automatic Updates provide correct options for this kind of thing. If the user sets an option to do pre-downloading then you do it. But DO NOT ASSUME IT.
It is really fun (not) to dial up a cell phone, expecting to spend a few seconds downloading or sending e-mail, and finding that some assumer has hijacked your connection. The train is leaving the station in 40 seconds. You want to download updates tonight, not now.
It is really fun (not) to find assumers doing the same thing on a pay-per-packet internet connection.
> Task Scheduler 1.0 interfaces (which are available on
> Windows platforms going back to Windows ME)
Does that mean 98 had Task Scheduler 0.0 interfaces?
In previous articles, I've pointed out: Programmer Hubris - He's just not that into you Programmer