Skip to main content

Reutilización de flujos de trabajo

Aprende cómo evitar la duplicación al crear un flujo de trabajo reusando los flujos existentes.

Crear un flujo de trabajo reutilizable

Los flujos de trabajo reutilizables son archivos con formato YAML, muy similares a cualquier otro archivo de flujo de trabajo. Al igual que con otros archivos de flujo de trabajo, puede buscar flujos de trabajo reutilizables en el directorio .github/workflows de un repositorio. No se admiten subdirectorios del directorio workflows.

Puedes estandarizar las implementaciones creando un grupo de ejecutores autohospedado que solo ejecute un flujo de trabajo reutilizable. Para más información, consulta Administración del acceso a los ejecutores autohospedados mediante grupos.

Para que un flujo de trabajo sea reutilizable, los valores de on deben incluir workflow_call:

on:
  workflow_call:

Utilizar entradas y secretos en un flujo de trabajo reutilizable

Puede definir entradas y secretos, las cuales pueden pasarse desde el flujo de trabajo llamante y luego utilizarse dentro del flujo llamado. Existen tres etapas para utilizar una entrada o un secreto en un flujo de trabajo reutilizable.

  1. En el flujo de trabajo reutilizable, use las palabras clave inputs y secrets para definir entradas o secretos que se enviarán desde un flujo de trabajo que inicia una llamada.

    on:
      workflow_call:
        inputs:
          config-path:
            required: true
            type: string
        secrets:
          personal_access_token:
            required: true
    

Para obtener más información sobre la sintaxis para definir entradas y secretos, consulte on.workflow_call.inputs y on.workflow_call.secrets.

  1. En el flujo de trabajo reutilizable, haz referencia a la entrada o el secreto que definiste en la clave on del paso anterior.

    Nota:

    Si los secretos se heredan mediante secrets: inherit flujos de trabajo de llamada, puedes hacer referencia a ellos incluso si no están definidos en la clave on. Para más información, consulta Sintaxis del flujo de trabajo para GitHub Actions.

    jobs:
      reusable_workflow_job:
        runs-on: ubuntu-latest
        steps:
        - uses: actions/labeler@v4
          with:
            repo-token: ${{ secrets.personal_access_token }}
            configuration-path: ${{ inputs.config-path }}
    

    En el ejemplo anterior, personal_access_token es un secreto que está definido a nivel de repositorio u organización.

    Advertencia

    Los secretos de entorno no se pueden pasar desde el flujo de trabajo del autor de la llamada, ya que on.workflow_call no admite la palabra clave environment. Si incluye environment en el flujo de trabajo reutilizable a nivel de trabajo, se usará el secreto de entorno y no el secreto pasado desde el flujo de trabajo del autor de la llamada. Para más información, consulta Administrar entornos para la implementación y Sintaxis del flujo de trabajo para GitHub Actions.

  2. Pasa la entrada o secreto desde el flujo de trabajo llamante.

    Para pasar entradas con nombre a un flujo de trabajo con nombre, use la palabra clave with en un trabajo. Use la palabra clave secrets para pasar secretos con nombre. Para las entradas, el tipo de datos del valor de entrada debe empatar con el tipo especificado en el flujo de trabajo llamado (ya sea booleano, número o secuencia).

    jobs:
      call-workflow-passing-data:
        uses: octo-org/example-repo/.github/workflows/reusable-workflow.yml@main
        with:
          config-path: .github/labeler.yml
        secrets:
          personal_access_token: ${{ secrets.token }}
    

    Los flujos de trabajo que llaman a flujos de trabajo reutilizables de la misma organización o empresa pueden usar la palabra clave inherit para pasar implícitamente los secretos.

    jobs:
      call-workflow-passing-data:
        uses: octo-org/example-repo/.github/workflows/reusable-workflow.yml@main
        with:
          config-path: .github/labeler.yml
        secrets: inherit
    

Flujo de trabajo reutilizable de ejemplo

Este archivo de flujo de trabajo reutilizable llamado workflow-B.yml (nos referiremos a él más adelante en el flujo de trabajo llamante de ejemplo) toma una cadena de entrada y un secreto del flujo que inicia la llamada y lo utiliza en una acción.

YAML
name: Reusable workflow example

on:
  workflow_call:
    inputs:
      config-path:
        required: true
        type: string
    secrets:
      token:
        required: true

