55"context"
66"encoding/json"
77"fmt"
8+ "io"
89"os"
910"path/filepath"
1011"runtime"
@@ -15,6 +16,7 @@ import (
1516
1617"github.com/docker/docker/api/types"
1718"github.com/docker/docker/api/types/container"
19+ "github.com/docker/docker/api/types/image"
1820"github.com/docker/docker/client"
1921"github.com/docker/docker/pkg/stdcopy"
2022"github.com/stretchr/testify/assert"
@@ -44,17 +46,14 @@ func TestIntegration(t *testing.T) {
4446ctx ,cancel := context .WithTimeout (context .Background (),time .Duration (timeoutMins )* time .Minute )
4547t .Cleanup (cancel )
4648
47- // Given: we have an existing Coder deployment running locally
48- ctrID := setup (ctx ,t )
49-
5049for _ ,tt := range []struct {
5150// Name of the folder under `integration/` containing a test template
52- templateName string
51+ name string
5352// map of string to regex to be passed to assertOutput()
5453expectedOutput map [string ]string
5554}{
5655{
57- templateName :"test-data-source" ,
56+ name :"test-data-source" ,
5857expectedOutput :map [string ]string {
5958"provisioner.arch" :runtime .GOARCH ,
6059"provisioner.id" :`[a-zA-Z0-9-]+` ,
@@ -82,20 +81,22 @@ func TestIntegration(t *testing.T) {
8281"workspace_owner.name" :`testing` ,
8382"workspace_owner.oidc_access_token" :`^$` ,// TODO: test OIDC integration
8483"workspace_owner.session_token" :`.+` ,
85- "workspace_owner.ssh_private_key" :`^$` , // Depends on coder/coder#13366
86- "workspace_owner.ssh_public_key" :`^ $` ,// Depends on coder/coder#13366
84+ "workspace_owner.ssh_private_key" :`(?s)^.+?BEGIN OPENSSH PRIVATE KEY.+?END OPENSSH PRIVATE KEY.+?$` ,
85+ "workspace_owner.ssh_public_key" :`(?s)^ssh-ed25519.+ $` ,
8786},
8887},
8988} {
90- t .Run (tt .templateName ,func (t * testing.T ) {
89+ t .Run (tt .name ,func (t * testing.T ) {
90+ // Given: we have an existing Coder deployment running locally
91+ ctrID := setup (ctx ,t ,tt .name )
9192// Import named template
92- _ ,rc := execContainer (ctx ,t ,ctrID ,fmt .Sprintf (`coder templates push %s --directory /src/integration/%s --var output_path=/tmp/%s.json --yes` ,tt .templateName ,tt .templateName ,tt .templateName ))
93+ _ ,rc := execContainer (ctx ,t ,ctrID ,fmt .Sprintf (`coder templates push %s --directory /src/integration/%s --var output_path=/tmp/%s.json --yes` ,tt .name ,tt .name ,tt .name ))
9394require .Equal (t ,0 ,rc )
9495// Create a workspace
95- _ ,rc = execContainer (ctx ,t ,ctrID ,fmt .Sprintf (`coder create %s -t %s --yes` ,tt .templateName ,tt .templateName ))
96+ _ ,rc = execContainer (ctx ,t ,ctrID ,fmt .Sprintf (`coder create %s -t %s --yes` ,tt .name ,tt .name ))
9697require .Equal (t ,0 ,rc )
9798// Fetch the output created by the template
98- out ,rc := execContainer (ctx ,t ,ctrID ,fmt .Sprintf (`cat /tmp/%s.json` ,tt .templateName ))
99+ out ,rc := execContainer (ctx ,t ,ctrID ,fmt .Sprintf (`cat /tmp/%s.json` ,tt .name ))
99100require .Equal (t ,0 ,rc )
100101actual := make (map [string ]string )
101102require .NoError (t ,json .NewDecoder (strings .NewReader (out )).Decode (& actual ))
@@ -104,7 +105,7 @@ func TestIntegration(t *testing.T) {
104105}
105106}
106107
107- func setup (ctx context.Context ,t * testing.T )string {
108+ func setup (ctx context.Context ,t * testing.T , name string )string {
108109var (
109110// For this test to work, we pass in a custom terraformrc to use
110111// the locally built version of the provider.
@@ -148,9 +149,17 @@ func setup(ctx context.Context, t *testing.T) string {
148149require .NoError (t ,err ,"get abs path of parent" )
149150t .Logf ("src path is %s\n " ,srcPath )
150151
152+ // Ensure the image is available locally.
153+ refStr := coderImg + ":" + coderVersion
154+ t .Logf ("ensuring image %q" ,refStr )
155+ resp ,err := cli .ImagePull (ctx ,refStr , image.PullOptions {})
156+ require .NoError (t ,err )
157+ _ ,err = io .ReadAll (resp )
158+ require .NoError (t ,err )
159+
151160// Stand up a temporary Coder instance
152161ctr ,err := cli .ContainerCreate (ctx ,& container.Config {
153- Image :coderImg + ":" + coderVersion ,
162+ Image :refStr ,
154163Env : []string {
155164"CODER_ACCESS_URL=" + localURL ,// Set explicitly to avoid creating try.coder.app URLs.
156165"CODER_IN_MEMORY=true" ,// We don't necessarily care about real persistence here.
@@ -163,7 +172,7 @@ func setup(ctx context.Context, t *testing.T) string {
163172tfrcPath + ":/tmp/integration.tfrc" ,// Custom tfrc from above.
164173srcPath + ":/src" ,// Bind-mount in the repo with the built binary and templates.
165174},
166- },nil ,nil ,"" )
175+ },nil ,nil ,"terraform-provider-coder-integration-" + name )
167176require .NoError (t ,err ,"create test deployment" )
168177
169178t .Logf ("created container %s\n " ,ctr .ID )