Pergunta

How to get all resources, which copies to created binary?

I think that it is all elements like this (has CopyToOutputDirectory tag):

<ItemGroup>
 <None Include="Configs\Config.config">
   <CopyToOutputDirectory>Always</CopyToOutputDirectory>
 </None>
</ItemGroup>

and like this:

<ItemGroup>
<Resource Include="Resources\Icons\icon4.png" />
</ItemGroup>
<ItemGroup>
  <Resource Include="Resources\Icons\icon5.png" />
</ItemGroup>
<ItemGroup>
  <Resource Include="Resources\Icons\icon6.png" />
</ItemGroup>
<ItemGroup>
  <Resource Include="icon7.ico" />
</ItemGroup>
<ItemGroup>
  <Resource Include="Resources\Icons\icon8.png" />
</ItemGroup>

And I should parse all elements with tag "Resource" like this (?):

XDocument doc = XDocument.Load(filePath);
        IEnumerable<XAttribute> attr = doc.Descendants().Attributes("Resource");

And another question- how to get element before CopyToOutputDirectory tag?

P.S. if it be useful- i have folder with projects(another folders). I parse all .csproj files from this folders and generate XML file with list of resources which copied to compiled binary of each project.

Foi útil?

Solução

Project files are NOT simple XML files, they can contain logic which needs to be evaluated.

You can achieve that by using the Microsoft.Build assembly and the Microsoft.Build.Evaluation namespace.

var project = new Project(@"..\..\StackOverflow.csproj");

        var itemsToCopy = new List<ProjectItem>();

        var projectItems = project.Items;
        foreach (var projectItem in projectItems)
        {
            // e.g get all elements with CopyToOutputDirectory == "Always"
            var projectMetadata = projectItem.GetMetadata("CopyToOutputDirectory");
            if (projectMetadata != null && projectMetadata.EvaluatedValue == "Always")
                itemsToCopy.Add(projectItem);
        }

        foreach (var projectItem in itemsToCopy)
        {
            // e.g get then Include-Attribute from <None Include="Configs\Config.config">
            var evaluatedInclude = projectItem.EvaluatedInclude;
        }

        // get the resources that are not set to CopyToOutputDirectory == "Always"
        var collection = project.GetItems("Resources");
        var resources = collection.Except(itemsToCopy);
        foreach (var projectItem in resources)
        {
            // e.g get then Include-Attribute from <Resource Include="Resources\Icons\icon8.png" />
            var evaluatedInclude = projectItem.EvaluatedInclude;
        }

UPDATE

This should give a general idea how to do certain tasks with project files.

Outras dicas

You can get parent element of CopyToOutputDirectory tag via it's Parent property. Also don't forget to get resources which are copied if newer:

XDocument xdoc = XDocument.Load(filePath);
var resources = from r in xdoc.Descendants("Resource")
                select (string)r.Attribute("Include");

var copiedContent = from c in xdoc.Descendants("CopyToOutputDirectory")
                    where (string)c == "Always" || (string)c == "PreserveNewest"
                    select (string)c.Parent.Attribute("Include");
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top