Commit Graph

60 Commits

Author SHA1 Message Date
James Bardin
7fa4c00d1a add validation for ignore_changes references
Ensure that ignore_changes only refers to arguments set in the
configuration.
2020-09-29 13:15:33 -04:00
Kristin Laemmert
67d441b131
terraform: refactor ProviderEvalTree (#26236)
* remove leftover debug line

* terraform: refactor ProviderEvalTree

This PR refactors the ProviderEvalTree by folding the entire tree into
straight-through code in NodeApplyableProvider Execute (formally
EvalTree). The EvalConfigProvider functions were refactored into
NodeApplyableProvider functions (since that was the only place they were
used).

I also removed the unused node_provider_disabled code.

* revert removal of graphNodeCloseProvider EvalTree, replace with Execute
2020-09-16 12:17:17 -04:00
Kristin Laemmert
7b510c4add
Mildwonkey/node resource validate (#26206)
* terraform: refactor signature of EvalContext.InitProvisioner

Nothing was using the returned provisioners.Interface, so I simplified
the signature.

* terraform: remove provisioner-related EvalTree()s

The various Evals in eval_provisioner were removed from all callers and
replaced with straight-through code.

`NodeValidatableResource.EvalTree()` to `Execute()` was more involved. I
chose to leave the `EvalValidateResource` and `EvalValidateProvisioner`
Eval functions mostly as-is, changing the main function to `.Validate` to
make it clear that these are no longer eval nodes. Eventually I expect
to rename the file (perhaps to just Validate).
2020-09-14 08:43:14 -04:00
James Bardin
a8884b18e3 split depends_on validation into its own function
Only resources were validating depends_on. We can use this same block to
ensure all depends_on validation has the same output.
2020-06-16 12:38:05 -04:00
James Bardin
b1bc7a792b rename and cleanup use of count/for_each eval func
Stop evaluating count and for each if they aren't set in the config.
Remove "Resource" from the function names, as they are also now used
with modules.
2020-04-08 17:21:23 -04:00
Paddy
e6592dc710
Add support for provider metadata to modules. (#22583)
Implement a new provider_meta block in the terraform block of modules, allowing provider-keyed metadata to be communicated from HCL to provider binaries.

Bundled in this change for minimal protocol version bumping is the addition of markdown support for attribute descriptions and the ability to indicate when an attribute is deprecated, so this information can be shown in the schema dump.

Co-authored-by: Paul Tyng <paul@paultyng.net>
2020-03-05 16:53:24 -08:00
Martin Atkins
8b511524d6
Initial steps towards AbsProviderConfig/LocalProviderConfig separation (#23978)
* Introduce "Local" terminology for non-absolute provider config addresses

In a future change AbsProviderConfig and LocalProviderConfig are going to
become two entirely distinct types, rather than Abs embedding Local as
written here. This naming change is in preparation for that subsequent
work, which will also include introducing a new "ProviderConfig" type
that is an interface that AbsProviderConfig and LocalProviderConfig both
implement.

This is intended to be largely just a naming change to get started, so
we can deal with all of the messy renaming. However, this did also require
a slight change in modeling where the Resource.DefaultProviderConfig
method has become Resource.DefaultProvider returning a Provider address
directly, because this method doesn't have enough information to construct
a true and accurate LocalProviderConfig -- it would need to refer to the
configuration to know what this module is calling the provider it has
selected.

In order to leave a trail to follow for subsequent work, all of the
changes here are intended to ensure that remaining work will become
obvious via compile-time errors when all of the following changes happen:
- The concept of "legacy" provider addresses is removed from the addrs
  package, including removing addrs.NewLegacyProvider and
  addrs.Provider.LegacyString.
- addrs.AbsProviderConfig stops having addrs.LocalProviderConfig embedded
  in it and has an addrs.Provider and a string alias directly instead.
- The provider-schema-handling parts of Terraform core are updated to
  work with addrs.Provider to identify providers, rather than legacy
  strings.

In particular, there are still several codepaths here making legacy
provider address assumptions (in order to limit the scope of this change)
but I've made sure each one is doing something that relies on at least
one of the above changes not having been made yet.

* addrs: ProviderConfig interface

In a (very) few special situations in the main "terraform" package we need
to make runtime decisions about whether a provider config is absolute
or local.

We currently do that by exploiting the fact that AbsProviderConfig has
LocalProviderConfig nested inside of it and so in the local case we can
just ignore the wrapping AbsProviderConfig and use the embedded value.

In a future change we'll be moving away from that embedding and making
these two types distinct in order to represent that mapping between them
requires consulting a lookup table in the configuration, and so here we
introduce a new interface type ProviderConfig that can represent either
AbsProviderConfig or LocalProviderConfig decided dynamically at runtime.

This also includes the Config.ResolveAbsProviderAddr method that will
eventually be responsible for that local-to-absolute translation, so
that callers with access to the configuration can normalize to an
addrs.AbsProviderConfig given a non-nil addrs.ProviderConfig. That's
currently unused because existing callers are still relying on the
simplistic structural transform, but we'll switch them over in a later
commit.

* rename LocalType to LocalName

Co-authored-by: Kristin Laemmert <mildwonkey@users.noreply.github.com>
2020-01-31 08:23:07 -05:00
Martin Atkins
39e609d5fd vendor: switch to HCL 2.0 in the HCL repository
Previously we were using the experimental HCL 2 repository, but now we'll
shift over to the v2 import path within the main HCL repository as part of
actually releasing HCL 2.0 as stable.

This is a mechanical search/replace to the new import paths. It also
switches to the v2.0.0 release of HCL, which includes some new code that
Terraform didn't previously have but should not change any behavior that
matters for Terraform's purposes.

For the moment the experimental HCL2 repository is still an indirect
dependency via terraform-config-inspect, so it remains in our go.sum and
vendor directories for the moment. Because terraform-config-inspect uses
a much smaller subset of the HCL2 functionality, this does still manage
to prune the vendor directory a little. A subsequent release of
terraform-config-inspect should allow us to completely remove that old
repository in a future commit.
2019-10-02 15:10:21 -07:00
Pam Selle
901ec990ed
Merge pull request #22156 from binlab/feature/bastion-ca-ssh
Add SSH certificate authentication method for connection via Bastion
2019-08-15 16:01:54 -04:00
Thayne McCombs
b9af3cd86b Support using self in the provisioner of resources that use for_each 2019-07-29 01:18:33 -06:00
Thayne McCombs
7c678d104f Add support for for_each for data blocks.
This also fixes a few things with resource for_each:

It makes validation more like validation for count.

It makes sure the index is stored in the state properly.
2019-07-25 16:59:06 -04:00
Pam Selle
7d905f6777 Resource for_each 2019-07-22 10:51:16 -04:00
Mark
3031aca971 Add SSH cert authentication method for connection via Bastion 2019-07-21 09:32:48 +03:00
tinocode
51a4055198 core: Fix panic on invalid depends_on root. (#21589)
Report an invalid reference to the user instead of crashing when there is in error traversing the `depends_on` attribute.

Fixes #21590
2019-06-06 08:43:22 -04:00
James Bardin
3c8b46fffe merge connection blocks for validation
The resource connection block was not being validated. Merge the two
bodies, with the provider as the override, before validation.
2019-03-26 11:59:23 -04:00
Martin Atkins
ac6e0e42dc configs/configupgrade: Upgrade the bodies of "connection" blocks
This uses the fixed "superset" schema from the main terraform package to
apply our standard expression mapping, with the exception of "type" where
interpolation sequences are not supported due to the type being evaluated
early to retrieve the schema for decoding the rest.
2019-02-22 12:32:56 -08:00
Sherod Taylor
c456d9608b updated ssh authentication and testing for ssh 2019-02-22 14:30:50 -05:00
James Bardin
8d17fcea4e make connection host Required
And provide the connection config for validation
2018-12-19 15:22:01 -05:00
Martin Atkins
2be524d6ac core: Validate depends_on and ignore_changes traversals
Both depends_on and ignore_changes contain references to objects that we
can validate.

Historically Terraform has not validated these, instead just ignoring
references to non-existent objects. Since there is no reason to refer to
something that doesn't exist, we'll now verify this and return errors so
that users get explicit feedback on any typos they may have made, rather
than just wondering why what they added seems to have no effect.

This is particularly important for ignore_changes because users have
historically used strange values here to try to exploit the fact that
Terraform was resolving ignore_changes against a flatmap. This will give
them explicit feedback for any odd constructs that the configuration
upgrade tool doesn't know how to detect and fix.
2018-12-17 09:02:25 -08:00
Martin Atkins
168d84b3c4 core: Make resource type schema versions visible to callers
Previously we were fetching these from the provider but then immediately
discarding the version numbers because the schema API had nowhere to put
them.

To avoid a late-breaking change to the internal structure of
terraform.ProviderSchema (which is constructed directly all over the
tests) we're retaining the resource type schemas in a new map alongside
the existing one with the same keys, rather than just switching to
using the providers.Schema struct directly there.

The methods that return resource type schemas now return two arguments,
intentionally creating a little API friction here so each new caller can
be reminded to think about whether they need to do something with the
schema version, though it can be ignored by many callers.

Since this was a breaking change to the Schemas API anyway, this also
fixes another API wart where there was a separate method for fetching
managed vs. data resource types and thus every caller ended up having a
switch statement on "mode". Now we just accept mode as an argument and
do the switch statement within the single SchemaForResourceType method.
2018-11-27 15:53:54 -08:00
James Bardin
155f899249 update terraform with PrepareProviderConfig
Change the call sites and update the MockProvider. No core behavior is
changed yet.
2018-10-18 08:48:55 -04:00
Martin Atkins
ed7e331041 terraform: Return validation diagnostics with source info where possible 2018-10-16 19:14:11 -07:00
James Bardin
08a8834882 ResourceProvisioner to provisioners.Interface
Replacing the core types, without touching tests yet.
2018-10-16 19:11:09 -07:00
James Bardin
16df9c37cf first step in core provider type replacement
Chaange ResourceProvider to providers.Interface starting from the
context, and fix all type errors.

This only replaced some of method calls directly applicable to the
providers themselves. The resource methods will follow.
2018-10-16 19:11:09 -07:00
Martin Atkins
479c6b2466 move "configschema" from "config" to "configs"
The "config" package is no longer used and will be removed as part
of the 0.12 release cleanup. Since configschema is part of the
"new world" of configuration modelling, it makes more sense for
it to live as a subdirectory of the newer "configs" package.
2018-10-16 18:50:29 -07:00
Martin Atkins
e4efe92e83 core: validate that depends_on addresses are for objects
Since the "References" function on graph nodes can't return errors, we
need to catch invalid depends_on references during the validation pass.

In this case, we're checking that the address is exact, rather than being
part of a traversal into an attribute of the object. In other words,
aws_instance.example is valid but aws_instance.example.id is not.
2018-10-16 18:50:29 -07:00
Martin Atkins
cf4a5e6336 core: Don't DynamicExpand during validate
Previously we would attempt to DynamicExpand during the validate walk and
then validate each expanded instance separately. However, this meant that
we would not be able to validate the contents of a block where count = 0
or if count is not yet known.

Here we instead do a more static validation pass against the resource
configuration itself, setting count.index to cty.UnknownVal(cty.Number) so
we can type-check everything inside the block as being correct regardless
of the final count.

This is another step towards repairing the "validate" command for our
changed assumptions in a world where we have a more sophisticated type
checker.

This doesn't yet address the remaining problem that the expression
evaluator can't, with the current state structures, distinguish between
a completed resource with count = 0 and a resource that doesn't exist
at all (during validate), and so we'll still get errors if an expression
elsewhere in configuration refers to a dynamic index of a resource with
"count" set. That's a pre-existing condition that's no longer being masked
by _this_ problem, but can't be addressed until we've introduced the new
state types (states.State, etc) and thus we _can_ distinguish these two
situations. That will therefore be addressed in a later commit.
2018-10-16 18:50:29 -07:00
Martin Atkins
fd371d838d core: Handle count.index evaluation more explicitly
Previously we had the evaluate methods accept directly an
addrs.InstanceKey and had our evaluator infer a suitable value for
count.index for it, but that prevents us from setting the index to be
unknown in the validation scenario where we may not be able to predict
the number of instances yet but we still want to be able to check that
the configuration block is type-safe for all possible count values.

To achieve this, we separate the concern of deciding on a value for
count.index from the concern of evaluating it, which then allows for
other implementations of this in future. For the purpose of this commit
there is no change in behavior, with the count.index value being populated
whenever the instance key is a number.

This commit does a little more groundwork for the future implementation
of the for_each feature (which'll support each.key and each.value) but
still doesn't yet implement it, leaving it just stubbed out for the
moment.
2018-10-16 18:50:29 -07:00
Martin Atkins
2002fee32e core: Context.Input as config walk, rather than graph walk
Now that core has access to the provider configuration schema, our input
logic can be implemented entirely within Context.Input, removing the need
to execute a full graph walk to gather input.

This commit replaces the graph walk call with instead just visiting the
provider configurations (explicit and implied) in the root module, using
the schema to prompt.

The code to manage the input graph walk is not yet removed by this commit,
and will be cleaned up in a subsequent commit once we've made sure there
aren't any other callers/tests depending on parts of it.
2018-10-16 18:49:20 -07:00
James Bardin
6a896c8748 fix the provisioner schema and update tests
The provisioenr schema needed to have `Optional: true` for all the
attributes. Also add the `type` attr and update the tests to match.
2018-10-16 18:49:20 -07:00
Martin Atkins
b8c3b8d45d core: Tolerate missing provider config schema in EvalValidateProvider
This should never happen in real code, but it comes up a lot in test code
where incomplete mock schemas are being used to test with very simple
configurations.
2018-10-16 18:48:28 -07:00
Martin Atkins
e4e3876332 core: EvalValidateProvider must always call provider.Validate
Previously we were skipping all of the validation steps if a provider was
being configured implicitly, and thus had no block in configuration.

This is incorrect, since a provider must still get an opportunity to
configure itself with an empty configuration and possibly reject that
empty configuration with errors.
2018-10-16 18:48:28 -07:00
Martin Atkins
509c6557dd core: Don't crash EvalValidateProvisioner if no connection block present 2018-10-16 18:48:28 -07:00
Martin Atkins
8d0bec5728 core: Don't include "type" in connection block schema
The config loader already extracts this during its initial pass and saves
it as a separate field in a configs.Connection value, so requiring it
again here causes confusing errors about this attribute being provided but
not set.
2018-10-16 18:48:28 -07:00
Martin Atkins
c82e3ec92f core: even more nil checks to catch missing objects
These are all things that ought to be present in normal use but can end up
being nil in incorrect tests. Test debugging is simpler if these things
return errors gracefully, rather than crashing.
2018-10-16 18:46:46 -07:00
Martin Atkins
7dacb6b6a8 core: Don't crash if EvaluateBlock returns nil during validation
There's actually no good reason for this to happen in the normal case, but
it can happen reasonably easy if a test doesn't properly configure the
MockEvalContext, and so having this check here makes test debugging a
little easier.
2018-10-16 18:46:46 -07:00
Martin Atkins
0dd7677d1f core: fail gracefully if provider schemas aren't available
The only reason these cases are arising right now is because we have tests
that haven't yet been updated to properly support schema, but it can't
hurt to add some robustness here to reduce the risk of real crashes.
2018-10-16 18:46:46 -07:00
Martin Atkins
d4cfe85361 core: pass InstanceKey to EvaluateBlock
This gives us the value we need to evaluate a "count.index" reference, and
later also the equivalent for the "for_each" argument once implemented.
2018-10-16 18:46:46 -07:00
Martin Atkins
c937c06a03 terraform: ugly huge change to weave in new HCL2-oriented types
Due to how deeply the configuration types go into Terraform Core, there
isn't a great way to switch out to HCL2 gradually. As a consequence, this
huge commit gets us from the old state to a _compilable_ new state, but
does not yet attempt to fix any tests and has a number of known missing
parts and bugs. We will continue to iterate on this in forthcoming
commits, heading back towards passing tests and making Terraform
fully-functional again.

The three main goals here are:
- Use the configuration models from the "configs" package instead of the
  older models in the "config" package, which is now deprecated and
  preserved only to help us write our migration tool.
- Do expression inspection and evaluation using the functionality of the
  new "lang" package, instead of the Interpolator type and related
  functionality in the main "terraform" package.
- Represent addresses of various objects using types in the addrs package,
  rather than hand-constructed strings. This is not critical to support
  the above, but was a big help during the implementation of these other
  points since it made it much more explicit what kind of address is
  expected in each context.

Since our new packages are built to accommodate some future planned
features that are not yet implemented (e.g. the "for_each" argument on
resources, "count"/"for_each" on modules), and since there's still a fair
amount of functionality still using old-style APIs, there is a moderate
amount of shimming here to connect new assumptions with old, hopefully in
a way that makes it easier to find and eliminate these shims later.

I apologize in advance to the person who inevitably just found this huge
commit while spelunking through the commit history.
2018-10-16 18:46:46 -07:00
Joe Khoobyar
852a74c49d first attempt at supporting NTLM authentication in Terraform 2018-03-30 21:11:53 -04:00
James Bardin
1a68fdb4f6 add support for ssh host key checking
Add `host_key` and `bastion_host_key` fields to the ssh communicator
config for strict host key checking.

Both fields expect the contents of an openssh formated public key. This
key can either be the remote host's public key, or the public key of the
CA which signed the remote host certificate.

Support for signed certificates is limited, because the provisioner
usually connects to a remote host by ip address rather than hostname, so
the certificate would need to be signed appropriately. Connecting via
a hostname needs to currently be done through a secondary provisioner,
like one attached to a null_resource.
2018-02-14 15:35:41 -05:00
James Bardin
35ce444851 add validation for the new connection field 2017-12-26 16:27:18 -05:00
Martin Atkins
0e963db2c5 Detect and reject unknown attributes in "connection" blocks
Since the validation of connection blocks is delegated to the communicator
selected by "type", we were not previously doing any validation of the
attribute names in these blocks until running provisioners during apply.

Proper validation here requires us to already have the instance state,
since the final connection info is a merge of values provided in config
with values assigned automatically by the resource. However, we can do
some basic name validation to catch typos during the validation pass, even
though semantic validation and checking for missing attributes will still
wait until the provisioner is instantiated.

This fixes #6582 as much as we reasonably can.
2017-04-06 13:46:43 -07:00
Mitchell Hashimoto
cf46e1c3e0
terraform: don't validate computed values in validate
This disables the computed value check for `count` during the validation
pass. This enables partial support for #3888 or #1497: as long as the
value is non-computed during the plan, complex values will work in
counts.

**Notably, this allows data source values to be present in counts!**

The "count" value can be disabled during validation safely because we
can treat it as if any field that uses `count.index` is computed for
validation. We then validate a single instance (as if `count = 1`) just
to make sure all required fields are set.
2017-01-27 21:15:43 -08:00
Paul Hinze
4a1b36ac0d
core: rerun resource validation before plan and apply
In #7170 we found two scenarios where the type checking done during the
`context.Validate()` graph walk was circumvented, and the subsequent
assumption of type safety in the provider's `Diff()` implementation
caused panics.

Both scenarios have to do with interpolations that reference Computed
values. The sentinel we use to indicate that a value is Computed does
not carry any type information with it yet.

That means that an incorrect reference to a list or a map in a string
attribute can "sneak through" validation only to crop up...

 1. ...during Plan for Data Source References
 2. ...during Apply for Resource references

In order to address this, we:

 * add high-level tests for each of these two scenarios in `provider/test`
 * add context-level tests for the same two scenarios in `terraform`
   (these tests proved _really_ tricky to write!)
 * place an `EvalValidateResource` just before `EvalDiff` and `EvalApply` to
   catch these errors
 * add some plumbing to `Plan()` and `Apply()` to return validation
   errors, which were previously only generated during `Validate()`
 * wrap unit-tests around `EvalValidateResource`
 * add an `IgnoreWarnings` option to `EvalValidateResource` to prevent
   active warnings from halting execution on the second-pass validation

Eventually, we might be able to attach type information to Computed
values, which would allow for these errors to be caught earlier. For
now, this solution keeps us safe from panics and raises the proper
errors to the user.

Fixes #7170
2016-07-01 13:12:57 -05:00
Martin Atkins
c1315b3f09 core: EvalValidate calls appropriate validator for resource mode
data resources are a separate namespace of resources than managed
resources, so we need to call a different provider method depending on
what mode of resource we're visiting.

Managed resources use ValidateResource, while data resources use
ValidateDataSource, since at the provider level of abstraction each
provider has separate sets of resources and data sources respectively.
2016-05-14 08:26:36 -07:00
Paul Hinze
5a9dad82d6 terraform: upgrade resource name regexp failure to error
We're well past Terraform 0.4, so it's time to finally make good on the
original promise. :)

Fixes #5243
2016-02-23 10:32:49 -06:00
Martin Atkins
8173cd25bb Demote some log lines to DEBUG.
Now that we support log line filtering (as of 0090c063) it's good to be
a bit more fussy about what log levels are assigned to different things.

Here we make a few things that are implementation details log as DEBUG,
and prevent spurious errors from EvalValidateCount where it was returning
an empty EvalValidateError rather than nil when everything was okay.
2015-10-11 10:45:33 -07:00
Mitchell Hashimoto
a0839da71a terraform: merge provider configs before validate [GH-1282] 2015-03-25 16:28:52 -07:00
Mitchell Hashimoto
b52881d232 terraform: clean up EvalNodes 2015-02-19 12:08:32 -08:00