V0.2.0.0: Working copy

git-svn-id: https://svn.code.sf.net/p/lazarus-ccr/svn@5641 8e941d3f-bd1b-0410-a28a-d453659cc2b4
This commit is contained in:
gbamber
2017-01-14 07:43:26 +00:00
parent 770575537e
commit 7568085be6
8 changed files with 204 additions and 131 deletions

View File

@ -10,7 +10,7 @@
<IsPartOfProject Value="True"/>
<EditorIndex Value="4"/>
<CursorPos X="33" Y="27"/>
<UsageCount Value="28"/>
<UsageCount Value="29"/>
<Loaded Value="True"/>
</Unit0>
<Unit1>
@ -19,9 +19,9 @@
<ComponentName Value="mainform"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
<TopLine Value="53"/>
<CursorPos X="29" Y="72"/>
<UsageCount Value="28"/>
<TopLine Value="88"/>
<CursorPos X="43" Y="108"/>
<UsageCount Value="29"/>
<Loaded Value="True"/>
<LoadedDesigner Value="True"/>
</Unit1>
@ -37,14 +37,14 @@
<Filename Value="..\ulazautoupdate.pas"/>
<IsVisibleTab Value="True"/>
<EditorIndex Value="3"/>
<TopLine Value="130"/>
<CursorPos X="58" Y="134"/>
<TopLine Value="334"/>
<CursorPos X="34" Y="358"/>
<ExtraEditorCount Value="1"/>
<ExtraEditor1>
<EditorIndex Value="-1"/>
<WindowIndex Value="-1"/>
<TopLine Value="-1"/>
<CursorPos X="-1" Y="-1"/>
<IsVisibleTab Value="True"/>
<WindowIndex Value="1"/>
<TopLine Value="1743"/>
<CursorPos X="63" Y="1782"/>
</ExtraEditor1>
<UsageCount Value="14"/>
<Loaded Value="True"/>
@ -103,123 +103,123 @@
<JumpHistory Count="30" HistoryIndex="29">
<Position1>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1703" Column="86" TopLine="1678"/>
<Caret Line="47" Column="34" TopLine="21"/>
</Position1>
<Position2>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1702" Column="93" TopLine="1682"/>
<Caret Line="1722" Column="21" TopLine="1702"/>
</Position2>
<Position3>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1736" Column="47" TopLine="1709"/>
<Caret Line="1763" Column="53" TopLine="1733"/>
</Position3>
<Position4>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1723" Column="17" TopLine="1716"/>
<Caret Line="1651" Column="39" TopLine="1637"/>
</Position4>
<Position5>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1721" Column="21" TopLine="1683"/>
<Caret Line="1652" Column="42" TopLine="1626"/>
</Position5>
<Position6>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="47" Column="34" TopLine="21"/>
<Caret Line="1663" Column="16" TopLine="1638"/>
</Position6>
<Position7>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1722" Column="21" TopLine="1702"/>
<Caret Line="1730" Column="5" TopLine="1698"/>
</Position7>
<Position8>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1763" Column="53" TopLine="1733"/>
<Caret Line="47" Column="27"/>
</Position8>
<Position9>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1651" Column="39" TopLine="1637"/>
<Caret Line="1355" Column="25" TopLine="1330"/>
</Position9>
<Position10>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1652" Column="42" TopLine="1626"/>
<Caret Line="1361" Column="14" TopLine="1319"/>
</Position10>
<Position11>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1663" Column="16" TopLine="1638"/>
<Caret Line="1360" Column="49" TopLine="1337"/>
</Position11>
<Position12>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1730" Column="5" TopLine="1698"/>
<Caret Line="1354" Column="15" TopLine="1330"/>
</Position12>
<Position13>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="47" Column="27"/>
<Caret Line="1670" Column="5" TopLine="1646"/>
</Position13>
<Position14>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1355" Column="25" TopLine="1330"/>
<Caret Line="1354" Column="16" TopLine="1330"/>
</Position14>
<Position15>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1361" Column="14" TopLine="1319"/>
<Caret Line="1361" Column="15" TopLine="1337"/>
</Position15>
<Position16>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1360" Column="49" TopLine="1337"/>
<Caret Line="1354" Column="17" TopLine="1330"/>
</Position16>
<Position17>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1354" Column="15" TopLine="1330"/>
<Filename Value="umainform.pas"/>
<Caret Line="9" Column="11"/>
</Position17>
<Position18>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1670" Column="5" TopLine="1646"/>
<Filename Value="umainform.pas"/>
<Caret Line="117" Column="65" TopLine="93"/>
</Position18>
<Position19>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1354" Column="16" TopLine="1330"/>
<Filename Value="umainform.pas"/>
<Caret Line="114" TopLine="91"/>
</Position19>
<Position20>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1361" Column="15" TopLine="1337"/>
<Filename Value="umainform.pas"/>
<Caret Line="113" TopLine="90"/>
</Position20>
<Position21>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="1354" Column="17" TopLine="1330"/>
<Filename Value="umainform.pas"/>
<Caret Line="88" TopLine="86"/>
</Position21>
<Position22>
<Filename Value="umainform.pas"/>
<Caret Line="9" Column="11"/>
<Caret Line="87" TopLine="85"/>
</Position22>
<Position23>
<Filename Value="umainform.pas"/>
<Caret Line="117" Column="65" TopLine="93"/>
<Caret Line="45" TopLine="30"/>
</Position23>
<Position24>
<Filename Value="umainform.pas"/>
<Caret Line="114" TopLine="91"/>
<Caret Line="78" Column="29" TopLine="58"/>
</Position24>
<Position25>
<Filename Value="umainform.pas"/>
<Caret Line="113" TopLine="90"/>
<Caret Line="77" Column="6" TopLine="53"/>
</Position25>
<Position26>
<Filename Value="umainform.pas"/>
<Caret Line="88" TopLine="86"/>
<Caret Line="73" Column="48" TopLine="53"/>
</Position26>
<Position27>
<Filename Value="umainform.pas"/>
<Caret Line="87" TopLine="85"/>
<Caret Line="75" Column="48" TopLine="55"/>
</Position27>
<Position28>
<Filename Value="umainform.pas"/>
<Caret Line="45" TopLine="30"/>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="7" Column="17"/>
</Position28>
<Position29>
<Filename Value="umainform.pas"/>
<Caret Line="78" Column="29" TopLine="58"/>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="359" Column="29" TopLine="341"/>
</Position29>
<Position30>
<Filename Value="umainform.pas"/>
<Caret Line="77" Column="6" TopLine="53"/>
<Filename Value="..\ulazautoupdate.pas"/>
<Caret Line="357" Column="58" TopLine="352"/>
</Position30>
</JumpHistory>
</ProjectSession>

