As a third party wishing to integrate with Pulp 3, you can use OpenAPI tooling to generate bindings for over 20 different languages. Here is an example of how to use swagger-codegen to generate Python bindings.

The REST API documentation for Pulp 3 is available on every Pulp instance at /pulp/api/v3/docs. The documentation is auto generated using the OpenAPI 2.0, formerly known as Swagger, schema definition. Each Pulp instance has a variety of plugins installed. The documentation is always a reflection of the installed plugins.

The schema can also be used to generate client bindings in many languages using swagger-codegen. The schema is available for your local Pulp at /pulp/api/v3/docs/api.json.

The “Getting Started” section of swagger-codegen documentation contains a link to the latest version of the jar that can be used to generate a client for Pulp. The example below can be used to generate the Python client.

# Download swagger-codegen-cli jar
curl -o swagger-codegen-cli.jar

# List available config options for Python clients
java -jar swagger-codegen-cli.jar config-help -l python

            python package name (convention: snake_case). (Default: swagger_client)

            python project name in (e.g. petstore-api).

            python package version. (Default: 1.0.0)

            python package URL.

            Sort method arguments to place required parameters before optional parameters. (Default: true)

            hides the timestamp when files were generated (Default: true)

            library template (sub-template) to use (Default: urllib3)

# Create a custom swagger-codegen config for Python
vim config.json


# Download the OpenAPI 2.0 schema from Pulp
curl -o pulp-api.json http://localhost:24817/pulp/api/v3/docs/api.json

# Generate the client
java -jar swagger-codegen-cli.jar generate \
  -i pulp-api.json \
  -l python \
  -o ./my_pulp3_client \
  -c config.json

# Install the new Python package
pip install my_pulp3_client/

Below is an example of a script that uses the new client package to interact with Pulp.

import my_pulp3_client
from my_pulp3_client import Distribution, FileContent, FilePublisher, FileRemote, Repository, \
    RepositorySyncURL, RepositoryPublishURL
from import ApiException
from pprint import pprint
from time import sleep

def monitor_task(task_href):
    """Polls the Task API until the task is in a completed state.

    Prints the task details and a success or failure message. Exits on failure.

        task_href(str): The href of the task to monitor

        list[str]: List of hrefs that identify resource created by the task

    completed = ['completed', 'failed', 'canceled']
    task = api.tasks_read(task_href)
    while task.state not in completed:
        task = api.tasks_read(task_href)
    if task.state == 'completed':
        print("The task was successfful.")
        return task.created_resources
        print("The task did not finish successfully.")

# Configure HTTP basic authorization: basic
configuration = my_pulp3_client.Configuration()
configuration.username = 'admin'
configuration.password = 'admin'
configuration.safe_chars_for_path_param = '/'

client = my_pulp3_client.ApiClient(configuration)

# create an instance of the API class
api = my_pulp3_client.PulpApi(client)

    # Create a File Remote
    remote_url = ''
    remote_data = FileRemote(name='bar', url=remote_url)
    file_remote = api.remotes_file_create(remote_data)

    # Create a Repository
    repository_data = Repository(name='foo')
    repository = api.repositories_create(repository_data)

    # Sync a Repository
    repository_sync_data = my_pulp3_client.RepositorySyncURL(repository=repository.href)
    sync_response = api.remotes_file_sync(file_remote.href, repository_sync_data)

    # Monitor the sync task
    created_resources = monitor_task(sync_response.href)

    repository_version_1 = api.repositories_versions_read(created_resources[0])

    # Create an artifact from a local file
    artifact = api.artifacts_create('devel/pulp3_python_client_example/')

    # Create a FileContent from the artifact
    file_data = FileContent(relative_path='foo.tar.gz', artifact=artifact.href)
    filecontent = api.content_file_files_create(file_data)

    # Add the new FileContent to a repository version
    repo_version_data = {'add_content_units': [filecontent.href]}
    repo_version_response = api.repositories_versions_create(repository.href, repo_version_data)

    # Monitor the repo version creation task
    created_resources = monitor_task(repo_version_response.href)

    repository_version_2 = api.repositories_versions_read(created_resources[0])

    # Create a FilePublisher
    file_publisher_data = FilePublisher(name='bar')
    file_publisher = api.publishers_file_create(file_publisher_data)

    # Create a publication from the latest version of the repository
    publish_data = RepositoryPublishURL(repository=repository.href)
    publish_response = api.publishers_file_publish(file_publisher.href, publish_data)

    # Monitor the publish task
    created_resources = monitor_task(publish_response.href)
    publication_href = created_resources[0]

    distribution_data = Distribution(name='baz', base_path='foo', publication=publication_href)
    distribution = api.distributions_create(distribution_data)
except ApiException as e:
    print("Exception when calling the Api: %s\n" % e)