| --- |
| page_title: Terraform v1.0 Compatibility Promises |
| description: |- |
| From Terraform v1.0 onwards the Terraform team promises to preserve backward |
| compatibility for most of the Terraform language and the primary CLI |
| workflow, until the next major release. |
| --- |
| |
| # Terraform v1.0 Compatibility Promises |
| |
| The release of Terraform v1.0 represents an important milestone in the |
| development of the Terraform language and workflow. Terraform v1.0 is a stable |
| platform for describing and managing infrastructure. |
| |
| In this release we're defining a number of Terraform behaviors that we intend |
| to remain compatible with throughout the 1.x releases: |
| |
| * A large subset of Terraform language features. |
| * A more conservative subset of the Terraform CLI workflow commands. |
| * The wire protocol for communication between Terraform Core and Terraform |
| providers. |
| * The wire protocols for installation of Terraform providers and external |
| Terraform modules. |
| |
| Our intention is that Terraform modules written for Terraform v1.0 will |
| continue to plan and apply successfully, without required changes, throughout |
| the v1.x releases. |
| |
| We also intend that automation built around the workflow subset described in |
| this document will work without changes in all future v1.x releases. |
| |
| Finally, we intend that providers built against the currently-documented |
| provider wire protocol will be compatible with all future Terraform v1.x |
| releases targeting the same operating system and architecture, without the |
| need for source code modification or binary recompilation. |
| |
| In short, we aim to make upgrades between v1.x releases straightforward, |
| requiring no changes to your configuration, no extra commands to run upgrade |
| steps, and no changes to any automation you've set up around Terraform. |
| |
| The Terraform v1.x series will be actively maintained for at least 18 months |
| after v1.0. |
| |
| The following sections include some specific guidance on what we will promise |
| throughout the v1.x series, for those who would like full details. At |
| a higher level though, we don't intend to make any changes that would cause |
| existing modules or automation to require changes when upgrading to a new |
| v1.x release. We will generally treat compatibility problems in new Terraform |
| CLI releases as bugs to be fixed unless there was a very significant |
| justification for the change, such as in addressing a critical security |
| problem or matching with a breaking change to a remote dependency that isn't |
| directly under our control. |
| |
| ## The Terraform Language |
| |
| The main Terraform Language includes the language syntax, the top-level |
| structures such as `resource`, `module`, and `provider` blocks, the |
| "meta-arguments" in those blocks, and the documented semantics and behaviors |
| for the operators and built-in functions available for use in expressions. |
| |
| There is not a single formal specification for the Terraform language, but the |
| Configuration section of the documentation on the Terraform website serves as a |
| description of the language features and their intended behaviors. |
| |
| The following top-level blocks and their defined "meta-arguments" (that is, |
| arguments defined by Terraform Core rather than by external plugins such as |
| providers) will retain their current functionality: |
| |
| * [`resource`](/language/resources) and |
| [`data`](/language/data-sources) blocks to |
| declare resources, including their nested block types `lifecycle`, |
| `connection`, and `provisioner`, and their meta-argument `provider`. |
| * [`module`](/language/modules/syntax) blocks to call other modules, |
| and its meta-argument `providers`. |
| * The [`count`](/language/meta-arguments/count), |
| [`for_each`](/language/meta-arguments/for_each), and |
| [`depends_on`](/language/meta-arguments/depends_on) meta-arguments |
| in `resource`, `data`, and `module` blocks. |
| * [`provider`](/language/providers/configuration) blocks to configure |
| providers, and the `alias` meta-argument. |
| * [`variable`](/language/values/variables#declaring-an-input-variable), |
| [`output`](/language/values/outputs#declaring-an-output-value), and |
| [`locals`](/language/values/locals#declaring-a-local-value) blocks |
| for declaring the various kinds of named values in a module. |
| * [`terraform`](/language/settings) blocks, including the nested |
| [`required_version`](/language/settings#specifying-a-required-terraform-version) |
| and |
| [`required_providers`](/language/providers/requirements#requiring-providers) |
| arguments, and nested |
| [`backend`](/language/settings/backends/configuration#using-a-backend-block) |
| blocks for backend configuration. |
| |
| We also intend to keep compatibility with all |
| [expression operators](/language/expressions) and |
| [built-in functions](/language/functions), with the exception of |
| references to |
| [`terraform.workspace`](/language/expressions/references#terraform-workspace), |
| whose behavior may change as part of future changes to the workspace model. |
| |
| We intend to retain broad compatibility with Terraform language features, with |
| a few specific caveats: |
| |
| * We consider a configuration to be valid if Terraform can create and apply |
| a plan for it without reporting any errors. |
| |
| A configuration that currently produces errors might generate different |
| errors or exhibit other non-error behaviors in a future version of |
| Terraform. A configuration that generates errors during the apply phase |
| might generate similar errors at an earlier phase in future, because |
| we generally consider it better to detect errors in as early a phase as |
| possible. |
| |
| Generally-speaking, the compatibility promises described in this document |
| apply only to valid configurations. Handling of invalid configurations is |
| always subject to change in future Terraform releases. |
| * If the actual behavior of a feature differs from what we explicitly |
| documented as the feature's behavior, we will usually treat that as a bug |
| and change the feature to match the documentation, although we will avoid |
| making such changes if they seem likely to cause broad compatibility problems. |
| We cannot promise to always remain "bug-compatible" with previous releases, |
| but we will consider such fixes carefully to minimize their impact. |
| * Any experimental features may change or may be removed entirely from future |
| releases. Terraform always produces a warning when an experimental language |
| feature is active, to make you aware of that risk. We don't recommend using |
| experimental features in production modules. |
| * We will introduce new language features, and if you start using them then |
| your configuration won't work with prior Terraform versions that didn't |
| support those features yet. |
| * Terraform Providers are separate plugins which can change independently of |
| Terraform Core and are therefore not subject to these compatibility promises. |
| If you upgrade any of the providers you are using then you might need to |
| change provider or resource configurations related to those providers. |
| * A small number of features remain deprecated with explicit warnings in |
| Terraform v1.0. Those deprecation cycles will end in a future v1.x release, |
| at which point we will remove the corresponding features. |
| |
| ## Workflow |
| |
| There is a set of often used Terraform workflows, which we are calling |
| _protected workflows_. We will not remove these commands, subcommands, and |
| flags or make backward-incompatible changes to protected workflow |
| functionality. If we accidentally change these, we will consider |
| backwards-incompatible changes to core workflows as bugs to be fixed. For a |
| list of the command and option combinations that are part of protected |
| workflows, see [Protected Workflow Commands](#protected-workflow-commands). |
| There is another set of commands that we are explicitly _not_ making |
| compatibility promises about, because we expect their functionality to change |
| in v1.x releases: see [Commands That Might Change](#commands-that-might-change). |
| |
| The supported ways for external software to interact with Terraform are via |
| the JSON output modes offered by some commands and via exit status codes. |
| We may extend certain JSON formats with new object properties but we will not |
| remove or make breaking changes to the definitions of existing properties. |
| |
| Natural language command output or log output is not a stable interface and |
| may change in any new version. If you write software that parses this output |
| then it may need to be updated when you upgrade Terraform. If you need access |
| to data that is not currently available via one of the machine-readable JSON |
| interfaces, we suggest opening a feature request to discuss your use-case. |
| |
| ## Upgrading and Downgrading |
| |
| Throughout the v1.x series of releases, we intend that you should be able to |
| switch to a newer Terraform version and use it just as before, without any |
| special upgrade steps. |
| |
| You should be able to upgrade from any v1.x release to any later v1.x release. |
| You might also be able to downgrade to an earlier v1.x release, but that isn't |
| guaranteed: later releases may introduce new features that earlier versions |
| cannot understand, including new storage formats for Terraform state snapshots. |
| |
| If you make use of features introduced in a later v1.x release, your |
| configuration won't be compatible with releases that predate that feature. |
| For example, if a language feature is added in v1.3 and you start using it, your |
| Terraform configuration will no longer be compatible with Terraform v1.2. |
| |
| ## Providers |
| |
| Terraform providers are separate plugins which communicate with Terraform using |
| a documented protocol. Therefore these compatibility promises can only cover |
| the "client" side of this protocol as implemented by Terraform Core; the |
| behaviors of individual providers, including which resource types they support |
| and which arguments they expect, are decided by the provider development teams |
| and can change independently of Terraform Core releases. |
| |
| If you upgrade to a new version of a provider then you might need to change |
| the parts of your configuration which are interpreted by that provider, even |
| if you are still using a Terraform v1.x release. |
| |
| ### Provider Installation Methods |
| |
| Terraform normally installs providers from a provider registry implementing |
| [the Provider Registry Protocol](/internals/provider-registry-protocol), |
| version 1. All Terraform v1.x releases will remain compatible with that |
| protocol, and so correctly-implemented provider registries will stay compatible. |
| |
| Terraform also supports installation of providers from |
| [local filesystem directories](/cli/config/config-file#filesystem_mirror) |
| (filesystem mirrors) and from |
| [network mirrors](/cli/config/config-file#network_mirror) |
| (implementing [the Provider Mirror Protocol](/internals/provider-network-mirror-protocol). |
| All Terraform v1.x releases will remain compatible with those installation |
| methods, including |
| [the Implied Local Mirror Directories](/cli/config/config-file#implied-local-mirror-directories). |
| |
| Specific provider registries or network mirrors are run independently from |
| Terraform itself and so their own behaviors are not subject to these |
| compatibility promises. |
| |
| ### Provider Protocol Versions |
| |
| The current major version of the provider plugin protocol as of Terraform v1.0 |
| is version 5, which is defined by a combination of a Protocol Buffers schema |
| describing the physical wire formats and by additional prose documentation |
| describing the expected provider behaviors. |
| |
| We will support protocol version 5 throughout the Terraform v1.x releases. If |
| we make new minor revisions to protocol version 5 in later releases then we |
| will design them such that existing plugins will continue to work, as long as |
| they correctly implemented the protocol. |
| |
| We may introduce new major versions of the protocol during the v1.x series. If |
| so, we will continue to support protocol version 5 alongside those new versions. |
| Individual provider teams might decide to remove support for protocol version 5 |
| in later releases, in which case those new provider releases will not be |
| compatible with all of the Terraform v1.x releases. |
| |
| ## External Modules |
| |
| Terraform modules are reusable infrastructure components written in the |
| Terraform language. Some modules are "external" in the sense that Terraform |
| automatically installs them from a location other than the current |
| configuration directory, in which case their contents could change |
| independently of changes to your local modules, of the providers you use, |
| and of Terraform itself. |
| |
| ### Module Installation Methods |
| |
| Terraform supports installing child modules from a number of different |
| [module source types](/language/modules/sources). We will continue |
| to support all of the existing source types throughout the v1.x releases. |
| |
| One of the supported source types is a module registry implementing |
| [the Module Registry Protocol](/internals/module-registry-protocol) |
| version 1. All Terraform v1.x releases will remain compatible with correct |
| implementations of that protocol. |
| |
| Some module source types work directly with services or protocols defined and |
| run by third parties. Although we will not remove Terraform's own client-side |
| support for those, we cannot guarantee that their owners will keep those |
| services running or that they will remain compatible with Terraform's client |
| implementations. |
| |
| ### External Module Compatibility |
| |
| If your configuration depends on external modules, newer versions of those |
| modules may include breaking changes. External modules are not part of |
| Terraform and are therefore not subject to these compatibility promises. |
| |
| ## Provisioners |
| |
| We will maintain compatibility for the `file`, `local-exec`, and `remote-exec` |
| provisioner types through all v1.x releases. |
| |
| Some additional vendor-specific provisioners were available in earlier |
| Terraform versions but were deprecated in Terraform v0.13 and removed in |
| Terraform v0.15. |
| |
| Terraform supports loading additional provisioners as plugins from certain |
| local filesystem directories. We'll continue to support that throughout the |
| Terraform v1.x releases, but since such plugins are separate from Terraform |
| Core itself their own behaviors cannot be subject to these compatibility |
| promises. However, we will continue to support the plugin wire protocol as |
| defined in Terraform v1.0 throughout the v1.x releases, and so |
| correctly-implemented provisioner plugins should remain compatible with future |
| Terraform releases. |
| |
| ## State Storage Backends |
| |
| When you use _remote state_, Terraform interacts with remote services over |
| the network in order to store and manage locks for Terraform state. |
| |
| For historical reasons, all supported state storage backends are included as |
| part of Terraform CLI but not all are supported directly by the Terraform |
| Team. Only the following backends maintained by the Terraform team are subject |
| to compatibility promises: |
| |
| * `local` (the default, when you are not using remote state) |
| * `http` |
| |
| The other state storage backends are maintained by external teams via |
| contributions to the Terraform CLI codebase, and so their expected |
| configuration arguments or behaviors might change even in v1.x releases, |
| although we will aim to still ensure a good migration path in such cases, |
| where possible. |
| |
| We are considering allowing external state storage backend implementations |
| via plugins, similar to provider plugins. If we introduce such a mechanism |
| during the v1.x releases then you may need to make configuration changes in |
| order to use those plugins, and state storage backends other than those |
| listed above may be removed from later versions of Terraform CLI once |
| equivalent plugins are available. |
| |
| ### The `remote` Backend and Terraform Cloud |
| |
| The `remote` backend is maintained by the Terraform Cloud team and so its |
| behavior may change along with ongoing changes to Terraform Cloud. |
| |
| There will be a supported mechanism to use Terraform CLI with Terraform Cloud |
| throughout the v1.x releases, but the exact details may change. Terraform Cloud |
| evolves independently of Terraform CLI and is therefore not subject to these |
| compatibility promises. |
| |
| ## Community-maintained State Storage Backends |
| |
| The `azurerm`, `consul`, `s3`, and `kubernetes` backends are maintained by |
| other teams at HashiCorp. Those teams intend to continue basic maintenence at |
| the level of bug fixes through the v1.x releases, unless we implement a plugin |
| protocol for backends at which point development of these backends is likely |
| to continue in the external plugins only, which may require configuration |
| changes to switch to the plugin equivalents. |
| |
| The `cos`, `oss`, `pg`, `gcs`, and `etcdv3` backends are maintained by outside |
| contributors and are not subject to these compatibility promises. |
| |
| ### Unmaintained State Storage Backends |
| |
| The `artifactory`, `etcdv2`, `manta`, and `swift` state storage backends do not |
| currently have any maintainers and thus remain in Terraform CLI releases on |
| a best-effort basis. They may be removed in later v1.x releases, and will not |
| be updated in case of any breaking changes to the services they integrate with. |
| |
| ## Supported Platforms |
| |
| Throughout the v1.x series we will continue to produce official releases for |
| the following platforms, and make changes as necessary to support new |
| releases of these operating systems: |
| |
| * macOS on x64 CPUs (`darwin_amd64`) |
| * Windows on x64 CPUs (`windows_amd64`) |
| * Linux on x64, 32-bit ARMv6, and 64-bit ARMv8 (`linux_amd64`, `linux_arm`, and `linux_arm64` respectively) |
| |
| Over time we may require newer versions of these operating systems. For |
| example, subsequent Terraform releases in the v1.x series might end support |
| for earlier versions of macOS or Windows, or earlier Linux kernel releases. |
| |
| We have historically produced official releases for a number of other platforms |
| as a convenience to users of those platforms, and we have no current plans to |
| stop publishing them but we cannot promise ongoing releases or bug fixes for |
| the other platforms throughout the v1.x series. We do not routinely test |
| Terraform on any platforms other than those listed above. |
| |
| We might add support for new platforms in later v1.x releases. If so, earlier |
| Terraform releases prior to that support will not be available on those |
| platforms. |
| |
| All Terraform plugins, including provider plugins, are separate programs that |
| have their own policies for which platforms they support. We cannot guarantee |
| that all providers currently support or will continue to support the platforms |
| listed above, even though Terraform CLI itself will support them. |
| |
| ## Later Revisions to These Promises |
| |
| We may extend or refine these promises throughout the v1.x series in order to |
| describe promises related to new features or to clarify existing promises if |
| we find via feedback that our earlier statements had been unclear. |
| |
| Promises for new features will be additive in the sense that they will add |
| further promises without retracting any existing ones. For promises that only |
| apply to later v1.x releases we will mention the earliest version(s) those |
| promises apply to. |
| |
| Even if we don't add an explicit statement to this document, we intend that |
| any non-experimental features added in later v1.x releases will remain |
| compatible at least through the remainder of the v1.x series, unless otherwise |
| stated. |
| |
| ## Appendices |
| |
| ### Protected Workflow Commands |
| |
| The following is the list of Terraform CLI subcommands and options that are |
| subject to these compatibility promises. If you build automation around |
| these commands then it should be compatible with all later v1.x releases. |
| |
| As noted above, compatibility with external software is limited to |
| explicitly-machine-readable output (`-json` and `-raw` modes) and exit codes. |
| Any natural-language output from these commands might change in later releases. |
| |
| * [`init`](/cli/commands/init) |
| * `-backend=false` |
| * `-backend-config=FILE` |
| * `-backend-config="KEY=VALUE"` |
| * `-force-copy` |
| * `-get=false` |
| * `-input=false` |
| * `-migrate-state` |
| * `-no-color` |
| * `-plugin-dir=DIR` |
| * `-reconfigure` |
| * `-upgrade` |
| * [`validate`](/cli/commands/validate) |
| * `-json` |
| * `-no-color` |
| * [`plan`](/cli/commands/plan) |
| * `-compact-warnings` |
| * `-destroy` |
| * `-detailed-exitcode` |
| * `-lock=false` |
| * `-lock-timeout=DURATION` |
| * `-input=false` |
| * `-json` |
| * `-no-color` |
| * `-out=FILE` |
| * `-parallelism=N` |
| * `-refresh=false` |
| * `-refresh-only` |
| * `-replace=ADDRESS` |
| * `-target=ADDRESS` |
| * `-var 'NAME=VALUE'` |
| * `-var-file=FILE` |
| * [`apply`](/cli/commands/apply) |
| * `-auto-approve` |
| * `-compact-warnings` |
| * `-lock=false` |
| * `-lock-timeout=DURATION` |
| * `-input=false` |
| * `-json` |
| * `-no-color` |
| * `-parallelism=N` |
| * `-refresh=false` |
| * `-refresh-only` |
| * `-replace=ADDRESS` |
| * `-target=ADDRESS` |
| * `-var 'NAME=VALUE'` |
| * `-var-file=FILE` |
| * [`show`](/cli/commands/show) |
| * `-no-color` |
| * `-json` |
| * (both with and without a plan file) |
| * [`providers`](/cli/commands/providers) (with no subcommand) |
| * [`providers lock`](/cli/commands/providers/lock) |
| * `-fs-mirror=PATH` |
| * `-net-mirror=URL` |
| * `-platform=OS_ARCH` |
| * [`providers mirror`](/cli/commands/providers/mirror) |
| * `-platform=OS_ARCH` |
| * [`providers schema`](/cli/commands/providers/schema) |
| * `-json` |
| * [`fmt`](/cli/commands/fmt) |
| * `-list=false` |
| * `-write=false` |
| * `-diff` |
| * `-recursive` |
| * `-check` |
| * [`version`](/cli/commands/version) |
| * `-json` |
| * [`output`](/cli/commands/output) |
| * `-no-color` |
| * `-json` |
| * `-raw` |
| * [`taint`](/cli/commands/taint) |
| * `-allow-missing` |
| * `-lock=false` |
| * `-lock-timeout=DURATION` |
| * `-ignore-remote-version` |
| * [`untaint`](/cli/commands/untaint) |
| * `-allow-missing` |
| * `-lock=false` |
| * `-lock-timeout=DURATION` |
| * `-ignore-remote-version` |
| * [`force-unlock`](/cli/commands/force-unlock) |
| * `-force` |
| * [`state list`](/cli/commands/state/list) |
| * `-id=ID` |
| * [`state pull`](/cli/commands/state/pull) |
| * [`state push`](/cli/commands/state/push) |
| * `-force` |
| * `-lock=false` |
| * `-lock-timeout=DURATION` |
| * [`state show`](/cli/commands/state/show) |
| * `-ignore-remote-version` |
| * [`login`](/cli/commands/login) |
| |
| For commands or options not in the above list, we will still avoid breaking |
| changes where possible, but can't promise full compatibility throughout the |
| v1.x series. If you are building automation around Terraform, use only the |
| commands above to avoid the need for changes when upgrading. |
| |
| Please note that although Terraform's internal logs (via the `TF_LOG` |
| environment variable) are available in a JSON format, the particular syntax |
| or structure of those log lines is _not_ a supported integration interface. |
| The logs are available as JSON only to help with ad-hoc filtering and |
| processing of logs by Terraform developers. |
| |
| ### Commands That Might Change |
| |
| All of the following commands and their subcommands/options are _not_ subject |
| to compatibility promises, either because we have existing plans to improve |
| them during the v1.x series or because we are aware of shortcomings in their |
| design that might require breaking changes for ongoing maintenence. |
| |
| While you can freely use these commands when running Terraform interactively |
| as long as they remain supported, we don't recommend using them as part of |
| any automation unless you are willing to potentially update that automation |
| when upgrading to a later v1.x release. |
| |
| * `destroy` (consider `terraform apply -destroy` instead) |
| * `console` |
| * `get` (consider `terraform init` instead) |
| * `graph` |
| * `import` |
| * `push` |
| * `refresh` (consider `terraform apply -refresh-only` instead) |
| * `state mv` |
| * `state replace-provider` |
| * `state rm` |
| * all subcommands of `workspace` (and its deprecated alias `env`) |
| |
| While we do intend to retain support for the main use-cases associated with |
| these commands in future releases, we cannot promise to retain the exact |
| command names or options used to meet those use-cases. |
| |
| ## How We Will Keep These Promises |
| |
| ### Automated Regression Testing |
| |
| The Terraform codebase includes various unit and integration tests intended to |
| help us to notice accidental behavior regressions before they ship in a stable |
| version. |
| |
| However, Terraform is a relatively complex system with many different features |
| that can interact in interesting ways. In the past we've seen reports of |
| behavior differences that appeared only when combining two or more features in |
| a way we hadn't previously anticipated or written automated tests for. |
| |
| In each case we have both implemented a change to resolve the compatibility |
| problem _and_ added one or more integration tests representing the behavior |
| of that combination of features. We intend to continue this approach, so we can |
| improve Terraform's test coverage over time. |
| |
| ### Prerelease Versions |
| |
| We intend that most accidental changes in behavior covered by these promises |
| will be caught by existing tests. However, we also accept that our test suite |
| can never have perfect coverage of all possible feature interactions or other |
| edge cases, and so we aim for each significant change to be included in both |
| alpha and beta releases before eventual inclusion in a final release. |
| |
| For minor releases we will typically also issue at least one release candidate |
| prior to the final release. A release candidate represents that planned |
| development is concluded and that we've fixed any regressions reported based |
| on the alpha and beta releases, and thus the final release that follows should |
| typically match exactly or almost exactly its most recent release candidate. |
| |
| ### Regressions in Final Releases |
| |
| For more obscure combinations of features it is possible that a regression |
| could be undetected during prerelease the prerelease periods and thus included |
| in a final release. |
| |
| If someone finds and reports such a regression soon after its release then we |
| will treat it as a bug and fix it to restore the previous behavior in future |
| releases, unless there is a very significant justification such as a security |
| advisory. In these cases, we'll typically recommend anyone affected by the |
| regression remain on the previous version until the problem is fixed and then |
| skip forward directly to the new release containing that fix. |
| |
| You can minimize the risk of being affected by missed regressions in final |
| releases by proactively testing modules against alpha, beta, and release |
| candidate packages. We recommend doing so only in isolated development or |
| staging environments rather than against your production infrastructure. If you |
| find a change in behavior in a prerelease build that seems contrary to the |
| promises in this document, please open an issue in Terraform's GitHub |
| repository to discuss it. |
| |
| ### Late-reported Regressions |
| |
| In the most extreme case, there may be a regression with a combination of |
| features that is so rare that it remains undetected for a long time. |
| |
| After a change has been included in more releases it becomes increasingly |
| likely that other users will have depended on the newer behavior and thus we |
| will need to make a tradeoff to decide whether restoring the behavior would |
| have a greater negative impact than retaining the new behavior. We will always |
| make this decision with due consideration to the implications of each unique |
| situation. |
| |
| You can minimize the risk of your modules being affected by late-reported |
| regressions by upgrading promptly to new minor and patch releases of Terraform |
| and reporting any compatibility problems you encounter in Terraform's GitHub |
| repository. |
| |
| ### Pragmatic Exceptions |
| |
| We are making the promises above in good faith, with the intent that your |
| investment in writing Terraform modules or automation will not be invalidated |
| by future changes to Terraform. However, broad promises like the above can't |
| possibly cover all nuances of practical problems that might arise as we |
| continue to develop Terraform. |
| |
| For that reason, there are some situations where we may still need to make |
| changes that may impact existing modules or automation: |
| |
| * Security problems: We may become aware of a design problem that has an |
| important security impact. Depending on our determination of the associated |
| risk, we may choose to break compatibility to achieve a more secure system. |
| * External Dependencies: Terraform's behavior depends on interfaces provided |
| by external codebases, including your chosen operating system and including |
| some remote network services for situations such as module and provider |
| installation. These external systems can change outside of our control, |
| including potentially removing or changing features that Terraform's own |
| features depend on. In that case, if there is no suitable replacement |
| mechanism then we may need to change Terraform's design to work within the |
| new constraints. |
| * Opt-in Compatibility Breaks: The design of a language new feature may require |
| changing the behavior or configuration representation of an existing feature. |
| If so, we will typically make the new feature opt-in only in order to avoid |
| breaking existing modules, but if you change your module to opt in to the |
| new feature then you may also then be required to change other parts of your |
| configuration to work with the new language design. |
| * Bugs in New Features: If we introduce a new feature to Terraform and the |
| initial implementation has problems that cause it to not match the documented |
| design intent at release, we may make a follow-up release that corrects |
| the implementation to match the documented design, even if that represents |
| a minor compatibility regression compared to the initial implementation. |
| However, once a feature is well-established and in common use we will usually |
| defer to the implemented behavior and instead change the documentation to |
| reflect it. |
| * Regressions in Existing Features: If we learn that a new Terraform release |
| includes a regression for an existing feature that wasn't detected during |
| the development and prerelease periods, and that learning comes promptly |
| after the new release, we will typically restore the previous behavior at |
| the expense of technically therefore breaking compatibility with the behavior |
| of the new release, under the assumption that more users will have systems |
| affected by the regression than will have systems depending on the |
| newly-introduced behavior. |
| * Late-reported regressions: As described in the previous section, if we |
| learn that there was an unintentional regression of a rarely-used feature or |
| combination of features in a much earlier release then restoring the previous |
| behavior may appear as a regression to later adopters. If we believe that |
| fixing the regression would affect more users than the regression itself |
| affects then we may choose to accept the regression as the new promised |
| behavior. |
| * Situations we cannot anticipate: Although we've made an effort to consider |
| various specific exceptional situations here, Terraform and its development |
| process are not isolated from broader context, and so we must consider that |
| there may be situations that we cannot possibly anticipate that would affect |
| the future of Terraform. In those situations, we will always do our best to |
| find a course of action that will minimize as much as possible the impact to |
| existing modules and automation. |
| |
| Our intent with these pragmatic exceptions is only to acknowledge that there |
| will always be situations that general compatibility promises cannot address. |
| We will use these exceptions only with due consideration and as a last resort. |