Skip to main content

Command Palette

Search for a command to run...

⚙️ Como automatizar tu librería en PyPI con GitHub Actions

Updated
7 min read
⚙️ Como automatizar tu librería en PyPI con GitHub Actions
R
Experienced software developer with 15+ years of expertise in designing, developing and implementing web systems across various sectors. Backend specialist skilled in Python, Linux, and Git. Passionate about continuous learning and open-source technology.

Continuando con un post anterior donde publicamos nuestra librería a PyPI, vamos a ir un paso más allá en el proceso de construcción y despliegue (o, mejor dicho, build y release). En este tutorial, crearemos nuestro propio workflow en GitHub Actions, aprovechando que nuestro repositorio ya está en GitHub, para automatizar este proceso y hacerlo más eficiente y menos propenso a errores.

Al final de este tutorial tendremos configurado un workflow que construye y publica en PyPI de forma automática con cada nueva release que se cree en el repositorio de GitHub.

👉 Si aún no publicaste tu librería en PyPI, te recomiendo comenzar por este tutorial previo:

⚙️ ¿Qué es GitHub Actions?

GitHub Actions es una plataforma de CI/CD (Integración y Entrega Continua) integrada directamente en GitHub. Permite automatizar tareas dentro del ciclo de vida de tu proyecto, como ejecutar tests, construir paquetes, y desplegar código, todo sin salir de tu repositorio.

La magia está en los workflows, que son conjuntos de instrucciones definidas en archivos YAML. Estos workflows se ejecutan en respuesta a eventos específicos, como hacer un push, crear un tag, abrir un pull request o crear un nuevo release.

En el caso de una librería de Python, esto nos permite automatizar pasos como:

  • Construir los paquetes (sdist y wheel)

  • Publicar automáticamente en PyPI o TestPyPI cuando subimos una nueva versión

Con unas pocas líneas de configuración, podemos lograr que todo esto suceda de forma automática cada vez que haces un release, reduciendo errores y ganando tiempo.

📦 Automatizando la publicación en PyPI con GitHub Actions

✅ Requisitos previos

Antes de iniciar, asegúrate de tener:

  • Un repositorio de GitHub con tu librería

  • Una cuenta de PyPI

  • Un API Token generado de tu cuenta de PyPI

👉 Si ya seguiste el tutorial anterior, deberías tener todo esto listo. Si no, te recomiendo revisarlo antes de seguir.

🔐 Agregar tu token de PyPI como secret en GitHub

Debemos configurar en nuestro repositorio un nuevo secret para usarlo en los workflows, para esto solo debemos seguir los siguientes pasos:

  1. Ir a tu repositorio en GitHub.

  2. Hacer clic en Settings.

  3. En el menú lateral, clic en Secrets and variables → Actions.

  1. Clic en New repository secret.

  2. El nombre será PYPI_API_TOKEN y en el valor pegá tu API key de PyPI.

  3. Clic en Add secret.

Esto es lo que usa GitHub Actions para autenticar y publicar la librería.

📁 Estructura de archivos

Ya con todo esto listo podemos empezar, lo primero que debemos saber es que para que nuestra Github Actions funcione los workflows deben estar en una carpeta llama .github/workflows en la raíz de nuestro repositorio, dentro de esta carpeta ira nuestro archivo de workflow llamado python-publish.yml.

Podemos crear todo usando los siguientes comandos:

$ mkdir -p .github/workflows
$ touch .github/workflows/python-publish.yml

La estructura de archivos quedaría similar a esta:

rafnixg-lib/
│
├── .github/
│   └── workflows/
│       └── python-publish.yml
├── src/
│   └── rafnixg/
│       ├── __init__.py
│       ├── __main__.py
│       └── rafnixg.py
│
├── LICENSE
├── README.md
└── pyproject.toml

🚀 Configurando el workflow

Vamos a iniciar creando el contenido de nuestro archivo de workflow python-publish.yml.

🎯Activando el workflow al publicar un release

name: Publicar Paquete a PyPI

on:
  release:
    types: [published]

Esto indica el nombre que tendrá nuestro workflow y también define que solo se va a ejecutar cuando las release sean published con esto limitamos que solo estas acciones sean las que disparen nuestro workflow.

🛡️Definir permisos mínimos necesarios

permissions:
  contents: read

Acá le decimos a GitHub Actions que este workflow solo necesita leer el contenido del repositorio. Es una buena práctica limitar los permisos al mínimo necesario.

🛠️Crear el job y configurar el entorno

jobs:
  deploy:
    runs-on: ubuntu-latest

Creamos un job llamado deploy, que se ejecutará en un entorno virtual Ubuntu. Este job va a encargarse de construir y publicar nuestro paquete.

📋Agregar los pasos del workflow

Los steps son partes del proceso que irán ejecutando de forma secuencia y serán lo que ejecutarán los pasos para publicar nuestra librería en PyPI luego de ser construida.

