2015-07-10 15:08:49 -05:00
|
|
|
package terraform
|
|
|
|
|
|
|
|
import (
|
|
|
|
"reflect"
|
2017-06-22 14:37:32 -05:00
|
|
|
"regexp"
|
2015-07-10 15:08:49 -05:00
|
|
|
"sort"
|
|
|
|
"strings"
|
2015-08-10 15:04:48 -05:00
|
|
|
"sync"
|
2015-07-10 15:08:49 -05:00
|
|
|
"testing"
|
2018-05-04 21:24:06 -05:00
|
|
|
|
2018-09-06 18:36:35 -05:00
|
|
|
"github.com/google/go-cmp/cmp"
|
2018-05-16 10:47:22 -05:00
|
|
|
"github.com/zclconf/go-cty/cty"
|
|
|
|
|
2018-05-04 21:24:06 -05:00
|
|
|
"github.com/hashicorp/terraform/addrs"
|
2018-07-05 12:33:29 -05:00
|
|
|
"github.com/hashicorp/terraform/configs/configschema"
|
2019-08-06 18:58:58 -05:00
|
|
|
"github.com/hashicorp/terraform/configs/hcl2shim"
|
2018-08-17 14:32:35 -05:00
|
|
|
"github.com/hashicorp/terraform/providers"
|
2018-11-30 12:56:50 -06:00
|
|
|
"github.com/hashicorp/terraform/states"
|
2015-07-10 15:08:49 -05:00
|
|
|
)
|
|
|
|
|
|
|
|
func TestContext2Refresh(t *testing.T) {
|
2018-09-06 18:36:35 -05:00
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-basic")
|
|
|
|
|
2018-10-15 20:07:01 -05:00
|
|
|
startingState := MustShimLegacyState(&State{
|
2018-09-06 18:36:35 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
Attributes: map[string]string{
|
|
|
|
"id": "foo",
|
|
|
|
"foo": "bar",
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
2018-09-06 18:36:35 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
})
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-06 18:36:35 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: startingState,
|
|
|
|
})
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-06 18:36:35 -05:00
|
|
|
schema := p.GetSchemaReturn.ResourceTypes["aws_instance"]
|
|
|
|
ty := schema.ImpliedType()
|
|
|
|
readState, err := hcl2shim.HCL2ValueFromFlatmap(map[string]string{"id": "foo", "foo": "baz"}, ty)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-06 18:36:35 -05:00
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: readState,
|
|
|
|
}
|
|
|
|
|
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatal(diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
if !p.ReadResourceCalled {
|
|
|
|
t.Fatal("ReadResource should be called")
|
|
|
|
}
|
|
|
|
|
|
|
|
mod := s.RootModule()
|
|
|
|
fromState, err := mod.Resources["aws_instance.web"].Instances[addrs.NoKey].Current.Decode(ty)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
newState, err := schema.CoerceValue(fromState.Value)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
if !cmp.Equal(readState, newState, valueComparer) {
|
|
|
|
t.Fatal(cmp.Diff(readState, newState, valueComparer, equateEmpty))
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2019-03-16 17:36:53 -05:00
|
|
|
func TestContext2Refresh_dynamicAttr(t *testing.T) {
|
|
|
|
m := testModule(t, "refresh-dynamic")
|
|
|
|
|
|
|
|
startingState := states.BuildState(func(ss *states.SyncState) {
|
|
|
|
ss.SetResourceInstanceCurrent(
|
|
|
|
addrs.Resource{
|
|
|
|
Mode: addrs.ManagedResourceMode,
|
|
|
|
Type: "test_instance",
|
|
|
|
Name: "foo",
|
|
|
|
}.Instance(addrs.NoKey).Absolute(addrs.RootModuleInstance),
|
|
|
|
&states.ResourceInstanceObjectSrc{
|
|
|
|
Status: states.ObjectReady,
|
|
|
|
AttrsJSON: []byte(`{"dynamic":{"type":"string","value":"hello"}}`),
|
|
|
|
},
|
|
|
|
addrs.ProviderConfig{
|
|
|
|
Type: "test",
|
|
|
|
}.Absolute(addrs.RootModuleInstance),
|
|
|
|
)
|
|
|
|
})
|
|
|
|
|
|
|
|
readStateVal := cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"dynamic": cty.EmptyTupleVal,
|
|
|
|
})
|
|
|
|
|
|
|
|
p := testProvider("test")
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"test_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"dynamic": {Type: cty.DynamicPseudoType, Optional: true},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: readStateVal,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"test": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: startingState,
|
|
|
|
})
|
|
|
|
|
|
|
|
schema := p.GetSchemaReturn.ResourceTypes["test_instance"]
|
|
|
|
ty := schema.ImpliedType()
|
|
|
|
|
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatal(diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
if !p.ReadResourceCalled {
|
|
|
|
t.Fatal("ReadResource should be called")
|
|
|
|
}
|
|
|
|
|
|
|
|
mod := s.RootModule()
|
|
|
|
newState, err := mod.Resources["test_instance.foo"].Instances[addrs.NoKey].Current.Decode(ty)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
if !cmp.Equal(readStateVal, newState.Value, valueComparer) {
|
|
|
|
t.Error(cmp.Diff(newState.Value, readStateVal, valueComparer, equateEmpty))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-03-17 17:29:10 -05:00
|
|
|
func TestContext2Refresh_dataComputedModuleVar(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-data-module-var")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2017-03-17 17:29:10 -05:00
|
|
|
})
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"id": cty.StringVal("foo"),
|
|
|
|
}),
|
2017-03-17 17:29:10 -05:00
|
|
|
}
|
|
|
|
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"foo": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
DataSources: map[string]*configschema.Block{
|
|
|
|
"aws_data_source": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2017-03-17 17:29:10 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
checkStateString(t, s, `
|
|
|
|
<no state>
|
2018-09-06 18:36:35 -05:00
|
|
|
`)
|
2017-03-17 17:29:10 -05:00
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
func TestContext2Refresh_targeted(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_elb": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"instances": {
|
|
|
|
Type: cty.Set(cty.String),
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
"vpc_id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_vpc": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
m := testModule(t, "refresh-targeted")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_vpc.metoo": resourceState("aws_vpc", "vpc-abc123"),
|
|
|
|
"aws_instance.notme": resourceState("aws_instance", "i-bcd345"),
|
|
|
|
"aws_instance.me": resourceState("aws_instance", "i-abc123"),
|
|
|
|
"aws_elb.meneither": resourceState("aws_elb", "lb-abc123"),
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2018-05-04 21:24:06 -05:00
|
|
|
Targets: []addrs.Targetable{
|
|
|
|
addrs.RootModuleInstance.Resource(
|
|
|
|
addrs.ManagedResourceMode, "aws_instance", "me",
|
|
|
|
),
|
|
|
|
},
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
|
|
|
refreshedResources := make([]string, 0, 2)
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
|
|
|
refreshedResources = append(refreshedResources, req.PriorState.GetAttr("id").AsString())
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: req.PriorState,
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-09-06 18:36:35 -05:00
|
|
|
expected := []string{"vpc-abc123", "i-abc123"}
|
2015-07-10 15:08:49 -05:00
|
|
|
if !reflect.DeepEqual(refreshedResources, expected) {
|
|
|
|
t.Fatalf("expected: %#v, got: %#v", expected, refreshedResources)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_targetedCount(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_elb": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"instances": {
|
|
|
|
Type: cty.Set(cty.String),
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
"vpc_id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_vpc": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
m := testModule(t, "refresh-targeted-count")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_vpc.metoo": resourceState("aws_vpc", "vpc-abc123"),
|
|
|
|
"aws_instance.notme": resourceState("aws_instance", "i-bcd345"),
|
|
|
|
"aws_instance.me.0": resourceState("aws_instance", "i-abc123"),
|
|
|
|
"aws_instance.me.1": resourceState("aws_instance", "i-cde567"),
|
|
|
|
"aws_instance.me.2": resourceState("aws_instance", "i-cde789"),
|
|
|
|
"aws_elb.meneither": resourceState("aws_elb", "lb-abc123"),
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2018-05-04 21:24:06 -05:00
|
|
|
Targets: []addrs.Targetable{
|
|
|
|
addrs.RootModuleInstance.Resource(
|
|
|
|
addrs.ManagedResourceMode, "aws_instance", "me",
|
|
|
|
),
|
|
|
|
},
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
|
|
|
refreshedResources := make([]string, 0, 2)
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
|
|
|
refreshedResources = append(refreshedResources, req.PriorState.GetAttr("id").AsString())
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: req.PriorState,
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
// Target didn't specify index, so we should get all our instances
|
|
|
|
expected := []string{
|
2018-09-06 18:36:35 -05:00
|
|
|
"vpc-abc123",
|
|
|
|
"i-abc123",
|
|
|
|
"i-cde567",
|
|
|
|
"i-cde789",
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
sort.Strings(expected)
|
|
|
|
sort.Strings(refreshedResources)
|
|
|
|
if !reflect.DeepEqual(refreshedResources, expected) {
|
2018-05-25 12:34:24 -05:00
|
|
|
t.Fatalf("wrong result\ngot: %#v\nwant: %#v", refreshedResources, expected)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_targetedCountIndex(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_elb": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"instances": {
|
|
|
|
Type: cty.Set(cty.String),
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
"vpc_id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_vpc": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
m := testModule(t, "refresh-targeted-count")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_vpc.metoo": resourceState("aws_vpc", "vpc-abc123"),
|
|
|
|
"aws_instance.notme": resourceState("aws_instance", "i-bcd345"),
|
|
|
|
"aws_instance.me.0": resourceState("aws_instance", "i-abc123"),
|
|
|
|
"aws_instance.me.1": resourceState("aws_instance", "i-cde567"),
|
|
|
|
"aws_instance.me.2": resourceState("aws_instance", "i-cde789"),
|
|
|
|
"aws_elb.meneither": resourceState("aws_elb", "lb-abc123"),
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2018-05-04 21:24:06 -05:00
|
|
|
Targets: []addrs.Targetable{
|
|
|
|
addrs.RootModuleInstance.ResourceInstance(
|
|
|
|
addrs.ManagedResourceMode, "aws_instance", "me", addrs.IntKey(0),
|
|
|
|
),
|
|
|
|
},
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
|
|
|
refreshedResources := make([]string, 0, 2)
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
|
|
|
refreshedResources = append(refreshedResources, req.PriorState.GetAttr("id").AsString())
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: req.PriorState,
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-09-06 18:36:35 -05:00
|
|
|
expected := []string{"vpc-abc123", "i-abc123"}
|
2015-07-10 15:08:49 -05:00
|
|
|
if !reflect.DeepEqual(refreshedResources, expected) {
|
2018-05-25 12:34:24 -05:00
|
|
|
t.Fatalf("wrong result\ngot: %#v\nwant: %#v", refreshedResources, expected)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_moduleComputedVar(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
"value": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
m := testModule(t, "refresh-module-computed-var")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
|
|
|
// This was failing (see GH-2188) at some point, so this test just
|
|
|
|
// verifies that the failure goes away.
|
2018-05-25 12:34:24 -05:00
|
|
|
if _, diags := ctx.Refresh(); diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errs: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_delete(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-basic")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = nil
|
2018-09-06 18:36:35 -05:00
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: cty.NullVal(p.GetSchemaReturn.ResourceTypes["aws_instance"].ImpliedType()),
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
mod := s.RootModule()
|
|
|
|
if len(mod.Resources) > 0 {
|
|
|
|
t.Fatal("resources should be empty")
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_ignoreUncreated(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-basic")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
State: nil,
|
|
|
|
})
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"id": cty.StringVal("foo"),
|
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
2018-09-05 16:35:30 -05:00
|
|
|
if p.ReadResourceCalled {
|
2015-07-10 15:08:49 -05:00
|
|
|
t.Fatal("refresh should not be called")
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_hook(t *testing.T) {
|
|
|
|
h := new(MockHook)
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-basic")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2015-07-10 15:08:49 -05:00
|
|
|
Hooks: []Hook{h},
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
if _, diags := ctx.Refresh(); diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errs: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
if !h.PreRefreshCalled {
|
|
|
|
t.Fatal("should be called")
|
|
|
|
}
|
|
|
|
if !h.PostRefreshCalled {
|
|
|
|
t.Fatal("should be called")
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_modules(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-modules")
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
2016-04-21 14:59:10 -05:00
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "bar",
|
|
|
|
Tainted: true,
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
|
|
|
|
&ModuleState{
|
|
|
|
Path: []string{"root", "child"},
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "baz",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2015-07-10 15:08:49 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
State: state,
|
|
|
|
})
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
|
|
|
if !req.PriorState.GetAttr("id").RawEquals(cty.StringVal("baz")) {
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: req.PriorState,
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
new, _ := cty.Transform(req.PriorState, func(path cty.Path, v cty.Value) (cty.Value, error) {
|
|
|
|
if len(path) == 1 && path[0].(cty.GetAttrStep).Name == "id" {
|
|
|
|
return cty.StringVal("new"), nil
|
|
|
|
}
|
|
|
|
return v, nil
|
|
|
|
})
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: new,
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
actual := strings.TrimSpace(s.String())
|
|
|
|
expected := strings.TrimSpace(testContextRefreshModuleStr)
|
|
|
|
if actual != expected {
|
2018-05-25 12:34:24 -05:00
|
|
|
t.Fatalf("wrong result\n\ngot:\n%s\n\nwant:\n%s", actual, expected)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_moduleInputComputedOutput(t *testing.T) {
|
|
|
|
m := testModule(t, "refresh-module-input-computed-output")
|
|
|
|
p := testProvider("aws")
|
|
|
|
p.DiffFn = testDiffFn
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"foo": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
"compute": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
if _, diags := ctx.Refresh(); diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errs: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_moduleVarModule(t *testing.T) {
|
|
|
|
m := testModule(t, "refresh-module-var-module")
|
|
|
|
p := testProvider("aws")
|
|
|
|
p.DiffFn = testDiffFn
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
if _, diags := ctx.Refresh(); diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errs: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// GH-70
|
|
|
|
func TestContext2Refresh_noState(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-no-state")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"id": cty.StringVal("foo"),
|
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
if _, diags := ctx.Refresh(); diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errs: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_output(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
2018-09-07 16:45:51 -05:00
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
2018-05-16 10:47:22 -05:00
|
|
|
"foo": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
m := testModule(t, "refresh-output")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
Attributes: map[string]string{
|
2018-09-07 16:45:51 -05:00
|
|
|
"id": "foo",
|
2015-07-10 15:08:49 -05:00
|
|
|
"foo": "bar",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
|
2016-05-11 19:05:02 -05:00
|
|
|
Outputs: map[string]*OutputState{
|
|
|
|
"foo": &OutputState{
|
|
|
|
Type: "string",
|
|
|
|
Sensitive: false,
|
|
|
|
Value: "foo",
|
|
|
|
},
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
actual := strings.TrimSpace(s.String())
|
|
|
|
expected := strings.TrimSpace(testContextRefreshOutputStr)
|
|
|
|
if actual != expected {
|
2018-09-07 16:45:51 -05:00
|
|
|
t.Fatalf("wrong result\n\ngot:\n%q\n\nwant:\n%q", actual, expected)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_outputPartial(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-output-partial")
|
2018-09-24 14:27:03 -05:00
|
|
|
|
|
|
|
// Refresh creates a partial plan for any instances that don't have
|
|
|
|
// remote objects yet, to get stub values for interpolation. Therefore
|
|
|
|
// we need to make DiffFn available to let that complete.
|
|
|
|
p.DiffFn = testDiffFn
|
|
|
|
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"foo": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: cty.NullVal(p.GetSchemaReturn.ResourceTypes["aws_instance"].ImpliedType()),
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.foo": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
2016-06-22 09:06:41 -05:00
|
|
|
Outputs: map[string]*OutputState{},
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
actual := strings.TrimSpace(s.String())
|
|
|
|
expected := strings.TrimSpace(testContextRefreshOutputPartialStr)
|
|
|
|
if actual != expected {
|
2018-05-25 12:34:24 -05:00
|
|
|
t.Fatalf("wrong result\n\ngot:\n%s\n\nwant:\n%s", actual, expected)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2017-01-21 13:22:40 -06:00
|
|
|
func TestContext2Refresh_stateBasic(t *testing.T) {
|
2018-09-07 16:45:51 -05:00
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-basic")
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2018-09-07 16:45:51 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "bar",
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
2018-09-07 16:45:51 -05:00
|
|
|
},
|
|
|
|
})
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: state,
|
|
|
|
})
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
schema := p.GetSchemaReturn.ResourceTypes["aws_instance"]
|
|
|
|
ty := schema.ImpliedType()
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
readStateVal, err := schema.CoerceValue(cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"id": cty.StringVal("foo"),
|
|
|
|
}))
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: readStateVal,
|
|
|
|
}
|
|
|
|
|
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
if !p.ReadResourceCalled {
|
|
|
|
t.Fatal("read resource should be called")
|
|
|
|
}
|
|
|
|
|
|
|
|
mod := s.RootModule()
|
|
|
|
newState, err := mod.Resources["aws_instance.web"].Instances[addrs.NoKey].Current.Decode(ty)
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
if !cmp.Equal(readStateVal, newState.Value, valueComparer, equateEmpty) {
|
|
|
|
t.Fatal(cmp.Diff(readStateVal, newState.Value, valueComparer, equateEmpty))
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2019-04-25 15:17:23 -05:00
|
|
|
func TestContext2Refresh_dataCount(t *testing.T) {
|
|
|
|
p := testProvider("test")
|
|
|
|
m := testModule(t, "refresh-data-count")
|
|
|
|
|
|
|
|
// This test is verifying that a data resource count can refer to a
|
|
|
|
// resource attribute that can't be known yet during refresh (because
|
|
|
|
// the resource in question isn't in the state at all). In that case,
|
|
|
|
// we skip the data resource during refresh and process it during the
|
|
|
|
// subsequent plan step instead.
|
|
|
|
//
|
|
|
|
// Normally it's an error for "count" to be computed, but during the
|
|
|
|
// refresh step we allow it because we _expect_ to be working with an
|
|
|
|
// incomplete picture of the world sometimes, particularly when we're
|
|
|
|
// creating object for the first time against an empty state.
|
|
|
|
//
|
|
|
|
// For more information, see:
|
|
|
|
// https://github.com/hashicorp/terraform/issues/21047
|
|
|
|
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"test": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"things": {Type: cty.List(cty.String), Optional: true},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
DataSources: map[string]*configschema.Block{
|
|
|
|
"test": {},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"test": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
Config: m,
|
|
|
|
})
|
|
|
|
|
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if p.ReadResourceCalled {
|
|
|
|
// The managed resource doesn't exist in the state yet, so there's
|
|
|
|
// nothing to refresh.
|
|
|
|
t.Errorf("ReadResource was called, but should not have been")
|
|
|
|
}
|
|
|
|
if p.ReadDataSourceCalled {
|
|
|
|
// The data resource should've been skipped because its count cannot
|
|
|
|
// be determined yet.
|
|
|
|
t.Errorf("ReadDataSource was called, but should not have been")
|
|
|
|
}
|
|
|
|
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
checkStateString(t, s, `<no state>`)
|
|
|
|
}
|
|
|
|
|
2017-02-03 13:58:03 -06:00
|
|
|
func TestContext2Refresh_dataOrphan(t *testing.T) {
|
|
|
|
p := testProvider("null")
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2017-02-03 13:58:03 -06:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"data.null_data_source.bar": &ResourceState{
|
2017-04-21 17:42:23 -05:00
|
|
|
Type: "null_data_source",
|
2017-02-03 13:58:03 -06:00
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
},
|
2018-06-01 14:36:55 -05:00
|
|
|
Provider: "provider.null",
|
2017-02-03 13:58:03 -06:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2017-02-03 13:58:03 -06:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"null": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2017-02-03 13:58:03 -06:00
|
|
|
State: state,
|
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2017-02-03 13:58:03 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
checkStateString(t, s, `<no state>`)
|
|
|
|
}
|
|
|
|
|
2016-05-21 10:48:22 -05:00
|
|
|
func TestContext2Refresh_dataState(t *testing.T) {
|
2018-09-07 16:45:51 -05:00
|
|
|
m := testModule(t, "refresh-data-resource-basic")
|
2018-06-01 16:52:27 -05:00
|
|
|
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2018-09-07 16:45:51 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
// Intentionally no resources since data resources are
|
|
|
|
// supposed to refresh themselves even if they didn't
|
|
|
|
// already exist.
|
|
|
|
Resources: map[string]*ResourceState{},
|
2016-05-21 10:48:22 -05:00
|
|
|
},
|
2018-09-07 16:45:51 -05:00
|
|
|
},
|
|
|
|
})
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
schema := &configschema.Block{
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"inputs": {
|
|
|
|
Type: cty.Map(cty.String),
|
|
|
|
Optional: true,
|
2018-05-16 10:47:22 -05:00
|
|
|
},
|
2018-09-07 16:45:51 -05:00
|
|
|
},
|
|
|
|
}
|
2018-06-01 16:52:27 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
p := testProvider("null")
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
DataSources: map[string]*configschema.Block{
|
|
|
|
"null_data_source": schema,
|
|
|
|
},
|
|
|
|
}
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"null": testProviderFuncFixed(p),
|
2016-05-21 10:48:22 -05:00
|
|
|
},
|
2018-09-07 16:45:51 -05:00
|
|
|
),
|
|
|
|
State: state,
|
|
|
|
})
|
2016-05-21 10:48:22 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
var readStateVal cty.Value
|
2016-05-21 10:48:22 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
p.ReadDataSourceFn = func(req providers.ReadDataSourceRequest) providers.ReadDataSourceResponse {
|
|
|
|
m := req.Config.AsValueMap()
|
|
|
|
m["inputs"] = cty.MapVal(map[string]cty.Value{"test": cty.StringVal("yes")})
|
|
|
|
readStateVal = cty.ObjectVal(m)
|
2016-05-21 10:48:22 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
return providers.ReadDataSourceResponse{
|
|
|
|
State: readStateVal,
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}
|
2016-05-21 10:48:22 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
// FIXME: should the "outputs" value here be added to the reutnred state?
|
|
|
|
// Attributes: map[string]*ResourceAttrDiff{
|
|
|
|
// "inputs.#": {
|
|
|
|
// Old: "0",
|
|
|
|
// New: "1",
|
|
|
|
// Type: DiffAttrInput,
|
|
|
|
// },
|
|
|
|
// "inputs.test": {
|
|
|
|
// Old: "",
|
|
|
|
// New: "yes",
|
|
|
|
// Type: DiffAttrInput,
|
|
|
|
// },
|
|
|
|
// "outputs.#": {
|
|
|
|
// Old: "",
|
|
|
|
// New: "",
|
|
|
|
// NewComputed: true,
|
|
|
|
// Type: DiffAttrOutput,
|
|
|
|
// },
|
|
|
|
// },
|
|
|
|
}
|
|
|
|
|
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
if !p.ReadDataSourceCalled {
|
|
|
|
t.Fatal("ReadDataSource should have been called")
|
|
|
|
}
|
|
|
|
|
|
|
|
// mod := s.RootModule()
|
|
|
|
// if got := mod.Resources["data.null_data_source.testing"].Primary.ID; got != "-" {
|
|
|
|
// t.Fatalf("resource id is %q; want %s", got, "-")
|
|
|
|
// }
|
|
|
|
// if !reflect.DeepEqual(mod.Resources["data.null_data_source.testing"].Primary, p.ReadDataApplyReturn) {
|
|
|
|
// t.Fatalf("bad: %#v", mod.Resources)
|
|
|
|
// }
|
|
|
|
|
|
|
|
mod := s.RootModule()
|
|
|
|
|
|
|
|
newState, err := mod.Resources["data.null_data_source.testing"].Instances[addrs.NoKey].Current.Decode(schema.ImpliedType())
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
if !cmp.Equal(readStateVal, newState.Value, valueComparer, equateEmpty) {
|
|
|
|
t.Fatal(cmp.Diff(readStateVal, newState.Value, valueComparer, equateEmpty))
|
|
|
|
}
|
2016-05-21 10:48:22 -05:00
|
|
|
}
|
|
|
|
|
2016-10-23 20:53:00 -05:00
|
|
|
func TestContext2Refresh_dataStateRefData(t *testing.T) {
|
|
|
|
p := testProvider("null")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
DataSources: map[string]*configschema.Block{
|
|
|
|
"null_data_source": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
2018-09-07 16:45:51 -05:00
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
2018-05-16 10:47:22 -05:00
|
|
|
"foo": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
"bar": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2016-10-23 20:53:00 -05:00
|
|
|
m := testModule(t, "refresh-data-ref-data")
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2016-10-23 20:53:00 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
// Intentionally no resources since data resources are
|
|
|
|
// supposed to refresh themselves even if they didn't
|
|
|
|
// already exist.
|
|
|
|
Resources: map[string]*ResourceState{},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2016-10-23 20:53:00 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"null": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2016-10-23 20:53:00 -05:00
|
|
|
State: state,
|
|
|
|
})
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadDataSourceFn = func(req providers.ReadDataSourceRequest) providers.ReadDataSourceResponse {
|
2018-09-07 16:45:51 -05:00
|
|
|
// add the required id
|
|
|
|
m := req.Config.AsValueMap()
|
|
|
|
m["id"] = cty.StringVal("foo")
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
return providers.ReadDataSourceResponse{
|
2018-09-07 16:45:51 -05:00
|
|
|
State: cty.ObjectVal(m),
|
2018-09-05 16:35:30 -05:00
|
|
|
}
|
|
|
|
}
|
2016-10-23 20:53:00 -05:00
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2016-10-23 20:53:00 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
actual := strings.TrimSpace(s.String())
|
|
|
|
expected := strings.TrimSpace(testTerraformRefreshDataRefDataStr)
|
|
|
|
if actual != expected {
|
2018-05-25 12:34:24 -05:00
|
|
|
t.Fatalf("wrong result\n\ngot:\n%s\n\nwant:\n%s", actual, expected)
|
2016-10-23 20:53:00 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
func TestContext2Refresh_tainted(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-basic")
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2015-07-10 15:08:49 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
2016-04-21 14:59:10 -05:00
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "bar",
|
|
|
|
Tainted: true,
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2015-07-10 15:08:49 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
State: state,
|
|
|
|
})
|
2018-09-07 16:45:51 -05:00
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
|
|
|
// add the required id
|
|
|
|
m := req.PriorState.AsValueMap()
|
|
|
|
m["id"] = cty.StringVal("foo")
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: cty.ObjectVal(m),
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
2018-09-05 16:35:30 -05:00
|
|
|
if !p.ReadResourceCalled {
|
|
|
|
t.Fatal("ReadResource was not called; should have been")
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
actual := strings.TrimSpace(s.String())
|
|
|
|
expected := strings.TrimSpace(testContextRefreshTaintedStr)
|
|
|
|
if actual != expected {
|
2018-05-25 12:34:24 -05:00
|
|
|
t.Fatalf("wrong result\n\ngot:\n%s\n\nwant:\n%s", actual, expected)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// Doing a Refresh (or any operation really, but Refresh usually
|
|
|
|
// happens first) with a config with an unknown provider should result in
|
|
|
|
// an error. The key bug this found was that this wasn't happening if
|
|
|
|
// Providers was _empty_.
|
|
|
|
func TestContext2Refresh_unknownProvider(t *testing.T) {
|
|
|
|
m := testModule(t, "refresh-unknown-provider")
|
|
|
|
p := testProvider("aws")
|
|
|
|
p.ApplyFn = testApplyFn
|
|
|
|
p.DiffFn = testDiffFn
|
2017-04-21 19:40:46 -05:00
|
|
|
|
2018-05-04 21:24:06 -05:00
|
|
|
_, diags := NewContext(&ContextOpts{
|
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{},
|
2017-04-21 19:40:46 -05:00
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2017-01-21 13:22:40 -06:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2018-05-04 21:24:06 -05:00
|
|
|
if !diags.HasErrors() {
|
2017-04-21 19:40:46 -05:00
|
|
|
t.Fatal("successfully created context; want error")
|
|
|
|
}
|
|
|
|
|
2018-05-04 21:24:06 -05:00
|
|
|
if !regexp.MustCompile(`provider ".+" is not available`).MatchString(diags.Err().Error()) {
|
|
|
|
t.Fatalf("wrong error: %s", diags.Err())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_vars(t *testing.T) {
|
2018-09-07 16:45:51 -05:00
|
|
|
p := testProvider("aws")
|
|
|
|
|
|
|
|
schema := &configschema.Block{
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"ami": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
2018-05-16 10:47:22 -05:00
|
|
|
},
|
2018-09-07 16:45:51 -05:00
|
|
|
"id": {
|
|
|
|
Type: cty.String,
|
|
|
|
Computed: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{"aws_instance": schema},
|
|
|
|
}
|
|
|
|
|
|
|
|
m := testModule(t, "refresh-vars")
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2018-10-15 20:07:01 -05:00
|
|
|
State: MustShimLegacyState(&State{
|
2018-09-07 16:45:51 -05:00
|
|
|
|
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.web": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
2015-07-10 15:08:49 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
2018-09-07 16:45:51 -05:00
|
|
|
},
|
|
|
|
}),
|
|
|
|
})
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
readStateVal, err := schema.CoerceValue(cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"id": cty.StringVal("foo"),
|
|
|
|
}))
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
p.ReadResourceFn = nil
|
|
|
|
p.ReadResourceResponse = providers.ReadResourceResponse{
|
|
|
|
NewState: readStateVal,
|
|
|
|
}
|
|
|
|
|
|
|
|
p.PlanResourceChangeFn = func(req providers.PlanResourceChangeRequest) providers.PlanResourceChangeResponse {
|
|
|
|
return providers.PlanResourceChangeResponse{
|
|
|
|
PlannedState: req.ProposedNewState,
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
}
|
2018-09-07 16:45:51 -05:00
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
|
2018-09-07 16:45:51 -05:00
|
|
|
s, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
if !p.ReadResourceCalled {
|
|
|
|
t.Fatal("read resource should be called")
|
|
|
|
}
|
|
|
|
|
|
|
|
mod := s.RootModule()
|
|
|
|
|
|
|
|
newState, err := mod.Resources["aws_instance.web"].Instances[addrs.NoKey].Current.Decode(schema.ImpliedType())
|
|
|
|
if err != nil {
|
|
|
|
t.Fatal(err)
|
|
|
|
}
|
|
|
|
|
|
|
|
if !cmp.Equal(readStateVal, newState.Value, valueComparer, equateEmpty) {
|
|
|
|
t.Fatal(cmp.Diff(readStateVal, newState.Value, valueComparer, equateEmpty))
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, r := range mod.Resources {
|
|
|
|
if r.Addr.Type == "" {
|
|
|
|
t.Fatalf("no type: %#v", r)
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
2018-09-07 16:45:51 -05:00
|
|
|
}
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
|
2015-08-10 15:04:48 -05:00
|
|
|
func TestContext2Refresh_orphanModule(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-module-orphan")
|
|
|
|
|
|
|
|
// Create a custom refresh function to track the order they were visited
|
|
|
|
var order []string
|
|
|
|
var orderLock sync.Mutex
|
2018-09-05 16:35:30 -05:00
|
|
|
p.ReadResourceFn = func(req providers.ReadResourceRequest) providers.ReadResourceResponse {
|
2015-08-10 15:04:48 -05:00
|
|
|
orderLock.Lock()
|
|
|
|
defer orderLock.Unlock()
|
|
|
|
|
2018-09-05 16:35:30 -05:00
|
|
|
order = append(order, req.PriorState.GetAttr("id").AsString())
|
|
|
|
return providers.ReadResourceResponse{
|
|
|
|
NewState: req.PriorState,
|
|
|
|
}
|
2015-08-10 15:04:48 -05:00
|
|
|
}
|
|
|
|
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2015-08-10 15:04:48 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.foo": &ResourceState{
|
2017-04-21 17:42:23 -05:00
|
|
|
Type: "aws_instance",
|
2015-08-10 15:04:48 -05:00
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "i-abc123",
|
|
|
|
Attributes: map[string]string{
|
2018-09-07 16:45:51 -05:00
|
|
|
"id": "i-abc123",
|
2015-08-10 15:04:48 -05:00
|
|
|
"childid": "i-bcd234",
|
|
|
|
"grandchildid": "i-cde345",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
Dependencies: []string{
|
|
|
|
"module.child",
|
|
|
|
"module.child",
|
|
|
|
},
|
2018-06-01 14:36:55 -05:00
|
|
|
Provider: "provider.aws",
|
2015-08-10 15:04:48 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
&ModuleState{
|
|
|
|
Path: append(rootModulePath, "child"),
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.bar": &ResourceState{
|
2017-04-21 17:42:23 -05:00
|
|
|
Type: "aws_instance",
|
2015-08-10 15:04:48 -05:00
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "i-bcd234",
|
|
|
|
Attributes: map[string]string{
|
2018-09-07 16:45:51 -05:00
|
|
|
"id": "i-bcd234",
|
2015-08-10 15:04:48 -05:00
|
|
|
"grandchildid": "i-cde345",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
Dependencies: []string{
|
|
|
|
"module.grandchild",
|
|
|
|
},
|
2018-06-01 14:36:55 -05:00
|
|
|
Provider: "provider.aws",
|
2015-08-10 15:04:48 -05:00
|
|
|
},
|
|
|
|
},
|
2016-05-11 19:05:02 -05:00
|
|
|
Outputs: map[string]*OutputState{
|
|
|
|
"id": &OutputState{
|
|
|
|
Value: "i-bcd234",
|
|
|
|
Type: "string",
|
|
|
|
},
|
|
|
|
"grandchild_id": &OutputState{
|
|
|
|
Value: "i-cde345",
|
|
|
|
Type: "string",
|
|
|
|
},
|
2015-08-10 15:04:48 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
&ModuleState{
|
|
|
|
Path: append(rootModulePath, "child", "grandchild"),
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.baz": &ResourceState{
|
2017-04-21 17:42:23 -05:00
|
|
|
Type: "aws_instance",
|
2015-08-10 15:04:48 -05:00
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "i-cde345",
|
2018-09-07 16:45:51 -05:00
|
|
|
Attributes: map[string]string{
|
|
|
|
"id": "i-cde345",
|
|
|
|
},
|
2015-08-10 15:04:48 -05:00
|
|
|
},
|
2018-06-01 14:36:55 -05:00
|
|
|
Provider: "provider.aws",
|
2015-08-10 15:04:48 -05:00
|
|
|
},
|
|
|
|
},
|
2016-05-11 19:05:02 -05:00
|
|
|
Outputs: map[string]*OutputState{
|
|
|
|
"id": &OutputState{
|
|
|
|
Value: "i-cde345",
|
|
|
|
Type: "string",
|
|
|
|
},
|
2015-08-10 15:04:48 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2015-08-10 15:04:48 -05:00
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-08-10 15:04:48 -05:00
|
|
|
State: state,
|
|
|
|
})
|
|
|
|
|
|
|
|
testCheckDeadlock(t, func() {
|
|
|
|
_, err := ctx.Refresh()
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("err: %s", err)
|
|
|
|
}
|
|
|
|
|
|
|
|
// TODO: handle order properly for orphaned modules / resources
|
|
|
|
// expected := []string{"i-abc123", "i-bcd234", "i-cde345"}
|
|
|
|
// if !reflect.DeepEqual(order, expected) {
|
|
|
|
// t.Fatalf("expected: %#v, got: %#v", expected, order)
|
|
|
|
// }
|
|
|
|
})
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
func TestContext2Validate(t *testing.T) {
|
|
|
|
p := testProvider("aws")
|
2018-05-16 10:47:22 -05:00
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
Provider: &configschema.Block{},
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"aws_instance": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"foo": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
"num": {
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
2015-07-10 15:08:49 -05:00
|
|
|
m := testModule(t, "validate-good")
|
|
|
|
c := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-04-21 19:40:46 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
2015-07-10 15:08:49 -05:00
|
|
|
})
|
|
|
|
|
2017-11-21 17:08:00 -06:00
|
|
|
diags := c.Validate()
|
|
|
|
if len(diags) != 0 {
|
2018-05-11 16:52:29 -05:00
|
|
|
t.Fatalf("unexpected error: %#v", diags.ErrWithWarnings())
|
2015-07-10 15:08:49 -05:00
|
|
|
}
|
|
|
|
}
|
2017-06-25 00:41:12 -05:00
|
|
|
|
|
|
|
// TestContext2Refresh_noDiffHookOnScaleOut tests to make sure that
|
|
|
|
// pre/post-diff hooks are not called when running EvalDiff on scale-out nodes
|
|
|
|
// (nodes with no state). The effect here is to make sure that the diffs -
|
|
|
|
// which only exist for interpolation of parallel resources or data sources -
|
|
|
|
// do not end up being counted in the UI.
|
|
|
|
func TestContext2Refresh_noDiffHookOnScaleOut(t *testing.T) {
|
|
|
|
h := new(MockHook)
|
|
|
|
p := testProvider("aws")
|
|
|
|
m := testModule(t, "refresh-resource-scale-inout")
|
|
|
|
|
2018-09-06 17:08:47 -05:00
|
|
|
// Refresh creates a partial plan for any instances that don't have
|
|
|
|
// remote objects yet, to get stub values for interpolation. Therefore
|
|
|
|
// we need to make DiffFn available to let that complete.
|
|
|
|
p.DiffFn = testDiffFn
|
|
|
|
|
2018-10-15 20:07:01 -05:00
|
|
|
state := MustShimLegacyState(&State{
|
2017-06-25 00:41:12 -05:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.foo.0": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Deposed: []*InstanceState{
|
|
|
|
&InstanceState{
|
|
|
|
ID: "foo",
|
2018-09-07 16:45:51 -05:00
|
|
|
Attributes: map[string]string{
|
|
|
|
"id": "foo",
|
|
|
|
},
|
2017-06-25 00:41:12 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
"aws_instance.foo.1": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Deposed: []*InstanceState{
|
|
|
|
&InstanceState{
|
|
|
|
ID: "bar",
|
2018-09-07 16:45:51 -05:00
|
|
|
Attributes: map[string]string{
|
|
|
|
"id": "foo",
|
|
|
|
},
|
2017-06-25 00:41:12 -05:00
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2017-06-25 00:41:12 -05:00
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2017-06-25 00:41:12 -05:00
|
|
|
Hooks: []Hook{h},
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-06-25 00:41:12 -05:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: state,
|
|
|
|
})
|
|
|
|
|
2018-05-25 12:34:24 -05:00
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("refresh errors: %s", diags.Err())
|
2017-06-25 00:41:12 -05:00
|
|
|
}
|
|
|
|
if h.PreDiffCalled {
|
|
|
|
t.Fatal("PreDiff should not have been called")
|
|
|
|
}
|
|
|
|
if h.PostDiffCalled {
|
|
|
|
t.Fatal("PostDiff should not have been called")
|
|
|
|
}
|
|
|
|
}
|
2017-11-07 20:41:49 -06:00
|
|
|
|
|
|
|
func TestContext2Refresh_updateProviderInState(t *testing.T) {
|
|
|
|
m := testModule(t, "update-resource-provider")
|
|
|
|
p := testProvider("aws")
|
|
|
|
p.DiffFn = testDiffFn
|
|
|
|
p.ApplyFn = testApplyFn
|
|
|
|
|
2018-10-15 20:07:01 -05:00
|
|
|
s := MustShimLegacyState(&State{
|
2017-11-07 20:41:49 -06:00
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"aws_instance.bar": &ResourceState{
|
|
|
|
Type: "aws_instance",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "foo",
|
2018-09-07 16:45:51 -05:00
|
|
|
Attributes: map[string]string{
|
|
|
|
"id": "foo",
|
|
|
|
},
|
2017-11-07 20:41:49 -06:00
|
|
|
},
|
|
|
|
Provider: "provider.aws.baz",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
terraform: Ugly huge change to weave in new State and Plan types
Due to how often the state and plan types are referenced throughout
Terraform, there isn't a great way to switch them out gradually. As a
consequence, this huge commit gets us from the old world to a _compilable_
new world, but still has a large number of known test failures due to
key functionality being stubbed out.
The stubs here are for anything that interacts with providers, since we
now need to do the follow-up work to similarly replace the old
terraform.ResourceProvider interface with its replacement in the new
"providers" package. That work, along with work to fix the remaining
failing tests, will follow in subsequent commits.
The aim here was to replace all references to terraform.State and its
downstream types with states.State, terraform.Plan with plans.Plan,
state.State with statemgr.State, and switch to the new implementations of
the state and plan file formats. However, due to the number of times those
types are used, this also ended up affecting numerous other parts of core
such as terraform.Hook, the backend.Backend interface, and most of the CLI
commands.
Just as with 5861dbf3fc49b19587a31816eb06f511ab861bb4 before, I apologize
in advance to the person who inevitably just found this huge commit while
spelunking through the commit history.
2018-08-14 16:24:45 -05:00
|
|
|
})
|
2017-11-07 20:41:49 -06:00
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
2018-05-04 21:24:06 -05:00
|
|
|
Config: m,
|
2018-08-17 14:32:35 -05:00
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
2017-11-07 20:41:49 -06:00
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: s,
|
|
|
|
})
|
|
|
|
|
|
|
|
expected := strings.TrimSpace(`
|
|
|
|
aws_instance.bar:
|
|
|
|
ID = foo
|
|
|
|
provider = provider.aws.foo`)
|
|
|
|
|
2018-05-16 10:47:22 -05:00
|
|
|
state, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatal(diags.Err())
|
2017-11-07 20:41:49 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
actual := state.String()
|
|
|
|
if actual != expected {
|
|
|
|
t.Fatalf("expected:\n%s\n\ngot:\n%s", expected, actual)
|
|
|
|
}
|
|
|
|
}
|
2018-11-30 12:56:50 -06:00
|
|
|
|
|
|
|
func TestContext2Refresh_schemaUpgradeFlatmap(t *testing.T) {
|
|
|
|
m := testModule(t, "empty")
|
|
|
|
p := testProvider("test")
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"test_thing": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"name": { // imagining we renamed this from "id"
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
ResourceTypeSchemaVersions: map[string]uint64{
|
|
|
|
"test_thing": 5,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
p.UpgradeResourceStateResponse = providers.UpgradeResourceStateResponse{
|
|
|
|
UpgradedState: cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"name": cty.StringVal("foo"),
|
|
|
|
}),
|
|
|
|
}
|
|
|
|
|
|
|
|
s := states.BuildState(func(s *states.SyncState) {
|
|
|
|
s.SetResourceInstanceCurrent(
|
|
|
|
addrs.Resource{
|
|
|
|
Mode: addrs.ManagedResourceMode,
|
|
|
|
Type: "test_thing",
|
|
|
|
Name: "bar",
|
|
|
|
}.Instance(addrs.NoKey).Absolute(addrs.RootModuleInstance),
|
|
|
|
&states.ResourceInstanceObjectSrc{
|
|
|
|
Status: states.ObjectReady,
|
|
|
|
SchemaVersion: 3,
|
|
|
|
AttrsFlat: map[string]string{
|
|
|
|
"id": "foo",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
addrs.ProviderConfig{Type: "test"}.Absolute(addrs.RootModuleInstance),
|
|
|
|
)
|
|
|
|
})
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"test": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: s,
|
|
|
|
})
|
|
|
|
|
|
|
|
state, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatal(diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
{
|
|
|
|
got := p.UpgradeResourceStateRequest
|
|
|
|
want := providers.UpgradeResourceStateRequest{
|
|
|
|
TypeName: "test_thing",
|
|
|
|
Version: 3,
|
|
|
|
RawStateFlatmap: map[string]string{
|
|
|
|
"id": "foo",
|
|
|
|
},
|
|
|
|
}
|
|
|
|
if !cmp.Equal(got, want) {
|
|
|
|
t.Errorf("wrong upgrade request\n%s", cmp.Diff(want, got))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
{
|
|
|
|
got := state.String()
|
|
|
|
want := strings.TrimSpace(`
|
|
|
|
test_thing.bar:
|
|
|
|
ID =
|
|
|
|
provider = provider.test
|
|
|
|
name = foo
|
|
|
|
`)
|
|
|
|
if got != want {
|
|
|
|
t.Fatalf("wrong result state\ngot:\n%s\n\nwant:\n%s", got, want)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestContext2Refresh_schemaUpgradeJSON(t *testing.T) {
|
|
|
|
m := testModule(t, "empty")
|
|
|
|
p := testProvider("test")
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"test_thing": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"name": { // imagining we renamed this from "id"
|
|
|
|
Type: cty.String,
|
|
|
|
Optional: true,
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
ResourceTypeSchemaVersions: map[string]uint64{
|
|
|
|
"test_thing": 5,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
p.UpgradeResourceStateResponse = providers.UpgradeResourceStateResponse{
|
|
|
|
UpgradedState: cty.ObjectVal(map[string]cty.Value{
|
|
|
|
"name": cty.StringVal("foo"),
|
|
|
|
}),
|
|
|
|
}
|
|
|
|
|
|
|
|
s := states.BuildState(func(s *states.SyncState) {
|
|
|
|
s.SetResourceInstanceCurrent(
|
|
|
|
addrs.Resource{
|
|
|
|
Mode: addrs.ManagedResourceMode,
|
|
|
|
Type: "test_thing",
|
|
|
|
Name: "bar",
|
|
|
|
}.Instance(addrs.NoKey).Absolute(addrs.RootModuleInstance),
|
|
|
|
&states.ResourceInstanceObjectSrc{
|
|
|
|
Status: states.ObjectReady,
|
|
|
|
SchemaVersion: 3,
|
|
|
|
AttrsJSON: []byte(`{"id":"foo"}`),
|
|
|
|
},
|
|
|
|
addrs.ProviderConfig{Type: "test"}.Absolute(addrs.RootModuleInstance),
|
|
|
|
)
|
|
|
|
})
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"test": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: s,
|
|
|
|
})
|
|
|
|
|
|
|
|
state, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatal(diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
{
|
|
|
|
got := p.UpgradeResourceStateRequest
|
|
|
|
want := providers.UpgradeResourceStateRequest{
|
|
|
|
TypeName: "test_thing",
|
|
|
|
Version: 3,
|
|
|
|
RawStateJSON: []byte(`{"id":"foo"}`),
|
|
|
|
}
|
|
|
|
if !cmp.Equal(got, want) {
|
|
|
|
t.Errorf("wrong upgrade request\n%s", cmp.Diff(want, got))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
{
|
|
|
|
got := state.String()
|
|
|
|
want := strings.TrimSpace(`
|
|
|
|
test_thing.bar:
|
|
|
|
ID =
|
|
|
|
provider = provider.test
|
|
|
|
name = foo
|
|
|
|
`)
|
|
|
|
if got != want {
|
|
|
|
t.Fatalf("wrong result state\ngot:\n%s\n\nwant:\n%s", got, want)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2019-06-01 10:40:54 -05:00
|
|
|
|
|
|
|
func TestContext2Refresh_dataValidation(t *testing.T) {
|
|
|
|
m := testModuleInline(t, map[string]string{
|
|
|
|
"main.tf": `
|
|
|
|
data "aws_data_source" "foo" {
|
|
|
|
foo = "bar"
|
|
|
|
}
|
|
|
|
`,
|
|
|
|
})
|
|
|
|
|
|
|
|
p := testProvider("aws")
|
|
|
|
p.PlanResourceChangeFn = func(req providers.PlanResourceChangeRequest) (resp providers.PlanResourceChangeResponse) {
|
|
|
|
resp.PlannedState = req.ProposedNewState
|
|
|
|
return
|
|
|
|
}
|
|
|
|
p.ReadDataSourceFn = func(req providers.ReadDataSourceRequest) (resp providers.ReadDataSourceResponse) {
|
|
|
|
resp.State = req.Config
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
})
|
|
|
|
|
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
// Should get this error:
|
|
|
|
// Unsupported attribute: This object does not have an attribute named "missing"
|
|
|
|
t.Fatal(diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
if !p.ValidateDataSourceConfigCalled {
|
|
|
|
t.Fatal("ValidateDataSourceConfig not called during plan")
|
|
|
|
}
|
|
|
|
}
|
2019-09-24 16:09:29 -05:00
|
|
|
|
|
|
|
func TestContext2Refresh_dataResourceDependsOn(t *testing.T) {
|
|
|
|
m := testModule(t, "plan-data-depends-on")
|
|
|
|
p := testProvider("test")
|
|
|
|
p.GetSchemaReturn = &ProviderSchema{
|
|
|
|
ResourceTypes: map[string]*configschema.Block{
|
|
|
|
"test_resource": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"id": {Type: cty.String, Computed: true},
|
|
|
|
"foo": {Type: cty.String, Optional: true},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
DataSources: map[string]*configschema.Block{
|
|
|
|
"test_data": {
|
|
|
|
Attributes: map[string]*configschema.Attribute{
|
|
|
|
"compute": {Type: cty.String, Computed: true},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
}
|
|
|
|
p.DiffFn = testDiffFn
|
|
|
|
|
|
|
|
s := MustShimLegacyState(&State{
|
|
|
|
Modules: []*ModuleState{
|
|
|
|
&ModuleState{
|
|
|
|
Path: rootModulePath,
|
|
|
|
Resources: map[string]*ResourceState{
|
|
|
|
"test_resource.a": &ResourceState{
|
|
|
|
Type: "test_resource",
|
|
|
|
Provider: "provider.test",
|
|
|
|
Primary: &InstanceState{
|
|
|
|
ID: "a",
|
|
|
|
Attributes: map[string]string{
|
|
|
|
"id": "a",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"test": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: s,
|
|
|
|
})
|
|
|
|
|
|
|
|
_, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("unexpected errors: %s", diags.Err())
|
|
|
|
}
|
|
|
|
}
|
2019-10-17 15:05:27 -05:00
|
|
|
|
|
|
|
// verify that dependencies are updated in the state during refresh
|
|
|
|
func TestRefresh_updateDependencies(t *testing.T) {
|
|
|
|
state := states.NewState()
|
|
|
|
root := state.EnsureModule(addrs.RootModuleInstance)
|
|
|
|
root.SetResourceInstanceCurrent(
|
|
|
|
addrs.Resource{
|
|
|
|
Mode: addrs.ManagedResourceMode,
|
|
|
|
Type: "aws_instance",
|
|
|
|
Name: "foo",
|
|
|
|
}.Instance(addrs.NoKey),
|
|
|
|
&states.ResourceInstanceObjectSrc{
|
|
|
|
Status: states.ObjectReady,
|
|
|
|
AttrsJSON: []byte(`{"id":"foo"}`),
|
2019-11-15 15:00:13 -06:00
|
|
|
Dependencies: []addrs.AbsResource{
|
|
|
|
// Existing dependencies should not be removed during refresh
|
|
|
|
{
|
|
|
|
Module: addrs.RootModuleInstance,
|
|
|
|
Resource: addrs.Resource{
|
|
|
|
Mode: addrs.ManagedResourceMode,
|
|
|
|
Type: "aws_instance",
|
|
|
|
Name: "baz",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
},
|
2019-10-17 15:05:27 -05:00
|
|
|
},
|
|
|
|
addrs.ProviderConfig{
|
|
|
|
Type: "aws",
|
|
|
|
}.Absolute(addrs.RootModuleInstance),
|
|
|
|
)
|
|
|
|
root.SetResourceInstanceCurrent(
|
|
|
|
addrs.Resource{
|
|
|
|
Mode: addrs.ManagedResourceMode,
|
|
|
|
Type: "aws_instance",
|
|
|
|
Name: "bar",
|
|
|
|
}.Instance(addrs.NoKey),
|
|
|
|
&states.ResourceInstanceObjectSrc{
|
|
|
|
Status: states.ObjectReady,
|
|
|
|
AttrsJSON: []byte(`{"id":"bar","foo":"foo"}`),
|
|
|
|
},
|
|
|
|
addrs.ProviderConfig{
|
|
|
|
Type: "aws",
|
|
|
|
}.Absolute(addrs.RootModuleInstance),
|
|
|
|
)
|
|
|
|
|
|
|
|
m := testModuleInline(t, map[string]string{
|
|
|
|
"main.tf": `
|
|
|
|
resource "aws_instance" "bar" {
|
|
|
|
foo = aws_instance.foo.id
|
|
|
|
}
|
|
|
|
|
|
|
|
resource "aws_instance" "foo" {
|
|
|
|
}`,
|
|
|
|
})
|
|
|
|
|
|
|
|
p := testProvider("aws")
|
|
|
|
p.ApplyFn = testApplyFn
|
|
|
|
p.DiffFn = testDiffFn
|
|
|
|
|
|
|
|
ctx := testContext2(t, &ContextOpts{
|
|
|
|
Config: m,
|
|
|
|
ProviderResolver: providers.ResolverFixed(
|
|
|
|
map[string]providers.Factory{
|
|
|
|
"aws": testProviderFuncFixed(p),
|
|
|
|
},
|
|
|
|
),
|
|
|
|
State: state,
|
|
|
|
})
|
|
|
|
|
|
|
|
result, diags := ctx.Refresh()
|
|
|
|
if diags.HasErrors() {
|
|
|
|
t.Fatalf("plan errors: %s", diags.Err())
|
|
|
|
}
|
|
|
|
|
|
|
|
expect := strings.TrimSpace(`
|
|
|
|
aws_instance.bar:
|
|
|
|
ID = bar
|
|
|
|
provider = provider.aws
|
|
|
|
foo = foo
|
|
|
|
|
|
|
|
Dependencies:
|
|
|
|
aws_instance.foo
|
|
|
|
aws_instance.foo:
|
|
|
|
ID = foo
|
|
|
|
provider = provider.aws
|
2019-11-15 15:00:13 -06:00
|
|
|
|
|
|
|
Dependencies:
|
|
|
|
aws_instance.baz
|
2019-10-17 15:05:27 -05:00
|
|
|
`)
|
|
|
|
|
|
|
|
checkStateString(t, result, expect)
|
|
|
|
}
|