共用方式為


逐步解說:使用 ClickOnce 部署 API 隨選下載組件

根據預設,ClickOnce 應用程式中包含的所有元件都會在第一次執行應用程式時下載。 不過,您的應用程式部分可能由一小部分使用者使用。 在這種情況下,您只需在創建其某一類型時才下載組件。 下列逐步解說示範如何將應用程式中的某些元件標示為「選擇性」,以及如何在共用語言執行階段 (CLR) 要求時使用命名空間中的 System.Deployment.Application 類別來下載它們。

備註

ApplicationDeployment命名空間中的System.Deployment.Application類別和 API 不支援 .NET Core 和 .NET 5 和更新版本。 在 .NET 7 中,支援存取應用程式部署屬性的新方法。 如需詳細資訊,請參閱 存取 .NET 中的 ClickOnce 部署屬性。 .NET 7 不支援對等的 ApplicationDeployment 方法。

備註

您的應用程式必須以完全信任的方式執行,才能使用此程式。

先決條件

您將需要下列其中一個元件才能完成本逐步解說:

  • Windows SDK。 Windows SDK 可以從 Microsoft 下載中心下載。

  • Visual Studio。

建立專案

建立一個使用隨選組合的專案

  1. 建立名為 ClickOnceOnDemand 的目錄。

  2. 開啟 Windows SDK 命令提示字元或 Visual Studio 命令提示字元。

  3. 變更為 ClickOnceOnDemand 目錄。

  4. 使用下列命令產生公開/私密金鑰組:

    sn -k TestKey.snk
    
  5. 使用記事本或其他文字編輯器,定義一個名為DynamicClass的類別,其有一個單一屬性,名為Message

    using System;
    using System.Collections.Generic;
    using System.Text;
    
    namespace Microsoft.Samples.ClickOnceOnDemand
    {
        public class DynamicClass
        {
            public DynamicClass() {}
    
            public string Message
            {
                get
                {
                    return ("Hello, world!");
                }
            }
        }
    }
    
  6. 將文字儲存為名為 ClickOnceLibrary.csClickOnceLibrary.vb 的檔案,視您使用的語言而定,儲存至 ClickOnceOnDemand 目錄。

  7. 將檔案編譯成組件。

    csc /target:library /keyfile:TestKey.snk ClickOnceLibrary.cs
    
  8. 若要取得元件的公開金鑰權杖,請使用下列命令:

    sn -T ClickOnceLibrary.dll
    
  9. 使用文字編輯器建立新檔案並輸入以下程式碼。 此程式碼會建立 Windows Forms 應用程式,在需要時即下載 ClickOnceLibrary 元件。

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Text;
    using System.Windows.Forms;
    using System.Reflection;
    using System.Deployment.Application;
    using Microsoft.Samples.ClickOnceOnDemand;
    
    namespace ClickOnceOnDemand
    {
        [System.Security.Permissions.SecurityPermission(System.Security.Permissions.SecurityAction.Demand, Unrestricted=true)]
        public class Form1 : Form
        {
            // Maintain a dictionary mapping DLL names to download file groups. This is trivial for this sample,
            // but will be important in real-world applications where a feature is spread across multiple DLLs,
            // and you want to download all DLLs for that feature in one shot. 
            Dictionary<String, String> DllMapping = new Dictionary<String, String>();
    
            public static void Main()
            {
                Form1 NewForm = new Form1();
                Application.Run(NewForm);
            }
    
            public Form1()
            {
                // Configure form. 
                this.Size = new Size(500, 200);
                Button getAssemblyButton = new Button();
                getAssemblyButton.Size = new Size(130, getAssemblyButton.Size.Height);
                getAssemblyButton.Text = "Test Assembly";
                getAssemblyButton.Location = new Point(50, 50);
                this.Controls.Add(getAssemblyButton);
                getAssemblyButton.Click += new EventHandler(getAssemblyButton_Click);
    
                DllMapping["ClickOnceLibrary"] = "ClickOnceLibrary";
                AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(CurrentDomain_AssemblyResolve);
            }
    
            /*
             * Use ClickOnce APIs to download the assembly on demand.
             */
            private Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
            {
                Assembly newAssembly = null;
    
                if (ApplicationDeployment.IsNetworkDeployed)
                {
                    ApplicationDeployment deploy = ApplicationDeployment.CurrentDeployment;
    
                    // Get the DLL name from the Name argument.
                    string[] nameParts = args.Name.Split(',');
                    string dllName = nameParts[0];
                    string downloadGroupName = DllMapping[dllName];
    
                    try
                    {
                        deploy.DownloadFileGroup(downloadGroupName);
                    }
                    catch (DeploymentException de)
                    {
                        MessageBox.Show("Downloading file group failed. Group name: " + downloadGroupName + "; DLL name: " + args.Name);
                        throw (de);
                    }
    
                    // Load the assembly.
                    // Assembly.Load() doesn't work here, as the previous failure to load the assembly
                    // is cached by the CLR. LoadFrom() is not recommended. Use LoadFile() instead.
                    try
                    {
                        newAssembly = Assembly.LoadFile(Application.StartupPath + @"\" + dllName + ".dll," +  
                "Version=1.0.0.0, Culture=en, PublicKeyToken=03689116d3a4ae33");
                    }
                    catch (Exception e)
                    {
                        throw (e);
                    }
                }
                else
                {
                    //Major error - not running under ClickOnce, but missing assembly. Don't know how to recover.
                    throw (new Exception("Cannot load assemblies dynamically - application is not deployed using ClickOnce."));
                }
    
    
                return (newAssembly);
            }
    
            private void getAssemblyButton_Click(object sender, EventArgs e)
            {
                DynamicClass dc = new DynamicClass();
                MessageBox.Show("Message: " + dc.Message);
            }
        }
    }
    
  10. 在程式碼中,找到對LoadFile的呼叫。

  11. 設定 PublicKeyToken 為您先前擷取的值。

  12. 將檔案儲存為 Form1.csForm1.vb

  13. 使用以下命令將其編譯為可執行檔。

    csc /target:exe /reference:ClickOnceLibrary.dll Form1.cs
    

