core: Fix various compile-time errors in tests

Significant changes to the provider interface left a lot of the
tests in a non-buildable state. This set of changes gets the
tests building again but does not attempt to make them run to
completion or pass.

After this commit, it is possible to build a test program for
the ./terraform package but it will panic during its run. That
will be addressed in subsequent commits.
This commit is contained in:
Martin Atkins 2018-09-05 14:35:30 -07:00
parent 6fd82ef97e
commit ebd3aba0be
12 changed files with 318 additions and 223 deletions

View File

@ -24,6 +24,7 @@ import (
"github.com/hashicorp/terraform/configs/configschema" "github.com/hashicorp/terraform/configs/configschema"
"github.com/hashicorp/terraform/plans" "github.com/hashicorp/terraform/plans"
"github.com/hashicorp/terraform/providers" "github.com/hashicorp/terraform/providers"
"github.com/hashicorp/terraform/provisioners"
"github.com/hashicorp/terraform/states" "github.com/hashicorp/terraform/states"
"github.com/hashicorp/terraform/tfdiags" "github.com/hashicorp/terraform/tfdiags"
) )
@ -1485,7 +1486,11 @@ func TestContext2Apply_dataBasic(t *testing.T) {
p := testProvider("null") p := testProvider("null")
p.ApplyFn = testApplyFn p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
p.ReadDataApplyReturn = &InstanceState{ID: "yo"} p.ReadDataSourceResponse = providers.ReadDataSourceResponse{
State: cty.ObjectVal(map[string]cty.Value{
"id": cty.StringVal("yo"),
}),
}
ctx := testContext2(t, &ContextOpts{ ctx := testContext2(t, &ContextOpts{
Config: m, Config: m,
@ -4274,9 +4279,11 @@ func TestContext2Apply_provisionerModule(t *testing.T) {
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
pr := testProvisioner() pr := testProvisioner()
pr.GetConfigSchemaReturnSchema = &configschema.Block{ pr.GetSchemaResponse = provisioners.GetSchemaResponse{
Attributes: map[string]*configschema.Attribute{ Provisioner: &configschema.Block{
"foo": {Type: cty.String, Optional: true}, Attributes: map[string]*configschema.Attribute{
"foo": {Type: cty.String, Optional: true},
},
}, },
} }
@ -5907,9 +5914,11 @@ func TestContext2Apply_Provisioner_ConnInfo(t *testing.T) {
} }
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
pr.GetConfigSchemaReturnSchema = &configschema.Block{ pr.GetSchemaResponse = provisioners.GetSchemaResponse{
Attributes: map[string]*configschema.Attribute{ Provisioner: &configschema.Block{
"foo": {Type: cty.String, Optional: true}, Attributes: map[string]*configschema.Attribute{
"foo": {Type: cty.String, Optional: true},
},
}, },
} }
@ -7635,15 +7644,17 @@ func TestContext2Apply_destroyProvisionerWithLocals(t *testing.T) {
} }
return nil return nil
} }
pr.GetConfigSchemaReturnSchema = &configschema.Block{ pr.GetSchemaResponse = provisioners.GetSchemaResponse{
Attributes: map[string]*configschema.Attribute{ Provisioner: &configschema.Block{
"command": { Attributes: map[string]*configschema.Attribute{
Type: cty.String, "command": {
Required: true, Type: cty.String,
}, Required: true,
"when": { },
Type: cty.String, "when": {
Optional: true, Type: cty.String,
Optional: true,
},
}, },
}, },
} }
@ -7701,15 +7712,17 @@ func TestContext2Apply_destroyProvisionerWithMultipleLocals(t *testing.T) {
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
pr := testProvisioner() pr := testProvisioner()
pr.GetConfigSchemaReturnSchema = &configschema.Block{ pr.GetSchemaResponse = provisioners.GetSchemaResponse{
Attributes: map[string]*configschema.Attribute{ Provisioner: &configschema.Block{
"command": { Attributes: map[string]*configschema.Attribute{
Type: cty.String, "command": {
Required: true, Type: cty.String,
}, Required: true,
"when": { },
Type: cty.String, "when": {
Optional: true, Type: cty.String,
Optional: true,
},
}, },
}, },
} }
@ -8572,9 +8585,6 @@ func TestContext2Apply_singleDestroy(t *testing.T) {
// GH-7824 // GH-7824
func TestContext2Apply_issue7824(t *testing.T) { func TestContext2Apply_issue7824(t *testing.T) {
p := testProvider("template") p := testProvider("template")
p.ResourcesReturn = append(p.ResourcesReturn, ResourceType{
Name: "template_file",
})
p.ApplyFn = testApplyFn p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
p.GetSchemaReturn = &ProviderSchema{ p.GetSchemaReturn = &ProviderSchema{
@ -8632,12 +8642,18 @@ func TestContext2Apply_issue5254(t *testing.T) {
// Create a provider. We use "template" here just to match the repro // Create a provider. We use "template" here just to match the repro
// we got from the issue itself. // we got from the issue itself.
p := testProvider("template") p := testProvider("template")
p.ResourcesReturn = append(p.ResourcesReturn, ResourceType{
Name: "template_file",
})
p.ApplyFn = testApplyFn p.ApplyFn = testApplyFn
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
p.GetSchemaReturn = &ProviderSchema{
ResourceTypes: map[string]*configschema.Block{
"template_file": {
Attributes: map[string]*configschema.Attribute{
"template": {Type: cty.String, Optional: true},
"__template_requires_new": {Type: cty.Bool, Optional: true},
},
},
},
}
m, snap := testModuleWithSnapshot(t, "issue-5254/step-0") m, snap := testModuleWithSnapshot(t, "issue-5254/step-0")
@ -9106,18 +9122,12 @@ func TestContext2Apply_dataDependsOn(t *testing.T) {
} }
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
p.ReadDataDiffFn = testDataDiffFn p.ReadDataSourceFn = func (req providers.ReadDataSourceRequest) providers.ReadDataSourceResponse{
return providers.ReadDataSourceResponse{
p.ReadDataApplyFn = func(*InstanceInfo, *InstanceDiff) (*InstanceState, error) { State: cty.ObjectVal(map[string]cty.Value{
// Read the artifact created by our dependency being applied. "foo": cty.StringVal(provisionerOutput),
// Without any "depends_on", this would be skipped as it's assumed the }),
// initial diff during refresh was all that's needed. }
return &InstanceState{
ID: "read",
Attributes: map[string]string{
"foo": provisionerOutput,
},
}, nil
} }
_, diags := ctx.Refresh() _, diags := ctx.Refresh()

View File

@ -431,11 +431,12 @@ func TestContextImport_refresh(t *testing.T) {
}, },
} }
p.RefreshFn = func(info *InstanceInfo, s *InstanceState) (*InstanceState, error) { p.ReadResourceFn = nil
return &InstanceState{ p.ReadResourceResponse = providers.ReadResourceResponse{
ID: "foo", NewState: cty.ObjectVal(map[string]cty.Value{
Attributes: map[string]string{"foo": "bar"}, "id": cty.StringVal("foo"),
}, nil "foo": cty.StringVal("bar"),
}),
} }
state, diags := ctx.Import(&ImportOpts{ state, diags := ctx.Import(&ImportOpts{
@ -479,8 +480,10 @@ func TestContextImport_refreshNil(t *testing.T) {
}, },
} }
p.RefreshFn = func(info *InstanceInfo, s *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
return nil, nil return providers.ReadResourceResponse{
NewState: cty.NullVal(cty.DynamicPseudoType),
}
} }
state, diags := ctx.Import(&ImportOpts{ state, diags := ctx.Import(&ImportOpts{

View File

@ -1,7 +1,6 @@
package terraform package terraform
import ( import (
"errors"
"reflect" "reflect"
"strings" "strings"
"sync" "sync"
@ -254,8 +253,8 @@ func TestContext2Input_providerOnce(t *testing.T) {
), ),
}) })
count := 0 //count := 0
p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) { /*p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) {
count++ count++
_, set := c.Config["from_input"] _, set := c.Config["from_input"]
@ -271,7 +270,7 @@ func TestContext2Input_providerOnce(t *testing.T) {
} }
return c, nil return c, nil
} }*/
if diags := ctx.Input(InputModeStd); diags.HasErrors() { if diags := ctx.Input(InputModeStd); diags.HasErrors() {
t.Fatalf("input errors: %s", diags.Err()) t.Fatalf("input errors: %s", diags.Err())
@ -444,10 +443,10 @@ func TestContext2Input_providerVars(t *testing.T) {
} }
var actual interface{} var actual interface{}
p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) { /*p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) {
c.Config["bar"] = "baz" c.Config["bar"] = "baz"
return c, nil return c, nil
} }*/
p.ConfigureFn = func(c *ResourceConfig) error { p.ConfigureFn = func(c *ResourceConfig) error {
actual, _ = c.Get("foo") actual, _ = c.Get("foo")
return nil return nil
@ -486,12 +485,12 @@ func TestContext2Input_providerVarsModuleInherit(t *testing.T) {
UIInput: input, UIInput: input,
}) })
p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) { /*p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) {
if errs := c.CheckSet([]string{"access_key"}); len(errs) > 0 { if errs := c.CheckSet([]string{"access_key"}); len(errs) > 0 {
return c, errs[0] return c, errs[0]
} }
return c, nil return c, nil
} }*/
p.ConfigureFn = func(c *ResourceConfig) error { p.ConfigureFn = func(c *ResourceConfig) error {
return nil return nil
} }
@ -528,10 +527,10 @@ func TestContext2Input_varOnly(t *testing.T) {
} }
var actual interface{} var actual interface{}
p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) { /*p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) {
c.Raw["foo"] = "bar" c.Raw["foo"] = "bar"
return c, nil return c, nil
} }*/
p.ConfigureFn = func(c *ResourceConfig) error { p.ConfigureFn = func(c *ResourceConfig) error {
actual = c.Raw["foo"] actual = c.Raw["foo"]
return nil return nil
@ -814,9 +813,9 @@ func TestContext2Input_submoduleTriggersInvalidCount(t *testing.T) {
UIInput: input, UIInput: input,
}) })
p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) { /*p.InputFn = func(i UIInput, c *ResourceConfig) (*ResourceConfig, error) {
return c, nil return c, nil
} }*/
p.ConfigureFn = func(c *ResourceConfig) error { p.ConfigureFn = func(c *ResourceConfig) error {
return nil return nil
} }
@ -842,7 +841,11 @@ func TestContext2Input_dataSourceRequiresRefresh(t *testing.T) {
}, },
}, },
} }
p.ReadDataDiffFn = testDataDiffFn p.ReadDataSourceFn = func(req providers.ReadDataSourceRequest) providers.ReadDataSourceResponse {
return providers.ReadDataSourceResponse{
State: req.Config,
}
}
state := states.BuildState(func(s *states.SyncState) { state := states.BuildState(func(s *states.SyncState) {
s.SetResourceInstanceCurrent( s.SetResourceInstanceCurrent(

View File

@ -17,6 +17,7 @@ import (
"github.com/hashicorp/terraform/addrs" "github.com/hashicorp/terraform/addrs"
"github.com/hashicorp/terraform/configs/configschema" "github.com/hashicorp/terraform/configs/configschema"
"github.com/hashicorp/terraform/providers" "github.com/hashicorp/terraform/providers"
"github.com/hashicorp/terraform/tfdiags"
) )
func TestContext2Plan_basic(t *testing.T) { func TestContext2Plan_basic(t *testing.T) {
@ -1457,18 +1458,17 @@ func TestContext2Plan_dataSourceTypeMismatch(t *testing.T) {
}, },
}, },
} }
p.ValidateResourceFn = func(t string, c *ResourceConfig) (ws []string, es []error) { p.ValidateResourceTypeConfigFn = func (req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
// Emulate the type checking behavior of helper/schema based validation var diags tfdiags.Diagnostics
if t == "aws_instance" { if req.TypeName == "aws_instance" {
ami, _ := c.Get("ami") amiVal := req.Config.GetAttr("ami")
switch a := ami.(type) { if amiVal.Type() != cty.String {
case string: diags = diags.Append(fmt.Errorf("Expected ami to be cty.String, got %#v", amiVal))
// ok
default:
es = append(es, fmt.Errorf("Expected ami to be string, got %T", a))
} }
} }
return return providers.ValidateResourceTypeConfigResponse{
Diagnostics: diags,
}
} }
p.DiffFn = func( p.DiffFn = func(
info *InstanceInfo, info *InstanceInfo,
@ -3891,8 +3891,10 @@ func TestContext2Plan_resourceNestedCount(t *testing.T) {
m := testModule(t, "nested-resource-count-plan") m := testModule(t, "nested-resource-count-plan")
p := testProvider("aws") p := testProvider("aws")
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
p.RefreshFn = func(i *InstanceInfo, is *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
return is, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
s := mustShimLegacyState(&State{ s := mustShimLegacyState(&State{
Modules: []*ModuleState{ Modules: []*ModuleState{
@ -4041,18 +4043,17 @@ func TestContext2Plan_computedAttrRefTypeMismatch(t *testing.T) {
m := testModule(t, "plan-computed-attr-ref-type-mismatch") m := testModule(t, "plan-computed-attr-ref-type-mismatch")
p := testProvider("aws") p := testProvider("aws")
p.DiffFn = testDiffFn p.DiffFn = testDiffFn
p.ValidateResourceFn = func(t string, c *ResourceConfig) (ws []string, es []error) { p.ValidateResourceTypeConfigFn = func (req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
// Emulate the type checking behavior of helper/schema based validation var diags tfdiags.Diagnostics
if t == "aws_instance" { if req.TypeName == "aws_instance" {
ami, _ := c.Get("ami") amiVal := req.Config.GetAttr("ami")
switch a := ami.(type) { if amiVal.Type() != cty.String {
case string: diags = diags.Append(fmt.Errorf("Expected ami to be cty.String, got %#v", amiVal))
// ok
default:
es = append(es, fmt.Errorf("Expected ami to be string, got %T", a))
} }
} }
return return providers.ValidateResourceTypeConfigResponse{
Diagnostics: diags,
}
} }
p.DiffFn = func( p.DiffFn = func(
info *InstanceInfo, info *InstanceInfo,

View File

@ -84,9 +84,11 @@ func TestContext2Refresh_dataComputedModuleVar(t *testing.T) {
), ),
}) })
p.RefreshFn = nil p.ReadResourceFn = nil
p.RefreshReturn = &InstanceState{ p.ReadResourceResponse = providers.ReadResourceResponse{
ID: "foo", NewState: cty.ObjectVal(map[string]cty.Value{
"id": cty.StringVal("foo"),
}),
} }
p.GetSchemaReturn = &ProviderSchema{ p.GetSchemaReturn = &ProviderSchema{
@ -193,9 +195,11 @@ func TestContext2Refresh_targeted(t *testing.T) {
}) })
refreshedResources := make([]string, 0, 2) refreshedResources := make([]string, 0, 2)
p.RefreshFn = func(i *InstanceInfo, is *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
refreshedResources = append(refreshedResources, i.Id) refreshedResources = append(refreshedResources, req.PriorState.GetAttr("id").AsString())
return is, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
_, diags := ctx.Refresh() _, diags := ctx.Refresh()
@ -276,9 +280,11 @@ func TestContext2Refresh_targetedCount(t *testing.T) {
}) })
refreshedResources := make([]string, 0, 2) refreshedResources := make([]string, 0, 2)
p.RefreshFn = func(i *InstanceInfo, is *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
refreshedResources = append(refreshedResources, i.Id) refreshedResources = append(refreshedResources, req.PriorState.GetAttr("id").AsString())
return is, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
_, diags := ctx.Refresh() _, diags := ctx.Refresh()
@ -367,9 +373,11 @@ func TestContext2Refresh_targetedCountIndex(t *testing.T) {
}) })
refreshedResources := make([]string, 0, 2) refreshedResources := make([]string, 0, 2)
p.RefreshFn = func(i *InstanceInfo, is *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
refreshedResources = append(refreshedResources, i.Id) refreshedResources = append(refreshedResources, req.PriorState.GetAttr("id").AsString())
return is, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
_, diags := ctx.Refresh() _, diags := ctx.Refresh()
@ -447,8 +455,8 @@ func TestContext2Refresh_delete(t *testing.T) {
}), }),
}) })
p.RefreshFn = nil p.ReadResourceFn = nil
p.RefreshReturn = nil p.ReadResourceResponse = providers.ReadResourceResponse{}
s, diags := ctx.Refresh() s, diags := ctx.Refresh()
if diags.HasErrors() { if diags.HasErrors() {
@ -474,16 +482,18 @@ func TestContext2Refresh_ignoreUncreated(t *testing.T) {
State: nil, State: nil,
}) })
p.RefreshFn = nil p.ReadResourceFn = nil
p.RefreshReturn = &InstanceState{ p.ReadResourceResponse = providers.ReadResourceResponse{
ID: "foo", NewState: cty.ObjectVal(map[string]cty.Value{
"id": cty.StringVal("foo"),
}),
} }
_, diags := ctx.Refresh() _, diags := ctx.Refresh()
if diags.HasErrors() { if diags.HasErrors() {
t.Fatalf("refresh errors: %s", diags.Err()) t.Fatalf("refresh errors: %s", diags.Err())
} }
if p.RefreshCalled { if p.ReadResourceCalled {
t.Fatal("refresh should not be called") t.Fatal("refresh should not be called")
} }
} }
@ -569,13 +579,22 @@ func TestContext2Refresh_modules(t *testing.T) {
State: state, State: state,
}) })
p.RefreshFn = func(info *InstanceInfo, s *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
if s.ID != "baz" { if !req.PriorState.GetAttr("id").RawEquals(cty.StringVal("baz")) {
return s, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
s.ID = "new" new, _ := cty.Transform(req.PriorState, func(path cty.Path, v cty.Value) (cty.Value, error) {
return s, nil if len(path) == 1 && path[0].(cty.GetAttrStep).Name == "id" {
return cty.StringVal("new"), nil
}
return v, nil
})
return providers.ReadResourceResponse{
NewState: new,
}
} }
s, diags := ctx.Refresh() s, diags := ctx.Refresh()
@ -657,9 +676,11 @@ func TestContext2Refresh_noState(t *testing.T) {
), ),
}) })
p.RefreshFn = nil p.ReadResourceFn = nil
p.RefreshReturn = &InstanceState{ p.ReadResourceResponse = providers.ReadResourceResponse{
ID: "foo", NewState: cty.ObjectVal(map[string]cty.Value{
"id": cty.StringVal("foo"),
}),
} }
if _, diags := ctx.Refresh(); diags.HasErrors() { if _, diags := ctx.Refresh(); diags.HasErrors() {
@ -719,8 +740,10 @@ func TestContext2Refresh_output(t *testing.T) {
}), }),
}) })
p.RefreshFn = func(info *InstanceInfo, s *InstanceState) (*InstanceState, error) { p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
return s, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
s, diags := ctx.Refresh() s, diags := ctx.Refresh()
@ -763,8 +786,8 @@ func TestContext2Refresh_outputPartial(t *testing.T) {
}), }),
}) })
p.RefreshFn = nil p.ReadResourceFn = nil
p.RefreshReturn = nil p.ReadResourceResponse = providers.ReadResourceResponse{}
p.GetSchemaReturn = &ProviderSchema{ p.GetSchemaReturn = &ProviderSchema{
Provider: &configschema.Block{}, Provider: &configschema.Block{},
@ -1016,8 +1039,11 @@ func TestContext2Refresh_dataStateRefData(t *testing.T) {
State: state, State: state,
}) })
p.ReadDataDiffFn = testDataDiffFn p.ReadDataSourceFn = func(req providers.ReadDataSourceRequest) providers.ReadDataSourceResponse {
p.ReadDataApplyFn = testDataApplyFn return providers.ReadDataSourceResponse{
State: req.Config,
}
}
s, diags := ctx.Refresh() s, diags := ctx.Refresh()
if diags.HasErrors() { if diags.HasErrors() {
@ -1060,18 +1086,19 @@ func TestContext2Refresh_tainted(t *testing.T) {
State: state, State: state,
}) })
p.RefreshFn = nil p.ReadResourceFn = nil
p.RefreshReturn = &InstanceState{ p.ReadResourceResponse = providers.ReadResourceResponse{
ID: "foo", NewState: cty.ObjectVal(map[string]cty.Value{
Tainted: true, "id": cty.StringVal("foo"),
}),
} }
s, diags := ctx.Refresh() s, diags := ctx.Refresh()
if diags.HasErrors() { if diags.HasErrors() {
t.Fatalf("refresh errors: %s", diags.Err()) t.Fatalf("refresh errors: %s", diags.Err())
} }
if !p.RefreshCalled { if !p.ReadResourceCalled {
t.Fatal("refresh should be called") t.Fatal("ReadResource was not called; should have been")
} }
actual := strings.TrimSpace(s.String()) actual := strings.TrimSpace(s.String())
@ -1205,14 +1232,14 @@ func TestContext2Refresh_orphanModule(t *testing.T) {
// Create a custom refresh function to track the order they were visited // Create a custom refresh function to track the order they were visited
var order []string var order []string
var orderLock sync.Mutex var orderLock sync.Mutex
p.RefreshFn = func( p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
info *InstanceInfo,
is *InstanceState) (*InstanceState, error) {
orderLock.Lock() orderLock.Lock()
defer orderLock.Unlock() defer orderLock.Unlock()
order = append(order, is.ID) order = append(order, req.PriorState.GetAttr("id").AsString())
return is, nil return providers.ReadResourceResponse{
NewState: req.PriorState,
}
} }
p.GetSchemaReturn = &ProviderSchema{ p.GetSchemaReturn = &ProviderSchema{
Provider: &configschema.Block{}, Provider: &configschema.Block{},
@ -1360,7 +1387,7 @@ func TestContext2Refresh_noDiffHookOnScaleOut(t *testing.T) {
h := new(MockHook) h := new(MockHook)
p := testProvider("aws") p := testProvider("aws")
m := testModule(t, "refresh-resource-scale-inout") m := testModule(t, "refresh-resource-scale-inout")
p.RefreshFn = nil p.ReadResourceFn = nil
p.GetSchemaReturn = &ProviderSchema{ p.GetSchemaReturn = &ProviderSchema{
Provider: &configschema.Block{}, Provider: &configschema.Block{},
ResourceTypes: map[string]*configschema.Block{ ResourceTypes: map[string]*configschema.Block{

View File

@ -1,17 +1,19 @@
package terraform package terraform
import ( import (
"errors"
"fmt" "fmt"
"strings" "strings"
"testing" "testing"
"github.com/hashicorp/terraform/providers"
"github.com/hashicorp/terraform/states"
"github.com/zclconf/go-cty/cty" "github.com/zclconf/go-cty/cty"
"github.com/hashicorp/terraform/addrs" "github.com/hashicorp/terraform/addrs"
"github.com/hashicorp/terraform/configs/configschema" "github.com/hashicorp/terraform/configs/configschema"
"github.com/hashicorp/terraform/providers"
"github.com/hashicorp/terraform/provisioners"
"github.com/hashicorp/terraform/states"
"github.com/hashicorp/terraform/tfdiags"
) )
func TestContext2Validate_badCount(t *testing.T) { func TestContext2Validate_badCount(t *testing.T) {
@ -367,7 +369,9 @@ func TestContext2Validate_moduleBadResource(t *testing.T) {
), ),
}) })
p.ValidateResourceReturnErrors = []error{fmt.Errorf("bad")} p.ValidateResourceTypeConfigResponse = providers.ValidateResourceTypeConfigResponse{
Diagnostics: tfdiags.Diagnostics{}.Append(fmt.Errorf("bad")),
}
diags := c.Validate() diags := c.Validate()
if !diags.HasErrors() { if !diags.HasErrors() {
@ -580,9 +584,14 @@ func TestContext2Validate_orphans(t *testing.T) {
State: state, State: state,
}) })
p.ValidateResourceFn = func( p.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
t string, c *ResourceConfig) ([]string, []error) { var diags tfdiags.Diagnostics
return nil, c.CheckSet([]string{"foo"}) if req.Config.GetAttr("foo").IsNull() {
diags.Append(errors.New("foo is not set"))
}
return providers.ValidateResourceTypeConfigResponse{
Diagnostics: diags,
}
} }
diags := c.Validate() diags := c.Validate()
@ -616,7 +625,9 @@ func TestContext2Validate_providerConfig_bad(t *testing.T) {
), ),
}) })
p.ValidateReturnErrors = []error{fmt.Errorf("bad")} p.ValidateProviderConfigResponse = providers.ValidateProviderConfigResponse{
Diagnostics: tfdiags.Diagnostics{}.Append(fmt.Errorf("bad")),
}
diags := c.Validate() diags := c.Validate()
if len(diags) != 1 { if len(diags) != 1 {
@ -652,7 +663,9 @@ func TestContext2Validate_providerConfig_badEmpty(t *testing.T) {
), ),
}) })
p.ValidateReturnErrors = []error{fmt.Errorf("bad")} p.ValidateProviderConfigResponse = providers.ValidateProviderConfigResponse{
Diagnostics: tfdiags.Diagnostics{}.Append(fmt.Errorf("bad")),
}
diags := c.Validate() diags := c.Validate()
if !diags.HasErrors() { if !diags.HasErrors() {
@ -718,7 +731,9 @@ func TestContext2Validate_provisionerConfig_bad(t *testing.T) {
}, },
}) })
pr.ValidateReturnErrors = []error{fmt.Errorf("bad")} p.ValidateProviderConfigResponse = providers.ValidateProviderConfigResponse{
Diagnostics: tfdiags.Diagnostics{}.Append(fmt.Errorf("bad")),
}
diags := c.Validate() diags := c.Validate()
if !diags.HasErrors() { if !diags.HasErrors() {
@ -745,11 +760,14 @@ func TestContext2Validate_provisionerConfig_good(t *testing.T) {
} }
pr := simpleMockProvisioner() pr := simpleMockProvisioner()
pr.ValidateFn = func(c *ResourceConfig) ([]string, []error) { pr.ValidateProvisionerConfigFn = func(req provisioners.ValidateProvisionerConfigRequest) provisioners.ValidateProvisionerConfigResponse {
if c == nil { var diags tfdiags.Diagnostics
t.Fatalf("missing resource config for provisioner") if req.Config.GetAttr("test_string").IsNull() {
diags.Append(errors.New("test_string is not set"))
}
return provisioners.ValidateProvisionerConfigResponse{
Diagnostics: diags,
} }
return nil, c.CheckSet([]string{"test_string"})
} }
c := testContext2(t, &ContextOpts{ c := testContext2(t, &ContextOpts{
@ -820,7 +838,9 @@ func TestContext2Validate_resourceConfig_bad(t *testing.T) {
), ),
}) })
p.ValidateResourceReturnErrors = []error{fmt.Errorf("bad")} p.ValidateResourceTypeConfigResponse = providers.ValidateResourceTypeConfigResponse{
Diagnostics: tfdiags.Diagnostics{}.Append(fmt.Errorf("bad")),
}
diags := c.Validate() diags := c.Validate()
if !diags.HasErrors() { if !diags.HasErrors() {
@ -896,9 +916,14 @@ func TestContext2Validate_tainted(t *testing.T) {
State: state, State: state,
}) })
p.ValidateResourceFn = func( p.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
t string, c *ResourceConfig) ([]string, []error) { var diags tfdiags.Diagnostics
return nil, c.CheckSet([]string{"foo"}) if req.Config.GetAttr("foo").IsNull() {
diags.Append(errors.New("foo is not set"))
}
return providers.ValidateResourceTypeConfigResponse{
Diagnostics: diags,
}
} }
diags := c.Validate() diags := c.Validate()
@ -986,14 +1011,14 @@ func TestContext2Validate_varRefFilled(t *testing.T) {
}, },
}) })
var value interface{} var value cty.Value
p.ValidateResourceFn = func(t string, c *ResourceConfig) ([]string, []error) { p.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
value, _ = c.Get("foo") value = req.Config.GetAttr("foo")
return nil, nil return providers.ValidateResourceTypeConfigResponse{}
} }
c.Validate() c.Validate()
if value != "bar" { if !value.RawEquals(cty.StringVal("bar")) {
t.Fatalf("bad: %#v", value) t.Fatalf("bad: %#v", value)
} }
} }

