Мини-чат
Наш опрос
Статистика
Онлайн всего: 1
Гостей: 1
Пользователей: 0
Поиск
Новое на форуме
Название : Способ отправки файлов с TClientSocket & TServerSocket | |
Название : Как получить список логических дисков? | |
Название : Как добавить приложение в автозагрузку | |
Название : Сохранение странички в файл из TWebBrowser | |
Название : Как програмно отключить и включить мышь | |
Календарь
« Ноябрь 2011 » | ||||||
Пн | Вт | Ср | Чт | Пт | Сб | Вс |
1 | 2 | 3 | 4 | 5 | 6 | |
7 | 8 | 9 | 10 | 11 | 12 | 13 |
14 | 15 | 16 | 17 | 18 | 19 | 20 |
21 | 22 | 23 | 24 | 25 | 26 | 27 |
28 | 29 | 30 |
Друзья сайта
Главная » 2011 Ноябрь 7 » Проверка обновления delphi
13:20 Проверка обновления delphi | |
Если кому будет нужна реализация обновления ПО через Интернет — привожу код простого класса для обновления. Как всегда рекомендации и ругань — приветсвуются . В принципе ничего не мешает оформить этот класс как компонент или сделать классу обвязку. Code unit BDSInetUpdater; interface Uses Classes,UrlMon,Windows,IniFiles; type // событие, сигнализирующее о том, что есть обновленная версия TOnStartUpdate=procedure (Sender:TObject; var StartUpdate:boolean) of object; // событие при проверке обновленнной версии TOnAddUpdateInfoCheck=procedure (Sender:TObject; Inf:TIniFile; var CheckResult,ContinueCheck:boolean; var DownloadURL:string) of object; // событие при проверке версии TOnUpdateVersionInfo=procedure (Sender:TObject; Version:string) of object; TInetUpdater=class private FUpdateInfoFile: string; FUpdateResultFile: string; FOnUpdateComplete: TNotifyEvent; FProductVersion:string; FProductName: string; FOnUpdateExists: TNotifyEvent; FOnStartUpdate: TOnStartUpdate; FOnAddUpInfoCheck: TOnAddUpdateInfoCheck; FOnUpdateVersionInfo: TOnUpdateVersionInfo; FInetResult:HRESULT; public Constructor Create; virtual; Destructor Destroy; override; // проверить обнвления и обновится при возможности function UpdateFile:boolean; virtual; // только проверить обновления function CheckUpdate(var DownloadURL:string):boolean; virtual; // получение кода при операциях с Инетом для разбора полетов property InetResult:HRESULT read FInetResult; // ссылка на файл с информацией об обновлениях property UpdateInfoFileURL:string read FUpdateInfoFile write FUpdateInfoFile; // временный файл для записи загруженного обновленного файла property UpdateResultFile:string read FUpdateResultFile write FUpdateResultFile; // наименование продукта property ProductName:string read FProductName write FProductName; // версия property ProductVersion:string read FProductVersion write FProductVersion; // событие, которое позволяет проверить дополнительныую информацию, используется для пользовательской проверки property OnAddUpdateInfoCheck:TOnAddUpdateInfoCheck read FOnAddUpInfoCheck write FOnAddUpInfoCheck; // событие при старте обновлений property OnUpdateStart:TOnStartUpdate read FOnStartUpdate write FOnStartUpdate; // событие при завершении обновления property OnUpdateComplete:TNotifyEvent read FOnUpdateComplete write FOnUpdateComplete; // событие о существовании обновления (т.е. информация об обновлениях загружена и новая версия найдена) property OnUpdateExists:TNotifyEvent read FOnUpdateExists write FOnUpdateExists; // событие при проверке версии property OnUpdateVersionInfo:TOnUpdateVersionInfo read FOnUpdateVersionInfo write FOnUpdateVersionInfo; end; implementation Uses SysUtils; // получить временное имя файла (тут возможна оптимизация, вместо времени можно например использовать GetTickCount()) Function GetTmpFileName:String; begin Result:=FormatDateTime('ddmmyyyyhhmmss',Now)+'.tmp'; end; { TInetUpdater } function TInetUpdater.CheckUpdate(var DownloadURL:string): boolean; var S1,TmpFileName:string; Res:HRESULT; Inf:TIniFile; CheckResult,ContinueCheck:boolean; begin Result:=False; // проверим, есть ли адрес для файла с информацией об обновлениях if Trim(FUpdateInfoFile)='' then exit; // будем файл с информацией сохранять во временный файл TmpFileName:=ExtractFilePath(ParamStr(0))+ChangeFileExt(GetTmpFileName,'.ini'); // пытаемся получить информацию об обновлениях FInetResult:=UrlDownloadToFile(nil,PChar(FUpdateInfoFile),PChar(TmpFileName),0,nil); if FInetResult=S_OK then begin // ОК, файл с информацией получили, пробуем проверить новую версию if Assigned(FOnUpdateExists) then FOnUpdateExists(Self); // предполагается, что файл с информацией об обновлениях представляет собой обычный INI файл Inf:=TIniFile.Create(TmpFileName); try CheckResult:=False; ContinueCheck:=True; // здесь мы должны проверить информацию о версии, вызывая обработчик для OnAddUpInfoCheck(). // если ContinueCheck TRUE мы должны проверить версию сами в этом классе //(в ином случае получим результат в переменной CheckResult и не будем проверять версию самостоятельно) // Если файл с информацией НЕ INI файл - можем использовать свойство Inf.FileName // для получения имени временного файла и попробовать получить данные другим методом // в обработчике OnAddUpInfoCheck() if Assigned(FOnAddUpInfoCheck) then FOnAddUpInfoCheck(Self,Inf,CheckResult,ContinueCheck,DownloadURL); // Проверяем версию самостоятельно if ContinueCheck and Inf.SectionExists(FProductName) then begin // Читаем версию S1:=Trim(Inf.ReadString(FProductName,'Version',FProductVersion)); // событие о получении информации о версии if Assigned(FOnUpdateVersionInfo) then FOnUpdateVersionInfo(Self,S1); // Если версия не такая, как у нас => есть обновления Result:=(S1<>Trim(FProductVersion)); // соответсвенно, получим URL для обновленного файла if Result then DownloadURL:=Inf.ReadString(FProductName,'File',DownloadURL); end else Result:=CheckResult; finally Inf.Free; end; end; // временный файл нам уже не нужен - удаляем его if FileExists(TmpFileName) then SysUtils.DeleteFile(TmpFileName); end; // первоначальная инициализация constructor TInetUpdater.Create; begin FUpdateInfoFile:='http://www.websitename.com/updates/verinfo.ini'; // URL к файлу с данными об обвлениях FUpdateResultFile:=''; // результирующий файл FProductName:=''; // имя продукта FProductVersion:='1.0.0.0'; // версия FOnUpdateComplete:=nil; FOnStartUpdate:=nil; FOnUpdateExists:=nil; FOnAddUpInfoCheck:=nil; FOnUpdateVersionInfo:=nil; FInetResult:=S_OK; end; destructor TInetUpdater.Destroy; begin inherited; end; // собственно обновление function TInetUpdater.UpdateFile; var Flag:boolean; DownloadURL:string; Res:HRESULT; begin Result:=False; // если мы не знаем, в какой файл сохранять обновления - они нам не нужны, уходим if Trim(FUpdateResultFile)='' then exit; DownloadURL:=''; // пробуем проверить обновления и получить URL для скачивания if CheckUpdate(DownloadURL) then begin if Trim(DownloadURL)='' then exit; // обновления есть, но вот URL для скачивания не получили - уходим Flag:=True; if Assigned(FOnStartUpdate) then FOnStartUpdate(Self,Flag); // сигнализируем, что начали процесс обновления // в переменной Flag - согласие на закачку ответ пользователя if Flag then // если закачка разрешена - качаем begin FInetResult:=UrlDownloadToFile(nil,PChar(DownloadURL),PChar(FUpdateResultFile),0,nil); Result:=FInetResult=S_OK; // если закачка обновления прошла нормально - сигнализируем, что все прошло удачно if Result and Assigned(FOnUpdateComplete) then FOnUpdateComplete(Self); end; end; end; end. Пример использования: 1) размещаем на своем сайте обычный Ini файл updates.ini со следующей информацией: Code [MyProgram] Version=1.2 File=http://www.myhomesite.com/updates/MyProgram_12_setup.exe 2) пишем примерно такой код Code Procedure MainForm.DoSelfInetUpdate; var IU:TInetUpdater; begin IU:=TInetUpdater.Create; try IU.UpdateInfoFileULR := 'http://www.myhomesite.com/updates/updates.ini'; // где лежит информация об обновлениях IU.UpdateResultFile := ChangeFileExt(ParamStr(0),'.new'); // куда ложить обновленную версию IU.ProductName := 'MyProgram'; // имя продукта IU.ProductVersion := '1.0.0 beta 123'; // текущая версия if IU.UpdateFile then // пробуем обновится begin RenameFile(ParamStr(0),ChangeFileExt(ParamStr(0),'.old'); RenameFile(IU.UpdateResultFile,ParamStr(0)); ShowMessage('Обновление прошло удачно!'); // перезапускаемся или что-то еще // ..................................................... end; finally IU.Free; end; end; | |
|
Всего комментариев: 2 | |
| |