En los steps se puede hacer uso de otros actions creados por otros usuarios como si de librerías se tratase, solo debemos indicarlo con uses: actions/nombre-del-actions@version y tambien podemos usar comando sobre la máquina virtual donde se está ejecutando la actions con el comando run: comando bash

steps:
    - name: Clonando repositorio
      uses: actions/checkout@v3

    - name: Configurando Python 3
      uses: actions/setup-python@v3
      with:
        python-version: '3.x'

    - name: Instalando dependencias
      run: |
        python -m pip install --upgrade pip
        pip install build

    - name: Construir Paquete
      run: python -m build

    - name: Publicar Paquete
      uses: pypa/gh-action-pypi-publish@release/v1
      with:
        user: __token__
        password: ${{ secrets.PYPI_API_TOKEN }}

📂 Clonando el repositorio

- name: Clonando repositorio
  uses: actions/checkout@v3

Usamos la acción oficial para clonar el código del repositorio, paso necesario para poder construir el paquete.

🐍 Configurar el entorno de Python

- name: Configurando Python 3
  uses: actions/setup-python@v3
  with:
    python-version: '3.x'

Le decimos a GitHub Actions que configure un entorno de Python (versión 3.x). Esto es clave para poder instalar dependencias y ejecutar los comandos de build.

📥 Instalando las dependencias necesarias

- name: Instalando dependencias
  run: |
    python -m pip install --upgrade pip
    pip install build

Actualizamos pip y luego instalamos el módulo build, que nos permite crear los archivos .tar.gz y .whl que necesita PyPI.

🏗️Construir el paquete

- name: Construir Paquete
  run: python -m build

Este paso ejecuta python -m build, que genera el paquete listo para ser publicado en la carpeta dist/.

📤Publicar el paquete en PyPI

- name: Publicar Paquete
  uses: pypa/gh-action-pypi-publish@release/v1
  with:
    user: __token__
    password: ${{ secrets.PYPI_API_TOKEN }}

Finalmente, usamos la acción oficial para subir el paquete a PyPI. Aquí usamos el API Key que se guarda como Secret en el repositorio de GitHub (PYPI_API_TOKEN), para evitar exponer credenciales.

📄 Archivo completo del workflow (python-publish.yml)

El archivo python-publish.yml finalmente queda de la siguiente manera:

name: Publicar Paquete a PyPI
on:
  release:
    types: [published]
jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
        - name: Clonando repositorio
          uses: actions/checkout@v3

        - name: Configurando Python 3
          uses: actions/setup-python@v3
          with:
            python-version: '3.x'

        - name: Instalando dependencias
          run: |
            python -m pip install --upgrade pip
            pip install build

        - name: Construir Paquete
          run: python -m build

        - name: Publicar Paquete
          uses: pypa/gh-action-pypi-publish@release/v1
          with:
            user: __token__
            password: ${{ secrets.PYPI_API_TOKEN }}

💾 Subiendo los cambios al repositorio

Ya con nuestro archivo creado, solo nos resta subir un commit con los cambios que tenemos:

$ git add .github/workflows/python-publish.yml
$ git commit -m "Add GitHub Actions workflow for PyPI release"
$ git push origin

Creamos un tag y lo subimos:

$ git tag v1.0.1
$ git push origin --tags

Revisamos nuestro repositorio de GitHub y nos aseguramos de que se subió todo correctamente, para seguir con la creación de una nueva release.

🏷️ Crear una nueva release en GitHub

En nuestro repositorio hacemos clic en Releases. para ingresar a la página de todas las releases que vamos a haciendo.

En esta página hacemos clic en “draf a new release“

Esto nos abre el formulario para crear nuevas releases, acá debemos seleccionar el tag correspondiente con la release en “Choose a tag“ y hacer clic en “Generate release notes“, esto genera una descripción usando los commits y los Pull Request.

Por último, revisa la descripción ajusta si lo necesitas y dale clic a “Publish release“.

✅ Verificar el resultado de la publicación

Cada vez que crees una nueva release, se publicará una nueva versión de tu paquete en PyPI. En la tab “Actions“ de nuestro repositorio vamos a ver cómo se ejecuta el workflow que lo publica.

🧠 Conclusión

Automatizar la publicación con GitHub Actions no solo te ahorra tiempo, también reduce errores y hace que todo el proceso sea mucho más limpio y profesional. Una vez configurado, solo tienes que enfocarte en mejorar tu librería y dejar que la publicación se maneje sola ✨

🔍Referencias

🔗 Documentación oficial GitHub Actions

🔗 Documentación oficial PyPI usando GitHub Actions

🔗 Documentacion del GitHub Actions PyPI Publish

More from this blog

R

Rafnix Guzman - Python Backend | AI Engineer | Odoo Developer

16 posts

Python Software Developer | Odoo Developer | Tech Writer | Generative AI