简体   繁体   English

如何将 C# 方法添加到现有的大型 wix 脚本

[英]How do I add C# methods to an existing large wix script

We have an existing wix script that is pretty complex & long.我们有一个现有的 wix 脚本,它非常复杂且很长。 All the CustomActions are performed with inline vbscript.所有 CustomActions 都使用内联 vbscript 执行。

I want to switch some of those actions from vbscript to C#.我想将其中一些操作从 vbscript 切换到 C#。 All the examples everywhere start with "create a wix project in VisualStudio...".所有示例都以“在 VisualStudio 中创建一个 wix 项目...”开头。 Is there any example out there about how to add in C# code to an existing wix project?有没有关于如何将 C# 代码添加到现有 wix 项目的示例? One where it is built using the old school wix command line apps?一个是使用老式 wix 命令行应用程序构建的?

A shameless promotion of C++ custom actions first! 先无耻宣传C++自定义动作! :-). :-)。

And: "WiX Quick Start" (some pointers to good WiX and MSI resources).和: “WiX 快速入门” (一些指向好的 WiX 和 MSI 资源的指针)。


Step-By-Step : I'll give it a try, please try this (you might want to skip to the bottom source if you are sort of done with these preliminary steps - this is step-by-step for real and very slow to get to the action - you might get what you need straight from the WiX source):一步一步:我会试一试,请试试这个(如果你完成了这些初步步骤,你可能想跳到底部的源代码 - 这是真正的一步一步,非常慢开始行动 - 您可能会直接从 WiX 源中获得所需内容):

  1. In WiX Visual Studio solution, right click solution node at top => Add => New Project...在 WiX Visual Studio 解决方案中, right click solution node at top => Add => New Project...

  2. Expand WiX Toolset node, select v3 (provided that is the version of WiX you use)展开 WiX Toolset 节点,选择 v3(前提是你使用的 WiX 版本)

  3. Double click "C# Custom Action Project for WiX v3"双击"C# Custom Action Project for WiX v3"

  4. Right click "References" in WiX project (not in C# project) => Add Reference...右键单击 WiX 项目中的"References" (不在 C# 项目中)=> Add Reference...

  5. Go "Projects" and add a reference to the C# project (double click and OK)转到"Projects"并添加对C# project的引用(双击并确定)

  6. Do a test build.进行测试构建。 Provided there were no errors before there should be none now.前提是之前没有错误,现在应该没有错误。

  7. You should see something like "CustomAction1.CA.dll" in the build Output window.您应该会在构建输出窗口中看到类似"CustomAction1.CA.dll"的内容。 The suffix *.CA.dll is added to a win32 wrapper dll for the original managed code dll.后缀*.CA.dll被添加到原始托管代码 dll 的 win32 包装 dll 中。 All of this is handled by WiX itself - or actually the Votive Visual Studio integration for WiX - just know the difference:所有这些都由 WiX 本身处理——或者实际上是 WiX 的 Votive Visual Studio 集成——只需知道区别:

    • "CustomAction1.dll" - managed code dll. "CustomAction1.dll" - 托管代码 dll。
    • "CustomAction1.CA.dll" - native win32 wrapper dll containing the native one and several other components. "CustomAction1.CA.dll" - 包含本机一个和其他几个组件的本机 win32 包装器 dll。 Include this version in your MSI . Include this version in your MSI
  8. Add the following snippet:添加以下代码段:

     <Binary Id="CustomActions" SourceFile="$(var.CustomAction1.TargetDir)\\$(var.CustomAction1.TargetName).CA.dll" />
  9. The above should compile the actual C# dll into the MSI.以上应该将实际的 C# dll 编译到 MSI 中。 You can open the MSI in Orca and see in the Binary table.您可以在 Orca 中打开 MSI 并在二进制表中查看。

  10. It is not great, but I like to add a reference to System.Windows.Forms and use a MessageBox.Show to show a dialog from within the custom action to ensure it is running as expected.这不是很好,但我喜欢添加对System.Windows.Forms的引用,并使用MessageBox.Show从自定义操作中显示一个对话框,以确保它按预期运行。 I also add the application debugger launch command for dlls built in debug mode.我还为在调试模式下构建的 dll 添加了应用程序调试器启动命令。 That way Visual Studio will be automatically invoked (if all works correctly) so the code can be stepped through.这样 Visual Studio 将被自动调用(如果一切正常),以便代码可以被单步执行。

  11. Add the reference to "System.Windows.Forms" by right clicking the C# project's Reference node and then add "System.Windows.Forms" .参考添加到"System.Windows.Forms"通过右键单击C#项目的参考节点,然后添加"System.Windows.Forms" Also add "using System.Windows.Forms;"还要添加"using System.Windows.Forms;" to the top of the source file - see full source below.到源文件的顶部 - 请参阅下面的完整源代码。 The key is to remember to reference "System.Windows.Forms" at a project level.关键是要记住在项目级别引用"System.Windows.Forms"

  12. Now add this as test code to the custom action project's "CustomAction1" custom action code snippet (see code section towards bottom for full source):现在将此作为测试代码添加到自定义操作项目的"CustomAction1"自定义操作代码片段(请参阅底部的代码部分以获取完整源代码):

     // will launch the debugger for debug-build dlls #if DEBUG System.Diagnostics.Debugger.Launch(); #endif MessageBox.Show("hello world");
  13. To get a standard setup GUI (for others who read this), add a reference to WiXUIExtension as explained here (that is a step-by-step for creating a basic WiX project that compiles and has a GUI), and then inject this into your source:要获得标准设置 GUI(对于阅读此内容的其他人), WiXUIExtension按照此处的说明添加对WiXUIExtension的引用(这是创建可编译并具有 GUI 的基本 WiX 项目的分步步骤),然后将其注入你的消息来源:

     <UIRef Id="WixUI_Mondo" />
  14. I like to change <MediaTemplate /> to <MediaTemplate EmbedCab="yes" /> to avoid external source cab files (with this change cabs are compiled into the MSI).我喜欢将<MediaTemplate />更改为<MediaTemplate EmbedCab="yes" />以避免外部源 cab 文件(通过此更改,cabs 被编译到 MSI 中)。

  15. If you don't have any components added, you can add this to include notepad.exe in your MSI for test installation under directory INSTALLFOLDER (just a trick to install something without having source files available - a source path that should resolve on any machine) - replace the whole "TODO" section - see full source below:如果您没有添加任何组件,您可以添加它以在您的 MSI 中包含notepad.exe以在INSTALLFOLDER目录下进行测试安装(只是在没有源文件的情况下安装某些东西的技巧 - 应该在任何机器上解析的源路径) - 替换整个“TODO”部分 - 请参阅下面的完整来源:

     <Component Feature="ProductFeature"> <File Source="$(env.SystemRoot)\\notepad.exe" /> </Component>
  16. Now we need to declare the actual custom action and insert it into an installation sequence.现在我们需要声明实际的自定义操作并将其插入到安装序列中。 Let's add this underneath the previous <Binary> element :让我们在之前的<Binary> element下面添加这个:

     <CustomAction Id="CA1" BinaryKey="CustomActions" DllEntry="CustomAction1"/> <InstallUISequence> <Custom Action="CA1" After="CostFinalize" /> </InstallUISequence> <InstallExecuteSequence> <Custom Action="CA1" After="CostFinalize" /> </InstallExecuteSequence>
  17. Now build and test run the MSI.现在构建并测试运行 MSI。 You should get numerous "hello world" messages.您应该会收到许多"hello world"消息。

  18. That is the overall "heartbeat" of a C# / managed code custom action - the way I sometimes use them.这是 C#/托管代码自定义操作的整体"heartbeat" ——我有时使用它们的方式。


WiX Source Actual : And now, the synthesis - remember to replace all GUIDs! WiX 源实际:现在,合成 -记得替换所有 GUID! :

The construct: $(env.SystemRoot) - in the WiX source below - gets the environment variable %SystemRoot% - which resolves to C:\\ on most systems (to list environment variables open a cmd.exe and type set and press Enter ).构造: $(env.SystemRoot) - 在下面的 WiX 源代码中 - 获取环境变量%SystemRoot% - 在大多数系统上解析为C:\\ (列出环境变量打开cmd.exe并输入set并按Enter ) . The below source should hence compile on all systems without modifications:因此,以下源代码应无需修改即可在所有系统上编译:

<?xml version="1.0" encoding="UTF-8"?>
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi">
    <Product Id="*" Name="DemoCA" Language="1033" Version="1.0.0.0" Manufacturer="test" UpgradeCode="0adf972a-5562-4a6f-a552-dd1c16761c55">
        <Package InstallerVersion="200" Compressed="yes" InstallScope="perMachine" />

        <MajorUpgrade DowngradeErrorMessage="A newer version of [ProductName] is already installed." />
        <MediaTemplate EmbedCab="yes" />
    
    <UIRef Id="WixUI_Mondo" />

 <!-- START CUSTOM ACTION CONSTRUCTS -->
    
    <Binary Id="CustomActions" SourceFile="$(var.CustomAction1.TargetDir)\$(var.CustomAction1.TargetName).CA.dll" />

    <CustomAction Id="CA1" BinaryKey="CustomActions" DllEntry="CustomAction1"/>

    <InstallUISequence>
      <Custom Action="CA1" After="CostFinalize" />
    </InstallUISequence>

    <InstallExecuteSequence>
      <Custom Action="CA1" After="CostFinalize" />
    </InstallExecuteSequence>

 <!-- END CUSTOM ACTION CONSTRUCTS -->

    <Feature Id="ProductFeature" Title="AddingCSharpCustomActions" Level="1">
            <ComponentGroupRef Id="ProductComponents" />
        </Feature>
    </Product>

    <Fragment>
        <Directory Id="TARGETDIR" Name="SourceDir">
            <Directory Id="ProgramFilesFolder">
               <Directory Id="INSTALLFOLDER" Name="AddingCSharpCustomActions"/>
            </Directory>
        </Directory>
    </Fragment>

    <Fragment>
        <ComponentGroup Id="ProductComponents" Directory="INSTALLFOLDER">

         <Component Feature="ProductFeature">
           <File Source="$(env.SystemRoot)\notepad.exe" />
         </Component>

        </ComponentGroup>
    </Fragment>
</Wix>

Steps-in-brief : short summary of changes needed:简要步骤:所需更改的简短摘要:

  1. Set manufacturer field to something.将制造商字段设置为某物。
  2. Add and modify the custom action constructs as indicated above.添加和修改自定义操作构造,如上所示。
  3. Add the Component / File elements towards bottom replacing the "TODO" section there.向底部添加组件/文件元素,替换那里的“TODO”部分。
  4. Set the MediaTemplate to use embedded cabs as described above (optional, not necessary for the sample to work).如上所述将MediaTemplate设置为使用嵌入式MediaTemplate (可选,对于示例工作不是必需的)。

Custom Action Code : And finally the actual C# custom action test code - updated with Debugger.Launch which will launch the debugger for a debug-build DLL.自定义操作代码:最后是实际的 C# 自定义操作测试代码 - 使用 Debugger.Launch 更新,它将启动调试构建 DLL 的调试器。 You can then attach the debugger to the correct source project and step-through the code:然后,您可以将调试器附加到正确的源项目并逐步执行代码:

using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.Deployment.WindowsInstaller;
using System.Windows.Forms;

namespace CustomAction1
{
    public class CustomActions
    {
        [CustomAction]
        public static ActionResult CustomAction1(Session session)
        {

#if DEBUG
            System.Diagnostics.Debugger.Launch();
#endif

            MessageBox.Show("hello world");

            session.Log("Begin CustomAction1");

            return ActionResult.Success;
        }
    }
}

Links :链接

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM