Exemplarische Vorgehensweise: Erstellen eines benutzerdefinierten Installers für eine ClickOnce-Anwendung
Jede ClickOnce-Anwendung, die auf einer EXE-Datei basiert, kann von einem benutzerdefinierten Installer automatisch installiert und aktualisiert werden. Ein benutzerdefinierter Installer kann während der Installation benutzerdefinierte Optionen implementieren, einschließlich benutzerdefinierter Dialogfelder für Sicherheits- und Wartungsvorgänge. Der benutzerdefinierte Installer führt Installationsvorgänge mithilfe der InPlaceHostingManager-Klasse aus. Diese exemplarische Vorgehensweise veranschaulicht, wie ein benutzerdefinierter Installer erstellt wird, der automatisch eine ClickOnce-Anwendung installiert.
So erstellen Sie einen benutzerdefinierten Installer für eine ClickOnce-Anwendung
Fügen Sie in der ClickOnce-Anwendung Verweise auf "System.Deployment" und "System.Windows.Forms" hinzu.
Fügen Sie der Anwendung eine neue Klasse hinzu, und geben Sie einen beliebigen Namen an. In dieser exemplarischen Vorgehensweise wird der Name MyInstaller verwendet.
Fügen Sie am Anfang der neuen Klasse die Anweisung Imports oder using hinzu.
Imports System.Deployment.Application Imports System.Windows.Forms
using System.Deployment.Application; using System.Windows.Forms;
Fügen Sie der Klasse die folgenden Methoden hinzu.
Diese Methoden rufen InPlaceHostingManager-Methoden auf, um das Bereitstellungsmanifest herunterzuladen, entsprechende Berechtigungen zu gewähren, beim Benutzer die Berechtigung zum Installieren anzufordern und dann die Anwendung in den ClickOnce-Cache herunterzuladen und zu installieren. Ein benutzerdefinierter Installer kann angeben, dass eine ClickOnce-Anwendung vorerst vertrauenswürdig ist, oder die Vertrauensentscheidung an den AssertApplicationRequirements-Methodenaufruf verweisen. Dieser Code stuft die Anwendung vorerst als vertrauenswürdig ein.
Tipp
Berechtigungen, die durch eine Einstufung als vorerst vertrauenswürdig erteilt werden, können nicht die Berechtigungen überschreiten, die im Code des benutzerdefinierten Installers definiert sind.
Dim WithEvents iphm As InPlaceHostingManager = Nothing Public Sub InstallApplication(ByVal deployManifestUriStr As String) Try Dim deploymentUri As New Uri(deployManifestUriStr) iphm = New InPlaceHostingManager(deploymentUri, False) MessageBox.Show("Created the object.") Catch uriEx As UriFormatException MessageBox.Show("Cannot install the application: " & _ "The deployment manifest URL supplied is not a valid URL." & _ "Error: " & uriEx.Message) Return Catch platformEx As PlatformNotSupportedException MessageBox.Show("Cannot install the application: " & _ "This program requires Windows XP or higher. " & _ "Error: " & platformEx.Message) Return Catch argumentEx As ArgumentException MessageBox.Show("Cannot install the application: " & _ "The deployment manifest URL supplied is not a valid URL." & _ "Error: " & argumentEx.Message) Return End Try iphm.GetManifestAsync() End Sub Private Sub iphm_GetManifestCompleted(ByVal sender As Object, ByVal e As GetManifestCompletedEventArgs) Handles iphm.GetManifestCompleted ' Check for an error. If (e.Error IsNot Nothing) Then ' Cancel download and install. MessageBox.Show("Could not download manifest. Error: " & e.Error.Message) Return End If ' Dim isFullTrust As Boolean = CheckForFullTrust(e.ApplicationManifest) ' Verify this application can be installed. Try ' the true parameter allows InPlaceHostingManager ' to grant the permissions requested in the application manifest. iphm.AssertApplicationRequirements(True) Catch ex As Exception MessageBox.Show("An error occurred while verifying the application. " & _ "Error text: " & ex.Message) Return End Try ' Use the information from GetManifestCompleted() to confirm ' that the user wants to proceed. Dim appInfo As String = "Application Name: " & e.ProductName appInfo &= ControlChars.Lf & "Version: " & e.Version.ToString() appInfo &= ControlChars.Lf & "Support/Help Requests: " If Not (e.SupportUri Is Nothing) Then appInfo &= e.SupportUri.ToString() Else appInfo &= "N/A" End If appInfo &= ControlChars.Lf & ControlChars.Lf & _ "Confirmed that this application can run with its requested permissions." ' If isFullTrust Then ' appInfo &= ControlChars.Lf & ControlChars.Lf & _ ' "This application requires full trust in order to run." ' End If appInfo &= ControlChars.Lf & ControlChars.Lf & "Proceed with installation?" Dim dr As DialogResult = MessageBox.Show(appInfo, _ "Confirm Application Install", MessageBoxButtons.OKCancel, MessageBoxIcon.Question) If dr <> System.Windows.Forms.DialogResult.OK Then Return End If ' Download the deployment manifest. ' Usually, this shouldn't throw an exception unless ' AssertApplicationRequirements() failed, or you did not call that method ' before calling this one. Try iphm.DownloadApplicationAsync() Catch downloadEx As Exception MessageBox.Show("Cannot initiate download of application. Error: " & downloadEx.Message) Return End Try End Sub #If 0 Then Private Function CheckForFullTrust(ByVal appManifest As XmlReader) As Boolean Dim isFullTrust As Boolean = False If (appManifest Is Nothing) Then Throw New ArgumentNullException("appManifest cannot be null.") End If Dim xaUnrestricted As XAttribute xaUnrestricted = XDocument.Load(appManifest) _ .Element("{urn:schemas-microsoft-com:asm.v1}assembly") _ .Element("{urn:schemas-microsoft-com:asm.v2}trustInfo") _ .Element("{urn:schemas-microsoft-com:asm.v2}security") _ .Element("{urn:schemas-microsoft-com:asm.v2}applicationRequestMinimum") _ .Element("{urn:schemas-microsoft-com:asm.v2}PermissionSet") _ .Attribute("Unrestricted") ' Attributes never have a namespace If xaUnrestricted Then If xaUnrestricted.Value = "true" Then Return True End If End If Return False End Function #End If Private Sub iphm_DownloadProgressChanged(ByVal sender As Object, ByVal e As DownloadProgressChangedEventArgs) Handles iphm.DownloadProgressChanged ' you can show percentage of task completed using e.ProgressPercentage End Sub Private Sub iphm_DownloadApplicationCompleted(ByVal sender As Object, ByVal e As DownloadApplicationCompletedEventArgs) Handles iphm.DownloadApplicationCompleted ' Check for an error. If (e.Error IsNot Nothing) Then ' Cancel download and install. MessageBox.Show("Could not download and install application. Error: " & e.Error.Message) Return End If ' Inform the user that their application is ready for use. MessageBox.Show("Application installed! You may now run it from the Start menu.") End Sub
InPlaceHostingManager iphm = null; public void InstallApplication(string deployManifestUriStr) { try { Uri deploymentUri = new Uri(deployManifestUriStr); iphm = new InPlaceHostingManager(deploymentUri, false); } catch (UriFormatException uriEx) { MessageBox.Show("Cannot install the application: " + "The deployment manifest URL supplied is not a valid URL. " + "Error: " + uriEx.Message); return; } catch (PlatformNotSupportedException platformEx) { MessageBox.Show("Cannot install the application: " + "This program requires Windows XP or higher. " + "Error: " + platformEx.Message); return; } catch (ArgumentException argumentEx) { MessageBox.Show("Cannot install the application: " + "The deployment manifest URL supplied is not a valid URL. " + "Error: " + argumentEx.Message); return; } iphm.GetManifestCompleted += new EventHandler<GetManifestCompletedEventArgs>(iphm_GetManifestCompleted); iphm.GetManifestAsync(); } void iphm_GetManifestCompleted(object sender, GetManifestCompletedEventArgs e) { // Check for an error. if (e.Error != null) { // Cancel download and install. MessageBox.Show("Could not download manifest. Error: " + e.Error.Message); return; } // bool isFullTrust = CheckForFullTrust(e.ApplicationManifest); // Verify this application can be installed. try { // the true parameter allows InPlaceHostingManager // to grant the permissions requested in the applicaiton manifest. iphm.AssertApplicationRequirements(true) ; } catch (Exception ex) { MessageBox.Show("An error occurred while verifying the application. " + "Error: " + ex.Message); return; } // Use the information from GetManifestCompleted() to confirm // that the user wants to proceed. string appInfo = "Application Name: " + e.ProductName; appInfo += "\nVersion: " + e.Version; appInfo += "\nSupport/Help Requests: " + (e.SupportUri != null ? e.SupportUri.ToString() : "N/A"); appInfo += "\n\nConfirmed that this application can run with its requested permissions."; // if (isFullTrust) // appInfo += "\n\nThis application requires full trust in order to run."; appInfo += "\n\nProceed with installation?"; DialogResult dr = MessageBox.Show(appInfo, "Confirm Application Install", MessageBoxButtons.OKCancel, MessageBoxIcon.Question); if (dr != System.Windows.Forms.DialogResult.OK) { return; } // Download the deployment manifest. iphm.DownloadProgressChanged += new EventHandler<DownloadProgressChangedEventArgs>(iphm_DownloadProgressChanged); iphm.DownloadApplicationCompleted += new EventHandler<DownloadApplicationCompletedEventArgs>(iphm_DownloadApplicationCompleted); try { // Usually this shouldn't throw an exception unless AssertApplicationRequirements() failed, // or you did not call that method before calling this one. iphm.DownloadApplicationAsync(); } catch (Exception downloadEx) { MessageBox.Show("Cannot initiate download of application. Error: " + downloadEx.Message); return; } } /* private bool CheckForFullTrust(XmlReader appManifest) { if (appManifest == null) { throw (new ArgumentNullException("appManifest cannot be null.")); } XAttribute xaUnrestricted = XDocument.Load(appManifest) .Element("{urn:schemas-microsoft-com:asm.v1}assembly") .Element("{urn:schemas-microsoft-com:asm.v2}trustInfo") .Element("{urn:schemas-microsoft-com:asm.v2}security") .Element("{urn:schemas-microsoft-com:asm.v2}applicationRequestMinimum") .Element("{urn:schemas-microsoft-com:asm.v2}PermissionSet") .Attribute("Unrestricted"); // Attributes never have a namespace if (xaUnrestricted != null) if (xaUnrestricted.Value == "true") return true; return false; } */ void iphm_DownloadApplicationCompleted(object sender, DownloadApplicationCompletedEventArgs e) { // Check for an error. if (e.Error != null) { // Cancel download and install. MessageBox.Show("Could not download and install application. Error: " + e.Error.Message); return; } // Inform the user that their application is ready for use. MessageBox.Show("Application installed! You may now run it from the Start menu."); } void iphm_DownloadProgressChanged(object sender, DownloadProgressChangedEventArgs e) { // you can show percentage of task completed using e.ProgressPercentage }
Um die Anwendung über den Code zu installieren, rufen Sie die InstallApplication-Methode auf. Wenn Sie der Klasse z. B. den Namen MyInstaller gegeben haben, könnten Sie InstallApplication wie folgt aufrufen.
Dim installer As New MyInstaller() installer.InstallApplication("\\myServer\myShare\myApp.application") MessageBox.Show("Installer object created.")
MyInstaller installer = new MyInstaller(); installer.InstallApplication(@"\\myServer\myShare\myApp.application"); MessageBox.Show("Installer object created.");
Nächste Schritte
Eine ClickOnce-Anwendung kann auch benutzerdefinierte Aktualisierungslogik hinzufügen, einschließlich einer benutzerdefinierten Benutzeroberfläche, die beim Aktualisierungsvorgang angezeigt wird. Weitere Informationen finden Sie unter UpdateCheckInfo. Eine ClickOnce-Anwendung kann auch den standardmäßigen Startmenüeintrag, die Verknüpfung und den Eintrag unter "Software" mithilfe des <customUX>-Elements unterdrücken. Weitere Informationen finden Sie unter <entryPoint>-Element (ClickOnce-Anwendung) und ShortcutAppId.