jobs:
  triage:
    runs-on: ubuntu-latest
    steps:
    - uses: actions/labeler@v4
      with:
        repo-token: ${{ secrets.token }}
        configuration-path: ${{ inputs.config-path }}

Llamar a un flujo de trabajo reutilizable

Para llamar a un flujo de trabajo reutilizable, use la palabra clave uses. A diferencia de cuando utilizas acciones en un flujo de trabajo, los flujos de trabajo reutilizables se llaman directamente desde un job y no dentro de los pasos de un job.

jobs.<job_id>.uses

Puede hacer referencia a archivos de flujo de trabajo reutilizables mediante una de las sintaxis siguientes:

  • {owner}/{repo}/.github/workflows/{filename}@{ref} para flujos de trabajo reutilizables en repositorios públicos, internos y privados.
  • ./.github/workflows/{filename} para flujos de trabajo reutilizables en el mismo repositorio.

En la primera opción, {ref} puede ser un SHA, una etiqueta de lanzamiento o un nombre de rama. Si una etiqueta de versión y una rama tienen el mismo nombre, la primera tiene prioridad sobre el nombre de la rama. Utilizar el SHA de la confirmación es la opción más segura para lograr estabilidad y seguridad. Para más información, consulta Referencia de uso seguro.

Si usas la segunda opción de sintaxis (sin {owner}/{repo} y @{ref}), el flujo de trabajo que se llama procede de la misma confirmación que el flujo de trabajo autor de la llamada. No se permiten prefijos de referencia como refs/heads y refs/tags. No puedes utilizar contextos o expresiones en esta palabra clave.

Puede llamar a flujos de trabajo múltiples, referenciando cada uno en un job separado.

jobs:
  call-workflow-1-in-local-repo:
    uses: octo-org/this-repo/.github/workflows/workflow-1.yml@172239021f7ba04fe7327647b213799853a9eb89
  call-workflow-2-in-local-repo:
    uses: ./.github/workflows/workflow-2.yml
  call-workflow-in-another-repo:
    uses: octo-org/another-repo/.github/workflows/workflow.yml@v1

Flujo de trabajo llamante de ejemplo

Este archivo de flujo de trabajo llama a otros dos archivos de flujo de trabajo. El segundo, workflow-B.yml (que se muestra en el flujo de trabajo reutilizable de ejemplo), recibe una entrada (config-path) y un secreto (token).

YAML
name: Call a reusable workflow

on:
  pull_request:
    branches:
      - main

jobs:
  call-workflow:
    uses: octo-org/example-repo/.github/workflows/workflow-A.yml@v1

  call-workflow-passing-data:
    permissions:
      contents: read
      pull-requests: write
    uses: octo-org/example-repo/.github/workflows/workflow-B.yml@main
    with:
      config-path: .github/labeler.yml
    secrets:
      token: ${{ secrets.GITHUB_TOKEN }}

Pasar entradas y secretos a un flujo de trabajo reutilizable

Para pasar entradas con nombre a un flujo de trabajo con nombre, use la palabra clave with en un trabajo. Use la palabra clave secrets para pasar secretos con nombre. Para las entradas, el tipo de datos del valor de entrada debe empatar con el tipo especificado en el flujo de trabajo llamado (ya sea booleano, número o secuencia).

jobs:
  call-workflow-passing-data:
    uses: octo-org/example-repo/.github/workflows/reusable-workflow.yml@main
    with:
      config-path: .github/labeler.yml
    secrets:
      personal_access_token: ${{ secrets.token }}

Los flujos de trabajo que llaman a flujos de trabajo reutilizables de la misma organización o empresa pueden usar la palabra clave inherit para pasar implícitamente los secretos.

jobs:
  call-workflow-passing-data:
    uses: octo-org/example-repo/.github/workflows/reusable-workflow.yml@main
    with:
      config-path: .github/labeler.yml
    secrets: inherit

Uso de una estrategia de matriz con un flujo de trabajo reutilizable

Los trabajos que usan la estrategia de matriz pueden llamar a un flujo de trabajo reutilizable.

Una estrategia de matriz permite usar variables en una definición de trabajo para crear automáticamente varias ejecuciones de trabajos basadas en las combinaciones de las variables. Por ejemplo, puede usar una estrategia de matriz para pasar diferentes entradas a un flujo de trabajo reutilizable. Para obtener más información sobre las matrices, consulta Ejecución de variaciones de trabajos en un flujo de trabajo.

