From f93c8f8f2f30ae0d2e1c5bc47579da790b106dff Mon Sep 17 00:00:00 2001 From: Steffen Neubauer Date: Wed, 4 Jan 2023 11:28:24 +0100 Subject: [PATCH] fix: re-initialize providers changing environments (#3481) * fix: re-initialize providers changing environments When users change environments, we need to re-initialize providers. Let's consider the following example: User has a provider config like so: ``` providers: - name: exec initScript: echo ${environment.name} > someFile ``` If user runs a garden command with --env foo, and then with --env bar, and then again with --env foo we would expect `someFile` to contain `foo`. But the file actually contains bar. Reason for this is that garden skipped executing the initScript in the foo env, because it has already been executed. But the cache logic is not aware that the last command that ran was in the bar env. This commit fixes that problem. * improvement: remove unnecessary check for env name Reasoning is that when the env name changes and that is relevant, the provider config changes too (assuming that we do not implicitly pass additional information like the environment name using env variables) * tests: add an integration test Co-authored-by: srihas-g Co-authored-by: Walther --- core/src/tasks/resolve-provider.ts | 5 +- core/test/data/exec-provider-cache/.gitignore | 1 + .../exec-provider-cache/project.garden.yml | 8 +++ core/test/integ/src/plugins/exec/resolve.ts | 61 +++++++++++++++++++ plugins/terraform/commands.ts | 1 - 5 files changed, 71 insertions(+), 5 deletions(-) create mode 100644 core/test/data/exec-provider-cache/.gitignore create mode 100644 core/test/data/exec-provider-cache/project.garden.yml create mode 100644 core/test/integ/src/plugins/exec/resolve.ts diff --git a/core/src/tasks/resolve-provider.ts b/core/src/tasks/resolve-provider.ts index 1d50437d78..1ac540b542 100644 --- a/core/src/tasks/resolve-provider.ts +++ b/core/src/tasks/resolve-provider.ts @@ -263,7 +263,6 @@ export class ResolveProviderTask extends BaseTask { return getProviderStatusCachePath({ gardenDirPath: this.garden.gardenDirPath, pluginName: this.plugin.name, - environmentName: this.garden.environmentName, }) } @@ -391,11 +390,9 @@ export class ResolveProviderTask extends BaseTask { export function getProviderStatusCachePath({ gardenDirPath, pluginName, - environmentName, }: { gardenDirPath: string pluginName: string - environmentName: string }) { - return join(gardenDirPath, "cache", "provider-statuses", `${pluginName}.${environmentName}.json`) + return join(gardenDirPath, "cache", "provider-statuses", `${pluginName}.json`) } diff --git a/core/test/data/exec-provider-cache/.gitignore b/core/test/data/exec-provider-cache/.gitignore new file mode 100644 index 0000000000..f8c3214fdc --- /dev/null +++ b/core/test/data/exec-provider-cache/.gitignore @@ -0,0 +1 @@ +theFile diff --git a/core/test/data/exec-provider-cache/project.garden.yml b/core/test/data/exec-provider-cache/project.garden.yml new file mode 100644 index 0000000000..d5117eccd3 --- /dev/null +++ b/core/test/data/exec-provider-cache/project.garden.yml @@ -0,0 +1,8 @@ +kind: Project +name: incident-repro +environments: + - name: one + - name: two +providers: + - name: exec + initScript: "echo '${environment.name}' > theFile" diff --git a/core/test/integ/src/plugins/exec/resolve.ts b/core/test/integ/src/plugins/exec/resolve.ts new file mode 100644 index 0000000000..650434df47 --- /dev/null +++ b/core/test/integ/src/plugins/exec/resolve.ts @@ -0,0 +1,61 @@ +/* + * Copyright (C) 2018-2022 Garden Technologies, Inc. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +import { expect } from "chai" +import { readFile } from "fs-extra" +import { join } from "node:path" +import { getDataDir, makeTestGarden, TestGarden } from "../../../../helpers" + +describe("exec provider initialization cache behaviour", () => { + let gardenOne: TestGarden + let tmpDir: string + let fileLocation: string + + beforeEach(async () => { + gardenOne = await makeTestGarden(getDataDir("exec-provider-cache"), { environmentName: "one" }) + + tmpDir = join(await gardenOne.getRepoRoot(), "project") + fileLocation = join(tmpDir, "theFile") + + await gardenOne.resolveProvider(gardenOne.log, "exec") + }) + + it("writes the environment name to theFile as configured in the initScript", async () => { + const contents = await readFile(fileLocation, { encoding: "utf-8" }) + + expect(contents).equal("one\n") + }) + + it("overwrites theFile when changing environments", async () => { + let contents = await readFile(fileLocation, { encoding: "utf-8" }) + expect(contents).equal("one\n") + + const gardenTwo = await makeTestGarden(tmpDir, { environmentName: "two", noTempDir: true }) + await gardenTwo.resolveProvider(gardenTwo.log, "exec") + + contents = await readFile(fileLocation, { encoding: "utf-8" }) + expect(contents).equal("two\n") + }) + + it("still overwrites theFile when changing environments back", async () => { + let contents = await readFile(fileLocation, { encoding: "utf-8" }) + expect(contents).equal("one\n") + + const gardenTwo = await makeTestGarden(tmpDir, { environmentName: "two", noTempDir: true }) + await gardenTwo.resolveProvider(gardenTwo.log, "exec") + + contents = await readFile(fileLocation, { encoding: "utf-8" }) + expect(contents).equal("two\n") + + const gardenOneAgain = await makeTestGarden(tmpDir, { environmentName: "one", noTempDir: true }) + await gardenOneAgain.resolveProvider(gardenOneAgain.log, "exec") + + contents = await readFile(fileLocation, { encoding: "utf-8" }) + expect(contents).equal("one\n") + }) +}) diff --git a/plugins/terraform/commands.ts b/plugins/terraform/commands.ts index 1fc15212e6..58a42dcb0a 100644 --- a/plugins/terraform/commands.ts +++ b/plugins/terraform/commands.ts @@ -43,7 +43,6 @@ function makeRootCommand(commandName: string): PluginCommand { const cachePath = getProviderStatusCachePath({ gardenDirPath: ctx.gardenDirPath, pluginName: provider.name, - environmentName: ctx.environmentName, }) await remove(cachePath)