Club Delphi  
    FTP   CCD     Buscar   Trucos   Trabajo   Foros

Retroceder   Foros Club Delphi > Principal > Varios
Registrarse FAQ Miembros Calendario Guía de estilo Buscar Temas de Hoy Marcar Foros Como Leídos

Respuesta
 
Herramientas Buscar en Tema Desplegado
  #1  
Antiguo 13-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Actualizar .exe

Hola!! Estoy haciendo un programa y se ejecuta en varios equipos, lo que quiero es que cuando cambie el .exe del servidor se actualicen automaticamente los .exe clientes, para esto he pensado en que junto a cada .exe haya un ficherito que ponga la version y si detecta que la version del servidor es mas nueva que la del cliente se actualice, ahora viene lo bueno, como puedo yo desde mi propio .exe copiar el otro y machacarlo?? Al estar ejecutandose me daria un error, a alguien se le ocurre alguna idea, muchas gracias!!!!!
Responder Con Cita
  #2  
Antiguo 14-11-2006
Avatar de seoane
[seoane] seoane is offline
Miembro Premium
 
Registrado: Feb 2004
Ubicación: A Coruña, España
Posts: 3.717
Poder: 18
seoane Va por buen camino
Cita:
Empezado por julian_ch
... como puedo yo desde mi propio .exe copiar el otro y machacarlo?? ...
La respuesta corta es que no puedes. No puedes modificar un ejecutable mientras estas en ejecución, así que necesitas la ayuda de alguien. Esa ayuda puede ser un programa auxiliar, un archivo .bat, o si no te importa esperar, puedes programar el reemplazo en el siguiente reinicio del equipo. A mi no se me ocurren mas ideas ...
Responder Con Cita
  #3  
Antiguo 14-11-2006
Avatar de dec
dec dec is offline
Moderador
 
Registrado: Dec 2004
Ubicación: Alcobendas, Madrid, España
Posts: 12.617
Poder: 27
dec Va camino a la famadec Va camino a la fama
Hola,

No puedes "machachar" el ejecutable mientras este esté en ejecución. Lo que se suele hacer es interponer un programa (aparte) que sea el encargado de descargar una versión actualizada de tu programa, y, cuando tu programa se cierre, sea este programa intermedio el que se encarge de borrar el antiguo ejecutable y sustituirlo por el actualizado.

Evidentemente lo expongo todo muy sintéticamente. Puedes buscar información en estos Foros sobre esta tarea de actualizar programas, puesto que se ha tratado en más de una ocasión de esto y se han dado varias soluciones al respecto.
__________________
David Esperalta
www.davidesperalta.com
Responder Con Cita
  #4  
Antiguo 14-11-2006
Avatar de dec
dec dec is offline
Moderador
 
Registrado: Dec 2004
Ubicación: Alcobendas, Madrid, España
Posts: 12.617
Poder: 27
dec Va camino a la famadec Va camino a la fama
Hola,

Eco, eeeeeeecoooo...
__________________
David Esperalta
www.davidesperalta.com

Última edición por dec fecha: 14-11-2006 a las 00:07:48.
Responder Con Cita
  #5  
Antiguo 14-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Ok, gracias por responder tan pronto, voy a ponerme a buscar..........

Salu2!!!
Responder Con Cita
  #6  
Antiguo 14-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Cita:
Empezado por dec
Puedes buscar información en estos Foros sobre esta tarea de actualizar programas, puesto que se ha tratado en más de una ocasión de esto y se han dado varias soluciones al respecto.
He encontrado este hilo en el foro http://www.clubdelphi.com/foros/showthread.php?t=32550 , pero no consigo hacerlo funcionar sin servidor ftp o http, no hay nada parecido a esto pero que no necesite ningun tipo de servidor, sino un equipo que haga de servidor???


Gracias!!!!
Responder Con Cita
  #7  
Antiguo 14-11-2006
Avatar de dec
dec dec is offline
Moderador
 
Registrado: Dec 2004
Ubicación: Alcobendas, Madrid, España
Posts: 12.617
Poder: 27
dec Va camino a la famadec Va camino a la fama
Hola,

Habría que hablarlo, pero, si un equipo hacer de servidor... ya tenemos servidor. ¿No?
__________________
David Esperalta
www.davidesperalta.com
Responder Con Cita
  #8  
Antiguo 14-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Si lo miras asi....... jeje pero es servidor de aplicaciones, no es ni web ni ftp
Responder Con Cita
  #9  
Antiguo 14-11-2006
Avatar de seoane
[seoane] seoane is offline
Miembro Premium
 
Registrado: Feb 2004
Ubicación: A Coruña, España
Posts: 3.717
Poder: 18
seoane Va por buen camino
Supongo que estamos hablando del programa "agent", si no recuerdo mal, que no lo hago En el código encontraras una función tal que así:

Código Delphi [-]
function Bajar(Url: string; Archivo: string): Boolean;

