ClickOnce deployed application asks to install update even if there exists none - c#

I have ClickOnce deployed application coded in C#. I wonder if anyone experienced the same problem.
Clickonce deployed application checks for updates always before execution. One of my clients using this application informs me about an update which the application asks to install even if there exists no update we had deployed. My clients installed the update. But what was installed is the same version. At this point, I wonder why a clickonce application decides if there is an update deployed. I believe this is a weird problem that I could not figure out why it happened.
Is there anyone who knows why such a weird thing could happen ? I suspect may be some of files of the installation removed, thus leading a reinstallation of the program. But I am not sure.

We've had this problem before with some of our clients. The problem ended up being due to object caching on their proxy server. Basically, the client actually is running an old version, so when they start your program, ClickOnce correctly reports that there is an update available. The problem is that the client's proxy server caches an old copy of your program, so when the updater runs the proxy server intercepts the update request and instead sends back a cached copy of your program in place of the update. ClickOnce doesn't notice until its next startup that the "updated" program still isn't actually updated.
The solution is to get in touch with your client's IT staff and try to figure out where the caching is happening and have them clear the cache. It's probably on their custom-built proxy server, but webfilters like Barracuda do object caching too, and so do some of the fancier Cisco routers.

Related

Azure Cloud Service Startup Task that requires reboot

Tried with osFamily 4, osVersion *
Background: we have an app that uses System.Management.Automation.dll (from the GAC, dev box is W10) to work with Powershell in C# code. Specifically, we are using InitialSessionState and the ExecutionPolicy property - which we found out is part of WMF 5 (it errors out with not found exception on type load on the cloud service).
Now, this can be properly fixed by installing WMF 5 (we tried first via Remote Desktop; and no, forcing only the newer s.m.a.dll into the GAC does not work). Problem is, the installer asks for a reboot - and that I think is a problem with the startup task.
We added the installer to the setup.cmd that we already had:
Win8.1AndW2K12R2-KB3134758-x64.msu /quiet
It indeed automatically reboots the role instance, and runs setup.cmd again (which adds an error entry to the setup event log to the tune that it is already installed).
This reboot does not flag the cloud service deployment as failed. Which we are happy about but, is this really a supported behavior? or accidental?
Is there the supported way to make an installer work that requires a reboot? Or is the behavior we found the "supported" way?
There's not really a "supported" way - how you initialize your cloud service is really up to you. Having said that:
Given that cloud service role instances typically survive reboots, there's nothing wrong with setting something up that requires a reboot. Then it's a matter of dealing with already-installed software when returning from the reboot (e.g. leaving a breadcrumb file from your .cmd that installed the software initially). This is sometimes the only way you can install software (where reboots are involved), and utilizing a breadcrumb helps cut down on subsequent reboot time (the clock-time required to complete the boot process; not the number of actual reboots).
In this type of scenario, only the initial role instance boot has an additional reboot. (other reboots, from Guest OS and Host OS updates, or failed hardware etc., are separate, of course).

how is better deploy (install) this application?