將組件標記為選擇性

使用 MageUI.exe 將元件標示為 ClickOnce 應用程式的選擇性元件

  1. 使用 MageUI.exe,建立應用程式資訊清單,如 逐步解說:手動部署 ClickOnce 應用程式中所述。 針對應用程式資訊清單使用下列設定:

    • 將應用程式資訊清單 ClickOnceOnDemand命名為 。

    • [檔案] 頁面的 ClickOnceLibrary.dll 列中,將 [檔案類型 ] 資料行設定為 [無]。

    • 檔案 頁面的 ClickOnceLibrary.dll 列中,在 群組 資料行輸入 ClickOnceLibrary.dll

  2. 使用 MageUI.exe,建立部署資訊清單,如 逐步解說:手動部署 ClickOnce 應用程式中所述。 針對部署資訊清單使用下列設定:

    • 將部署資訊清單 ClickOnceOnDemand命名為 。

測試新組件

測試隨選組件

  1. 將您的 ClickOnce 部署上傳至 Web 伺服器。

  2. 輸入部署資訊清單的 URL,從網頁瀏覽器啟動使用 ClickOnce 部署的應用程式。 如果您呼叫 ClickOnce 應用程式 ClickOnceOnDemand,並將它上傳至 adatum.com 的根目錄,您的 URL 看起來會像這樣:

    http://www.adatum.com/ClickOnceOnDemand/ClickOnceOnDemand.application
    
  3. 當您的主表單出現時,請按 Button。 您應該會在訊息方塊視窗中看到一個字串,上面寫著「Hello, World!」。