View File

@ -1,17 +1,12 @@
package terraform package terraform
import ( import (
"fmt"
"testing" "testing"
"github.com/hashicorp/hcl2/hcl/hclsyntax"
"github.com/hashicorp/hcl2/hcl"
"github.com/hashicorp/terraform/configs"
) )
func TestProcessIgnoreChanges(t *testing.T) { func TestProcessIgnoreChanges(t *testing.T) {
var evalDiff *EvalDiff t.Fatalf("TestProcessIgnoreChanges not yet updated for new processIgnoreChanges signature")
/*var evalDiff *EvalDiff
var instanceDiff *InstanceDiff var instanceDiff *InstanceDiff
var testDiffs = func(t *testing.T, ignoreChanges []string, newAttribute string) (*EvalDiff, *InstanceDiff) { var testDiffs = func(t *testing.T, ignoreChanges []string, newAttribute string) (*EvalDiff, *InstanceDiff) {
@ -108,5 +103,5 @@ func TestProcessIgnoreChanges(t *testing.T) {
} }
} }
}) })
} }*/
} }

View File

@ -19,17 +19,14 @@ import (
func TestEvalValidateResource_managedResource(t *testing.T) { func TestEvalValidateResource_managedResource(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateResourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
expected := "test_object" if got, want := req.TypeName, "test_object"; got != want {
if rt != expected { t.Fatalf("wrong resource type\ngot: %#v\nwant: %#v", got, want)
t.Fatalf("wrong resource type\ngot: %#v\nwant: %#v", rt, expected)
} }
expected = "bar" if got, want := req.Config.GetAttr("test_string"), cty.StringVal("bar"); !got.RawEquals(want) {
val, _ := c.Get("test_string") t.Fatalf("wrong value for test_string\ngot: %#v\nwant: %#v", got, want)
if val != expected {
t.Fatalf("wrong value for test_string\ngot: %#v\nwant: %#v", val, expected)
} }
return return providers.ValidateResourceTypeConfigResponse{}
} }
p := providers.Interface(mp) p := providers.Interface(mp)
@ -60,24 +57,21 @@ func TestEvalValidateResource_managedResource(t *testing.T) {
t.Fatalf("err: %s", err) t.Fatalf("err: %s", err)
} }
if !mp.ValidateResourceCalled { if !mp.ValidateResourceTypeConfigCalled {
t.Fatal("Expected ValidateResource to be called, but it was not!") t.Fatal("Expected ValidateResourceTypeConfig to be called, but it was not!")
} }
} }
func TestEvalValidateResource_managedResourceCount(t *testing.T) { func TestEvalValidateResource_managedResourceCount(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateResourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
expected := "test_object" if got, want := req.TypeName, "test_object"; got != want {
if rt != expected { t.Fatalf("wrong resource type\ngot: %#v\nwant: %#v", got, want)
t.Fatalf("wrong resource type\ngot: %#v\nwant: %#v", rt, expected)
} }
expected = "bar" if got, want := req.Config.GetAttr("test_string"), cty.StringVal("bar"); !got.RawEquals(want) {
val, _ := c.Get("test_string") t.Fatalf("wrong value for test_string\ngot: %#v\nwant: %#v", got, want)
if val != expected {
t.Fatalf("wrong value for test_string\ngot: %#v\nwant: %#v", val, expected)
} }
return return providers.ValidateResourceTypeConfigResponse{}
} }
p := providers.Interface(mp) p := providers.Interface(mp)
@ -109,24 +103,21 @@ func TestEvalValidateResource_managedResourceCount(t *testing.T) {
t.Fatalf("err: %s", err) t.Fatalf("err: %s", err)
} }
if !mp.ValidateResourceCalled { if !mp.ValidateResourceTypeConfigCalled {
t.Fatal("Expected ValidateResource to be called, but it was not!") t.Fatal("Expected ValidateResourceTypeConfig to be called, but it was not!")
} }
} }
func TestEvalValidateResource_dataSource(t *testing.T) { func TestEvalValidateResource_dataSource(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateDataSourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateDataSourceConfigFn = func(req providers.ValidateDataSourceConfigRequest) providers.ValidateDataSourceConfigResponse {
expected := "test_object" if got, want := req.TypeName, "test_object"; got != want {
if rt != expected { t.Fatalf("wrong resource type\ngot: %#v\nwant: %#v", got, want)
t.Fatalf("expected: %s, got: %s", expected, rt)
} }
expected = "bar" if got, want := req.Config.GetAttr("test_string"), cty.StringVal("bar"); !got.RawEquals(want) {
val, _ := c.Get("test_string") t.Fatalf("wrong value for test_string\ngot: %#v\nwant: %#v", got, want)
if val != expected {
t.Fatalf("expected: %s, got: %s", expected, val)
} }
return return providers.ValidateDataSourceConfigResponse{}
} }
p := providers.Interface(mp) p := providers.Interface(mp)
@ -158,15 +149,15 @@ func TestEvalValidateResource_dataSource(t *testing.T) {
t.Fatalf("err: %s", err) t.Fatalf("err: %s", err)
} }
if !mp.ValidateDataSourceCalled { if !mp.ValidateDataSourceConfigCalled {
t.Fatal("Expected ValidateDataSource to be called, but it was not!") t.Fatal("Expected ValidateDataSourceConfig to be called, but it was not!")
} }
} }
func TestEvalValidateResource_validReturnsNilError(t *testing.T) { func TestEvalValidateResource_validReturnsNilError(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateResourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
return return providers.ValidateResourceTypeConfigResponse{}
} }
p := providers.Interface(mp) p := providers.Interface(mp)
@ -198,10 +189,13 @@ func TestEvalValidateResource_validReturnsNilError(t *testing.T) {
func TestEvalValidateResource_warningsAndErrorsPassedThrough(t *testing.T) { func TestEvalValidateResource_warningsAndErrorsPassedThrough(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateResourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
ws = append(ws, "warn") var diags tfdiags.Diagnostics
es = append(es, errors.New("err")) diags = diags.Append(tfdiags.SimpleWarning("warn"))
return diags = diags.Append(errors.New("err"))
return providers.ValidateResourceTypeConfigResponse{
Diagnostics: diags,
}
} }
p := providers.Interface(mp) p := providers.Interface(mp)
@ -246,9 +240,12 @@ func TestEvalValidateResource_warningsAndErrorsPassedThrough(t *testing.T) {
func TestEvalValidateResource_ignoreWarnings(t *testing.T) { func TestEvalValidateResource_ignoreWarnings(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateResourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
ws = append(ws, "warn") var diags tfdiags.Diagnostics
return diags = diags.Append(tfdiags.SimpleWarning("warn"))
return providers.ValidateResourceTypeConfigResponse{
Diagnostics: diags,
}
} }
p := providers.Interface(mp) p := providers.Interface(mp)
@ -282,8 +279,8 @@ func TestEvalValidateResource_ignoreWarnings(t *testing.T) {
func TestEvalValidateResource_invalidDependsOn(t *testing.T) { func TestEvalValidateResource_invalidDependsOn(t *testing.T) {
mp := simpleMockProvider() mp := simpleMockProvider()
mp.ValidateResourceFn = func(rt string, c *ResourceConfig) (ws []string, es []error) { mp.ValidateResourceTypeConfigFn = func(req providers.ValidateResourceTypeConfigRequest) providers.ValidateResourceTypeConfigResponse {
return return providers.ValidateResourceTypeConfigResponse{}
} }
// We'll check a _valid_ config first, to make sure we're not failing // We'll check a _valid_ config first, to make sure we're not failing
@ -390,8 +387,8 @@ func TestEvalValidateProvisioner_valid(t *testing.T) {
t.Errorf("node.Eval returned non-nil result") t.Errorf("node.Eval returned non-nil result")
} }
if !mp.ValidateCalled { if !mp.ValidateProvisionerConfigCalled {
t.Fatalf("p.Validate not called") t.Fatalf("p.ValidateProvisionerConfig not called")
} }
} }
@ -429,7 +426,13 @@ func TestEvalValidateProvisioner_warning(t *testing.T) {
}, },
} }
mp.ValidateReturnWarns = []string{"foo is deprecated"} {
var diags tfdiags.Diagnostics
diags = diags.Append(tfdiags.SimpleWarning("foo is deprecated"))
mp.ValidateProvisionerConfigResponse = provisioners.ValidateProvisionerConfigResponse{
Diagnostics: diags,
}
}
_, err := node.Eval(ctx) _, err := node.Eval(ctx)
if err == nil { if err == nil {
@ -442,7 +445,7 @@ func TestEvalValidateProvisioner_warning(t *testing.T) {
t.Fatalf("wrong number of diagsnostics in %#v; want one warning", diags) t.Fatalf("wrong number of diagsnostics in %#v; want one warning", diags)
} }
if got, want := diags[0].Description().Summary, mp.ValidateReturnWarns[0]; got != want { if got, want := diags[0].Description().Summary, mp.ValidateProvisionerConfigResponse.Diagnostics[0].Description().Summary; got != want {
t.Fatalf("wrong warning %q; want %q", got, want) t.Fatalf("wrong warning %q; want %q", got, want)
} }
} }

