diff --git a/command/jsonplan/plan.go b/command/jsonplan/plan.go index 93980fbac..f1563abef 100644 --- a/command/jsonplan/plan.go +++ b/command/jsonplan/plan.go @@ -91,12 +91,7 @@ func Marshal( p *plans.Plan, sf *statefile.File, schemas *terraform.Schemas, - stateSchemas *terraform.Schemas, ) ([]byte, error) { - if stateSchemas == nil { - stateSchemas = schemas - } - output := newPlan() output.TerraformVersion = version.String() @@ -125,7 +120,7 @@ func Marshal( // output.PriorState if sf != nil && !sf.State.Empty() { - output.PriorState, err = jsonstate.Marshal(sf, stateSchemas) + output.PriorState, err = jsonstate.Marshal(sf, schemas) if err != nil { return nil, fmt.Errorf("error marshaling prior state: %s", err) } diff --git a/command/show.go b/command/show.go index 54224aaec..d72f97782 100644 --- a/command/show.go +++ b/command/show.go @@ -115,7 +115,7 @@ func (c *ShowCommand) Run(args []string) int { // if that fails, try to read the cli argument as a path to a statefile if len(args) > 0 { path := args[0] - plan, planErr = getPlanFromPath(path) + plan, stateFile, planErr = getPlanFromPath(path) if planErr != nil { stateFile, stateErr = getStateFromPath(path) if stateErr != nil { @@ -129,9 +129,7 @@ func (c *ShowCommand) Run(args []string) int { return 1 } } - } - - if stateFile == nil { + } else { env := c.Workspace() stateFile, stateErr = getStateFromEnv(b, env) if err != nil { @@ -143,29 +141,7 @@ func (c *ShowCommand) Run(args []string) int { if plan != nil { if jsonOutput == true { config := ctx.Config() - - var err error - var jsonPlan []byte - - // If there is no prior state, we have all the schemas needed. - if stateFile == nil { - jsonPlan, err = jsonplan.Marshal(config, plan, stateFile, schemas, nil) - } else { - // If there is state, we need the state-specific schemas, which - // may differ from the schemas loaded from the plan. - // This occurs if there is a data_source in the state that was - // removed from the configuration, because terraform core does - // not need to load the schema to remove a data source. - opReq.PlanFile = nil - ctx, _, ctxDiags := local.Context(opReq) - diags = diags.Append(ctxDiags) - if ctxDiags.HasErrors() { - c.showDiagnostics(diags) - return 1 - } - stateSchemas := ctx.Schemas() - jsonPlan, err = jsonplan.Marshal(config, plan, stateFile, schemas, stateSchemas) - } + jsonPlan, err := jsonplan.Marshal(config, plan, stateFile, schemas) if err != nil { c.Ui.Error(fmt.Sprintf("Failed to marshal plan to json: %s", err)) @@ -224,19 +200,21 @@ func (c *ShowCommand) Synopsis() string { return "Inspect Terraform state or plan" } -// getPlanFromPath returns a plan if the user-supplied path points to a planfile. -// If both plan and error are nil, the path is likely a directory. -// An error could suggest that the given path points to a statefile. -func getPlanFromPath(path string) (*plans.Plan, error) { +// getPlanFromPath returns a plan and statefile if the user-supplied path points +// to a planfile. If both plan and error are nil, the path is likely a +// directory. An error could suggest that the given path points to a statefile. +func getPlanFromPath(path string) (*plans.Plan, *statefile.File, error) { pr, err := planfile.Open(path) if err != nil { - return nil, err + return nil, nil, err } plan, err := pr.ReadPlan() if err != nil { - return nil, err + return nil, nil, err } - return plan, nil + + stateFile, err := pr.ReadStateFile() + return plan, stateFile, nil } // getStateFromPath returns a statefile if the user-supplied path points to a statefile. diff --git a/command/show_test.go b/command/show_test.go index 9fca88b00..530385b36 100644 --- a/command/show_test.go +++ b/command/show_test.go @@ -412,6 +412,11 @@ type plan struct { PlannedValues map[string]interface{} `json:"planned_values,omitempty"` ResourceChanges []interface{} `json:"resource_changes,omitempty"` OutputChanges map[string]interface{} `json:"output_changes,omitempty"` - PriorState map[string]interface{} `json:"prior_state,omitempty"` + PriorState priorState `json:"prior_state,omitempty"` Config map[string]interface{} `json:"configuration,omitempty"` } + +type priorState struct { + FormatVersion string `json:"format_version,omitempty"` + Values map[string]interface{} `json:"values,omitempty"` +} diff --git a/command/test-fixtures/show-json/basic-create/output.json b/command/test-fixtures/show-json/basic-create/output.json index da8afad4d..8c4295f83 100644 --- a/command/test-fixtures/show-json/basic-create/output.json +++ b/command/test-fixtures/show-json/basic-create/output.json @@ -53,6 +53,18 @@ ] } }, + "prior_state": { + "format_version": "0.1", + "values": { + "outputs": { + "test": { + "sensitive": false, + "value": "bar" + } + }, + "root_module": {} + } + }, "resource_changes": [ { "address": "test_instance.test[0]", diff --git a/command/test-fixtures/show-json/basic-delete/output.json b/command/test-fixtures/show-json/basic-delete/output.json index 874e2d86d..5c9d9e8c6 100644 --- a/command/test-fixtures/show-json/basic-delete/output.json +++ b/command/test-fixtures/show-json/basic-delete/output.json @@ -82,8 +82,13 @@ }, "prior_state": { "format_version": "0.1", - "terraform_version": "0.12.0", "values": { + "outputs": { + "test": { + "sensitive": false, + "value": "bar" + } + }, "root_module": { "resources": [ { diff --git a/command/test-fixtures/show-json/basic-update/output.json b/command/test-fixtures/show-json/basic-update/output.json index 5f46ecc10..a7b69cad1 100644 --- a/command/test-fixtures/show-json/basic-update/output.json +++ b/command/test-fixtures/show-json/basic-update/output.json @@ -64,8 +64,13 @@ }, "prior_state": { "format_version": "0.1", - "terraform_version": "0.12.0", "values": { + "outputs": { + "test": { + "sensitive": false, + "value": "bar" + } + }, "root_module": { "resources": [ { diff --git a/command/test-fixtures/show-json/modules/output.json b/command/test-fixtures/show-json/modules/output.json index ab38acc7e..be1b6fdf9 100644 --- a/command/test-fixtures/show-json/modules/output.json +++ b/command/test-fixtures/show-json/modules/output.json @@ -69,6 +69,18 @@ ] } }, + "prior_state": { + "format_version": "0.1", + "values": { + "outputs": { + "test": { + "sensitive": false, + "value": "baz" + } + }, + "root_module": {} + } + }, "resource_changes": [ { "address": "module.module_test_bar.test_instance.test",