在Windows和Delphi中实现应用程序可移植性?

eye*_*ton 1 windows delphi portability delphi-7

我们有这个应用程序不写入Windows注册表或将其配置文件(如INI文件)存储在用户的配置文件中; 相反,它将其配置文件存储在程序的目录中.维基百科有此声明

便携式应用程序(便携式应用程序)是一种计算机软件程序,旨在独立于操作系统运行.这种类型的应用程序存储在可移动存储设备上,例如CD,USB闪存驱动器,闪存卡 - 仅在存储介质上存储其程序文件,配置信息和数据.

所以我们的问题是,这会使我们的应用程序成为真正的便携式应用程序(便携式应用程

我应该指出,如果应用程序在写保护介质上,我们使用下面的函数,因此它不会尝试写入该介质.

function GetTempFile(): string;
var
  Buffer: array[0..MAX_PATH] of Char;
begin
  Windows.ZeroMemory(@Buffer, System.SizeOf(Buffer));
  SysUtils.StrPCopy(Buffer, SysUtils.ExcludeTrailingBackslash(SysUtils.ExtractFilePath(System.ParamStr(0))));
  Windows.GetTempFileName(Buffer, '~', 0, Buffer);
  Result := string(Buffer);
end;

function IsMediumWriteProtected(): Boolean;
var
  ErrorMode: Word;
  hHandle: THandle;
begin
  ErrorMode := Windows.SetErrorMode(SEM_FAILCRITICALERRORS);
  try
    hHandle := Windows.CreateFile(PChar(GetTempFile()), GENERIC_WRITE, 0, nil, 
      CREATE_ALWAYS, FILE_ATTRIBUTE_TEMPORARY or FILE_FLAG_DELETE_ON_CLOSE, 0);
    try
      Result := (hHandle = INVALID_HANDLE_VALUE);
    finally
      Windows.CloseHandle(hHandle);
    end;
  finally
    Windows.SetErrorMode(ErrorMode);
  end;
end;
Run Code Online (Sandbox Code Playgroud)

War*_* P 11

一个真正便携的应用程序,如果这是真正的问题,应该:

  • 不需要任何安装.
  • 在您复制到的任何地方工作.

我自己的便携式应用程序的格式塔定义并不总是要求应用程序在位于只读位置时工作,除了这个维基百科参考,我不确定它是否是标准的.你正试图遵循维基百科文章中所阐述的法律条款,这真是太棒了.让我感到烦恼的是,你从维基百科文章中提到的引用包含了一些内部矛盾; 如果定义都期望必须支持CDROM(或者您的应用程序不可移植),并且还指定数据应该仅存储在该介质上.你遇到了这个矛盾,现在正在违反法律条文的一部分,以避免违反其中的第一部分.所以这个定义要么阻止你在这种情况下保存任何东西,要么这个定义实际上不是法律本身,你可以自由地按照你的意愿去做,前提是我遵循上面提到的两点.

我在上面给出了便携式应用程序的极简主义定义,除了这两点之外你应该做的事情应该是适合你的用户的.

我真的没有看到SO上的任何人如何能够为您提供便携性方面的绿灯.您只能通过测试来真正验证可移植性,并且最好通过一组人进行测试,例如beta测试或fieldtest用户.我也没有看到StackOverflow是测试二进制文件的帮助请求的好地方.这是一个询问编程问题的网站,不是用于形成beta测试,现场测试等,也不是用于推广您的应用.事实上,我没有看到我们如何安全地从您下载二进制文件,并没有冒险运行我们的系统运行我们从链接下载的二进制代码.我建议你删除二进制文件的链接.

我会做的测试:

  • 将它放在USB密钥上,并在几个不同的干净窗口系统上的几台不同的PC上运行,包括XP,Vista,Win 7,Windows Server 2008,几个服务包级别(XP上没有SP,Sp1,Sp2,Sp3等) ,以及几个不同的脏系统(安装了Visual Studio的系统,安装了delphi,安装了办公室,以及各种防病毒系统).

  • 确保您不需要外部运行时BPL/DLL或其他运行时内容,除了那些与可执行文件位于同一文件夹中的内容(并排配置).这样就不必修改用户的路径以使你的应用程序正常工作,而且你不必担心DLL地狱的混乱.

  • 检查应用程序中是否存在注册表写入或应用程序文件夹外的文件系统写入.SysInternals Process Monitor非常适合这种情况.


Rem*_*eau 6

不要Windows.GetCurrentDirectory()用于检索可执行文件的目录.它返回进程的当前工作目录,该目录可以在进程的生命周期内动态更改,因此无法保证每次都能获得正确的目录.要可靠地获取应用程序目录,请Sysutils.ExtractFilePath(Sysutils.ParamStr(0))改用.在内部,这用于Windows.GetModuleFileName(nil)获取应用程序的完整路径,然后截断可执行文件名,留下所需的目录路径.