Tengo una situación similar con las fuentes de paquetes externos e internos con proyectos referenciados en más de una solución. Acabo de hacer que esto funcione con una de nuestras bases de código hoy y parece estar funcionando con las estaciones de trabajo del desarrollador y nuestro servidor de compilación. El siguiente proceso tiene este escenario en mente (aunque no debería ser difícil adaptarse para tener la carpeta de paquetes comunes en otro lugar).
- Codebase
- Proyecto a
- Proyecto B
- Proyecto c
- Soluciones
- Solución 1
- Solución 2
- Solución 3
- Paquetes (este es el común compartido por todas las soluciones)
Respuesta actualizada a partir de NuGet 3.5.0.1484 con Visual Studio 2015 Update 3
Este proceso es un poco más fácil ahora que cuando lo aborde originalmente y pensé que era hora de actualizarlo. En general, el proceso es el mismo con menos pasos. El resultado es un proceso que resuelve o proporciona lo siguiente:
- Todo lo que necesita ser comprometido con el control del código fuente es visible y rastreado en la solución
- Instalar nuevos paquetes o actualizar paquetes usando el Administrador de paquetes en Visual Studio usará la ruta correcta del repositorio
- Después de la configuración inicial, no hackear archivos .csproj
- Sin modificaciones de la estación de trabajo del desarrollador (el código está listo para construir al finalizar la compra)
Hay algunos inconvenientes potenciales a tener en cuenta (aún no los he experimentado, YMMV). Vea la respuesta y los comentarios de Benol a continuación.
Añadir NuGet.Config
Deberá crear un archivo NuGet.Config en la raíz de la carpeta \ Solutions \. Asegúrese de que este es un archivo codificado UTF-8 que cree, si no está seguro de cómo hacerlo, use el menú Archivo-> Nuevo-> Archivo de Visual Studio y luego elija la plantilla de Archivo XML. Agregue a NuGet.Config lo siguiente:
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<config>
<add key="repositoryPath" value="$\..\Packages" />
</config>
</configuration>
Para la configuración repositoryPath, puede especificar una ruta absoluta o una ruta relativa (recomendado) utilizando el token $. El token $ se basa en la ubicación del NuGet.Config (el token $ en realidad es relativo a un nivel por debajo de la ubicación del NuGet.Config). Entonces, si tengo \ Solutions \ NuGet.Config y quiero \ Solutions \ Packages, necesitaría especificar $ \ .. \ Packages como el valor.
A continuación, tendrá que agregar una carpeta de soluciones a su solución llamada algo así como "NuGet" (haga clic con el botón derecho en su solución, Agregar-> Nueva carpeta de soluciones). Las carpetas de soluciones son carpetas virtuales que solo existen en la solución de Visual Studio y no crearán una carpeta real en la unidad (y puede hacer referencia a archivos desde cualquier lugar). Haga clic con el botón derecho en la carpeta de la solución "NuGet" y luego en Agregar-> Elemento existente y seleccione \ Solutions \ NuGet.Config.
La razón por la que estamos haciendo esto es para que sea visible en la solución y debería ayudar a garantizar que esté correctamente comprometida con el control de su código fuente. Es posible que desee realizar este paso para cada solución en su base de código que participa con sus proyectos compartidos.
Al colocar el archivo NuGet.Config en \ Solutions \ sobre cualquier archivo .sln, estamos aprovechando el hecho de que NuGet navegará recursivamente la estructura de carpetas hacia arriba desde el "directorio de trabajo actual" en busca de un archivo NuGet.Config para usar. El "directorio de trabajo actual" significa un par de cosas diferentes aquí, una es la ruta de ejecución de NuGet.exe y la otra es la ubicación del archivo .sln.
Cambiar su carpeta de paquetes
Primero, le recomiendo que revise cada una de las carpetas de su solución y elimine cualquier carpeta \ Paquetes \ que exista (primero deberá cerrar Visual Studio). Esto hace que sea más fácil ver dónde NuGet está colocando su carpeta \ Packages \ recién configurada y garantiza que cualquier enlace a la carpeta \ Packages \ errónea fallará y luego podrá repararse.
Abra su solución en Visual Studio y comience un Reconstruir todo. Ignore todos los errores de compilación que recibirá, esto se espera en este momento. Sin embargo, esto debería iniciar la función de restauración del paquete NuGet al comienzo del proceso de compilación. Verifique que su carpeta \ Solutions \ Packages \ se haya creado en el lugar que desee. Si no es así, revise su configuración.
Ahora, para cada proyecto en su solución, querrá:
- Haga clic derecho en el proyecto y seleccione Descargar proyecto
- Haga clic derecho en el proyecto y seleccione Editar your-xxx.csproj
- Encuentre referencias a \ paquetes \ y actualícelas a la nueva ubicación.
- La mayoría de estos serán referencias <HintPath>, pero no todas. Por ejemplo, WebGrease y Microsoft.Bcl.Build tendrán configuraciones de ruta separadas que deberán actualizarse.
- Guarde el archivo .csproj y luego haga clic derecho en el proyecto y seleccione Actualizar proyecto
Una vez que se hayan actualizado todos sus archivos .csproj, inicie otro Reconstruir todo y no debería tener más errores de compilación sobre referencias faltantes. En este punto ya ha terminado, y ahora tiene NuGet configurado para usar una carpeta de paquetes compartidos.
A partir de NuGet 2.7.1 (2.7.40906.75) con VStudio 2012
Lo primero a tener en cuenta es que nuget.config no controla todas las configuraciones de ruta en el sistema de paquetes nuget. Esto fue particularmente confuso de entender. Específicamente, el problema es que msbuild y Visual Studio (que llaman a msbuild) no usan la ruta en nuget.config sino que la anulan en el archivo nuget.targets.
Preparación ambiental
Primero, revisaría la carpeta de su solución y eliminaría todos los \ paquetes \ carpetas que existen. Esto ayudará a garantizar que todos los paquetes se instalen visiblemente en la carpeta correcta y ayudará a descubrir cualquier referencia de ruta incorrecta en todas sus soluciones. A continuación, me aseguraría de que tenga instalada la última extensión nuget de Visual Studio. También me aseguraría de que tenga instalado el último nuget.exe en cada solución. Abra un símbolo del sistema y vaya a cada carpeta $ (SolutionDir) \ .nuget \ y ejecute el siguiente comando:
nuget update -self
Establecer una ruta de carpeta de paquete común para NuGet
Abra cada $ (SolutionDir) \ .nuget \ NuGet.Config y agregue lo siguiente dentro de la sección <configuration>:
<config>
<add key="repositorypath" value="$\..\..\..\Packages" />
</config>
Nota: Puede usar una ruta absoluta o una ruta relativa. Tenga en cuenta que si está utilizando una ruta relativa con $ que es relativa a un nivel por debajo de la ubicación de NuGet.Config (crea que esto es un error).
Establecer una ruta de carpeta de paquete común para MSBuild y Visual Studio
Abra cada $ (SolutionDir) \ .nuget \ NuGet.targets y modifique la siguiente sección (tenga en cuenta que para los que no son Windows hay otra sección debajo):
<PropertyGroup Condition=" '$(OS)' == 'Windows_NT'">
<!-- Windows specific commands -->
<NuGetToolsPath>$([System.IO.Path]::Combine($(SolutionDir), ".nuget"))</NuGetToolsPath>
<PackagesConfig>$([System.IO.Path]::Combine($(ProjectDir), "packages.config"))</PackagesConfig>
<PackagesDir>$([System.IO.Path]::Combine($(SolutionDir), "packages"))</PackagesDir>
</PropertyGroup>
Paquetes de actualizaciónDir to be
<PackagesDir>$([System.IO.Path]::GetFullPath("$(SolutionDir)\..\Packages"))</PackagesDir>
Nota: GetFullPath resolverá nuestra ruta relativa en una ruta absoluta.
Restaurar todos los paquetes nuget en una carpeta común
Abra un símbolo del sistema y vaya a cada $ (SolutionDir) \ .nuget y ejecute el siguiente comando:
nuget restore ..\YourSolution.sln
En este punto, debe tener una sola carpeta \ packages \ en su ubicación común y ninguna dentro de ninguna de las carpetas de su solución. Si no, verifique sus caminos.
Arreglando referencias de proyectos
Abra todos los archivos .csproj en un editor de texto y encuentre referencias a \ packages y actualícelos a la ruta correcta. La mayoría de estos serán referencias <HintPath>, pero no todas. Por ejemplo, WebGrease y Microsoft.Bcl.Build tendrán configuraciones de ruta separadas que deberán actualizarse.
Construye tu solución
Abra su solución en Visual Studio y comience una compilación. Si se queja de paquetes faltantes que necesitan ser restaurados, no asuma que falta el paquete y necesita ser restaurado (el error puede ser engañoso). Podría ser una mala ruta en uno de sus archivos .csproj. Verifique eso primero antes de restaurar el paquete.
¿Tiene un error de compilación sobre paquetes faltantes?
Si ya ha verificado que las rutas en sus archivos .csproj son correctas, entonces tiene dos opciones para probar. Si este es el resultado de actualizar su código desde el control del código fuente, entonces puede intentar verificar una copia limpia y luego construirla. Esto funcionó para uno de nuestros desarrolladores y creo que había un artefacto en el archivo .suo o algo similar. La otra opción es forzar manualmente la restauración de un paquete usando la línea de comando en la carpeta .nuget de la solución en cuestión:
nuget restore ..\YourSolution.sln
$
frente de la ruta relativa. Además, la respuesta a su pregunta sobre los archivos NuGet.Config está aquí . Primero busca en .nuget, luego en todos los directorios principales, luego en el archivo 'global' en su AppData: luego los aplica en orden REVERSE (lo que sea que eso signifique).