Visual Studio 2010 не может загрузить проект, в который импортированы элементы <ProjectConfiguration> - PullRequest
4 голосов
/ 08 апреля 2011

У нас есть большая (~ 800 отдельных проектов) система, которую мы переносим из старой системы сборки в Visual Studio 2010. За последние несколько недель мы вручную создавали файлы проектов Visual Studio (формат .vcxproj) для каждойиз проектов, и мы можем собрать всю систему из командной строки, используя только MSBuild.exe (WIN !!).Из-за большого количества проектов, которые необходимо преобразовать, было более эффективно создавать файлы проектов вручную, чем создавать их с помощью мастера проектов VS, поскольку наша предыдущая система сборки не использовала файлы проектов Visual Studio.

Для обслуживания и соблюдения DRY у нас большая часть конфигурации сборки (переключатели компилятора / компоновщика, пути включения и т. Д.), Преобразованные в общие файлы .targets и .props.Поскольку набор конфигураций одинаков для каждого проекта, мы также помещаем <ItemGroup>, содержащий элементы <ProjectConfiguration>, в общий файл .props, и все отлично работает для нашей автоматической ночной сборки.

К сожалению,Visual Studio 2010 IDE (окончательная версия) не может загрузить эти проекты.Когда я пытаюсь загрузить проект, я получаю сообщение об ошибке «Project [Foo] не содержит никаких настроек».Если я вручную скопирую <ItemGroup> из нашего файла .props в любой из проектов, IDE сможет загрузить проект.

При поиске я обнаружил эту проблему в MS Connect,но он помечен как «Закрыто как внешний» в ответе MS о том, что проблема исследуется для следующего публичного выпуска Visual Studio.Ручное добавление точно такого же элемента <ItemGroup> вручную к ~ 800 проектам не является приемлемым решением.Поскольку проекты строятся вне VS и работают отлично, я должен предположить, что проблема заключается в том, как Visual Studio анализирует / загружает файлы проекта.

Кто-нибудь смог найти решение этой проблемы?У кого-нибудь есть информация о том, когда / если это будет исправлено в Visual Studio?

Ответы [ 3 ]

3 голосов
/ 07 февраля 2013

Я создал обходной путь для этой проблемы. Это работает только на VS2010, а не на предыдущих версиях, поскольку требует MSBuild 4.

Сначала создайте файл с именем Configure.xslt со следующим содержимым.

<?xml version="1.0" encoding="utf-8"?>
<xsl:transform version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msbuild="http://schemas.microsoft.com/developer/msbuild/2003">
  <xsl:output version="1.0" encoding="UTF-8" indent="yes" />
  <xsl:template match="/msbuild:Project">
    <xsl:copy>
      <xsl:copy-of select="@*" />
      <xsl:apply-templates />
    </xsl:copy>
  </xsl:template>
  <xsl:template match="*">
    <xsl:copy-of select="." />
  </xsl:template>
  <xsl:template match="msbuild:ItemGroup[@Label = 'ProjectConfigurations']">
    <xsl:copy-of select="document('Default.props')/msbuild:Project/msbuild:ItemGroup[@Label = 'ProjectConfigurations']" />
  </xsl:template>
</xsl:transform>

Теперь создайте файл с именем Default.props со следующим содержимым.

<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" InitialTargets="Configure" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
  <!-- This must come first, or else VS IDE's property sheets will choke. -->
  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />

  <!-- The following configurations will be pasted into the importing project file on demand. -->
  <ItemGroup Label="ProjectConfigurations">
    <ProjectConfiguration Include="Debug|Win32">
      <Configuration>Debug</Configuration>
      <Platform>Win32</Platform>
    </ProjectConfiguration>
    <ProjectConfiguration Include="Release|Win32">
      <Configuration>Release</Configuration>
      <Platform>Win32</Platform>
    </ProjectConfiguration>
  </ItemGroup>

  <!-- XLST task which manipulates the project file and performs an in-place replacement. -->
  <Target Name="Configure" Condition="Exists('$(MSBuildThisFileDirectory)Configure.xslt')" Inputs="$(MSBuildProjectFile);$(MSBuildThisFileFullPath);$(MSBuildThisFileDirectory)Configure.xslt" Outputs="$(MSBuildProjectFile);$(OutDir)">
    <Message Text="Configuring $(MSBuildProjectFile)..." />
    <XslTransformation XslInputPath="$(MSBuildThisFileDirectory)Configure.xslt" XmlInputPaths="$(MSBuildProjectFile)" OutputPaths="$(MSBuildProjectFile).tmp" />
    <Move SourceFiles="$(MSBuildProjectFile).tmp" DestinationFiles="$(MSBuildProjectFile)" />
    <MakeDir Directories="$(OutDir)" />
  </Target>

  <!-- The remaining MSBuild imports. -->
  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
</Project>

Этот файл представляет собой отдельный «лист свойств», содержащий все общие свойства для ваших проектов, включая конфигурации. Настройте его под свои нужды. Важными частями являются узел <Target> (который создает новую цель с именем Configure) и атрибут InitialTargets в узле <Project> (который указывает MSBuild на первоначальное выполнение цели Configure).

После этого переместите Configure.xslt и Default.props в каталог по вашему выбору.

Наконец, используйте следующий шаблон во всех ваших проектах.

<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
  <!-- Change the directory below according to the path containing the above files. -->
  <Import Project="Directory\Default.props" />
  <!-- The ItemGroup below will be effectively replaced by the same ItemGroup inside Default.props. -->
  <ItemGroup Label="ProjectConfigurations" />
</Project>

В командной строке VS запустите начальный msbuild, чтобы заполнить ваш файл конфигурациями, иначе VS IDE не откроет ваш проект (из-за той же ошибки, которая изначально спровоцировала этот обходной путь). В качестве альтернативы ваш шаблон может содержать любую фиктивную конфигурацию, просто для того, чтобы в IDE можно было изначально открыть проект - эффект тот же.

Известные предостережения: Вы не можете создавать конфигурации для каждого проекта, используя IDE (поскольку IDE принудительно группирует любые конфигурации, найденные под меткой ProjectConfigurations). Вы можете создать их непосредственно в XML-данных файла проекта, и, как только вы не пометите их ProjectConfigurations, они не будут заменены или удалены.

1 голос
/ 15 июня 2012

Это возможно на VS2012, однако вы должны помнить, что порядок импорта / инициализации переменных очень важен.

Вам понадобится очень рано быть в файле проекта, на самом деле это первый элемент.Я думаю, что конфигурация может потребоваться для правильной работы системных файлов .props, и именно поэтому вы получаете эту ошибку.У меня была такая же ошибка, как и у вас на VS2012, пока я не взломал свой proj VS.

0 голосов
/ 08 апреля 2011

Ответили на этот вопрос: Можно ли переместить определения конфигурации в лист свойств с помощью MSBuild?

Вот проблема с соединением, которая утверждает, что она не попала в RTM: https://connect.microsoft.com/VisualStudio/feedback/details/514008/vcxproj-doesnt-examine-imports-to-find-project-configurations-beta-2

Я не нашел другого выхода, кроме генерации проектов. Одна хитрость заключается в том, чтобы поместить в файл проекта часовое значение, скажем, $ {CommonConfigurations}, и просто использовать функцию строкового свойства для его замены, создавая совершенно новые файлы проекта для использования в решении VS. В этом случае я бы также создал файл решения, поэтому вам не нужно вести список проектов в двух местах.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...