Стратегия зависимости NuGet - PullRequest
       100

Стратегия зависимости NuGet

0 голосов
/ 22 октября 2018

Я разделяю многие из моих моделей приложений и интерфейсов на собственный пакет nuGet.

Вопрос в том, существует ли рекомендуемая стратегия при создании пакетов nuGet, касающихся определения зависимостей?

Иногда package A зависит от package B.Если я не объявляю конкретную версию package B в nuspec моего package A, то при последующем импорте пакета package A nuGet в любое решение может произойти сбой во время выполнения, так как эта зависимость не была доступна.

Иногда дерево зависимостей идет еще глубже.Но если я явно добавлю зависимости в каждый файл nuspec, то позже я смогу обнаружить конфликты версий.

Вопрос: какова рекомендуемая стратегия для решения этих проблем, если все находится под моим контролем?Должен ли я указывать зависимости только тогда, когда зависимость является чем-то «неочевидным» для проекта (например, сторонней библиотеки, которая нужна проекту, импортирующему оболочку nuGet, во время выполнения, но не использует напрямую)?Должен ли я делать это всегда, а потом решать конфликты версий по-другому?Любой хороший источник информации об этом был бы очень признателен, так как я нашел несколько примеров, но не рекомендовал определенный способ сделать что-то.

ПРИЛОЖЕННЫЙ : Я создаю пакеты nuGet с помощьювключая файл nuspec, который я редактирую вручную.Например, если у меня следующая структура решения:

ToolBelt.CityContracts.sln
-ToolBelt.CityContracts.NuGet
--ToolBelt.CityContracts.NuGet.nuspec
-ToolBelt.CityContractsOne
-ToolBelt.CityContractsTwo

В ToolBelt.CityContractsOne и ToolBelt.CityContractsTwo у меня есть исходные файлы c #.А из проекта ToolBelt.CityContracts.NuGet я добавляю ссылку на ToolBelt.CityContractsOne и ToolBelt.CityContractsTwo, чтобы убедиться, что nuspec «знает», где находятся исходные файлы.

Тогда nuspec выглядит примерно так:

<?xml version="1.0" encoding="utf-8" ?>
<package xmlns="http://schemas.microsoft.com/packaging/2010/07/nuspec.xsd">
  <metadata>
    <id>ToolBelt.CityContracts</id>
    <version>1.0.0</version>
    <authors>iberodev</authors>
    <requireLicenseAcceptance>false</requireLicenseAcceptance>
    <description>Shared Contracts</description>
    <dependencies>
      <!--here sub-dependencies that I want to drag across-->
    </dependencies>
  </metadata>
  <files>
    <file src="bin/*/netstandard2.0/ToolBelt.CityContractsOne.dll" target="lib/netstandard2.0" />
    <file src="bin/*/netstandard2.0/ToolBelt.CityContractsOne.pdb" target="lib/netstandard2.0" />
    <file src="bin/*/netstandard2.0/ToolBelt.CityContractsTwo.dll" target="lib/netstandard2.0" />
    <file src="bin/*/netstandard2.0/ToolBelt.CityContractsTwo.pdb" target="lib/netstandard2.0" />
  </files>
</package>

Пока все здесь довольно стандартно.

Затем я использую инструмент команды nuget для создания пакета nuget внутри папки с именем nupkgs с помощью команды:

nuget pack ToolBelt.CityContracts.NuGet.nuspec -Version $VERSION -OutputDirectory nupkgs -Prop Configuration=Release -NoDefaultExcludes -Verbosity detailed

ОБНОВЛЕНИЕ 1: На данный момент моя стратегия заключается в следующем.

  1. Если package A предоставляет классы / интерфейсы в своем публичном API, которые являются частью package B, то package A не добавляет зависимость к package B в своем nuspec.Поэтому проект, который добавляет package A, должен также явно добавить package B
  2. Если package A не предоставляет классы / интерфейсы в своем публичном API, которые являются частью package B, но использует их внутренне,тогда package A должен добавить зависимость к package B в своем nuspec, чтобы в проекте, который добавляет package A, также автоматически устанавливался package B, чтобы избежать риска исключительной ситуации во время выполнения.

Идея такова: если код компилируется, он должен работать без исключений времени выполнения из-за несуществующих зависимостей.

Это имеет смысл для меня, но я не могу найти надежного источника, чтобы подтвердить, что это путь.

1 Ответ

0 голосов
/ 22 октября 2018

Поскольку вы нацеливаетесь на netstandard2.0, проще создать пакет - использовать dotnet pack , а не создавать nuspec самостоятельно и использовать nuget pack.dotnet pack или msbuild /t:pack будет извлекать метаданные из csproj, и он автоматически добавляет любые PackageReference в качестве зависимости к вашему пакету.если у вас есть зависимость во время сборки, которую вы не хотите, чтобы пользователи вашего пакета получали, вы можете использовать PrivateAssets .

Рекомендуется добавлять все ваши зависимости времени выполнения в качестве зависимостей.в ваш пакет, так что любой, кто ссылается только на ваш пакет, их программа не будет аварийно завершать работу из-за отсутствия DLL.NuGet restore автоматически обрабатывает выбор версий зависимостей, когда разные пакеты запрашивают разные версии, так что вам, как правило, не стоит тратить на это слишком много времени, хотя полезно придерживаться семантического управления версиями.

Кстати, мой личный комментарийМнение заключается в том, что чем меньше пакетов, тем лучше.Существуют абсолютно веские причины, по которым реализация интерфейса может быть в другой сборке / пакете, чем определение интерфейса.Но если вы не можете обосновать это веской причиной, я бы предложил сохранить интерфейс и реализацию в одной сборке / пакете.Одна кодовая база, над которой я работал в прошлом, содержала код в нескольких пакетах в нескольких репозиториях, потому что команда думала, что некоторый общий код может быть полезен для других проектов.Но исправление ошибок означало, что вам нужно создать новую версию зависимости, затем обновить ссылку в развернутом приложении, и отладка зависимости была трудной.Это значительно замедлило разработку, когда нам пришлось работать с этим пакетом зависимостей, и в конце концов ничто другое не использовало его, так что разделять его было действительно бесполезно.

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