Compartir a través de


Compatibilidad con varias versiones de .NET

Muchas bibliotecas tienen como destino una versión específica de .NET Framework. Por ejemplo, puede tener una versión de la biblioteca específica de UWP y otra versión que aproveche las características de .NET Framework 4.6. Para dar cabida a esto, NuGet admite la colocación de varias versiones de la misma biblioteca en un único paquete.

En este artículo se describe el diseño de un paquete NuGet, independientemente de cómo se compilan el paquete o los ensamblados (es decir, el diseño es el mismo si se usan varios archivos .csproj de estilo no SDK y un archivo .nuspec personalizado o un único archivo .csproj de estilo SDK de varios destinos). Para un proyecto de estilo SDK, los destinos del paquete NuGet saben cómo se debe diseñar el paquete y automatiza la colocación de los ensamblados en las carpetas lib correctas y la creación de grupos de dependencias para cada marco de destino (TFM). Para obtener instrucciones detalladas, consulte Compatibilidad con varias versiones de .NET Framework en el archivo de proyecto.

Debe diseñar manualmente el paquete como se describe en este artículo al usar el método de directorio de trabajo basado en convención descrito en Creación de un paquete. En el caso de un proyecto de estilo SDK, se recomienda el método automatizado, pero también puede elegir diseñar manualmente el paquete como se describe en este artículo.

Estructura de carpetas de la versión del framework

Al crear un paquete que contiene solo una versión de una biblioteca o cuando se dirige a múltiples frameworks, siempre debes crear subcarpetas bajo lib utilizando nombres de frameworks que distingan entre mayúsculas y minúsculas, siguiendo la siguiente convención:

lib\{framework name}[{version}]

Para obtener una lista completa de los nombres admitidos, consulte la referencia de marcos de destino.

Nunca debe tener una versión de la biblioteca que no sea específica de un marco y que se coloque directamente en la carpeta raíz lib . (Esta funcionalidad solo se admite con packages.config). Si lo hace, la biblioteca sería compatible con cualquier marco de destino y permitir que se instale en cualquier lugar, lo que probablemente provocaría errores inesperados en tiempo de ejecución. La adición de ensamblados en la carpeta raíz (como lib\abc.dll) o subcarpetas (como lib\abc\abc.dll) está en desuso y se omite al usar el formato PackagesReference.

Por ejemplo, la siguiente estructura de carpetas admite cuatro versiones de un ensamblado que son específicas del marco:

\lib
    \net46
        \MyAssembly.dll
    \net461
        \MyAssembly.dll
    \uap
        \MyAssembly.dll
    \netcore
        \MyAssembly.dll

Para incluir fácilmente todos estos archivos al compilar el paquete, use un carácter comodín recursivo ** en la sección <files> de .nuspec:

<files>
    <file src="lib\**" target="lib/{framework name}[{version}]" />
</files>

Carpetas específicas para la arquitectura

Si tiene ensamblados específicos de la arquitectura, es decir, ensamblados independientes que tienen como destino ARM, x86 y x64, debe colocarlos en una carpeta denominada runtimes dentro de las subcarpetas denominadas {platform}-{architecture}\lib\{framework} o {platform}-{architecture}\native. Por ejemplo, la siguiente estructura de carpetas acomodaría los archivos DLL nativos y administrados destinados a Windows 10 y el uap10.0 marco:

\runtimes
    \win10-arm
        \native
        \lib\uap10.0
    \win10-x86
        \native
        \lib\uap10.0
    \win10-x64
        \native
        \lib\uap10.0

Estos ensamblados solo estarán disponibles en tiempo de ejecución, por lo que, si desea proporcionar el ensamblado correspondiente para el tiempo de compilación, también debe tener el ensamblado AnyCPU en la carpeta /ref/{tfm}.

Tenga en cuenta que NuGet siempre elige estos recursos de compilación o en tiempo de ejecución de una carpeta, por lo que si hay algunos recursos compatibles de /ref, entonces se omitirán para agregar los ensamblados en tiempo de compilación de /lib. Del mismo modo, si hay algunos recursos compatibles de /runtimes, entonces también se omitirán en tiempo de ejecución por /lib.

Consulta Crear paquetes para UWP para obtener un ejemplo de hacer referencia a estos archivos en el .nuspec manifiesto.

Consulte también empaquetado de un componente de aplicación de Microsoft Store con NuGet.

Coincidencia de versiones de ensamblaje y del marco de trabajo de destino en un proyecto

Cuando NuGet instala un paquete que tiene varias versiones de ensamblado, intenta coincidir con el nombre de marco del ensamblado con la plataforma de destino del proyecto.

Si no se encuentra una coincidencia, NuGet copia el ensamblado para la versión más alta que sea menor o igual al framework objetivo del proyecto, si está disponible. Si no se encuentra ningún ensamblado compatible, NuGet devuelve un mensaje de error adecuado.

