Use private R and Python packages from Package Manager

Enhanced Advanced

This guide explains how to deploy content to Posit Connect that depends on private R or Python packages, such as packages that your organization develops in a private Git repository. Posit recommends that you publish these packages to Posit Package Manager and install them from an authenticated Package Manager repository.

With this approach, Connect installs private packages the same way that it installs packages from CRAN or the Python Package Index (PyPI). It works with any Git server, including self-hosted servers. Publishers install a package by its name and version, and Package Manager controls who can download it.

Why use Package Manager for private packages

Connect can also install packages directly from private Git repositories with a GitCredential. See private R packages from Git repositories and private Python packages from Git repositories. That approach has these limits:

  • R package installation uses a GitCredential only for repositories on github.com, gitlab.com, and bitbucket.org. It does not support self-hosted servers such as GitHub Enterprise Server.
  • A GitCredential is one server-wide credential for each Git host. Connect uses the same credential for every content item, no matter which publisher owns it. You cannot use an access control list (ACL) to choose which publishers can install packages with it.
  • If the credential stops working, every package installation from that host fails, including installations from public repositories on the same host.
  • Connect cannot install R packages that publishers install with remotes::install_git().

With Package Manager, publishers install packages by version from a repository, as they do from CRAN or PyPI. The ACL of a Package Manager integration controls which publishers can install from authenticated repositories. Each build receives a short-lived token for its content owner.

Note

This guide is about package installation. Connect still uses GitCredential entries to deploy Git-backed content from private repositories.

Prerequisites

Before you begin, you must have:

  • A Package Manager server that Connect can reach over the network.
  • A Package Manager administrator who can create sources and repositories.
  • A Connect administrator who can change the Connect configuration and create integrations.

Step 1: Publish the package to Package Manager

A Package Manager administrator adds the private package to a local source in Package Manager. Package Manager offers two ways to do this:

  • Git builders: Package Manager builds R and Python packages from a Git repository. It builds a package version for each commit on a branch, or for each tag. Package Manager authenticates to the Git server with Secure Shell (SSH) keys, HTTPS credentials, OAuth2 federated credentials, or GitHub App credentials. See Building Git packages in the Package Manager documentation.
  • Remote publishing: Your CI/CD pipeline builds the package and uploads it to Package Manager. The pipeline uses the rspm CLI for R packages and Twine for Python packages. This works with any Git server, because Package Manager never connects to the Git server. See Remote publishing in the Package Manager documentation.

After the package is in a source, the Package Manager administrator subscribes a repository to that source. You can add the source to a repository that also serves CRAN or PyPI packages, or you can create a separate repository for internal packages. Package Manager repositories serve one language, so R and Python packages need separate repositories. This guide calls them the internal repositories.

Step 2: Restrict access to the repository

The Package Manager administrator turns on authentication for the repository, and the Connect administrator creates a Package Manager integration. With the integration, each R and Python build receives a short-lived token to download from the repository. Follow the steps in Authenticated repositories.

Use the ACL of the integration to choose which publishers can install the private packages. Use its scopes value to choose which repositories the token can read. For example, repos:read:internal allows only a repository named internal.

Step 3: Configure Connect to use the repository

By default, Connect installs packages from the repositories that the publisher records in the content bundle, so this step is optional. If you want every deployment to use the internal repository, a Connect administrator adds it to the server configuration.

Important

If R.PackageRepositoryResolution or Python.PackageRepositoryResolution is strict, this step is required. In strict mode, Connect ignores the repositories in the content bundle, including --extra-index-url lines in requirements.txt. If the internal repository is not in the server configuration, the build cannot find the private package.

See Configuring Package Manager for R and Configuring Package Manager for Python.

Step 4: Install the package and deploy

A publisher installs the private package from the internal repository in their development environment. To download from the authenticated repository, the publisher needs a Package Manager token on their computer. See Token authentication in the Package Manager documentation.

For R, add the internal repository to the repos option, for example in the .Rprofile file of your project. Then install the package. See Configuring R package repositories for deployment.

For Python, add the internal repository to requirements.txt with an --extra-index-url line, and list the package by version. See Requirements files.

Deploy your content to Connect as usual. The content needs no extra configuration for the private package. During the build, the Package Manager integration gives the build a token. Connect then installs the private package with your other dependencies. If the build cannot install the package, the build log names the package and the repository that it tried.