A preview environment is an isolated development environment created during a development process to enable you keep track of the changes made to your application during that period. Preview environments serve an important role when performing code reviews for an incoming change or addition to an application’s codebase. It is a fantastic way for technical and non-technical members of your team to assess and give feedback on the changes made to your application.

In previous posts of our series on Docker Compose, you have learned how to build and deploy a Golang application to Okteto using a docker-compose manifest and how to remotely develop a docker-compose application in Okteto. In this article, you will learn how to automatically create a preview environment for your pull requests, using GitHub Actions and Okteto.

What are GitHub Actions

GitHub Actions are event-driven task automation tools that runs a series of commands after an event has occurred. These events and commands are contained in a workflow file. The workflow file is responsible for the orderly execution by GitHub Actions.

Creating a GitHub Action workflow

GitHub Actions are created and managed from the Actions tab in a repository. Create a new workflow from the Actions tab:

Create A New Workflow

There are a number of available templates in the GitHub Actions page. However, click on the set up a workflow yourself link. This opens a new page with a default workflow. Let's rewrite the workflow file:

Start by defining the name of the workflow, and the event which should trigger the execution of the workflow file:

name: MyFood App Preview Deployment

on: 
  pull_request:
    branches:
      - main

In the code block above, you have set the name of the workflow, and the event to trigger the workflow. The workflow file is executed when a pull request is made to the main branch. Next, define the series of tasks to be executed. These tasks are called jobs in GitHub Actions.

You'll be using Okteto's published GitHub Actions to execute the jobs.

Add the instructions below to the existing code in the workflow file:

jobs:
  preview:
    runs-on: ubuntu-latest
    steps:
    - name: checkout
      uses: actions/[email protected]

    - name: Login
      uses: okteto/[email protected]
      with:
        token: ${{ secrets.OKTETO_TOKEN }}

    - name: Create namespace
      uses: okteto/create-[email protected]
      with:
        namespace: pr-${{ github.event.number }}-namespace
   
    - name: Deploy application
      uses: okteto/deploy-[email protected]
      with:
        build: "true"
        namespace: pr-${{ github.event.number }}-namespace

    - name: add comment to PR
      uses: okteto/notify-[email protected]
      env:
        GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
      with:
        message: "Preview environment available at https://web-pr-${{ github.event.number }}-namespace.cloud.okteto.net"  

In the code block above, we defined the job preview which runs on the ubuntu-latest environment. The steps to be executed under this job are defined under the steps heading. Let's go over these steps.

Replace namespace in the code block above with the name of your Okteto username. Your username can be found by clicking on your gravatar in the bottom left corner of your dashboard:

Username

Steps

In our preview job, we have five tasks to be executed.

  1. checkout: This step checks out the repository using the actions/[email protected] actions, so that the repository is accessible by the entire workflow.

  2. Login: This step logs into your Okteto account. This task makes use of secrets.OKTETO_TOKEN, which holds the value of your Okteto token. You'll learn how to create the secret in the next section.

  3. Create Namespace: This step creates a new namespace using the okteto/[email protected] action.

  4. Deploy Application: This step uses the action okteto/[email protected] to deploy the application using the okteto stack file defined in the repository. Once again, we have witnessed the adaptability of Okteto stacks.

  5. add comment to PR: This step adds a comment on the pull request discussion indicating a link to the deployed application. It makes use of the okteto/[email protected] action.

Adding your Okteto token to GitHub

The workflow file needs access to your Okteto account. Okteto provides Personal Access Tokens which can be used for this case. In your dashboard, generate and copy a new personal access token:

Okteto dashboard - Settings

Next, add the personal access token you created as a repository secret. Follow the steps below to add the personal access token to your GitHub repository:

  1. In your repository, navigate to the Settings tab and click on the Secrets link on the menu by the left. Click on New Repository Secret:

Secrets

  1. Create a new secret OKTETO_TOKEN and set the value to the token you copied from your dashboard:

Create New Secret

You can learn more on how to store and manage GitHub secrets on their official documentation.

Building the preview environment

With the workflow and secret in place, clone the repository locally:

$ git clone https://github.com/okteto/go-api-docker-compose
$ cd go-api-docker-compose

Add a new function before AddFood() in main.go:

func Welcome(response http.ResponseWriter, request *http.request) {
    fmt.Fprint(response, "Welcome to MyFood App")
}

In the main() function, register the route:

func main() {
    ...
    router.HandleFunc("/", Welcome)/Methods("GET")
    http.ListenAndServe(":8080", router)
}

Save the file and commit the changes into a new branch dev:

$ git checkout -b dev
$ git add main.go
$ git commit -m "Added a welcome route"

Push the changes to the newly created branch:

$ git push --set-upstream origin dev

Next, create a pull request to the main branch:

Pull Request

Click on Checks:

Checks

Click on Preview to watch the preview environment creation process:

Preview Workflow

Once the process is completed, a comment with the link to the application built in the preview environment is made:

Comment from GH Bot

Click on the link generated for the preview environment and confirm that the changes made are reflected:

Changes work

Deleting preview environment namespace

The preview environment ceases to be of use after the pull request has been merged. As such, there is no point in keeping the namespace created by the workflow earlier as newer pull requests will create new namespaces. Okteto provides an action to automatically delete a namespace.

Repeating the steps followed in creating a workflow above, create a new workflow preview-close to automatically destroy the namespace after the pull request has either been merged or closed:

name: Delete Preview Namespace

on:
  pull_request:
    types:
      - closed

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - name: checkout
        uses: actions/[email protected]

      - name: Login
        uses: okteto/[email protected]
        with:
          token: ${{ secrets.OKTETO_TOKEN }}

      - name: Delete namespace
        uses: okteto/delete-[email protected]
        with:
          namespace: pr-${{ github.event.number }}-namespace

Remember to change namespace to your Okteto username.

With the workflow in place, let's merge the pull request and verify that the Delete Preview Namespace workflow was executed:

Pull Request closed

Verify that the namespace has been deleted from the Checks section:

Namespace deleted

Conclusion

In this article, you built a workflow for creating a preview environment when a pull request is made to the main branch and another workflow to delete the namespace containing the preview environment after the pull request has either been closed or merged.

Once again, the deployment of the preview environment was made possible by the Docker Compose manifest we have been using from the first post in the series. This way, you are reusing the same manifest for development, deployment, and preview environments.

The complete code used in this article can be found in our GitHub repository