terraform: validate almost done
This commit is contained in:
parent
012d68923c
commit
d9a964f44c
|
@ -0,0 +1,114 @@
|
||||||
|
package terraform
|
||||||
|
|
||||||
|
import (
|
||||||
|
"sync"
|
||||||
|
|
||||||
|
"github.com/hashicorp/terraform/config/module"
|
||||||
|
"github.com/hashicorp/terraform/dag"
|
||||||
|
)
|
||||||
|
|
||||||
|
// ContextOpts are the user-configurable options to create a context with
|
||||||
|
// NewContext.
|
||||||
|
type ContextOpts struct {
|
||||||
|
Diff *Diff
|
||||||
|
Hooks []Hook
|
||||||
|
Module *module.Tree
|
||||||
|
Parallelism int
|
||||||
|
State *State
|
||||||
|
Providers map[string]ResourceProviderFactory
|
||||||
|
Provisioners map[string]ResourceProvisionerFactory
|
||||||
|
Variables map[string]string
|
||||||
|
|
||||||
|
UIInput UIInput
|
||||||
|
}
|
||||||
|
|
||||||
|
// Context represents all the context that Terraform needs in order to
|
||||||
|
// perform operations on infrastructure. This structure is built using
|
||||||
|
// NewContext. See the documentation for that.
|
||||||
|
type Context2 struct {
|
||||||
|
module *module.Tree
|
||||||
|
providers map[string]ResourceProviderFactory
|
||||||
|
state *State
|
||||||
|
}
|
||||||
|
|
||||||
|
// NewContext creates a new Context structure.
|
||||||
|
//
|
||||||
|
// Once a Context is creator, the pointer values within ContextOpts
|
||||||
|
// should not be mutated in any way, since the pointers are copied, not
|
||||||
|
// the values themselves.
|
||||||
|
func NewContext2(opts *ContextOpts) *Context2 {
|
||||||
|
return &Context2{
|
||||||
|
module: opts.Module,
|
||||||
|
providers: opts.Providers,
|
||||||
|
state: opts.State,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// GraphBuilder returns the GraphBuilder that will be used to create
|
||||||
|
// the graphs for this context.
|
||||||
|
func (c *Context2) GraphBuilder() GraphBuilder {
|
||||||
|
// TODO test
|
||||||
|
providers := make([]string, 0, len(c.providers))
|
||||||
|
for k, _ := range c.providers {
|
||||||
|
providers = append(providers, k)
|
||||||
|
}
|
||||||
|
|
||||||
|
return &BuiltinGraphBuilder{
|
||||||
|
Root: c.module,
|
||||||
|
Providers: providers,
|
||||||
|
State: c.state,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Validate validates the configuration and returns any warnings or errors.
|
||||||
|
func (c *Context2) Validate() ([]string, []error) {
|
||||||
|
evalCtx := c.evalContext()
|
||||||
|
evalCtx.ComputeMissing = true
|
||||||
|
|
||||||
|
// Build the graph
|
||||||
|
graph, err := c.GraphBuilder().Build(RootModulePath)
|
||||||
|
if err != nil {
|
||||||
|
return nil, []error{err}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Valiate the graph
|
||||||
|
if err := graph.Validate(); err != nil {
|
||||||
|
return nil, []error{err}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Walk the graph
|
||||||
|
var warns []string
|
||||||
|
var errs []error
|
||||||
|
var lock sync.Mutex
|
||||||
|
graph.Walk(func(v dag.Vertex) {
|
||||||
|
ev, ok := v.(GraphNodeEvalable)
|
||||||
|
if !ok {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err := Eval(ev.EvalTree(), evalCtx)
|
||||||
|
if err == nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
lock.Lock()
|
||||||
|
defer lock.Unlock()
|
||||||
|
|
||||||
|
verr, ok := err.(*EvalValidateError)
|
||||||
|
if !ok {
|
||||||
|
errs = append(errs, err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
warns = append(warns, verr.Warnings...)
|
||||||
|
errs = append(errs, verr.Errors...)
|
||||||
|
})
|
||||||
|
|
||||||
|
return warns, errs
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *Context2) evalContext() *BuiltinEvalContext {
|
||||||
|
return &BuiltinEvalContext{
|
||||||
|
Providers: c.providers,
|
||||||
|
}
|
||||||
|
}
|
|
@ -44,21 +44,6 @@ type Context struct {
|
||||||
sh *stopHook
|
sh *stopHook
|
||||||
}
|
}
|
||||||
|
|
||||||
// ContextOpts are the user-creatable configuration structure to create
|
|
||||||
// a context with NewContext.
|
|
||||||
type ContextOpts struct {
|
|
||||||
Diff *Diff
|
|
||||||
Hooks []Hook
|
|
||||||
Module *module.Tree
|
|
||||||
Parallelism int
|
|
||||||
State *State
|
|
||||||
Providers map[string]ResourceProviderFactory
|
|
||||||
Provisioners map[string]ResourceProvisionerFactory
|
|
||||||
Variables map[string]string
|
|
||||||
|
|
||||||
UIInput UIInput
|
|
||||||
}
|
|
||||||
|
|
||||||
// InputMode defines what sort of input will be asked for when Input
|
// InputMode defines what sort of input will be asked for when Input
|
||||||
// is called on Context.
|
// is called on Context.
|
||||||
type InputMode byte
|
type InputMode byte
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,40 @@
|
||||||
|
package terraform
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"github.com/hashicorp/terraform/config"
|
||||||
|
)
|
||||||
|
|
||||||
|
// EvalValidateError is the error structure returned if there were
|
||||||
|
// validation errors.
|
||||||
|
type EvalValidateError struct {
|
||||||
|
Warnings []string
|
||||||
|
Errors []error
|
||||||
|
}
|
||||||
|
|
||||||
|
func (e *EvalValidateError) Error() string {
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
// EvalValidateResource is an EvalNode implementation that validates
|
||||||
|
// the configuration of a resource.
|
||||||
|
type EvalValidateResource struct {
|
||||||
|
Provider EvalNode
|
||||||
|
Config *config.RawConfig
|
||||||
|
}
|
||||||
|
|
||||||
|
func (n *EvalValidateResource) Args() ([]EvalNode, []EvalType) {
|
||||||
|
return []EvalNode{n.Provider},
|
||||||
|
[]EvalType{EvalTypeResourceProvider}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (n *EvalValidateResource) Eval(
|
||||||
|
ctx EvalContext, args []interface{}) (interface{}, error) {
|
||||||
|
//provider := args[0].(ResourceProvider)
|
||||||
|
return nil, fmt.Errorf("WHAT")
|
||||||
|
}
|
||||||
|
|
||||||
|
func (n *EvalValidateResource) Type() EvalType {
|
||||||
|
return EvalTypeNull
|
||||||
|
}
|
|
@ -119,6 +119,14 @@ func (n *GraphNodeConfigResource) Name() string {
|
||||||
return n.Resource.Id()
|
return n.Resource.Id()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GraphNodeEvalable impl.
|
||||||
|
func (n *GraphNodeConfigResource) EvalTree() EvalNode {
|
||||||
|
return &EvalValidateResource{
|
||||||
|
Provider: &EvalGetProvider{Name: n.ProvidedBy()},
|
||||||
|
Config: n.Resource.RawConfig,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// GraphNodeProviderConsumer
|
// GraphNodeProviderConsumer
|
||||||
func (n *GraphNodeConfigResource) ProvidedBy() string {
|
func (n *GraphNodeConfigResource) ProvidedBy() string {
|
||||||
return resourceProvider(n.Resource.Type)
|
return resourceProvider(n.Resource.Type)
|
||||||
|
|
Loading…
Reference in New Issue