View File

@ -5,6 +5,7 @@ import (
"testing" "testing"
"github.com/hashicorp/terraform/addrs" "github.com/hashicorp/terraform/addrs"
"github.com/hashicorp/terraform/configs/configschema"
"github.com/hashicorp/terraform/providers" "github.com/hashicorp/terraform/providers"
) )
@ -14,22 +15,20 @@ func TestPlanGraphBuilder_impl(t *testing.T) {
func TestPlanGraphBuilder(t *testing.T) { func TestPlanGraphBuilder(t *testing.T) {
awsProvider := &MockProvider{ awsProvider := &MockProvider{
GetSchemaResponse: provider.GetSchemaResponse{ GetSchemaReturn: &ProviderSchema{
Provider: providers.Schema{ Provider: simpleTestSchema(),
Block: simpleTestSchema(), ResourceTypes: map[string]*configschema.Block{
}, "aws_security_group": simpleTestSchema(),
ResourceTypes: map[string]providers.Schema{ "aws_instance": simpleTestSchema(),
"aws_security_group": {Block: simpleTestSchema()}, "aws_load_balancer": simpleTestSchema(),
"aws_instance": {Block: simpleTestSchema()},
"aws_load_balancer": {Block: simpleTestSchema()},
}, },
}, },
} }
openstackProvider := &MockProvider{ openstackProvider := &MockProvider{
GetSchemaResponse: providers.GetSchemaResponse{ GetSchemaReturn: &ProviderSchema{
Provider: providers.Schema{Block: simpleTestSchema()}, Provider: simpleTestSchema(),
ResourceTypes: map[string]providers.Schema{ ResourceTypes: map[string]*configschema.Block{
"openstack_floating_ip": {Block: simpleTestSchema()}, "openstack_floating_ip": simpleTestSchema(),
}, },
}, },
} }

View File

@ -7,6 +7,7 @@ import (
"github.com/hashicorp/terraform/addrs" "github.com/hashicorp/terraform/addrs"
"github.com/hashicorp/terraform/plans" "github.com/hashicorp/terraform/plans"
"github.com/hashicorp/terraform/providers"
"github.com/hashicorp/terraform/states" "github.com/hashicorp/terraform/states"
) )
@ -90,7 +91,7 @@ func (h *testHook) PreImportState(addr addrs.AbsResourceInstance, importID strin
return HookActionContinue, nil return HookActionContinue, nil
} }
func (h *testHook) PostImportState(addr addrs.AbsResourceInstance, imported []*states.ImportedObject) (HookAction, error) { func (h *testHook) PostImportState(addr addrs.AbsResourceInstance, imported []providers.ImportedResource) (HookAction, error) {
h.Calls = append(h.Calls, &testHookCall{"PostImportState", addr.String()}) h.Calls = append(h.Calls, &testHookCall{"PostImportState", addr.String()})
return HookActionContinue, nil return HookActionContinue, nil
} }

View File

@ -1,9 +1,11 @@
package terraform package terraform
import ( import (
"encoding/json"
"fmt" "fmt"
"sync" "sync"
"github.com/hashicorp/terraform/config/hcl2shim"
"github.com/hashicorp/terraform/tfdiags" "github.com/hashicorp/terraform/tfdiags"
"github.com/hashicorp/terraform/providers" "github.com/hashicorp/terraform/providers"
@ -73,6 +75,9 @@ type MockProvider struct {
ImportResourceStateResponse providers.ImportResourceStateResponse ImportResourceStateResponse providers.ImportResourceStateResponse
ImportResourceStateRequest providers.ImportResourceStateRequest ImportResourceStateRequest providers.ImportResourceStateRequest
ImportResourceStateFn func(providers.ImportResourceStateRequest) providers.ImportResourceStateResponse ImportResourceStateFn func(providers.ImportResourceStateRequest) providers.ImportResourceStateResponse
// Legacy return type for existing tests, which will be shimmed into an
// ImportResourceStateResponse if set
ImportStateReturn []*InstanceState
ReadDataSourceCalled bool ReadDataSourceCalled bool
ReadDataSourceResponse providers.ReadDataSourceResponse ReadDataSourceResponse providers.ReadDataSourceResponse
@ -259,6 +264,29 @@ func (p *MockProvider) ImportResourceState(r providers.ImportResourceStateReques
p.Lock() p.Lock()
defer p.Unlock() defer p.Unlock()
if p.ImportStateReturn != nil {
for _, is := range p.ImportStateReturn {
is.Attributes["id"] = is.ID
schema := p.GetSchemaReturn.ResourceTypes[r.TypeName]
private, err := json.Marshal(is.Meta)
if err != nil {
panic(err)
}
state, err := hcl2shim.HCL2ValueFromFlatmap(is.Attributes, schema.ImpliedType())
if err != nil {
panic(err)
}
p.ImportResourceStateResponse.ImportedResources = append(
p.ImportResourceStateResponse.ImportedResources,
providers.ImportedResource{
TypeName: r.TypeName,
State: state,
Private: private,
})
}
}
p.ImportResourceStateCalled = true p.ImportResourceStateCalled = true
p.ImportResourceStateRequest = r p.ImportResourceStateRequest = r
if p.ImportResourceStateFn != nil { if p.ImportResourceStateFn != nil {

View File

@ -12,7 +12,7 @@ func simpleTestSchemas() *Schemas {
"test": provider.GetSchemaReturn, "test": provider.GetSchemaReturn,
}, },
provisioners: map[string]*configschema.Block{ provisioners: map[string]*configschema.Block{
"test": provisioner.GetConfigSchemaReturnSchema, "test": provisioner.GetSchemaResponse.Provisioner,
}, },
} }
} }