CPM(중앙 패키지 관리)
종속성 관리는 NuGet의 핵심 기능입니다. 단일 프로젝트에 대한 종속성을 쉽게 관리할 수 있습니다. 다중 프로젝트 솔루션의 종속성을 관리하는 것은 크기와 복잡성이 증가하기 시작하면 어려울 수 있습니다. 다양한 프로젝트에 대한 일반적인 종속성을 관리하는 경우 NuGet의 CPM(중앙 패키지 관리) 기능을 활용하여 단일 위치의 용이성에서 이 모든 작업을 수행할 수 있습니다.
지금까지 NuGet 패키지 종속성은 다음 두 위치 중 하나에서 관리되었습니다.
-
packages.config
- 프로젝트에서 참조하는 패키지 목록을 유지하기 위해 이전 프로젝트 형식에서 사용되는 XML 파일입니다. -
<PackageReference />
- MSBuild 프로젝트에 사용되는 XML 요소는 NuGet 패키지 종속성을 정의합니다.
NuGet 6.2시작하여 Directory.Packages.props
파일 및 MSBuild 속성을 추가하여 프로젝트의 종속성을 중앙에서 관리할 수 있습니다.
이 기능은 다음 버전부터 모든 NuGet 통합 도구에서 사용할 수 있습니다.
이전 도구는 중앙 패키지 관리 구성 및 기능을 무시합니다. 이 기능을 최대한 활용하려면 모든 빌드 환경에서 호환되는 최신 도구 버전을 사용해야 합니다.
중앙 패키지 관리는 호환되는 도구가 사용되는 한 모든 <PackageReference>
기반 MSBuild 프로젝트(레거시 CSPROJ포함)에 적용됩니다.
중앙 패키지 관리를 활성화하기
중앙 패키지 관리를 시작하려면 리포지토리의 루트에 Directory.Packages.props
파일을 만들고 MSBuild 속성 ManagePackageVersionsCentrally
true
설정해야 합니다.
수동으로 만들거나 dotnet CLI를 사용할 수 있습니다.
dotnet new packagesprops
그런 다음 패키지 ID 및 버전을 정의하는 <PackageVersion />
요소를 사용하여 프로젝트에 필요한 각 패키지 버전을 정의합니다.
<Project>
<PropertyGroup>
<ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
</PropertyGroup>
<ItemGroup>
<PackageVersion Include="Newtonsoft.Json" Version="13.0.1" />
</ItemGroup>
</Project>
그런 다음 각 프로젝트에 대해 <PackageReference />
정의하지만 해당 <PackageVersion />
항목에서 버전이 달성되므로 Version
특성을 생략합니다.
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net6.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Newtonsoft.Json" />
</ItemGroup>
</Project>
이제 중앙 패키지 관리를 사용하고 중앙 위치에서 버전을 관리합니다.
중앙 패키지 관리 규칙
Directory.Packages.props
파일에는 리포지토리의 디렉터리 및 해당 컨텍스트에 있는 위치에 대한 여러 규칙이 있습니다. 간단히 하기 위해 지정된 프로젝트에 대해 하나의 Directory.Packages.props
파일만 평가됩니다.
즉, 리포지토리에 여러 Directory.Packages.props
파일이 있는 경우 프로젝트의 디렉터리에 가장 가까운 파일이 평가됩니다. 이렇게 하면 리포지토리의 다양한 수준에서 추가 제어할 수 있습니다.
다음은 다음 리포지토리 구조를 고려하는 예제입니다.
Repository
|-- Directory.Packages.props
|-- Solution1
|-- Directory.Packages.props
|-- Project1
|-- Solution2
|-- Project2
- Project1은
Repository\Solution1\
디렉터리의Directory.Packages.props
파일을 평가하고 원하는 경우 다음 파일을 수동으로 가져와야 합니다.<Project> <Import Project="$([MSBuild]::GetPathOfFileAbove(Directory.Packages.props, $(MSBuildThisFileDirectory)..))" /> <ItemGroup> <PackageVersion Update="Newtonsoft.Json" Version="12.0.1" /> </ItemGroup> </Project>
- Project2는
Repository\
디렉터리의Directory.Packages.props
파일을 평가합니다.
참고: MSBuild는 사용자 대신 각 Directory.Packages.props
를 자동으로 가져오지 않으며, 프로젝트에 가장 가까운 첫 번째 것만 가져옵니다. 여러 개의 Directory.Packages.props
가 있는 경우, 루트 Directory.Packages.props
은 자동으로 가져오지 않으므로 부모 항목은 수동으로 가져와야 합니다.
시작
리포지토리를 완전히 온보딩하려면 다음 단계를 수행하는 것이 좋습니다.
- 중앙에서 정의된 패키지 버전을 선언하고 MSBuild 속성
ManagePackageVersionsCentrally
true
설정하는Directory.Packages.props
리포지토리의 루트에 새 파일을 만듭니다. -
<PackageVersion />
항목을 귀하의Directory.Packages.props
에서 선언하십시오. - 프로젝트 파일에서
Version
특성 없이<PackageReference />
항목을 선언합니다.
중앙 패키지 관리의 모양에 대한 자세한 내용은 샘플 리포지토리참조하세요.
전이적 고정
의존성 고정이라는 기능을 활성화하여 명시적 최상위 <PackageReference />
없이도 전이적 패키지 버전을 자동으로 재정의할 수 있습니다. 이렇게 하면 필요한 경우 전이적 종속성을 사용자 대신 암시적으로 최상위 종속성으로 승격합니다.
패키지를 전이적으로 고정할 때 다운그레이드가 허용됩니다. 종속성에서 요청한 것보다 낮은 버전으로 패키지를 고정하려고 하면 복원하면 NU1109 오류가 발생합니다.
프로젝트나 Directory.Packages.props
, Directory.Build.props
가져오기 파일에서 MSBuild 속성 CentralPackageTransitivePinningEnabled
를 true
로 설정하여 이 기능을 활성화할 수 있습니다.
<PropertyGroup>
<CentralPackageTransitivePinningEnabled>true</CentralPackageTransitivePinningEnabled>
</PropertyGroup>
전이적 고정 및 패키징
패키지가 전이적으로 고정되면 프로젝트는 종속성에서 요청한 것보다 높은 값을 사용합니다. 프로젝트에서 패키지를 만드는 경우 패키지가 작동하는지 확인하기 위해 NuGet은 전이적으로 고정된 종속성을 nuspec의 명시적 종속성으로 승격합니다.
다음 예제에서는 PackageA 1.0.0
PackageB 1.0.0
대한 종속성을 가합니다.
<Project>
<ItemGroup>
<PackageVersion Include="PackageA" Version="1.0.0" />
<PackageVersion Include="PackageB" Version="2.0.0" />
</ItemGroup>
</Project>
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<CentralPackageTransitivePinningEnabled>true</CentralPackageTransitivePinningEnabled>
<TargetFramework>net6.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="PackageA" />
</ItemGroup>
</Project>
pack 명령을 사용하여 패키지를 만들면 두 패키지가 모두 종속성 그룹에 표시됩니다.
<group targetFramework="net6.0">
<dependency id="PackageA" version="6.12.1" exclude="Build,Analyzers" />
<dependency id="PackageB" version="6.12.1" exclude="Build,Analyzers" />
</group>
이 때문에 라이브러리를 작성할 때는 예상하지 못한 종속성이 발생할 수 있으므로 전이적 고정을 신중하게 평가해야 합니다.
패키지 버전 재정의
<PackageReference />
항목의 VersionOverride
속성을 사용하여 개별 패키지 버전을 재정의할 수 있습니다. 이것은 중앙에서 정의된 모든 <PackageVersion />
를 재정의합니다.
<Project>
<ItemGroup>
<PackageVersion Include="PackageA" Version="1.0.0" />
<PackageVersion Include="PackageB" Version="2.0.0" />
</ItemGroup>
</Project>
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net6.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="PackageA" VersionOverride="3.0.0" />
</ItemGroup>
</Project>
프로젝트 또는 Directory.Packages.props
또는 Directory.Build.props
가져오기 파일에서 MSBuild 속성 CentralPackageVersionOverrideEnabled
을 false
로 설정하여 이 기능을 비활성화할 수 있습니다.
<PropertyGroup>
<CentralPackageVersionOverrideEnabled>false</CentralPackageVersionOverrideEnabled>
</PropertyGroup>
이 기능을 사용하지 않도록 설정하면 <PackageReference />
항목에 VersionOverride
지정하면 복원 시 기능이 비활성화되었음을 나타내는 오류가 발생합니다.
중앙 패키지 관리 비활성화
특정 프로젝트에 대해 중앙 패키지 관리를 사용하지 않도록 설정하려면 MSBuild 속성 ManagePackageVersionsCentrally
false
설정하여 사용하지 않도록 설정할 수 있습니다.
<PropertyGroup>
<ManagePackageVersionsCentrally>false</ManagePackageVersionsCentrally>
</PropertyGroup>
전역 패키지 참조
메모
이 기능은 Visual Studio 2022 17.4 이상, .NET SDK 7.0.100.preview7 이상 및 NuGet 6.4 이상에서만 사용할 수 있습니다.
전역 패키지 참조는 리포지토리의 모든 프로젝트에서 패키지를 사용하도록 지정하는 데 사용됩니다. 여기에는 버전 관리를 수행하는 패키지, 빌드 확장 또는 모든 프로젝트에 필요한 다른 패키지가 포함됩니다. 전역 패키지 참조는 다음 메타데이터를 사용하여 PackageReference 항목 그룹에 추가됩니다.
IncludeAssets="Runtime;Build;Native;contentFiles;Analyzers"
이렇게 하면 패키지가 개발 종속성으로만 사용되고 컴파일 시간 어셈블리 참조를 방지할 수 있습니다.PrivateAssets="All"
이렇게 하면 전역 패키지 참조가 다운스트림 종속성에 의해 사용되지 않습니다.
GlobalPackageReference
항목은 리포지토리 내 모든 프로젝트에서 사용될 수 있도록 Directory.Packages.props
에 보관해야 합니다.
<Project>
<ItemGroup>
<GlobalPackageReference Include="Nerdbank.GitVersioning" Version="3.5.109" />
</ItemGroup>
</Project>
여러 패키지 원본을 사용하는 경우 경고
중앙 패키지 관리를 사용하는 경우 구성에 둘 이상의 패키지 원본이 정의된 경우 NU1507
경고가 표시됩니다. 이 경고를 해결하려면 패키지 원본을 패키지 원본 매핑 매핑하거나 단일 패키지 원본을 지정합니다.
There are 3 package sources defined in your configuration. When using central package management, please map your package sources with package source mapping (https://aka.ms/nuget-package-source-mapping) or specify a single package source.