# Gestión de caché con GitHub Actions


Esta página contiene ejemplos sobre el uso de los backends de almacenamiento de caché con GitHub Actions.

> [!NOTE]
>
> Consulta [Backends de almacenamiento de caché](/build/cache/backends/) para
> más detalles sobre los backends de almacenamiento de caché.

## Caché inline

En la mayoría de los casos, querrás usar el [exportador de caché inline](/build/cache/backends/inline/). Sin embargo, ten en cuenta que el exportador de caché `inline` solo admite el modo de caché `min`. Para usar el modo de caché `max`, envía la imagen y la caché por separado utilizando el exportador de caché de registro (`registry`) con la opción `cache-to`, como se muestra en el [ejemplo de caché de registro](#registry-cache).

```yaml
name: ci

on:
  push:

jobs:
  docker:
    runs-on: ubuntu-latest
    steps:
      - name: Iniciar sesión en Docker Hub
        uses: docker/login-action@v4
        with:
          username: ${{ vars.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Configurar Docker Buildx
        uses: docker/setup-buildx-action@v4

      - name: Compilar y enviar
        uses: docker/build-push-action@v7
        with:
          push: true
          tags: user/app:latest
          cache-from: type=registry,ref=user/app:latest
          cache-to: type=inline
```

## Caché de registro (registry)

Puedes importar y exportar caché desde un manifiesto de caché o una configuración de imagen (especial) en el registro con el [exportador de caché de registro (`registry`)](/build/cache/backends/registry/).

```yaml
name: ci

on:
  push:

jobs:
  docker:
    runs-on: ubuntu-latest
    steps:
      - name: Iniciar sesión en Docker Hub
        uses: docker/login-action@v4
        with:
          username: ${{ vars.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Configurar Docker Buildx
        uses: docker/setup-buildx-action@v4

      - name: Compilar y enviar
        uses: docker/build-push-action@v7
        with:
          push: true
          tags: user/app:latest
          cache-from: type=registry,ref=user/app:buildcache
          cache-to: type=registry,ref=user/app:buildcache,mode=max
```

## Caché de GitHub

### API del backend de caché




El backend del [exportador de caché de GitHub Actions](/build/cache/backends/gha/) utiliza la [API del servicio de caché de GitHub](https://github.com/tonistiigi/go-actions-cache) para recuperar y cargar blobs de caché. Por eso, solo deberías utilizar este backend de caché en un flujo de trabajo de GitHub Actions, ya que los atributos `url` (`$ACTIONS_RESULTS_URL`) y `token` (`$ACTIONS_RUNTIME_TOKEN`) solo se rellenan en el contexto de un flujo de trabajo.

```yaml
name: ci

on:
  push:

jobs:
  docker:
    runs-on: ubuntu-latest
    steps:
      - name: Iniciar sesión en Docker Hub
        uses: docker/login-action@v4
        with:
          username: ${{ vars.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Configurar Docker Buildx
        uses: docker/setup-buildx-action@v4

      - name: Compilar y enviar
        uses: docker/build-push-action@v7
        with:
          push: true
          tags: user/app:latest
          cache-from: type=gha
          cache-to: type=gha,mode=max
```

> [!IMPORTANT]
>
> A partir del 15 de abril de 2025, [solo se admite la API v2 del servicio de caché de GitHub.](https://gh.io/gha-cache-sunset). La API v1 heredada se ha desactivado.
>
> Si encuentras el siguiente error durante tu compilación:
>
> ```console
> ERROR: failed to solve: This legacy service is shutting down, effective April 15, 2025. Migrate to the new service ASAP. For more information: https://gh.io/gha-cache-sunset
> ```
>
> Es probable que estés utilizando herramientas obsoletas que solo admiten la API v1 heredada del servicio de caché de GitHub. Aquí tienes las versiones mínimas a las que debes actualizar según tu caso de uso:
>
> - Docker Buildx >= v0.21.0
> - BuildKit >= v0.20.0
> - Docker Compose >= v2.33.1
> - Docker Engine >= v28.0.0 (si estás compilando con el controlador Docker y tienes habilitado el almacén de imágenes de containerd)
>
> Si estás compilando con las acciones `docker/build-push-action` o `docker/bake-action` en runners alojados por GitHub, Docker Buildx y BuildKit ya están actualizados, pero en runners autohospedados (self-hosted), es posible que debas actualizarlos tú mismo. Alternativamente, puedes usar la acción `docker/setup-buildx-action` para instalar la versión más reciente de Docker Buildx:
>
> ```yaml
> - name: Set up Docker Buildx
>   uses: docker/setup-buildx-action@v4
>   with:
>     version: latest
> ```
>
> Si estás compilando con Docker Compose, puedes usar la acción `docker/setup-compose-action`:
>
> ```yaml
> - name: Set up Docker Compose
>   uses: docker/setup-compose-action@v2
>   with:
>     version: latest
> ```
>
> Si estás compilando con Docker Engine y tienes habilitado el almacén de imágenes de containerd, puedes usar la acción `docker/setup-docker-action`:
>
> ```yaml
> - name: Set up Docker
>   uses: docker/setup-docker-action@v5
>   with:
>     version: latest
>     daemon-config: |
>       {
>         "features": {
>           "containerd-snapshotter": true
>         }
>       }
> ```

### Montajes de caché (cache mounts)

BuildKit no conserva los montajes de caché (cache mounts) en la caché de GitHub Actions de forma predeterminada. Para colocar tus montajes de caché en la caché de GitHub Actions y reutilizarlos entre compilaciones, puedes utilizar una solución alternativa proporcionada por [`reproducible-containers/buildkit-cache-dance`](https://github.com/reproducible-containers/buildkit-cache-dance).

Esta GitHub Action crea contenedores temporales para extraer e inyectar los datos del montaje de caché con tus pasos de compilación de Docker.

El siguiente ejemplo muestra cómo utilizar esta solución con un proyecto en Go.

Ejemplo de Dockerfile en `build/package/Dockerfile`

```Dockerfile
FROM golang:1.21.1-alpine as base-build

WORKDIR /build

RUN --mount=type=cache,target=/go/pkg/mod \
    --mount=type=bind,source=go.mod,target=go.mod \
    --mount=type=bind,source=go.sum,target=go.sum \
    go mod download

RUN --mount=type=cache,target=/go/pkg/mod \
    --mount=type=cache,target=/root/.cache/go-build \
    --mount=type=bind,target=. \
    go build -o /bin/app ./src
...
```

Ejemplo de acción de CI

```yaml
name: ci

on:
  push:

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - name: Iniciar sesión en Docker Hub
        uses: docker/login-action@v4
        with:
          username: ${{ vars.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Configurar QEMU
        uses: docker/setup-qemu-action@v4

      - name: Configurar Docker Buildx
        uses: docker/setup-buildx-action@v4

      - name: Docker meta
        id: meta
        uses: docker/metadata-action@v6
        with:
          images: user/app
          tags: |
            type=ref,event=branch
            type=ref,event=pr
            type=semver,pattern={{version}}
            type=semver,pattern={{major}}.{{minor}}

      - name: Caché de compilación de Go para Docker
        uses: actions/cache@v5
        with:
          path: go-build-cache
          key: ${{ runner.os }}-go-build-cache-${{ hashFiles('**/go.sum') }}

      - name: Inyectar go-build-cache
        uses: reproducible-containers/buildkit-cache-dance@4b2444fec0c0fb9dbf175a96c094720a692ef810 # v2.1.4
        with:
          cache-source: go-build-cache

      - name: Compilar y enviar
        uses: docker/build-push-action@v7
        with:
          cache-from: type=gha
          cache-to: type=gha,mode=max
          file: build/package/Dockerfile
          push: ${{ github.event_name != 'pull_request' }}
          tags: ${{ steps.meta.outputs.tags }}
          labels: ${{ steps.meta.outputs.labels }}
          platforms: linux/amd64,linux/arm64
```

Para obtener más información sobre esta solución alternativa, consulta el [repositorio de GitHub](https://github.com/reproducible-containers/buildkit-cache-dance).

### Caché local

> [!WARNING]
>
> En este momento, las entradas de caché antiguas no se eliminan, por lo que el tamaño de la caché [sigue creciendo](https://github.com/docker/build-push-action/issues/252).
> El siguiente ejemplo utiliza el paso `Move cache` como solución alternativa (consulta [`moby/buildkit#1896`](https://github.com/moby/buildkit/issues/1896)
> para obtener más información).

También puedes aprovechar la [caché de GitHub](https://docs.github.com/en/actions/using-workflows/caching-dependencies-to-speed-up-workflows) utilizando [actions/cache](https://github.com/actions/cache) y el [exportador de caché local](/build/cache/backends/local/) con esta acción:

```yaml
name: ci

on:
  push:

jobs:
  docker:
    runs-on: ubuntu-latest
    steps:
      - name: Iniciar sesión en Docker Hub
        uses: docker/login-action@v4
        with:
          username: ${{ vars.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Configurar Docker Buildx
        uses: docker/setup-buildx-action@v4

      - name: Almacenar en caché las capas de Docker
        uses: actions/cache@v5
        with:
          path: ${{ runner.temp }}/.buildx-cache
          key: ${{ runner.os }}-buildx-${{ github.sha }}
          restore-keys: |
            ${{ runner.os }}-buildx-

      - name: Compilar y enviar
        uses: docker/build-push-action@v7
        with:
          push: true
          tags: user/app:latest
          cache-from: type=local,src=${{ runner.temp }}/.buildx-cache
          cache-to: type=local,dest=${{ runner.temp }}/.buildx-cache-new,mode=max

      - # Solución temporal
        # https://github.com/docker/build-push-action/issues/252
        # https://github.com/moby/buildkit/issues/1896
        name: Mover caché
        run: |
          rm -rf ${{ runner.temp }}/.buildx-cache
          mv ${{ runner.temp }}/.buildx-cache-new ${{ runner.temp }}/.buildx-cache
```

