![]() |
Updater funktion im Thread
Hallo Zusammen,
Ich habe mir einen Updater nach diesem Tutorial nachgebaut: ![]() Jetzt möchte ich gerne den Updater in mein Hauptprogramm einfügen, ohne den Willkommens und Installation Erfolgreich Tab und ohne das ich erst auf Installation Starten klicken muss. Lasse ich die sachen nun einfach weg und setze die Progressbars und Anzeigen des Updates Tabs auf eine leere Form, dann hängt sich das Programm auf und zeigt sich erst nach dem Erfolgreichen Update. mein Problem ist jetzt, versuche ich die funktion in ein Thread zu setzen funktioniert nichts. Dabei muss ich aber auch sagen, das ich den Aufbau des Threads nicht wirklich verstehe. Vielleicht gibt es hier jemand nettes, der mein Problem bzw. vorhaben anhand meiner unten beigefügten Unit erkennt und mir es vielleicht beheben könnte.
Delphi-Quellcode:
unit UpdaterETS;
interface uses Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics, Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.ExtCtrls, Vcl.StdCtrls, Vcl.ComCtrls, IdBaseComponent, IdComponent, IdTCPConnection, IdTCPClient, IdExplicitTLSClientServerBase, IdFTP, ShellAPI; type Tupdater = class(TForm) FortschrittNow: TLabel; FortschrittGesamt: TLabel; ProgressAktuell: TProgressBar; ProgressGesamt: TProgressBar; FileNumber: TLabel; DownSpeed: TLabel; FTP: TIdFTP; procedure FTPWorkBegin(ASender: TObject; AWorkMode: TWorkMode; AWorkCountMax: Int64); procedure FTPWork(ASender: TObject; AWorkMode: TWorkMode; AWorkCount: Int64); procedure FormCreate(Sender: TObject); private //procedure Connect; //procedure Disconnect; public { Public declarations } end; type ThUpdater = class(TThread) FortschrittNow: TLabel; FortschrittGesamt: TLabel; ProgressAktuell: TProgressBar; ProgressGesamt: TProgressBar; FileNumber: TLabel; DownSpeed: TLabel; FTP: TIdFTP; procedure UpdateFunc; private procedure Connect; procedure Disconnect; { Private-Deklarationen } protected procedure Execute; override; end; var updater: Tupdater; versionAK, versionNeu: string; StartTime: TDateTime; Size: Int64; CurrentFile, FileCount: Integer; UpdatingActive: Boolean = false; implementation {$R *.dfm} uses UnitConnection; function DeleteFileDir(const AFile: string): Boolean; var SH: SHFILEOPSTRUCT; begin ZeroMemory(@SH,SizeOf(SH)); with sh do begin WND:=Application.Handle; wFunc:=FO_DELETE; pFrom:=PChar(AFile+#0); fFlags:=FOF_SILENT or FOF_NOCONFIRMATION; end; Result:=ShFileOperation(sh)=0; end; procedure Thupdater.Connect; begin FTP.Host:=ConHost; FTP.Username:=ConUser; FTP.Password:=ConPass; FTP.Connect; FTP.ChangeDir(ConDir); end; procedure Thupdater.Disconnect; begin FTP.Disconnect; end; procedure Tupdater.FTPWorkBegin(ASender: TObject; AWorkMode: TWorkMode; AWorkCountMax: Int64); begin StartTime:=Now; if AWorkCountMax>0 then begin ProgressAktuell.Max:=AWorkCountMax; end else ProgressAktuell.Max:=Size; end; procedure ThUpdater.UpdateFunc; var Update, Befehl: tstringlist; I: Integer; begin CurrentFile:= i; Size:= FTP.Size(Befehl[1]); FTP.Get(Befehl[1],Befehl[2],True); ProgressGesamt.Position:=ProgressGesamt.Position+1; end; procedure ThUpdater.Execute; var Update, Befehl: tstringlist; I: Integer; begin Connect; Update:=tstringlist.Create; Befehl:=tstringlist.Create; CreateDir('tmp'); FTP.Get('updates.ini','tmp\updates.ini',true); Update.LoadFromFile('version.txt'); versionAK:=Update[0]; Update.Clear; Update.LoadFromFile('tmp\updates.ini'); versionNeu:=Update[0]; try //----------------------------------------------------------------------------------------- //FileCount bestimmen //----------------------------------------------------------------------------------------- for i := Update.Count - 1 downto 0 do begin Befehl.Clear; ExtractStrings([';'],[],PChar(Update[i]),Befehl); if Befehl[0]='get' then inc(FileCount); end; //----------------------------------------------------------------------------------------- UpdatingActive:=True; for i := Update.Count - 1 downto 0 do begin Befehl.Clear; ExtractStrings([';'],[],PChar(Update[i]),Befehl); if Befehl[0]='dir' then CreateDir(Befehl[1]); if Befehl[0]='del' then DeleteFileDir(Befehl[1]); if Befehl[0]='get' then begin CurrentFile:= i; Size:= FTP.Size(Befehl[1]); FTP.Get(Befehl[1],Befehl[2],True); ProgressGesamt.Position:=ProgressGesamt.Position+1; end; end; finally UpdatingActive:=False; Update.Free; Befehl.Free; DeleteFileDir('tmp'); Disconnect; end; end; procedure Tupdater.FormCreate(Sender: TObject); var myTh: ThUpdater; begin myTh:= Thupdater.Create(True); myTh.Resume; end; procedure Tupdater.FTPWork(ASender: TObject; AWorkMode: TWorkMode; AWorkCount: Int64); var Speed: String; TotalTime: TDateTime; H,M,Sec,MS: Word; DLTime: Double; begin if UpdatingActive=True then begin TotalTime:= Now-StartTime; DecodeTime(TotalTime,H,M,Sec,MS); Sec:=Sec+M*60+H*3600; DLTime:=Sec+MS/1000; if DLTime>0 then Speed:= FormatFloat('0.00 KB/s',(AWorkCount/1024)/DLTime); FileNumber.Caption:='Datei: ' +IntToStr(CurrentFile)+ ' von ' +IntToStr(FileCount); DownSpeed.Caption:= 'Geschwindigkeit: '+Speed; ProgressAktuell.Position:=AWorkCount; end; end; end. Gruss Jappa |
AW: Updater funktion im Thread
Zitat:
Ansonsten: Zugriffe auf visuelle Komponenten (Label, ProgressBar usw) aus einem Thread heraus müssen immer Synchronisiert werden. Beispiel
Delphi-Quellcode:
Es kann auch ohne Synchronize funktionieren, geht aber irgendwann auf irgendeinem System in die Hose und verursacht Probleme.
Synchronize(
procedure begin // hier auf die Komponente zugreifen end); |
AW: Updater funktion im Thread
Zitat:
Hab es als Update.rar am Beitragsende angehängt :D Gruss Jappa |
AW: Updater funktion im Thread
Ich bin mir nicht sicher. Aber ich glaube viele werden da gar nicht erst draufklicken.
Da könnte ja was mit mod_rewrite oder so dahinterstecken :P |
AW: Updater funktion im Thread
Zitat:
Ok, verständlich, dann werde ich es als code Zitieren :D EDIT: Code steht oben, mit Synchronize hatte ich es gestern schon versucht, aber leider klappte es auch nicht :/ |
AW: Updater funktion im Thread
Wo sind die Verbindungsdaten gespeichert?
Ich frage deshalb, weil wenn die im Programm selber liegen, dann kannst du alles was mit FTP zu tun hat direkt rausschmeißen oder dein Passwort direkt im Klatext in die Form-Caption schreiben. Ein Tutorial über so einen Updater nachzubauen ist meiner Meinung nach leichtsinnig. |
AW: Updater funktion im Thread
Die Connect-Daten sind in einer UnitConnection.pas gespeichert und werden in die Hauptform mit Uses UnitConnection; implementiert.
Delphi-Quellcode:
unit UnitConnection;
interface const ConDir='xxxx'; ConHost='xxxxx'; ConUser='xxxx'; ConPass='xxxxx'; implementation end. |
AW: Updater funktion im Thread
Ich kann dir nicht empfehlen das so zu machen wie im Video gezeigt wird.
Ich sehe da nur Probleme: - Benutzerkonten Steuerung - keine Schreibrechte - FTP geht schlecht durch Firewalls - Umgehung von "Installern" - Falsche Versionsnummern in der Systemsteuerung unter Software - evtl. große Sicherheitslücken Bei den Delphi Tagen 2010 und im Entwickler Magazin hatte ich eine alternative gezeigt: ![]() - MSI als Setup - MSP für kleine Downloads wenn Patch - BITS für Download weil in Firewall freigeschaltet - HTTPS als Download Protokoll |
AW: Updater funktion im Thread
Zitat:
Dieses Tutorial sollte vom Netz genommen werden. |
AW: Updater funktion im Thread
Zitat:
Nimm das bitte als positive Kritik wahr und fühl dich nicht angegriffen. :zwinker: |
Alle Zeitangaben in WEZ +1. Es ist jetzt 22:36 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz