use of com.thoughtworks.gocd.elasticagent.ecs.exceptions.ContainerFailedToRegisterException in project gocd-ecs-elastic-agent by gocd.
the class TaskHelper method create.
public Optional<ECSTask> create(CreateAgentRequest createAgentRequest, PluginSettings pluginSettings, ConsoleLogAppender consoleLogAppender) throws ContainerInstanceFailedToRegisterException, LimitExceededException, ContainerFailedToRegisterException {
final String taskName = "GoCD" + UUID.randomUUID().toString().replaceAll("-", "");
final ElasticAgentProfileProperties elasticAgentProfileProperties = createAgentRequest.elasticProfile();
ContainerDefinition containerDefinition = new ContainerDefinitionBuilder().withName(taskName).pluginSettings(pluginSettings).createAgentRequest(createAgentRequest).withServerId(getServerId()).build();
StopPolicy stopPolicy = elasticAgentProfileProperties.platform() == LINUX ? pluginSettings.getLinuxStopPolicy() : pluginSettings.getWindowsStopPolicy();
Optional<ContainerInstance> containerInstance = instanceSelectionStrategyFactory.strategyFor(stopPolicy).instanceForScheduling(pluginSettings, elasticAgentProfileProperties, containerDefinition);
if (!containerInstance.isPresent()) {
consoleLogAppender.accept("No running instance(s) found to build the ECS Task to perform current job.");
LOG.info(format("[create-agent] No running instances found to build container with profile {0}", createAgentRequest.elasticProfile().toJson()));
if (elasticAgentProfileProperties.runAsSpotInstance()) {
spotInstanceService.create(pluginSettings, elasticAgentProfileProperties, consoleLogAppender);
return Optional.empty();
} else {
containerInstance = containerInstanceHelper.startOrCreateOneInstance(pluginSettings, elasticAgentProfileProperties, consoleLogAppender);
}
} else {
consoleLogAppender.accept("Found existing running container instance platform matching ECS Task instance configuration. Not starting a new EC2 instance...");
}
final RegisterTaskDefinitionRequest registerTaskDefinitionRequest = registerTaskDefinitionRequestBuilder.build(pluginSettings, elasticAgentProfileProperties, containerDefinition).withFamily(taskName);
consoleLogAppender.accept("Registering ECS Task definition with cluster...");
LOG.debug(format("[create-agent] Registering task definition: {0} ", registerTaskDefinitionRequest.toString()));
RegisterTaskDefinitionResult taskDefinitionResult = pluginSettings.ecsClient().registerTaskDefinition(registerTaskDefinitionRequest);
consoleLogAppender.accept("Done registering ECS Task definition with cluster.");
LOG.debug("[create-agent] Done registering task definition");
TaskDefinition taskDefinitionFromNewTask = taskDefinitionResult.getTaskDefinition();
StartTaskRequest startTaskRequest = new StartTaskRequest().withTaskDefinition(taskDefinitionFromNewTask.getTaskDefinitionArn()).withContainerInstances(containerInstance.get().getContainerInstanceArn()).withCluster(pluginSettings.getClusterName());
consoleLogAppender.accept("Starting ECS Task to perform current job...");
LOG.debug(format("[create-agent] Starting task : {0} ", startTaskRequest.toString()));
StartTaskResult startTaskResult = pluginSettings.ecsClient().startTask(startTaskRequest);
LOG.debug("[create-agent] Done executing start task request.");
if (isStarted(startTaskResult)) {
String message = elasticAgentProfileProperties.runAsSpotInstance() ? "[WARNING] The ECS task is scheduled on a Spot Instance. A spot instance termination would re-schedule the job." : String.format("ECS Task %s scheduled on container instance %s.", taskName, containerInstance.get().getEc2InstanceId());
consoleLogAppender.accept(message);
LOG.info(format("[create-agent] Task {0} scheduled on container instance {1}", taskName, containerInstance.get().getEc2InstanceId()));
return Optional.of(new ECSTask(startTaskResult.getTasks().get(0), taskDefinitionFromNewTask, elasticAgentProfileProperties, createAgentRequest.getJobIdentifier(), createAgentRequest.environment(), containerInstance.get().getEc2InstanceId()));
} else {
deregisterTaskDefinition(pluginSettings, taskDefinitionFromNewTask.getTaskDefinitionArn());
String errors = startTaskResult.getFailures().stream().map(failure -> " " + failure.getArn() + " failed with reason :" + failure.getReason()).collect(Collectors.joining("\n"));
throw new ContainerFailedToRegisterException("Fail to start task " + taskName + ":\n" + errors);
}
}
use of com.thoughtworks.gocd.elasticagent.ecs.exceptions.ContainerFailedToRegisterException in project gocd-ecs-elastic-agent by gocd.
the class TaskHelperTest method shouldDeregisterTaskAndErrorOutIfFailsToCreateTask.
@Test
void shouldDeregisterTaskAndErrorOutIfFailsToCreateTask() throws Exception {
final InstanceSelectionStrategy instanceSelectionStrategy = mock(InstanceSelectionStrategy.class);
when(elasticAgentProfileProperties.getImage()).thenReturn("alpine");
when(ecsClient.registerTaskDefinition(any(RegisterTaskDefinitionRequest.class))).thenReturn(new RegisterTaskDefinitionResult().withTaskDefinition(new TaskDefinition().withTaskDefinitionArn("task-definition-arn")));
when(registerTaskDefinitionRequestBuilder.build(eq(pluginSettings), eq(elasticAgentProfileProperties), any(ContainerDefinition.class))).thenReturn(new RegisterTaskDefinitionRequest());
when(instanceSelectionStrategyFactory.strategyFor(any())).thenReturn(instanceSelectionStrategy);
when(instanceSelectionStrategy.instanceForScheduling(eq(pluginSettings), eq(elasticAgentProfileProperties), any(ContainerDefinition.class))).thenReturn(Optional.of(new ContainerInstance().withContainerInstanceArn("container-instance-arn")));
when(ecsClient.startTask(any(StartTaskRequest.class))).thenReturn(new StartTaskResult().withFailures(new Failure().withReason("Failed to start task.").withArn("task-arn")));
try {
taskHelper.create(createAgentRequest, pluginSettings, consoleLogAppender);
fail("Should fail");
} catch (ContainerFailedToRegisterException e) {
assertThat(e.getMessage()).contains("Failed to start task.");
}
verify(ecsClient).deregisterTaskDefinition(any(DeregisterTaskDefinitionRequest.class));
}
Aggregations