使用NANT脚本发布ClickOnce应用程序

时间:2014-04-24 07:11:02

标签: visual-studio-2010 msbuild clickonce nant mage

我的WPF应用程序已部署ClickOnce

Visual Studio我打开“Project properties / Publish”。

我有:

  • 发布位置
  • 发布网址
  • 签名

问题是,我必须发布每个版本以供测试和生产。 它们之间的区别是属性publish locationpublish URL。目前,我必须执行该过程两次,同时在发布生产之前更改值。

因此,按发布的结果是包含文件夹“ApplicationFiles”,application manifest文件和setup.exe的文件夹。

然后我决定使用NANT自动执行此过程。

我首先构建/发布应用程序以进行测试(这里我设置了.csproj文件位置,发布文件夹和应用程序代码)

<target name="BuildTestApplication" depends="Clean" description="Build">
  <echo message="Building..." />    
  <exec program="${msbuildExe}" workingdir="." verbose="true">
    <arg value="${projectFile}" />
    <arg value="/target:Clean;Publish" />
    <arg value="/p:PublishDir=${testPublishFolder}" />
    <arg value="/p:ApplicationVersion=${version}" />
    <arg value="/p:Publisher=&quot;${publisherName}&quot;" />
  </exec>
  <echo message="Built" />
</target>

有了这个,我发现构建没有设置发布者。另外,我需要更改提供程序URL,因为应用程序也是通过Internet安装的(不同的URL用于测试和生产)。所以我做了:

<target name="UpdateTestApplication" depends="BuildTestApplication" description="Update">
  <echo message="Updating..." />    
  <exec program="${mageExe}" workingdir="." verbose="true">
    <arg value="-Update" />
    <arg value="${testPublishFolder}/EdpClient.application" />
    <arg value="-ProviderUrl" />
    <arg value="&quot;${testPublishUrl}&quot;" />
    <arg value="-Publisher" />
    <arg value="&quot;${publisherName}&quot;" />
  </exec>
  <echo message="Updated" />
</target>

有了这个,我更新了application manifest文件的正确值(PublisherProviderUrl)......

我对生产构建也这样做,这意味着我将应用程序构建到另一个文件夹并使用不同的ProviderUrl进行更新并添加Publisher,因为它必须包含在每个mage中更新...

现在问题在于 setup.exe 文件。 Setup.exe在构建时生成,它从.csproj文件中获取值。

考虑到上述所有问题,我有三个问题:

1 有没有办法使用正确的参数构建应用程序,因此setup.exe将包含正确的值?

2 另外,如何在构建之前更新程序集信息(参数版本)?从VS发布时,我需要在“Probject properties / Application / Assembly Information

上进行更新

第3 我注意到,当从VS发布时,应用程序清单文件也会在“Application Files”文件夹中生成,而使用MSBUILD发布则不会。那是为什么?

提前感谢您和最好的问候,no9

修改

我解决了问题#2 ,如下所示:

<!--UPDATE ASSEMBLY INFORMATION BEFORE BUILD-->
  <target name="UpdateAssemblyInfo">
    <asminfo output="${assemblyInfoFile}" language="CSharp">
      <imports>
        <import namespace="System" />
        <import namespace="System.Reflection" />
        <import namespace="System.Resources" />
        <import namespace="System.Runtime.CompilerServices" />
        <import namespace="System.Runtime.InteropServices" />
        <import namespace="System.Windows" />
      </imports>
      <attributes>
        <attribute type="AssemblyTitleAttribute" value="some value" />
        <attribute type="AssemblyDescriptionAttribute" value="some value" />
        <attribute type="AssemblyConfigurationAttribute" value="some value" />
        <attribute type="AssemblyCompanyAttribute" value="some value" />
        <attribute type="AssemblyProductAttribute" value="some value" />
        <attribute type="AssemblyVersionAttribute" value="some value" />
        <attribute type="AssemblyFileVersionAttribute" value="some value" />
        <attribute type="AssemblyCopyrightAttribute" value="some value" />
        <attribute type="AssemblyTrademarkAttribute" value="some value" />
        <attribute type="AssemblyCultureAttribute" value="some value" />
        <attribute type="CLSCompliantAttribute" value="boolean value" />
        <attribute type="ComVisibleAttribute" value="boolean value" />
      </attributes>
    </asminfo>
    <echo file="${assemblyInfoFile}" append="true">
