package terraform

import (
	"fmt"

	"github.com/zclconf/go-cty/cty"

	"github.com/hashicorp/terraform/internal/configs"
	"github.com/hashicorp/terraform/internal/tfdiags"
)

// InputValue represents a raw value for a root module input variable as
// provided by the external caller into a function like terraform.Context.Plan.
//
// InputValue should represent as directly as possible what the user set the
// variable to, without any attempt to convert the value to the variable's
// type constraint or substitute the configured default values for variables
// that wasn't set. Those adjustments will be handled by Terraform Core itself
// as part of performing the requested operation.
//
// A Terraform Core caller must provide an InputValue object for each of the
// variables declared in the root module, even if the end user didn't provide
// an explicit value for some of them. See the Value field documentation for
// how to handle that situation.
//
// Terraform Core also internally uses InputValue to represent the raw value
// provided for a variable in a child module call, following the same
// conventions. However, that's an implementation detail not visible to
// outside callers.
type InputValue struct {
	// Value is the raw value as provided by the user as part of the plan
	// options, or a corresponding similar data structure for non-plan
	// operations.
	//
	// If a particular variable declared in the root module is _not_ set by
	// the user then the caller must still provide an InputValue for it but
	// must set Value to cty.NilVal to represent the absense of a value.
	// This requirement is to help detect situations where the caller isn't
	// correctly detecting and handling all of the declared variables.
	//
	// For historical reasons it's important that callers distinguish the
	// situation of the value not being set at all (cty.NilVal) from the
	// situation of it being explicitly set to null (a cty.NullVal result):
	// for "nullable" input variables that distinction unfortunately decides
	// whether the final value will be the variable's default or will be
	// explicitly null.
	Value cty.Value

	// SourceType is a high-level category for where the value of Value
	// came from, which Terraform Core uses to tailor some of its error
	// messages to be more helpful to the user.
	//
	// Some SourceType values should be accompanied by a populated SourceRange
	// value. See that field's documentation below for more information.
	SourceType ValueSourceType

	// SourceRange provides source location information for values whose
	// SourceType is either ValueFromConfig, ValueFromNamedFile, or
	// ValueForNormalFile. It is not populated for other source types, and so
	// should not be used.
	SourceRange tfdiags.SourceRange
}

// ValueSourceType describes what broad category of source location provided
// a particular value.
type ValueSourceType rune

const (
	// ValueFromUnknown is the zero value of ValueSourceType and is not valid.
	ValueFromUnknown ValueSourceType = 0

	// ValueFromConfig indicates that a value came from a .tf or .tf.json file,
	// e.g. the default value defined for a variable.
	ValueFromConfig ValueSourceType = 'C'

	// ValueFromAutoFile indicates that a value came from a "values file", like
	// a .tfvars file, that was implicitly loaded by naming convention.
	ValueFromAutoFile ValueSourceType = 'F'

	// ValueFromNamedFile indicates that a value came from a named "values file",
	// like a .tfvars file, that was passed explicitly on the command line (e.g.
	// -var-file=foo.tfvars).
	ValueFromNamedFile ValueSourceType = 'N'

	// ValueFromCLIArg indicates that the value was provided directly in
	// a CLI argument. The name of this argument is not recorded and so it must
	// be inferred from context.
	ValueFromCLIArg ValueSourceType = 'A'

	// ValueFromEnvVar indicates that the value was provided via an environment
	// variable. The name of the variable is not recorded and so it must be
	// inferred from context.
	ValueFromEnvVar ValueSourceType = 'E'

	// ValueFromInput indicates that the value was provided at an interactive
	// input prompt.
	ValueFromInput ValueSourceType = 'I'

	// ValueFromPlan indicates that the value was retrieved from a stored plan.
	ValueFromPlan ValueSourceType = 'P'

	// ValueFromCaller indicates that the value was explicitly overridden by
	// a caller to Context.SetVariable after the context was constructed.
	ValueFromCaller ValueSourceType = 'S'
)

func (v *InputValue) GoString() string {
	if (v.SourceRange != tfdiags.SourceRange{}) {
		return fmt.Sprintf("&terraform.InputValue{Value: %#v, SourceType: %#v, SourceRange: %#v}", v.Value, v.SourceType, v.SourceRange)
	} else {
		return fmt.Sprintf("&terraform.InputValue{Value: %#v, SourceType: %#v}", v.Value, v.SourceType)
	}
}

// HasSourceRange returns true if the reciever has a source type for which
// we expect the SourceRange field to be populated with a valid range.
func (v *InputValue) HasSourceRange() bool {
	return v.SourceType.HasSourceRange()
}

// HasSourceRange returns true if the reciever is one of the source types
// that is used along with a valid SourceRange field when appearing inside an
// InputValue object.
func (v ValueSourceType) HasSourceRange() bool {
	switch v {
	case ValueFromConfig, ValueFromAutoFile, ValueFromNamedFile:
		return true
	default:
		return false
	}
}

func (v ValueSourceType) GoString() string {
	return fmt.Sprintf("terraform.%s", v)
}

