Python bindings for Podman's RESTful API

Overview

podman-py

Build Status

This python package is a library of bindings to use the RESTful API of Podman. It is currently under development and contributors are welcome!

Dependencies

Example usage

"""Demonstrate PodmanClient."""
import json
from podman import PodmanClient

# Provide a URI path for the libpod service.  In libpod, the URI can be a unix
# domain socket(UDS) or TCP.  The TCP connection has not been implemented in this
# package yet.

uri = "unix:///run/user/1000/podman/podman.sock"

with PodmanClient(base_url=uri) as client:
    version = client.version()
    print("Release: ", version["Version"])
    print("Compatible API: ", version["ApiVersion"])
    print("Podman API: ", version["Components"][0]["Details"]["APIVersion"], "\n")

    # get all images
    for image in client.images.list():
        print(image, image.id, "\n")

    # find all containers
    for container in client.containers.list():
        first_name = container['Names'][0]
        container = client.containers.get(first_name)
        print(container, container.id, "\n")

        # available fields
        print(sorted(container.attrs.keys()))

    print(json.dumps(client.df(), indent=4))

Contributing

See CONTRIBUTING.md

Comments
  • Add exec_run implementation for containers

    Add exec_run implementation for containers

    This change adds a basic implementation of exec_run for containers Environment variable conversions are handled from dict->list[str] DetachKeys will need an actual argument option detach, stream, socket, and demux arguments are currently not handled.

    approved lgtm 
    opened by JacobCallahan 38
  • Use modern tomllib/tomli modules for reading TOML files

    Use modern tomllib/tomli modules for reading TOML files

    Replace the unmaintained toml/pytoml dependencies with the modern alternatives: the built-in tomllib module in Python 3.11, and tomli in older Python versions. Preserving backwards compatibility does not seem necessary, as podman-py no longer supports Python versions older than 3.6.

    Signed-off-by: Michał Górny [email protected]

    approved 
    opened by mgorny 27
  • miscell fixes in README and images, and the embryo of a containers module

    miscell fixes in README and images, and the embryo of a containers module

    • the example in the README now works fine
    • fix broken images.remove()
    • new containers submodule with list_containers, inspect and kill for starters

    this builds on top of PR#18 that I closed before it was merged

    opened by parmentelat 26
  • Add bors for mergebot action

    Add bors for mergebot action

    See documentation https://bors.tech/documentation/getting-started/ and https://bors.tech/documentation/

    Syntax Description bors r+ Run the test suite and push to master if it passes. Short for “reviewed: looks good.” bors merge Equivalent to bors r+. bors r=[list] Same as r+, but the “reviewer” in the commit log will be recorded as the user(s) given as the argument. bors merge=[list] Equivalent to bors r=[list] bors r- Cancel an r+, r=, merge, or merge= bors merge- Equivalent to bors r- bors try Run the test suite without pushing to master. bors try- Cancel a try bors delegate+ bors d+ Allow the pull request author to r+ their changes. bors delegate=[list] bors d=[list] Allow the listed users to r+ this pull request’s changes. bors ping Check if bors is up. If it is, it will comment with pong. bors retry Run the previous command a second time. bors p=[priority] Set the priority of the current pull request. Pull requests with different priority are never batched together. The pull request with the bigger priority number goes first. bors r+ p=[priority] Set the priority, run the test suite, and push to master (shorthand for doing p= and r+ one after the other). bors merge p=[priority] Equivalent to bors r+ p=[priority]

    The keyword (bors) may be separated with a space or a colon. That is, bors try and bors: try are the same thing. Also, the command will be recognized if, and only if, the word “bors” is at the beginning of a line.

    Signed-off-by: Brent Baude [email protected]

    opened by baude 24
  • Allow passing labels to volumes

    Allow passing labels to volumes

    Signed-off-by: Jankowiak Szymon-PRFJ46 [email protected]

    Before changes :

    >>> import podman
    >>> client = podman.PodmanClient(base_url='unix:///run/podman/podman.sock', timeout=300)
    >>> v = client.volumes.create('test', labels={'test_label': 'test_value'})
    >>> v.attrs.get('Labels')
    {}
    >>>
    
    [root@host~]# podman inspect test
    [
        {
            "Name": "test",
            "Driver": "local",
            "Mountpoint": "/var/lib/containers/storage/volumes/test/_data",
            "CreatedAt": "2021-10-21T10:18:06.845889973Z",
            "Labels": {},
            "Scope": "local",
            "Options": {}
        }
    ]
    
    
    Ran 277 tests in 34.861s
    
    FAILED (SKIP=3, errors=5, failures=3)
    

    After changes :

    >>> import podman
    >>> client = podman.PodmanClient(base_url='unix:///run/podman/podman.sock', timeout=300)
    >>> v = client.volumes.create('test', labels={'test_label': 'test_value'})
    >>> v.attrs.get('Labels')
    {'test_label': 'test_value'}
    >>>
    
    [root@host~]# podman inspect test
    [
        {
            "Name": "test",
            "Driver": "local",
            "Mountpoint": "/var/lib/containers/storage/volumes/test/_data",
            "CreatedAt": "2021-10-21T09:27:52.934957768Z",
            "Labels": {
                "test_label": "test_value"
            },
            "Scope": "local",
            "Options": {}
        }
    ]
    
    
    # tox -e coverage
    
    ...
    
    Ran 277 tests in 35.419s
    
    FAILED (SKIP=3, errors=5, failures=3)
    

    Tested on:

    [root@host~]# uname -a
    Linux host.example.com 4.18.0-305.17.1.el8_4.x86_64 #1 SMP Mon Aug 30 07:26:31 EDT 2021 x86_64 x86_64 x86_64 GNU/Linux
    [root@host~]# podman --version
    podman version 3.2.3
    

    I had to modify the test case since it failed on assertion (Labels vs Label), but I'm wondering how this test even passed when it allegedly compared labels from create volume (https://github.com/containers/podman-py/blob/main/podman/tests/unit/test_volumesmanager.py#L77-L82).

    approved lgtm 
    opened by msisj 16
  • Typos style

    Typos style

    Description

    The purpose of this PR is improve the code quality. At this time I used black as code formatter, keeping the maximum length of the line as 79.

    Changes

    Just 4 files were modified:

    • podman/api_connection.py
    • podman/system/__ init __.py
    • podman/images/__ init __.py
    • podman/errors/__ init __.py
    opened by danvergara 14
  • Allow passing all available options to volume mount

    Allow passing all available options to volume mount

    Signed-off-by: Jankowiak Szymon-PRFJ46 [email protected]

    Right now it is possible only to pass mode to mounted volume during container creation. I have no idea what was the reasoning behind it but the Podman REST API is capable of passing more options.

    I'm only concerned about backward compatibility :

    • In docker-py option was called mode but there was possibility to pass multiple arguments (e.g. z,ro)
    • I've renamed option mode -> options to be more precise what this option is actually doing so there is actually no backward compatibility with podman-py. Maybe this option should still be named mode and accept strings as well as list (?) - no idea whether it has to be backward compatible, if not, it is better to rename it.
    >>> import podman
    >>> client = podman.PodmanClient(base_url='unix:///run/podman/podman.sock')
    >>> c1 = client.containers.create(name='test_noexec', image='test_image', volumes={"test_volume": {"bind": "/m", "options": ["rw", "noexec"]}}, command=['/bin/sleep', '12345'])
    >>> c1.start()
    >>> c2 = client.containers.create(name='test_exec', image='test_image', volumes={"test_volume": {"bind": "/m", "options": ["rw", "exec"]}}, command=['/bin/sleep', '12345'])
    >>> c2.start()
    >>> c1.attrs['HostConfig']['Binds']
    ['test_volume:/m:rw,noexec,rprivate,nosuid,nodev,rbind']
    >>> c2.attrs['HostConfig']['Binds']
    ['test_volume:/m:rw,exec,rprivate,nosuid,nodev,rbind']
    
    ...
    
    [root@host ~]# podman exec test_exec cp /bin/true /m/
    [root@host ~]# podman exec -ti test_noexec /m/true
    Error: exec failed: container_linux.go:380: starting container process caused: permission denied: OCI permission denied
    [root@host ~]# podman exec -ti test_exec /m/true
    [root@host ~]#
    

    Ran 277 tests in 40.010s

    FAILED (SKIP=3, errors=4, failures=4)

    approved lgtm 
    opened by msisj 13
  • Add possibility to expose device

    Add possibility to expose device

    Signed-off-by: Jankowiak Szymon-PRFJ46 [email protected]

    This change is temporary solution which allows exposing devices to container. But since podman REST API bases on minor/major numbers (which does not work as it should - path to device on host is needed to be pass and there is a minor/major number which makes no sense to pass too, since path on host is needed. What is more there is no possibility to change path on container according to REST API. On top of all these things, this REST API is non where near compliant with podman CLI (options are totally different). Either way I've heard this is to be reworked in future. Here I just want to give possibility to expose devices in a simplest form.

    >>> import podman
    >>> client = podman.PodmanClient(base_url='unix:///run/podman/podman.sock')
    >>> c = client.containers.create(name='test', image='image:tag', devices=['/dev/hwrng', '/dev/tpm0'])
    >>> c.start()
    >>>
    >>> c.attrs['HostConfig']['Devices']
    [{'PathOnHost': '/dev/hwrng', 'PathInContainer': '/dev/hwrng', 'CgroupPermissions': ''}, {'PathOnHost': '/dev/tpm0', 'PathInContainer': '/dev/tpm0', 'CgroupPermissions': ''}]
    
    ...
    [root@host ~]# podman exec test ls -l /dev/tpm0 /dev/hwrng
    crw------- 1 root root 10, 183 Nov  9 13:40 /dev/hwrng
    crw-rw---- 1 root 9999 10, 224 Nov  9 13:40 /dev/tpm0
    
    approved 
    opened by msisj 12
  • Offer to help

    Offer to help

    Hi 👋 ,

    I just read the announcement that podman is getting a new API that also offers compatibility with Docker. Even though it might seem creepy since this repository is only three days old, I would like to offer my help on this. Currently, I am employed as a python developer, have some spare time soon and would like to use podman from now on. Also, since I have implemented a tool that currently uses the python library for docker quite heavily, I am willing to put some time in the podman API.

    However, I have a question about this repository. As I understood it, the podman API will have a docker compatible API. Why not start by forking the official docker libraries and modifying them? There was a lot of work invested in building them, they work quite well and have no real shortcoming as far as I can tell. Especially docker-compose is a lot more advanced currently than podman-compose.

    opened by nick-lehmann 10
  • update urllib to 1.26.5 for a CVE found in previous versions

    update urllib to 1.26.5 for a CVE found in previous versions

    resolves https://github.com/advisories/GHSA-wqvq-5m8c-6g24 https://issues.redhat.com/browse/OCPBUGS-1926

    Signed-off-by: Charlie Doern [email protected]

    approved lgtm 
    opened by cdoern 9
  • Followup to master -> main conversion

    Followup to master -> main conversion

    Fix the intended destination branch referenced in Cirrus-CI configuration.

    Also update the latest_podman.sh script so it won't be sensitive to containers/podman converting master -> main at some future date.

    Signed-off-by: Chris Evich [email protected]

    opened by cevich 9
  • Added port binding range

    Added port binding range

    Signed-off-by: Jankowiak Szymon-PRFJ46 [email protected]

    Added support for range in ports. The range is available at REST API but was not supported in podman-py. I've tried to keep the backward compatibility (hopefully it works, previously written test case works at the very least). Unfortunately it was impossible to add range without adding new syntax for ports (using dictionary instead of None or int or tuple or list). The newly added syntax should work in the same manner as the previously used one, but with addition of range keyword.

    opened by msisj 2
  • podman.from_env() not working

    podman.from_env() not working

    Everytime I try podman.from_env() I get this error:

    >>> import podman
    >>> podman.from_env()
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "/usr/local/lib/python3.6/site-packages/podman/client.py", line 131, in from_env
        max_pool_size=max_pool_size,
      File "/usr/local/lib/python3.6/site-packages/podman/client.py", line 76, in __init__
        self.api = APIClient(**api_kwargs)
      File "/usr/local/lib/python3.6/site-packages/podman/api/client.py", line 116, in __init__
        self.base_url = self._normalize_url(base_url)
      File "/usr/local/lib/python3.6/site-packages/podman/api/client.py", line 159, in _normalize_url
        f"The scheme '{uri.scheme}' must be one of {APIClient.supported_schemes}"
    ValueError: The scheme 'b''' must be one of ('unix', 'http+unix', 'ssh', 'http+ssh', 'tcp', 'http')
    

    Have tried CentOS 8 stream with a native podman setup and MacOS with podman machine.

    Are they any pre-reqs to be able to use podman.from_env() ?

    Thanks

    CentOS Stream release 8:

    $ podman version
    Client:       Podman Engine
    Version:      4.2.0
    API Version:  4.2.0
    Go Version:   go1.18.4
    Built:        Wed Sep 21 13:15:04 2022
    OS/Arch:      linux/amd64
    

    MacOS:

    % podman version
    Client:       Podman Engine
    Version:      4.3.0
    API Version:  4.3.0
    Go Version:   go1.19
    Git Commit:   ad42af94903ce4f3c3cd0693e4e17e4286bf094b
    Built:        Wed Oct 19 15:33:33 2022
    OS/Arch:      darwin/amd64
    
    Server:       Podman Engine
    Version:      4.3.1
    API Version:  4.3.1
    Go Version:   go1.19.2
    Built:        Fri Nov 11 16:01:27 2022
    OS/Arch:      linux/amd64
    
    opened by josecastillolema 0
  • Issue with the stats container method

    Issue with the stats container method

    I try to grab stats from my podman containers.

    >>> import podman
    >>> client = podman.PodmanClient(base_url="unix:///run/user/1000/podman/podman.sock")
    
    >>> client.version()
    {'Platform': {'Name': 'linux/amd64/ubuntu-22.04'}, 'Components': [{'Name': 'Podman Engine', 'Version': '3.4.4', 'Details': {'APIVersion': '3.4.4', 'Arch': 'amd64', 'BuildTime': '1970-01-01T01:00:00+01:00', 'Experimental': 'false', 'GitCommit': '', 'GoVersion': 'go1.17.3', 'KernelVersion': '5.15.0-48-generic', 'MinAPIVersion': '3.1.0', 'Os': 'linux'}}, {'Name': 'Conmon', 'Version': 'conmon version 2.0.25, commit: unknown', 'Details': {'Package': 'conmon: /usr/bin/conmon'}}, {'Name': 'OCI Runtime (crun)', 'Version': 'crun version 0.17\ncommit: 0e9229ae34caaebcb86f1fde18de3acaf18c6d9a\nspec: 1.0.0\n+SYSTEMD +SELINUX +APPARMOR +CAP +SECCOMP +EBPF +YAJL', 'Details': {'Package': 'crun: /usr/bin/crun'}}], 'Version': '3.4.4', 'ApiVersion': '1.40', 'MinAPIVersion': '1.24', 'GitCommit': '', 'GoVersion': 'go1.17.3', 'Os': 'linux', 'Arch': 'amd64', 'KernelVersion': '5.15.0-48-generic', 'BuildTime': '1970-01-01T01:00:00+01:00'}
    
    >>> containers = client.containers.list()
    >>> containers
    [<Container: 9491515251>, <Container: 1da5bc154a>]
    

    First issue with stream=False:

    >>> print(containers[1].stats(stream=False, decode=True))
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "/home/nicolargo/dev/glances/venv/lib/python3.10/site-packages/podman/domain/containers.py", line 393, in stats
        buffer.writer(json.dumps(entry) + "\n")
    
    

    Second issue with stream=True (nothing is displayed...):

    >>> for s in containers[1].stats(stream=True, decode=False):
    ...     print(s)
    

    Information regarding my system:

    • OS: Ubuntu 22.04
    • Python: 3.10.6
    • Podman-py (installed with Pypi): 4.0.0
    opened by nicolargo 0
  • Getting logs from exec_run in a stream fashion

    Getting logs from exec_run in a stream fashion

    What I want to do is to get stdout/stderr of the command in exec_run line after line. I tried settung stream=True and also detach=True and then after retrieving logs, but no luck. I was only abailable to retrieve logs, once command in exec_run is executed.

    Below example, where logs just hang and nothing happens.

    from podman import PodmanClient
    
    with PodmanClient() as client:
        client.containers.run(
            image="ubuntu",
            name="test",
            detach=True,
        )
        cmd = "apt-get update"
    
        print(cmd)
        res = client.containers.list()[-1].exec_run(
            cmd,
            detach=True,
        )
        print("before")
        print(res)
        logs = client.containers.list()[-1].logs(stream=True)
    
        for r in logs:
            print(r.decode("UTF-8"))
    

    If I set stream=True, then bug in https://github.com/containers/podman-py/issues/201 will happen.

    Is there a way to get these logs in a streamed way until fix for https://github.com/containers/podman-py/issues/201 is ready?

    opened by AlexKaravaev 0
  • podman run not working

    podman run not working

    Hello,

    I use the lib version 4.2.0, Python 3.10.4, podman 3.4.4.

    If I try to use client.containers.run I get the following error:

    >>> import podman
    >>> 
    >>> client = podman.PodmanClient()
    >>> 
    >>> client.images.pull("docker.io/library/ubuntu:20.04")
    <Image: 'docker.io/library/ubuntu:20.04'>
    >>> 
    >>> image = client.images.pull("docker.io/library/ubuntu:20.04")
    >>> 
    >>> client.containers.run(image, ["ls", "/"])
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "/home/kai/.local/lib/python3.10/site-packages/podman/domain/containers_run.py", line 80, in run
        exit_status = container.wait()["StatusCode"]
    TypeError: 'int' object is not subscriptable
    >>> 
    

    Are I'm doing something wrong or is there a bug?

    Thanks for the help Kai

    opened by KaiBroeker 4
Releases(v4.2.1)
Owner
Containers
Open Repository for Container Tools
Containers
Restful API framework wrapped around MongoEngine

Flask-MongoRest A Restful API framework wrapped around MongoEngine. Setup from flask import Flask from flask_mongoengine import MongoEngine from flask

Close 525 Jan 1, 2023
RESTful Todolist API

RESTful Todolist API GET todolist/ POST todolist/ {"desc" : "Description of task to do"} DELETE todolist/<int:id> PUT todolist/<int:id> Requirements D

Gabriel Tavares 5 Dec 20, 2021
A RESTful way to use your Notion tables as a database.

rest-notion-db A RESTful way to use your Notion tables as a database. Use-cases Form submissions or frontend websites, use one database that

Oorjit Chowdhary 42 Dec 27, 2022
A RESTful whois

whois-rest A RESTful whois. Installation $ pip install poetry $ poetry install $ uvicorn app:app INFO: Started server process [64616] INFO: W

Manabu Niseki 4 Feb 19, 2022
A simple API example in Python (Flask framework)

API-Example A simple API in Python(Flask) ✨ Features An API i guess? ??‍♀️ How to use first download the main.py install python then install flask fra

Portgas D Ace 2 Jan 6, 2022
Build a Backend REST API with Python & Django

Build a Backend REST API with Python & Django Skills Python Django djangorestframework Aws Git Use the below Git commands in the Windows Command Promp

JeonSoohyun a.k.a Edoc.. 1 Jan 25, 2022
Allows simplified Python interaction with Rapid7's InsightIDR REST API.

InsightIDR4Py Allows simplified Python interaction with Rapid7's InsightIDR REST API. InsightIDR4Py allows analysts to query log data from Rapid7 Insi

Micah Babinski 8 Sep 12, 2022
A small project in Python + Flask to demonstrate how to create a REST API

SmartBed-RESTApi-Example This application is an example of how to build a REST API. The application os a mock IoT device, simulating a Smart Bed. Impl

Rares Cristea 6 Jan 28, 2022
Flask RestAPI Project - Transimage Rest API For Python

[ 이미지 변환 플라스크 Rest API ver01 ] 0. Flask Rest API - in SunnyWeb : 이미지 변환 웹의 Flask

OliverKim 1 Jan 12, 2022
Mlflow-rest-client - Python client for MLflow REST API

Python Client for MLflow Python client for MLflow REST API. Features: Minimal de

MTS 35 Dec 23, 2022
REST API framework designed for human beings

Eve Eve is an open source Python REST API framework designed for human beings. It allows to effortlessly build and deploy highly customizable, fully f

eve 6.6k Jan 4, 2023
The Web API toolkit. 🛠

?? The Web API toolkit. ?? Community: https://discuss.apistar.org ?? ?? ?? ?? ?? Documentation: https://docs.apistar.com ?? Requirements: Python 3.6+

Encode 5.6k Dec 27, 2022
Kong API Manager with Prometheus And Splunk

API Manager Stack Run Kong Server + Konga + Prometheus + Grafana + API & DDBB + Splunk Clone the proyect and run docker-compose up

Santiago Fernandez 82 Nov 26, 2022
Django REST API with React BoilerPlate

This is a setup of Authentication and Registration Integrated with React.js inside the Django Templates for web apps

Faisal Nazik 91 Dec 30, 2022
Estudo e desenvolvimento de uma API REST

Estudo e desenvolvimento de uma API REST ??‍?? Tecnologias Esse projeto utilizará as seguintes tecnologias: Git Python Flask DBeaver Vscode SQLite ??

Deusimar 7 May 30, 2022
Example Starlette REST API application

The idea of this project is to show how Starlette, Marshmallow, and SQLAlchemy can be combined to create a RESTful HTTP API application that is modular, lightweight, and capable of dealing with many simultaneous requests.

Robert Wikman 0 Jan 7, 2022
RESTler is the first stateful REST API fuzzing tool for automatically testing cloud services through their REST APIs and finding security and reliability bugs in these services.

RESTler is the first stateful REST API fuzzing tool for automatically testing cloud services through their REST APIs and finding security and reliability bugs in these services.

Microsoft 1.8k Jan 4, 2023
JSON:API support for Django REST framework

JSON:API and Django REST framework Overview JSON:API support for Django REST framework Documentation: https://django-rest-framework-json-api.readthedo

null 1k Dec 27, 2022