[assembly: ThemeInfo(
ResourceDictionaryLocation.None, //where theme specific resource dictionaries are located
//(used if a resource is not found in the page, 
// or application resource dictionaries)
ResourceDictionaryLocation.SourceAssembly //where the generic resource dictionary is located
//(used if a resource is not found in the page, 
// app, or any theme specific resource dictionaries)
)]
    </echo>
    <echo message="Updated" />
  </target>

含义我在构建之前覆盖Assembly.info文件并添加相关值。

问题#3是这样的:

   <!--COPY APPLICATION MANIFEST TO APPLICATIONFILES FOLDER-->
      <target name="CopyTestApplicationManifestToApplicationFilesFolder"     depends="Dependency target name" description="Update">
      <echo message="Copying..." />
      <copy 
        file="source file"
        tofile="target file" />
       <echo message="Copied" />
     </target>

1 个答案:

答案 0 :(得分:0)

我能够创建正确生成您在问题中提到的资产(setup.exe,应用程序文件夹等)的任务,而无需显式签名清单。

&#34; clean_and_publish_application&#34;任务执行以下操作

  1. 清理项目
  2. 重建项目
  3. 发布项目**这里我提供了几个参数来指定我的发布网址,BootstrapperSDKPath,应用程序版本和应用程序修订

    <target name="clean_and_publish_application" description="Build the application.">
    <echo message="Clean the build directory"/>
    <msbuild project ="${src.dir}\${target.assembly.name}.csproj">
             <arg value="/property:Configuration=Debug;outdir=bin\Debug" />
             <arg value="/t:clean" />
     </msbuild>
     <echo message="Rebuild the application"/>
     <msbuild project ="${src.dir}\${target.assembly.name}.csproj">
     <arg value="/property:Configuration=Debug;outdir=bin\Debug" />
     <arg value="/t:rebuild" />
    </msbuild>
    <echo message="Publish the application"/>
    <msbuild project ="${src.dir}\${target.assembly.name}.csproj">
    <arg value="/p:publishurl=${publish.url};
    GenerateBootstrapperSdkPath=
    C:\Program Files (x86)\Microsoft  SDKs\Windows\v8.0A\Bootstrapper\;
    ApplicationVersion=${app.version};
    ApplicationRevision=${app.revision}" />
    <arg value="/t:publish" />
    </msbuild>
    </target>
    
  4. 创建setup.exe文件需要BootstrapperSdkPath属性。我对位置进行了硬编码,因为它没有改变。 MSBuild正在该目录中查找setup.bin文件。

    ApplicationVersion属性的格式为例如2.0.0。%2a

    ApplicationRevision属性的格式为数字,例如24(这些值是我们在visual studio中看到的发布版本。我根本没有实际更新AssemplyInfo.cs文件。)

    您在.csproj文件中列出的任何属性都可以作为msbuild的参数传递。我发现此文档非常有用MSBuild Command-Line Reference

    上述任务可以完成您需要的一切EXCEPT实际上将文件复制到您的发布网址(仍在寻找答案)。所以我只是手动复制发布创建的app.config目录中的所有文件

    <target name="copy_src">
    <echo message="Copying app.config folder"/>
        <copy todir="${publish.url}" overwrite="true"  failonerror="true">
            <fileset basedir="${src.dir}\${app.config.location}">
                <include name="**" />
            </fileset>
        </copy>
    </target>
    

    我在Team City中运行这些脚本。因为我使用了发布目标,所以我不必担心签署任何清单。另外,我使用NAnt.Contrib.Tasks.dll中的msbuild任务,你可以在这里下载NAntContrib