//go:generate go run golang.org/x/tools/cmd/stringer -type ValueSourceType

// InputValues is a map of InputValue instances.
type InputValues map[string]*InputValue

// InputValuesFromCaller turns the given map of naked values into an
// InputValues that attributes each value to "a caller", using the source
// type ValueFromCaller. This is primarily useful for testing purposes.
//
// This should not be used as a general way to convert map[string]cty.Value
// into InputValues, since in most real cases we want to set a suitable
// other SourceType and possibly SourceRange value.
func InputValuesFromCaller(vals map[string]cty.Value) InputValues {
	ret := make(InputValues, len(vals))
	for k, v := range vals {
		ret[k] = &InputValue{
			Value:      v,
			SourceType: ValueFromCaller,
		}
	}
	return ret
}

// Override merges the given value maps with the receiver, overriding any
// conflicting keys so that the latest definition wins.
func (vv InputValues) Override(others ...InputValues) InputValues {
	// FIXME: This should check to see if any of the values are maps and
	// merge them if so, in order to preserve the behavior from prior to
	// Terraform 0.12.
	ret := make(InputValues)
	for k, v := range vv {
		ret[k] = v
	}
	for _, other := range others {
		for k, v := range other {
			ret[k] = v
		}
	}
	return ret
}

// JustValues returns a map that just includes the values, discarding the
// source information.
func (vv InputValues) JustValues() map[string]cty.Value {
	ret := make(map[string]cty.Value, len(vv))
	for k, v := range vv {
		ret[k] = v.Value
	}
	return ret
}

// SameValues returns true if the given InputValues has the same values as
// the receiever, disregarding the source types and source ranges.
//
// Values are compared using the cty "RawEquals" method, which means that
// unknown values can be considered equal to one another if they are of the
// same type.
func (vv InputValues) SameValues(other InputValues) bool {
	if len(vv) != len(other) {
		return false
	}

	for k, v := range vv {
		ov, exists := other[k]
		if !exists {
			return false
		}
		if !v.Value.RawEquals(ov.Value) {
			return false
		}
	}

	return true
}

// HasValues returns true if the reciever has the same values as in the given
// map, disregarding the source types and source ranges.
//
// Values are compared using the cty "RawEquals" method, which means that
// unknown values can be considered equal to one another if they are of the
// same type.
func (vv InputValues) HasValues(vals map[string]cty.Value) bool {
	if len(vv) != len(vals) {
		return false
	}

	for k, v := range vv {
		oVal, exists := vals[k]
		if !exists {
			return false
		}
		if !v.Value.RawEquals(oVal) {
			return false
		}
	}

	return true
}

// Identical returns true if the given InputValues has the same values,
// source types, and source ranges as the receiver.
//
// Values are compared using the cty "RawEquals" method, which means that
// unknown values can be considered equal to one another if they are of the
// same type.
//
// This method is primarily for testing. For most practical purposes, it's
// better to use SameValues or HasValues.
func (vv InputValues) Identical(other InputValues) bool {
	if len(vv) != len(other) {
		return false
	}

	for k, v := range vv {
		ov, exists := other[k]
		if !exists {
			return false
		}
		if !v.Value.RawEquals(ov.Value) {
			return false
		}
		if v.SourceType != ov.SourceType {
			return false
		}
		if v.SourceRange != ov.SourceRange {
			return false
		}
	}

	return true
}

// checkInputVariables ensures that the caller provided an InputValue
// definition for each root module variable declared in the configuration.
// The caller must provide an InputVariables with keys exactly matching
// the declared variables, though some of them may be marked explicitly
// unset by their values being cty.NilVal.
//
// This doesn't perform any type checking, default value substitution, or
// validation checks. Those are all handled during a graph walk when we
// visit the graph nodes representing each root variable.
//
// The set of values is considered valid only if the returned diagnostics
// does not contain errors. A valid set of values may still produce warnings,
// which should be returned to the user.
func checkInputVariables(vcs map[string]*configs.Variable, vs InputValues) tfdiags.Diagnostics {
	var diags tfdiags.Diagnostics

	for name := range vcs {
		_, isSet := vs[name]
		if !isSet {
			// Always an error, since the caller should have produced an
			// item with Value: cty.NilVal to be explicit that it offered
			// an opportunity to set this variable.
			diags = diags.Append(tfdiags.Sourceless(
				tfdiags.Error,
				"Unassigned variable",
				fmt.Sprintf("The input variable %q has not been assigned a value. This is a bug in Terraform; please report it in a GitHub issue.", name),
			))
			continue
		}
	}

	// Check for any variables that are assigned without being configured.
	// This is always an implementation error in the caller, because we
	// expect undefined variables to be caught during context construction
	// where there is better context to report it well.
	for name := range vs {
		if _, defined := vcs[name]; !defined {
			diags = diags.Append(tfdiags.Sourceless(
				tfdiags.Error,
				"Value assigned to undeclared variable",
				fmt.Sprintf("A value was assigned to an undeclared input variable %q.", name),
			))
		}
	}

	return diags
}
