{"id":13416622,"url":"https://github.com/ory/dockertest","last_synced_at":"2025-05-12T05:32:55.927Z","repository":{"id":29022754,"uuid":"32550033","full_name":"ory/dockertest","owner":"ory","description":"Write better integration tests! Dockertest helps you boot up ephermal docker images for your Go tests with minimal work.","archived":false,"fork":false,"pushed_at":"2025-05-05T14:45:05.000Z","size":1167,"stargazers_count":4308,"open_issues_count":22,"forks_count":246,"subscribers_count":29,"default_branch":"v3","last_synced_at":"2025-05-11T23:55:04.340Z","etag":null,"topics":["automation","ci","docker","go","integration-testing","tests","unit-testing"],"latest_commit_sha":null,"homepage":"https://www.ory.sh/?utm_source=github\u0026utm_medium=banner\u0026utm_campaign=dockertest","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ory.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":"SECURITY.md","support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null},"funding":{"patreon":"_ory","open_collective":"ory"}},"created_at":"2015-03-19T22:40:20.000Z","updated_at":"2025-05-11T05:35:04.000Z","dependencies_parsed_at":"2024-04-12T09:21:36.458Z","dependency_job_id":"173979c9-2d5f-4d49-b8c9-4d6f0b27160e","html_url":"https://github.com/ory/dockertest","commit_stats":{"total_commits":354,"total_committers":108,"mean_commits":"3.2777777777777777","dds":0.8022598870056497,"last_synced_commit":"45d199cba3e6639259c2c7e7895e9ccf9d4f955e"},"previous_names":["ory-am/dockertest"],"tags_count":55,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ory%2Fdockertest","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ory%2Fdockertest/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ory%2Fdockertest/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ory%2Fdockertest/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ory","download_url":"https://codeload.github.com/ory/dockertest/tar.gz/refs/heads/v3","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":253657163,"owners_count":21943213,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["automation","ci","docker","go","integration-testing","tests","unit-testing"],"created_at":"2024-07-30T22:00:17.194Z","updated_at":"2025-05-12T05:32:55.884Z","avatar_url":"https://github.com/ory.png","language":"Go","readme":"\u003ch1 align=\"center\"\u003e\u003cimg src=\"./docs/images/banner_dockertest.png\" alt=\"ORY Dockertest\"\u003e\u003c/h1\u003e\n\n[![Build Status](https://travis-ci.org/ory/dockertest.svg)](https://travis-ci.org/ory/dockertest?branch=master)\n[![Coverage Status](https://coveralls.io/repos/github/ory/dockertest/badge.svg?branch=v3)](https://coveralls.io/github/ory/dockertest?branch=v3)\n\nUse Docker to run your Golang integration tests against third party services on\n**Microsoft Windows, Mac OSX and Linux**!\n\n\u003c!-- START doctoc generated TOC please keep comment here to allow auto update --\u003e\n\u003c!-- DON'T EDIT THIS SECTION, INSTEAD RE-RUN doctoc TO UPDATE --\u003e\n\n**Table of Contents**\n\n- [Why should I use Dockertest?](#why-should-i-use-dockertest)\n- [Installing and using Dockertest](#installing-and-using-dockertest)\n  - [Using Dockertest](#using-dockertest)\n  - [Examples](#examples)\n- [Troubleshoot \u0026 FAQ](#troubleshoot--faq)\n  - [Out of disk space](#out-of-disk-space)\n  - [Removing old containers](#removing-old-containers)\n\n\u003c!-- END doctoc generated TOC please keep comment here to allow auto update --\u003e\n\n## Why should I use Dockertest?\n\nWhen developing applications, it is often necessary to use services that talk to\na database system. Unit Testing these services can be cumbersome because mocking\ndatabase/DBAL is strenuous. Making slight changes to the schema implies\nrewriting at least some, if not all of the mocks. The same goes for API changes\nin the DBAL. To avoid this, it is smarter to test these specific services\nagainst a real database that is destroyed after testing. Docker is the perfect\nsystem for running unit tests as you can spin up containers in a few seconds and\nkill them when the test completes. The Dockertest library provides easy to use\ncommands for spinning up Docker containers and using them for your tests.\n\n## Installing and using Dockertest\n\nUsing Dockertest is straightforward and simple. Check the\n[releases tab](https://github.com/ory/dockertest/releases) for available\nreleases.\n\nTo install dockertest, run\n\n```\ngo get -u github.com/ory/dockertest/v3\n```\n\n### Using Dockertest\n\n```go\npackage dockertest_test\n\nimport (\n\t\"database/sql\"\n\t\"fmt\"\n\t\"log\"\n\t\"os\"\n\t\"testing\"\n\n\t_ \"github.com/go-sql-driver/mysql\"\n\t\"github.com/ory/dockertest/v3\"\n)\n\nvar db *sql.DB\n\nfunc TestMain(m *testing.M) {\n\t// uses a sensible default on windows (tcp/http) and linux/osx (socket)\n\tpool, err := dockertest.NewPool(\"\")\n\tif err != nil {\n\t\tlog.Fatalf(\"Could not construct pool: %s\", err)\n\t}\n\n\t// uses pool to try to connect to Docker\n\terr = pool.Client.Ping()\n\tif err != nil {\n\t\tlog.Fatalf(\"Could not connect to Docker: %s\", err)\n\t}\n\n\t// pulls an image, creates a container based on it and runs it\n\tresource, err := pool.Run(\"mysql\", \"5.7\", []string{\"MYSQL_ROOT_PASSWORD=secret\"})\n\tif err != nil {\n\t\tlog.Fatalf(\"Could not start resource: %s\", err)\n\t}\n\n\t// exponential backoff-retry, because the application in the container might not be ready to accept connections yet\n\tif err := pool.Retry(func() error {\n\t\tvar err error\n\t\tdb, err = sql.Open(\"mysql\", fmt.Sprintf(\"root:secret@(localhost:%s)/mysql\", resource.GetPort(\"3306/tcp\")))\n\t\tif err != nil {\n\t\t\treturn err\n\t\t}\n\t\treturn db.Ping()\n\t}); err != nil {\n\t\tlog.Fatalf(\"Could not connect to database: %s\", err)\n\t}\n\n\t// as of go1.15 testing.M returns the exit code of m.Run(), so it is safe to use defer here\n    defer func() {\n      if err := pool.Purge(resource); err != nil {\n        log.Fatalf(\"Could not purge resource: %s\", err)\n      }\n\n    }()\n\n\tm.Run()\n}\n\nfunc TestSomething(t *testing.T) {\n\t// db.Query()\n}\n```\n\n### Examples\n\nWe provide code examples for well known services in the [examples](examples/)\ndirectory, check them out!\n\n## Troubleshoot \u0026 FAQ\n\n### Out of disk space\n\nTry cleaning up the images with\n[docker-cleanup-volumes](https://github.com/chadoe/docker-cleanup-volumes).\n\n### Removing old containers\n\nSometimes container clean up fails. Check out\n[this stackoverflow question](http://stackoverflow.com/questions/21398087/how-to-delete-dockers-images)\non how to fix this. You may also set an absolute lifetime on containers:\n\n```go\nresource.Expire(60) // Tell docker to hard kill the container in 60 seconds\n```\n\nTo let stopped containers removed from file system automatically, use\n`pool.RunWithOptions()` instead of `pool.Run()` with `config.AutoRemove` set to\ntrue, e.g.:\n\n```go\npostgres, err := pool.RunWithOptions(\u0026dockertest.RunOptions{\n\tRepository: \"postgres\",\n\tTag:        \"11\",\n\tEnv: []string{\n\t\t\"POSTGRES_USER=test\",\n\t\t\"POSTGRES_PASSWORD=test\",\n\t\t\"listen_addresses = '*'\",\n\t},\n}, func(config *docker.HostConfig) {\n\t// set AutoRemove to true so that stopped container goes away by itself\n\tconfig.AutoRemove = true\n\tconfig.RestartPolicy = docker.RestartPolicy{\n\t\tName: \"no\",\n\t}\n})\n```\n\n## Running dockertest in Gitlab CI\n\n### How to run dockertest on shared gitlab runners?\n\nYou should add docker dind service to your job which starts in sibling\ncontainer. That means database will be available on host `docker`.  \nYou app should be able to change db host through environment variable.\n\nHere is the simple example of `gitlab-ci.yml`:\n\n```yaml\nstages:\n  - test\ngo-test:\n  stage: test\n  image: golang:1.15\n  services:\n    - docker:dind\n  variables:\n    DOCKER_HOST: tcp://docker:2375\n    DOCKER_DRIVER: overlay2\n    YOUR_APP_DB_HOST: docker\n  script:\n    - go test ./...\n```\n\nPlus in the `pool.Retry` method that checks for connection readiness, you need\nto use `$YOUR_APP_DB_HOST` instead of localhost.\n\n### How to run dockertest on group(custom) gitlab runners?\n\nGitlab runner can be run in docker executor mode to save compatibility with\nshared runners.  \nHere is the simple register command:\n\n```shell script\ngitlab-runner register -n \\\n --url https://gitlab.com/ \\\n --registration-token $YOUR_TOKEN \\\n --executor docker \\\n --description \"My Docker Runner\" \\\n --docker-image \"docker:19.03.12\" \\\n --docker-privileged\n```\n\nYou only need to instruct docker dind to start with disabled tls.  \nAdd variable `DOCKER_TLS_CERTDIR: \"\"` to `gitlab-ci.yml` above. It will tell\ndocker daemon to start on 2375 port over http.\n\n## Running Dockertest Using GitHub Actions\n\n```yaml\nname: Test with Docker\n\non: [push]\n\njobs:\n  test:\n    runs-on: ubuntu-latest\n    services:\n      dind:\n        image: docker:23.0-rc-dind-rootless\n        ports:\n          - 2375:2375\n    steps:\n      - name: Checkout code\n        uses: actions/checkout@v2\n\n      - name: Set up Go\n        uses: actions/setup-go@v4\n        with:\n          go-version: \"1.21\"\n\n      - name: Test with Docker\n        run: go test -v ./...\n```\n\n### How to run dockertest with remote Docker\n\nUse-case: locally installed docker CLI (client), docker daemon somewhere\nremotely, environment properly set (ie: `DOCKER_HOST`, etc..). For example,\nremote docker can be provisioned by docker-machine.\n\nCurrently, dockertest in case of `resource.GetHostPort()` will return docker\nhost binding address (commonly - `localhost`) instead of remote docker host.\nUniversal solution is:\n\n```go\nfunc getHostPort(resource *dockertest.Resource, id string) string {\n\tdockerURL := os.Getenv(\"DOCKER_HOST\")\n\tif dockerURL == \"\" {\n\t\treturn resource.GetHostPort(id)\n\t}\n\tu, err := url.Parse(dockerURL)\n\tif err != nil {\n\t\tpanic(err)\n\t}\n\treturn u.Hostname() + \":\" + resource.GetPort(id)\n}\n```\n\nIt will return the remote docker host concatenated with the allocated port in\ncase `DOCKER_HOST` env is defined. Otherwise, it will fall back to the embedded\nbehavior.\n","funding_links":["https://patreon.com/_ory","https://opencollective.com/ory"],"categories":["Testing","Repositories","Go","Ecosystem","automation","go","Resources"],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fory%2Fdockertest","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fory%2Fdockertest","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fory%2Fdockertest/lists"}