func StateValueToJSONMap(val cty.Value, ty cty.Type) (map[string]interface{}, error) {
	js, err := ctyjson.Marshal(val, ty)
	if err != nil {
		return nil, err
	}
	var m map[string]interface{}
	if err := json.Unmarshal(js, &m); err != nil {
		return nil, err
	}
	return m, nil
}
StateValueToJSONMap converts a cty.Value to generic JSON map via the cty JSON
encoding.
package schema
import (
	"encoding/json"
	"github.com/zclconf/go-cty/cty"
	ctyjson "github.com/zclconf/go-cty/cty/json"
	"github.com/hashicorp/terraform/configs/configschema"
	"github.com/hashicorp/terraform/configs/hcl2shim"
	"github.com/hashicorp/terraform/terraform"
)
func DiffFromValues(prior, planned cty.Value, res *Resource) (*terraform.InstanceDiff, error) {
	return diffFromValues(prior, planned, res, nil)
}
func diffFromValues(prior, planned cty.Value, res *Resource, cust CustomizeDiffFunc) (*terraform.InstanceDiff, error) {
	instanceState, err := res.ShimInstanceStateFromValue(prior)
	if err != nil {
		return nil, err
	}
	configSchema := res.CoreConfigSchema()
	cfg := terraform.NewResourceConfigShimmed(planned, configSchema)
	removeConfigUnknowns(cfg.Config)
	removeConfigUnknowns(cfg.Raw)
	diff, err := schemaMap(res.Schema).Diff(instanceState, cfg, cust, nil, false)
	if err != nil {
		return nil, err
	}
	return diff, err
}
func removeConfigUnknowns(cfg map[string]interface{}) {
	for k, v := range cfg {
		switch v := v.(type) {
		case string:
			if v == hcl2shim.UnknownVariableValue {
				delete(cfg, k)
			}
		case []interface{}:
			for _, i := range v {
				if m, ok := i.(map[string]interface{}); ok {
					removeConfigUnknowns(m)
				}
			}
		case map[string]interface{}:
			removeConfigUnknowns(v)
		}
	}
}
func ApplyDiff(base cty.Value, d *terraform.InstanceDiff, schema *configschema.Block) (cty.Value, error) {
	return d.ApplyToValue(base, schema)
}