2010-01-12 17 views
45

¿Cómo puedo recuperar la fecha de creación del ensamblado actual de .NET?Obteniendo la fecha de un ensamblado .NET

Me gustaría agregar algunas funcionalidades realmente simples donde mi aplicación deja de funcionar una semana después de la fecha de compilación del ensamblaje principal. Ya escribí el código que mata mi aplicación después de una fecha determinada. Solo necesito recuperar programáticamente la fecha de creación del ensamblado.

Respuesta

41

No creo que el montaje en sí contiene su fecha de creación. Sospecho que lo más cercano que puede obtener es la fecha de creación del archivo de ensamblaje en sí:

File.GetCreationTime(Assembly.GetExecutingAssembly().Location) 

debería hacer el truco.

EDIT:

Creo solución de Jeff Atwood, redactado por "granada" en este hilo, es probablemente la mejor manera de ir ahora.

+8

Funciona en la mayoría de los casos, pero si intenta usarlo en la solución VSTO (por ejemplo, complemento de Excel), siempre obtendrá la fecha de hoy porque los archivos de ensamblaje se copian en la carpeta AppData \ Local \ assembly antes de ejecutar el complemento dentro de Excel – surfen

+0

Tampoco funciona si lo copias en una red para descargarlo de ftp, etc. –

+1

Para ser sincero, creo que la solución de Jeff Atwood, escrita por granada en este hilo, es probablemente la mejor manera de hacerlo ahora. –

4

Esto debería funcionar:

var entryAssembly = Assembly.GetEntryAssembly(); 
var fileInfo = new FileInfo(entryAssembly.Location); 
var buildDate = fileInfo.LastWriteTime; 
22

Qué hay de malo en:

System.IO.File.GetLastWriteTime(Assembly.GetExecutingAssembly().Location); 
+0

Esto es mucho mejor porque tengo varias DLL en proceso de actualización. ¡Gracias! –

+3

Mucho mejor. 'GetCreationTime()' devuelve la hora en que se creó PRIMERO el ensamblaje. Esto no devuelve el momento en que el ensamblaje fue ÚLTIMO creado. – Jop

2

La mejor manera de hacerlo sería con un atributo personalizado que establezca en el PreBuild de su conjunto.

Y a continuación, utilice la reflexión estándar para obtener el atributo que ha creado.

Pero, por curiosidad, ¿por qué matar la aplicación después de la fecha BUILD?

+0

No necesita ser la fecha de compilación. Escogí esa fecha porque sabía que esa fecha cambiaría automáticamente a medida que se crea la aplicación. El objetivo, solo quiero permitir que la aplicación funcione durante aproximadamente una semana.También podría codificar una fecha en el código, pero tendría que cambiar esa variable a medida que se realizan cambios en la aplicación. – DenaliHardtail

+0

@Scott pero que a su manera de matar la aplicación, se evita fácilmente. –

+1

Asesinar la aplicación en función de la fecha de compilación parece una buena forma de reducir el ruido al realizar pruebas alfa en un entorno no estructurado (es decir, voluntarios de Internet). De esta forma evitará que las personas descarguen el último alfa, lo olvidarán durante 3 semanas y luego probarán y reportarán muchos errores que ya se han solucionado. Asegura que los evaluadores alfa siempre estén usando una versión reciente de la aplicación, sin tener algo que pueda introducir aún más errores en esa etapa, como una característica de actualización automática. – David

9

Tal vez este post on coding horror puede ayudar

+0

+1 ¡Eso funcionó muy bien! – devios1

+0

Este enlace está muerto. –

+0

enlace actualizado, aunque varias otras respuestas aquí hacen lo mismo o hacen referencia a esta nueva ubicación de artículos – jmlumpkin

56

El siguiente se basa en: https://blog.codinghorror.com/determining-build-date-the-hard-way/

public static class ApplicationInformation 
{ 
    /// <summary> 
    /// Gets the executing assembly. 
    /// </summary> 
    /// <value>The executing assembly.</value> 
    public static System.Reflection.Assembly ExecutingAssembly 
    { 
     get { return executingAssembly ?? (executingAssembly = System.Reflection.Assembly.GetExecutingAssembly()); } 
    } 
    private static System.Reflection.Assembly executingAssembly; 

    /// <summary> 
    /// Gets the executing assembly version. 
    /// </summary> 
    /// <value>The executing assembly version.</value> 
    public static System.Version ExecutingAssemblyVersion 
    { 
     get { return executingAssemblyVersion ?? (executingAssemblyVersion = ExecutingAssembly.GetName().Version); } 
    } 
    private static System.Version executingAssemblyVersion; 

    /// <summary> 
    /// Gets the compile date of the currently executing assembly. 
    /// </summary> 
    /// <value>The compile date.</value> 
    public static System.DateTime CompileDate 
    { 
     get 
     { 
      if (!compileDate.HasValue) 
       compileDate = RetrieveLinkerTimestamp(ExecutingAssembly.Location); 
      return compileDate ?? new System.DateTime(); 
     } 
    } 
    private static System.DateTime? compileDate; 

    /// <summary> 
    /// Retrieves the linker timestamp. 
    /// </summary> 
    /// <param name="filePath">The file path.</param> 
    /// <returns></returns> 
    /// <remarks>http://www.codinghorror.com/blog/2005/04/determining-build-date-the-hard-way.html</remarks> 
    private static System.DateTime RetrieveLinkerTimestamp(string filePath) 
    { 
     const int peHeaderOffset = 60; 
     const int linkerTimestampOffset = 8; 
     var b = new byte[2048]; 
     System.IO.FileStream s = null; 
     try 
     { 
      s = new System.IO.FileStream(filePath, System.IO.FileMode.Open, System.IO.FileAccess.Read); 
      s.Read(b, 0, 2048); 
     } 
     finally 
     { 
      if(s != null) 
       s.Close(); 
     } 
     var dt = new System.DateTime(1970, 1, 1, 0, 0, 0).AddSeconds(System.BitConverter.ToInt32(b, System.BitConverter.ToInt32(b, peHeaderOffset) + linkerTimestampOffset)); 
     return dt.AddHours(System.TimeZone.CurrentTimeZone.GetUtcOffset(dt).Hours); 
    } 
} 
+0

Esto hace un buen método de extensión en la clase de ensamblaje. –

+1

No funciona para conjuntos creados mediante reflejo (en memoria). Aquellos no tienen Ubicación (cadena vacía). –

+19

No esperaría encontrar una fecha de compilación en un ensamblaje en memoria al igual que no esperaría encontrar rayas de cebra en un pony. – grenade

1

Si estás escribiendo una aplicación para un dispositivo móvil con el framwork compacta, Assembly.Location no está disponible .

Here, encontré una alternativa:

 System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().GetName().CodeBase) 
Cuestiones relacionadas