Search code examples
asp.net-corenugetasp.net-core-6.0

How to address (suspected) outdated external package dependencies?


We have a .Net Core 6.0 solution and two of the projects have NuGet package references set to Azure.Storage.Blobs 12.14.1 (the latest version at the time of writing):

<ItemGroup>
   <PackageReference Include="Azure.Storage.Blobs" Version="12.14.1" />
</ItemGroup>

Today a new security scanning tool that IT are testing flagged up a "critical" issue:

System.Text.Encodings.Web Remote Code Execution (RCE) CVE-2021-26701 CVSS 9.8 Critical

Introduced through: project   
› Azure.Storage.Blobs 12.14.1 
› System.Text.Json 4.7.2 
› System.Text.Encodings.Web 4.7.1

I looked at the nuget.org page for Azure.Storage.Blobs and it shows System.Text.Json (>= 4.7.2) which implied to me (perhaps wrongly) that Blobs should work just fine with later versions of Encodings.Web:

enter image description here

I'm only referencing Azure.Storage.Blobs, so does this mean that Azure.Storage.Blobs itself is referencing an out-of-date package?

I'm keen to avoid creating my own dependency on the nested packages when they're not directly used. My research showed that NPM has a way around these issues, but I've been unable to find a NuGet-based solution.

Can anyone please explain what the solution is to ensure that my dependencies are kept secure here?


Solution

  • Central package management offers a feature called transitive pinning to manage (the versions of) transitive/indirect dependencies, without making them direct dependencies.

    From the documentation

    Starting with NuGet 6.2, you can centrally manage your dependencies in your projects with the addition of a Directory.Packages.props file and an MSBuild property.

    You can automatically override a transitive package version even without an explicit top-level by opting into a feature known as transitive pinning. This promotes a transitive dependency to a top-level dependency implicitly on your behalf when necessary.


    First enable central package management.

    Add a Directory.Packages.props file to e.g. the root of your repository (near your .sln file).

    Set ManagePackageVersionsCentrally to true.

    <ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
    

    Include any direct NuGet packages using PackageVersion tags; notice the difference with PackageReference tags.


    <Project>
      <PropertyGroup>
        <ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>    
      </PropertyGroup>  
      <ItemGroup>        
        <PackageVersion Include="Azure.Storage.Blobs" Version="12.14.1" />    
      </ItemGroup>
    </Project>
    

    Adjust your .csproj file(s) by removing the version indication from any PackageReference tags since this will now be managed centrally, although you can still override if needed.

    <Project Sdk="Microsoft.NET.Sdk">
      <ItemGroup>        
        <PackageReference Include="Azure.Storage.Blobs" />
      </ItemGroup>  
    </Project>
    

    Next enable transitive pinning by setting ManagePackageVersionsCentrally to true.

    Add below tag in a PropertyGroup.

    <ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally>
    

    Then include the concerning packages.
    In your case you can e.g. upgrade and pin System.Text.Json or System.Text.Encodings.Web to a higher version, e.g.:

    <PackageVersion Include="System.Text.Json" Version="6.0.7" />
    

    You need to figure out which version applies for your concrete case.


    Full Directory.Package.props example.
    The transitive dependencies don't need to be in a separate ItemGroup, but it might be more insightful.

    <Project>
      <PropertyGroup>
        <ManagePackageVersionsCentrally>true</ManagePackageVersionsCentrally> 
        <CentralPackageTransitivePinningEnabled>true</CentralPackageTransitivePinningEnabled>    
      </PropertyGroup>  
      <ItemGroup>        
        <PackageVersion Include="Azure.Storage.Blobs" Version="12.14.1" />    
      </ItemGroup>
      <!-- Transitive packages -->
      <ItemGroup> 
        <PackageVersion Include="System.Text.Json" Version="6.0.7" />  
      </ItemGroup>
    </Project>