¿Cuáles son las diferencias entre AssemblyVersion, AssemblyFileVersion y AssemblyInformationalVersion?


Hay tres atributos de versión ensamblada. ¿Cuáles son las diferencias? ¿Está bien si uso AssemblyVersion e ignoro el resto?


MSDN dice:

  • AssemblyVersion :

    Especifica la versión del ensamblado que se atribuye.

  • AssemblyFileVersion :

    Indica a un compilador que use un número de versión específico para el recurso de versión del archivo Win32. No es necesario que la versión del archivo Win32 sea el mismo que el número de versión de la asamblea.

  • AssemblyInformationalVersion :

    Define información adicional de versión para un manifiesto de ensamblado.


Este es un seguimiento de ¿Cuáles son las mejores prácticas para el uso de atributos de Ensamblado?

Author: Ian Kemp, 2008-09-15

7 answers

AssemblyVersion

Dónde buscarán otras asambleas que hacen referencia a tu asamblea. Si este número cambia, ¡otros ensamblados tienen que actualizar sus referencias a su ensamblado! Se requiere el AssemblyVersion.

Utilizo el formato: mayor.minor . Esto resultaría en:

[assembly: AssemblyVersion("1.0")]

AssemblyFileVersion

Utilizado para el despliegue. Puede aumentar este número para cada implementación. Es utilizado por los programas de instalación. Utilícelo para marcar asambleas que tienen el mismo AssemblyVersion, pero se generan a partir de diferentes compilaciones.

En Windows, se puede ver en las propiedades del archivo.

Si es posible, que sea generado por MSBuild. El AssemblyFileVersion es opcional. Si no se da, se usa la AssemblyVersion.

Utilizo el formato: mayor.menor.revision.build, donde uso la revisión para la etapa de desarrollo (Alfa, Beta, RC y RTM), service packs y hot fixes. Esto resultaría en:

[assembly: AssemblyFileVersion("1.0.3100.1242")]

AssemblyInformationalVersion

La versión del producto del ensamblaje. Esta es la versión que usarías al hablar con los clientes o para mostrarla en tu sitio web. Esta versión puede ser una cadena, como '1.0 Release Candidate'.

