Rambler's Top100
"Knowledge itself is power"
F.Bacon
Поиск | Карта сайта | Помощь | О проекте | ТТХ  
 Сокровищница
  
 

Фильтр по датам

 
 К н и г и
 
Книжная полка
 
 
Библиотека
 
  
  
 


Поиск
 
Поиск по КС
Поиск в статьях
Яndex© + Google©
Поиск книг

 
  
Тематический каталог
Все манускрипты

 
  
Карта VCL
ОШИБКИ
Сообщения системы

 
Форумы
 
Круглый стол
Новые вопросы

 
  
Базарная площадь
Городская площадь

 
   
С Л С

 
Летопись
 
Королевские Хроники
Рыцарский Зал
Глас народа!

 
  
ТТХ
Конкурсы
Королевская клюква

 
Разделы
 
Hello, World!
Лицей

Квинтана

 
  
Сокровищница
Подземелье Магов
Подводные камни
Свитки

 
  
Школа ОБЕРОНА

 
  
Арсенальная башня
Фолианты
Полигон

 
  
Книга Песка
Дальние земли

 
  
АРХИВЫ

 
 

Сейчас на сайте присутствуют:
 
  
 
Во Флориде и в Королевстве сейчас  17:26[Войти] | [Зарегистрироваться]

Обновление программы самой программой

Евгений Бабенко
дата публикации 31-05-2005 04:41

Обновление программы самой программой
Условия работы:
Локальная сеть(Win2000, WinNt4), сервер СУБД (Oracle, SQL Server ...), множество клиентов, работающих с базой.
Постановка задачи:
Автоматическое обновление программы клиента при внесении каких либо изменений в эти программы.

У администраторов - программистов, которые впервые сталкиваются с подобной проблемой, первое желание - заставить программу саму себя обновлять. Это законное желание. Нет промежуточного программного обеспечения, которое, в свою очередь, необходимо администрировать. Проблема в том, что программа не может удалить сама себя. В свое время, столкнувшись с этой проблемой, мы у себя на предприятии решили эту проблему стандартным способом - скриптами. А недавно я обнаружил интересную особенность ОСей и сделал это способом, максимально приближенным к "идеалу".

В обоих случаях, для ускорения закачки файла с сервера, программы были перекомпилированы с использование Runtime Packages и после этого упакованы упаковщиком Exe - файлов. В итоге размеры полученных файлов не превышал 300 К.

Способ №1. Обновление с помощью VB скрипта.