Esta función baja un archivo de un http o ftp y lo guarda en el disco duro, pues solo tienes que reemplazar esa función por la que necesites para obtener los archivos del "servidor de aplicaciones". No estoy seguro, pero si el programa esta colocado en una carpeta compartida se podría usar la instrucción Copyfile, corregirme si me equivoco, solo tendrías que tener en cuenta a la hora de hacer los archivos de inicio que donde antes era una url ahora seria la dirección del archivo en formato UNC
Responder Con Cita
  #10  
Antiguo 14-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Sasto!! de ese programa estamos hablando, mañana lo pruebo y posteo resultados, de todas formas seoane, aprobechando que estas por aqui, jeje, me podrias decir en que parte del programa "agent" configuras esto:

Paso 6: Si no lo consigue, lo retrasa hasta el proximo reinicio del equipo (No hay prisa)
Paso 7: Esperar (15 minutos o lo que se programe)

porque a mi si que me interesaria que cerrara la aplicacion, la actualizara y la volviera a abrir. Gracias!!!
Responder Con Cita
  #11  
Antiguo 14-11-2006
Avatar de seoane
[seoane] seoane is offline
Miembro Premium
 
Registrado: Feb 2004
Ubicación: A Coruña, España
Posts: 3.717
Poder: 18
seoane Va por buen camino
Vamos a destripar esta pieza de relojería
Código Delphi [-]
// Esta funcion nos indica si sobre un archivo hay alguna operacion pendiente
// de realizarse en el siguiente reinicio
function Pendiente(Archivo: string): Boolean;
var
  Buffer: PChar;
  Size: Integer;
  i: integer;
