将内容文件设置为“复制本地:始终";在 nuget 包中 [英] Set content files to "copy local : always" in a nuget package

查看:20
本文介绍了将内容文件设置为“复制本地:始终";在 nuget 包中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在构建后事件中使用此命令从项目生成了一个 nuget 包.变量 %conf% 设置为正确的配置(调试或发布),%1 是项目名称(例如MyCompany.MyProject").

I generate a nuget package from a project with this command in the post-build event. the variable %conf% is set to the right configuration (debug or release) and %1 is the project name (e.g. "MyCompany.MyProject").

nuget pack -Prop Configuration=%conf% "%1.csproj" -exclude *.sql -IncludeReferencedProjects

这个包仅供我们自己使用,永远不会在nuget上发布.它以我们的私有存储库结束.

This package is for our own usage only, it will never be published on nuget. It ends in our private repository.

在项目中,有一个文件设置为generate action : contentcopy local : always.(我的 Visual Studio 是法语,所以我不是 100% 确定翻译).我们将其命名为 importantfile.xml.

In the project, there is a file that is set to generate action : content and copy local : always. (My Visual Studio is in French, so I'm not 100% sure of the translation). Let's name it importantfile.xml.

在生成的包中,我最终得到了这样的结构:

In the generated package, I end up with this structure :

- content
    - importantfile.xml
- lib
    -net45 (.NetFramework,Version=v4.5)
        -MyCompany.MyProject.dll

这很好,我希望将importantfile.xml 部署在包中,因为,嗯,这个文件很重要!

Which is fine, I want importantfile.xml to be deployed in the package, because, well, this file is important!

当我在另一个项目中安装包时,importantfile.xml 部署在项目的根目录下.没关系.但它没有设置为copy local : always.

When I install the package in another project, importantfile.xml is deployed at the root of the project. That's OK. But it is not set to copy local : always.

在我安装包的项目中,我需要 importantfile.xml 成为copy local : always.

I need importantfile.xml to be copy local : always in this project where I install my package.

我怎样才能做到这一点?

注意事项:

可以在安装包后立即在文件上设置copy local : always,这没什么大不了的.如果包的以后更新会让这个属性保持原样,我会接受它,事实并非如此.更新包时,copy local 重置为 never(如这里).

I can set copy local : always on the file just after installing the package, that's no big deal. I would live with it if later updates of the package would let this property as-is, which is not the case. When updating the package, copy local is reset to never (as stated here).

项目文件夹中有一个 nuspec 文件,在这里:

There's a nuspec file in the project's folder, here it is :

<?xml version="1.0"?>
<package >
  <metadata>
    <id>$id$</id>
    <version>$version$</version>
    <title>$title$</title>
    <authors>$author$</authors>
    <owners>$author$</owners>
    <requireLicenseAcceptance>false</requireLicenseAcceptance>
    <description>$description$</description>
    <copyright>Copyright 2014</copyright>
    <tags>some random tags</tags>
  </metadata>
</package>

推荐答案

您可以使用 PowerShell 和 NuGet 提供的 Install.ps1 钩子.

You can use PowerShell and the Install.ps1 hook provided by NuGet.

请参阅文档.

通过 PowerShell,您必须搜索"在属性中包含您的 importantfile.xml 的内容元素.当脚本找到它时,它必须添加 Always 作为子元素.

Via PowerShell you have to 'search' for the content element which includes your importantfile.xml in an attribute. When the script found it, it has to add <CopyToOutputDirectory>Always</CopyToOutputDirectory> as a child element.

    <Content Include="importantfile.xml">
      <CopyToOutputDirectory>Always</CopyToOutputDirectory>
    </Content>

您可以在此处找到一些 PowerShell 片段.只需查看 .ps1 文件.

You can find some PowerShell snippets here. Just take a look at the .ps1 files.

您可以尝试以下操作(未测试).该文件必须命名为 Install.ps1 并复制到 tools 文件夹中:

You could try the following (not tested). The file has to be named Install.ps1 and copied into the tools folder:

param($installPath, $toolsPath, $package, $project)

# Load project XML.
$doc = New-Object System.Xml.XmlDocument
$doc.Load($project.FullName)
$namespace = 'http://schemas.microsoft.com/developer/msbuild/2003'

# Find the node containing the file. The tag "Content" may be replace by "None" depending of the case, check your .csproj file.
$xmlNode = Select-Xml "//msb:Project/msb:ItemGroup/msb:Content[@Include='importantfile.xml']" $doc -Namespace @{msb = $namespace}


#check if the node exists.
if($xmlNode -ne $null)
{
    $nodeName = "CopyToOutputDirectory"

    #Check if the property already exists, just in case.
    $property = $xmlNode.Node.SelectSingleNode($nodeName)
    if($property -eq $null)
    {
        $property = $doc.CreateElement($nodeName, $namespace)
        $property.AppendChild($doc.CreateTextNode("Always"))
        $xmlNode.Node.AppendChild($property)

        # Save changes.
        $doc.Save($project.FullName)
    }
}

您还应该检查卸载软件包时是否完全删除了所有内容.

You should also check if everything is removed completely when uninstalling the package.

Jonhhy5 的笔记

当通过 update-package 更新包时,Visual Studio 会警告项目在环境之外"被修改.这是由 $doc.Save($project.FullName) 引起的.如果我在命令完全终止之前点击重新加载 ,它有时会导致错误.诀窍是将对话框留在那里,直到过程完成,然后然后重新加载项目.

When updating the package via update-package, Visual Studio warns that the project is modified "outside the environnment". That's caused by $doc.Save($project.FullName). If I click reload before the command is fully terminated, it sometimes causes errors. The trick is to leave the dialog there until the process finishes, and then reload the projects.

这篇关于将内容文件设置为“复制本地:始终";在 nuget 包中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