Как написать пакет NuGet, который обновляет перенаправления привязки при обновлении ссылки на пакет?
Мы используем VS 2017 и используем пакеты NuGet по-старому. Мы еще не используем PackageReference.
Когда ссылка на пакет NuGet обновляется через диспетчер NuGet в VS, соответствующее перенаправление привязки сборки не обновляется автоматически - мы должны сделать это вручную.
Итак, я полагаю, что пакет должен позаботиться об этом через скрипт tools \ install.ps1. Теперь я думаю, что знаю, как это реализовать, но я не хочу изобретать колесо. Конечно, код уже существует где-то, но где?
осветление
Наше приложение строго подписано, и в настоящее время оно нацелено на.NET 4.5.2 (скоро будет обновлено до 4.7.2). Мы используем packages.config.
Мне нужно объяснить, что происходит. На поле три игрока:
- Инструмент - DbUpgrade
- Инструментальный плагин Api - DbUpgradeApi
- Реализация плагина Api - LogDbUpgradeProgress
Давайте проверим пакет DbUpgradeApi. 3 его версии актуальны для нас:
- Версия, по которой компилируется LogDbUpgradeProgress - A
- Версия, по которой скомпилирован DbUpgrade - B
- Последняя версия DbUpgradeApi - C
Инструмент DbUpgrade загружает плагин LogDbUpgradeProgress во время выполнения. Переадресация обязательна, потому что A - это не то же самое, что B (и, поскольку код подписан, здесь делать нечего)
Если C выше, чем B, то мы должны обновить ссылку на DbUpgradeApi в DbUpgrade. Но это должно сопровождаться обновлением перенаправления привязки. И это суть этого вопроса.
1 ответ
Итак, я только что провел последний час тестирования, и мне не нужно было делать ничего, что я считаю особенным для привязки перенаправлений к работе.
Но сначала, вы уверены, что вам нужны обязательные перенаправления? .NET Core не нуждается в этом. Если вы используете.NET Framework, но с проектом, использующим PackageReference, то он разрешается во время сборки, ваш app.config не нуждается в перенаправлении привязки в версии, проверенной вашим кодом, но при сборке и проверке файл [ваше exe-имя].config содержит перенаправления привязки. Кроме того, привязка перенаправляет значение только тогда, когда ваша сборка имеет строгие имена. Если вы не подписали свою сборку, то перенаправление привязки не требуется.
Вот шаги, которые я предпринял, чтобы создать репродукцию получения перенаправлений привязки в консольном приложении с использованием packages.config.
- Создайте пустую папку для начала. я использовал
dotnet new sln
,dotnet net nugetconfig
создать новый файл sln и nuget.config. Я отредактировал файл nuget.config, чтобы добавить папкуlocalFeed
в качестве источника и установитеglobalPackagesFolder
вgpf
таким образом, я не загрязнял свою настоящую глобальную папку пакетов тестовыми пакетами. Также создан ключ строгого имени сsn -k snk.snk
, - Создать первую тестовую библиотеку классов.
dotnet new classlib -n someLib
, Я редактировалClass1.cs
изменить имя класса наSomeClass
и добавил свойство, которое возвращает значение "Версия 1". Использовал Visual Studio для установкиsnk.snk
как ключ подписи.dotnet pack
сгенерировать V1 пакета. Я тогда отредактировалSomeClass
изменить сообщение на "Версия 2", а затем запустилdotnet pack /p:version=2.0.0
, Наконец, использовалиnuget.exe add -source localFeed someLib\bin\Debug\someLib.1.0.0.nupkg
и снова для v2 nupkg. - Создайте второй тестовый classlib,
dotnet new classlib -n anotherLib
и установите ключ подписи вsnk.snk
, Изменен Class1.cs наAnotherClass
и добавил свойствоpublic string Message => new someLib.SomeClass().Message;
, Добавил ссылку на someLib версии 1 в csproj, затем собрал, упаковал и использовал nuget.exe для добавления nupkg в localFeed. - Открыл Visual Studio и создал консольное приложение.NET Framework. Добавлена ссылка на
anotherLib
, который автоматически принес в v1 изsomeLib
, Модернизированная ссылкаsomeLib
до v2, и подтвердил, чтоpackages.config
теперь имеет перенаправление привязки дляsomeLib
, - Создал другое консольное приложение.NET Framework и сделал то же самое, что и на шаге 3, но на этот раз, используя
PackageReference
вместоpackages.config
, Проект app.config не имеет перенаправлений привязки, но файл.config в папке bin после сборки делает.
изменить: возможно, важной частью для понимания поведения перенаправления привязки NuGet/MSBuild является следующее: на обоих шагах 3 и 4, если я добавлю ссылку только на anotherLib
, тогда перенаправление привязки не создается, потому что все собирает эту ссылку someLib
ссылаться на ту же версию. Только сделав в моем консольном приложении ссылку на другую версию someLib
чем anotherLib
использует, то перенаправление привязки создается.
В приложении с плагинами сборка приложения не будет иметь перенаправления привязки, потому что это единственная сборка в командной строке компиляции, которая использует контрактный модуль плагина dll, поэтому нет необходимости в перенаправлении привязки. Когда сборка плагина построена, только плагин зависит от dll контракта плагина, поэтому опять нет конфликта, поэтому нет перенаправления привязки. Если вы скопируете все библиотеки в одну папку, то может возникнуть конфликт в требуемой версии, но это проблема времени развертывания, а не проблема времени сборки / компиляции, поэтому инструменты сборки могут не помочь. Один из способов решения этой проблемы - добавить ссылку на проект плагина из сборки приложения. Таким образом, во время компиляции инструменты сборки могут видеть, что используются две разные версии dll контракта плагина, поэтому можно создать перенаправление привязки. Это работает только при сборке приложения. Если приложение представляет собой только двоичный файл, который вы дали, то изменение перенаправлений привязки становится обязанностью времени развертывания, поэтому инструменты разработки / сборки могут не помочь.