在Windows上保存依赖于机器(非用户)的ini文件的位置

Cod*_*ats 5 windows delphi environment delphi-7

我的应用程序当前将设置存储在当前用户配置文件下的INI文件中(C:\Documents and Settings\<CurrentUser>\Application Data\MyApplication\MySettings.ini在WinXP下).但我已经意识到其中一些设置对于机器而言不是用户所特有的,因此希望(实际上需要)将它们保存在所有用户的单个位置.

Windows XP(及更高版本)上是否有文件夹位置,我可以存储用户独立设置?

注意:我不想将它们存储在与我的应用程序相同的文件夹中,也不想将它们存储在注册表中.

我注意到"C:\ Documents and Settings \"下有一个"所有用户"文件夹?我应该在那里存放吗?

奖励积分:我更有可能将答案授予任何能告诉我如何从Delphi 7中的Windows返回此路径的人.

pax*_*blo 12

对于XP,Windows提供SHGetFolderPath()来获取已知位置.您正在寻找的CSIDL CSIDL_COMMON_APPDATA描述如下:

包含所有用户的应用程序数据的文件系统目录.典型的路径是"C:\Documents and Settings\All Users\Application Data".此文件夹用于非用户特定的应用程序数据.例如,应用程序可以在该CSIDL_COMMON_APPDATA文件夹中存储拼写检查字典,剪贴画数据库或日志文件.此信息不会漫游,并且可供使用该计算机的任何人使用.

对于Vista及更高版本,虽然SHGetFolderPath()仍可作为包装函数使用,但它已被SHGetKnownFolderPath()取代.如果你使用真正的Vista通话,你应该使用FOLDERID_ProgramData而不是CSIDL_COMMON_APPDATA.

此链接在这里似乎表明这样做的一种方式.

它似乎归结为这个(谨慎对待这个,我不熟悉Delphi):

function ShGetKnownFolderPath (
    const rfid:   TGUID;
    dwFlags:      DWord;
    hToken:       THandle;
    out ppszPath: PWideChar): HResult;
var
    Shell: HModule;
    Fn: TShGetKnownFolderPath;
begin
    Shell := LoadLibrary ('shell32.dll');
    Win32Check(Shell <> 0);
    try
        @Fn := GetProcAddress (Shell, 'SHGetKnownFolderPath');
        Win32Check (Assigned (Fn));
        Result := Fn (rfid, dwFlags, hToken, ppszPath);
    finally
        FreeLibrary (Shell);
    end;
end;
Run Code Online (Sandbox Code Playgroud)

 

function GetKnownFolderPath (
    const rfid: TGUID;
    dwFlags:    DWord;
    hToken:     THandle): WideString;
var
    buffer: PWideChar;
    ret: HResult;
begin
    ret :=ShGetKnownFolderPath (rfid, dwFlags, hToken, buffer);
    OleCheck (ret);
    try
        Result := buffer;
    finally
        CoTaskMemFree (buffer);
    end;
end;
Run Code Online (Sandbox Code Playgroud)

此页面提供了所有CSIDL_*FOLDERID_*值的列表.请记住,您应该将这些功能用于特定于用户的数据,而不是硬编码值"C:\Documents and Settings\<CurrentUser>\Application Data\".可能是Windows的不同语言版本使用不同的目录名称,或者用户可以自由移动其数据区域.

  • 这是正确使用的API,以及在这种情况下要求的正确的folderid.但是,还有一件事需要澄清: - 在该位置创建的文件对管理员和所有者是RW,对其他用户是R. 每个_user_(即非UAC提升的管理员或用户)是否可以写入ini文件是否重要?如果是这样,则在创建时,必须调整文件或文件夹的访问控制列表以包括显式的所有用户RW条目. (4认同)

Lac*_*anG 6

我建议使用开源JEDI代码库来做这类事情.

在JclShell.pas中,你会发现GetSpecialFolderLocation()

YourDataFolder := GetSpecialFolderLocation(CSIDL_COMMON_APPDATA);
Run Code Online (Sandbox Code Playgroud)

它是免费的,经过良好测试,适用于所有Windows版本,并且使用它可以使您免受未来对Windows API的更改.