Skip to content

Packaging external apps

By default, Briefcase assumes that you will be using Briefcase to manage the full app packaging life cycle. In this mode, your Briefcase configuration defines all your app's source code, dependencies, and resources; and Briefcase generates a distributable artefact that is appropriate for the target platform.

However, Briefcase can also be used to package an application which has been constructed using another tool, such as PyInstaller or py2app. In this mode of operation, Briefcase can be used to convert the app generated by those tools into an installer artefact, performing signing and notarization where necessary.

Briefcase refers to this mode of Briefcase usage as packaging an "external app".

Configuring an external app

The process of configuring an external app is mostly the same as a normal Briefcase app, with one important difference: you do not define a sources entry, but instead define an external_package_path. This should be the content produced by your build tool that you want to distribute to end users.

The following would be a minimal pyproject.toml configuration for an external app called "Hello World":

[tool.briefcase]
project_name = "Hello World"
bundle = "com.example"

[tool.briefcase.app.helloworld]
formal_name = "Hello World"
version = "0.0.1"

[tool.briefcase.app.helloworld.macOS]
external_package_path = "..."

[tool.briefcase.app.helloworld.linux]
external_package_path = "..."

[tool.briefcase.app.helloworld.windows]
external_package_path = "..."

The required format for external_package_path is different on each platform.

macOS

On macOS, the external_package_path should be the location of the .app bundle that you want to distribute to users. The configured formal_name must match the name of the app bundle (e.g., Hello World.app should use a formal name of Hello World); the app_name will be used for the shortcut installed in /usr/local/bin when creating a console app.

Briefcase will sign and notarize the app bundle, as well as any DMG or PKG file that is produced.

External macOS apps must be full macOS app bundles. Briefcase cannot be used to package standalone binaries.

Linux

On Linux, the external_package_path should be a path that contains the root of a installation tree to be packaged. If you define an external_package_path of external, it is assumed that external/usr/bin/<app_name> will be the executable for your application, which will be installed as /usr/bin/<app_name>. Any other content that should be installed as part of your app should be included in the tree contained under external.

Although it is not possible to specify requires for external applications, external Linux applications must define system_runtime_requires. These requirements are used to define system-level requirements in the generated system packages.

Windows

On Windows, the external_package_path should be the directory that contains all the content to be installed into the end-user's Program Files directory. By default, it is assumed that the executable used to launch the app is named <external_package_path>/<formal_name>.exe (or <external_package_path>/<app_name>.exe for a console app). If this is not the name or path to your executable, you can define external_package_executable_path to define the path inside external_package_path to your executable binary. For example, an external_package_path value of external, and an external_package_executable_path value of somewhere/myapp.exe, would define that external/somewhere/myapp.exe is the executable that should be installed as the application shortcut.

Customizing packaging metadata

In the process of packaging an external app, Briefcase will generate an application template. The template is used to populate packaging metadata, installer and signing configuration files. The template that is used is identical to the one used for a normal Briefcase application; however, the packaged app will be removed from the template, and no attempt will be made to install application dependencies, resources, or a support package.

The files generated by the template should not be modified by hand. If you need to customize the contents of these templated files, you should use Briefcase app configuration settings to define those changes. For example, on macOS if you need to add an entitlement for signing purposes, you should not modify the templated Entitlements.plist file by hand - you should use the entitlement setting in your pyproject.toml.

If Briefcase's configuration options are not sufficient for your requirements, you can either fork the template used by Briefcase and use the template option to point at your custom template; or you can submit a pull request to Briefcase to support your customization use case.

Packaging an external app

Once you have configured your external app, you can call briefcase package. There is no need to invoke briefcase create, briefcase build, or any other Briefcase command:

(venv) $ briefcase package

[helloworld] Packaging external content from /Users/brutus/helloworld/output/Hello World.app

[helloworld] Generating application template...
...
[helloworld] Packaged dist/Hello World-0.0.1.dmg

The dist folder will contain the .dmg that that was created.

The output of the package step will be slightly different depending on your Linux distribution; however, it will follow the following general format:

(venv) $ briefcase package

[helloworld] Finalizing application configuration...
Targeting ubuntu:jammy (Vendor base debian)
Determining glibc version... done
Targeting glibc 2.35
Targeting Python3.10

[helloworld] Packaging external content from /Users/brutus/helloworld/output/linux-app

[helloworld] Generating application template...
...
[helloworld] Packaged dist/helloworld_0.0.1-1~ubuntu-jammy_amd64.deb

The dist folder will contain the system package that was created.

Docker (and the --target option) cannot be used to package external apps for different operating systems.

(venv) C:\...>briefcase package

[helloworld] Packaging external content from Z:\projects\helloworld\output\windows-app

[helloworld] Generating application template...
...
[helloworld] Packaged dist\Hello_World-0.0.1.msi

The dist folder will contain the installer that was created.

Any arguments to briefcase package that are allowed for normal Briefcase apps will also be honored for external apps. See the documentation of the Package command for details.

Briefcase will re-generate the templated app content on every invocation of briefcase package. On a second invocation of briefcase package for the same project, you will be prompted to overwrite the application. This will only overwrite the templated packaging metadata, not the application itself.