I have an application that has two main parts. First, the client, basicly is the user iterface, second, a repository that is a library, that connects with the database and has all the logic to insert, update, delete... and ensures the coherence of the data.
The application is not deplyed yet, and by the moment the client uses directly the repository to access to the database. But when I will have to deploy the application to be used for many users, inside the LAN, I think that this is not the best solution.
First solution
Install the client and the repository in all the computer of the users that need the application.
This have the disadvantage that when I update the application, I have to update many applications, and perhaps not all the applications are updated because of any reason. So if the update is of the repository that fix some problem, if the client that has not updated the application will introduce incoherence data in the database, if the fix is to correct this type of problem.
Second solution
The client use direcly the repository, but the application is installed in a network drive. I have only one installation, so if I need to update the application, I have to do it once.
The application is not so big, about 12MB, but it could be a bit slow because has to go through the net from the server to user computer. So perhaps some user could copy the application to the local computer, so I can't ensure that happens the problem with the first solution.
Third solution
The client application does not use the repository directly, the repository is in the server and the client use WCF to communicate with the server, and the server uses the repository to access to the database.
The disadvantage is that the server has to run the repository, so if there are many clients connected, it needs a lot of RAM, instead that if the computers of the users have the application in local, the memory is needed in the local computer.
In sumary, when I have to deply this kind of application, which is the best solution, or which is the solution that would you use in your projects?
Thank you so much.
This really depends on your deployment method, are you using a ClickOnce to deploy it? If so you could keep the data local to each PC, avoid those RAM issue, and if you send out a new update change the required version number and set it to check prior to running, that way they will be unable to run the program without updating it. The problem is they must have network access, but this would also be an issue with remote data. In this situation you would only need network access during the update, not sure if this would be an issue or not.

False positive detection of c# .net program by anti-virus as trojan

I have developed a windows service using C#.Net which collects data and send to my server using custom APIs on a regular interval basis with the client user's permission.
It was working fine until the user installed the anti-virus software (Kaspersky). It, false positively, detected my .exes as PDM:trojan.win32.generic, thrown away into quarantine and removed its service because I am doing web requests using HTTPWebRequest and HTTPWebResponse to push and pull data.
As for temporary, I have white listed .exes and program directory under exclusions rules in anti-virus software program settings and installed service once again. As so it is working fine for now.
But as for final solution, I want to know can we fix this within program itself (programmatically). So that any anti-virus software do not detect it as trojan or any other kind of virus as soon as my program and its service get installed.
Edit - 8th, June 2015
Earlier forgotten to mention that within service .exe it downloads its own latest .exe file to update itself. I wonder if this process is making it to appear as a Trojan.
You can apply to have your program added to the Kasperky whitelist. You may also want to apply for the Kaspersky Lab Trusted Logo.
Other anti virus solutions offer similar whitelist programs, Symantec for example.
Going through these whitelists -IMHO- is the proper way here. If your users place their trust in those solutions your making an effort to be whitelisted i.e. labeled as trustworthy by these solutions should go a long way with your user base.

How to test and deploy distributed applications?

I've written a client-server application. There is one computer running the server application, and several computers running the client application.
So far, every time I had a new version / patch of my application, I copied the binaries first through VNC to the server application, and then start a script, that performs a script on client-side, that is copying the binaries to a local folder (network execution is not working!)... Then the client application is started on every client computer...
So what are good opportunities that can replace my old-style method?
I tried creating a click-once application that is updating over http/ftp... but without success ^^
We use an open source app called Presto: http://presto.codeplex.com/
After doing the initial setup, there are only two manual steps with each deployment:
1. Copy the binaries to a network location
2. Press the button in Presto to initiate a new deployment
The big win with Presto is that you use it to initially set up your apps and servers, and specify the appropriate config settings for each environment. Once you initiate a deployment, the installation happens automatically, and the correct values are written to the config files (QA gets QA values, production gets production values, etc...).
With Presto, you can stop services, delete folders, copy new binaries, update config files, etc... and it's all automated.
That's why web front-end is so popular :)
Try to implement good auto-update mechanism and versioning. Client has hard coded server version, with first call all with each call server includes own version. When version mismatch - time to auto update. On server - it's just endpoint to download client application installation, which is standard across versions.
So client has external updater process, that is initiated after client knows that new version exists. Goal of updater process is to download new installation/package and that either to run installation that will update/re-install client either unpack and copy new/modified files.
When not using some external libraries. Process looks like this.
Click-once is another approach and also should work.
Similr question is here
Auto update .NET applications
Anyway probably your client apps need a good installer. When you have installer just left to implement simple downloader/updater and versioning on service.
It is not that hard to do this with less code.
Set up a http service in your application.
Create a File where the current version is listed.
Set up a ftp service in your application to provide the new binaries.
Add a Updater.exe application to the client, this will check for new updates via http and download the new version via ftp. Also a client version file should be made.
So you just have to do your old-style method just one more time and you are done!
Now I don't know if the client application can run the server, if that case is so, I would advice to seperate the services (http, ftp) from your server app.