Создаем на сервере папку с доступом для группы пользователей, использующих наши программы. Например \\Server1\ExeLib$ (приставка с $ позволит скрыть папку из сетевого окружения. Для того, чтобы не привязываться к конкретному имени сервера, мы создали линк с помощью Distributed File System (Dfs) : \\VirtualServer\ExeLib. Теперь физическое местоположение программ не имеет значение. При падении сервера мы просто копируем папку на другой сервер и делаем соответствующие изменения в Active Directory. Или это делает наш администратор домена. В папку ExeLib складываем exe-файлы. Там же создаем папку VBS, в которую поместим наши скрипты. Для каждого exe - файла свой скрипт. Вот пример скрипта:

Dim fs, f1, f2
Dim WshShell 

const SPatch = "\\VirtualServer\ExeLib\"
const DPatch = "C:\Client\"
const SExe = "Prog1.Exe"

Set fs = CreateObject("Scripting.FileSystemObject")
Set f1 = fs.getfile(SPatch+SExe)
Set WshShell = WScript.CreateObject("WScript.Shell") 
    
 If fs.FileExists(DPatch+SExe) Then
     Set f2 = fs.getfile(DPatch+SExe)
     If f1.DateLastModified > f2.DateLastModified Then
         fs.CopyFile SPatch+SExe, DPatch, True
     End If
Else
    fs.CopyFile SPatch+SExe, DPatch, True
End If
WshShell.Run (DPatch+SExe)

Скрипт проверяет дату последнего изменения exe - файла. Если файл локально не существует или на сервере лежит более новый файл, скрипт копирует файл на клиентский компьютер. После этого программа запускается на выполнение. На клиенте все наши программы должны лежать в одной папке. Желательно на диске C:, т.к. в домене могут встречаться машины с дисками малого размера. Для WinNt4 необходимо проверить наличие WScript.exe. У клиентов должны быть права на запуск WScript.exe. Скрипт запускается из папки \\VirtualServer\ExeLib\VBS, т.е. сервера. Это позволит нам легко модифицировать скрипт и не заботиться об обновлении самого скрипта. Например, добавить код для вызова другого скрипта, в котором мы прописываем обновление bpl - файлов.

Способ №2. Обновление программы самой программой.

Если вы запустите программу и после этого попытаетесь переименовать exe - файл, никаких возражений со стороны операционный системы не последует. Программа после такой операции продолжает работать без видимых проблем. Я, во всяко случае, проблем не обнаружил. Этот факт и используется в коде, приведенном ниже.

unit uUpdateApp;

interface
uses Classes, Windows, SysUtils, Forms;

type
  TUpdateApp=class(TThread)
  protected
     procedure Execute; override;
  end;

implementation

{ TUpdateApp }

procedure TUpdateApp.Execute;
var iFileName: String;
     iFileNameBak: String;
     iFileNameR: String;
     iLDate, iRDate: TDateTime;
begin
  Sleep(100);
  iFileName:=Application.ExeName;
  iFileNameBak:=iFileName+'.bak';
  if FileExists(iFileNameBak) then DeleteFile(iFileNameBak);
  if FileExists(iFileNameBak+'1') then DeleteFile(iFileNameBak+'1');
  iFileNameR:='\\VirtualServer\ExeLib\+ExtractFileName(iFileName);
  if not FileExists(iFileNameR) then Exit;
  iLDate:=FileDateToDateTime(FileAge(iFileName));
  iRDate:=FileDateToDateTime(FileAge(iFileNameR));
  if iLDate>=iRDate then Exit;
  if not CopyFile(PChar(iFileNameR),PChar(iFileNameBak),false) then  Exit;
  Sleep(1000);
  if not MoveFile(PChar(iFileName),PChar(iFileNameBak+'1')) then  Exit;
  Sleep(100);
  if not MoveFile(PChar(iFileNameBak),PChar(iFileName)) then  Exit;
  Sleep(100);
  if not MoveFile(PChar(iFileNameBak+'1'),PChar(iFileNameBak)) then  Exit;
end;

initialization
   TUpdateApp.Create(false);
end.

Модуль просто подключается к проекту. В секции инициализации запускаем поток. В потоке делаем следующее:
  1. Проверяем наличие bak файла, который мог остаться от предыдущего обновления и если находим - удаляем.
  2. Сравниваем дату изменения локального файла и файла, находящегося на сервере.
  3. Если необходимо обновление - копируем файл с сервера в файл "bak1". Еще один промежуточный файл используется для уменьшения вероятности нарваться на сбой в программе, когда у нас не окажется в папке файла с оригинальным названием.
    1. Переименовываем оригинал в файл с расширением "bak" .
    2. Восстанавливаем оригинал из файла "bak1"

Далее - на любителя. Можно попытаться предупредить пользователя и заставить его перезапустить программу. Или оставить все, как есть. Этот способ проверен на WinNt4 и Win2000. Прав особых пользователям не надо.




Смотрите также материалы по темам:
[Установка ПО] [Удаленная установка] [Параметры процесса/приложения]

 Обсуждение материала [ 29-08-2008 07:23 ] 21 сообщение
  
Время на сайте: GMT минус 5 часов

Если вы заметили орфографическую ошибку на этой странице, просто выделите ошибку мышью и нажмите Ctrl+Enter.
Функция может не работать в некоторых версиях броузеров.

Web hosting for this web site provided by DotNetPark (ASP.NET, SharePoint, MS SQL hosting)  
Software for IIS, Hyper-V, MS SQL. Tools for Windows server administrators. Server migration utilities  

 
© При использовании любых материалов «Королевства Delphi» необходимо указывать источник информации. Перепечатка авторских статей возможна только при согласии всех авторов и администрации сайта.
Все используемые на сайте торговые марки являются собственностью их производителей.

Яндекс цитирования