command/init: Support -plugin-dir again
This is a slightly different approach than we used to take for this option: rather than disabling the installer and causing all future commands to look elsewhere for plugins, we'll now leave the installer enabled by constrain it to only look at the given directories. This is overall simpler because it doesn't require any special tracking of the plugin directories for subsequent commands. Instead, the selections file generated by the installer will record the versions it selected from the specified directories, and we'll link them in to the local cache just as we would normally so that other commands don't need to do anything special to select the right plugins in either case.
This commit is contained in:
parent
f7072a8f29
commit
c4fb22863c
|
@ -291,7 +291,7 @@ func (c *InitCommand) Run(args []string) int {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Now that we have loaded all modules, check the module tree for missing providers.
|
// Now that we have loaded all modules, check the module tree for missing providers.
|
||||||
providersOutput, providerDiags := c.getProviders(earlyConfig, state, flagUpgrade)
|
providersOutput, providerDiags := c.getProviders(earlyConfig, state, flagUpgrade, flagPluginPath)
|
||||||
diags = diags.Append(providerDiags)
|
diags = diags.Append(providerDiags)
|
||||||
if providerDiags.HasErrors() {
|
if providerDiags.HasErrors() {
|
||||||
c.showDiagnostics(diags)
|
c.showDiagnostics(diags)
|
||||||
|
@ -422,7 +422,7 @@ the backend configuration is present and valid.
|
||||||
|
|
||||||
// Load the complete module tree, and fetch any missing providers.
|
// Load the complete module tree, and fetch any missing providers.
|
||||||
// This method outputs its own Ui.
|
// This method outputs its own Ui.
|
||||||
func (c *InitCommand) getProviders(earlyConfig *earlyconfig.Config, state *states.State, upgrade bool) (output bool, diags tfdiags.Diagnostics) {
|
func (c *InitCommand) getProviders(earlyConfig *earlyconfig.Config, state *states.State, upgrade bool, pluginDirs []string) (output bool, diags tfdiags.Diagnostics) {
|
||||||
// First we'll collect all the provider dependencies we can see in the
|
// First we'll collect all the provider dependencies we can see in the
|
||||||
// configuration and the state.
|
// configuration and the state.
|
||||||
reqs, moreDiags := earlyConfig.ProviderRequirements()
|
reqs, moreDiags := earlyConfig.ProviderRequirements()
|
||||||
|
@ -435,11 +435,19 @@ func (c *InitCommand) getProviders(earlyConfig *earlyconfig.Config, state *state
|
||||||
reqs = reqs.Merge(stateReqs)
|
reqs = reqs.Merge(stateReqs)
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: If the user gave at least one -plugin-dir option on the command
|
var inst *providercache.Installer
|
||||||
// line, we should construct a one-off getproviders.Source that consults
|
if len(pluginDirs) == 0 {
|
||||||
// only those directories and pass that to c.providerInstallerCustomSource
|
// By default we use a source that looks for providers in all of the
|
||||||
// instead.
|
// standard locations, possibly customized by the user in CLI config.
|
||||||
inst := c.providerInstaller()
|
inst = c.providerInstaller()
|
||||||
|
} else {
|
||||||
|
// If the user passes at least one -plugin-dir then that circumvents
|
||||||
|
// the usual sources and forces Terraform to consult only the given
|
||||||
|
// directories. Anything not available in one of those directories
|
||||||
|
// is not available for installation.
|
||||||
|
source := c.providerCustomLocalDirectorySource(pluginDirs)
|
||||||
|
inst = c.providerInstallerCustomSource(source)
|
||||||
|
}
|
||||||
|
|
||||||
// Because we're currently just streaming a series of events sequentially
|
// Because we're currently just streaming a series of events sequentially
|
||||||
// into the terminal, we're showing only a subset of the events to keep
|
// into the terminal, we're showing only a subset of the events to keep
|
||||||
|
|
|
@ -61,6 +61,25 @@ func (m *Meta) providerInstallerCustomSource(source getproviders.Source) *provid
|
||||||
return inst
|
return inst
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// providerCustomLocalDirectorySource produces a provider source that consults
|
||||||
|
// only the given local filesystem directories for plugins to install.
|
||||||
|
//
|
||||||
|
// This is used to implement the -plugin-dir option for "terraform init", where
|
||||||
|
// the result of this method is used instead of what would've been returned
|
||||||
|
// from m.providerInstallSource.
|
||||||
|
//
|
||||||
|
// If the given list of directories is empty then the resulting source will
|
||||||
|
// have no providers available for installation at all.
|
||||||
|
func (m *Meta) providerCustomLocalDirectorySource(dirs []string) getproviders.Source {
|
||||||
|
var ret getproviders.MultiSource
|
||||||
|
for _, dir := range dirs {
|
||||||
|
ret = append(ret, getproviders.MultiSourceSelector{
|
||||||
|
Source: getproviders.NewFilesystemMirrorSource(dir),
|
||||||
|
})
|
||||||
|
}
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
// providerLocalCacheDir returns an object representing the
|
// providerLocalCacheDir returns an object representing the
|
||||||
// configuration-specific local cache directory. This is the
|
// configuration-specific local cache directory. This is the
|
||||||
// only location consulted for provider plugin packages for Terraform
|
// only location consulted for provider plugin packages for Terraform
|
||||||
|
|
Loading…
Reference in New Issue