diff --git a/README.md b/README.md index 2f09466..246910f 100644 --- a/README.md +++ b/README.md @@ -35,6 +35,101 @@ Litmus supports CI plugin for the following CI platforms: +## Environment Variables + +Chaos CI Lib uses standardized environment variables to configure environments, infrastructure, and probes. Below is the comprehensive list of supported environment variables. + +### Litmus SDK & Authentication + +| Variable | Description | Default | Example | +|----------|-------------|---------|---------| +| `LITMUS_ENDPOINT` | Litmus server endpoint URL | `""` | `https://chaos.example.com` | +| `LITMUS_USERNAME` | Username for Litmus authentication | `""` | `admin` | +| `LITMUS_PASSWORD` | Password for Litmus authentication | `""` | `litmus` | +| `LITMUS_PROJECT_ID` | ID of the Litmus project to use | `""` | `project-123` | + +### Environment Management Variables + +| Variable | Description | Default | Example | +|----------|-------------|---------|---------| +| `CREATE_ENV` | Whether to create a new environment | `true` | `false` | +| `USE_EXISTING_ENV` | Whether to use an existing environment | `false` | `true` | +| `EXISTING_ENV_ID` | ID of existing environment (required if `USE_EXISTING_ENV=true`) | `""` | `env-123456` | +| `ENV_NAME` | Name for the new environment | `chaos-ci-env` | `my-k8s-env` | +| `ENV_TYPE` | Type of environment to create | `NON_PROD` | `PROD` | +| `ENV_DESCRIPTION` | Description of the environment | `CI Test Environment` | `Production Test Environment` | + +### Infrastructure Management Variables + +| Variable | Description | Default | Example | +|----------|-------------|---------|---------| +| `INSTALL_INFRA` | Whether to install infrastructure | `true` | `false` | +| `USE_EXISTING_INFRA` | Whether to use existing infrastructure | `false` | `true` | +| `EXISTING_INFRA_ID` | ID of existing infrastructure (required if `USE_EXISTING_INFRA=true`) | `""` | `infra-123456` | +| `INFRA_NAME` | Name for the infrastructure | `ci-infra-{expName}` | `my-k8s-infra` | +| `INFRA_NAMESPACE` | Kubernetes namespace for infrastructure | `litmus` | `chaos-testing` | +| `INFRA_SCOPE` | Scope of infrastructure | `namespace` | `cluster` | +| `INFRA_SERVICE_ACCOUNT` | Service account for infrastructure | `litmus` | `chaos-runner` | +| `INFRA_DESCRIPTION` | Description of infrastructure | `CI Test Infrastructure` | `Production Test Infra` | +| `INFRA_PLATFORM_NAME` | Platform name | `others` | `gcp` | +| `INFRA_NS_EXISTS` | Whether namespace already exists | `false` | `true` | +| `INFRA_SA_EXISTS` | Whether service account already exists | `false` | `true` | +| `INFRA_SKIP_SSL` | Whether to skip SSL verification | `false` | `true` | +| `INFRA_NODE_SELECTOR` | Node selector for infrastructure | `""` | `disk=ssd` | +| `INFRA_TOLERATIONS` | Tolerations for infrastructure | `""` | `key=value:NoSchedule` | + +### Probe Management Variables + +| Variable | Description | Default | Example | +|----------|-------------|---------|---------| +| `LITMUS_CREATE_PROBE` | Whether to create a probe | `false` | `true` | +| `LITMUS_PROBE_NAME` | Name of the probe | `http-probe` | `http-status-check` | +| `LITMUS_PROBE_TYPE` | Type of probe | `httpProbe` | `httpProbe` | +| `LITMUS_PROBE_MODE` | Mode of the probe | `SOT` | `Continuous` | +| `LITMUS_PROBE_URL` | URL for HTTP probe | `http://localhost:8080/health` | `http://app:8080/health` | +| `LITMUS_PROBE_TIMEOUT` | Timeout for probe | `30s` | `5s` | +| `LITMUS_PROBE_INTERVAL` | Interval for probe | `10s` | `5s` | +| `LITMUS_PROBE_ATTEMPTS` | Number of attempts for probe | `1` | `3` | +| `LITMUS_PROBE_RESPONSE_CODE` | Expected HTTP response code | `200` | `200` | + +### Example Usage + +To create a new environment and infrastructure: +```bash +# Authentication +export LITMUS_ENDPOINT="https://chaos.example.com" +export LITMUS_USERNAME="admin" +export LITMUS_PASSWORD="litmus" +export LITMUS_PROJECT_ID="project-123" + +# Environment setup +export CREATE_ENV="true" +export ENV_NAME="test-environment" +export ENV_TYPE="NON_PROD" + +# Infrastructure setup +export INSTALL_INFRA="true" +export INFRA_NAME="test-infra" +export INFRA_NAMESPACE="chaos-testing" +export INFRA_SCOPE="namespace" + +# Optional probe setup +export LITMUS_CREATE_PROBE="true" +export LITMUS_PROBE_NAME="http-status-check" +export LITMUS_PROBE_TYPE="httpProbe" +export LITMUS_PROBE_URL="http://app:8080/health" +export LITMUS_PROBE_RESPONSE_CODE="200" +``` + +To use existing environment and infrastructure: +```bash +# Set environment variables for existing resources +export USE_EXISTING_ENV="true" +export EXISTING_ENV_ID="env-123456" +export USE_EXISTING_INFRA="true" +export EXISTING_INFRA_ID="infra-789012" +``` + ## How to get started? Refer the [LitmusChaos Docs](https://docs.litmuschaos.io) and [Experiment Docs](https://litmuschaos.github.io/litmus/experiments/categories/contents/) diff --git a/experiments/container-kill_test.go b/experiments/container-kill_test.go index 211c10e..26b310f 100644 --- a/experiments/container-kill_test.go +++ b/experiments/container-kill_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/container-kill/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestContainerKill(t *testing.T) { @@ -22,62 +26,144 @@ func TestContainerKill(t *testing.T) { //BDD for running container-kill experiment var _ = Describe("BDD of running container-kill experiment", func() { - Context("Check for container-kill experiment", func() { + Context("Check for container-kill experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "container-kill", "container-kill-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallContainerKillEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the container kill experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("container-kill") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructContainerKillExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) -}) +}) \ No newline at end of file diff --git a/experiments/disk-fill_test.go b/experiments/disk-fill_test.go index 2be7fe3..b5039ec 100644 --- a/experiments/disk-fill_test.go +++ b/experiments/disk-fill_test.go @@ -1,83 +1,169 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/disk-fill/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestDiskFill(t *testing.T) { RegisterFailHandler(Fail) RunSpecs(t, "BDD test") } - + //BDD for running disk-fill experiment var _ = Describe("BDD of running disk-fill experiment", func() { - Context("Check for disk-fill experiment", func() { - - It("Should check for the pod delete experiment", func() { + Context("Check for disk-fill experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "disk-fill", "disk-fill-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallDiskFillEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the disk fill experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("disk-fill") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructDiskFillExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/experiments/node-cpu-hog_test.go b/experiments/node-cpu-hog_test.go index 8b7ff75..2c2110b 100644 --- a/experiments/node-cpu-hog_test.go +++ b/experiments/node-cpu-hog_test.go @@ -1,17 +1,22 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/node-cpu-hog/lib" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/log" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestNodeCPUHog(t *testing.T) { @@ -22,62 +27,144 @@ func TestNodeCPUHog(t *testing.T) { //BDD for running node-cpu-hog experiment var _ = Describe("BDD of running node-cpu-hog experiment", func() { - Context("Check for node-cpu-hog experiment", func() { + Context("Check for node-cpu-hog experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "node-cpu-hog", "node-cpu-hog-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallNodeCPUHogEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the node cpu hog experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("node-cpu-hog") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructNodeCPUHogExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/experiments/node-io-stress_test.go b/experiments/node-io-stress_test.go index fcb893c..fff708b 100644 --- a/experiments/node-io-stress_test.go +++ b/experiments/node-io-stress_test.go @@ -1,17 +1,22 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/node-io-stress/lib" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/log" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestNodeIOStress(t *testing.T) { @@ -22,62 +27,144 @@ func TestNodeIOStress(t *testing.T) { //BDD for running node-io-stress experiment var _ = Describe("BDD of running node-io-stress experiment", func() { - Context("Check for node-io-stress experiment", func() { + Context("Check for node-io-stress experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "node-io-stress", "node-io-stress-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallNodeIOStressEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the node io stress experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("node-io-stress") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructNodeIOStressExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) + diff --git a/experiments/node-memory-hog_test.go b/experiments/node-memory-hog_test.go index 854e1e4..29858df 100644 --- a/experiments/node-memory-hog_test.go +++ b/experiments/node-memory-hog_test.go @@ -1,17 +1,22 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/node-memory-hog/lib" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/log" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestNodeMemoryHog(t *testing.T) { @@ -22,62 +27,144 @@ func TestNodeMemoryHog(t *testing.T) { //BDD for running node-memory-hog experiment var _ = Describe("BDD of running node-memory-hog experiment", func() { - Context("Check for node-memory-hog experiment", func() { + Context("Check for node-memory-hog experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "node-memory-hog", "node-memory-hog-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallNodeMemoryHogEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the node memory hog experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("node-memory-hog") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructNodeMemoryHogExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) + diff --git a/experiments/pod-autoscaler_test.go b/experiments/pod-autoscaler_test.go index 38b8e68..ea71505 100644 --- a/experiments/pod-autoscaler_test.go +++ b/experiments/pod-autoscaler_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-autoscaler/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodAutoscaler(t *testing.T) { @@ -22,62 +26,144 @@ func TestPodAutoscaler(t *testing.T) { //BDD for running pod-autoscaler experiment var _ = Describe("BDD of running pod-autoscaler experiment", func() { - Context("Check for pod-autoscaler experiment", func() { + Context("Check for pod-autoscaler experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-autoscaler", "pod-autoscaler-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodAutoscalerEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod autoscaler experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-autoscaler") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodAutoscalerExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/experiments/pod-cpu-hog_test.go b/experiments/pod-cpu-hog_test.go index 437e37a..8cd0cc5 100644 --- a/experiments/pod-cpu-hog_test.go +++ b/experiments/pod-cpu-hog_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-cpu-hog/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodCPUHog(t *testing.T) { @@ -22,62 +26,145 @@ func TestPodCPUHog(t *testing.T) { //BDD for running pod-cpu-hog experiment var _ = Describe("BDD of running pod-cpu-hog experiment", func() { - Context("Check for pod-cpu-hog experiment", func() { + Context("Check for pod-cpu-hog experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-cpu-hog", "pod-cpu-hog-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodCPUHogEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod cpu hog experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-cpu-hog") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodCPUHogExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) + diff --git a/experiments/pod-delete_test.go b/experiments/pod-delete_test.go index cb27529..ec79ef7 100644 --- a/experiments/pod-delete_test.go +++ b/experiments/pod-delete_test.go @@ -1,13 +1,17 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-delete/lib" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" @@ -22,62 +26,145 @@ func TestPodDelete(t *testing.T) { //BDD for running pod-delete experiment var _ = Describe("BDD of running pod-delete experiment", func() { - Context("Check for pod-delete experiment", func() { + Context("Check for pod-delete experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-delete", "pod-delete-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodDeleteEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod delete experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-delete") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodDeleteExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) + diff --git a/experiments/pod-memory-hog_test.go b/experiments/pod-memory-hog_test.go index 446e38c..a459bcc 100644 --- a/experiments/pod-memory-hog_test.go +++ b/experiments/pod-memory-hog_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-memory-hog/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodMemoryHog(t *testing.T) { @@ -22,62 +26,145 @@ func TestPodMemoryHog(t *testing.T) { //BDD for running pod-memory-hog experiment var _ = Describe("BDD of running pod-memory-hog experiment", func() { - Context("Check for pod-memory-hog experiment", func() { + Context("Check for pod-memory-hog experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-memory-hog", "pod-memory-hog-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodMemoryHogEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod memory hog experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-memory-hog") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodMemoryHogExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) + diff --git a/experiments/pod-network-corruption_test.go b/experiments/pod-network-corruption_test.go index 70089a2..0be64b4 100644 --- a/experiments/pod-network-corruption_test.go +++ b/experiments/pod-network-corruption_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-network-corruption/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodNetworkCorruption(t *testing.T) { @@ -22,62 +26,144 @@ func TestPodNetworkCorruption(t *testing.T) { //BDD for running pod-network-corruption experiment var _ = Describe("BDD of running pod-network-corruption experiment", func() { - Context("Check for pod-network-corruption experiment", func() { + Context("Check for pod-network-corruption experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-network-corruption", "pod-network-corruption-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodNetworkCorruptionEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod network corruption experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-network-corruption") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodNetworkCorruptionExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/experiments/pod-network-duplication_test.go b/experiments/pod-network-duplication_test.go index a0640b1..15950db 100644 --- a/experiments/pod-network-duplication_test.go +++ b/experiments/pod-network-duplication_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-network-duplication/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodNetworkDuplication(t *testing.T) { @@ -22,62 +26,144 @@ func TestPodNetworkDuplication(t *testing.T) { //BDD for running pod-network-duplication experiment var _ = Describe("BDD of running pod-network-duplication experiment", func() { - Context("Check for pod-network-duplication experiment", func() { + Context("Check for pod-network-duplication experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-network-duplication", "pod-network-duplication-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodNetworkDuplicationEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod network duplication experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-network-duplication") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodNetworkDuplicationExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/experiments/pod-network-latency_test.go b/experiments/pod-network-latency_test.go index 940b8b3..9cc3caf 100644 --- a/experiments/pod-network-latency_test.go +++ b/experiments/pod-network-latency_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-network-latency/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodNetworkLatency(t *testing.T) { @@ -22,62 +26,144 @@ func TestPodNetworkLatency(t *testing.T) { //BDD for running pod-network-latency experiment var _ = Describe("BDD of running pod-network-latency experiment", func() { - Context("Check for pod-network-latency experiment", func() { + Context("Check for pod-network-latency experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-network-latency", "pod-network-latency-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodNetworkLatencyEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod network latency experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-network-latency") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodNetworkLatencyExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/experiments/pod-network-loss_test.go b/experiments/pod-network-loss_test.go index ef51a6d..888edd0 100644 --- a/experiments/pod-network-loss_test.go +++ b/experiments/pod-network-loss_test.go @@ -1,17 +1,21 @@ package experiments import ( + "fmt" "testing" + "time" "github.com/litmuschaos/chaos-ci-lib/pkg" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" - engine "github.com/litmuschaos/chaos-ci-lib/pkg/generic/pod-network-loss/lib" - "github.com/litmuschaos/chaos-ci-lib/pkg/log" + "github.com/litmuschaos/chaos-ci-lib/pkg/infrastructure" "github.com/litmuschaos/chaos-ci-lib/pkg/types" - "github.com/litmuschaos/chaos-operator/pkg/apis/litmuschaos/v1alpha1" + "github.com/litmuschaos/chaos-ci-lib/pkg/workflow" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" + "k8s.io/klog" ) func TestPodNetworkLoss(t *testing.T) { @@ -22,62 +26,144 @@ func TestPodNetworkLoss(t *testing.T) { //BDD for running pod-network-loss experiment var _ = Describe("BDD of running pod-network-loss experiment", func() { - Context("Check for pod-network-loss experiment", func() { + Context("Check for pod-network-loss experiment via SDK", func() { + // Define variables accessible to It and AfterEach + var ( + experimentsDetails types.ExperimentDetails + sdkClient sdk.Client + err error + ) - It("Should check for the pod delete experiment", func() { - - experimentsDetails := types.ExperimentDetails{} - clients := environment.ClientSets{} - chaosEngine := v1alpha1.ChaosEngine{} - - //Getting kubeConfig and Generate ClientSets - By("[PreChaos]: Getting kubeconfig and generate clientset") - err := clients.GenerateClientSetFromKubeConfig() - Expect(err).To(BeNil(), "Unable to Get the kubeconfig, due to {%v}", err) + BeforeEach(func() { + experimentsDetails = types.ExperimentDetails{} + err = nil //Fetching all the default ENV By("[PreChaos]: Fetching all default ENVs") - log.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) + klog.Infof("[PreReq]: Getting the ENVs for the %v experiment", experimentsDetails.ExperimentName) environment.GetENV(&experimentsDetails, "pod-network-loss", "pod-network-loss-engine") - // Install RBAC for experiment Execution - By("[Prepare]: Prepare and install RBAC") - err = pkg.InstallRbac(&experimentsDetails, experimentsDetails.ChaosNamespace) - Expect(err).To(BeNil(), "fail to install rbac for the experiment, due to {%v}", err) - - // Install ChaosEngine for experiment Execution - By("[Prepare]: Prepare and install ChaosEngine") - err = engine.InstallPodNetworkLossEngine(&experimentsDetails, &chaosEngine, clients) - Expect(err).To(BeNil(), "fail to install chaosengine, due to {%v}", err) - - //Checking runner pod running state - By("[Status]: Runner pod running status check") - err = pkg.RunnerPodStatus(&experimentsDetails, chaosEngine.Namespace, clients) - if err != nil && chaosEngine.Namespace != experimentsDetails.AppNS { - err = pkg.RunnerPodStatus(&experimentsDetails, experimentsDetails.AppNS, clients) + // Initialize SDK client + By("[PreChaos]: Initializing SDK client") + sdkClient, err = environment.GenerateClientSetFromSDK() + Expect(err).To(BeNil(), "Unable to generate Litmus SDK client, due to {%v}", err) + + // Setup infrastructure + By("[PreChaos]: Setting up infrastructure") + err = infrastructure.SetupInfrastructure(&experimentsDetails, sdkClient) + Expect(err).To(BeNil(), "Failed to setup infrastructure, due to {%v}", err) + + // Validate that infrastructure ID is properly set + Expect(experimentsDetails.ConnectedInfraID).NotTo(BeEmpty(), "Setup failed: ConnectedInfraID is empty after connection attempt.") + + // Setup probe if configured to do so + if experimentsDetails.CreateProbe { + By("[PreChaos]: Setting up probe") + err = workflow.CreateProbe(&experimentsDetails, sdkClient, experimentsDetails.LitmusProjectID) + Expect(err).To(BeNil(), "Failed to create probe, due to {%v}", err) + // Validate that probe was created successfully + Expect(experimentsDetails.CreatedProbeID).NotTo(BeEmpty(), "Probe creation failed: CreatedProbeID is empty") } - Expect(err).To(BeNil(), "Runner pod status check failed, due to {%v}", err) - - //Chaos pod running status check - err = pkg.ChaosPodStatus(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Chaos pod status check failed, due to {%v}", err) - - //Waiting for chaos pod to get completed - //And Print the logs of the chaos pod - By("[Status]: Wait for chaos pod completion and then print logs") - err = pkg.ChaosPodLogs(&experimentsDetails, clients) - Expect(err).To(BeNil(), "Fail to get the experiment chaos pod logs, due to {%v}", err) - - //Checking the chaosresult verdict - By("[Verdict]: Checking the chaosresult verdict") - err = pkg.ChaosResultVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChasoResult Verdict check failed, due to {%v}", err) - - //Checking chaosengine verdict - By("Checking the Verdict of Chaos Engine") - err = pkg.ChaosEngineVerdict(&experimentsDetails, clients) - Expect(err).To(BeNil(), "ChaosEngine Verdict check failed, due to {%v}", err) + }) + It("Should run the pod network loss experiment via SDK", func() { + + // Ensure pre-checks passed from BeforeEach + Expect(err).To(BeNil(), "Error during BeforeEach setup: %v", err) + klog.Info("Executing V3 SDK Path for Experiment") + + + // 1. Construct Experiment Request + By("[SDK Prepare]: Constructing Chaos Experiment Request") + experimentName := pkg.GenerateUniqueExperimentName("pod-network-loss") + experimentsDetails.ExperimentName = experimentName + experimentID := pkg.GenerateExperimentID() + experimentRequest, errConstruct := workflow.ConstructPodNetworkLossExperimentRequest(&experimentsDetails, experimentID, experimentName) + Expect(errConstruct).To(BeNil(), "Failed to construct experiment request: %v", errConstruct) + + // 2. Create and Run Experiment via SDK + By("[SDK Prepare]: Creating and Running Chaos Experiment") + createResponse, err := sdkClient.Experiments().Create(experimentsDetails.LitmusProjectID, *experimentRequest) + Expect(err).To(BeNil(), "Failed to create experiment via SDK: %v", err) + klog.Infof("Created experiment: %s", createResponse) + + // 3. Get the experiment run ID + By("[SDK Query]: Polling for experiment run to become available") + var experimentRunID string + maxRetries := 10 + found := false + + for i := 0; i < maxRetries; i++ { + time.Sleep(3 * time.Second) + + listExperimentRunsReq := models.ListExperimentRunRequest{ + ExperimentIDs: []*string{&experimentID}, + } + + runsList, err := sdkClient.Experiments().ListRuns(listExperimentRunsReq) + if err != nil { + klog.Warningf("Error fetching experiment runs: %v", err) + continue + } + + klog.Infof("Attempt %d: Found %d experiment runs", i+1, + len(runsList.ExperimentRuns)) + + if len(runsList.ExperimentRuns) > 0 { + experimentRunID = runsList.ExperimentRuns[0].ExperimentRunID + klog.Infof("Found experiment run ID: %s", experimentRunID) + found = true + break + } + + klog.Infof("Retrying after delay...") + } + + Expect(found).To(BeTrue(), "No experiment runs found for experiment after %d retries", maxRetries) + + // 4. Poll for Experiment Run Status + By("[SDK Status]: Polling for Experiment Run Status") + var finalPhase string + var pollError error + timeout := time.After(time.Duration(experimentsDetails.ExperimentTimeout) * time.Minute) + ticker := time.NewTicker(time.Duration(experimentsDetails.ExperimentPollingInterval) * time.Second) + defer ticker.Stop() + + pollLoop: + for { + select { + case <-timeout: + pollError = fmt.Errorf("timed out waiting for experiment run %s to complete after %d minutes", experimentRunID, experimentsDetails.ExperimentTimeout) + klog.Error(pollError) + break pollLoop + case <-ticker.C: + phase, errStatus := sdkClient.Experiments().GetRunPhase(experimentRunID) + if errStatus != nil { + klog.Errorf("Error fetching experiment run status for %s: %v", experimentRunID, errStatus) + continue + } + klog.Infof("Experiment Run %s current phase: %s", experimentRunID, phase) + finalPhases := []string{"Completed", "Completed_With_Error", "Failed", "Error", "Stopped", "Skipped", "Aborted", "Timeout", "Terminated"} + if pkg.ContainsString(finalPhases, phase) { + finalPhase = phase + klog.Infof("Experiment Run %s reached final phase: %s", experimentRunID, phase) + break pollLoop + } + } + } + + // 5. Post Validation / Verdict Check + By("[SDK Verdict]: Checking Experiment Run Verdict") + Expect(pollError).To(BeNil()) + Expect(finalPhase).NotTo(BeEmpty(), "Final phase should not be empty after polling") + Expect(finalPhase).To(Equal("Completed"), fmt.Sprintf("Experiment Run phase should be Completed, but got %s", finalPhase)) + }) + // Cleanup using AfterEach + AfterEach(func() { + // Disconnect infrastructure using the new module + By("[CleanUp]: Cleaning up infrastructure") + errDisconnect := infrastructure.DisconnectInfrastructure(&experimentsDetails, sdkClient) + Expect(errDisconnect).To(BeNil(), "Failed to clean up infrastructure, due to {%v}", errDisconnect) }) }) }) diff --git a/go.mod b/go.mod index 9aa5377..9491640 100644 --- a/go.mod +++ b/go.mod @@ -1,27 +1,86 @@ module github.com/litmuschaos/chaos-ci-lib -go 1.14 +go 1.24.0 + +toolchain go1.24.1 replace gopkg.in/fsnotify.v1 v1.4.8 => github.com/fsnotify/fsnotify v1.4.8 require ( github.com/ghodss/yaml v1.0.1-0.20190212211648-25d852aebe32 - github.com/litmuschaos/chaos-operator v0.0.0-20210430184607-cb675e58922d - github.com/litmuschaos/litmus-e2e v0.0.0-20210713061120-32af01dc2757 - github.com/litmuschaos/litmus-go v0.0.0-20210430161537-788b26f5b445 - github.com/onsi/ginkgo v1.16.2 - github.com/onsi/gomega v1.12.0 + github.com/google/uuid v1.6.0 + github.com/litmuschaos/chaos-operator v0.0.0-20240601063404-e96a7ee7f1f7 + github.com/litmuschaos/litmus-go v0.0.0-20210705063441-babf0c4aa57d + github.com/litmuschaos/litmus-go-sdk v0.0.0-20250513045254-3a81cc911979 + github.com/litmuschaos/litmus/chaoscenter/graphql/server v0.0.0-20250317093827-172c4b9ffb24 + github.com/onsi/ginkgo v1.16.5 + github.com/onsi/gomega v1.34.1 github.com/pkg/errors v0.9.1 - github.com/sirupsen/logrus v1.7.0 - k8s.io/api v0.17.3 - k8s.io/apimachinery v0.17.3 + github.com/sirupsen/logrus v1.9.3 + k8s.io/api v0.26.0 + k8s.io/apimachinery v0.26.0 k8s.io/client-go v12.0.0+incompatible k8s.io/klog v1.0.0 + sigs.k8s.io/yaml v1.4.0 +) + +require ( + cloud.google.com/go/compute v1.25.1 // indirect + cloud.google.com/go/compute/metadata v0.2.3 // indirect + github.com/PuerkitoBio/purell v1.1.1 // indirect + github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 // indirect + github.com/davecgh/go-spew v1.1.1 // indirect + github.com/emicklei/go-restful v2.16.0+incompatible // indirect + github.com/fatih/color v1.18.0 // indirect + github.com/fsnotify/fsnotify v1.5.1 // indirect + github.com/go-openapi/jsonpointer v0.19.5 // indirect + github.com/go-openapi/jsonreference v0.19.6 // indirect + github.com/go-openapi/spec v0.20.4 // indirect + github.com/go-openapi/swag v0.19.15 // indirect + github.com/gogo/protobuf v1.3.2 // indirect + github.com/golang-jwt/jwt v3.2.2+incompatible // indirect + github.com/golang/protobuf v1.5.4 // indirect + github.com/google/go-cmp v0.6.0 // indirect + github.com/google/gofuzz v1.2.0 // indirect + github.com/googleapis/gnostic v0.5.5 // indirect + github.com/imdario/mergo v0.3.9 // indirect + github.com/josharian/intern v1.0.0 // indirect + github.com/json-iterator/go v1.1.12 // indirect + github.com/kr/pretty v0.3.1 // indirect + github.com/mailru/easyjson v0.7.7 // indirect + github.com/mattn/go-colorable v0.1.13 // indirect + github.com/mattn/go-isatty v0.0.20 // indirect + github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect + github.com/modern-go/reflect2 v1.0.2 // indirect + github.com/nxadm/tail v1.4.8 // indirect + github.com/rogpeppe/go-internal v1.11.0 // indirect + github.com/spf13/pflag v1.0.5 // indirect + golang.org/x/crypto v0.31.0 // indirect + golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56 // indirect + golang.org/x/net v0.33.0 // indirect + golang.org/x/oauth2 v0.18.0 // indirect + golang.org/x/sys v0.28.0 // indirect + golang.org/x/term v0.27.0 // indirect + golang.org/x/text v0.21.0 // indirect + golang.org/x/time v0.5.0 // indirect + google.golang.org/appengine v1.6.8 // indirect + google.golang.org/protobuf v1.34.2 // indirect + gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c // indirect + gopkg.in/inf.v0 v0.9.1 // indirect + gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 // indirect + gopkg.in/yaml.v2 v2.4.0 // indirect + gopkg.in/yaml.v3 v3.0.1 // indirect + k8s.io/kube-openapi v0.0.0-20220124234850-424119656bbf // indirect + k8s.io/utils v0.0.0-20221107191617-1a15be271d1d // indirect + sigs.k8s.io/controller-runtime v0.11.1 // indirect ) // Pinned to kubernetes-1.16.2 replace ( github.com/docker/docker => github.com/moby/moby v0.7.3-0.20190826074503-38ab9da00309 + github.com/go-openapi/spec => github.com/go-openapi/spec v0.19.5 + github.com/googleapis/gnostic => github.com/googleapis/gnostic v0.3.1 + github.com/litmuschaos/chaos-operator => github.com/litmuschaos/chaos-operator v0.0.0-20210610071657-a58dbd939e73 k8s.io/api => k8s.io/api v0.0.0-20191016110408-35e52d86657a k8s.io/apiextensions-apiserver => k8s.io/apiextensions-apiserver v0.0.0-20191016113550-5357c4baaf65 k8s.io/apimachinery => k8s.io/apimachinery v0.0.0-20191004115801-a2eda9f80ab8 @@ -36,6 +95,7 @@ replace ( k8s.io/csi-translation-lib => k8s.io/csi-translation-lib v0.0.0-20191016115521-756ffa5af0bd k8s.io/kube-aggregator => k8s.io/kube-aggregator v0.0.0-20191016112429-9587704a8ad4 k8s.io/kube-controller-manager => k8s.io/kube-controller-manager v0.0.0-20191016114939-2b2b218dc1df + k8s.io/kube-openapi => k8s.io/kube-openapi v0.0.0-20200805222855-6aeccd4b50c6 k8s.io/kube-proxy => k8s.io/kube-proxy v0.0.0-20191016114407-2e83b6f20229 k8s.io/kube-scheduler => k8s.io/kube-scheduler v0.0.0-20191016114748-65049c67a58b k8s.io/kubectl => k8s.io/kubectl v0.0.0-20191016120415-2ed914427d51 @@ -43,4 +103,5 @@ replace ( k8s.io/legacy-cloud-providers => k8s.io/legacy-cloud-providers v0.0.0-20191016115753-cf0698c3a16b k8s.io/metrics => k8s.io/metrics v0.0.0-20191016113814-3b1a734dba6e k8s.io/sample-apiserver => k8s.io/sample-apiserver v0.0.0-20191016112829-06bb3c9d77c9 + sigs.k8s.io/controller-runtime => sigs.k8s.io/controller-runtime v0.6.0 ) diff --git a/go.sum b/go.sum index fc3362f..0b1b87c 100644 --- a/go.sum +++ b/go.sum @@ -3,29 +3,11 @@ bou.ke/monkey v1.0.1/go.mod h1:FgHuK96Rv2Nlf+0u1OOVDpCMdsWyOFmeeketDHE7LIg= cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= cloud.google.com/go v0.37.4/go.mod h1:NHPJ89PdicEuT9hdPXMROBD91xc5uRDxsMtSB16k7hw= -cloud.google.com/go v0.38.0 h1:ROfEUZz+Gh5pa62DJWXSaonyu3StP6EA6lPEXPI6mCo= cloud.google.com/go v0.38.0/go.mod h1:990N+gfupTy94rShfmMCWGDn0LpTmnzTp2qbd1dvSRU= -cloud.google.com/go v0.44.1/go.mod h1:iSa0KzasP4Uvy3f1mN/7PiObzGgflwredwwASm/v6AU= -cloud.google.com/go v0.44.2/go.mod h1:60680Gw3Yr4ikxnPRS/oxxkBccT6SA1yMk63TGekxKY= -cloud.google.com/go v0.45.1/go.mod h1:RpBamKRgapWJb87xiFSdk4g1CME7QZg3uwTez+TSTjc= -cloud.google.com/go v0.46.3/go.mod h1:a6bKKbmY7er1mI7TEI4lsAkts/mkhTSZK8w33B4RAg0= -cloud.google.com/go v0.50.0/go.mod h1:r9sluTvynVuxRIOHXQEHMFffphuXHOMZMycpNR5e6To= -cloud.google.com/go v0.52.0/go.mod h1:pXajvRH/6o3+F9jDHZWQ5PbGhn+o8w9qiu/CffaVdO4= -cloud.google.com/go v0.53.0/go.mod h1:fp/UouUEsRkN6ryDKNW/Upv/JBKnv6WDthjR6+vze6M= -cloud.google.com/go v0.54.0 h1:3ithwDMr7/3vpAMXiH+ZQnYbuIsh+OPhUPMFC9enmn0= -cloud.google.com/go v0.54.0/go.mod h1:1rq2OEkV3YMf6n/9ZvGWI3GWw0VoqH/1x2nd8Is/bPc= -cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o= -cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE= -cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= -cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE= -cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= -cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= -cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= -cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= -cloud.google.com/go/storage v1.0.0/go.mod h1:IhtSnM/ZTZV8YYJWCY8RULGVqBDmpoyjwiyrjsg+URw= -cloud.google.com/go/storage v1.5.0/go.mod h1:tpKbwo567HUNpVclU5sGELwQWBDZ8gh0ZeosJ0Rtdos= -cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk= -dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= +cloud.google.com/go/compute v1.25.1 h1:ZRpHJedLtTpKgr3RV1Fx23NuaAEN1Zfx9hw1u4aJdjU= +cloud.google.com/go/compute v1.25.1/go.mod h1:oopOIR53ly6viBYxaDhBfJwzUAxf1zE//uf3IB011ls= +cloud.google.com/go/compute/metadata v0.2.3 h1:mg4jlk7mCAj6xXp9UJ4fjI9VUI5rubuGBW5aJ7UnBMY= +cloud.google.com/go/compute/metadata v0.2.3/go.mod h1:VAV5nSsACxMJvgaAuX6Pk2AawlZn8kiOGuCv6gTkwuA= github.com/Azure/azure-sdk-for-go v32.5.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= github.com/Azure/azure-sdk-for-go v35.0.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc= github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8= @@ -91,7 +73,7 @@ github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:l github.com/auth0/go-jwt-middleware v0.0.0-20170425171159-5493cabe49f7/go.mod h1:LWMyo4iOLWXHGdBki7NIht1kHru/0wM179h+d3g8ATM= github.com/aws/aws-sdk-go v1.16.26/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= github.com/aws/aws-sdk-go v1.17.7/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo= -github.com/aws/aws-sdk-go v1.36.27/go.mod h1:hcU610XS61/+aQV88ixoOzUoG7v3b31pl2zKMmprdro= +github.com/aws/aws-sdk-go v1.38.59/go.mod h1:hcU610XS61/+aQV88ixoOzUoG7v3b31pl2zKMmprdro= github.com/bazelbuild/bazel-gazelle v0.0.0-20181012220611-c728ce9f663e/go.mod h1:uHBSeeATKpVazAACZBDPL/Nk/UhQDDsJWDlqYJo8/Us= github.com/bazelbuild/bazel-gazelle v0.18.2/go.mod h1:D0ehMSbS+vesFsLGiD6JXu3mVEzOlfUl8wNnq+x/9p0= github.com/bazelbuild/bazel-gazelle v0.19.1-0.20191105222053-70208cbdc798/go.mod h1:rPwzNHUqEzngx1iVBfO/2X2npKaT3tqPqqHW6rVsn/A= @@ -125,9 +107,7 @@ github.com/cespare/xxhash/v2 v2.1.0/go.mod h1:dgIUBU3pDso/gPgZ1osOZ0iQf77oPR28Tj github.com/chai2010/gettext-go v0.0.0-20160711120539-c6fed771bfd5/go.mod h1:/iP1qXHoty45bqomnu2LM+VVyAEdWN+vtSHGlQgyxbw= github.com/checkpoint-restore/go-criu v0.0.0-20190109184317-bdb7599cd87b/go.mod h1:TrMrLQfeENAPYPRsJuq3jsqdlRh3lvi6trTZJG8+tho= github.com/cheekybits/genny v0.0.0-20170328200008-9127e812e1e9/go.mod h1:+tQajlRqAUrPI7DOSpB0XAqZYtQakVtB7wXkRAgjxjQ= -github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= -github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI= -github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU= +github.com/cilium/ebpf v0.4.0/go.mod h1:4tRaxcgiL706VnOzHOdBlY8IEAIdxINsQBcU4xJJXRs= github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= github.com/cloudflare/cfssl v0.0.0-20180726162950-56268a613adf/go.mod h1:yMWuSON2oQp+43nFtAV/uvKQIFpSPerB57DCt9t8sSA= github.com/clusterhq/flocker-go v0.0.0-20160920122132-2b8b7259d313/go.mod h1:P1wt9Z3DP8O6W3rvwCt0REIlshg1InHImaLW0t3ObY0= @@ -137,13 +117,13 @@ github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:z github.com/codegangsta/negroni v1.0.0/go.mod h1:v0y3T5G7Y1UlFfyxFn/QLRU4a2EuNau2iZY63YTKWo0= github.com/container-storage-interface/spec v1.1.0/go.mod h1:6URME8mwIBbpVyZV93Ce5St17xBiQJQY67NDsuohiy4= github.com/container-storage-interface/spec v1.2.0/go.mod h1:6URME8mwIBbpVyZV93Ce5St17xBiQJQY67NDsuohiy4= +github.com/containerd/cgroups v1.0.1/go.mod h1:0SJrPIenamHDcZhEcJMNBB85rHcUsw4f25ZfBiPYRkU= github.com/containerd/console v0.0.0-20170925154832-84eeaae905fa/go.mod h1:Tj/on1eG8kiEhd0+fhSDzsPAFESxzBBvdyEgyryXffw= github.com/containerd/containerd v1.0.2/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= github.com/containerd/containerd v1.2.7/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= github.com/containerd/containerd v1.3.0-beta.2.0.20190823190603-4a2f61c4f2b4/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= github.com/containerd/containerd v1.3.0/go.mod h1:bC6axHOhabU15QhwfG7w5PipXdVtMXFTttgp+kVtyUA= github.com/containerd/continuity v0.0.0-20181203112020-004b46473808/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= -github.com/containerd/ttrpc v1.0.2/go.mod h1:UAxOpgT9ziI0gJrmKvgcZivgxOp8iFPSk8httJEt98Y= github.com/containerd/typeurl v0.0.0-20190228175220-2a93cfde8c20/go.mod h1:Cm3kwCdlkCfMSHURc+r6fwoGH6/F1hH3S4sg0rLFWPc= github.com/containernetworking/cni v0.7.1/go.mod h1:LGwApLUm2FpoOfxTDEeq8T9ipbpZ61X79hmU3w8FmsY= github.com/coredns/corefile-migration v1.0.2/go.mod h1:OFwBp/Wc9dJt5cAZzHWMNhK1r5L0p0jDwIBc6j8NC8E= @@ -160,14 +140,17 @@ github.com/coreos/go-systemd v0.0.0-20180511133405-39ca1b05acc7/go.mod h1:F5haX7 github.com/coreos/go-systemd v0.0.0-20181012123002-c6f51f82210d/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= github.com/coreos/go-systemd v0.0.0-20190620071333-e64a0ec8b42a/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= +github.com/coreos/go-systemd/v22 v22.1.0/go.mod h1:xO0FLkIi5MaZafQlIrOotqXZ90ih+1atmu1JpKERPPk= github.com/coreos/pkg v0.0.0-20160727233714-3ac0863d7acf/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= github.com/coreos/pkg v0.0.0-20180108230652-97fdf19511ea/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= github.com/coreos/pkg v0.0.0-20180928190104-399ea9e2e55f/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= github.com/coreos/prometheus-operator v0.34.0/go.mod h1:Li6rMllG/hYIyXfMuvUwhyC+hqwJVHdsDdP21hypT1M= github.com/coreos/rkt v1.30.0/go.mod h1:O634mlH6U7qk87poQifK6M2rsFNt+FyUTWNMnP1hF1U= github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE= +github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= github.com/cpuguy83/go-md2man/v2 v2.0.0/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7DoTY= +github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/cyphar/filepath-securejoin v0.2.2/go.mod h1:FpkQEhXnPnOthhzymB7CGsFk2G9VLXONKD9G7QGMM+4= github.com/cznic/b v0.0.0-20180115125044-35e9bbe41f07/go.mod h1:URriBxXwVq5ijiJ12C7iIZqlA69nTlI+LgI6/pwftG8= github.com/cznic/fileutil v0.0.0-20180108211300-6a051e75936f/go.mod h1:8S58EK26zhXSxzv7NQFpnliaOQsmDUxvoQO3rt154Vg= @@ -179,7 +162,6 @@ github.com/cznic/ql v1.2.0/go.mod h1:FbpzhyZrqr0PVlK6ury+PoW3T0ODUV22OeWIxcaOrSE github.com/cznic/sortutil v0.0.0-20150617083342-4c7342852e65/go.mod h1:q2w6Bg5jeox1B+QkJ6Wp/+Vn0G/bo3f1uY7Fn3vivIQ= github.com/cznic/strutil v0.0.0-20171016134553-529a34b1c186/go.mod h1:AHHPPPXTw0h6pVabbcbyGRK1DckRn7r/STdZEeIDzZc= github.com/cznic/zappy v0.0.0-20160723133515-2533cb5b45cc/go.mod h1:Y1SNZ4dRUOKXshKUbwUapqNncRrho4mkjQebgEHZLj8= -github.com/davecgh/go-spew v0.0.0-20151105211317-5215b55f46b2/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -217,8 +199,9 @@ github.com/emicklei/go-restful v0.0.0-20170410110728-ff4f55a20633/go.mod h1:otzb github.com/emicklei/go-restful v2.9.5+incompatible/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= github.com/emicklei/go-restful v2.9.6+incompatible/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= github.com/emicklei/go-restful v2.11.1+incompatible/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= -github.com/emicklei/go-restful v2.12.0+incompatible h1:SIvoTSbsMEwuM3dzFirLwKc4BH6VXP5CNf+G1FfJVr4= github.com/emicklei/go-restful v2.12.0+incompatible/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= +github.com/emicklei/go-restful v2.16.0+incompatible h1:rgqiKNjTnFQA6kkhFe16D8epTksy9HQ1MyrbDXSdYhM= +github.com/emicklei/go-restful v2.16.0+incompatible/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/euank/go-kmsg-parser v2.0.0+incompatible/go.mod h1:MhmAMZ8V4CYH4ybgdRwPr2TU5ThnS43puaKEMpja1uw= @@ -229,13 +212,16 @@ github.com/exponent-io/jsonpath v0.0.0-20151013193312-d6023ce2651d/go.mod h1:ZZM github.com/fatih/camelcase v1.0.0/go.mod h1:yN2Sb0lFhZJUdVvtELVWefmrXpuZESvPmqwoZc+/fpc= github.com/fatih/color v1.6.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= +github.com/fatih/color v1.18.0 h1:S8gINlzdQ840/4pfAwic/ZE0djQEH3wM94VfqLTZcOM= +github.com/fatih/color v1.18.0/go.mod h1:4FelSpRwEGDpQ12mAdzqdOukCy4u8WUtOY6lkT/6HfU= github.com/fatih/structtag v1.1.0/go.mod h1:mBJUNpUnHmRKrKlQQlmCrh5PuhftFbNv8Ys4/aAZl94= github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g= +github.com/frankban/quicktest v1.11.3/go.mod h1:wRf/ReqHper53s+kmmSZizM8NamnL3IM0I9ntUbOk+k= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= -github.com/fsnotify/fsnotify v1.4.8/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= -github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= +github.com/fsnotify/fsnotify v1.5.1 h1:mZcQUHVQUQWoPXXtuf9yuEXKudkV2sx1E06UadKWpgI= +github.com/fsnotify/fsnotify v1.5.1/go.mod h1:T3375wBYaZdLLcVNkcVbzGHY7f1l/uK5T5Ai1i3InKU= github.com/fsouza/fake-gcs-server v1.7.0/go.mod h1:5XIRs4YvwNbNoz+1JF8j6KLAyDh7RHGAyAK3EP2EsNk= github.com/garyburd/redigo v1.6.0/go.mod h1:NR3MbYisc3/PwhQ00EMzDiPmrwpPxAn5GI05/YaO1SY= github.com/ghodss/yaml v0.0.0-20150909031657-73d445a93680/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= @@ -249,15 +235,14 @@ github.com/globalsign/mgo v0.0.0-20181015135952-eeefdecb41b8/go.mod h1:xkRDCp4j0 github.com/go-acme/lego v2.5.0+incompatible/go.mod h1:yzMNe9CasVUhkquNvti5nAtPmG94USbYxYrZfTkIn0M= github.com/go-bindata/go-bindata v3.1.1+incompatible/go.mod h1:xK8Dsgwmeed+BBsSy2XTopBn/8uK2HWuGSnA11C3Joo= github.com/go-critic/go-critic v0.3.5-0.20190526074819-1df300866540/go.mod h1:+sE8vrLDS2M0pZkBk0wy6+nLdKexVDrl/jBqQOTDThA= -github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU= -github.com/go-gl/glfw/v3.3/glfw v0.0.0-20191125211704-12ad95a8df72/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= -github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-lintpack/lintpack v0.5.2/go.mod h1:NwZuYi2nUHho8XEIZ6SIxihrnPoqBTDqfpXvXAN0sXM= github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE= github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk= github.com/go-logr/logr v0.1.0/go.mod h1:ixOQHD9gLJUVQQ2ZOR7zLEifBX6tGkNJF4QyIY7sIas= +github.com/go-logr/logr v1.4.1 h1:pKouT5E8xu9zeFC39JXRDukb6JFQPXM5p5I91188VAQ= +github.com/go-logr/logr v1.4.1/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= github.com/go-logr/zapr v0.1.0/go.mod h1:tabnROwaDl0UNxkVeFRbY8bwB37GwRv0P8lg6aAiEnk= github.com/go-logr/zapr v0.1.1/go.mod h1:tabnROwaDl0UNxkVeFRbY8bwB37GwRv0P8lg6aAiEnk= github.com/go-ole/go-ole v1.2.1/go.mod h1:7FAglXiTm7HKlQRDeOQ6ZNUHidzCWXuZWq/1dTyBNF8= @@ -273,14 +258,16 @@ github.com/go-openapi/jsonpointer v0.0.0-20160704185906-46af16f9f7b1/go.mod h1:+ github.com/go-openapi/jsonpointer v0.17.0/go.mod h1:cOnomiV+CVVwFLk0A/MExoFMjwdsUdVpsRhURCKh+3M= github.com/go-openapi/jsonpointer v0.18.0/go.mod h1:cOnomiV+CVVwFLk0A/MExoFMjwdsUdVpsRhURCKh+3M= github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg= -github.com/go-openapi/jsonpointer v0.19.3 h1:gihV7YNZK1iK6Tgwwsxo2rJbD1GTbdm72325Bq8FI3w= github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= +github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY= +github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= github.com/go-openapi/jsonreference v0.0.0-20160704190145-13c6e3589ad9/go.mod h1:W3Z9FmVs9qj+KR4zFKmDPGiLdk1D9Rlm7cyMvf57TTg= github.com/go-openapi/jsonreference v0.17.0/go.mod h1:g4xxGn04lDIRh0GJb5QlpE3HfopLOL6uZrK/VgnsK9I= github.com/go-openapi/jsonreference v0.18.0/go.mod h1:g4xxGn04lDIRh0GJb5QlpE3HfopLOL6uZrK/VgnsK9I= github.com/go-openapi/jsonreference v0.19.2/go.mod h1:jMjeRr2HHw6nAVajTXJ4eiUwohSTlpa0o73RUL1owJc= -github.com/go-openapi/jsonreference v0.19.3 h1:5cxNfTy0UVC3X8JL5ymxzyoUZmo8iZb+jeTWn7tUa8o= github.com/go-openapi/jsonreference v0.19.3/go.mod h1:rjx6GuL8TTa9VaixXglHmQmIL98+wF9xc8zWvFonSJ8= +github.com/go-openapi/jsonreference v0.19.6 h1:UBIxjkht+AWIgYzCDSv2GN+E/togfwXUJFRTWhl2Jjs= +github.com/go-openapi/jsonreference v0.19.6/go.mod h1:diGHMEHg2IqXZGKxqyvWdfWU/aim5Dprw5bqpKkTvns= github.com/go-openapi/loads v0.17.0/go.mod h1:72tmFy5wsWx89uEVddd0RjRWPZm92WRLhf7AC+0+OOU= github.com/go-openapi/loads v0.18.0/go.mod h1:72tmFy5wsWx89uEVddd0RjRWPZm92WRLhf7AC+0+OOU= github.com/go-openapi/loads v0.19.0/go.mod h1:72tmFy5wsWx89uEVddd0RjRWPZm92WRLhf7AC+0+OOU= @@ -289,14 +276,8 @@ github.com/go-openapi/loads v0.19.4/go.mod h1:zZVHonKd8DXyxyw4yfnVjPzBjIQcLt0CCs github.com/go-openapi/runtime v0.0.0-20180920151709-4f900dc2ade9/go.mod h1:6v9a6LTXWQCdL8k1AO3cvqx5OtZY/Y9wKTgaoP6YRfA= github.com/go-openapi/runtime v0.19.0/go.mod h1:OwNfisksmmaZse4+gpV3Ne9AyMOlP1lt4sK4FXt0O64= github.com/go-openapi/runtime v0.19.4/go.mod h1:X277bwSUBxVlCYR3r7xgZZGKVvBd/29gLDlFGtJ8NL4= -github.com/go-openapi/spec v0.0.0-20160808142527-6aced65f8501/go.mod h1:J8+jY1nAiCcj+friV/PDoE1/3eeccG9LYBs0tYvLOWc= -github.com/go-openapi/spec v0.17.0/go.mod h1:XkF/MOi14NmjsfZ8VtAKf8pIlbZzyoTvZsdfssdxcBI= -github.com/go-openapi/spec v0.18.0/go.mod h1:XkF/MOi14NmjsfZ8VtAKf8pIlbZzyoTvZsdfssdxcBI= -github.com/go-openapi/spec v0.19.2/go.mod h1:sCxk3jxKgioEJikev4fgkNmwS+3kuYdJtcsZsD5zxMY= -github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo= -github.com/go-openapi/spec v0.19.4/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo= -github.com/go-openapi/spec v0.19.7 h1:0xWSeMd35y5avQAThZR2PkEuqSosoS5t6gDH4L8n11M= -github.com/go-openapi/spec v0.19.7/go.mod h1:Hm2Jr4jv8G1ciIAo+frC/Ft+rR2kQDh8JHKHb3gWUSk= +github.com/go-openapi/spec v0.19.5 h1:Xm0Ao53uqnk9QE/LlYV5DEU09UAgpliA85QoT9LzqPw= +github.com/go-openapi/spec v0.19.5/go.mod h1:Hm2Jr4jv8G1ciIAo+frC/Ft+rR2kQDh8JHKHb3gWUSk= github.com/go-openapi/strfmt v0.17.0/go.mod h1:P82hnJI0CXkErkXi8IKjPbNBM6lV6+5pLP5l494TcyU= github.com/go-openapi/strfmt v0.18.0/go.mod h1:P82hnJI0CXkErkXi8IKjPbNBM6lV6+5pLP5l494TcyU= github.com/go-openapi/strfmt v0.19.0/go.mod h1:+uW+93UVvGGq2qGaZxdDeJqSAqBqBdl+ZPMF/cC8nDY= @@ -307,8 +288,9 @@ github.com/go-openapi/swag v0.18.0/go.mod h1:AByQ+nYG6gQg71GINrmuDXCPWdL640yX49/ github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= github.com/go-openapi/swag v0.19.4/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= -github.com/go-openapi/swag v0.19.9 h1:1IxuqvBUU3S2Bi4YC7tlP9SJF1gVpCvqN0T2Qof4azE= github.com/go-openapi/swag v0.19.9/go.mod h1:ao+8BpOPyKdpQz3AOJfbeEVpLmWAvlT1IfTe5McPyhY= +github.com/go-openapi/swag v0.19.15 h1:D2NRCBzS9/pEY3gP9Nl8aDqGUcPFrwG2p+CNFrLyrCM= +github.com/go-openapi/swag v0.19.15/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= github.com/go-openapi/validate v0.18.0/go.mod h1:Uh4HdOzKt19xGIGm1qHf/ofbX1YQ4Y+MYsct2VUrAJ4= github.com/go-openapi/validate v0.19.2/go.mod h1:1tRCw7m3jtI8eNWEEliiAqUIcBztB2KDnRCRMUi7GTA= github.com/go-openapi/validate v0.19.5/go.mod h1:8DJv2CVJQ6kGNpFW6eV9N3JviE1C85nY1c2z52x1Gk4= @@ -316,7 +298,10 @@ github.com/go-ozzo/ozzo-validation v3.5.0+incompatible/go.mod h1:gsEKFIVnabGBt6m github.com/go-sql-driver/mysql v1.4.0/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= +github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0 h1:p104kn46Q8WdvHunIJ9dAyjPVtrBPhSr3KT2yUst43I= github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0/go.mod h1:fyg7847qk6SyHyPtNmDHnmrv/HOrqktSC+C9fM+CJOE= +github.com/go-task/slim-sprig/v3 v3.0.0 h1:sUs3vkvUymDpBKi3qH1YSqBQk9+9D/8M2mN1vB6EwHI= +github.com/go-task/slim-sprig/v3 v3.0.0/go.mod h1:W848ghGpv3Qj3dhTPRyJypKRiqCdHZiAzKg9hl15HA8= github.com/go-toolsmith/astcast v1.0.0/go.mod h1:mt2OdQTeAQcY4DQgPSArJjHCcOwlX+Wl/kwN+LbLGQ4= github.com/go-toolsmith/astcopy v1.0.0/go.mod h1:vrgyG+5Bxrnz4MZWPF+pI4R8h3qKRjjyvV/DSez4WVQ= github.com/go-toolsmith/astequal v0.0.0-20180903214952-dcb477bfacd6/go.mod h1:H+xSiq0+LtiDC11+h1G32h7Of5O3CYFJ99GVbS5lDKY= @@ -341,6 +326,7 @@ github.com/gobwas/glob v0.2.3/go.mod h1:d3Ez4x06l9bZtSvzIay5+Yzi0fmZzPgnTbPcKjJA github.com/gocql/gocql v0.0.0-20190301043612-f6df8288f9b4/go.mod h1:4Fw1eo5iaEhDUs8XyuhSVCVy52Jq3L+/3GJgYkwc+/0= github.com/godbus/dbus v0.0.0-20181101234600-2ff6f7ffd60f/go.mod h1:/YcGZj5zSblfDWMMoOzV4fas9FZnQYTkDnsGvmh2Grw= github.com/godbus/dbus v4.1.0+incompatible/go.mod h1:/YcGZj5zSblfDWMMoOzV4fas9FZnQYTkDnsGvmh2Grw= +github.com/godbus/dbus/v5 v5.0.3/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= github.com/gofrs/flock v0.7.1/go.mod h1:F1TvTiK9OcQqauNUHlbJvyl9Qa1QvF/gOUDKA14jxHU= github.com/gofrs/uuid v3.2.0+incompatible/go.mod h1:b2aQJv3Z4Fp6yNu3cdSllBxTCLRxnplIgP/c0N/04lM= github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= @@ -348,32 +334,26 @@ github.com/gogo/protobuf v1.2.0/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7a github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4= github.com/gogo/protobuf v1.2.2-0.20190723190241-65acae22fc9d/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= github.com/gogo/protobuf v1.2.2-0.20190730201129-28a6bbf47e48/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= -github.com/gogo/protobuf v1.3.1 h1:DqDEcV5aeaTmdFBePNpYsp3FlcVH/2ISVVM9Qf8PSls= github.com/gogo/protobuf v1.3.1/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= +github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q= +github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q= +github.com/golang-jwt/jwt v3.2.2+incompatible h1:IfV12K8xAKAnZqdXVzCZ+TOjboZ2keLg81eXfW3O+oY= +github.com/golang-jwt/jwt v3.2.2+incompatible/go.mod h1:8pz2t5EyA70fFQQSrl6XZXzqecmYZeUEB8OUGHkxJ+I= github.com/golang-migrate/migrate/v4 v4.6.2/go.mod h1:JYi6reN3+Z734VZ0akNuyOJNcrg45ZL7LDBMW3WGJL0= github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q= github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= -github.com/golang/groupcache v0.0.0-20180513044358-24b0969c4cb7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20181024230925-c65c006176ff/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20190129154638-5b532d6fd5ef/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= -github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20191027212112-611e8accdfc9/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= -github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= -github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:tluoj9z5200jBnyusfRPU2LqT6J+DAorxEvtC7LHB+E= github.com/golang/mock v1.0.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= github.com/golang/mock v1.2.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= github.com/golang/mock v1.3.1/go.mod h1:sBzyDLLjw3U8JLTeZvSv8jJB+tU5PVekmnlKIyFUx0Y= -github.com/golang/mock v1.4.0/go.mod h1:UOMv5ysSaYNkG+OFQykRIcU/QvvxJf3p21QfJ2Bt3cw= -github.com/golang/mock v1.4.1/go.mod h1:UOMv5ysSaYNkG+OFQykRIcU/QvvxJf3p21QfJ2Bt3cw= -github.com/golang/protobuf v0.0.0-20161109072736-4bd1920723d7/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= -github.com/golang/protobuf v1.0.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.3.1/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.3.3/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= -github.com/golang/protobuf v1.3.4/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8= github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA= github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs= @@ -382,8 +362,9 @@ github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvq github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= -github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw= github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= +github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek= +github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps= github.com/golang/snappy v0.0.0-20170215233205-553a64147049/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= github.com/golang/snappy v0.0.1/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q= @@ -417,33 +398,29 @@ github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMyw github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.4/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= +github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= github.com/google/go-github v17.0.0+incompatible/go.mod h1:zLgOLi98H3fifZn+44m+umXrS52loVEgC2AApnigrVQ= github.com/google/go-querystring v1.0.0/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck= -github.com/google/gofuzz v0.0.0-20161122191042-44d81051d367/go.mod h1:HP5RmnzzSNb993RKQDq4+1A4ia9nllfqcQFTQJedwGI= github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= -github.com/google/gofuzz v1.1.0 h1:Hsa8mG0dQ46ij8Sl2AYJDUv1oA9/d6Vk+3LG99Oe02g= github.com/google/gofuzz v1.1.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= +github.com/google/gofuzz v1.2.0 h1:xRy4A+RhZaiKjJ1bPfwQ8sedCA+YS2YcCHW6ec7JMi0= +github.com/google/gofuzz v1.2.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= github.com/google/pprof v0.0.0-20181206194817-3ea8567a2e57/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc= -github.com/google/pprof v0.0.0-20190515194954-54271f7e092f/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc= -github.com/google/pprof v0.0.0-20191218002539-d4f498aebedc/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= -github.com/google/pprof v0.0.0-20200212024743-f11f1df84d12/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= -github.com/google/pprof v0.0.0-20200229191704-1ebb73c60ed3/go.mod h1:ZgVRPoUq/hfqzAqh7sHMqb3I9Rq5C59dIz2SbBwJ4eM= +github.com/google/pprof v0.0.0-20240424215950-a892ee059fd6 h1:k7nVchz72niMH6YLQNvHSdIE7iqsQxK1P41mySCvssg= +github.com/google/pprof v0.0.0-20240424215950-a892ee059fd6/go.mod h1:kf6iHlnVGwgKolg33glAes7Yg/8iWP8ukqeldJSO7jw= github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510/go.mod h1:pupxD2MaaD3pAXIBCelhxNneeOaAeabZDe5s4K6zSpQ= github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= +github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= -github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= -github.com/googleapis/gnostic v0.0.0-20170729233727-0c5108395e2d/go.mod h1:sJBsCZ4ayReDTBIg8b9dl28c5xFWyhBTVRp3pOg5EKY= -github.com/googleapis/gnostic v0.2.0/go.mod h1:sJBsCZ4ayReDTBIg8b9dl28c5xFWyhBTVRp3pOg5EKY= -github.com/googleapis/gnostic v0.3.0/go.mod h1:sJBsCZ4ayReDTBIg8b9dl28c5xFWyhBTVRp3pOg5EKY= github.com/googleapis/gnostic v0.3.1 h1:WeAefnSUHlBb0iJKwxFDZdbfGwkd7xRNuV+IpXMJhYk= github.com/googleapis/gnostic v0.3.1/go.mod h1:on+2t9HRStVgn95RSsFWFz+6Q0Snyqv1awfrALZdbtU= -github.com/googleapis/gnostic v0.4.0 h1:BXDUo8p/DaxC+4FJY/SSx3gvnx9C1VdHNgaUkiEL5mk= -github.com/googleapis/gnostic v0.4.0/go.mod h1:on+2t9HRStVgn95RSsFWFz+6Q0Snyqv1awfrALZdbtU= github.com/gophercloud/gophercloud v0.1.0/go.mod h1:vxM41WHh5uqHVBMZHzuwNOHh8XEoIEcSTewFxm1c5g8= github.com/gophercloud/gophercloud v0.2.0/go.mod h1:vxM41WHh5uqHVBMZHzuwNOHh8XEoIEcSTewFxm1c5g8= github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY= @@ -492,7 +469,6 @@ github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpO github.com/huandu/xstrings v1.2.0/go.mod h1:DvyZB1rfVYsBIigL8HwpZgxHwXozlTgGqn63UyNX5k4= github.com/huandu/xstrings v1.3.1/go.mod h1:y5/lhBue+AyNmUVz9RLU9xbLR0o4KIIExikq4ovT0aE= github.com/iancoleman/strcase v0.0.0-20190422225806-e506e3ef7365/go.mod h1:SK73tn/9oHe+/Y0h39VT4UCxmurVJkR5NA7kMEAOgSE= -github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= github.com/imdario/mergo v0.3.5/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= github.com/imdario/mergo v0.3.6/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= github.com/imdario/mergo v0.3.7/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJh5FfA= @@ -512,16 +488,17 @@ github.com/jmoiron/sqlx v1.2.0/go.mod h1:1FEQNm3xlJgrMD+FBdI9+xvCksHtbpVBBw5dYhB github.com/joefitzgerald/rainbow-reporter v0.1.0/go.mod h1:481CNgqmVHQZzdIbN52CupLJyoVwB10FQ/IQlF1pdL8= github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg= github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo= +github.com/josharian/intern v1.0.0 h1:vlS4z54oSdjm0bgjRigI+G1HpF+tI+9rE5LLzOg8HmY= +github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y= github.com/jpillora/go-ogle-analytics v0.0.0-20161213085824-14b04e0594ef/go.mod h1:PlwhC7q1VSK73InDzdDatVetQrTsQHIbOvcJAZzitY0= -github.com/json-iterator/go v0.0.0-20180612202835-f2b4162afba3/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= github.com/json-iterator/go v1.1.7/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.8/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= -github.com/json-iterator/go v1.1.9 h1:9yzud/Ht36ygwatGx56VwCZtlI/2AD15T1X2sjSuGns= github.com/json-iterator/go v1.1.9/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= +github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= +github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/jsonnet-bundler/jsonnet-bundler v0.1.0/go.mod h1:YKsSFc9VFhhLITkJS3X2PrRqWG9u2Jq99udTdDjQLfM= github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU= -github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/XSXhF0NWZEnDohbsk= github.com/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU= github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= github.com/kardianos/osext v0.0.0-20170510131534-ae77be60afb1/go.mod h1:1NbS8ALrpOvjt0rHPNLyCIeMtbizbir8U//inJ+zuB8= @@ -530,6 +507,7 @@ github.com/karrick/godirwalk v1.7.5/go.mod h1:2c9FRhkDxdIbgkOnCEvnSWs71Bhugbl46s github.com/karrick/godirwalk v1.10.12/go.mod h1:RoGL9dQei4vP9ilrpETWE8CLOZ1kiN0LhBygSwrAsHA= github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q= github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00= +github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= github.com/kisielk/gotool v0.0.0-20161130080628-0de1eaf82fa3/go.mod h1:jxZFDH7ILpTPQTk+E2s+z4CUas9lVNjIuKR4c5/zKgM= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/klauspost/compress v1.4.0/go.mod h1:RyIbtBH6LamlWaDj8nUwkbUhJ87Yi3uG0guNDohfE1A= @@ -540,13 +518,14 @@ github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxv github.com/konsorten/go-windows-terminal-sequences v1.0.2/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= -github.com/kr/pretty v0.2.0 h1:s5hAObm+yFO5uHYt5dYjxi2rXrsnmRpJx4OYvIWUaQs= -github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pretty v0.3.1 h1:flRD4NNwYAUpkphVc1HcthR4KEIFJ65n8Mw5qdRn3LE= +github.com/kr/pretty v0.3.1/go.mod h1:hoEshYVHaxMs3cyo3Yncou5ZscifuDolrwPKZanG3xk= github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= github.com/kr/pty v1.1.3/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= -github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA= -github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= +github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= +github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= github.com/kshvakov/clickhouse v1.3.5/go.mod h1:DMzX7FxRymoNkVgizH0DWAL8Cur7wHLgx3MUnGwJqpE= github.com/kylelemons/godebug v0.0.0-20170820004349-d65d576e9348/go.mod h1:B69LEHPfb2qLo0BaaOLcbitczOKLWTsrBG9LczfCD4k= github.com/kyokomi/emoji v2.2.4+incompatible/go.mod h1:mZ6aGCD7yk8j6QY6KICwnZ2pxoszVseX1DNoGtU2tBA= @@ -555,16 +534,15 @@ github.com/lib/pq v1.2.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= github.com/libopenstorage/openstorage v1.0.0/go.mod h1:Sp1sIObHjat1BeXhfMqLZ14wnOzEhNx2YQedreMcUyc= github.com/liggitt/tabwriter v0.0.0-20181228230101-89fcab3d43de/go.mod h1:zAbeS9B/r2mtpb6U+EI2rYA5OAXxsYw6wTamcNW+zcE= github.com/lithammer/dedent v1.1.0/go.mod h1:jrXYCQtgg0nJiN+StA2KgR7w6CiQNv9Fd/Z9BP0jIOc= -github.com/litmuschaos/chaos-operator v0.0.0-20210325093226-50a357ad2256/go.mod h1:Z2GpYjqXwFd8bx+kv58YEQFxynx1v9PMGCGTQFRVnFQ= -github.com/litmuschaos/chaos-operator v0.0.0-20210412053502-dd484bbadfb9/go.mod h1:Z2GpYjqXwFd8bx+kv58YEQFxynx1v9PMGCGTQFRVnFQ= -github.com/litmuschaos/chaos-operator v0.0.0-20210430184607-cb675e58922d h1:adUehke01xRj7kixQd8Kknnjl2zUOLr6W8w0A3C90ME= -github.com/litmuschaos/chaos-operator v0.0.0-20210430184607-cb675e58922d/go.mod h1:QMjfAVIfwcpj/P1jikyz5+C5vWICiUXsFZMR7Ihnzro= +github.com/litmuschaos/chaos-operator v0.0.0-20210610071657-a58dbd939e73 h1:waXMmW5R0irh0gTSCMmXfYvEZ5cwaeMGulAwKp0zpFU= +github.com/litmuschaos/chaos-operator v0.0.0-20210610071657-a58dbd939e73/go.mod h1:QMjfAVIfwcpj/P1jikyz5+C5vWICiUXsFZMR7Ihnzro= github.com/litmuschaos/elves v0.0.0-20201107015738-552d74669e3c/go.mod h1:DsbHGNUq/78NZozWVVI9Q6eBei4I+JjlkkD5aibJ3MQ= -github.com/litmuschaos/litmus-e2e v0.0.0-20210713061120-32af01dc2757 h1:MdNv9zAyIp8T3EMpQLdyxh3ONtZKaQM91KZ7q0WTXtY= -github.com/litmuschaos/litmus-e2e v0.0.0-20210713061120-32af01dc2757/go.mod h1:Ka9QB0DJUha4yFNf/e/AYA4zWLm/s1IwLJ+soGWOGTU= -github.com/litmuschaos/litmus-go v0.0.0-20210415042401-c79b9ea0fdd2/go.mod h1:+K6BVCWcJkusItjR9xuR+B/nQYJN94V140tXsfx3WAs= -github.com/litmuschaos/litmus-go v0.0.0-20210430161537-788b26f5b445 h1:N4TQ+bVwsQvOrrlaGmxEy0M28saGXdKaP0Eetn7zpLw= -github.com/litmuschaos/litmus-go v0.0.0-20210430161537-788b26f5b445/go.mod h1:gfeCtlRJwr/zw81paU/DmyC7VSLYj1QJT5BhNmjcWNw= +github.com/litmuschaos/litmus-go v0.0.0-20210705063441-babf0c4aa57d h1:QCIy9qxYtAQ6XoI5o935yKbulaVswl6X5lGQire2bwQ= +github.com/litmuschaos/litmus-go v0.0.0-20210705063441-babf0c4aa57d/go.mod h1:MNO+1u4jBPjLtFO56bckIv87EhwTkppJxDf8+6PbLRY= +github.com/litmuschaos/litmus-go-sdk v0.0.0-20250513045254-3a81cc911979 h1:hx4q3qS1B2eXeQoO76GcVe4qNL7XHGMEFrdhv6+hQ70= +github.com/litmuschaos/litmus-go-sdk v0.0.0-20250513045254-3a81cc911979/go.mod h1:f93Jf8U6NTm8WtQKo0c/koK/9EbIJgbkJOkCQxpR4j0= +github.com/litmuschaos/litmus/chaoscenter/graphql/server v0.0.0-20250317093827-172c4b9ffb24 h1:y5XvMZkwPBjUlbjheYNHX8XkHdf6VBrZ6QKxmLm0dCQ= +github.com/litmuschaos/litmus/chaoscenter/graphql/server v0.0.0-20250317093827-172c4b9ffb24/go.mod h1:/5E4at+TglA7QAUlMVzKmCyj03pohORGCDSKeIZmXyA= github.com/logrusorgru/aurora v0.0.0-20181002194514-a7b3b318ed4e/go.mod h1:7rIyQOR62GCctdiQpZ/zOJlFyk6y+94wXzv6RNZgaR4= github.com/lpabon/godbc v0.1.1/go.mod h1:Jo9QV0cf3U6jZABgiJ2skINAXb9j8m51r07g4KI92ZA= github.com/lucas-clemente/aes12 v0.0.0-20171027163421-cd47fb39b79f/go.mod h1:JpH9J1c9oX6otFSgdUHwUBUizmKlrMjxWnIAjff4m04= @@ -580,8 +558,10 @@ github.com/mailru/easyjson v0.0.0-20190312143242-1de009706dbe/go.mod h1:C1wdFJiN github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs= -github.com/mailru/easyjson v0.7.1 h1:mdxE1MF9o53iCb2Ghj1VfWvh7ZOwHpnVG/xwXrV90U8= github.com/mailru/easyjson v0.7.1/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs= +github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= +github.com/mailru/easyjson v0.7.7 h1:UGYAvKxe3sBsEDzO8ZeWOSlIQfWFlxbzLZe7hwFURr0= +github.com/mailru/easyjson v0.7.7/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= github.com/maorfr/helm-plugin-utils v0.0.0-20181205064038-588190cb5e3b/go.mod h1:p3gwmRSFqbWw6plBpR0sKl3n3vpu8kX70gvCJKMvvCA= github.com/markbates/inflect v1.0.4/go.mod h1:1fR9+pO2KHEO9ZRtto13gDwwZaAKstQzferVeWqbgNs= github.com/marten-seemann/qtls v0.2.3/go.mod h1:xzjG7avBwGGbdZ8dTGxlBnLArsVKLvwmjgmPuiQEcYk= @@ -589,11 +569,16 @@ github.com/martinlindhe/base36 v1.0.0/go.mod h1:+AtEs8xrBpCeYgSLoY/aJ6Wf37jtBuR0 github.com/mattbaird/jsonpatch v0.0.0-20171005235357-81af80346b1a/go.mod h1:M1qoD/MqPgTZIk0EWKB38wE28ACRfVcn+cU08jyArI0= github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= +github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA= +github.com/mattn/go-colorable v0.1.13/go.mod h1:7S9/ev0klgBDR4GtXTXX8a3vIGJpMovkB8vQcUbaXHg= github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-isatty v0.0.6/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-isatty v0.0.9/go.mod h1:YNRxwqDuOph6SZLI9vUUz6OYw3QyUt7WiY2yME+cCiQ= +github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM= +github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= +github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= github.com/mattn/go-runewidth v0.0.4/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= github.com/mattn/go-shellwords v1.0.5/go.mod h1:3xCvwCdWdlDJUrvuMn7Wuy9eWs4pE8vqg+NOMyg4B2o= @@ -625,10 +610,10 @@ github.com/moby/moby v0.7.3-0.20190826074503-38ab9da00309/go.mod h1:fDXVQ6+S340v github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/reflect2 v0.0.0-20180320133207-05fbef0ca5da/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= github.com/modern-go/reflect2 v0.0.0-20180701023420-4b7aa43c6742/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= -github.com/modern-go/reflect2 v1.0.1 h1:9f412s+6RmYXLWZSEzVVgPGK7C2PphHj5RJrvfx9AWI= github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3RllmbCylyMrvgv0= +github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= +github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= github.com/mohae/deepcopy v0.0.0-20170603005431-491d3605edfb/go.mod h1:TaXosZuwdSHYgviHp1DAtfrULt5eUgsSMsZf+YrPgl8= github.com/morikuni/aec v0.0.0-20170113033406-39771216ff4c/go.mod h1:BbKIizmSmc5MMPqRYbxO4ZU0S0+P200+tUnFx7PXmsc= github.com/mozilla/tls-observatory v0.0.0-20180409132520-8791a200eb40/go.mod h1:SrKMQvPiws7F7iqYp8/TX+IhxCYhzr6N/1yb8cwHsGk= @@ -645,6 +630,7 @@ github.com/naoina/go-stringutil v0.1.0/go.mod h1:XJ2SJL9jCtBh+P9q5btrd/Ylo8XwT/h github.com/naoina/toml v0.1.1/go.mod h1:NBIhNtsFMo3G2szEBne+bO4gS192HuIYRqfvOWb4i1E= github.com/nbutton23/zxcvbn-go v0.0.0-20160627004424-a22cb81b2ecd/go.mod h1:o96djdrsSGy3AWPyBgZMAGfxZNfgntdJG+11KU4QvbU= github.com/nbutton23/zxcvbn-go v0.0.0-20171102151520-eafdab6b0663/go.mod h1:o96djdrsSGy3AWPyBgZMAGfxZNfgntdJG+11KU4QvbU= +github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI8A= github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE= github.com/nxadm/tail v1.4.8/go.mod h1:+ncqLTQzXmGhMZNUePPaPqPvBxHAIsmXswZKocGu+AU= @@ -652,35 +638,37 @@ github.com/oklog/run v1.0.0/go.mod h1:dlhp/R75TPv97u0XWUtDeV/lRKWPKSdTuV0TZvrmrQ github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U= github.com/olekukonko/tablewriter v0.0.0-20170122224234-a0225b3f23b5/go.mod h1:vsDQFd/mU46D+Z4whnwzcISnGGzXWMclvtLoiIKAKIo= github.com/onsi/ginkgo v0.0.0-20170829012221-11459a886d9c/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= -github.com/onsi/ginkgo v1.4.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.8.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.10.1/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= +github.com/onsi/ginkgo v1.11.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.12.0/go.mod h1:oUhWkIvk5aDxtKvDDuw8gItl8pKl42LzjC9KZE0HfGg= github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk= -github.com/onsi/ginkgo v1.16.2 h1:HFB2fbVIlhIfCfOW81bZFbiC/RvnpXSdhbF2/DJr134= -github.com/onsi/ginkgo v1.16.2/go.mod h1:CObGmKUOKaSC0RjmoAK7tKyn4Azo5P2IWuoMnvwxz1E= +github.com/onsi/ginkgo v1.16.5 h1:8xi0RTUf59SOSfEtZMvwTvXYMzG4gV23XVHOZiXNtnE= +github.com/onsi/ginkgo v1.16.5/go.mod h1:+E8gABHa3K6zRBolWtd+ROzc/U5bkGt0FwiG042wbpU= +github.com/onsi/ginkgo/v2 v2.19.0 h1:9Cnnf7UHo57Hy3k6/m5k3dRfGTMXGvxhHFvkDTCTpvA= +github.com/onsi/ginkgo/v2 v2.19.0/go.mod h1:rlwLi9PilAFJ8jCg9UE1QP6VBpd6/xj3SRC0d6TU0To= github.com/onsi/gomega v0.0.0-20170829124025-dcabb60a477c/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA= -github.com/onsi/gomega v1.3.0/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA= github.com/onsi/gomega v1.4.2/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= github.com/onsi/gomega v1.5.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= github.com/onsi/gomega v1.7.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY= +github.com/onsi/gomega v1.8.1/go.mod h1:Ho0h+IUsWyvy1OpqCwxlQ/21gkhVunqlU8fDGcoTdcA= github.com/onsi/gomega v1.9.0/go.mod h1:Ho0h+IUsWyvy1OpqCwxlQ/21gkhVunqlU8fDGcoTdcA= github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo= -github.com/onsi/gomega v1.12.0 h1:p4oGGk2M2UJc0wWN4lHFvIB71lxsh0T/UiKCCgFADY8= -github.com/onsi/gomega v1.12.0/go.mod h1:lRk9szgn8TxENtWd0Tp4c3wjlRfMTMH27I+3Je41yGY= +github.com/onsi/gomega v1.34.1 h1:EUMJIKUjM8sKjYbtxQI9A4z2o+rruxnzNvpknOXie6k= +github.com/onsi/gomega v1.34.1/go.mod h1:kU1QgUvBDLXBJq618Xvm2LUX6rSAfRaFRTcdOeDLwwY= github.com/opencontainers/go-digest v1.0.0-rc1/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s= github.com/opencontainers/image-spec v1.0.1/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= github.com/opencontainers/runc v0.1.1/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= github.com/opencontainers/runc v1.0.0-rc2.0.20190611121236-6cc515888830/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= github.com/opencontainers/runc v1.0.0-rc9/go.mod h1:qT5XzbpPznkRYVz/mWwUaVBUv2rmF59PVA73FjuZG0U= github.com/opencontainers/runtime-spec v1.0.0/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= +github.com/opencontainers/runtime-spec v1.0.2/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0= github.com/opencontainers/selinux v1.2.2/go.mod h1:+BLncwf63G4dgOzykXAxcmnFlUaOlkDdmw/CqsW6pjs= github.com/opencontainers/selinux v1.3.1-0.20190929122143-5215b1806f52/go.mod h1:+BLncwf63G4dgOzykXAxcmnFlUaOlkDdmw/CqsW6pjs= -github.com/openebs/maya v0.0.0-20200411140727-1c81f9e017b0/go.mod h1:QQY9cOHKQwZ73qbv6O//UYUBLNV2S0MRDIfG7t5KOCk= github.com/openebs/maya v1.12.1/go.mod h1:E9CmKbURtsthTyASz0piTxljLmGxjbaJ3aFhtWEko2Y= github.com/openshift/api v3.9.1-0.20190924102528-32369d4db2ad+incompatible/go.mod h1:dh9o4Fs58gpFXGSYfnVxGR9PnV53I8TW84pQaJDdGiY= github.com/openshift/client-go v0.0.0-20190923180330-3b6373338c9b/go.mod h1:6rzn+JTr7+WYS2E1TExP4gByoABxMznR6y2SnUIkmxk= @@ -706,11 +694,11 @@ github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/9 github.com/peterbourgon/diskv v2.0.1+incompatible/go.mod h1:uqqh8zWWbv1HBMNONnaR/tNboyR3/BZd58JJSHlUSCU= github.com/phayes/freeport v0.0.0-20171002181615-b8543db493a5/go.mod h1:iIss55rKnNBTvrwdmkUpLnDpZoAHvWaiq5+iMmen4AE= github.com/pierrec/lz4 v2.0.5+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY= +github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA= github.com/pkg/errors v0.8.0/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= -github.com/pmezard/go-difflib v0.0.0-20151028094244-d8ed2627bdf0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pquerna/cachecontrol v0.0.0-20171018203845-0dec1b30a021/go.mod h1:prYjPmNq4d1NPVmpShWobRqXY3q7Vp+80DqgxxUrUIA= @@ -726,6 +714,7 @@ github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1: github.com/prometheus/client_model v0.0.0-20190115171406-56726106282f/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/common v0.0.0-20181113130724-41aa239b4cce/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro= github.com/prometheus/common v0.0.0-20181126121408-4724e9255275/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro= github.com/prometheus/common v0.2.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= @@ -738,7 +727,6 @@ github.com/prometheus/procfs v0.0.0-20181204211112-1dc9a6cbc91a/go.mod h1:c3At6R github.com/prometheus/procfs v0.0.0-20190117184657-bf6a532e95b1/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= github.com/prometheus/procfs v0.0.0-20190129233650-316cf8ccfec5/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= -github.com/prometheus/procfs v0.0.0-20190522114515-bc1a522cf7b1/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.0.2/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.0.3/go.mod h1:4A/X28fw3Fc593LaREMrKMqOKvUAntwMDaekg4FpcdQ= github.com/prometheus/procfs v0.0.5/go.mod h1:4A/X28fw3Fc593LaREMrKMqOKvUAntwMDaekg4FpcdQ= @@ -755,6 +743,9 @@ github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6So github.com/rogpeppe/go-internal v1.1.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4= github.com/rogpeppe/go-internal v1.5.0/go.mod h1:xXDCJY+GAPziupqXw64V24skbSoqbTEfhy4qGm1nDQc= +github.com/rogpeppe/go-internal v1.9.0/go.mod h1:WtVeX8xhTBvf0smdhujwtBcq4Qrzq/fJaraNFVN+nFs= +github.com/rogpeppe/go-internal v1.11.0 h1:cWPaGQEPrBb5/AsnsZesgZZ9yb1OQ+GOISoDNXVBh4M= +github.com/rogpeppe/go-internal v1.11.0/go.mod h1:ddIwULY96R17DhadqLgMfk9H9tvdUzkipdSkR5nkCZA= github.com/rubenv/sql-migrate v0.0.0-20191025130928-9355dd04f4b3/go.mod h1:WS0rl9eEliYI8DPnr3TOwz4439pay+qNgzJoVya/DmY= github.com/rubiojr/go-vhd v0.0.0-20160810183302-0bfd3b39853c/go.mod h1:DM5xW0nvfNNm2uytzsvhI3OnX8uzaRAg8UX/CnDqbto= github.com/russross/blackfriday v0.0.0-20170610170232-067529f716f4/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g= @@ -777,8 +768,9 @@ github.com/sirupsen/logrus v1.0.6/go.mod h1:pMByvHTf9Beacp5x1UXfOR9xyW/9antXMhjM github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= github.com/sirupsen/logrus v1.4.1/go.mod h1:ni0Sbl8bgC9z8RoU9G6nDWqqs/fq4eDPysMBDgk/93Q= github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE= -github.com/sirupsen/logrus v1.7.0 h1:ShrD1U9pZB12TX0cVy0DtePoCH97K8EtX+mg7ZARUtM= github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= +github.com/sirupsen/logrus v1.9.3 h1:dueUQJ1C2q9oE3F7wvmSGAaVtTmUizReu6fjN8uqzbQ= +github.com/sirupsen/logrus v1.9.3/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ= github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc= github.com/smartystreets/goconvey v0.0.0-20190330032615-68dc04aab96a/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= github.com/soheilhy/cmux v0.1.3/go.mod h1:IM3LyeVVIOuxMH7sFAkER9+bJ4dT7Ms6E4xg4kGIyLM= @@ -809,12 +801,14 @@ github.com/storageos/go-api v0.0.0-20180912212459-343b3eff91fc/go.mod h1:ZrLn+e0 github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE= -github.com/stretchr/testify v0.0.0-20151208002404-e3a8ff8ce365/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= -github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.10.0 h1:Xv5erBjTwe/5IxqUQTdXv5kgmIvbHo3QQyRwhJsOfJA= +github.com/stretchr/testify v1.10.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= github.com/syndtr/gocapability v0.0.0-20160928074757-e7cb7fa329f4/go.mod h1:hkRG7XYTFWNJGYcbNJQlaLq0fg1yr4J4t/NcTQtrfww= github.com/syndtr/gocapability v0.0.0-20180916011248-d98352740cb2/go.mod h1:hkRG7XYTFWNJGYcbNJQlaLq0fg1yr4J4t/NcTQtrfww= github.com/tarm/serial v0.0.0-20180830185346-98f6abe2eb07/go.mod h1:kDXzergiv9cbyO7IOYJZWg1U88JhDg3PB6klq9Hg2pA= @@ -829,6 +823,7 @@ github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljT github.com/ultraware/funlen v0.0.1/go.mod h1:Dp4UiAus7Wdb9KUZsYWZEWiRzGuM2kXM1lPbfaF6xhA= github.com/ultraware/funlen v0.0.2/go.mod h1:Dp4UiAus7Wdb9KUZsYWZEWiRzGuM2kXM1lPbfaF6xhA= github.com/urfave/cli v1.20.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA= +github.com/urfave/cli v1.22.2/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= github.com/urfave/negroni v1.0.0/go.mod h1:Meg73S6kFm/4PpbYdq35yYWoCZ9mS/YSx+lKnmiohz4= github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc= github.com/valyala/fasthttp v1.2.0/go.mod h1:4vX61m6KN+xDduDNwXrhIAVZaZaZiQ1luJk8LWSxF3s= @@ -852,7 +847,9 @@ github.com/xiang90/probing v0.0.0-20160813154853-07dd2e8dfe18/go.mod h1:UETIi67q github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2/go.mod h1:UETIi67q53MR2AWcXfiuqkDkRtnGDLqkBTpCHuJHxtU= github.com/xlab/handysort v0.0.0-20150421192137-fb3537ed64a1/go.mod h1:QcJo0QPSfTONNIgpN5RA8prR7fF8nkF6cTWTcNerRO8= github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q= +github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= +github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= github.com/yvasiyarov/go-metrics v0.0.0-20150112132944-c25f46c4b940/go.mod h1:aX5oPXxHm3bOH+xeAttToC8pqch2ScQN/JoXYupl6xs= github.com/yvasiyarov/gorelic v0.0.6/go.mod h1:NUSPSUX/bi6SeDMUh6brw0nXpxHnc96TguQh0+r/ssA= github.com/yvasiyarov/newrelic_platform_go v0.0.0-20140908184405-b21fdbd4370f/go.mod h1:GlGEuHIJweS1mbCqG+7vt2nvWLzLLnRHbXz5JKd/Qbg= @@ -867,9 +864,6 @@ go.mongodb.org/mongo-driver v1.1.1/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qL go.mongodb.org/mongo-driver v1.1.2/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM= go.opencensus.io v0.20.1/go.mod h1:6WKK9ahsWS3RSO+PY9ZHZUfv2irvY6gN279GOPZjmmk= go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU= -go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8= -go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= -go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= go.uber.org/atomic v0.0.0-20181018215023-8dc6146f7569/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= @@ -879,7 +873,6 @@ go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/ go.uber.org/multierr v1.3.0/go.mod h1:VgVr7evmIr6uPjLBxg28wmKNXyqE9akIJ5XnfpiKl+4= go.uber.org/tools v0.0.0-20190618225709-2cfd321de3ee/go.mod h1:vJERXedbb3MVM5f9Ejo0C68/HhF8uaILCdgjnY+goOA= go.uber.org/zap v0.0.0-20180814183419-67bc79d13d15/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= -go.uber.org/zap v1.9.1/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= go.uber.org/zap v1.13.0/go.mod h1:zwrFLgMcdUuIBviXEYEH1YKNaOBnKXsx2IPda5bBwHM= go4.org v0.0.0-20180809161055-417644f6feb5/go.mod h1:MkTOUMDaeVYJUOUsaDXIhWPZYa1yOyC1qaOBpL57BhE= @@ -897,7 +890,6 @@ golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACk golang.org/x/crypto v0.0.0-20190424203555-c05e17bb3b2d/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190426145343-a29dc8fdc734/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= -golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190611184440-5c40567a22f8/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190617133340-57b3e21c3d56/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190621222207-cc06ce4a13d4/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= @@ -905,44 +897,29 @@ golang.org/x/crypto v0.0.0-20190820162420-60c769a6c586/go.mod h1:yigFU9vqHzYiE8U golang.org/x/crypto v0.0.0-20190911031432-227b76d455e7/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20191028145041-f83a4685e152/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9 h1:psW17arqaxU48Z5kZ0CQnkZWQJsqcURM6tKiBApRjXI= golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= +golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/crypto v0.31.0 h1:ihbySMvVjLAeSH1IbfcRTkD/iNscyz8rGzjF/E5hV6U= +golang.org/x/crypto v0.31.0/go.mod h1:kDsLvtWBEx7MV9tJOj9bnXsPbxwJQ6csT/x4KIN4Ssk= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190125153040-c74c464bbbf2/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= -golang.org/x/exp v0.0.0-20190306152737-a1d7652674e8/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190312203227-4b39c73a6495/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8= -golang.org/x/exp v0.0.0-20190510132918-efd6b22b2522/go.mod h1:ZjyILWgesfNpC6sMxTJOJm9Kp84zZh5NQWvqDGG3Qr8= -golang.org/x/exp v0.0.0-20190829153037-c13cbed26979/go.mod h1:86+5VVa7VpoJ4kLfm080zCjGlMRFzhUhsZKEZO7MGek= -golang.org/x/exp v0.0.0-20191030013958-a1ab85dbe136/go.mod h1:JXzH8nQsPlswgeRAPE3MuO9GYsAcnJvJ4vnMwN/5qkY= -golang.org/x/exp v0.0.0-20191129062945-2f5052295587/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= -golang.org/x/exp v0.0.0-20191227195350-da58074b4299/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= -golang.org/x/exp v0.0.0-20200119233911-0405dc783f0a/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4= -golang.org/x/exp v0.0.0-20200207192155-f17229e696bd/go.mod h1:J/WKrq2StrnmMY6+EHIKF9dgMWnmCNThgcyBT1FY9mM= -golang.org/x/exp v0.0.0-20200224162631-6cc2880d07d6/go.mod h1:3jZMyOhIsHpP37uCMkUooju7aAi5cS1Q23tOzKc+0MU= +golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56 h1:2dVuKD2vS7b0QIHQbpyTISPd0LeHDbnYEryqj5Q1ug8= +golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56/go.mod h1:M4RDyNAINzryxdtnbRXRL/OHtkFuWGRjvuhBJpk2IlY= golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js= -golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= golang.org/x/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= golang.org/x/lint v0.0.0-20190301231843-5614ed5bae6f/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= golang.org/x/lint v0.0.0-20190409202823-959b441ac422/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= -golang.org/x/lint v0.0.0-20190909230951-414d861bb4ac/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= golang.org/x/lint v0.0.0-20190930215403-16217165b5de/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= -golang.org/x/lint v0.0.0-20191125180803-fdd1cda4f05f/go.mod h1:5qLYkcX4OjUUV8bRuDixDT3tpyyb+LUpUlRWLxfhWrs= -golang.org/x/lint v0.0.0-20200130185559-910be7a94367/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= -golang.org/x/lint v0.0.0-20200302205851-738671d3881b/go.mod h1:3xt1FjdF8hUf6vQPIChWIBhFzV8gjjsPE/fR3IyQdNY= golang.org/x/mobile v0.0.0-20190312151609-d3739f865fa6/go.mod h1:z+o9i4GpDbdi3rU15maQ/Ox0txvL9dWGYEHz965HBQE= -golang.org/x/mobile v0.0.0-20190719004257-d2bd2a29d028/go.mod h1:E/iHnbuqvinMTCcRqshq8CkpyQDoeVncDDYHnLhea+o= golang.org/x/mod v0.0.0-20190513183733-4bf6d317e70e/go.mod h1:mXi4GBBbnImb6dmsKGUJ2LatrhH/nqhxcFungHvyanc= -golang.org/x/mod v0.1.0/go.mod h1:0QHyrYULN0/3qlju5TqG8bIK38QM8yzMo5ekMj3DlcY= -golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= -golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= -golang.org/x/net v0.0.0-20170114055629-f2499483f923/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= +golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= golang.org/x/net v0.0.0-20170915142106-8351a756f30f/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20180112015858-5ccada7d0a7b/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= @@ -962,7 +939,6 @@ golang.org/x/net v0.0.0-20190320064053-1272bf9dcd53/go.mod h1:t9HGtf8HONx5eT2rtn golang.org/x/net v0.0.0-20190328230028-74de082e2cca/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190424112056-4829fb13d2c6/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= -golang.org/x/net v0.0.0-20190501004415-9ce7a6920f09/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190502183928-7f726cade0ab/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190503192946-f4e77d36d62c/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190522155817-f3200d17e092/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks= @@ -970,31 +946,29 @@ golang.org/x/net v0.0.0-20190603091049-60506f45cf65/go.mod h1:HSz+uSET+XFnRR8LxR golang.org/x/net v0.0.0-20190613194153-d28f0bde5980/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190628185345-da137c7871d7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20190724013045-ca1201d0de80/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190812203447-cdfb69ac37fc/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190813141303-74dc4d7220e7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20191004110552-13f9640d40b9/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20191028085509-fe3aa8a45271/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20191209160850-c0dbc17a3553/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200114155413-6afb5195e5aa/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200222125558-5a598a2470a0/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200301022130-244492dfa37a/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A= golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= -golang.org/x/net v0.0.0-20210428140749-89ef3d95e781 h1:DzZ89McO9/gWPsQXS/FVKAlG02ZjaQ6AlZRBimEYOd0= -golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= +golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20210421230115-4e50805a0758/go.mod h1:72T/g9IO56b78aLF+1Kcs5dz7/ng1VjMUvfKvpfy+jM= +golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= +golang.org/x/net v0.33.0 h1:74SYHlV8BIgHIFC/LrYkOGIwL19eTYXQ5wc6TBuO36I= +golang.org/x/net v0.33.0/go.mod h1:HXLR5J+9DxmrqMwG9qjGCxZ+zKXxBru04zlTvWlWuN4= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20181106182150-f42d05182288/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190402181905-9f3314589c9a/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= -golang.org/x/oauth2 v0.0.0-20191202225959-858c2ad4c8b6/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= -golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d h1:TzXSXBo42m9gQenoE3b9BGiEpg5IG2JkU5FkPIawgtw= golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= +golang.org/x/oauth2 v0.18.0 h1:09qnuIAgzdx1XplqJvW6CQqMCtGZykZWcXzPMPUusvI= +golang.org/x/oauth2 v0.18.0/go.mod h1:Wf7knwG0MPoWIMMBgFlEaSUDaKskp0dCfrlJRJXbBi8= golang.org/x/perf v0.0.0-20180704124530-6e6d33e29852/go.mod h1:JLpeXjPJfIyPr5TlbXLkXWLhP8nz10XfvxElABhCtcw= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -1003,9 +977,8 @@ golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJ golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sys v0.0.0-20170830134202-bb24a47a89ea/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sys v0.0.0-20171026204733-164713f0dfce/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= -golang.org/x/sys v0.0.0-20180117170059-2c42eef0765b/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= @@ -1027,58 +1000,57 @@ golang.org/x/sys v0.0.0-20190321052220-f7bb7a8bee54/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190426135247-a129542de9ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190502145724-3ef323f4f1fd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190515120540-06a5c4944438/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190606165138-5da285871e9c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190616124812-15dcb6c0061f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190624142023-c5567b49c5d0/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190626221950-04f50cda93cb/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190726091711-fc99dfbffb4e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190801041406-cbf593c0f2f3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190813064441-fde4db37ae7a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190826190057-c7b8b68b1456/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20191001151750-bb3f8db39f24/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191010194322-b09406accb47/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191028164358-195ce5e7f934/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191120155948-bd437916bb0e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20191204072324-ce4227a45e2e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20191228213918-04cbcbbfeed8/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200113162924-86b910548bc1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200120151820-655fe14d7479/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200122134326-e047566fdf82/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200202164722-d101bd2416d5/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200212091648-12a6c2dcc1e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210423082822-04245dca01da h1:b3NXsE2LusjYGGjL5bxEVZZORm/YEFFrWFjR8eFrw/c= -golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210420072515-93ed5bcd2bfe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.28.0 h1:Fksou7UEQUWlKvIdsqzJmUmCX3cZuD2+P3XyyzwMhlA= +golang.org/x/sys v0.28.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/text v0.0.0-20160726164857-2910a502d2bf/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= -golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/term v0.27.0 h1:WP60Sv1nlK1T6SupCHbXzSaN0b9wUmsPoRS9b61A23Q= +golang.org/x/term v0.27.0/go.mod h1:iMsnZpn0cago0GOrHO2+Y7u7JPn5AylBrcoWkElMTSM= golang.org/x/text v0.0.0-20170915090833-1cbadb444a80/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= -golang.org/x/text v0.3.1-0.20171227012246-e19ae1496984/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= +golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ= +golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo= +golang.org/x/text v0.21.0/go.mod h1:4IBbMaMmOPCJ8SecivzSH54+73PCFmPWxNTLm+vZkEQ= golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= -golang.org/x/time v0.0.0-20200416051211-89c76fbcd5d1 h1:NusfzzA6yGQ+ua51ck7E3omNUX/JuqbFSaRGqU8CcLI= golang.org/x/time v0.0.0-20200416051211-89c76fbcd5d1/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.5.0 h1:o7cqy6amK/52YcAKIPlM3a+Fpj35zvRj2TP+e1xFSfk= +golang.org/x/time v0.5.0/go.mod h1:3BpzKBy/shNhVucY/MWOyx10tF3SFh9QdLuxbVysPQM= golang.org/x/tools v0.0.0-20170824195420-5d2fd3ccab98/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20170915040203-e531a2a1c15f/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20180221164845-07fd8470d635/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= @@ -1106,41 +1078,25 @@ golang.org/x/tools v0.0.0-20190425222832-ad9eeb80039a/go.mod h1:RgjU9mgBXZiqYHBn golang.org/x/tools v0.0.0-20190506145303-2d16b83fe98c/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= golang.org/x/tools v0.0.0-20190521203540-521d6ed310dd/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= -golang.org/x/tools v0.0.0-20190606124116-d0a3d012864b/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= -golang.org/x/tools v0.0.0-20190614205625-5aca471b1d59/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190617190820-da514acc4774/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190621195816-6e04913cbbac/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190624180213-70d37148ca0c/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= -golang.org/x/tools v0.0.0-20190628153133-6cdbf07be9d0/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190706070813-72ffa07ba3db/go.mod h1:jcCCGcm9btYwXyDqrUWc6MKQKKGJCWEQ3AfLSRIbEuI= -golang.org/x/tools v0.0.0-20190816200558-6889da9d5479/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20190909030654-5b82db07426d/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20190911174233-4f2ddba30aff/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20190920225731-5eefd052ad72/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191012152004-8de300cfc20a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191018212557-ed542cd5b28a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191029041327-9cc4af7d6b2c/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191029190741-b9c20aec41a5/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191113191852-77e3bb0ad9e7/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191115202509-3a792d9c32b2/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191125144606-a911d9008d1f/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191130070609-6e064ea0cf2d/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= -golang.org/x/tools v0.0.0-20191216173652-a0e659d51361/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20191227053925-7b8e75db28f4/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200117161641-43d50277825c/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200122220014-bf1340f18c4a/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200130002326-2f3ba24bd6e7/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200204074204-1cc6d1ef6c74/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200207183749-b753a1ba74fa/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200212150539-ea181f53ac56/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200224181240-023911ca70b2/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= -golang.org/x/tools v0.0.0-20200304193943-95d2e580d8eb/go.mod h1:o4KQGtdN14AW+yjsvvwRTJJuXz8XRtIHtEnmAXLyFUw= +golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= golang.org/x/tools v0.0.0-20201224043029-2b0845dc783e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= +golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= +golang.org/x/tools v0.23.0 h1:SGsXPZ+2l4JsgaCKkx+FQ9YZ5XEtA1GZYuoDjenLjvg= +golang.org/x/tools v0.23.0/go.mod h1:pnu6ufv6vQkll6szChhK3C3L/ruaIv5eBeztNG8wtsI= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gomodules.xyz/jsonpatch/v2 v2.0.1/go.mod h1:IhYNNY4jnS53ZnfE4PAmpKtDpTCj1JFXc+3mwe7XcUU= gonum.org/v1/gonum v0.0.0-20190331200053-3d26580ed485/go.mod h1:2ltnJ7xHfj0zHS40VVPYEAAMTa3ZGguvHGBSJeRWqE0= @@ -1151,23 +1107,14 @@ google.golang.org/api v0.3.1/go.mod h1:6wY9I6uQWHQ8EM57III9mq/AjF+i8G65rmVagqKMt google.golang.org/api v0.3.2/go.mod h1:6wY9I6uQWHQ8EM57III9mq/AjF+i8G65rmVagqKMtkk= google.golang.org/api v0.4.0/go.mod h1:8k5glujaEP+g9n7WNsDg8QP6cUVNI86fCNMcbazEtwE= google.golang.org/api v0.6.1-0.20190607001116-5213b8090861/go.mod h1:btoxGiFvQNVUZQ8W08zLtrVS08CNpINPEfxXxgJL1Q4= -google.golang.org/api v0.7.0/go.mod h1:WtwebWUNSVBH/HAw79HIFXZNqEvBhG+Ra+ax0hx3E3M= -google.golang.org/api v0.8.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg= -google.golang.org/api v0.9.0/go.mod h1:o4eAsZoiT+ibD93RtjEohWalFOjRDx6CVaqeizhEnKg= -google.golang.org/api v0.13.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI= -google.golang.org/api v0.14.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI= -google.golang.org/api v0.15.0/go.mod h1:iLdEw5Ide6rF15KTC1Kkl0iskquN2gFfn9o9XIsbkAI= -google.golang.org/api v0.17.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= -google.golang.org/api v0.18.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= -google.golang.org/api v0.20.0/go.mod h1:BwFmGc8tA3vsd7r/7kR8DY7iEEGSU04BFxCo5jP/sfE= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.3.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= -google.golang.org/appengine v1.6.1/go.mod h1:i06prIuMbXzDqacNJfV5OdTW448YApPu5ww/cMBSeb0= google.golang.org/appengine v1.6.5/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= -google.golang.org/appengine v1.6.6 h1:lMO5rYAqUxkmaj76jAkRUvt5JZgFymx/+Q5Mzfivuhc= google.golang.org/appengine v1.6.6/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= +google.golang.org/appengine v1.6.8 h1:IhEN5q69dyKagZPYMSdIjS2HqprW324FRQZJcGqPAsM= +google.golang.org/appengine v1.6.8/go.mod h1:1jJ3jBArFh5pcgW8gCtRJnepW8FzD1V44FJffLiz/Ds= google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= google.golang.org/genproto v0.0.0-20190128161407-8ac453e89fca/go.mod h1:L3J43x8/uS+qIUoksaLKe6OS3nUKxOKuIFz1sl2/jx4= google.golang.org/genproto v0.0.0-20190307195333-5fe7a883aa19/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= @@ -1175,34 +1122,18 @@ google.golang.org/genproto v0.0.0-20190404172233-64821d5d2107/go.mod h1:VzzqZJRn google.golang.org/genproto v0.0.0-20190418145605-e7d98fc518a7/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= google.golang.org/genproto v0.0.0-20190425155659-357c62f0e4bb/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= google.golang.org/genproto v0.0.0-20190502173448-54afdca5d873/go.mod h1:VzzqZJRnGkLBvHegQrXjBqPurQTc5/KpmUdxsrq26oE= -google.golang.org/genproto v0.0.0-20190801165951-fa694d86fc64/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc= google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc= -google.golang.org/genproto v0.0.0-20190911173649-1774047e7e51/go.mod h1:IbNlFCBrqXvoKpeg0TB2l7cyZUmoaFKYIwrEpbDKLA8= google.golang.org/genproto v0.0.0-20191028173616-919d9bdd9fe6/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20191108220845-16a3f7862a1a/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20191115194625-c23dd37a84c9/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20191216164720-4f79533eabd1/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20191230161307-f3c370f40bfb/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20200115191322-ca5a22157cba/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20200117163144-32f20d992d24/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20200122232147-0452cf42e150/go.mod h1:n3cpQtvxv34hfy77yVDNjmbRyujviMdxYliBSkLhpCc= -google.golang.org/genproto v0.0.0-20200204135345-fa8e72b47b90/go.mod h1:GmwEX6Z4W5gMy59cAlVYjN9JhxgbQH6Gn+gFDQe2lzA= -google.golang.org/genproto v0.0.0-20200212174721-66ed5ce911ce/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= -google.golang.org/genproto v0.0.0-20200224152610-e50cd9704f63/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= -google.golang.org/genproto v0.0.0-20200305110556-506484158171/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo= google.golang.org/grpc v1.16.0/go.mod h1:0JHn/cJsOMiMfNA9+DeHDlAU7KAAB5GDlYFpa9MZMio= google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= google.golang.org/grpc v1.21.0/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= -google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= google.golang.org/grpc v1.23.1/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= google.golang.org/grpc v1.24.0/go.mod h1:XDChyiUovWa60DnaeDeZmSW86xtLtjtZbwvSiRnRtcA= -google.golang.org/grpc v1.26.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= -google.golang.org/grpc v1.27.1/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM= @@ -1213,14 +1144,17 @@ google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2 google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= google.golang.org/protobuf v1.24.0/go.mod h1:r/3tXBNzIEhYS9I1OUVjXDlt8tc493IdKGjtUeSXeh4= google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= -google.golang.org/protobuf v1.26.0 h1:bxAC2xTBsZGibn2RTntX0oH50xLsqy1OxA9tTL3p/lk= google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= +google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg= +google.golang.org/protobuf v1.34.2/go.mod h1:qYOHts0dSfpeUzUFpOMr/WGzszTmLH+DiWniOlNbLDw= gopkg.in/airbrake/gobrake.v2 v2.0.9/go.mod h1:/h5ZAUhDkGaJfjzjKLSjv6zCL6O0LLBxU4K+aSYdM/U= gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15 h1:YR8cESwS4TdDjEe65xsg0ogRM/Nc3DYOhEAlW+xobZo= gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= gopkg.in/cheggaaa/pb.v1 v1.0.25/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw= gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI= gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys= @@ -1239,7 +1173,6 @@ gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkep gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw= gopkg.in/warnings.v0 v0.1.1/go.mod h1:jksf8JmL6Qr/oQM2OXTHunEvvTAsrWBLb6OOjuVWRNI= gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74= -gopkg.in/yaml.v2 v2.0.0/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74= gopkg.in/yaml.v2 v2.1.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= @@ -1249,6 +1182,10 @@ gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= gopkg.in/yaml.v3 v3.0.0-20190905181640-827449938966/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gotest.tools v2.1.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw= gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw= gotest.tools/gotestsum v0.3.5/go.mod h1:Mnf3e5FUzXbkCfynWBGOwLssY7gTQgCHObK9tMpAriY= @@ -1262,7 +1199,6 @@ honnef.co/go/tools v0.0.0-20190418001031-e561f6794a2a/go.mod h1:rf3lG4BRIbNafJWh honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= honnef.co/go/tools v0.0.1-2019.2.2/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg= honnef.co/go/tools v0.0.1-2019.2.3/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg= -honnef.co/go/tools v0.0.1-2020.1.3/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= k8s.io/api v0.0.0-20191016110408-35e52d86657a h1:VVUE9xTCXP6KUPMf92cQmN88orz600ebexcRRaBTepQ= k8s.io/api v0.0.0-20191016110408-35e52d86657a/go.mod h1:/L5qH+AD540e7Cetbui1tuJeXdmNhO8jM6VkXeDdDhQ= k8s.io/apiextensions-apiserver v0.0.0-20191016113550-5357c4baaf65/go.mod h1:5BINdGqggRXXKnDgpwoJ7PyQH8f+Ypp02fvVNcIFy9s= @@ -1279,12 +1215,11 @@ k8s.io/code-generator v0.0.0-20191004115455-8e001e5d1894/go.mod h1:mJUgkl06XV4ks k8s.io/component-base v0.0.0-20191016111319-039242c015a9/go.mod h1:SuWowIgd/dtU/m/iv8OD9eOxp3QZBBhTIiWMsBQvKjI= k8s.io/cri-api v0.0.0-20190828162817-608eb1dad4ac/go.mod h1:BvtUaNBr0fEpzb11OfrQiJLsLPtqbmulpo1fPwcpP6Q= k8s.io/csi-translation-lib v0.0.0-20191016115521-756ffa5af0bd/go.mod h1:lf1VBseeLanBpSXD0N9tuPx1ylI8sA0j6f+rckCKiIk= -k8s.io/gengo v0.0.0-20190128074634-0689ccc1d7d6/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= k8s.io/gengo v0.0.0-20190822140433-26a664648505/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= k8s.io/gengo v0.0.0-20191010091904-7fa3014cb28f/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= +k8s.io/gengo v0.0.0-20200413195148-3a45101e95ac/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= k8s.io/heapster v1.2.0-beta.1/go.mod h1:h1uhptVXMwC8xtZBYsPXKVi8fpdlYkTs6k949KozGrM= k8s.io/helm v2.16.1+incompatible/go.mod h1:LZzlS4LQBHfciFOurYBFkCMTaZ0D1l+p0teMg7TSULI= -k8s.io/klog v0.0.0-20181102134211-b9b56d5dfc92/go.mod h1:Gq+BEi5rUBO/HRz0bTSXDUcqjScdoY3a9IHpCEIOOfk= k8s.io/klog v0.3.0/go.mod h1:Gq+BEi5rUBO/HRz0bTSXDUcqjScdoY3a9IHpCEIOOfk= k8s.io/klog v0.3.3/go.mod h1:Gq+BEi5rUBO/HRz0bTSXDUcqjScdoY3a9IHpCEIOOfk= k8s.io/klog v0.4.0/go.mod h1:4Bi6QPql/J/LkTDqv7R/cd3hPo4k2DG6Ptcz060Ez5I= @@ -1293,12 +1228,8 @@ k8s.io/klog v1.0.0/go.mod h1:4Bi6QPql/J/LkTDqv7R/cd3hPo4k2DG6Ptcz060Ez5I= k8s.io/klog/v2 v2.0.0/go.mod h1:PBfzABfn139FHAV07az/IF9Wp1bkk3vpT2XSJ76fSDE= k8s.io/kube-aggregator v0.0.0-20191016112429-9587704a8ad4/go.mod h1:+aW0UZgSXdTSHTIFnWnueEuXjOqerDUxGIw6Ygr+vYY= k8s.io/kube-controller-manager v0.0.0-20191016114939-2b2b218dc1df/go.mod h1:WgrTcPKYAfNa9C0LV1UeK+XqfbSOUH1WGq/vX5UiW40= -k8s.io/kube-openapi v0.0.0-20190320154901-5e45bb682580/go.mod h1:BXM9ceUBTj2QnfH2MK1odQs778ajze1RxcmP6S8RVVc= -k8s.io/kube-openapi v0.0.0-20190816220812-743ec37842bf/go.mod h1:1TqjTSzOxsLGIKfj0lK8EeCP7K1iUG65v09OM0/WG5E= -k8s.io/kube-openapi v0.0.0-20190918143330-0270cf2f1c1d/go.mod h1:1TqjTSzOxsLGIKfj0lK8EeCP7K1iUG65v09OM0/WG5E= -k8s.io/kube-openapi v0.0.0-20191107075043-30be4d16710a/go.mod h1:1TqjTSzOxsLGIKfj0lK8EeCP7K1iUG65v09OM0/WG5E= -k8s.io/kube-openapi v0.0.0-20200121204235-bf4fb3bd569c h1:/KUFqjjqAcY4Us6luF5RDNZ16KJtb49HfR3ZHB9qYXM= -k8s.io/kube-openapi v0.0.0-20200121204235-bf4fb3bd569c/go.mod h1:GRQhZsXIAJ1xR0C9bd8UpWHZ5plfAS9fzPjJuQ6JL3E= +k8s.io/kube-openapi v0.0.0-20200805222855-6aeccd4b50c6 h1:+WnxoVtG8TMiudHBSEtrVL1egv36TkkJm+bA8AxicmQ= +k8s.io/kube-openapi v0.0.0-20200805222855-6aeccd4b50c6/go.mod h1:UuqjUnNftUyPE5H64/qeyjQoUZhGpeFDVdxjTeEVN2o= k8s.io/kube-proxy v0.0.0-20191016114407-2e83b6f20229/go.mod h1:2Hxci1uzXO5ipP0h9n2+h18fvNkBTpYlckk5dOPu8zg= k8s.io/kube-scheduler v0.0.0-20191016114748-65049c67a58b/go.mod h1:BgDUHHC5Wl0xcBUQgo2XEprE5nG5i9tlRR4iNgEFbL0= k8s.io/kube-state-metrics v1.7.2/go.mod h1:U2Y6DRi07sS85rmVPmBFlmv+2peBcL8IWGjM+IjYA/E= @@ -1318,8 +1249,10 @@ k8s.io/utils v0.0.0-20190801114015-581e00157fb1/go.mod h1:sZAwmy6armz5eXlNoLmJcl k8s.io/utils v0.0.0-20191010214722-8d271d903fe4/go.mod h1:sZAwmy6armz5eXlNoLmJcl4F1QuKu7sr+mFQ0byX7Ew= k8s.io/utils v0.0.0-20191114184206-e782cd3c129f/go.mod h1:sZAwmy6armz5eXlNoLmJcl4F1QuKu7sr+mFQ0byX7Ew= k8s.io/utils v0.0.0-20200124190032-861946025e34/go.mod h1:sZAwmy6armz5eXlNoLmJcl4F1QuKu7sr+mFQ0byX7Ew= -k8s.io/utils v0.0.0-20200414100711-2df71ebbae66 h1:Ly1Oxdu5p5ZFmiVT71LFgeZETvMfZ1iBIGeOenT2JeM= +k8s.io/utils v0.0.0-20200324210504-a9aa75ae1b89/go.mod h1:sZAwmy6armz5eXlNoLmJcl4F1QuKu7sr+mFQ0byX7Ew= k8s.io/utils v0.0.0-20200414100711-2df71ebbae66/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= +k8s.io/utils v0.0.0-20221107191617-1a15be271d1d h1:0Smp/HP1OH4Rvhe+4B8nWGERtlqAGSftbSbbmm45oFs= +k8s.io/utils v0.0.0-20221107191617-1a15be271d1d/go.mod h1:OLgZIPagt7ERELqWJFomSt595RzquPNLL48iOWgYOg0= modernc.org/cc v1.0.0/go.mod h1:1Sk4//wdnYJiUIxnW8ddKpaOJCF37yAdqYnkxUpaYxw= modernc.org/golex v1.0.0/go.mod h1:b/QX9oBD/LhixY6NDh+IdGv17hgB+51fET1i2kPSmvk= modernc.org/mathutil v1.0.0/go.mod h1:wU0vUrJsVWBZ4P6e7xtFJEhFSNsfRLJ8H458uRjg03k= @@ -1328,21 +1261,17 @@ modernc.org/xc v1.0.0/go.mod h1:mRNCo0bvLjGhHO9WsyuKVU4q0ceiDDDoEeWDJHrNx8I= mvdan.cc/interfacer v0.0.0-20180901003855-c20040233aed/go.mod h1:Xkxe497xwlCKkIaQYRfC7CSLworTXY9RMqwhhCm+8Nc= mvdan.cc/lint v0.0.0-20170908181259-adc824a0674b/go.mod h1:2odslEg/xrtNQqCYg2/jCoyKnw3vv5biOc3JnIcYfL4= mvdan.cc/unparam v0.0.0-20190209190245-fbb59629db34/go.mod h1:H6SUd1XjIs+qQCyskXg5OFSrilMRUkD8ePJpHKDPaeY= -rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8= rsc.io/letsencrypt v0.0.1/go.mod h1:buyQKZ6IXrRnB7TdkHP0RyEybLx18HHyOSoTyoOLqNY= -rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= -rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA= -sigs.k8s.io/controller-runtime v0.4.0 h1:wATM6/m+3w8lj8FXNaO6Fs/rq/vqoOjO1Q116Z9NPsg= -sigs.k8s.io/controller-runtime v0.4.0/go.mod h1:ApC79lpY3PHW9xj/w9pj+lYkLgwAAUZwfXkME1Lajns= +sigs.k8s.io/controller-runtime v0.6.0 h1:Fzna3DY7c4BIP6KwfSlrfnj20DJ+SeMBK8HSFvOk9NM= +sigs.k8s.io/controller-runtime v0.6.0/go.mod h1:CpYf5pdNY/B352A1TFLAS2JVSlnGQ5O2cftPHndTroo= sigs.k8s.io/controller-tools v0.2.4/go.mod h1:m/ztfQNocGYBgTTCmFdnK94uVvgxeZeE3LtJvd/jIzA= sigs.k8s.io/kustomize v2.0.3+incompatible/go.mod h1:MkjgH3RdOWrievjo6c9T245dYlB5QeXV4WCbnt/PEpU= sigs.k8s.io/sig-storage-lib-external-provisioner v4.1.0+incompatible/go.mod h1:qhqLyNwJC49PoUalmtzYb4s9fT8HOMBTLbTY1QoVOqI= -sigs.k8s.io/structured-merge-diff v0.0.0-20190525122527-15d366b2352e/go.mod h1:wWxsB5ozmmv/SG7nM11ayaAW51xMvak/t1r0CSlcokI= sigs.k8s.io/structured-merge-diff v0.0.0-20190817042607-6149e4549fca/go.mod h1:IIgPezJWb76P0hotTxzDbWsMYB8APh18qZnxkomBpxA= -sigs.k8s.io/structured-merge-diff/v3 v3.0.0-20200116222232-67a7b8c61874/go.mod h1:PlARxl6Hbt/+BC80dRLi1qAmnMqwqDg62YvvVkZjemw= -sigs.k8s.io/testing_frameworks v0.1.2/go.mod h1:ToQrwSC3s8Xf/lADdZp3Mktcql9CG0UAmdJG9th5i0w= +sigs.k8s.io/structured-merge-diff/v4 v4.0.1/go.mod h1:bJZC9H9iH24zzfZ/41RGcq60oK1F7G282QMXDPYydCw= sigs.k8s.io/yaml v1.1.0/go.mod h1:UJmg0vDUVViEyp3mgSv9WPwZCDxu4rQW1olrI1uml+o= -sigs.k8s.io/yaml v1.2.0 h1:kr/MCeFWJWTwyaHoR9c8EjH9OumOmoF9YGiZd7lFm/Q= sigs.k8s.io/yaml v1.2.0/go.mod h1:yfXDCHCao9+ENCvLSE62v9VSji2MKu5jeNfTrofGhJc= +sigs.k8s.io/yaml v1.4.0 h1:Mk1wCc2gy/F0THH0TAp1QYyJNzRm2KCLy3o5ASXVI5E= +sigs.k8s.io/yaml v1.4.0/go.mod h1:Ejl7/uTz7PSA4eKMyQCUTnhZYNmLIl+5c2lQPGR2BPY= sourcegraph.com/sqs/pbtypes v0.0.0-20180604144634-d3ebe8f20ae4/go.mod h1:ketZ/q3QxT9HOBeFhu6RdvsftgpsbFHBF5Cas6cDKZ0= vbom.ml/util v0.0.0-20160121211510-db5cfe13f5cc/go.mod h1:so/NYdZXCz+E3ZpW0uAoCj6uzU2+8OWDFv/HxUSs7kI= diff --git a/pkg/common.go b/pkg/common.go index b7656bd..f13ea62 100644 --- a/pkg/common.go +++ b/pkg/common.go @@ -5,6 +5,7 @@ import ( "fmt" "os/exec" + "github.com/google/uuid" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" "github.com/litmuschaos/chaos-ci-lib/pkg/log" "github.com/pkg/errors" @@ -51,3 +52,25 @@ func (envDetails *ENVDetails) SetEnv(key, value string) *ENVDetails { } return envDetails } + +// GenerateUniqueExperimentName creates a unique experiment name by combining +// a base name with a unique identifier. This ensures there are no naming +// conflicts between experiment runs +func GenerateUniqueExperimentName(baseName string) string { + // Generate a short UUID (first 8 characters) + uniqueID := uuid.New().String()[:8] + return fmt.Sprintf("%s-%s", baseName, uniqueID) +} + +// GenerateExperimentIDs creates all necessary IDs for a chaos experiment +// including workflow name, experiment ID, and other related identifiers. +func GenerateExperimentID() (string) { + // Generate a unique ID for the experiment + experimentID := uuid.New().String()[:8] + return experimentID +} + +// GenerateEnvironmentID creates a unique environment ID +func GenerateEnvironmentID() string { + return uuid.New().String()[:8] +} diff --git a/pkg/environment/clientset.go b/pkg/environment/clientset.go index 9269f0a..f9b629a 100644 --- a/pkg/environment/clientset.go +++ b/pkg/environment/clientset.go @@ -4,21 +4,72 @@ import ( "os" chaosClient "github.com/litmuschaos/chaos-operator/pkg/client/clientset/versioned/typed/litmuschaos/v1alpha1" + litmusSDK "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + "github.com/litmuschaos/litmus-go-sdk/pkg/types" "github.com/pkg/errors" - "k8s.io/client-go/kubernetes" - - // _ "k8s.io/client-go/plugin/pkg/client/auth/gcp" "k8s.io/client-go/dynamic" + "k8s.io/client-go/kubernetes" "k8s.io/client-go/rest" "k8s.io/client-go/tools/clientcmd" + "k8s.io/klog" ) -// ClientSets is a collection of clientSets and kubeConfig needed +// // ClientSets is a collection of clientSets and kubeConfig needed type ClientSets struct { KubeClient *kubernetes.Clientset LitmusClient *chaosClient.LitmuschaosV1alpha1Client KubeConfig *rest.Config DynamicClient dynamic.Interface + SDKClient litmusSDK.Client + LitmusEndpoint string + LitmusUsername string + LitmusPassword string + LitmusProjectID string + LitmusToken string +} + +// GenerateClientSetFromSDK will generate the Litmus SDK client +func GenerateClientSetFromSDK() (litmusSDK.Client, error) { + // Initialize Litmus SDK client + endpoint := os.Getenv("LITMUS_ENDPOINT") + username := os.Getenv("LITMUS_USERNAME") + password := os.Getenv("LITMUS_PASSWORD") + projectID := os.Getenv("LITMUS_PROJECT_ID") + + if endpoint == "" || username == "" || password == "" || projectID == "" { + return nil, errors.New("LITMUS_ENDPOINT, LITMUS_USERNAME, LITMUS_PASSWORD, and LITMUS_PROJECT_ID environment variables must be set") + } + + // Initialize Litmus SDK client + sdkClient, err := litmusSDK.NewClient(litmusSDK.ClientOptions{ + Endpoint: endpoint, + Username: username, + Password: password, + ProjectID: projectID, + }) + if err != nil { + return nil, errors.Wrapf(err, "Unable to create Litmus SDK client: %v", err) + } + + // Get the token using the Auth() method + token := sdkClient.Auth().GetToken() + if token != "" { + klog.Infof("Successfully retrieved token from SDK client") + } else { + klog.Warningf("Could not retrieve token from SDK client Auth().GetToken()") + return nil, errors.New("Failed to retrieve token from SDK client") + } + return sdkClient, nil +} + +// Helper method to construct Credentials struct for SDK calls +func (clientSets *ClientSets) GetSDKCredentials() types.Credentials { + return types.Credentials{ + Endpoint: clientSets.LitmusEndpoint, + Token: clientSets.LitmusToken, + Username: clientSets.LitmusUsername, + ProjectID: clientSets.LitmusProjectID, + } } // GenerateClientSetFromKubeConfig will generation both ClientSets (k8s, and Litmus) as well as the KubeConfig @@ -89,3 +140,4 @@ func DynamicClientSet(config *rest.Config) (dynamic.Interface, error) { } return dynamicClientSet, nil } + diff --git a/pkg/environment/environment.go b/pkg/environment/environment.go index 8b05129..9a7c4f7 100644 --- a/pkg/environment/environment.go +++ b/pkg/environment/environment.go @@ -47,6 +47,8 @@ func GetENV(experimentDetails *types.ExperimentDetails, expName, engineName stri experimentDetails.NodesAffectedPerc, _ = strconv.Atoi(Getenv("NODES_AFFECTED_PERC", "0")) experimentDetails.FilesystemUtilizationBytes, _ = strconv.Atoi(Getenv("FILESYSTEM_UTILIZATION_BYTES", "")) experimentDetails.Replicas, _ = strconv.Atoi(Getenv("REPLICA_COUNT", "0")) + experimentDetails.ExperimentTimeout, _ = strconv.Atoi(Getenv("EXPERIMENT_TIMEOUT", "8")) + experimentDetails.ExperimentPollingInterval, _ = strconv.Atoi(Getenv("EXPERIMENT_POLLING_INTERVAL", "15")) //All Images for running chaos test experimentDetails.GoExperimentImage = Getenv("EXPERIMENT_IMAGE", "litmuschaos/go-runner:ci") @@ -58,6 +60,41 @@ func GetENV(experimentDetails *types.ExperimentDetails, expName, engineName stri experimentDetails.EnginePath = Getenv("ENGINE_PATH", "https://hub.litmuschaos.io/api/chaos/master?file=charts/generic/"+expName+"/engine.yaml") experimentDetails.InstallLitmus = Getenv("INSTALL_LITMUS_URL", "https://litmuschaos.github.io/litmus/litmus-operator-latest.yaml") + // V3 SDK Related ENV parsing + experimentDetails.InstallLitmusFlag, _ = strconv.ParseBool(Getenv("INSTALL_CHAOS_CENTER", "false")) + experimentDetails.ConnectInfraFlag, _ = strconv.ParseBool(Getenv("CONNECT_INFRA", "false")) + experimentDetails.LitmusEndpoint = Getenv("LITMUS_ENDPOINT", "") + experimentDetails.LitmusUsername = Getenv("LITMUS_USERNAME", "") + experimentDetails.LitmusPassword = Getenv("LITMUS_PASSWORD", "") + experimentDetails.LitmusProjectID = Getenv("LITMUS_PROJECT_ID", "") + experimentDetails.InfraName = Getenv("INFRA_NAME", "ci-infra-"+expName) + experimentDetails.InfraNamespace = Getenv("INFRA_NAMESPACE", "litmus") + experimentDetails.InfraScope = Getenv("INFRA_SCOPE", "namespace") + experimentDetails.InfraSA = Getenv("INFRA_SERVICE_ACCOUNT", "litmus") + experimentDetails.InfraDescription = Getenv("INFRA_DESCRIPTION", "CI Test Infrastructure") + experimentDetails.InfraPlatformName = Getenv("INFRA_PLATFORM_NAME", "others") + experimentDetails.InfraEnvironmentID = Getenv("INFRA_ENVIRONMENT_ID", "") + experimentDetails.InfraNsExists, _ = strconv.ParseBool(Getenv("INFRA_NS_EXISTS", "false")) + experimentDetails.InfraSaExists, _ = strconv.ParseBool(Getenv("INFRA_SA_EXISTS", "false")) + experimentDetails.InfraSkipSSL, _ = strconv.ParseBool(Getenv("INFRA_SKIP_SSL", "false")) + experimentDetails.InfraNodeSelector = Getenv("INFRA_NODE_SELECTOR", "") + experimentDetails.InfraTolerations = Getenv("INFRA_TOLERATIONS", "") + + // New infrastructure control variables + experimentDetails.InstallInfra, _ = strconv.ParseBool(Getenv("INSTALL_INFRA", "true")) + experimentDetails.UseExistingInfra, _ = strconv.ParseBool(Getenv("USE_EXISTING_INFRA", "false")) + experimentDetails.ExistingInfraID = Getenv("EXISTING_INFRA_ID", "") + + // Probe configuration + experimentDetails.CreateProbe, _ = strconv.ParseBool(Getenv("LITMUS_CREATE_PROBE", "false")) + experimentDetails.ProbeType = Getenv("LITMUS_PROBE_TYPE", "httpProbe") + experimentDetails.ProbeName = Getenv("LITMUS_PROBE_NAME", "http-probe") + experimentDetails.ProbeMode = Getenv("LITMUS_PROBE_MODE", "SOT") + experimentDetails.ProbeURL = Getenv("LITMUS_PROBE_URL", "http://localhost:8080/health") + experimentDetails.ProbeTimeout = Getenv("LITMUS_PROBE_TIMEOUT", "30s") + experimentDetails.ProbeInterval = Getenv("LITMUS_PROBE_INTERVAL", "10s") + experimentDetails.ProbeAttempts, _ = strconv.Atoi(Getenv("LITMUS_PROBE_ATTEMPTS", "1")) + experimentDetails.ProbeResponseCode = Getenv("LITMUS_PROBE_RESPONSE_CODE", "200") } // Getenv fetch the env and set the default value, if any diff --git a/pkg/file.go b/pkg/file.go index ebf2702..3d90539 100644 --- a/pkg/file.go +++ b/pkg/file.go @@ -3,7 +3,6 @@ package pkg import ( "fmt" "io" - "io/ioutil" "net/http" "os" "strings" @@ -14,7 +13,7 @@ import ( // EditFile will edit the content of a file func EditFile(filepath, old, new string) error { failFlag := true - fileData, err := ioutil.ReadFile(filepath) + fileData, err := os.ReadFile(filepath) if err != nil { return errors.Wrapf(err, "Failed to read the given file, due to:%v", err) } @@ -30,7 +29,7 @@ func EditFile(filepath, old, new string) error { return errors.Errorf("Error in updating \"%v\" please check the file", old) } output := strings.Join(lines, "\n") - err = ioutil.WriteFile(filepath, []byte(output), 0644) + err = os.WriteFile(filepath, []byte(output), 0644) if err != nil { return errors.Wrapf(err, "Failed to write the data in the given file, due to:%v", err) } @@ -41,7 +40,7 @@ func EditFile(filepath, old, new string) error { // EditKeyValue will edit the value according to key content of the file func EditKeyValue(filepath, key, oldvalue, newvalue string) error { failFlag := true - fileData, err := ioutil.ReadFile(filepath) + fileData, err := os.ReadFile(filepath) if err != nil { return errors.Wrapf(err, "Failed to read the given file, due to:%v", err) } @@ -57,7 +56,7 @@ func EditKeyValue(filepath, key, oldvalue, newvalue string) error { return errors.Errorf("Error in updating \"%v\" please check the file", oldvalue) } output := strings.Join(lines, "\n") - err = ioutil.WriteFile(filepath, []byte(output), 0644) + err = os.WriteFile(filepath, []byte(output), 0644) if err != nil { return errors.Wrapf(err, "Failed to write the data in the given file, due to:%v", err) } @@ -68,7 +67,7 @@ func EditKeyValue(filepath, key, oldvalue, newvalue string) error { // AddAfterMatch will add a new line when a match is found func AddAfterMatch(filepath, key, newvalue string) error { failFlag := true - fileData, err := ioutil.ReadFile(filepath) + fileData, err := os.ReadFile(filepath) if err != nil { return errors.Wrapf(err, "Failed to read the given file, due to:%v", err) } @@ -86,7 +85,7 @@ func AddAfterMatch(filepath, key, newvalue string) error { return errors.Errorf("Error in adding \"%v\", \"%v\" not found ", newvalue, key) } output := strings.Join(lines, "\n") - err = ioutil.WriteFile(filepath, []byte(output), 0644) + err = os.WriteFile(filepath, []byte(output), 0644) if err != nil { return errors.Wrapf(err, "Failed to write the data in the given file, due to:%v", err) } diff --git a/pkg/generic/node-io-stress/lib/node-io-stress.go b/pkg/generic/node-io-stress/lib/node-io-stress.go index f9d2791..087cbb1 100644 --- a/pkg/generic/node-io-stress/lib/node-io-stress.go +++ b/pkg/generic/node-io-stress/lib/node-io-stress.go @@ -27,7 +27,8 @@ func setNodeIOStressExperimentENV(experimentsDetails *types.ExperimentDetails) * } // Add Experiment ENV's envDetails.SetEnv("FILESYSTEM_UTILIZATION_PERCENTAGE", strconv.Itoa(experimentsDetails.NodeCPUCore)). - SetEnv("FILESYSTEM_UTILIZATION_BYTES", strconv.Itoa(experimentsDetails.FilesystemUtilizationBytes)) + SetEnv("FILESYSTEM_UTILIZATION_BYTES", strconv.Itoa(experimentsDetails.FilesystemUtilizationBytes)). + SetEnv("NODES_AFFECTED_PERC", strconv.Itoa(experimentsDetails.PodsAffectedPerc)) return &envDetails } diff --git a/pkg/infrastructure/infra.go b/pkg/infrastructure/infra.go new file mode 100644 index 0000000..38da89c --- /dev/null +++ b/pkg/infrastructure/infra.go @@ -0,0 +1,169 @@ +package infrastructure + +import ( + "errors" + "os" + "strconv" + + "github.com/litmuschaos/chaos-ci-lib/pkg" + "github.com/litmuschaos/chaos-ci-lib/pkg/types" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + sdkTypes "github.com/litmuschaos/litmus-go-sdk/pkg/types" + "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" + "k8s.io/klog" +) + +// SetupInfrastructure handles the creation or connection to infrastructure +// It checks if infrastructure should be installed and if it's already connected +func SetupInfrastructure(experimentsDetails *types.ExperimentDetails, sdkClient sdk.Client) error { + // Check if infrastructure operations should be performed + installInfra, _ := strconv.ParseBool(os.Getenv("INSTALL_INFRA")) + if !installInfra { + klog.Info("INSTALL_INFRA is set to false, skipping infrastructure setup") + // Handle case where we're using existing infrastructure but not installing + if experimentsDetails.ConnectedInfraID == "" && experimentsDetails.UseExistingInfra && experimentsDetails.ExistingInfraID != "" { + experimentsDetails.ConnectedInfraID = experimentsDetails.ExistingInfraID + klog.Infof("Manually set ConnectedInfraID to %s from ExistingInfraID", experimentsDetails.ConnectedInfraID) + } + return nil + } + + // Check if we should use existing infrastructure + useExistingInfra, _ := strconv.ParseBool(os.Getenv("USE_EXISTING_INFRA")) + if useExistingInfra { + infraID := os.Getenv("EXISTING_INFRA_ID") + if infraID == "" { + return errors.New("USE_EXISTING_INFRA is true but EXISTING_INFRA_ID is not provided") + } + experimentsDetails.ConnectedInfraID = infraID + klog.Infof("Using existing infrastructure with ID: %s", infraID) + return nil + } + + // If not using existing infrastructure, connect to new one + return ConnectInfrastructure(experimentsDetails, sdkClient) +} + +// SetupEnvironment checks if we should use an existing environment or create a new one +// It returns the environmentID to be used for infrastructure creation +func SetupEnvironment(experimentsDetails *types.ExperimentDetails, sdkClient sdk.Client) (string, error) { + // Check if we should use an existing environment + useExistingEnv, _ := strconv.ParseBool(os.Getenv("USE_EXISTING_ENV")) + if useExistingEnv { + envID := os.Getenv("EXISTING_ENV_ID") + if envID == "" { + return "", errors.New("USE_EXISTING_ENV is true but EXISTING_ENV_ID is not provided") + } + klog.Infof("Using existing environment with ID: %s", envID) + return envID, nil + } + + // Create a new environment + envName := os.Getenv("ENV_NAME") + if envName == "" { + envName = "chaos-ci-env" // Default environment name + } + + // Configure environment properties + // Valid values for environment type are "PROD" and "NON_PROD" + envType := os.Getenv("ENV_TYPE") + if envType == "" || (envType != "PROD" && envType != "NON_PROD") { + envType = "NON_PROD" // Default environment type + } + + envDescription := os.Getenv("ENV_DESCRIPTION") + if envDescription == "" { + envDescription = "CI Test Environment" + } + + environmentID := pkg.GenerateEnvironmentID() + + // Create the environment request with the correct environment type + createEnvironmentRequest := model.CreateEnvironmentRequest{ + Name: envName, + Type: model.EnvironmentType(envType), + Description: &envDescription, + EnvironmentID: environmentID, + } + + // Create the environment using SDK + klog.Infof("Creating new environment: %s with type: %s", envName, envType) + _, err := sdkClient.Environments().Create(envName, createEnvironmentRequest) + if err != nil { + return "", err + } + + klog.Infof("Successfully created environment with ID: %s", environmentID) + return environmentID, nil +} + +// ConnectInfrastructure connects to a new infrastructure via the SDK +func ConnectInfrastructure(experimentsDetails *types.ExperimentDetails, sdkClient sdk.Client) error { + klog.Infof("Attempting to connect infrastructure: %s", experimentsDetails.InfraName) + + // Setup environment (create new or use existing) + environmentID, err := SetupEnvironment(experimentsDetails, sdkClient) + if err != nil { + return err + } + + // Use the obtained environmentID + experimentsDetails.InfraEnvironmentID = environmentID + + // Prepare infrastructure configuration + sdkConfig := sdkTypes.Infra{ + Namespace: experimentsDetails.InfraNamespace, + ServiceAccount: experimentsDetails.InfraSA, + Mode: experimentsDetails.InfraScope, + Description: experimentsDetails.InfraDescription, + PlatformName: experimentsDetails.InfraPlatformName, + EnvironmentID: experimentsDetails.InfraEnvironmentID, + NsExists: experimentsDetails.InfraNsExists, + SAExists: experimentsDetails.InfraSaExists, + SkipSSL: experimentsDetails.InfraSkipSSL, + NodeSelector: experimentsDetails.InfraNodeSelector, + Tolerations: experimentsDetails.InfraTolerations, + } + + // Create infrastructure via SDK + infraID, errSdk := sdkClient.Infrastructure().Create(experimentsDetails.InfraName, sdkConfig) + if errSdk != nil { + return errSdk + } + + // Process response and extract infra ID + if infraID == "" { + return errors.New("infrastructure create call returned nil data") + } + + experimentsDetails.ConnectedInfraID = infraID + klog.Infof("Successfully connected infrastructure via SDK. Stored ID: %s", experimentsDetails.ConnectedInfraID) + + return nil +} + +// DisconnectInfrastructure disconnects from infrastructure if it was created during the test +func DisconnectInfrastructure(experimentsDetails *types.ExperimentDetails, sdkClient sdk.Client) error { + // Don't disconnect if we're using an existing infrastructure + useExistingInfra, _ := strconv.ParseBool(os.Getenv("USE_EXISTING_INFRA")) + if useExistingInfra { + klog.Info("Using existing infrastructure, skipping disconnection") + return nil + } + + // Check if we have an infrastructure to disconnect + if experimentsDetails.ConnectedInfraID == "" { + klog.Info("No connected infrastructure ID found, skipping disconnection") + return nil + } + + // Disconnect the infrastructure + klog.Infof("Attempting to disconnect infrastructure with ID: %s", experimentsDetails.ConnectedInfraID) + err := sdkClient.Infrastructure().Disconnect(experimentsDetails.ConnectedInfraID) + if err != nil { + return err + } + + klog.Infof("Successfully disconnected infrastructure: %s", experimentsDetails.ConnectedInfraID) + return nil +} \ No newline at end of file diff --git a/pkg/install.go b/pkg/install.go index c294d9c..4c6c932 100644 --- a/pkg/install.go +++ b/pkg/install.go @@ -1,6 +1,8 @@ package pkg import ( + "io" + yamlChe "github.com/ghodss/yaml" "github.com/litmuschaos/chaos-ci-lib/pkg/environment" "github.com/litmuschaos/chaos-ci-lib/pkg/log" @@ -12,7 +14,6 @@ import ( "bytes" "encoding/json" - "io/ioutil" "net/http" "strconv" @@ -133,7 +134,7 @@ func InstallChaosEngine(experimentsDetails *types.ExperimentDetails, chaosEngine } // ReadAll reads from response until an error or EOF and returns the data it read. - fileInput, err := ioutil.ReadAll(res.Body) + fileInput, err := io.ReadAll(res.Body) if err != nil { log.Errorf("Fail to read data from response: %v", err) } diff --git a/pkg/slice.go b/pkg/slice.go new file mode 100644 index 0000000..e2e30a5 --- /dev/null +++ b/pkg/slice.go @@ -0,0 +1,11 @@ +package pkg + +// ContainsString checks if a string is present in a slice of strings +func ContainsString(slice []string, str string) bool { + for _, item := range slice { + if item == str { + return true + } + } + return false +} \ No newline at end of file diff --git a/pkg/types/types.go b/pkg/types/types.go index fbd251f..d38d981 100644 --- a/pkg/types/types.go +++ b/pkg/types/types.go @@ -36,6 +36,7 @@ type ExperimentDetails struct { ContainerPath string SocketPath string NetworkPacketDuplicationPercentage int + NetworkPacketCorruptionPercentage int FileSystemUtilizationPercentage int FilesystemUtilizationBytes int NetworkPacketLossPercentage int @@ -47,4 +48,45 @@ type ExperimentDetails struct { PodsAffectedPerc int NodesAffectedPerc int Replicas int + ExperimentTimeout int + ExperimentPollingInterval int + + // V3 SDK Related Fields + InstallLitmusFlag bool + ConnectInfraFlag bool + LitmusEndpoint string + LitmusUsername string + LitmusPassword string + LitmusProjectID string + InfraName string + InfraNamespace string + InfraScope string + InfraSA string + InfraDescription string + InfraPlatformName string + InfraEnvironmentID string + InfraNsExists bool + InfraSaExists bool + InfraSkipSSL bool + InfraNodeSelector string + InfraTolerations string + ConnectedInfraID string // Stores the ID of the infra connected via SDK + ExperimentRunID string // Stores the ID of the experiment run started via SDK + + // New infrastructure control variables + InstallInfra bool // Flag to determine if infrastructure should be installed + UseExistingInfra bool // Flag to determine if existing infrastructure should be used + ExistingInfraID string // ID of existing infrastructure if UseExistingInfra is true + + // Probe configuration + CreateProbe bool // Flag to determine if a new probe should be created + ProbeType string // Type of probe (http, cmd, etc.) + ProbeName string // Name of the probe + ProbeMode string // Mode of the probe (SOT, EOT, Edge, Continuous, etc.) + ProbeURL string // URL for HTTP probe + ProbeTimeout string // Timeout for probe + ProbeInterval string // Interval for probe + ProbeAttempts int // Number of attempts for probe + ProbeResponseCode string // Expected HTTP response code for HTTP probe + CreatedProbeID string // ID of the created probe } diff --git a/pkg/workflow/workflow.go b/pkg/workflow/workflow.go new file mode 100644 index 0000000..5ac3532 --- /dev/null +++ b/pkg/workflow/workflow.go @@ -0,0 +1,2276 @@ +package workflow + +import ( + "encoding/json" + "fmt" + "log" + "os" + "regexp" + "strconv" + "strings" + + "github.com/litmuschaos/chaos-ci-lib/pkg/types" + probe "github.com/litmuschaos/litmus-go-sdk/pkg/apis/probe" + "github.com/litmuschaos/litmus-go-sdk/pkg/sdk" + models "github.com/litmuschaos/litmus/chaoscenter/graphql/server/graph/model" +) + +// ExperimentType defines the available chaos experiment types +type ExperimentType string + +const ( + // Pod state chaos + PodDelete ExperimentType = "pod-delete" + PodCPUHog ExperimentType = "pod-cpu-hog" + PodMemoryHog ExperimentType = "pod-memory-hog" + + // Network chaos + PodNetworkCorruption ExperimentType = "pod-network-corruption" + PodNetworkLatency ExperimentType = "pod-network-latency" + PodNetworkLoss ExperimentType = "pod-network-loss" + PodNetworkDuplication ExperimentType = "pod-network-duplication" + + // Autoscaling + PodAutoscaler ExperimentType = "pod-autoscaler" + + // Container chaos + ContainerKill ExperimentType = "container-kill" + + // Disk chaos + DiskFill ExperimentType = "disk-fill" + + // Node chaos + NodeCPUHog ExperimentType = "node-cpu-hog" + NodeMemoryHog ExperimentType = "node-memory-hog" + NodeIOStress ExperimentType = "node-io-stress" +) + +// ExperimentConfig holds configuration for an experiment +type ExperimentConfig struct { + AppNamespace string + AppLabel string + AppKind string + ChaosDuration string + ChaosInterval string + Description string + Tags []string + + // Common parameters + TargetContainer string + PodsAffectedPerc string + RampTime string + TargetPods string + DefaultHealthCheck string + + // CPU hog specific parameters + CPUCores string + + // Memory hog specific parameters + MemoryConsumption string + + // Node memory hog specific parameters + MemoryConsumptionPercentage string + MemoryConsumptionMebibytes string + NumberOfWorkers string + + // Network chaos common parameters + NetworkInterface string + TCImage string + LibImage string + ContainerRuntime string + SocketPath string + DestinationIPs string + DestinationHosts string + NodeLabel string + Sequence string + + // Network corruption specific + NetworkPacketCorruptionPercentage string + + // Network latency specific + NetworkLatency string + Jitter string + + // Network loss specific + NetworkPacketLossPercentage string + + // Network duplication specific + NetworkPacketDuplicationPercentage string + + // Pod Autoscaler specific + ReplicaCount string + + // Container kill specific parameters + Signal string + + // Disk fill specific parameters + FillPercentage string + DataBlockSize string + EphemeralStorageMebibytes string + + // Probe configuration + UseExistingProbe bool + ProbeName string + ProbeMode string +} + +// GetDefaultExperimentConfig returns default configuration for a given experiment type +func GetDefaultExperimentConfig(experimentType ExperimentType) ExperimentConfig { + // Base config with common defaults + config := ExperimentConfig{ + AppNamespace: "litmus-2", + AppLabel: "app=nginx", + AppKind: "deployment", + PodsAffectedPerc: "", + RampTime: "", + TargetContainer: "", + DefaultHealthCheck: "false", + UseExistingProbe: true, + ProbeName: "myprobe", + ProbeMode: "SOT", + Sequence: "parallel", + } + + // Set network experiment common defaults + if isNetworkExperiment(experimentType) { + config.NetworkInterface = "eth0" + config.TCImage = "gaiadocker/iproute2" + config.LibImage = "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + config.ContainerRuntime = "containerd" + config.SocketPath = "/run/containerd/containerd.sock" + config.DestinationIPs = "" + config.DestinationHosts = "" + config.NodeLabel = "" + config.TargetPods = "" + } + + // Apply experiment-specific defaults + switch experimentType { + case PodDelete: + config.ChaosDuration = "15" + config.ChaosInterval = "5" + config.Description = "Pod delete chaos experiment execution" + config.Tags = []string{"pod-delete", "chaos", "litmus"} + + case PodCPUHog: + config.ChaosDuration = "30" + config.ChaosInterval = "10" + config.CPUCores = "1" + config.Description = "Pod CPU hog chaos experiment execution" + config.Tags = []string{"pod-cpu-hog", "chaos", "litmus"} + + case PodMemoryHog: + config.ChaosDuration = "30" + config.ChaosInterval = "10" + config.MemoryConsumption = "500" + config.Description = "Pod memory hog chaos experiment execution" + config.Tags = []string{"pod-memory-hog", "chaos", "litmus"} + + case PodNetworkCorruption: + config.ChaosDuration = "60" + config.NetworkPacketCorruptionPercentage = "100" + config.Description = "Pod network corruption chaos experiment execution" + config.Tags = []string{"pod-network-corruption", "network-chaos", "litmus"} + + case PodNetworkLatency: + config.ChaosDuration = "60" + config.NetworkLatency = "2000" + config.Jitter = "0" + config.Description = "Pod network latency chaos experiment execution" + config.Tags = []string{"pod-network-latency", "network-chaos", "litmus"} + + case PodNetworkLoss: + config.ChaosDuration = "60" + config.NetworkPacketLossPercentage = "100" + config.Description = "Pod network loss chaos experiment execution" + config.Tags = []string{"pod-network-loss", "network-chaos", "litmus"} + + case PodNetworkDuplication: + config.ChaosDuration = "60" + config.NetworkPacketDuplicationPercentage = "100" + config.Description = "Pod network duplication chaos experiment execution" + config.Tags = []string{"pod-network-duplication", "network-chaos", "litmus"} + + case PodAutoscaler: + config.ChaosDuration = "60" + config.ReplicaCount = "5" + config.Description = "Pod autoscaler chaos experiment execution" + config.Tags = []string{"pod-autoscaler", "autoscaling", "litmus"} + + case ContainerKill: + config.ChaosDuration = "20" + config.ChaosInterval = "10" + config.Signal = "SIGKILL" + config.Description = "Container kill chaos experiment execution" + config.Tags = []string{"container-kill", "chaos", "litmus"} + + case DiskFill: + config.ChaosDuration = "60" + config.FillPercentage = "80" + config.DataBlockSize = "256" + config.EphemeralStorageMebibytes = "" + config.Description = "Disk fill chaos experiment execution" + config.Tags = []string{"disk-fill", "chaos", "litmus"} + + case NodeCPUHog: + config.ChaosDuration = "60" + config.CPUCores = "2" + config.Description = "Node CPU hog chaos experiment execution" + config.Tags = []string{"node-cpu-hog", "chaos", "litmus"} + + case NodeMemoryHog: + config.ChaosDuration = "60" + config.MemoryConsumptionPercentage = "0" + config.MemoryConsumptionMebibytes = "0" + config.NumberOfWorkers = "1" + config.NodeLabel = "" // Explicitly set to empty + config.Description = "Node memory hog chaos experiment execution" + config.Tags = []string{"node-memory-hog", "chaos", "litmus"} + + case NodeIOStress: + config.ChaosDuration = "60" + config.Description = "Node IO stress chaos experiment execution" + config.Tags = []string{"node-io-stress", "chaos", "litmus"} + } + + return config +} + +// isNetworkExperiment returns true if the experiment type is a network experiment +func isNetworkExperiment(experimentType ExperimentType) bool { + return experimentType == PodNetworkCorruption || + experimentType == PodNetworkLatency || + experimentType == PodNetworkLoss || + experimentType == PodNetworkDuplication +} + +// ConstructExperimentRequest creates an Argo Workflow manifest for LitmusChaos +func ConstructExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string, experimentType ExperimentType, config ExperimentConfig) (*models.SaveChaosExperimentRequest, error) { + // Get base workflow manifest for the experiment type + manifest, err := GetExperimentManifest(experimentType, experimentName, config) + if err != nil { + return nil, fmt.Errorf("failed to get experiment manifest: %v", err) + } + + // Construct the experiment request + experimentRequest := &models.SaveChaosExperimentRequest{ + ID: experimentID, + Name: experimentName, + InfraID: details.ConnectedInfraID, + Description: config.Description, + Tags: config.Tags, + Manifest: manifest, + } + + return experimentRequest, nil +} + +// GetExperimentManifest returns the complete workflow manifest string for a given experiment type +func GetExperimentManifest(experimentType ExperimentType, experimentName string, config ExperimentConfig) (string, error) { + // Base workflow structure that's common for all experiments + baseManifest := map[string]interface{}{ + "apiVersion": "argoproj.io/v1alpha1", + "kind": "Workflow", + "metadata": map[string]interface{}{ + "name": experimentName, + "namespace": "litmus-2", + }, + "spec": map[string]interface{}{ + "entrypoint": string(experimentType) + "-engine", + "serviceAccountName": "argo-chaos", + "podGC": map[string]string{ + "strategy": "OnWorkflowCompletion", + }, + "securityContext": map[string]interface{}{ + "runAsUser": 1000, + "runAsNonRoot": true, + }, + "arguments": map[string]interface{}{ + "parameters": []map[string]string{ + { + "name": "adminModeNamespace", + "value": "litmus-2", + }, + }, + }, + "templates": []map[string]interface{}{ + // Main workflow template + { + "name": string(experimentType) + "-engine", + "steps": [][]map[string]interface{}{ + { + { + "name": "install-chaos-faults", + "template": "install-chaos-faults", + "arguments": map[string]interface{}{}, + }, + }, + { + { + "name": string(experimentType) + "-ce5", + "template": string(experimentType) + "-ce5", + "arguments": map[string]interface{}{}, + }, + }, + { + { + "name": "cleanup-chaos-resources", + "template": "cleanup-chaos-resources", + "arguments": map[string]interface{}{}, + }, + }, + }, + }, + }, + }, + "status": map[string]interface{}{}, + } + + // Add experiment-specific templates + templates, err := getExperimentTemplates(experimentType, config) + if err != nil { + return "", err + } + + // Append templates to the base manifest + baseManifest["spec"].(map[string]interface{})["templates"] = append( + baseManifest["spec"].(map[string]interface{})["templates"].([]map[string]interface{}), + templates..., + ) + + // Convert to JSON and then to pretty-printed string + jsonBytes, err := json.MarshalIndent(baseManifest, "", " ") + if err != nil { + return "", fmt.Errorf("failed to marshal workflow manifest: %v", err) + } + + // Convert JSON to string + manifestStr := string(jsonBytes) + + // Replace with specific placeholders + manifestStr = strings.ReplaceAll(manifestStr, "__EXPERIMENT_NAME__", experimentName) + manifestStr = strings.ReplaceAll(manifestStr, "__EXPERIMENT_TYPE__", string(experimentType)) + manifestStr = strings.ReplaceAll(manifestStr, "__APP_NAMESPACE__", config.AppNamespace) + manifestStr = strings.ReplaceAll(manifestStr, "__APP_LABEL__", config.AppLabel) + manifestStr = strings.ReplaceAll(manifestStr, "__APP_KIND__", config.AppKind) + manifestStr = strings.ReplaceAll(manifestStr, "__CHAOS_DURATION_VALUE__", config.ChaosDuration) + manifestStr = strings.ReplaceAll(manifestStr, "__CHAOS_INTERVAL_VALUE__", config.ChaosInterval) + manifestStr = strings.ReplaceAll(manifestStr, "__TARGET_CONTAINER_VALUE__", config.TargetContainer) + manifestStr = strings.ReplaceAll(manifestStr, "__PODS_AFFECTED_PERC_VALUE__", config.PodsAffectedPerc) + manifestStr = strings.ReplaceAll(manifestStr, "__RAMP_TIME_VALUE__", config.RampTime) + manifestStr = strings.ReplaceAll(manifestStr, "__TARGET_PODS_VALUE__", config.TargetPods) + manifestStr = strings.ReplaceAll(manifestStr, "__DEFAULT_HEALTH_CHECK_VALUE__", config.DefaultHealthCheck) + + // Replace network experiment specific placeholders + if isNetworkExperiment(experimentType) { + manifestStr = strings.ReplaceAll(manifestStr, "__NETWORK_INTERFACE_VALUE__", config.NetworkInterface) + manifestStr = strings.ReplaceAll(manifestStr, "__TC_IMAGE_VALUE__", config.TCImage) + manifestStr = strings.ReplaceAll(manifestStr, "__LIB_IMAGE_VALUE__", config.LibImage) + manifestStr = strings.ReplaceAll(manifestStr, "__CONTAINER_RUNTIME_VALUE__", config.ContainerRuntime) + manifestStr = strings.ReplaceAll(manifestStr, "__SOCKET_PATH_VALUE__", config.SocketPath) + manifestStr = strings.ReplaceAll(manifestStr, "__DESTINATION_IPS_VALUE__", config.DestinationIPs) + manifestStr = strings.ReplaceAll(manifestStr, "__DESTINATION_HOSTS_VALUE__", config.DestinationHosts) + manifestStr = strings.ReplaceAll(manifestStr, "__SEQUENCE_VALUE__", config.Sequence) + + // For network tests, completely remove NODE_LABEL environment variable + nodeLabelRegex1 := regexp.MustCompile(`(?m)^\s*-\s+name:\s+NODE_LABEL\s+value:\s+.*$`) + nodeLabelRegex2 := regexp.MustCompile(`(?m)^\s*-\s+name:\s+["']?NODE_LABEL["']?\s+value:\s+.*$`) + nodeLabelRegex3 := regexp.MustCompile(`(?m)^\s*name:\s+["']?NODE_LABEL["']?\s+value:\s+.*$`) + + manifestStr = nodeLabelRegex1.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex2.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex3.ReplaceAllString(manifestStr, "") + + // Directly replace any target with nodeLabel + targetNodeLabelRegex1 := regexp.MustCompile(`target:\s*{nodeLabel:\s*[^}]*}`) + targetNodeLabelRegex2 := regexp.MustCompile(`"target":\s*"{nodeLabel:\s*[^}]*}"`) + targetNodeLabelRegex3 := regexp.MustCompile(`"target":\s*"?{nodeLabel:[^}]*}"?`) + targetNodeLabelRegex4 := regexp.MustCompile(`target:[^{]*{nodeLabel:[^}]*}`) + + manifestStr = targetNodeLabelRegex1.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex2.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + manifestStr = targetNodeLabelRegex3.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + manifestStr = targetNodeLabelRegex4.ReplaceAllString(manifestStr, "target: {}") + + // Replace specific __NODE_LABEL_VALUE__ directly + manifestStr = strings.ReplaceAll(manifestStr, "__NODE_LABEL_VALUE__", "") + manifestStr = strings.ReplaceAll(manifestStr, "nodeLabel: ", "") + manifestStr = strings.ReplaceAll(manifestStr, "nodeLabel:", "") + + // Replace experiment-specific network parameters + switch experimentType { + case PodNetworkCorruption: + manifestStr = strings.ReplaceAll(manifestStr, "__NETWORK_PACKET_CORRUPTION_PERCENTAGE_VALUE__", config.NetworkPacketCorruptionPercentage) + case PodNetworkLatency: + manifestStr = strings.ReplaceAll(manifestStr, "__NETWORK_LATENCY_VALUE__", config.NetworkLatency) + manifestStr = strings.ReplaceAll(manifestStr, "__JITTER_VALUE__", config.Jitter) + case PodNetworkLoss: + manifestStr = strings.ReplaceAll(manifestStr, "__NETWORK_PACKET_LOSS_PERCENTAGE_VALUE__", config.NetworkPacketLossPercentage) + case PodNetworkDuplication: + manifestStr = strings.ReplaceAll(manifestStr, "__NETWORK_PACKET_DUPLICATION_PERCENTAGE_VALUE__", config.NetworkPacketDuplicationPercentage) + } + } else { + // Replace non-network specific placeholders + switch experimentType { + case PodCPUHog: + manifestStr = strings.ReplaceAll(manifestStr, "__CPU_CORES_VALUE__", config.CPUCores) + case PodMemoryHog: + manifestStr = strings.ReplaceAll(manifestStr, "__MEMORY_CONSUMPTION_VALUE__", config.MemoryConsumption) + case PodAutoscaler: + manifestStr = strings.ReplaceAll(manifestStr, "__REPLICA_COUNT_VALUE__", config.ReplicaCount) + case ContainerKill: + manifestStr = strings.ReplaceAll(manifestStr, "__SIGNAL_VALUE__", config.Signal) + case DiskFill: + manifestStr = strings.ReplaceAll(manifestStr, "__FILL_PERCENTAGE_VALUE__", config.FillPercentage) + manifestStr = strings.ReplaceAll(manifestStr, "__DATA_BLOCK_SIZE_VALUE__", config.DataBlockSize) + manifestStr = strings.ReplaceAll(manifestStr, "__EPHEMERAL_STORAGE_MEBIBYTES_VALUE__", config.EphemeralStorageMebibytes) + + // Handle NODE_LABEL specially for DiskFill experiment - if it's empty, remove the entire env var entry + if config.NodeLabel == "" { + // More aggressive pattern match for disk-fill + nodeLabelRegex1 := regexp.MustCompile(`\s*-\s+name:\s+NODE_LABEL\s+value:\s+["']?__NODE_LABEL_VALUE__["']?\s*`) + nodeLabelRegex2 := regexp.MustCompile(`\s*-\s+name:\s+["']?NODE_LABEL["']?\s+value:\s+.*\s*`) + nodeLabelRegex3 := regexp.MustCompile(`\s*name:\s+["']?NODE_LABEL["']?\s+value:\s+.*\s*`) + + manifestStr = nodeLabelRegex1.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex2.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex3.ReplaceAllString(manifestStr, "") + + // For yaml target field with nodeLabel - matching more formats + targetNodeLabelRegex1 := regexp.MustCompile(`target:\s*{nodeLabel:\s*__NODE_LABEL_VALUE__}`) + targetNodeLabelRegex2 := regexp.MustCompile(`"target":\s*"{nodeLabel:\s*__NODE_LABEL_VALUE__}"`) + targetNodeLabelRegex3 := regexp.MustCompile(`target:\s*["{]\s*nodeLabel:\s*__NODE_LABEL_VALUE__\s*[}"]`) + targetNodeLabelRegex4 := regexp.MustCompile(`"target":\s*"?{nodeLabel:\s*__NODE_LABEL_VALUE__}"?`) + + manifestStr = targetNodeLabelRegex1.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex2.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + manifestStr = targetNodeLabelRegex3.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex4.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + } else { + manifestStr = strings.ReplaceAll(manifestStr, "__NODE_LABEL_VALUE__", config.NodeLabel) + } + case NodeCPUHog: + // NODE_LABEL specific handling (similar to disk-fill) + if config.NodeLabel == "" { + // Remove NODE_LABEL environment variable if empty + nodeLabelRegex1 := regexp.MustCompile(`\s*-\s+name:\s+NODE_LABEL\s+value:\s+["']?__NODE_LABEL_VALUE__["']?\s*`) + nodeLabelRegex2 := regexp.MustCompile(`\s*-\s+name:\s+["']?NODE_LABEL["']?\s+value:\s+.*\s*`) + nodeLabelRegex3 := regexp.MustCompile(`\s*name:\s+["']?NODE_LABEL["']?\s+value:\s+.*\s*`) + + manifestStr = nodeLabelRegex1.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex2.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex3.ReplaceAllString(manifestStr, "") + + // For yaml target field with nodeLabel - matching more formats + targetNodeLabelRegex1 := regexp.MustCompile(`target:\s*{nodeLabel:\s*__NODE_LABEL_VALUE__}`) + targetNodeLabelRegex2 := regexp.MustCompile(`"target":\s*"{nodeLabel:\s*__NODE_LABEL_VALUE__}"`) + targetNodeLabelRegex3 := regexp.MustCompile(`target:\s*["{]\s*nodeLabel:\s*__NODE_LABEL_VALUE__\s*[}"]`) + targetNodeLabelRegex4 := regexp.MustCompile(`"target":\s*"?{nodeLabel:\s*__NODE_LABEL_VALUE__}"?`) + + manifestStr = targetNodeLabelRegex1.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex2.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + manifestStr = targetNodeLabelRegex3.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex4.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + } else { + manifestStr = strings.ReplaceAll(manifestStr, "__NODE_LABEL_VALUE__", config.NodeLabel) + } + case NodeMemoryHog: + // Replace memory consumption values + manifestStr = strings.ReplaceAll(manifestStr, "__MEMORY_CONSUMPTION_PERCENTAGE_VALUE__", config.MemoryConsumptionPercentage) + manifestStr = strings.ReplaceAll(manifestStr, "__MEMORY_CONSUMPTION_MEBIBYTES_VALUE__", config.MemoryConsumptionMebibytes) + manifestStr = strings.ReplaceAll(manifestStr, "__NUMBER_OF_WORKERS_VALUE__", config.NumberOfWorkers) + manifestStr = strings.ReplaceAll(manifestStr, "__TARGET_NODES_VALUE__", config.TargetPods) + manifestStr = strings.ReplaceAll(manifestStr, "__NODES_AFFECTED_PERC_VALUE__", config.PodsAffectedPerc) + + // Handle NODE_LABEL specially - if it's empty, replace with empty string + if config.NodeLabel == "" { + // Remove NODE_LABEL environment variable if empty + nodeLabelRegex1 := regexp.MustCompile(`\s*-\s+name:\s+NODE_LABEL\s+value:\s+["']?__NODE_LABEL_VALUE__["']?\s*`) + nodeLabelRegex2 := regexp.MustCompile(`\s*-\s+name:\s+["']?NODE_LABEL["']?\s+value:\s+.*\s*`) + nodeLabelRegex3 := regexp.MustCompile(`\s*name:\s+["']?NODE_LABEL["']?\s+value:\s+.*\s*`) + + manifestStr = nodeLabelRegex1.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex2.ReplaceAllString(manifestStr, "") + manifestStr = nodeLabelRegex3.ReplaceAllString(manifestStr, "") + + // For yaml target field with nodeLabel - matching more formats + targetNodeLabelRegex1 := regexp.MustCompile(`target:\s*{nodeLabel:\s*__NODE_LABEL_VALUE__}`) + targetNodeLabelRegex2 := regexp.MustCompile(`"target":\s*"{nodeLabel:\s*__NODE_LABEL_VALUE__}"`) + targetNodeLabelRegex3 := regexp.MustCompile(`target:\s*["{]\s*nodeLabel:\s*__NODE_LABEL_VALUE__\s*[}"]`) + targetNodeLabelRegex4 := regexp.MustCompile(`"target":\s*"?{nodeLabel:\s*__NODE_LABEL_VALUE__}"?`) + + manifestStr = targetNodeLabelRegex1.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex2.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + manifestStr = targetNodeLabelRegex3.ReplaceAllString(manifestStr, "target: {}") + manifestStr = targetNodeLabelRegex4.ReplaceAllString(manifestStr, "\"target\": \"{}\"") + } else { + manifestStr = strings.ReplaceAll(manifestStr, "__NODE_LABEL_VALUE__", config.NodeLabel) + } + } + } + + return manifestStr, nil +} + +func getExperimentTemplates(experimentType ExperimentType, config ExperimentConfig) ([]map[string]interface{}, error) { + var templates []map[string]interface{} + + // Artifact name and path matching the working YAML + installTemplate := map[string]interface{}{ + "name": "install-chaos-faults", + "inputs": map[string]interface{}{ + "artifacts": []map[string]interface{}{ + { + "name": string(experimentType) + "-ce5", + "path": "/tmp/" + string(experimentType) + "-ce5.yaml", + "raw": map[string]interface{}{ + "data": getChaosExperimentData(experimentType), + }, + }, + }, + }, + "container": map[string]interface{}{ + "name": "", + "image": "litmuschaos/k8s:2.11.0", + "command": []string{"sh", "-c"}, + "args": []string{ + "kubectl apply -f /tmp/ -n {{workflow.parameters.adminModeNamespace}} && sleep 30", + }, + "resources": map[string]interface{}{}, + }, + } + + // Create the raw data string for the chaos engine + engineData := getChaosEngineData(experimentType) + + // Create a raw string version of the probe annotation to directly insert into the YAML + probeAnnotation := fmt.Sprintf("probeRef: '[{\"name\":\"%s\",\"mode\":\"%s\"}]'", + config.ProbeName, config.ProbeMode) + + // Add the annotation directly into the YAML string + engineData = strings.Replace( + engineData, + "metadata:", + "metadata:\n annotations:\n " + probeAnnotation, + 1) + + runTemplate := map[string]interface{}{ + "name": string(experimentType) + "-ce5", + "inputs": map[string]interface{}{ + "artifacts": []map[string]interface{}{ + { + "name": string(experimentType) + "-ce5", + "path": "/tmp/" + string(experimentType) + "-ce5.yaml", + "raw": map[string]interface{}{ + "data": engineData, + }, + }, + }, + }, + "outputs": map[string]interface{}{}, + "metadata": map[string]interface{}{ + "labels": map[string]string{ + "weight": "10", + }, + }, + "container": map[string]interface{}{ + "name": "", + "image": "docker.io/litmuschaos/litmus-checker:2.11.0", + "args": []string{ + "-file=/tmp/" + string(experimentType) + "-ce5.yaml", + "-saveName=/tmp/engine-name", + }, + "resources": map[string]interface{}{}, + }, + } + + cleanupTemplate := map[string]interface{}{ + "name": "cleanup-chaos-resources", + "inputs": map[string]interface{}{}, + "outputs": map[string]interface{}{}, + "metadata": map[string]interface{}{}, + "container": map[string]interface{}{ + "name": "", + "image": "litmuschaos/k8s:2.11.0", + "command": []string{"sh", "-c"}, + "args": []string{ + "kubectl delete chaosengine -l workflow_run_id={{ workflow.uid }} -n {{workflow.parameters.adminModeNamespace}}", + }, + "resources": map[string]interface{}{}, + }, + } + + templates = append(templates, installTemplate, runTemplate, cleanupTemplate) + return templates, nil +} + +// getChaosExperimentData returns the ChaosExperiment definition for the specified experiment type +func getChaosExperimentData(experimentType ExperimentType) string { + switch experimentType { + case PodDelete: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Deletes a pod belonging to a deployment/statefulset/daemonset +kind: ChaosExperiment +metadata: + name: pod-delete +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + # Additional permissions omitted for brevity + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + imagePullPolicy: Always + args: + - -c + - ./experiments -name pod-delete + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + - name: KILL_COUNT + value: '' + - name: FORCE + value: 'true' + - name: CHAOS_INTERVAL + value: '__CHAOS_INTERVAL_VALUE__' + labels: + name: pod-delete` + case PodCPUHog: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects cpu consumption on pods belonging to an app deployment +kind: ChaosExperiment +metadata: + name: pod-cpu-hog +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + - "batch" + - "litmuschaos.io" + resources: + - "jobs" + - "pods" + - "pods/log" + - "events" + - "chaosengines" + - "chaosexperiments" + - "chaosresults" + verbs: + - "create" + - "list" + - "get" + - "patch" + - "update" + - "delete" + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + args: + - -c + - ./experiments -name pod-cpu-hog + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: CHAOS_INTERVAL + value: '__CHAOS_INTERVAL_VALUE__' + - name: CPU_CORES + value: '__CPU_CORES_VALUE__' + - name: PODS_AFFECTED_PERC + value: '__PODS_AFFECTED_PERC_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + labels: + name: pod-cpu-hog` + + case PodMemoryHog: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects memory consumption on pods belonging to an app deployment +kind: ChaosExperiment +metadata: + name: pod-memory-hog +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + - "batch" + - "litmuschaos.io" + resources: + - "jobs" + - "pods" + - "pods/log" + - "events" + - "chaosengines" + - "chaosexperiments" + - "chaosresults" + verbs: + - "create" + - "list" + - "get" + - "patch" + - "update" + - "delete" + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + args: + - -c + - ./experiments -name pod-memory-hog + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: CHAOS_INTERVAL + value: '__CHAOS_INTERVAL_VALUE__' + - name: MEMORY_CONSUMPTION + value: '__MEMORY_CONSUMPTION_VALUE__' + - name: PODS_AFFECTED_PERC + value: '__PODS_AFFECTED_PERC_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + labels: + name: pod-memory-hog` + + case PodNetworkCorruption: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Inject network packet corruption into application pod +kind: ChaosExperiment +metadata: + name: pod-network-corruption + labels: + name: pod-network-corruption + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0 + imagePullPolicy: Always + args: + - -c + - ./experiments -name pod-network-corruption + command: + - /bin/bash + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_PACKET_CORRUPTION_PERCENTAGE + value: "__NETWORK_PACKET_CORRUPTION_PERCENTAGE_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__" + labels: + name: pod-network-corruption` + + case PodNetworkLatency: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects network latency on pods belonging to an app deployment +kind: ChaosExperiment +metadata: + name: pod-network-latency + labels: + name: pod-network-latency + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0 + imagePullPolicy: Always + args: + - -c + - ./experiments -name pod-network-latency + command: + - /bin/bash + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_LATENCY + value: "__NETWORK_LATENCY_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: JITTER + value: "__JITTER_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__" + labels: + name: pod-network-latency` + + case PodNetworkLoss: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects network packet loss on pods belonging to an app deployment +kind: ChaosExperiment +metadata: + name: pod-network-loss + labels: + name: pod-network-loss + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0 + imagePullPolicy: Always + args: + - -c + - ./experiments -name pod-network-loss + command: + - /bin/bash + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_PACKET_LOSS_PERCENTAGE + value: "__NETWORK_PACKET_LOSS_PERCENTAGE_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__" + labels: + name: pod-network-loss` + + case PodNetworkDuplication: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects network packet duplication on pods belonging to an app deployment +kind: ChaosExperiment +metadata: + name: pod-network-duplication + labels: + name: pod-network-duplication + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0 + imagePullPolicy: Always + args: + - -c + - ./experiments -name pod-network-duplication + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: NETWORK_PACKET_DUPLICATION_PERCENTAGE + value: "__NETWORK_PACKET_DUPLICATION_PERCENTAGE_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__" + labels: + name: pod-network-duplication` + + case PodAutoscaler: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Scale the application replicas and test the node autoscaling on cluster +kind: ChaosExperiment +metadata: + name: pod-autoscaler + labels: + name: pod-autoscaler + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Cluster + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + - apiGroups: + - "" + resources: + - events + verbs: + - create + - get + - list + - patch + - update + - apiGroups: + - "" + resources: + - configmaps + verbs: + - get + - list + - apiGroups: + - "" + resources: + - pods/log + verbs: + - get + - list + - watch + - apiGroups: + - "" + resources: + - pods/exec + verbs: + - get + - list + - create + - apiGroups: + - apps + resources: + - deployments + - statefulsets + verbs: + - list + - get + - patch + - update + - apiGroups: + - batch + resources: + - jobs + verbs: + - create + - list + - get + - delete + - deletecollection + - apiGroups: + - litmuschaos.io + resources: + - chaosengines + - chaosexperiments + - chaosresults + verbs: + - create + - list + - get + - patch + - update + - delete + image: litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0 + imagePullPolicy: Always + args: + - -c + - ./experiments -name pod-autoscaler + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: REPLICA_COUNT + value: "__REPLICA_COUNT_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + labels: + name: pod-autoscaler + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: experiment-job + app.kubernetes.io/version: 3.16.0` + + case ContainerKill: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Kills a container belonging to an application pod +kind: ChaosExperiment +metadata: + name: container-kill + labels: + name: container-kill + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + imagePullPolicy: Always + args: + - -c + - ./experiments -name container-kill + command: + - /bin/bash + env: + - name: TARGET_CONTAINER + value: '__TARGET_CONTAINER_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + - name: TARGET_PODS + value: '__TARGET_PODS_VALUE__' + - name: CHAOS_INTERVAL + value: '__CHAOS_INTERVAL_VALUE__' + - name: SIGNAL + value: '__SIGNAL_VALUE__' + - name: SOCKET_PATH + value: '/run/containerd/containerd.sock' + - name: CONTAINER_RUNTIME + value: 'containerd' + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: PODS_AFFECTED_PERC + value: '__PODS_AFFECTED_PERC_VALUE__' + - name: DEFAULT_HEALTH_CHECK + value: '__DEFAULT_HEALTH_CHECK_VALUE__' + - name: LIB_IMAGE + value: 'litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0' + - name: SEQUENCE + value: 'parallel' + labels: + name: container-kill` + + case DiskFill: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Fillup Ephemeral Storage of a Resource +kind: ChaosExperiment +metadata: + name: disk-fill + labels: + name: disk-fill + app.kubernetes.io/part-of: litmus + app.kubernetes.io/component: chaosexperiment + app.kubernetes.io/version: 3.16.0 +spec: + definition: + scope: Namespaced + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + imagePullPolicy: Always + args: + - -c + - ./experiments -name disk-fill + command: + - /bin/bash + env: + - name: TARGET_CONTAINER + value: '__TARGET_CONTAINER_VALUE__' + - name: FILL_PERCENTAGE + value: '__FILL_PERCENTAGE_VALUE__' + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + - name: DATA_BLOCK_SIZE + value: '__DATA_BLOCK_SIZE_VALUE__' + - name: TARGET_PODS + value: '__TARGET_PODS_VALUE__' + - name: EPHEMERAL_STORAGE_MEBIBYTES + value: '__EPHEMERAL_STORAGE_MEBIBYTES_VALUE__' + - name: PODS_AFFECTED_PERC + value: '__PODS_AFFECTED_PERC_VALUE__' + - name: DEFAULT_HEALTH_CHECK + value: '__DEFAULT_HEALTH_CHECK_VALUE__' + - name: LIB_IMAGE + value: 'litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0' + - name: SOCKET_PATH + value: '/run/containerd/containerd.sock' + - name: CONTAINER_RUNTIME + value: 'containerd' + - name: SEQUENCE + value: 'parallel' + labels: + name: disk-fill` + + case NodeCPUHog: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects cpu consumption on node +kind: ChaosExperiment +metadata: + name: node-cpu-hog + labels: + name: node-cpu-hog +spec: + definition: + scope: Cluster + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + imagePullPolicy: Always + args: + - -c + - ./experiments -name node-cpu-hog + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + - name: NODE_CPU_CORE + value: '' + - name: CPU_LOAD + value: '100' + - name: NODES_AFFECTED_PERC + value: '__PODS_AFFECTED_PERC_VALUE__' + - name: TARGET_NODES + value: '__TARGET_PODS_VALUE__' + - name: DEFAULT_HEALTH_CHECK + value: '__DEFAULT_HEALTH_CHECK_VALUE__' + - name: LIB_IMAGE + value: 'litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0' + - name: SEQUENCE + value: 'parallel' + labels: + name: node-cpu-hog` + + case NodeMemoryHog: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Give a memory hog on a node belonging to a deployment +kind: ChaosExperiment +metadata: + name: node-memory-hog + labels: + name: node-memory-hog +spec: + definition: + scope: Cluster + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + - apiGroups: + - "" + resources: + - events + verbs: + - create + - get + - list + - patch + - update + - apiGroups: + - "" + resources: + - configmaps + verbs: + - get + - list + - apiGroups: + - "" + resources: + - pods/log + verbs: + - get + - list + - watch + - apiGroups: + - "" + resources: + - pods/exec + verbs: + - get + - list + - create + - apiGroups: + - batch + resources: + - jobs + verbs: + - create + - list + - get + - delete + - deletecollection + - apiGroups: + - litmuschaos.io + resources: + - chaosengines + - chaosexperiments + - chaosresults + verbs: + - create + - list + - get + - patch + - update + - delete + - apiGroups: + - "" + resources: + - nodes + verbs: + - get + - list + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + imagePullPolicy: Always + args: + - -c + - ./experiments -name node-memory-hog + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + - name: MEMORY_CONSUMPTION_PERCENTAGE + value: '__MEMORY_CONSUMPTION_PERCENTAGE_VALUE__' + - name: MEMORY_CONSUMPTION_MEBIBYTES + value: '__MEMORY_CONSUMPTION_MEBIBYTES_VALUE__' + - name: NUMBER_OF_WORKERS + value: '__NUMBER_OF_WORKERS_VALUE__' + - name: TARGET_NODES + value: '__TARGET_NODES_VALUE__' + - name: NODES_AFFECTED_PERC + value: '__NODES_AFFECTED_PERC_VALUE__' + - name: DEFAULT_HEALTH_CHECK + value: '__DEFAULT_HEALTH_CHECK_VALUE__' + - name: LIB_IMAGE + value: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + - name: SEQUENCE + value: "parallel" + labels: + name: node-memory-hog` + + case NodeIOStress: + return `apiVersion: litmuschaos.io/v1alpha1 +description: + message: | + Injects IO stress on node +kind: ChaosExperiment +metadata: + name: node-io-stress + labels: + name: node-io-stress +spec: + definition: + scope: Cluster + permissions: + - apiGroups: + - "" + resources: + - pods + verbs: + - create + - delete + - get + - list + - patch + - update + - deletecollection + image: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + imagePullPolicy: Always + args: + - -c + - ./experiments -name node-io-stress + command: + - /bin/bash + env: + - name: TOTAL_CHAOS_DURATION + value: '__CHAOS_DURATION_VALUE__' + - name: RAMP_TIME + value: '__RAMP_TIME_VALUE__' + - name: FILESYSTEM_UTILIZATION_PERCENTAGE + value: '10' + - name: FILESYSTEM_UTILIZATION_BYTES + value: '' + - name: NODES_AFFECTED_PERC + value: '__PODS_AFFECTED_PERC_VALUE__' + - name: TARGET_NODES + value: '__TARGET_PODS_VALUE__' + - name: DEFAULT_HEALTH_CHECK + value: '__DEFAULT_HEALTH_CHECK_VALUE__' + - name: LIB_IMAGE + value: 'litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0' + - name: SEQUENCE + value: 'parallel' + labels: + name: node-io-stress` + + default: + return "" + } +} + +// getChaosEngineData returns the ChaosEngine definition for the specified experiment type +func getChaosEngineData(experimentType ExperimentType) string { + switch experimentType { + case PodDelete: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-delete-ce5 +spec: + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + engineState: active + chaosServiceAccount: litmus-admin + experiments: + - name: pod-delete + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: FORCE + value: "true" + - name: CHAOS_INTERVAL + value: "__CHAOS_INTERVAL_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__"` + + case PodCPUHog: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-cpu-hog-ce5 +spec: + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + engineState: active + chaosServiceAccount: litmus-admin + experiments: + - name: pod-cpu-hog + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: CPU_CORES + value: "__CPU_CORES_VALUE__" + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__"` + + case PodMemoryHog: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-memory-hog-ce5 +spec: + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + engineState: active + chaosServiceAccount: litmus-admin + experiments: + - name: pod-memory-hog + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: MEMORY_CONSUMPTION + value: "__MEMORY_CONSUMPTION_VALUE__" + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__"` + + case PodNetworkCorruption: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-network-corruption-ce5 +spec: + engineState: active + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: pod-network-corruption + spec: + components: + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_PACKET_CORRUPTION_PERCENTAGE + value: "__NETWORK_PACKET_CORRUPTION_PERCENTAGE_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__"` + + case PodNetworkLatency: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-network-latency-ce5 +spec: + engineState: active + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: pod-network-latency + spec: + components: + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_LATENCY + value: "__NETWORK_LATENCY_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: JITTER + value: "__JITTER_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__"` + + case PodNetworkLoss: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-network-loss-ce5 +spec: + engineState: active + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: pod-network-loss + spec: + components: + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_PACKET_LOSS_PERCENTAGE + value: "__NETWORK_PACKET_LOSS_PERCENTAGE_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__"` + + case PodNetworkDuplication: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-network-duplication-ce5 +spec: + engineState: active + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: pod-network-duplication + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: TC_IMAGE + value: "__TC_IMAGE_VALUE__" + - name: NETWORK_INTERFACE + value: "__NETWORK_INTERFACE_VALUE__" + - name: NETWORK_PACKET_DUPLICATION_PERCENTAGE + value: "__NETWORK_PACKET_DUPLICATION_PERCENTAGE_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: NODE_LABEL + value: "__NODE_LABEL_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: LIB_IMAGE + value: "__LIB_IMAGE_VALUE__" + - name: CONTAINER_RUNTIME + value: "__CONTAINER_RUNTIME_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: DESTINATION_IPS + value: "__DESTINATION_IPS_VALUE__" + - name: DESTINATION_HOSTS + value: "__DESTINATION_HOSTS_VALUE__" + - name: SOCKET_PATH + value: "__SOCKET_PATH_VALUE__" + - name: SEQUENCE + value: "__SEQUENCE_VALUE__"` + + case PodAutoscaler: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + name: nginx-chaos + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: pod-autoscaler-ce5 +spec: + engineState: active + auxiliaryAppInfo: "" + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: pod-autoscaler + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: REPLICA_COUNT + value: "__REPLICA_COUNT_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__"` + + case ContainerKill: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: container-kill-ce5 +spec: + engineState: active + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: container-kill + spec: + components: + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: CHAOS_INTERVAL + value: "__CHAOS_INTERVAL_VALUE__" + - name: SIGNAL + value: "__SIGNAL_VALUE__" + - name: SOCKET_PATH + value: "/run/containerd/containerd.sock" + - name: CONTAINER_RUNTIME + value: "containerd" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: LIB_IMAGE + value: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + - name: SEQUENCE + value: "parallel"` + + case DiskFill: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: disk-fill-ce5 +spec: + engineState: active + appinfo: + appns: __APP_NAMESPACE__ + applabel: __APP_LABEL__ + appkind: __APP_KIND__ + chaosServiceAccount: litmus-admin + experiments: + - name: disk-fill + spec: + components: + env: + - name: TARGET_CONTAINER + value: "__TARGET_CONTAINER_VALUE__" + - name: FILL_PERCENTAGE + value: "__FILL_PERCENTAGE_VALUE__" + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: DATA_BLOCK_SIZE + value: "__DATA_BLOCK_SIZE_VALUE__" + - name: TARGET_PODS + value: "__TARGET_PODS_VALUE__" + - name: EPHEMERAL_STORAGE_MEBIBYTES + value: "__EPHEMERAL_STORAGE_MEBIBYTES_VALUE__" + - name: PODS_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: LIB_IMAGE + value: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + - name: SOCKET_PATH + value: "/run/containerd/containerd.sock" + - name: CONTAINER_RUNTIME + value: "containerd" + - name: SEQUENCE + value: "parallel"` + + case NodeCPUHog: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: node-cpu-hog-ce5 +spec: + engineState: active + annotationCheck: "false" + chaosServiceAccount: litmus-admin + experiments: + - name: node-cpu-hog + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: NODE_CPU_CORE + value: "" + - name: CPU_LOAD + value: "100" + - name: NODES_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_NODES + value: "__TARGET_PODS_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: SEQUENCE + value: "parallel"` + + case NodeMemoryHog: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: node-memory-hog-ce5 +spec: + engineState: active + annotationCheck: "false" + chaosServiceAccount: litmus-admin + experiments: + - name: node-memory-hog + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: MEMORY_CONSUMPTION_PERCENTAGE + value: "__MEMORY_CONSUMPTION_PERCENTAGE_VALUE__" + - name: MEMORY_CONSUMPTION_MEBIBYTES + value: "__MEMORY_CONSUMPTION_MEBIBYTES_VALUE__" + - name: NUMBER_OF_WORKERS + value: "__NUMBER_OF_WORKERS_VALUE__" + - name: TARGET_NODES + value: "__TARGET_NODES_VALUE__" + - name: NODES_AFFECTED_PERC + value: "__NODES_AFFECTED_PERC_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: LIB_IMAGE + value: "litmuschaos.docker.scarf.sh/litmuschaos/go-runner:3.16.0" + - name: SEQUENCE + value: "parallel"` + + case NodeIOStress: + return `apiVersion: litmuschaos.io/v1alpha1 +kind: ChaosEngine +metadata: + namespace: "{{workflow.parameters.adminModeNamespace}}" + labels: + workflow_run_id: "{{ workflow.uid }}" + workflow_name: __EXPERIMENT_NAME__ + generateName: node-io-stress-ce5 +spec: + engineState: active + annotationCheck: "false" + chaosServiceAccount: litmus-admin + experiments: + - name: node-io-stress + spec: + components: + env: + - name: TOTAL_CHAOS_DURATION + value: "__CHAOS_DURATION_VALUE__" + - name: RAMP_TIME + value: "__RAMP_TIME_VALUE__" + - name: FILESYSTEM_UTILIZATION_PERCENTAGE + value: "10" + - name: FILESYSTEM_UTILIZATION_BYTES + value: "" + - name: NODES_AFFECTED_PERC + value: "__PODS_AFFECTED_PERC_VALUE__" + - name: TARGET_NODES + value: "__TARGET_PODS_VALUE__" + - name: DEFAULT_HEALTH_CHECK + value: "__DEFAULT_HEALTH_CHECK_VALUE__" + - name: SEQUENCE + value: "parallel"` + + default: + return "" + } +} + +// Helper functions for constructing experiment requests with default configuration +func ConstructPodDeleteExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodDelete) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodDelete, config) +} + +func ConstructPodCPUHogExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodCPUHog) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodCPUHog, config) +} + +func ConstructPodMemoryHogExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodMemoryHog) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodMemoryHog, config) +} + +func ConstructPodNetworkCorruptionExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodNetworkCorruption) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodNetworkCorruption, config) +} + +func ConstructPodNetworkLatencyExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodNetworkLatency) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodNetworkLatency, config) +} + +func ConstructPodNetworkLossExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodNetworkLoss) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodNetworkLoss, config) +} + +func ConstructPodNetworkDuplicationExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodNetworkDuplication) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodNetworkDuplication, config) +} + +func ConstructPodAutoscalerExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(PodAutoscaler) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, PodAutoscaler, config) +} + +func ConstructContainerKillExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(ContainerKill) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, ContainerKill, config) +} + +func ConstructDiskFillExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(DiskFill) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, DiskFill, config) +} + +func ConstructNodeCPUHogExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(NodeCPUHog) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, NodeCPUHog, config) +} + +func ConstructNodeMemoryHogExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(NodeMemoryHog) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, NodeMemoryHog, config) +} + +func ConstructNodeIOStressExperimentRequest(details *types.ExperimentDetails, experimentID string, experimentName string) (*models.SaveChaosExperimentRequest, error) { + config := GetDefaultExperimentConfig(NodeIOStress) + applyProbeConfigFromEnv(&config) + return ConstructExperimentRequest(details, experimentID, experimentName, NodeIOStress, config) +} + +// applyProbeConfigFromEnv reads probe configuration from environment variables and applies them to the config +func applyProbeConfigFromEnv(config *ExperimentConfig) { + // Check if probe configuration is specified in environment variables + useExistingProbeStr := os.Getenv("LITMUS_USE_EXISTING_PROBE") + if useExistingProbeStr != "" { + useExistingProbe, err := strconv.ParseBool(useExistingProbeStr) + if err == nil { + config.UseExistingProbe = useExistingProbe + + // Get probe name and mode regardless of useExistingProbe value + probeName := os.Getenv("LITMUS_PROBE_NAME") + if probeName != "" { + config.ProbeName = probeName + } + + probeMode := os.Getenv("LITMUS_PROBE_MODE") + if probeMode != "" { + config.ProbeMode = probeMode + } + + if !useExistingProbe { + // We now support creating custom probes through the SDK. + // This is handled in the CreateProbe function which should be called before experiment creation. + // Environment variables LITMUS_CREATE_PROBE, LITMUS_PROBE_TYPE, etc. control probe creation. + log.Printf("Note: To create a custom probe, set LITMUS_CREATE_PROBE=true along with other probe parameters.") + log.Printf("For now, using specified probe details: %s with mode: %s\n", config.ProbeName, config.ProbeMode) + } else { + log.Printf("Using existing probe: %s with mode: %s\n", config.ProbeName, config.ProbeMode) + } + } else { + log.Printf("Warning: Failed to parse LITMUS_USE_EXISTING_PROBE environment variable: %v\n", err) + } + } else { + log.Printf("No probe configuration provided. Using default probe: %s with mode: %s\n", config.ProbeName, config.ProbeMode) + } +} + +// CreateProbe creates a probe using the experiment details +func CreateProbe(details *types.ExperimentDetails, sdkClient sdk.Client, litmusProjectID string) error { + if !details.CreateProbe { + log.Println("Skipping probe creation as LITMUS_CREATE_PROBE is not set to true") + return nil + } + + log.Printf("Creating a new probe with name: %s", details.ProbeName) + + // Setup defaults for HTTP probe + trueBool := true + desc := fmt.Sprintf("HTTP probe for %s", details.ProbeName) + + // Prepare probe request based on probe type + var probeReq probe.ProbeRequest + + switch details.ProbeType { + case "httpProbe": + probeReq = probe.ProbeRequest{ + Name: details.ProbeName, + Description: &desc, + Type: probe.ProbeTypeHTTPProbe, + InfrastructureType: probe.InfrastructureTypeKubernetes, + Tags: []string{"http", "probe", "chaos"}, + KubernetesHTTPProperties: &probe.KubernetesHTTPProbeRequest{ + ProbeTimeout: details.ProbeTimeout, + Interval: details.ProbeInterval, + Attempt: &details.ProbeAttempts, + URL: details.ProbeURL, + Method: &probe.Method{ + Get: &probe.GetMethod{ + ResponseCode: details.ProbeResponseCode, + Criteria: "==", + }, + }, + InsecureSkipVerify: &trueBool, + }, + } + case "cmdProbe": + probeReq = probe.ProbeRequest{ + Name: details.ProbeName, + Description: &desc, + Type: probe.ProbeTypeCMDProbe, + InfrastructureType: probe.InfrastructureTypeKubernetes, + Tags: []string{"cmd", "probe", "chaos"}, + KubernetesCMDProperties: &probe.KubernetesCMDProbeRequest{ + Command: "ls -l", + ProbeTimeout: details.ProbeTimeout, + Interval: details.ProbeInterval, + Attempt: &details.ProbeAttempts, + Comparator: &probe.ComparatorInput{ + Type: "string", + Criteria: "contains", + Value: "total", + }, + }, + } + default: + return fmt.Errorf("unsupported probe type: %s", details.ProbeType) + } + + // Create probe + createdProbe, err := sdkClient.Probes().Create(probeReq, litmusProjectID) + if err != nil { + log.Printf("Failed to create probe: %v", err) + return err + } + + log.Printf("Successfully created probe: %s", createdProbe.Name) + + details.CreatedProbeID = createdProbe.Name + return nil +} \ No newline at end of file