Как вы разделяете внешние зависимости между решениями Visual Studio?
-
06-07-2019 - |
Вопрос
У меня есть опыт работы с Java, поэтому я привык к тому, что Maven решает все проблемы, связанные с загрузкой и поддержанием зависимостей в актуальном состоянии.Но в среде .NET я еще не нашел хорошего способа управлять всеми этими внешними зависимостями.
Основная проблема здесь заключается в том, что я массово создаю решения, и все они, как правило, зависят от одних и тех же сторонних библиотек DLL.Но я не хочу поддерживать отдельные копии каждого компонента в каждом решении.Поэтому мне нужен способ связать все различные решения с одним и тем же набором dll-файлов.
Я понял, что одним из решений может быть включение внешних библиотек в ”библиотечный проект”, который включен во все решения, и позволить другим проектам ссылаться на них через него.(Или просто убедитесь, что ссылаетесь на внешние библиотеки dll из одного и того же места для всех проектов.)
Но есть ли какие-нибудь лучшие способы сделать это?(Желательно использовать какой-нибудь подключаемый модуль для Visual Studio.)
Я просмотрел этот Диспетчер зависимостей Visual Studio и это кажется идеальным сочетанием, но пробовал ли кто-нибудь это по-настоящему?Я также видел .NET-порты Maven, но, к сожалению, я был не слишком впечатлен их состоянием.(Но, пожалуйста, продолжайте и порекомендуйте им кого-нибудь, если считаете, что я должен дать им еще одну попытку.)
Итак, каков был бы самый разумный способ решения этой проблемы?
Обновить:
Я понял , что мне нужно объяснить, что я имел в виду, говоря ссылка на один и тот же набор dll-файлов.
Одна из вещей, которой я пытаюсь добиться здесь, - избежать того, чтобы разные решения ссылались на разные версии каждого компонента.Если я обновляю компонент до новой версии, он должен быть обновлен для всех решений при следующей сборке.Это заставило бы меня убедиться, что все решения соответствуют последним компонентам.
Обновление 2: Обратите внимание, что это старый вопрос, задаваемый перед такими инструментами, как Самородок или Открытая упаковка существовал.Если кто-нибудь готов предоставить более актуальный ответ, пожалуйста, продолжайте, и я изменю принятый ответ.
Решение
Найдите какое-нибудь место для хранения сборок.Например, я храню сборки .Net core следующим образом:
<branch
> etFX\2.0527\
*<branch
> etFX\3.0\
*<branch
> etFX\3.5\
*<branch
> etFX\Silverlight 2\
*<branch
> etFX\Silverlight 3\
*
Используйте свойство ReferencePath в MSBuild (или AdditionalReferencePath в Team Build), чтобы указать вашим проектам соответствующие пути.Для простоты и удобства обслуживания у меня есть файл 1 *.targets, который знает о каждом таком каталоге;все мои проекты импортируют этот файл.
- Убедитесь, что ваша стратегия управления версиями (ветвление, объединение, локальная<-> сопоставления серверов) сохраняет относительные пути между вашими проектами и вашими ссылочными путями постоянными.
Редактировать
В ответ на обновление в вопросе позвольте мне добавить еще один шаг:
4) Убедитесь, что каждая ссылка на сборку в каждом файле проекта использует полное.Чистое строгое имя и больше ничего.
Плохой:
<Reference Include="Microsoft.SqlServer.Smo">
<SpecificVersion`>False</SpecificVersion>
<HintPath>..\..\..\..\..\..\..\Program Files (x86)\Microsoft SQL Server\100\Shared\Microsoft.SqlServer.Smo.dll</HintPath>
</Reference>
Хорошо:
<Reference Include="Microsoft.SqlServer.Smo, Version=10.0.0.0, Culture=neutral, PublicKeyToken=89845dcd8080cc91, processorArchitecture=MSIL" />
Преимущества последнего формата:
- Использование HintPath в среде совместной разработки неизбежно приведет к ситуациям, когда "это работает у меня", но не у других.Особенно ваш сервер сборки.Опуская его, вы должны корректно указать пути к ссылкам, иначе он не будет компилироваться.
- Использование слабого имени создает вероятность "ада DLL". Если вы используете сильные имена, то безопасно иметь несколько версий одной и той же сборки в ваших ссылочных путях, потому что компоновщик загрузит только те, которые соответствуют каждому критерию.Кроме того, если вы решите обновить некоторые сборки на месте (вместо добавления копий), то вы будете уведомлены о любых критических изменениях во время компиляции, а не всякий раз, когда начинают появляться жуки.
Другие советы
Помимо всего прочего, все сводится к двум вещам:
<Ол>Как указывает Ричард Берг, вы можете использовать ReferencePath и / или AdditionalReferencePath, чтобы помочь решить # 2. Если вы используете msbuild в своем процессе сборки (в нашем случае мы используем CruiseControl вместо MS Team Build), вы также можете передать ему ReferencePath в командной строке. Чтобы решить # 1, я обнаружил, что svn: externals полезно (если вы используете SVN).
Мой опыт работы с Maven заключается в том, что в большинстве случаев это излишне. Р>
Обычно у меня есть отдельная структура папок в системе управления версиями для внешних или внутренних зависимостей, и эти файлы имеют сборки в соответствии с номером сборки или версии, например
общедоступные\Внешние\библиотеки unit\2.6\
или
Общедоступные\Внутренние\библиотеки\Регистратор\5.4.312\
и внутри решений все проекты, которым необходимо использовать любую из зависимостей, просто добавляют ссылку на эти сборки в общедоступные внутренние или внешние папки.