begin
  Result := FALSE;
  with TRegistry.Create do
  try
    Access := KEY_READ;
    RootKey := HKEY_LOCAL_MACHINE;
    if OpenKey('\SYSTEM\CurrentControlSet\Control\Session Manager', FALSE) then
    begin
      if ValueExists('PendingFileRenameOperations') then
      begin
        Size := GetDataSize('PendingFileRenameOperations');
        if Size > 0 then
        try
          GetMem(Buffer, Size);
          try
            Fillchar(Buffer^, Size, #0);
            ReadBinaryData('PendingFileRenameOperations', Buffer^, Size);
            for i := 0 to Size - 2 do
              if Buffer[i] = #0 then
                Buffer[i] := #13
              else
                Buffer[i] := upcase(Buffer[i]);
            if StrPos(Buffer, PChar(Uppercase(Archivo))) <> nil then
              Result := TRUE;
          finally
            FreeMem(Buffer);
          end;
        except
        end;
      end;
      CloseKey;
    end;
  finally
    Free;
  end;
end;

procedure Reemplazar(Viejo, Nuevo: string);
begin
  // Comprobamos si hay alguna operacion pendiente sobre los archivos
  if Pendiente(Viejo) or Pendiente(Nuevo) then
    Exit;
  // Si no hay archivo nuevo es que lo queremos borrar
  if Nuevo = '' then
  begin
    // Para borrarlo primero tiene que existir
    if FileExists(Viejo) then
      // Lo intentamos borrar por las buenas
      if not DeleteFile(Viejo) then
        // Si no podemos lo dejamos pendiente hasta reiniciar el equipo
        MoveFileEx(PChar(Viejo), nil, MOVEFILE_DELAY_UNTIL_REBOOT or
          MOVEFILE_REPLACE_EXISTING);
  end
  else
  begin
    // Intentamos reemplazar un archivo por otro, por las buenas
    if MoveFileEx(PChar(Nuevo), PChar(Viejo), MOVEFILE_REPLACE_EXISTING) then
    begin
      // Si lo conseguimos y el archivo se llama autorun.exe lo ejecutamos
      if Uppercase(ExtractFileName(Viejo)) = 'AUTORUN.EXE' then
        ShellExecute(0, nil, PChar(Viejo), nil, nil, SW_SHOW);
    end
    else
    begin
      // Si no conseguimos hacerlo por las buenas lo retrasamos hasta el siguiente reinicio
      MoveFileEx(PChar(Nuevo), PChar(Viejo), MOVEFILE_DELAY_UNTIL_REBOOT or
        MOVEFILE_REPLACE_EXISTING)
    end;
  end;
end;

En ningún momento intento cerrar la aplicación. Si es eso lo que quieres puedes intentar mostrar un aviso y esperar a que el usuario la cierre, cerrarla por las malas o si estas intentando actualizar tu propia aplicación hacer algo como esto (que ya puse en otro hilo):
Código Delphi [-]
procedure Actualizate(Nuevo: string);
var
  Actual: String;
  Buffer: array[0..MAX_PATH] of Char;
begin
  if GetShortPathName(PChar(ParamStr(0)),@Buffer, Sizeof(Buffer) -1) = 0 then
    Exit;
  Actual:= String(PChar(@Buffer));
  if GetShortPathName(PChar(Nuevo),@Buffer, Sizeof(Buffer) -1) = 0 then
    Exit;
  Nuevo:= String(PChar(@Buffer));
  with TStringList.Create do
  try
    Add(':BUCLE');
    Add('Del ' + Actual);
    Add('if %ERRORLEVEL% NEQ 0 goto BUCLE');
    Add('Copy ' + Nuevo + ' ' + Actual);
    Add('Start ' + Actual);
    SaveToFile(ChangeFileExt(ParamStr(0),'.bat'));    
    ShellExecute(0,nil,PChar(ChangeFileExt(ParamStr(0),'.bat')),nil,nil,SW_SHOW);
  finally
    Free;
  end;
end;

// Ejemplo de uso
Actualizate('c:\Windows\Temp\nuevo.exe');
Halt; // Lo apropiado seria usar close, o algo similar
Responder Con Cita
  #12  
Antiguo 19-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Muy bueno el programa, lo he probado y con algunas modificaciones es justo lo k necesitaba, no se si te pasara a ti tb seoane pero solo me funciona bien cuando lo ejecuto desde delphi, si es con el ejecutable no funciona, de todas formas gracias!!!!
Responder Con Cita
  #13  
Antiguo 19-11-2006
Avatar de seoane
[seoane] seoane is offline
Miembro Premium
 
Registrado: Feb 2004
Ubicación: A Coruña, España
Posts: 3.717
Poder: 18
seoane Va por buen camino
Cita:
Empezado por julian_ch
Muy bueno el programa, lo he probado y con algunas modificaciones es justo lo k necesitaba, no se si te pasara a ti tb seoane pero solo me funciona bien cuando lo ejecuto desde delphi, si es con el ejecutable no funciona, de todas formas gracias!!!!
¿que es lo que no te funciona? A mi todos mis programas me funcionan dentro y fuera del IDE.
Responder Con Cita
  #14  
Antiguo 19-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Le doy al agent.exe y no hace nada, es como si kedara bloqueado, tengo que ir al administrador de tareas de windows y terminarlo a lo bruto.
Responder Con Cita
  #15  
Antiguo 19-11-2006
Avatar de seoane
[seoane] seoane is offline
Miembro Premium
 
Registrado: Feb 2004
Ubicación: A Coruña, España
Posts: 3.717
Poder: 18
seoane Va por buen camino
Ese es el comportamiento normal. El programa esta pensado para que busque actualizaciones cada 15 minutos, en un bucle que nunca termina. Si no es ese el comportamiento que buscas, elimina el bucle y punto, entonces se ejecutara y terminara.

Es decir, donde tienes esto:
Código Delphi [-]
procedure Loop;
var
  Mutex: Cardinal;
begin
  Mutex:= CreateMutex(nil,TRUE,'{C1DEF361-AA1F-4F8F-A35E-29FA672A7E7A}');
  if  GetLastError = 0 then
  begin
    Environment:= TEnvironment.Create;
    try
      StartHook;
      Terminar:= FALSE;
      Espera:= StrToIntDef(ParamStr(1),900000);
      repeat // <--Elimina esto
        Sleep(Espera); // <--Elimina esto
        Vamos;
      until Terminar or (Espera < 5000); // <--Elimina esto
    finally
      StopHook;
      Environment.Free;
    end;
    CloseHandle(Mutex);
  end;
end;

Y puede que tengas que hacer algún ajuste mas. Dentro del IDE te funcionaba porque en los parámetros de ejecución esta puesto 0, es decir le indico un tiempo de espera 0 lo que equivale a que no queremos el bucle.

Hay que revisar el código antes de decir que algo no funciona.
Responder Con Cita
  #16  
Antiguo 19-11-2006
julian_ch julian_ch is offline
Miembro
 
Registrado: Jun 2003
Posts: 18
Poder: 0
julian_ch Va por buen camino
Gracias, tienes razon, revisandolo me acabo de dar cuenta, jeje, ya "funciona" como yo quiero
Responder Con Cita
Respuesta


Herramientas Buscar en Tema
Buscar en Tema:

Búsqueda Avanzada
Desplegado

Normas de Publicación
no Puedes crear nuevos temas
no Puedes responder a temas
no Puedes adjuntar archivos
no Puedes editar tus mensajes

El código vB está habilitado
Las caritas están habilitado
Código [IMG] está habilitado
Código HTML está deshabilitado
Saltar a Foro

Temas Similares
Tema Autor Foro Respuestas Último mensaje
Actualizar de Fb 1.0.2 a Fb 1.5 Sergio J. Firebird e Interbase 5 07-04-2006 12:03:59
Actualizar Tablas Ledian2006 Conexión con bases de datos 2 12-01-2006 14:43:01
actualizar interbase... celesdiaz Firebird e Interbase 2 10-06-2005 01:42:03
actualizar fabriciof Conexión con bases de datos 3 27-05-2004 14:58:56
actualizar un DBGrid Salomon Conexión con bases de datos 0 28-01-2004 11:33:52


La franja horaria es GMT +2. Ahora son las 14:18:17.


Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2018, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi
Copyright 1996-2007 Club Delphi