View File

@ -11,6 +11,7 @@ object mainform: Tmainform
OnCreate = FormCreate
Position = poDesktopCenter
LCLVersion = '1.7'
Visible = True
object StatusBar1: TStatusBar
Left = 0
Height = 23
@ -80,6 +81,17 @@ object mainform: Tmainform
ParentColor = False
ParentFont = False
end
object cmd_SilentUpdate: TButton
Left = 184
Height = 25
Top = 80
Width = 96
AutoSize = True
Caption = 'Silent Update'
OnClick = cmd_SilentUpdateClick
TabOrder = 6
Visible = False
end
object LazAutoUpdate1: TLazAutoUpdate
About.Description.Strings = (
'A component for updating your application'#13#10'Designed for projects hosted by SourceForge'#13#10#13#10'Main methods:'#13#10'Procedure AutoUpdate'#13#10'Function NewVersionAvailable: Boolean'#13#10'Function DownloadNewVersion: Boolean'#13#10'Function UpdateToNewVersion: Boolean'#13#10'Procedure ShowWhatsNewIfAvailable'#13#10'For troubleshooting, set DebugMode=TRUE'

View File

@ -34,6 +34,7 @@ type
{ Tmainform }
Tmainform = class(TForm)
cmd_SilentUpdate: TButton;
cmd_AutoUpdate: TButton;
cmd_updateToNewVersion: TButton;
cmd_DownloadNewVersion: TButton;
@ -45,6 +46,7 @@ type
procedure cmd_AutoUpdateClick(Sender: TObject);
procedure cmd_DownloadNewVersionClick(Sender: TObject);
procedure cmd_NewVersionAvailableClick(Sender: TObject);
procedure cmd_SilentUpdateClick(Sender: TObject);
procedure cmd_updateToNewVersionClick(Sender: TObject);
procedure FormActivate(Sender: TObject);
procedure FormCreate(Sender: TObject);
@ -83,6 +85,11 @@ begin
LazAutoUpdate1.NewVersionAvailable;
end;
procedure Tmainform.cmd_SilentUpdateClick(Sender: TObject);
begin
LazAutoUpdate1.SilentUpdate;
end;
procedure Tmainform.cmd_updateToNewVersionClick(Sender: TObject);
begin
LazAutoUpdate1.UpdateToNewVersion;

View File

@ -42,7 +42,7 @@ uses
fileinfo, winpeimagereader {need this for reading exe info}
, elfreader {needed for reading ELF executables}
, machoreader {needed for reading MACH-O executables}
{$IFDEF WINDOWS},Windows,ShellAPI{$ENDIF}; // Thanks to Windows 10 and 704 error
{$IFDEF WINDOWS}, Windows, ShellAPI{$ENDIF}; // Thanks to Windows 10 and 704 error
const
C_OnlineAppPath =
@ -114,14 +114,16 @@ const
C_GUIEntry = 'GUI';
C_ModuleEntry = 'Module';
{$IFDEF WINDOWS}
{$IFDEF CPU32}C_Updater = 'updatehmwin32.exe';{$ENDIF}
{$IFDEF CPU64}C_Updater = 'updatehmwin64.exe';{$ENDIF}
C_LOCALUPDATER = 'lauupdate.exe';
{$IFDEF CPU32}C_UPDATER = 'updatehmwin32.exe';
C_LOCALUPDATER = 'lauupdatewin32.exe';{$ENDIF}
{$IFDEF CPU64}C_UPDATER = 'updatehmwin64.exe';
C_LOCALUPDATER = 'lauupdatewin64.exe';{$ENDIF}
{$ENDIF}
{$IFDEF LINUX}
{$IFDEF CPU32}C_Updater = 'updatehmlinux32';{$ENDIF}
{$IFDEF CPU64}C_Updater = 'updatehmlinux64';{$ENDIF}
C_LOCALUPDATER = 'lauupdate';
{$IFDEF CPU32}C_UPDATER = 'updatehmlinux32';
C_LOCALUPDATER = 'lauupdatelinux32';{$ENDIF}
{$IFDEF CPU64}C_UPDATER = 'updatehmlinux64';
C_LOCALUPDATER = 'lauupdatelinux64';{$ENDIF}
{$ENDIF}
resourcestring
@ -229,6 +231,7 @@ type
fQuad: TVersionQuad;
fProgVersion: TProgramVersion;
objFileVerInfo: TFileVersionInfo;
fUpdateExe,fUpdateSilentExe:String;
procedure SetProjectType(AValue: TProjectType);
// projectype=auOther property Sets
procedure SetauOtherSourceFilename(AValue: string);
@ -353,7 +356,8 @@ type
write fDownloadCountLimit;
// Default is application filename.zip
property ZipfileName: string read fZipfileName write fZipfileName;
property UpdateExe:String read fUpdateExe;
property UpdateExeSilent:String read fUpdateSilentExe;
end;
{TThreadedDownload }
@ -526,6 +530,10 @@ begin
fZipfileName := ''; // assign later
fUpdateExe:=C_UPDATER;
fUpdateSilentExe:=C_LOCALUPDATER;
// Assorted versioninfo properties
fLCLVersion := GetLCLVersion;
fWidgetSet := GetWidgetSet;
@ -560,11 +568,13 @@ begin
AboutBoxAuthorEmail := 'minesadorada@charcodelvalle.com';
AboutBoxLicenseType := 'MODIFIEDGPL';
end;
destructor TLazAutoUpdate.Destroy;
begin
FreeAndNil(fThreadDownload);
inherited destroy;
inherited Destroy;
end;
function TLazAutoUpdate.AppIsActive(const ExeName: string): boolean;
begin
Result := AppIsRunning(ExeName);
@ -1345,13 +1355,13 @@ begin
if not FileExistsUTF8(szDestLAUTrayPath + C_LAUTRayINI) then
begin
// Move C_LAUTRayINI from app folder to local <AppData> folder
if FileUtil.CopyFile(szSourceLAUTrayPath, szDestLAUTrayPath + C_LAUTRayINI,
[cffOverwriteFile]) then
if FileUtil.CopyFile(szSourceLAUTrayPath, szDestLAUTrayPath +
C_LAUTRayINI, [cffOverwriteFile]) then
begin
if fFireDebugEvent then
fOndebugEvent(Self, 'RelocateLauImportFile',
Format('Relocated %s from %s to %s',
[C_LAUTRayINI, szSourceLAUTrayPath, szDestLAUTrayPath]));
Format('Relocated %s from %s to %s', [C_LAUTRayINI,
szSourceLAUTrayPath, szDestLAUTrayPath]));
SysUtils.DeleteFile(szSourceLAUTrayPath);
end
else
@ -1541,9 +1551,28 @@ end;
function TLazAutoUpdate.RemoteUpdateToNewVersion: boolean;
// Shells to 'lauupdate' console app in ProgramDirectory to remotely update an app
{$IFDEF WINDOWS}
function RunAsAdmin(const Handle: THandle; const Path, Params: string): boolean;
var
sei: TShellExecuteInfoA;
begin
FillChar(sei, SizeOf(sei), 0);
sei.cbSize := SizeOf(sei);
sei.Wnd := Handle;
sei.fMask := SEE_MASK_FLAG_DDEWAIT or SEE_MASK_FLAG_NO_UI;
sei.lpVerb := 'runas';
sei.lpFile := PAnsiChar(Path);
sei.lpParameters := PAnsiChar(Params);
sei.nShow := SW_SHOWNORMAL;
Result := ShellExecuteExA(@sei);
end;
{$ENDIF}
var
cCount: cardinal;
szAppDir: string;
szAppDir, szParams: string;
begin
Result := False;
szAppDir := AppendPathDelim(ExtractFilePath(fAppFilename));
@ -1583,10 +1612,33 @@ begin
end;
{$IFDEF WINDOWS}
szParams := ExtractFileName(fAppFilename);
szParams := szParams + ' ' + fUpdatesFolder;
szParams := szParams + ' ' + C_WhatsNewFilename;
szParams := szParams + ' ' + fParentApplication.Title;
if (fCopyTree = True) then
szParams := szParams + ' copytree';
if fFireDebugEvent then
fOndebugEvent(Self, 'RemoteUpdateToNewVersion',
Format('Executing %s', [ProgramDirectory + C_LOCALUPDATER]));
RunAsAdmin(fParentForm.Handle, ProgramDirectory + C_LOCALUPDATER, szParams);
// Check for C_WhatsNewFilename in the app directory in a LOOP
if fFireDebugEvent then
fOndebugEvent(Self, 'RemoteUpdateToNewVersion',
Format('Waiting for %s', [szAppDir + C_WhatsNewFilename]));
while not FileExistsUTF8(szAppDir + C_WhatsNewFilename) do
begin
fParentApplication.ProcessMessages;
Inc(CCount);
if cCount > 10000000 then
Break; // Get out of jail in case updatehm.exe fails to copy file
end;
{$ELSE}
// Update and re-start the app
FUpdateHMProcess := TAsyncProcess.Create(nil);
try
FUpdateHMProcess.Executable := ProgramDirectory + C_LOCALUPDATER;
FUpdateHMProcess.CurrentDirectory := ProgramDirectory;
if not fSilentMode then
@ -1603,6 +1655,8 @@ begin
if fFireDebugEvent then
fOndebugEvent(Self, 'RemoteUpdateToNewVersion',
Format('Executing %s', [ProgramDirectory + C_LOCALUPDATER]));
try
FUpdateHMProcess.Execute;
// Check for C_WhatsNewFilename in the app directory in a LOOP
@ -1616,7 +1670,10 @@ begin
if cCount > 10000000 then
Break; // Get out of jail in case updatehm.exe fails to copy file
end;
finally
FUpdateHMProcess.Free;
end;
{$ENDIF}
// remotely shut down the app?
if fSilentMode then
begin
@ -1627,11 +1684,8 @@ begin
Format('Killing %s ready for update', [fAppFilename]));
end;
finally
FUpdateHMProcess.Free;
if not fSilentMode then
fParentForm.Close;
end;
if fFireDebugEvent then
fOndebugEvent(Self, 'RemoteUpdateToNewVersion',
'Success');
@ -1642,11 +1696,10 @@ end;
function TLazAutoUpdate.UpdateToNewVersion: boolean;
{$IFDEF WINDOWS}
// function RunAsAdmin(const Handle: Hwnd; const Path, Params: string): Boolean;
function RunAsAdmin(const Handle: THandle; const Path, Params: string): Boolean;
var
function RunAsAdmin(const Handle: THandle; const Path, Params: string): boolean;
var
sei: TShellExecuteInfoA;
begin
begin
FillChar(sei, SizeOf(sei), 0);
sei.cbSize := SizeOf(sei);
sei.Wnd := Handle;
@ -1656,12 +1709,13 @@ begin
sei.lpParameters := PAnsiChar(Params);
sei.nShow := SW_SHOWNORMAL;
Result := ShellExecuteExA(@sei);
end;
end;
{$ENDIF}
var
cCount: cardinal;
szAppDir: string;
szParams:String;
szParams: string;
begin
Result := False;
szAppDir := AppendPathDelim(ExtractFilePath(fAppFilename));
@ -1679,13 +1733,13 @@ begin
else
begin
cCount := 0;
if not FileExistsUTF8(szAppDir + C_Updater) then
if not FileExistsUTF8(szAppDir + C_UPDATER) then
begin
if fShowDialogs then
ShowMessageFmt(C_UpdaterMissing, [szAppDir + C_Updater]);
ShowMessageFmt(C_UpdaterMissing, [szAppDir + C_UPDATER]);
if fFireDebugEvent then
fOndebugEvent(Self, 'UpdateToNewVersion',
Format(C_UpdaterMissing, [szAppDir + C_Updater]));
Format(C_UpdaterMissing, [szAppDir + C_UPDATER]));
Exit;
end;
@ -1710,16 +1764,16 @@ begin
Format('Killing %s ready for update', [fAppFilename]));
end;
{$IFDEF WINDOWS}
szParams:=ExtractFileName(fAppFilename);
szParams:=szParams + ' ' + fUpdatesFolder;
szParams:=szParams + ' ' + C_WhatsNewFilename;
szParams:=szParams + ' ' + fParentApplication.Title;
szParams := ExtractFileName(fAppFilename);
szParams := szParams + ' ' + fUpdatesFolder;
szParams := szParams + ' ' + C_WhatsNewFilename;
szParams := szParams + ' ' + fParentApplication.Title;
if (fCopyTree = True) then
szParams:=szParams + ' copytree';
szParams := szParams + ' copytree';
if fFireDebugEvent then
fOndebugEvent(Self, 'UpdateToNewVersion',
Format('Executing %s', [szAppDir + C_UPDATER]));
RunAsAdmin(fParentForm.Handle,szAppDir + C_UPDATER, szParams);
RunAsAdmin(fParentForm.Handle, szAppDir + C_UPDATER, szParams);
// Check for C_WhatsNewFilename in the app directory in a LOOP
if fFireDebugEvent then
@ -1736,9 +1790,9 @@ begin
// Update and re-start the app
FUpdateHMProcess := TAsyncProcess.Create(nil);
try
// FUpdateHMProcess.Executable := AppendPathDelim(GetAppConfigDir(false)) + C_Updater;
// FUpdateHMProcess.Executable := AppendPathDelim(GetAppConfigDir(false)) + C_Updater;
FUpdateHMProcess.Executable := szAppDir + C_UPDATER;
// FUpdateHMProcess.CurrentDirectory := AppendPathDelim(GetAppConfigDir(false));
// FUpdateHMProcess.CurrentDirectory := AppendPathDelim(GetAppConfigDir(false));
FUpdateHMProcess.CurrentDirectory := szAppDir;
if not fSilentMode then
FUpdateHMProcess.ConsoleTitle :=
@ -1754,11 +1808,12 @@ begin
if fFireDebugEvent then
fOndebugEvent(Self, 'UpdateToNewVersion',
Format('Executing %s', [szAppDir + C_UPDATER]));
TRY
try
FUpdateHMProcess.Execute;
EXCEPT
raise Exception.CreateFmt('Error %d: Run this application in Administrator mode or turn off UAC',[GetLastOSError]);
END;
except
raise Exception.CreateFmt(
'Error %d: Run this application in Administrator mode or turn off UAC', [GetLastOSError]);
end;
// Check for C_WhatsNewFilename in the app directory in a LOOP
if fFireDebugEvent then
@ -1771,9 +1826,9 @@ END;
if cCount > 10000000 then
Break; // Get out of jail in case updatehm.exe fails to copy file
end;
finally
finally
FUpdateHMProcess.Free;
end;
end;
{$ENDIF}
if fFireDebugEvent then
fOndebugEvent(Self, 'UpdateToNewVersion',
@ -1975,8 +2030,8 @@ begin
end;
{ End of class members}
function DownloadHTTP(URL, TargetFile: string;
var ReturnCode, DownloadSize: integer; bIsSourceForge, fDebugmode: boolean): boolean;
function DownloadHTTP(URL, TargetFile: string; var ReturnCode, DownloadSize: integer;
bIsSourceForge, fDebugmode: boolean): boolean;
// Download file; retry if necessary.
// Deals with SourceForge download links
const
@ -1991,9 +2046,8 @@ begin
HTTPClient := TFPHTTPClient.Create(nil);
if bIsSourceForge then
begin
HTTPClient.AllowRedirect:=True;
HTTPClient.AllowRedirect := True;
end;
// ReturnCode may not be useful, but it's provided here
try
try