package hcltest

import (
	"fmt"

	"github.com/hashicorp/hcl/v2/hclsyntax"

	"github.com/hashicorp/hcl/v2"
	"github.com/zclconf/go-cty/cty"
)

// MockBody returns a hcl.Body implementation that works in terms of a
// caller-constructed hcl.BodyContent, thus avoiding the need to parse
// a "real" HCL config file to use as input to a test.
func MockBody(content *hcl.BodyContent) hcl.Body {
	return mockBody{content}
}

type mockBody struct {
	C *hcl.BodyContent
}

func (b mockBody) Content(schema *hcl.BodySchema) (*hcl.BodyContent, hcl.Diagnostics) {
	content, remainI, diags := b.PartialContent(schema)
	remain := remainI.(mockBody)
	for _, attr := range remain.C.Attributes {
		diags = append(diags, &hcl.Diagnostic{
			Severity: hcl.DiagError,
			Summary:  "Extraneous argument in mock body",
			Detail:   fmt.Sprintf("Mock body has extraneous argument %q.", attr.Name),
			Subject:  &attr.NameRange,
		})
	}
	for _, block := range remain.C.Blocks {
		diags = append(diags, &hcl.Diagnostic{
			Severity: hcl.DiagError,
			Summary:  "Extraneous block in mock body",
			Detail:   fmt.Sprintf("Mock body has extraneous block of type %q.", block.Type),
			Subject:  &block.DefRange,
		})
	}
	return content, diags
}

func (b mockBody) PartialContent(schema *hcl.BodySchema) (*hcl.BodyContent, hcl.Body, hcl.Diagnostics) {
	ret := &hcl.BodyContent{
		Attributes:       map[string]*hcl.Attribute{},
		Blocks:           []*hcl.Block{},
		MissingItemRange: b.C.MissingItemRange,
	}
	remain := &hcl.BodyContent{
		Attributes:       map[string]*hcl.Attribute{},
		Blocks:           []*hcl.Block{},
		MissingItemRange: b.C.MissingItemRange,
	}
	var diags hcl.Diagnostics

	if len(schema.Attributes) != 0 {
		for _, attrS := range schema.Attributes {
			name := attrS.Name
			attr, ok := b.C.Attributes[name]
			if !ok {
				if attrS.Required {
					diags = append(diags, &hcl.Diagnostic{
						Severity: hcl.DiagError,
						Summary:  "Missing required argument",
						Detail:   fmt.Sprintf("Mock body doesn't have argument %q", name),
						Subject:  b.C.MissingItemRange.Ptr(),
					})
				}
				continue
			}
			ret.Attributes[name] = attr
		}
	}

	for attrN, attr := range b.C.Attributes {
		if _, ok := ret.Attributes[attrN]; !ok {
			remain.Attributes[attrN] = attr
		}
	}

	wantedBlocks := map[string]hcl.BlockHeaderSchema{}
	for _, blockS := range schema.Blocks {
		wantedBlocks[blockS.Type] = blockS
	}

	for _, block := range b.C.Blocks {
		if blockS, ok := wantedBlocks[block.Type]; ok {
			if len(block.Labels) != len(blockS.LabelNames) {
				diags = append(diags, &hcl.Diagnostic{
					Severity: hcl.DiagError,
					Summary:  "Wrong number of block labels",
					Detail:   fmt.Sprintf("Block of type %q requires %d labels, but got %d", blockS.Type, len(blockS.LabelNames), len(block.Labels)),
					Subject:  b.C.MissingItemRange.Ptr(),
				})
			}

			ret.Blocks = append(ret.Blocks, block)
		} else {
			remain.Blocks = append(remain.Blocks, block)
		}
	}

	return ret, mockBody{remain}, diags
}

func (b mockBody) JustAttributes() (hcl.Attributes, hcl.Diagnostics) {
	var diags hcl.Diagnostics
	if len(b.C.Blocks) != 0 {
		diags = append(diags, &hcl.Diagnostic{
			Severity: hcl.DiagError,
			Summary:  "Mock body has blocks",
			Detail:   "Can't use JustAttributes on a mock body with blocks.",
			Subject:  b.C.MissingItemRange.Ptr(),
		})
	}

	return b.C.Attributes, diags
}

func (b mockBody) MissingItemRange() hcl.Range {
	return b.C.MissingItemRange
}

// MockExprLiteral returns a hcl.Expression that evaluates to the given literal
// value.
func MockExprLiteral(val cty.Value) hcl.Expression {
	return mockExprLiteral{val}
}

type mockExprLiteral struct {
	V cty.Value
}

func (e mockExprLiteral) Value(ctx *hcl.EvalContext) (cty.Value, hcl.Diagnostics) {
	return e.V, nil
}

func (e mockExprLiteral) Variables() []hcl.Traversal {
	return nil
}

func (e mockExprLiteral) Range() hcl.Range {
	return hcl.Range{
		Filename: "MockExprLiteral",
	}
}

func (e mockExprLiteral) StartRange() hcl.Range {
	return e.Range()
}

// Implementation for hcl.ExprList
func (e mockExprLiteral) ExprList() []hcl.Expression {
	v := e.V
	ty := v.Type()
	if v.IsKnown() && !v.IsNull() && (ty.IsListType() || ty.IsTupleType()) {
		ret := make([]hcl.Expression, 0, v.LengthInt())
		for it := v.ElementIterator(); it.Next(); {
			_, v := it.Element()
			ret = append(ret, MockExprLiteral(v))
		}
		return ret
	}
	return nil
}

