Skip to content

Commit

Permalink
update terraform-boot healthcheck method
Browse files Browse the repository at this point in the history
  • Loading branch information
jinyangyang222 committed Aug 21, 2023
1 parent db59b7e commit e3c67df
Show file tree
Hide file tree
Showing 5 changed files with 84 additions and 7 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@
import jakarta.validation.Valid;
import lombok.extern.slf4j.Slf4j;
import org.eclipse.xpanse.terraform.boot.models.SystemStatus;
import org.eclipse.xpanse.terraform.boot.models.enums.HealthStatus;
import org.eclipse.xpanse.terraform.boot.models.request.TerraformDeployRequest;
import org.eclipse.xpanse.terraform.boot.models.request.TerraformDestroyRequest;
import org.eclipse.xpanse.terraform.boot.models.request.async.TerraformAsyncDeployRequest;
Expand Down Expand Up @@ -55,12 +54,13 @@ public TerraformApiController(TerraformExecutor terraformExecutor) {
*/
@Tag(name = "Terraform", description = "APIs for running Terraform commands")
@Operation(description = "Check health of Terraform API service")
@GetMapping(value = "/health", produces = MediaType.APPLICATION_JSON_VALUE)
@GetMapping(value = "/health/{module_directory}", produces = MediaType.APPLICATION_JSON_VALUE)
@ResponseStatus(HttpStatus.OK)
public SystemStatus healthCheck() {
SystemStatus systemStatus = new SystemStatus();
systemStatus.setHealthStatus(HealthStatus.OK);
return systemStatus;
public SystemStatus healthCheck(
@Parameter(name = "module_directory",
description = "directory name where the Terraform module files exist.")
@PathVariable("module_directory") String moduleDirectory) {
return this.terraformExecutor.tfHealthCheck(moduleDirectory);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -92,4 +92,16 @@ public Response handleHttpMessageConversionException(HttpMessageConversionExcept
return Response.errorResponse(ResultType.BAD_PARAMETERS,
Collections.singletonList(failMessage));
}

/**
* Exception handler for TerraformHealthCheckException.
*/
@ExceptionHandler({TerraformHealthCheckException.class})
@ResponseStatus(HttpStatus.SERVICE_UNAVAILABLE)
public Response handleTerraformHealthCheckException(TerraformHealthCheckException ex) {
log.error("TerraformHealthCheckException: ", ex);
String failMessage = ex.getMessage();
return Response.errorResponse(ResultType.SERVICE_UNAVAILABLE,
Collections.singletonList(failMessage));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
/*
* SPDX-License-Identifier: Apache-2.0
* SPDX-FileCopyrightText: Huawei Inc.
*/

package org.eclipse.xpanse.terraform.boot.models.exceptions;

/**
* Used to indicate Terraform health check anomalies.
*/
public class TerraformHealthCheckException extends RuntimeException {

public TerraformHealthCheckException(String message) {
super(message);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,8 @@ public enum ResultType {
ACCESS_DENIED("Access Denied"),
SENSITIVE_FIELD_ENCRYPTION_DECRYPTION_EXCEPTION("Sensitive "
+ "Field Encryption Or Decryption Failed Exception"),
UNSUPPORTED_ENUM_VALUE("Unsupported Enum Value");
UNSUPPORTED_ENUM_VALUE("Unsupported Enum Value"),
SERVICE_UNAVAILABLE("Service Unavailable");

private final String value;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.nio.file.Files;
import java.util.Collections;
Expand All @@ -18,7 +19,10 @@
import java.util.Objects;
import lombok.NonNull;
import lombok.extern.slf4j.Slf4j;
import org.eclipse.xpanse.terraform.boot.models.SystemStatus;
import org.eclipse.xpanse.terraform.boot.models.enums.HealthStatus;
import org.eclipse.xpanse.terraform.boot.models.exceptions.TerraformExecutorException;
import org.eclipse.xpanse.terraform.boot.models.exceptions.TerraformHealthCheckException;
import org.eclipse.xpanse.terraform.boot.models.request.TerraformDeployRequest;
import org.eclipse.xpanse.terraform.boot.models.request.TerraformDestroyRequest;
import org.eclipse.xpanse.terraform.boot.models.request.async.TerraformAsyncDeployRequest;
Expand All @@ -41,6 +45,13 @@
public class TerraformExecutor {
private static final String VARS_FILE_NAME = "variables.tfvars.json";
private static final ObjectMapper OBJECT_MAPPER = new ObjectMapper();
private static final String OUTPUT_CONFIG_FILE_NAME = "hello-world.tf";
private static final String HELLO_WORLD_TEMPLATE = """
output "hello_world" {
value = "Hello, World!"
}
""";
private static final String HEALTH_CHECK_DIR = "health_check";

static {
OBJECT_MAPPER.setSerializationInclusion(JsonInclude.Include.NON_NULL);
Expand Down Expand Up @@ -254,6 +265,43 @@ public TerraformValidationResult tfValidate(String moduleDirectory) {
}
}

/**
* Performs a Terraform health check for the specified module directory.
*
* @return SystemStatus.
*/
public SystemStatus tfHealthCheck(String moduleDirectory) {
String filePath =
getModuleFullPath(moduleDirectory) + File.separator + HEALTH_CHECK_DIR
+ File.separator + OUTPUT_CONFIG_FILE_NAME;
try {
File file = new File(filePath);
if (!file.exists()) {
file.getParentFile().mkdirs();
file.createNewFile();
}
FileWriter writer = new FileWriter(filePath);
writer.write(HELLO_WORLD_TEMPLATE);
writer.close();
} catch (IOException e) {
throw new TerraformHealthCheckException(
"Error creating or writing to file '" + filePath + "': " + e.getMessage());
}
tfValidate(moduleDirectory + File.separator + HEALTH_CHECK_DIR);
SystemCmdResult systemCmdResult =
execute("terraform destroy -auto-approve -input=false -no-color ",
getModuleFullPath(moduleDirectory
+ File.separator + HEALTH_CHECK_DIR),
new HashMap<>());
SystemStatus systemStatus = new SystemStatus();
if (systemCmdResult.isCommandSuccessful()) {
systemStatus.setHealthStatus(HealthStatus.OK);
return systemStatus;
}
systemStatus.setHealthStatus(HealthStatus.NOK);
return systemStatus;
}

private String getModuleFullPath(String moduleDirectory) {
return this.moduleParentDirectoryPath + File.separator + moduleDirectory;
}
Expand Down

0 comments on commit e3c67df

Please sign in to comment.