El siguiente trabajo de ejemplo llama a un flujo de trabajo reutilizable y hace referencia al contexto de la matriz mediante la definición de la variable target con los valores [dev, stage, prod]. Ejecutará tres trabajos, uno para cada valor de la variable.

YAML
jobs:
  ReusableMatrixJobForDeployment:
    strategy:
      matrix:
        target: [dev, stage, prod]
    uses: octocat/octo-repo/.github/workflows/deployment.yml@main
    with:
      target: ${{ matrix.target }}

Anidación de flujos de trabajo reutilizables

Puede conectar un máximo de cuatro niveles de flujos de trabajo, es decir, el flujo de trabajo del autor de la llamada de nivel superior y hasta tres niveles de flujos de trabajo reutilizables. Por ejemplo: caller-workflow.ymlcalled-workflow-1.ymlcalled-workflow-2.ymlcalled-workflow-3.yml. No se permiten bucles en el árbol de flujo de trabajo.

Nota:

Los flujos de trabajo reutilizables anidados requieren que todos los flujos de trabajo de la cadena sean accesibles para el autor de la llamada, y los permisos solo se pueden mantener o reducir (no elevar) en toda la cadena. Para más información, consulta Referencia de flujos de trabajo reutilizables.

Desde dentro de un flujo de trabajo reutilizable, puede llamar a otro flujo de trabajo reutilizable.

YAML
name: Reusable workflow

on:
  workflow_call:

jobs:
  call-another-reusable:
    uses: octo-org/example-repo/.github/workflows/another-reusable.yml@v1

Pasar secretos a flujos de trabajo anidados

Puede usar jobs.<job_id>.secrets en un flujo de trabajo de llamada para pasar secretos con nombre a un flujo de trabajo llamado directamente. Como alternativa, puede usar jobs.<job_id>.secrets.inherit para pasar todos los secretos del flujo de trabajo de llamada a un flujo de trabajo llamado directamente. Para obtener más información, consulta la sección Reutilización de flujos de trabajo anterior y el artículo de referencia Sintaxis del flujo de trabajo para GitHub Actions. Los secretos solo se pasan al flujo de trabajo llamado directamente, por lo que en la cadena de flujo de trabajo A > B > C, el flujo de trabajo C solo recibirá secretos de A si se han pasado de A a B y, a continuación, de B a C.

En el ejemplo siguiente, el flujo de trabajo A pasa todos sus secretos al flujo de trabajo B, mediante la palabra clave inherit, pero el flujo de trabajo B solo pasa un secreto al flujo de trabajo C. Ninguno de los demás secretos pasados al flujo de trabajo B no está disponible para el flujo de trabajo C.

jobs:
  workflowA-calls-workflowB:
    uses: octo-org/example-repo/.github/workflows/B.yml@main
    secrets: inherit # pass all secrets
jobs:
  workflowB-calls-workflowC:
    uses: different-org/example-repo/.github/workflows/C.yml@main
    secrets:
      repo-token: ${{ secrets.personal_access_token }} # pass just this secret

Utilizar salidas desde un flujo de trabajo reutilizable

Un flujo de trabajo reutilizable podría generar datos que quieras utilizar en el flujo de trabajo llamante. Para utilizar estas salidas, debes especificarlas como las salidas del flujo de trabajo reutilizable.

Si un flujo de trabajo reutilizable que establece una salida se ejecuta con una estrategia de matriz, la salida será la salida establecida por el último flujo de trabajo reutilizable completado correctamente de la matriz que realmente establece un valor. Esto significa que si el último flujo de trabajo reutilizable completado correctamente establece una cadena vacía para su salida y el segundo último flujo de trabajo reutilizable completado correctamente establece un valor real para su salida, la salida contendrá el valor del segundo último flujo de trabajo reutilizable completado.

Los siguientes flujos de trabajo reutilizables tienen un solo job que contiene dos pasos. En cada uno de estos pasos, configuramos una sola palabra como la salida: "hello" y "world". En la sección outputs del trabajo, asignamos estas salidas de paso a las salidas de trabajo llamadas: output1 y output2. En la sección on.workflow_call.outputs, definimos dos salidas para el propio flujo de trabajo: una denominada firstword que se asigna a output1 y otra denominada secondword que se asigna a output2.

