Helper Apps
(and a bit of Save As)

Sept. 12, 2002

by Boris Zbarsky

Bird's Eye View

Flow of control

  1. URILoader tries to find a content listener for the MIME type in question.
  2. When this fails, URILoader asks an nsIExternalHelperAppService to handle the load.
  3. The nsExternalHelperAppService looks up the nsIMIMEInfo for the load and creates an nsIHelperAppLauncher to manage the load.
  4. The nsExternalAppHandler (which implements nsIHelperAppLauncher) uses the nsIMIMEInfo and an nsIHelperAppLauncherDialog to decide what to do with the data.
  5. The nsExternalAppHandler does whatever it decided to do.

nsIMIMEInfo lookup

  1. Look in built-in list which the user cannot override (types we handle internally).
  2. Look in user preferences.
  3. Ask the OS:
    • Registry on Windows.
    • Internet Config on the Mac.
    • mailcap/mime.types on Linux.
  4. Look in second built-in list, which the user can override.

nsExternalAppHandler details

nsExternalAppHandler::OnStartRequest

  1. Creates a temporary file with a salted name to hold the data.
  2. Decides on a suggested filename for the data in case it will be saved.
  3. Decides whether the data should be content-decoded (based on some not-so-great heuristics).
  4. Decides whether the user should be prompted (based on a preference).
  5. Calls Show() on the nsIHelperAppLauncherDialog, which asynchronously puts up the helper app dialog.

nsExternalAppHandler::OnDataAvailable

nsExternalAppHandler::OnStopRequest

Set a flag that we're done, then do whatever the user wants if the user has decided (save to disk and open in helper are the current options the user has).

Helper App dialog

This is our implementation of nsIHelperAppLauncherDialog

It calls back to the nsExternalAppHandler to let it know what the user picked

Saving to disk

If a user decides to "save to disk", we just move/copy the temporary file over to the chosen location once the download completes. If an error occurs while we do this we delete the temp file and put up an error dialog.

Launching a helper application

This is delegated to the nsPIExternalAppLauncher (also implemented by the nsExternalHelperAppHandler):

Security considerations

Multiple checks for whether a file is executable (on Windows) to keep from launching such files via ::ShellExecute(). Checks happen in OnStartRequest, in the helper app dialog, and as a last ditch in the launching code.

Limitations of nsIMIMEInfo

Ongoing work

Future work