How can I get the Name of the Program associated with a file extension using Delphi?

Don't go spelunking in the registry when there are API functions designed to do what you need.

In your case, you want AssocQueryString. You can give it the file-name extension, and it will tell your the program registered to handle that extension (AssocStr_Executable). If you're planning on running that program to open a document, then you'll really want the command string instead of just the executable; AssocQueryString can give you that, too (AssocStr_Command). It can also tell you the document type like what's displayed in Windows Explorer, like "Text Document" or "Zip Archive" (AssocStr_FriendlyDocName).

That API function is a wrapper for the IQueryAssociations interface. If you're looking for programs from many file types, or lots of strings associated with a single type, you may wish to instantiate that interface and re-use it instead of calling the API function over and over.


Delphi comes with a unit ShellApi.pas that is used in the sample code below. The file has to exist.

Here's how to use it:

function MyShellFindExecutable(const aFileName: string): string;
var
  Buffer: array[0..WINDOWS.MAX_PATH] of Char;
begin
  Result := '';
  FillChar(Buffer, SizeOf(Buffer), #0);
  if (SHELLAPI.FindExecutable(PChar(aFileName), nil, Buffer) > 32) then
    Result := Buffer;
end;

Step 1

Get the executable which is assigned to a file extension, for instance with the following function:

uses Registry, Windows, SysUtils;

function GetAssociation(const DocFileName: string): string;
var
  FileClass: string;
  Reg: TRegistry;
begin
  Result := '';
  Reg := TRegistry.Create(KEY_EXECUTE);
  Reg.RootKey := HKEY_CLASSES_ROOT;
  FileClass := '';
  if Reg.OpenKeyReadOnly(ExtractFileExt(DocFileName)) then
  begin
    FileClass := Reg.ReadString('');
    Reg.CloseKey;
  end;
  if FileClass <> '' then begin
    if Reg.OpenKeyReadOnly(FileClass + '\Shell\Open\Command') then
    begin
      Result := Reg.ReadString('');
      Reg.CloseKey;
    end;
  end;
  Reg.Free;
end;

(See here, or marc_s' anwser to this question :-)

Step 2

Now you can read out the name of the program from the version information of this executable! The easiest way is using the TVersionInfo class you can find via Google, for instance here.

var VersionInfo: TVersionInfo;  
VersionInfo := TVersionInfo.Create('PathToExe\name.exe');  
s := VersionInfo.KeyValue['Description'];

However, you have to be aware that some programs use the description key therefore (like RAD Studio itself or MS Excel), while others use the product name key...