value debe establecerse en el valor de una salida de nivel de trabajo dentro del flujo de trabajo llamado. Las salidas de nivel de paso deben asignarse primero a las salidas de nivel de trabajo, como se muestra a continuación.

Para más información, consulta Pasar información entre trabajos y Sintaxis del flujo de trabajo para GitHub Actions.

YAML
name: Reusable workflow

on:
  workflow_call:
    # Map the workflow outputs to job outputs
    outputs:
      firstword:
        description: "The first output string"
        value: ${{ jobs.example_job.outputs.output1 }}
      secondword:
        description: "The second output string"
        value: ${{ jobs.example_job.outputs.output2 }}

jobs:
  example_job:
    name: Generate output
    runs-on: ubuntu-latest
    # Map the job outputs to step outputs
    outputs:
      output1: ${{ steps.step1.outputs.firstword }}
      output2: ${{ steps.step2.outputs.secondword }}
    steps:
      - id: step1
        run: echo "firstword=hello" >> $GITHUB_OUTPUT
      - id: step2
        run: echo "secondword=world" >> $GITHUB_OUTPUT

Ahora podemos utilizar las salidas en el flujo de trabajo llamante, de la misma forma en la que utilizarías las salidas de un job dentro del mismo flujo de trabajo. Hacemos referencia a las salidas mediante los nombres definidos a nivel de flujo de trabajo en el flujo de trabajo reutilizable: firstword y secondword. En este flujo de trabajo, job1 llama al flujo de trabajo reutilizable y job2 imprime las salidas del flujo de trabajo reutilizable ("hola mundo") a la salida estándar del registro de flujo de trabajo.

YAML
name: Call a reusable workflow and use its outputs

on:
  workflow_dispatch:

jobs:
  job1:
    uses: octo-org/example-repo/.github/workflows/called-workflow.yml@v1

  job2:
    runs-on: ubuntu-latest
    needs: job1
    steps:
      - run: echo ${{ needs.job1.outputs.firstword }} ${{ needs.job1.outputs.secondword }}

Para obtener más información sobre el uso de salidas de trabajo, consulta Sintaxis del flujo de trabajo para GitHub Actions. Si desea compartir algo distinto de una variable (por ejemplo, un artefacto de compilación) entre flujos de trabajo, consulta Store and share data with workflow artifacts.

Monitorear qué flujos de trabajo se están utilizando

Puede utilizar la API de REST de GitHub para monitorear cómo se utilizan los flujos de trabajo reutilizables. La acción de registro de auditoría prepared_workflow_job se desencadena cuando se inicia un trabajo de flujo de trabajo. Entre los datos registrados se incluyen:

  • repo: la organización o el repositorio donde se ubica el trabajo de flujo de trabajo. Para un job que llama a otro flujo de trabajo, esta es la organización/repositorio del flujo llamador.
  • @timestamp: la fecha y hora en que se inició el trabajo, en formato de tiempo de Unix.
  • job_name: el nombre del trabajo que se ejecutó.
  • calling_workflow_refs : una matriz de rutas de acceso de archivo para todos los flujos de trabajo del autor de la llamada implicados en este trabajo del flujo de trabajo. Los elementos de la matriz están en el orden inverso con el que se llamaron. Por ejemplo, en una cadena de flujos de trabajo A > B > C, al ver los registros de un trabajo en el flujo de trabajo C, la matriz será ["octo-org/octo-repo/.github/workflows/B.yml", "octo-org/octo-repo/.github/workflows/A.yml"].
  • calling_workflow_shas : una matriz de varios SHA para todos los flujos de trabajo del autor de la llamada implicados en este trabajo del flujo de trabajo. La matriz contiene el mismo número de elementos, y en el mismo orden, que la matriz calling_workflow_refs.
  • job_workflow_ref: el archivo de flujo de trabajo que se usó, con el formato {owner}/{repo}/{path}/{filename}@{ref}. Para un job que llama a otro flujo de trabajo, esto identifica al flujo llamado.

Para más información, consulta Revisar el registro de auditoría de tu organización.

Nota:

Los datos de auditoría de prepared_workflow_job solo se pueden ver mediante la API REST. No se puede ver en la interfaz web de GitHub ni se incluye en los datos de auditoría exportados en JSON/CSV.

Pasos siguientes

Para buscar información sobre las complejidades de la reutilización de flujos de trabajo, consulta Referencia de flujos de trabajo reutilizables.