El Análisis de Código se quejará de ello (CA2243) { reportado a Microsoft (no arreglado en VS2013).

El AssemblyInformationalVersion es opcional. Si no se da, se utiliza el AssemblyFileVersion.

Utilizo el formato: mayor.menor [revisión como cadena] . Esto resultaría en:

[assembly: AssemblyInformationalVersion("1.0 RC1")]
 830
Author: Rémy van Duijkeren,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-02-20 18:07:38

El control de versiones de ensamblados en.NET puede ser una perspectiva confusa dado que actualmente hay al menos tres formas de especificar una versión para su ensamblado.

Aquí están los tres principales atributos de ensamblado relacionados con la versión:

// Assembly mscorlib, Version 2.0.0.0
[assembly: AssemblyFileVersion("2.0.50727.3521")]
[assembly: AssemblyInformationalVersion("2.0.50727.3521")]
[assembly: AssemblyVersion("2.0.0.0")]

Por convención, las cuatro partes de la versión se conoce como el Versión Principal, Versión Menor, Construir, y Revisión.

El AssemblyFileVersion está destinado a identificar de manera única una construcción de la asamblea individual

Normalmente configurará manualmente el AssemblyFileVersion Mayor y Menor para reflejar la versión del ensamblado, luego incrementará la Compilación y/o Revisión cada vez que su sistema de compilación compile el ensamblado. La AssemblyFileVersion debería permitirle identificar de forma única una compilación del ensamblado, de modo que pueda usarla como punto de partida para depurar cualquier problema.

En mi proyecto actual tenemos el servidor de compilación codificar el número de lista de cambios desde nuestro repositorio de control de código fuente en las partes de Compilación y Revisión del AssemblyFileVersion. Esto nos permite mapear directamente desde un ensamblado a su código fuente, para cualquier ensamblado generado por el servidor de compilación (sin tener que usar etiquetas o ramas en el control de código fuente, o mantener manualmente ningún registro de las versiones liberadas).

Este número de versión se almacena en el recurso de versión Win32 y se puede ver al ver las páginas de propiedades del Explorador de Windows para el Asamblea.

Al CLR no le importa ni examina el AssemblyFileVersion.

El AssemblyInformationalVersion está destinado a representar la versión de todo su producto

El AssemblyInformationalVersion está destinado a permitir el versionado coherente de todo el producto, que puede consistir en muchos ensamblados que están versionados de forma independiente, tal vez con diferentes políticas de versionado, y potencialmente desarrollados por equipos dispares.

" Por ejemplo, la versión 2.0 de un producto puede contener varias asambleas; una de estas asambleas se marca como versión 1.0 ya que es un nuevo ensamblado no incluidos en la versión 1.0 de la el mismo producto. Por lo general, se establece la partes mayores y menores de esta versión número para representar la versión pública de su producto. Entonces usted aumenta las partes de compilación y revisión cada vez empaquetar un producto completo con todos sus montajes." - Jeffrey Richter, [CLR vía C #(Segunda edición)] p. 57

El CLR no se preocupa ni examina la versión de Assemblyinformation.

La AssemblyVersion es la única versión que le importa a CLR (pero le importa todo AssemblyVersion)

La AssemblyVersion es usada por el CLR para enlazar a ensamblajes fuertemente nombrados. Se almacena en la tabla de metadatos del manifiesto AssemblyDef del ensamblado construido, y en la tabla AssemblyRef de cualquier ensamblado que lo haga referencia.

Esto es muy importante, porque significa que cuando se hace referencia a un ensamblado fuertemente nombrado, se está fuertemente ligado a una versión de ensamblado específica de ese ensamblado. Toda la AssemblyVersion debe ser una coincidencia exacta para que el enlace tenga éxito. Por ejemplo, si hace referencia a la versión 1.0.0.0 de un ensamblado con nombre fuerte en tiempo de compilación, pero solo la versión 1.0.0.1 de ese ensamblado está disponible en tiempo de ejecución, el enlace fallará. (Entonces tendrá que trabajar alrededor de esto usando Redirección de Enlace de ensamblado.)

Confusión sobre si todo AssemblyVersion tiene que coincidir. (Sí, lo hace.)

Hay una pequeña confusión acerca de si toda la AssemblyVersion tiene que ser una coincidencia exacta para que se cargue un ensamblado. Algunas personas están bajo la falsa creencia de que solo las partes Mayores y Menores de la AssemblyVersion tienen que coincidir para que la unión tenga éxito. Esta es una suposición sensata, sin embargo, en última instancia es incorrecta (a partir de.NET 3.5), y es trivial verificar esto para su versión del CLR. Simplemente ejecute este código de ejemplo.

En mi máquina la segunda carga de ensamblaje falla, y las dos últimas líneas del registro de fusión dejan perfectamente claro por qué:

.NET Framework Version: 2.0.50727.3521
---
Attempting to load assembly: Rhino.Mocks, Version=3.5.0.1337, Culture=neutral, PublicKeyToken=0b3305902db7183f
Successfully loaded assembly: Rhino.Mocks, Version=3.5.0.1337, Culture=neutral, PublicKeyToken=0b3305902db7183f
---
Attempting to load assembly: Rhino.Mocks, Version=3.5.0.1336, Culture=neutral, PublicKeyToken=0b3305902db7183f
Assembly binding for  failed:
System.IO.FileLoadException: Could not load file or assembly 'Rhino.Mocks, Version=3.5.0.1336, Culture=neutral, 
PublicKeyToken=0b3305902db7183f' or one of its dependencies. The located assembly's manifest definition 
does not match the assembly reference. (Exception from HRESULT: 0x80131040)
File name: 'Rhino.Mocks, Version=3.5.0.1336, Culture=neutral, PublicKeyToken=0b3305902db7183f'

=== Pre-bind state information ===
LOG: User = Phoenix\Dani
LOG: DisplayName = Rhino.Mocks, Version=3.5.0.1336, Culture=neutral, PublicKeyToken=0b3305902db7183f
 (Fully-specified)
LOG: Appbase = [...]
LOG: Initial PrivatePath = NULL
Calling assembly : AssemblyBinding, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null.
===
LOG: This bind starts in default load context.
LOG: No application configuration file found.
LOG: Using machine configuration file from C:\Windows\Microsoft.NET\Framework64\v2.0.50727\config\machine.config.
LOG: Post-policy reference: Rhino.Mocks, Version=3.5.0.1336, Culture=neutral, PublicKeyToken=0b3305902db7183f
LOG: Attempting download of new URL [...].
WRN: Comparing the assembly name resulted in the mismatch: Revision Number
ERR: Failed to complete setup of assembly (hr = 0x80131040). Probing terminated.

Creo que la fuente de esta confusión es probablemente porque Microsoft originalmente pretendía ser un poco más indulgente en esta estricta coincidencia de la versión de ensamblaje completa, al coincidir solo en las partes de la versión Mayor y Menor:

" Al cargar un ensamblaje, el CLR encontrará automáticamente reciente versión de servicio instalada que coincide con la versión mayor/menor de la se solicita la asamblea." - Jeffrey Richter, [CLR vía C #(Segunda edición)] p. 56

Este era el comportamiento en la Beta 1 del CLR 1.0, sin embargo, esta característica se eliminó antes de la versión 1.0, y no ha logrado reaparecer en. NET 2.0:

" Nota: Acabo de describir cómo debería pensar en números de versión. Desafortunadamente, el CLR no trata versión números por aquí. [En. NET 2.0], el CLR trata un número de versión como un valor opaco, y si un ensamblado depende de la versión 1.2.3.4 de otro montaje, el CLR intenta cargar versión 1.2.3.4 solamente (a menos que redirección está en su lugar). Obstante, Microsoft tiene planes para cambiar la Cargador de CLR en una versión futura que carga lo último compilación / revisión para un mayor/menor dado versión de un ensamblado. Por ejemplo, en una versión futura del CLR, si el cargador está tratando de encontrar la versión 1.2.3.4 de un montaje y la versión 1.2.5.0 existe, el cargador con recoger automáticamente la última versión de mantenimiento. Esto será un muy bienvenido cambio al cargador - I del CLR porque uno no puede esperar." - Jeffrey Richter, [CLR vía C# (Segunda Edición)] p. 164 (Énfasis mine)

Como este cambio aún no se ha implementado, creo que es seguro asumir que Microsoft había retrocedido en esta intención, y tal vez sea demasiado tarde para cambia esto ahora. Traté de buscar en la web para averiguar qué pasó con estos planes, pero no pude encontrar ninguna respuesta. Todavía quería llegar al fondo de esto.

Así que envié un correo electrónico a Jeff Richter y le pregunté directamente - pensé que si alguien sabía lo que había pasado, sería él.

Respondió dentro de las 12 horas, un sábado por la mañana, y aclaró que el cargador. NET 1.0 Beta 1 implementó este mecanismo de 'avance automático' de recoger lo último disponible Compilación y revisión de un ensamblado, pero este comportamiento se revirtió antes de que se enviara.NET 1.0. Más tarde se intentó revivir esto, pero no lo hizo antes de que el CLR 2.0 se enviara. Luego vino Silverlight, que tuvo prioridad para el equipo de CLR, por lo que esta funcionalidad se retrasó aún más. Mientras tanto, la mayoría de las personas que estaban alrededor en los días de CLR 1.0 Beta 1 han seguido adelante, por lo que es poco probable que esto vea la luz del día, a pesar de todo el trabajo duro que ya se había puesto en ello.

El comportamiento actual, parece, ha llegado para quedarse.

También vale la pena señalar de mi discusión con Jeff que AssemblyFileVersion solo se agregó después de la eliminación del mecanismo 'roll-forward automático', porque después de 1.0 Beta 1, cualquier cambio en la AssemblyVersion fue un cambio decisivo para sus clientes, entonces no había ningún lugar para almacenar de forma segura su número de compilación. AssemblyFileVersion es ese refugio seguro, ya que nunca es examinado automáticamente por el CLR. Posiblemente es más claro de esa manera, tener dos números de versión separados, con significados separados, en lugar de tratar de hacer esa separación entre las partes Mayor/Menor (ruptura) y la Construcción/Revisión (no ruptura) de la AssemblyVersion.

La conclusión: Piense cuidadosamente cuando cambie su AssemblyVersion

La moraleja es que si estás enviando ensamblajes a los que otros desarrolladores van a hacer referencia, debes tener mucho cuidado cuando cambias (y no cambias) AssemblyVersion de esos ensamblajes. Cualquier cambio en AssemblyVersion significará que los desarrolladores de aplicaciones tendrán que volver a compilar contra la nueva versión (para actualizar esas entradas de AssemblyRef) o usar redirecciones de enlace de ensamblado para anular manualmente el enlace.

  • No cambie la versión de ensamblaje para una versión de servicio que está destinada a ser compatible con versiones anteriores.
  • Haga cambiar la versión de ensamblador para una versión que sabe que tiene rompiendo cambios.

Basta con echar otro vistazo a los atributos de la versión en mscorlib:

// Assembly mscorlib, Version 2.0.0.0
[assembly: AssemblyFileVersion("2.0.50727.3521")]
[assembly: AssemblyInformationalVersion("2.0.50727.3521")]
[assembly: AssemblyVersion("2.0.0.0")]

Tenga en cuenta que es la AssemblyFileVersion la que contiene toda la información de servicio interesante (es la parte de Revisión de esta versión la que le dice en qué Service Pack está), mientras que la AssemblyVersion está fija en una aburrida versión 2.0.0.0. Cualquier cambio en AssemblyVersion forzaría a cada aplicación. NET a hacer referencia a mscorlib.dll para volver a compilar contra el nuevo versión!

 544
Author: Daniel Fortunov,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-06-06 18:06:33

AssemblyVersion prácticamente permanece interno a. NET, mientras que AssemblyFileVersion es lo que Windows ve. Si va a las propiedades de un ensamblado que se encuentra en un directorio y cambia a la pestaña versión, el AssemblyFileVersion es lo que verá arriba. Si ordena los archivos por versión, esto es lo que usa Explorer.

El AssemblyInformationalVersion se asigna a la "Versión del producto" y está destinado a ser puramente "de uso humano".

AssemblyVersion es sin duda el más importante, pero yo no saltaría AssemblyFileVersion, tampoco. Si no proporciona AssemblyInformationalVersion, el compilador lo agrega para usted quitando la pieza" revisión " de su número de versión y dejando el mayor.menor.construir.

 39
Author: Bob King,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-04-10 21:33:15

AssemblyInformationalVersion y AssemblyFileVersion se muestran cuando se ve la información de "Versión" en un archivo a través del Explorador de Windows al ver las propiedades del archivo. Estos atributos realmente se compilan en un recurso VERSION_INFO que es creado por el compilador.

AssemblyInformationalVersion es el valor "Versión del producto". AssemblyFileVersion es el valor "File version".

El AssemblyVersion es específico para ensamblados.NET y es utilizado por el cargador de ensamblados. NET para saber qué versión de un ensamblado cargar/enlazar en tiempo de ejecución.

Fuera de estos, el único que es absolutamente requerido por.NET es el atributo AssemblyVersion. Desafortunadamente también puede causar la mayoría de los problemas cuando cambia indiscriminadamente, especialmente si eres fuerte nombrando tus asambleas.

 21
Author: Scott Dorman,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-01-24 00:08:33

Vale la pena señalar algunas otras cosas:

1) Como se muestra en el diálogo de propiedades del explorador de Windows para el archivo de ensamblaje generado, hay dos lugares llamados "Versión de archivo". El que se ve en el encabezado del diálogo muestra la AssemblyVersion, no la AssemblyFileVersion.

En la sección de información de Otra versión, hay otro elemento llamado "File Version". Aquí es donde se puede ver lo que se introdujo como el AssemblyFileVersion.

2) AssemblyFileVersion es justo texto plano. No tiene que ajustarse a las restricciones del esquema de numeración que hace AssemblyVersion (., si lo desea. Tu sistema de construcción tendrá que rellenar los tokens.

Además, no está sujeto al reemplazo de comodines que es AssemblyVersion. Si solo tiene un valor de " 3.0.1.* "in the AssemblyInfo.cs, eso es exactamente lo que se mostrará en el elemento Other version information- > File Version.

3) I sin embargo, no sé el impacto en un instalador de usar algo que no sea números de versión de archivos numéricos.

 7
Author: DavidM,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-02-21 10:40:44

Para mantener esta pregunta actualizada, vale la pena resaltar que AssemblyInformationalVersion es utilizado por NuGet y refleja la versión del paquete incluyendo cualquier sufijo de pre-lanzamiento.

Por ejemplo, una versión ensamblada de 1.0.3.* empaquetado con el asp.net core dotnet-cli

dotnet pack --version-suffix ci-7 src/MyProject

Produce un paquete con la versión 1.0.3-ci-7 que puede inspeccionar con reflexión usando:

CustomAttributeExtensions.GetCustomAttribute<AssemblyInformationalVersionAttribute>(asm);
 6
Author: KCD,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-06-23 04:51:15

Cuando se cambia la AssemblyVersion de un ensamblado, Si tiene un nombre fuerte, los ensamblados de referencia deben recompilarse, de lo contrario, ¡el ensamblaje no se carga! Si no tiene un nombre fuerte, si no se agrega explícitamente al archivo de proyecto, no se copiará al directorio de salida cuando se compile, por lo que puede perder ensamblados dependientes, especialmente después de limpiar el directorio de salida.

 2
Author: linquize,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-02-17 05:21:50