// Implementation for hcl.ExprMap
func (e mockExprLiteral) ExprMap() []hcl.KeyValuePair {
	v := e.V
	ty := v.Type()
	if v.IsKnown() && !v.IsNull() && (ty.IsObjectType() || ty.IsMapType()) {
		ret := make([]hcl.KeyValuePair, 0, v.LengthInt())
		for it := v.ElementIterator(); it.Next(); {
			k, v := it.Element()
			ret = append(ret, hcl.KeyValuePair{
				Key:   MockExprLiteral(k),
				Value: MockExprLiteral(v),
			})
		}
		return ret
	}
	return nil
}

// MockExprVariable returns a hcl.Expression that evaluates to the value of
// the variable with the given name.
func MockExprVariable(name string) hcl.Expression {
	return mockExprVariable(name)
}

type mockExprVariable string

func (e mockExprVariable) Value(ctx *hcl.EvalContext) (cty.Value, hcl.Diagnostics) {
	name := string(e)
	for ctx != nil {
		if val, ok := ctx.Variables[name]; ok {
			return val, nil
		}
		ctx = ctx.Parent()
	}

	// If we fall out here then there is no variable with the given name
	return cty.DynamicVal, hcl.Diagnostics{
		{
			Severity: hcl.DiagError,
			Summary:  "Reference to undefined variable",
			Detail:   fmt.Sprintf("Variable %q is not defined.", name),
		},
	}
}

func (e mockExprVariable) Variables() []hcl.Traversal {
	return []hcl.Traversal{
		{
			hcl.TraverseRoot{
				Name:     string(e),
				SrcRange: e.Range(),
			},
		},
	}
}

func (e mockExprVariable) Range() hcl.Range {
	return hcl.Range{
		Filename: "MockExprVariable",
	}
}

func (e mockExprVariable) StartRange() hcl.Range {
	return e.Range()
}

// Implementation for hcl.AbsTraversalForExpr and hcl.RelTraversalForExpr.
func (e mockExprVariable) AsTraversal() hcl.Traversal {
	return hcl.Traversal{
		hcl.TraverseRoot{
			Name:     string(e),
			SrcRange: e.Range(),
		},
	}
}

// MockExprTraversal returns a hcl.Expression that evaluates the given
// absolute traversal.
func MockExprTraversal(traversal hcl.Traversal) hcl.Expression {
	return mockExprTraversal{
		Traversal: traversal,
	}
}

// MockExprTraversalSrc is like MockExprTraversal except it takes a
// traversal string as defined by the native syntax and parses it first.
//
// This method is primarily for testing with hard-coded traversal strings, so
// it will panic if the given string is not syntactically correct.
func MockExprTraversalSrc(src string) hcl.Expression {
	traversal, diags := hclsyntax.ParseTraversalAbs([]byte(src), "MockExprTraversal", hcl.Pos{})
	if diags.HasErrors() {
		panic("invalid traversal string")
	}
	return MockExprTraversal(traversal)
}

type mockExprTraversal struct {
	Traversal hcl.Traversal
}

func (e mockExprTraversal) Value(ctx *hcl.EvalContext) (cty.Value, hcl.Diagnostics) {
	return e.Traversal.TraverseAbs(ctx)
}

func (e mockExprTraversal) Variables() []hcl.Traversal {
	return []hcl.Traversal{e.Traversal}
}

func (e mockExprTraversal) Range() hcl.Range {
	return e.Traversal.SourceRange()
}

func (e mockExprTraversal) StartRange() hcl.Range {
	return e.Range()
}

// Implementation for hcl.AbsTraversalForExpr and hcl.RelTraversalForExpr.
func (e mockExprTraversal) AsTraversal() hcl.Traversal {
	return e.Traversal
}

func MockExprList(exprs []hcl.Expression) hcl.Expression {
	return mockExprList{
		Exprs: exprs,
	}
}

type mockExprList struct {
	Exprs []hcl.Expression
}

func (e mockExprList) Value(ctx *hcl.EvalContext) (cty.Value, hcl.Diagnostics) {
	if len(e.Exprs) == 0 {
		return cty.ListValEmpty(cty.DynamicPseudoType), nil
	}
	vals := make([]cty.Value, 0, len(e.Exprs))
	var diags hcl.Diagnostics

	for _, expr := range e.Exprs {
		val, valDiags := expr.Value(ctx)
		diags = append(diags, valDiags...)
		vals = append(vals, val)
	}

	return cty.ListVal(vals), diags
}

func (e mockExprList) Variables() []hcl.Traversal {
	var traversals []hcl.Traversal
	for _, expr := range e.Exprs {
		traversals = append(traversals, expr.Variables()...)
	}
	return traversals
}

func (e mockExprList) Range() hcl.Range {
	return hcl.Range{
		Filename: "MockExprList",
	}
}

func (e mockExprList) StartRange() hcl.Range {
	return e.Range()
}

// Implementation for hcl.ExprList
func (e mockExprList) ExprList() []hcl.Expression {
	return e.Exprs
}

// MockAttrs constructs and returns a hcl.Attributes map with attributes
// derived from the given expression map.
//
// Each entry in the map becomes an attribute whose name is the key and
// whose expression is the value.
func MockAttrs(exprs map[string]hcl.Expression) hcl.Attributes {
	ret := make(hcl.Attributes)
	for name, expr := range exprs {
		ret[name] = &hcl.Attribute{
			Name: name,
			Expr: expr,
			Range: hcl.Range{
				Filename: "MockAttrs",
			},
			NameRange: hcl.Range{
				Filename: "MockAttrs",
			},
		}
	}
	return ret
}
