![]() |
Versionsinfo aus Ressource (Stream?) lesen
Hallo!
Ich würde gerne in meinem Install-Programm die Versionsinfo des zu installierenden EXE-Files auslesen und anzeigen, bevor ich mit der Installation beginne. Die zu installierende Exe ist als Ressource in die Exe des Install-Programms integriert. |
AW: Versionsinfo aus Ressource (Stream?) lesen
Nja, die API braucht eine Datei, also wirst du sie wohl temporär speichern müssen.
und dann ![]() Oder du mußt halt das PE-Format selber parsen, dir aus dem Stream die Resourceinfo rausholen und diese dann ebenfalls selber parsen. Alternativ kannst du mal ausprobieren, ob die VersionsInfoAPI mit RessourceLinks klar kommt. http://www.delphipraxis.net/101085-%7B$resource-html-res%7D-html-aus-ressource-webbrowser-laden.html ![]() |
AW: Versionsinfo aus Ressource (Stream?) lesen
Das wäre natürlich genau das, was ich mir gewünscht habe - werde ich gleich ausprobieren
|
AW: Versionsinfo aus Ressource (Stream?) lesen
Wie himitsu sagte, musst du die Datei erst mal speichern, bevor du die Windows API "GetFileVersionInfo" benutzt.
Oder du liest die Daten direkt selbst aus, ist nicht schwierig. Ich habe das auch mal gebraucht, hier meine Lösung:
Delphi-Quellcode:
Liefert die Version als String zurück ("w.x.y.z") und optional als Int64.
function VSFixedFileInfoToString(const VS: TVSFixedFileInfo; const AsInt64: PInt64): string;
begin with VS do begin Result := Format('%d.%d.%d.%d', [HiWord(dwFileVersionMS), // Major LoWord(dwFileVersionMS), // Minor HiWord(dwFileVersionLS), // Release LoWord(dwFileVersionLS)]); // Build if Assigned(AsInt64) then AsInt64^ := Int64(dwFileVersionMS) shl 32 or dwFileVersionLS; end; end; function GetFileVersionFromResource(const ResourceName: string; AsInt64: PInt64 = nil): string; var RS: TResourceStream; begin RS := TResourceStream.Create(HInstance, ResourceName, RT_RCDATA); try Result := GetFileVersionFromStream(RS, AsInt64); finally RS.Free; end; end; function GetFileVersionFromStream(Stream: TStream; AsInt64: PInt64 = nil): string; const Offset = 2048; VS_VERSION_INFO: WideString = 'VS_VERSION_INFO'; Signature = $FEEF04BD; var WS: WideString; PVerValue: PVSFixedFileInfo; i: Integer; begin Result := ''; if Assigned(AsInt64) then AsInt64^ := 0; // Die Versionsinfo-Daten befinden sich ziemlich am Ende einer EXE/DLL // gehe also zum Ende des Streams minus Offset (2 KB sollten genügen) Stream.Seek(-Offset, soFromEnd); // Daten in WideString kopieren i := Stream.Size - Stream.Position; SetLength(WS, i div 2 + 1); Stream.ReadBuffer(WS[Low(WS)], i); // Position der ID 'VS_VERSION_INFO' ermitteln, Signatur prüfen, Version auslesen i := Pos(VS_VERSION_INFO, WS); PVerValue := PVSFixedFileInfo(@WS[i + Length(VS_VERSION_INFO) + 2]); if (i >= Low(WS)) and (PVerValue^.dwSignature = Signature) then Result := VSFixedFileInfoToString(PVerValue^, AsInt64); end; |
AW: Versionsinfo aus Ressource (Stream?) lesen
Zitat:
Für die Erstellung meiner Setup.exe hab ich ein eigenständiges kleines Setup-Erstellungs-Programm geschrieben. Damit wird erst mal die fertige Install-Exe mit $00 zu einem Vielfachen von 1024 Bytes aufgefüllt. Dann kommt 1 KB Install-Header mit Informationen über das Installationsprogramm. Diese Informationen generiert das Setup-Erstellungs-Programm selbständig beim Erstellen der Setup.exe anhand der Dateien (Dateiversion, Erstellungsdatum usw.) und einer INI-Datei die ich vor der Erstellung anpasse. Dann kommen die Installations-Daten in Form einer oder mehrerer ZIP-Dateien. Die ZIP-Dateien werden über einen Memory-Stream direkt aus der Setup.exe in das Zielverzeichnis entpackt, wozu ich die Komponente von ZipForge verwende. Somit ist alles kompakt in einer Setup.exe. Es werden keine temporären Dateien bei der Installation benötigt. Das Erstellen einer neuen Setup.exe geht auch ganz einfach. |
AW: Versionsinfo aus Ressource (Stream?) lesen
@SMO
Danke für den Code, das wird mir einige Arbeit sparen, denn im Prinzip auf die Art, aber wahrscheinlich etwas umständlicher, wollte ich es zuletzt machen, weil die VersionsInfoAPI mit Ressourcenlinks leider nichts anfangen kann - zumindest ist es mir nicht gelungen, der die Exe so unterzujubeln. @mm1256 Ein Programm zum Erstellen des Install-Programms werde ich demnächst auch in Angriff nehmen, weil das Setup-Programm für jeden User (die zum Teil DAUs sind) ein paar individuelle Konfigurationsdaten automatisch mitbekommen muss, und da manuell jedesmal vor dem Build die entsprechenden Files zu editieren, ist recht umständlich. Wenn ich das fertig habe, könnte ich damit natürlich die Versionsinfo schon beim Erstellen des Setups ganz normal auslesen, das wäre auch eine Möglichkeit (wahrscheinlich sogar die bessere). Aber auch mit meinem Setup-Erstellungsprogramm wollte ich eigentlich Ressourcen erzeugen und ins Setup-Programm einbinden. Was wäre deiner Meinung nach der Vorteil, das anders zu machen? |
AW: Versionsinfo aus Ressource (Stream?) lesen
----
|
AW: Versionsinfo aus Ressource (Stream?) lesen
Zitat:
Der aktuelle Trend geht bei den Installationsprogrammen dazu, dass man die Setup.exe so klein wie möglich hält, und die zur Installation erforderlichen Daten erst vom WEB herunter geladen werden. Das ist der Grund, warum ich die Variante mit separater Datendatei derzeit favorisiere. Der Hintergrund ist auch verständlich. Kein User mag mehr einige Minuten warten, bis die Installation beginnt. Eher wird akzeptiert, wenn die Installation sofort beginnt, und dafür die Installation ein paar Minuten länger dauert. Darum teile ich derzeit die Daten zum Download auf mehrere Dateien auf. Während das Installationsprogramm auf User-Eingaben warten muss, oder Dateien entpackt, werden in einem separaten Thread im Hintergrund die Dateien von meinem Webserver heruntergeladen. Und das finde ich, ist das Hauptargument GEGEN eine einzige Setup.exe mit integrierten Ressourcen, egal in welcher Form. Aber, das ist eine Design-Frage die letztendlich jeder für sich entscheiden muss. Wobei ich hier der Meinung bin: Wenn man schon kein Setup von der Stange verwenden möchte/muss/kann, dann sollte man sich schon die Zeit nehmen, es gleich vernünftig zu machen. Und darum würde ich bei einem neuen Projekt in jedem Fall eine Lösung mit einer (oder mehreren vom WEB nachladbaren) Datendatei(en) bevorzugen. Eine für den User sehr viel Zeit sparende Lösung wäre, die Zwischenspeicherung "als Datei" völlig abzuschaffen. Ich teste das gerade...mit einem Memory-Stream als Zwischenspeicher/Datenpuffer. |
AW: Versionsinfo aus Ressource (Stream?) lesen
Zitat:
Bei meinem aktuellen Projekt ist das aber ohnedies kein Thema, weil jedes Setup.Exe für die Erstinstallation komplett individualisiert per Email an einen geschlossenen Benutzerkreis versandt wird (das Versenden wird dann ebenfalls in mein Setup-Erzeugungsprogramm integriert, inkl. einer Datenbank der User). |
AW: Versionsinfo aus Ressource (Stream?) lesen
Zitat:
Ohne Internet ist das natürlich schlecht. Aber dagegen kann man auch was machen: Die heruntergeladenen Dateien könnte der Benutzer ja behalten. Eine Option zum herunterladen aller Pakete und dann ist auch der Poweruser/Admin glücklich. Der für mich idealer Installer wäre im Prinzip ein kleiner Packagemanager für das Programm :wink: |
Alle Zeitangaben in WEZ +1. Es ist jetzt 14:38 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