testcontainers: Docker containers for your integration tests.

[ development, library, mit ] [ Propose Tags ] [ Report a vulnerability ]

testcontainers is a Haskell library that provides a friendly API to run Docker containers. It is designed to create a runtime environment to use during your integration tests


[Skip to Readme]

Downloads

Note: This package has metadata revisions in the cabal description newer than included in the tarball. To unpack the package including the revisions, use 'cabal get'.

Maintainer's Corner

Package maintainers

For package maintainers and hackage trustees

Candidates

Versions [RSS] 0.1.0.0, 0.2.0.0, 0.3.0.0, 0.3.0.1, 0.3.1.0, 0.4.0.0, 0.5.0.0 (info)
Change log CHANGELOG.md
Dependencies aeson (>=1.4.6 && <3), aeson-optics (>=1.1 && <2), async, base (>=4.12 && <5), bytestring (>=0.10.8 && <0.12), directory (>=1.3.6 && <2), exceptions (>=0.10.4 && <0.11), http-client (>=0.5.14 && <1), http-types (>=0.12.3 && <1), mtl (>=2.2.2 && <3), network (>=3.1.2.0 && <3.2), optics-core (>=0.1 && <0.5), process (>=1.6.5 && <1.7), random (>=1.2 && <2), resourcet (>=1.2.4 && <1.4), tasty (>=1.0 && <1.6), text (>=1.2.3 && <3), unliftio-core (>=0.1.0 && <0.3) [details]
Tested with ghc ==8.8.4 || ==8.10.7 || ==9.0.2 || ==9.2.4 || ==9.4.2
License MIT
Copyright 2023 Alex Biehl
Author Alex Biehl
Maintainer alex.biehl@gmail.com
Revised Revision 2 made by alexbiehl at 2024-11-15T08:50:02Z
Category Development
Source repo head: git clone https://github.com/testcontainers/testcontainers-hs
Uploaded by alexbiehl at 2023-02-20T16:16:48Z
Distributions
Downloads 990 total (32 in the last 30 days)
Rating 2.25 (votes: 2) [estimated by Bayesian average]
Your Rating
  • λ
  • λ
  • λ
Status Docs available [build log]
Last success reported on 2023-02-20 [all 1 reports]

Readme for testcontainers-0.5.0.0

[back to package description]

About

Testcontainers is a Haskell library that provides a friendly API to run Docker containers. It is designed to create a runtime environment to use during your integration tests

Example

{-# LANGUAGE FlexibleContexts  #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE RecordWildCards   #-}
module Main where

import qualified Test.Tasty           as Tasty
import qualified Test.Tasty.HUnit     as Tasty
import qualified TestContainers.Tasty as TC


data Endpoints = Endpoints
  {
    redisHost :: String
  , redisPort :: Int
  }


-- | Sets up and runs the containers required for this test suite.
setupContainers :: TC.MonadDocker m => m Endpoints
setupContainers = do

  -- Launch the container based on the redis:5.0.0 image.
  redisContainer <- TC.run $ TC.containerRequest (TC.fromTag "redis:5.0.0")
    -- Expose the port 6379 from within the container. The respective port
    -- on the host machine can be looked up using `containerPort` (see below).
    TC.& TC.setExpose [ 6379 ]
    -- Wait until the container is ready to accept requests. `run` blocks until
    -- readiness can be established.
    TC.& TC.setWaitingFor (TC.waitUntilMappedPortReachable 6379)

  pure $ Endpoints
    {
      redisHost = "0.0.0.0"
    , redisPort =
        -- Look up the corresponding port on the host machine for the exposed
        -- port 6379.
        TC.containerPort redisContainer 6379
    }


main :: IO ()
main =
  Tasty.defaultMain $
  -- Use `withContainers` to make the containers available in the closed over
  -- tests. Due to how Tasty handles resources `withContainers` passes down
  -- an IO action `start` to actually start up the containers. `start` can be
  -- invoked multiple times, Tasty makes sure to only start up the containrs
  -- once.
  --
  -- `withContainers` ensures the started containers are shut down correctly
  -- once execution leaves its scope.
  TC.withContainers setupContainers $ \start ->
    Tasty.testGroup "Some test group"
      [
        Tasty.testCase "Redis test" $ do
          -- Actually start the containers!!
          Endpoints {..} <- start
          -- ... assert some properties
          pure ()

      , Tasty.testCase "Another Redis test" $ do
          -- Invoking `start` twice gives the same Endpoints!
          Endpoints {..} <- start
          -- ... assert some properties
          pure ()
      ]