C# ClickOnce deployment for Windows Services?

What are some best practices for being able to deploy a Windows service that will have to be updated?
I have a Windows service that I will be deploying but might require some debugging and new versions during the beta process. What is the best way to handle that? Ideally, I'd like to find a ClickOnce-style deployment solution for Windows services but my understanding is that this does not exist. What is the closest I can get to ClickOnce for a Windows service?
A simple solution that I use is to merely stop the service and x-copy the files from my bin folder into the service folder.
A batch file to stop the service then copy the files should be easy to throw together.
Net stop myService
xcopy \\myServerWithFiles\*.* c:\WhereverTheServiceFilesAre
net start myService
I have a system we use at work here that seems to function pretty well with services. Our deployed system has around 20-30 services at any given time. At work we use a product called TopShelf you can find it here http://topshelf-project.com/
Basically TopShelf handles a lot of the service related stuff. Installing, Uninstalling etc all from the cmd line of the service. One of the very useful features is the ability to run as console for debugging. You build one service, and with a different cmd line start you can run it as a console to see the output of the service. We added one custom feature to this software that lets us configure profiles in advance. Basically our profiles configure a few things like logging, resource locations etc so that we can control all that without having to republish any code. All we do is run a command like
D:\Services\ServiceName.exe Core.Profiles.Debug or
D:\Services\ServiceName.exe Core.Profiles.Production
to get different logging configurations.
Our build script creates install.cmd and uninstall.cmd scripts for each of our services all we do is copy the files to the server and run the script. If we want to see debug output we stop the service and double click the exe and we get a console to read all the output.
One more thing that topshelf has which we don't use because its not necessary is the concept of shelving (there is documentation on this website for this). This allows you to update the service without having to "restart" but you still need to copy the files manually unless you build an automated system for that.
However, my suggestion if you need 100% service availability is to have a redundant system. No matter how you configure your service for updates you cannot avoid hardware failure causing downtime without an automated failover system. If said system was in place my recommended update strategy would be to turn off 1 node, update, test, turn on turn off the other node, update, test and turn the 2nd node back on. You can do this all of course with a simple script. This may be a more complicated system than you need but if you can't take a service offline for a simple restart that takes 5 seconds then you really need some system in place to deal with hardware issues because I can guarantee it will happen eventually.
Since a service is long-running anyway, using ClickOnce style deployment might not be viable - because ClickOnce only updates when you launch the app. A service will typically only be launched when the machine is rebooted.
If you need automatic update of a service then your best bet might be to hand-code something into the service, but I'd forsee problems with almost any solution: most install processes will require some level of user interaction (if only to get around UAC), so I can't imagine this would lead an answer that doesn't involve getting a logged-on user in front of the screen at some point.
One idea that might just work is active-directory deployment (or some similar equivalent). If your service is deployed via a standard MSI-type installer, AD allows you to update the application silently as part of the computer policy. I suspect you'd have to force the server to refresh the AD policy (by rebooting or using gpupdate from the console), but other than that it should be a hands-off deployment.
I would suggest using the "plugin" approach on this, that is, using the Proxy Design Pattern.
While using this pattern, an independant thread may verify over a folder for updates. You will need to use ShadowCopy over your assembly deployment. When your service update-thread encounters a new version of your service, it shall unload the current production assembly and load the new version, without stopping the service itself. Even more! Your service should never notice the difference, if there is no breaking code within your assembly.
I would suggest to create a normal setup project, and add the windows service project output in that setup project.
For more information please refer to http://support.microsoft.com/kb/816169.

Categories

Resources