Por ejemplo, considere la siguiente estructura de carpetas en un paquete:

\lib
    \net45
        \MyAssembly.dll
    \net461
        \MyAssembly.dll

Al instalar este paquete en un proyecto destinado a .NET Framework 4.6, NuGet instala el ensamblado en la net45 carpeta , ya que es la versión más alta disponible que es menor o igual que 4.6.

Si el proyecto tiene como destino .NET Framework 4.6.1, por otro lado, NuGet instala el ensamblado en la net461 carpeta .

Si el proyecto tiene como destino .NET Framework 4.0 y versiones anteriores, NuGet produce un mensaje de error adecuado para no encontrar el ensamblado compatible.

Agrupación de ensamblados por versión del marco

NuGet copia los ensamblados desde una sola carpeta de biblioteca del paquete. Por ejemplo, supongamos que un paquete tiene la siguiente estructura de carpetas:

\lib
    \net40
        \MyAssembly.dll (v1.0)
        \MyAssembly.Core.dll (v1.0)
    \net45
        \MyAssembly.dll (v2.0)

Cuando el paquete se instala en un proyecto que tiene como destino .NET Framework 4.5, MyAssembly.dll (v2.0) es el único ensamblado instalado. MyAssembly.Core.dll (v1.0) no está instalado porque no aparece en la net45 carpeta . NuGet se comporta de esta manera porque MyAssembly.Core.dll podría haberse combinado con la versión 2.0 de MyAssembly.dll.

Para que MyAssembly.Core.dll se instale para .NET Framework 4.5, coloque una copia en la carpeta net45.

Agrupación de ensamblados por perfil de entorno

NuGet también admite el destino de un perfil de marco específico anexando un guión y el nombre del perfil al final de la carpeta.

lib{framework name}-{profile}

Los perfiles admitidos son los siguientes:

  • client: Perfil de cliente
  • full: perfil completo
  • wp:Windows Phone
  • cf: Marco compacto

Declaración de dependencias (avanzado)

Al empaquetar un archivo de proyecto, NuGet intenta generar automáticamente las dependencias del proyecto. La información de esta sección sobre el uso de un archivo .nuspec para declarar dependencias suele ser necesaria solo para escenarios avanzados.

(Versión 2.0+) Puede declarar dependencias de paquete en el .nuspec correspondiente al marco de trabajo del proyecto de destino utilizando elementos <group> en el elemento <dependencies>. Para obtener más información, consulte el elemento de dependencias.

Cada grupo tiene un atributo denominado targetFramework y contiene cero o más <dependency> elementos. Esas dependencias se instalan juntas cuando el marco de trabajo de destino es compatible con el perfil de marco del proyecto. Consulte Plataformas de destino para ver los identificadores exactos del marco.

Se recomienda usar un grupo por Moniker de plataforma de destino (TFM) para los archivos de las carpetas lib/ y ref/ .

En el ejemplo siguiente se muestran diferentes variaciones del <group> elemento:

<dependencies>

    <group targetFramework="net472">
        <dependency id="jQuery" version="1.10.2" />
        <dependency id="WebActivatorEx" version="2.2.0" />
    </group>

    <group targetFramework="net20">
    </group>

</dependencies>

Determinar qué objetivo de NuGet utilizar

Al empaquetar bibliotecas destinadas a la Biblioteca de Clases Portátil, puede resultar complicado determinar qué objetivo de NuGet debe usar en los nombres de carpeta y el archivo .nuspec, especialmente si se apunta solo a un subconjunto de la PCL. Los siguientes recursos externos le ayudarán con esto:

Archivos de contenido y scripts de PowerShell

Advertencia

Los archivos de contenido mutable y la ejecución de scripts solo están disponibles con el packages.config formato ; están en desuso con todos los demás formatos y no deben usarse para ningún paquete nuevo.

Con packages.config, los archivos de contenido y los scripts de PowerShell se pueden agrupar mediante la plataforma de destino mediante la misma convención de carpeta dentro de las content carpetas y tools . Por ejemplo:

\content
    \net46
        \MyContent.txt
    \net461
        \MyContent461.txt
    \uap
        \MyUWPContent.html
    \netcore
\tools
    init.ps1
    \net46
        install.ps1
        uninstall.ps1
    \uap
        install.ps1
        uninstall.ps1

Si una carpeta de marco se deja vacía, NuGet no agrega referencias de ensamblado ni archivos de contenido ni ejecuta los scripts de PowerShell para ese marco.

Nota:

Dado que init.ps1 se ejecuta en el nivel de solución y no depende del proyecto, debe colocarse directamente en la tools carpeta . Se omite si se coloca en una carpeta de framework.