// Copyright 2015 The Vanadium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package vdlgen

// TODO(toddw): Add tests

import (
	"fmt"
	"strconv"

	"v.io/v23/vdl"
	"v.io/x/ref/lib/vdl/codegen"
)

// TypedConst returns the explicitly-typed vdl const corresponding to v, in the
// given pkgPath, with the given imports.
func TypedConst(v *vdl.Value, pkgPath string, imports codegen.Imports) string {
	if v == nil {
		return "nil"
	}
	k, t := v.Kind(), v.Type()
	typestr := Type(t, pkgPath, imports)
	if k == vdl.Optional {
		// TODO(toddw): This only works if the optional elem is a composite literal.
		if elem := v.Elem(); elem != nil {
			return typestr + UntypedConst(elem, pkgPath, imports)
		}
		return typestr + "(nil)"
	}
	valstr := UntypedConst(v, pkgPath, imports)
	if k == vdl.TypeObject || t == vdl.BoolType || t == vdl.StringType {
		// TypeObject already includes the type in its value.
		// Built-in bool and string are implicitly convertible from literals.
		return valstr
	}
	switch k {
	case vdl.Array, vdl.List, vdl.Set, vdl.Map, vdl.Struct, vdl.Union:
		// { } are used instead of ( ) for composites, except for []byte and [N]byte
		if !t.IsBytes() {
			return typestr + valstr
		}
	case vdl.Enum:
		if t.Name() != "" {
			return typestr + "." + valstr
		}
		return valstr
	}
	return typestr + "(" + valstr + ")"
}

// UntypedConst returns the untyped vdl const corresponding to v, in the given
// pkgPath, with the given imports.
func UntypedConst(v *vdl.Value, pkgPath string, imports codegen.Imports) string {
	k, t := v.Kind(), v.Type()
	if t.IsBytes() {
		return strconv.Quote(string(v.Bytes()))
	}
	switch k {
	case vdl.Any:
		if elem := v.Elem(); elem != nil {
			return TypedConst(elem, pkgPath, imports)
		}
		return "nil"
	case vdl.Optional:
		if elem := v.Elem(); elem != nil {
			return UntypedConst(elem, pkgPath, imports)
		}
		return "nil"
	case vdl.Bool:
		return strconv.FormatBool(v.Bool())
	case vdl.Byte, vdl.Uint16, vdl.Uint32, vdl.Uint64:
		return strconv.FormatUint(v.Uint(), 10)
	case vdl.Int8, vdl.Int16, vdl.Int32, vdl.Int64:
		return strconv.FormatInt(v.Int(), 10)
	case vdl.Float32, vdl.Float64:
		return formatFloat(v.Float(), k)
	case vdl.String:
		return strconv.Quote(v.RawString())
	case vdl.Enum:
		return v.EnumLabel()
	case vdl.TypeObject:
		return "typeobject(" + Type(v.TypeObject(), pkgPath, imports) + ")"
	case vdl.Array, vdl.List:
		if v.IsZero() {
			return "{}"
		}
		s := "{"
		for ix := 0; ix < v.Len(); ix++ {
			if ix > 0 {
				s += ", "
			}
			s += UntypedConst(v.Index(ix), pkgPath, imports)
		}
		return s + "}"
	case vdl.Set, vdl.Map:
		s := "{"
		for ix, key := range vdl.SortValuesAsString(v.Keys()) {
			if ix > 0 {
				s += ", "
			}
			s += UntypedConst(key, pkgPath, imports)
			if k == vdl.Map {
				s += ": " + UntypedConst(v.MapIndex(key), pkgPath, imports)
			}
		}
		return s + "}"
	case vdl.Struct:
		s := "{"
		hasFields := false
		for ix := 0; ix < t.NumField(); ix++ {
			vf := v.StructField(ix)
			if vf.IsZero() {
				continue
			}
			if hasFields {
				s += ", "
			}
			s += t.Field(ix).Name + ": " + UntypedConst(vf, pkgPath, imports)
			hasFields = true
		}
		return s + "}"
	case vdl.Union:
		index, value := v.UnionField()
		return "{" + t.Field(index).Name + ": " + UntypedConst(value, pkgPath, imports) + "}"
	default:
		panic(fmt.Errorf("vdlgen.Const unhandled type: %v %v", k, t))
	}
}

func formatFloat(x float64, kind vdl.Kind) string {
	var bitSize int
	switch kind {
	case vdl.Float32:
		bitSize = 32
	case vdl.Float64:
		bitSize = 64
	default:
		panic(fmt.Errorf("formatFloat unhandled kind: %v", kind))
	}
	return strconv.FormatFloat(x, 'g', -1, bitSize)
}
