cloud-8.x-2.0-beta1/modules/cloud_service_providers/aws_cloud/tests/src/Functional/Ec2/InstanceTest.php
modules/cloud_service_providers/aws_cloud/tests/src/Functional/Ec2/InstanceTest.php
<?php
namespace Drupal\Tests\aws_cloud\Functional\Ec2;
use Drupal\Tests\aws_cloud\Functional\AwsCloudTestCase;
use Drupal\Tests\aws_cloud\Functional\Utils;
/**
* Tests AWS Cloud Instance for basic operations.
*
* @group AWS Cloud
*/
class InstanceTest extends AwsCloudTestCase {
/**
* Create three Instances for a test case.
*/
const AWS_CLOUD_INSTANCE_REPEAT_COUNT = 3;
/**
* {@inheritdoc}
*/
protected function getPermissions() {
return [
'add aws cloud instance',
'list aws cloud instance',
'edit own aws cloud instance',
'delete own aws cloud instance',
'view own aws cloud instance',
'edit any aws cloud instance',
'list cloud server template',
'view own published cloud server templates',
'launch cloud server template',
'add aws cloud image',
'list aws cloud image',
'view any aws cloud image',
'edit any aws cloud image',
'delete any aws cloud image',
'administer aws_cloud',
];
}
/**
* {@inheritdoc}
*/
protected function getMockDataTemplateVars() {
$public_ip = Utils::getRandomPublicIp();
$private_ip = Utils::getRandomPrivateIp();
$regions = ['us-west-1', 'us-west-2'];
$region = $regions[array_rand($regions)];
return [
// 12 digits.
'account_id' => mt_rand(100000000000, 999999999999),
'reservation_id' => 'r-' . $this->getRandomAwsId(),
'group_name' => $this->random->name(8, TRUE),
'host_id' => $this->random->name(8, TRUE),
'affinity' => $this->random->name(8, TRUE),
'launch_time' => date('c'),
'security_group_id' => 'sg-' . $this->getRandomAwsId(),
'security_group_name' => $this->random->name(10, TRUE),
'public_dns_name' => Utils::getPublicDns($region, $public_ip),
'public_ip_address' => $public_ip,
'private_dns_name' => Utils::getPrivateDns($region, $private_ip),
'private_ip_address' => $private_ip,
'vpc_id' => 'vpc-' . $this->getRandomAwsId(),
'subnet_id' => 'subnet-' . $this->getRandomAwsId(),
'image_id' => 'ami-' . $this->getRandomAwsId(),
'reason' => $this->random->string(16, TRUE),
'instance_id' => 'i-' . $this->getRandomAwsId(),
'state' => 'running',
];
}
/**
* Tests EC2 instance.
*/
public function testInstance() {
$cloud_context = $this->cloudContext;
// IAM Roles.
$iam_roles = $this->createIamRolesRandomTestFormData();
$this->updateIamRolesMockData($iam_roles);
// Add an empty value to IAM roles.
$iam_roles = array_merge([[]], $iam_roles);
// List Instance for Amazon EC2.
$this->drupalGet("/clouds/aws_cloud/${cloud_context}/instance");
$this->assertResponse(200, t('HTTP 200: List | Instance'));
$this->assertNoText(t('Notice'), t('List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('List | Make sure w/o Warnings'));
// Launch a new Instance.
$add = $this->createInstanceTestFormData(self::AWS_CLOUD_INSTANCE_REPEAT_COUNT);
for ($i = 0, $num = 1; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++, $num++) {
// Create image.
$image = $this->createImageTestEntity($i, $add[$i]['image_id'], $cloud_context);
// Make sure if the image entity is created or not.
$this->drupalGet("/clouds/aws_cloud/${cloud_context}/image");
$this->assertResponse(200, t('HTTP 200: Image | The new AWS Cloud Image #@num', ['@num' => $num]));
$this->assertNoText(t('warning'), t('Image | Make sure w/o Warnings'));
$this->assertText($image->getName(), t('Image | Make sure w/ Image Name (TestEntity): @name', ['@name' => $image->getName()]));
$this->assertText($image->getImageId(), t('Image | Make sure w/ Image ID (TestEntity): @image_id', ['@image_id' => $image->getImageId()]));
$this->assertText($add[$i]['image_id'], t('Image | Make sure w/ Image ID (TestFormData): @image_id', ['@image_id' => $add[$i]['image_id']]));
// Setup cloud server template and instance.
$server_template = $this->createServerTemplateTestEntity($iam_roles, $image, $cloud_context);
// Make sure if the cloud_server_template entity is created or not.
$this->drupalGet("/clouds/design/server_template/${cloud_context}");
$this->assertResponse(200, t('HTTP 200: CloudServerTemplate | The new CloudServerTemplate #@num', ['@num' => $num]));
$this->assertNoText(t('warning'), t('CloudServerTemplate | Make sure w/o Warnings'));
$this->assertText($server_template->name->value,
t('CloudServerTemplate | Make sure w/ CloudServerTemplate Name: @name', [
'@name' => $server_template->name->value,
])
);
$this->addInstanceMockData($add[$i]['name'], $add[$i]['key_pair_name']);
$this->drupalPostForm("/clouds/design/server_template/${cloud_context}/{$server_template->id()}/launch",
[],
t('Launch'));
$this->assertResponse(200, t('HTTP 200: Launch | The new Cloud Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Launch | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Launch | Make sure w/o Warnings'));
// Make sure listing.
for ($j = 0; $j < $i + 1; $j++) {
$this->assertText($add[$j]['name'], t('Make sure w/ Listing: @name', [
'@name' => $add[$j]['name'],
]));
}
}
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
// Make sure the all instance listing exists.
$this->drupalGet('/clouds/aws_cloud');
$this->assertResponse(200, t('Edit | List | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | List | Make sure w/o Warnings'));
for ($j = 0; $j < $i + 1; $j++) {
$this->assertText($add[$j]['name'], t('Make sure w/ Listing: @name', [
'@name' => $add[$j]['name'],
]));
}
}
// Edit an Instance information.
$edit = $this->createInstanceTestFormData(self::AWS_CLOUD_INSTANCE_REPEAT_COUNT);
for ($i = 0, $num = 1; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++, $num++) {
unset($edit[$i]['image_id']);
unset($edit[$i]['min_count']);
unset($edit[$i]['max_count']);
unset($edit[$i]['key_pair_name']);
unset($edit[$i]['is_monitoring']);
unset($edit[$i]['availability_zone']);
unset($edit[$i]['instance_type']);
unset($edit[$i]['kernel_id']);
unset($edit[$i]['ramdisk_id']);
unset($edit[$i]['user_data']);
// Change security groups.
$security_groups = $this->createSecurityGroupRandomTestFormData();
$this->updateDescribeSecurityGroupsMockData($security_groups);
$edit[$i]['security_groups[]'] = [array_column($security_groups, 'GroupName')[0]];
// Termination.
$edit[$i]['termination_timestamp[0][value][date]'] = date('Y-m-d', time() + 365.25 * 3);
$edit[$i]['termination_timestamp[0][value][time]'] = '00:00:00';
$edit[$i]['termination_protection'] = '1';
// IAM role.
$iam_role_index = array_rand($iam_roles);
if ($iam_role_index == 0) {
$iam_role_name = '';
$edit[$i]['iam_role'] = '';
}
else {
$iam_role = $iam_roles[$iam_role_index]['Arn'];
$iam_role_name = $iam_roles[$iam_role_index]['InstanceProfileName'];
$edit[$i]['iam_role'] = $iam_role;
}
$this->drupalPostForm("/clouds/aws_cloud/$cloud_context/instance/$num/edit",
$edit[$i],
t('Save'));
// Termination validation.
$this->assertText(
t(
'"@name1" should be left blank if "@name2" is selected. Please leave "@name1" blank or unselect "@name2".',
['@name1' => t('Termination Date'), '@name2' => t('Termination Protection')]
), 'Termination validation'
);
unset($edit[$i]['termination_timestamp[0][value][date]']);
unset($edit[$i]['termination_timestamp[0][value][time]']);
unset($edit[$i]['termination_protection']);
$this->drupalPostForm("/clouds/aws_cloud/$cloud_context/instance/$num/edit",
$edit[$i],
t('Save'));
$this->updateInstanceMockData($i, $edit[$i]['name']);
$this->assertResponse(200, t('Edit | HTTP 200: The new Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | Make sure w/o Warnings'));
$this->assertText(
t('The AWS Cloud Instance "@name" has been saved.', ['@name' => $edit[$i]['name']]),
t('Confirm Message: Edit | The AWS Cloud Instance "@name" has been saved.', [
'@name' => $edit[$i]['name'],
])
);
if ($iam_role_name != '') {
$this->assertText($iam_role_name);
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
$this->assertResponse(200, t('Edit | List | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | List | Make sure w/o Warnings'));
for ($j = 0; $j < $i + 1; $j++) {
$this->assertText(
$edit[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $edit[$i]['name'],
])
);
}
}
// Terminate Instance.
for ($i = 0, $num = 1; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++, $num++) {
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/$num/terminate");
$this->assertResponse(200, t('Terminate: HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Terminate | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Terminate | Make sure w/o Warnings'));
$this->deleteFirstInstanceMockData();
$this->drupalPostForm("/clouds/aws_cloud/$cloud_context/instance/$num/terminate",
[],
t('Delete | Terminate'));
$this->assertResponse(200, t('Terminate | HTTP 200: The Cloud Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Terminate | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Terminate | Make sure w/o Warnings'));
$this->assertText($edit[$i]['name'], t('Instance Name: @name', ['@name' => $edit[$i]['name']]));
$this->assertText(
t('The AWS Cloud Instance "@name" has been terminated.', ['@name' => $edit[$i]['name']]),
t('Confirm Message: Terminate | The AWS Cloud Instance "@name" has been terminated.', [
'@name' => $edit[$i]['name'],
]));
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
$this->assertResponse(200, t('Terminate | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Terminate | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Terminate | List | Make sure w/o Warnings'));
for ($j = 0; $j < $i + 1; $j++) {
$this->assertNoText($edit[$i]['name'],
t('Terminate | List | Make sure w/ Listing: @name', [
'@name' => $edit[$i]['name'],
]));
}
}
}
/**
* Tests updating instances.
*/
public function testUpdateInstances() {
$cloud_context = $this->cloudContext;
// IAM Roles.
$iam_roles = $this->createIamRolesRandomTestFormData();
$this->updateIamRolesMockData($iam_roles);
// Add an empty value to IAM roles.
$iam_roles = array_merge([[]], $iam_roles);
// Create image.
$add = $this->createInstanceTestFormData();
$image = $this->createImageTestEntity(0, $add[0]['image_id'], $cloud_context);
// Make sure if the image entity is created or not.
$this->drupalGet("/clouds/aws_cloud/${cloud_context}/image");
$this->assertResponse(200, t('HTTP 200: Image | The new AWS Cloud Image #@num', ['@num' => 1]));
$this->assertNoText(t('warning'), t('Image | Make sure w/o Warnings'));
$this->assertText($image->getName(), t('Image | Make sure w/ Image Name (TestEntity): @name', ['@name' => $image->getName()]));
$this->assertText($image->getImageId(), t('Image | Make sure w/ Image ID (TestEntity): @image_id', ['@image_id' => $image->getImageId()]));
$this->assertText($add[0]['image_id'], t('Image | Make sure w/ Image ID (TestFormData): @image_id', ['@image_id' => $add[0]['image_id']]));
// Setup cloud server template and instance.
$server_template = $this->createServerTemplateTestEntity($iam_roles, $image, $cloud_context);
// Make sure if the cloud_server_template entity is created or not.
$this->drupalGet("/clouds/design/server_template/${cloud_context}");
$this->assertResponse(200, t('HTTP 200: CloudServerTemplate | The new CloudServerTemplate #@num', ['@num' => 1]));
$this->assertNoText(t('warning'), t('CloudServerTemplate | Make sure w/o Warnings'));
$this->assertText($server_template->name->value,
t('CloudServerTemplate | Make sure w/ CloudServerTemplate Name: @name', [
'@name' => $server_template->name->value,
])
);
// Launch a new Instance.
$this->addInstanceMockData($add[0]['name'], $add[0]['key_pair_name']);
$this->drupalPostForm("/clouds/design/server_template/$cloud_context/1/launch",
[],
t('Launch'));
$this->assertResponse(200, t('HTTP 200: Launch | The new Cloud Instance 1'));
$this->assertNoText(t('Notice'), t('Launch | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Launch | Make sure w/o Warnings'));
// Change security groups.
$security_group_name1 = $this->random->name(8, TRUE);
$security_group_name2 = $this->random->name(8, TRUE);
$this->updateSecurityGroupsMockData($security_group_name1, $security_group_name2);
// Change instance type.
$instance_type = $this->random->name(6, TRUE);
$this->updateInstanceTypeMockData($instance_type);
// Update the schedule tag.
$schedule_value = $this->random->name(8, TRUE);
$this->updateScheduleTagMockData($schedule_value);
// Run cron job to update instances.
$key = \Drupal::state()->get('system.cron_key');
$this->drupalGet('/cron/' . $key);
$this->assertResponse(204);
// Verify schedule tag.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/1");
$this->assertResponse(200, t('View | HTTP 200: The Cloud Instance 1'));
$this->assertNoText(t('Notice'), t('View | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('View | Make sure w/o Warnings'));
$this->assertText("$schedule_value", t('Schedule'));
// Verify security group.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/1");
$this->assertResponse(200, t('View | HTTP 200: The Cloud Instance 1'));
$this->assertNoText(t('Notice'), t('View | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('View | Make sure w/o Warnings'));
$this->assertText("$security_group_name1, $security_group_name2", t('Security Group'));
$this->assertText($instance_type, t('Instance Type'));
}
/**
* Test validation of launching instances.
*/
public function testLaunchValidation() {
$this->repeatTestLaunchValidation(self::AWS_CLOUD_INSTANCE_REPEAT_COUNT);
}
/**
* Repeat testing validation of launching instances.
*
* @param int $max_test_repeat_count
* Max test repeating count.
*/
private function repeatTestLaunchValidation($max_test_repeat_count = 1) {
$cloud_context = $this->cloudContext;
// IAM Roles.
$iam_roles = $this->createIamRolesRandomTestFormData();
$this->updateIamRolesMockData($iam_roles);
// Add an empty value to IAM roles.
$iam_roles = array_merge([[]], $iam_roles);
// Launch a new Instance, with termination protection.
$add = $this->createInstanceTestFormData($max_test_repeat_count);
for ($i = 0, $num = 1; $i < $max_test_repeat_count; $i++, $num++) {
// Create image.
$image = $this->createImageTestEntity($i, $add[$i]['image_id'], $cloud_context);
// Make sure if the image entity is created or not.
$this->drupalGet("/clouds/aws_cloud/${cloud_context}/image");
$this->assertResponse(200, t('HTTP 200: Image | The new AWS Cloud Image #@num', ['@num' => $num]));
$this->assertNoText(t('warning'), t('Image | Make sure w/o Warnings'));
$this->assertText($image->getName(), t('Image | Make sure w/ Image Name (TestEntity): @name', ['@name' => $image->getName()]));
$this->assertText($image->getImageId(), t('Image | Make sure w/ Image ID (TestEntity): @image_id', ['@image_id' => $image->getImageId()]));
$this->assertText($add[$i]['image_id'], t('Image | Make sure w/ Image ID (TestFormData): @image_id', ['@image_id' => $add[$i]['image_id']]));
// Setup cloud server template and instance.
$server_template = $this->createServerTemplateTestEntity($iam_roles, $image, $cloud_context);
// Make sure if the cloud_server_template entity is created or not.
$this->drupalGet("/clouds/design/server_template/${cloud_context}");
$this->assertResponse(200, t('HTTP 200: CloudServerTemplate | The new CloudServerTemplate #@num', ['@num' => $num]));
$this->assertNoText(t('warning'), t('CloudServerTemplate | Make sure w/o Warnings'));
$this->assertText($server_template->name->value,
t('CloudServerTemplate | Make sure w/ CloudServerTemplate Name: @name', [
'@name' => $server_template->name->value,
])
);
$this->drupalPostForm("/clouds/design/server_template/$cloud_context/$num/launch",
[
'terminate' => '1',
'termination_protection' => '1',
],
t('Launch')
);
$this->assertText(
t('"@name1" and "@name2" can\'t be selected both. Please unselect one of them.',
[
'@name1' => t('Termination Protection'),
'@name2' => t('Automatically terminate instance'),
]
),
'Launch validation'
);
}
}
/**
* Tests updating instances.
*/
public function testUpdateInstanceList() {
$cloud_context = $this->cloudContext;
// IAM Roles.
$iam_roles = $this->createIamRolesRandomTestFormData();
$this->updateIamRolesMockData($iam_roles);
// Add an empty value to IAM roles.
$iam_roles = array_merge([[]], $iam_roles);
// Create image.
$add = $this->createInstanceTestFormData(self::AWS_CLOUD_INSTANCE_REPEAT_COUNT);
$image = $this->createImageTestEntity(0, $add[0]['image_id'], $cloud_context);
// Make sure if the image entity is created or not.
$this->drupalGet("/clouds/aws_cloud/${cloud_context}/image");
$this->assertResponse(200, t('HTTP 200: Image | The new AWS Cloud Image #@num', ['@num' => 1]));
$this->assertNoText(t('warning'), t('Image | Make sure w/o Warnings'));
$this->assertText($image->getName(), t('Image | Make sure w/ Image Name (TestEntity): @name', ['@name' => $image->getName()]));
$this->assertText($image->getImageId(), t('Image | Make sure w/ Image ID (TestEntity): @image_id', ['@image_id' => $image->getImageId()]));
$this->assertText($add[0]['image_id'], t('Image | Make sure w/ Image ID (TestFormData): @image_id', ['@image_id' => $add[0]['image_id']]));
// Setup cloud server template and instance.
$server_template = $this->createServerTemplateTestEntity($iam_roles, $image, $cloud_context);
// Make sure if the cloud_server_template entity is created or not.
$this->drupalGet("/clouds/design/server_template/${cloud_context}");
$this->assertResponse(200, t('HTTP 200: CloudServerTemplate | The new CloudServerTemplate #@num', ['@num' => 1]));
$this->assertNoText(t('warning'), t('CloudServerTemplate | Make sure w/o Warnings'));
$this->assertText($server_template->name->value,
t('CloudServerTemplate | Make sure w/ CloudServerTemplate Name: @name', [
'@name' => $server_template->name->value,
])
);
// Create Instances in mock data.
for ($i = 0, $num = 1; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++, $num++) {
$instance_id = $this->addInstanceMockData($add[$i]['name'], $add[$i]['key_pair_name']);
$add[$i]['instance_id'] = $instance_id;
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
$this->assertResponse(200, t('Edit | List | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | List | Make sure w/o Warnings'));
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoText($add[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $add[$i]['name'],
]));
}
// Click 'Refresh'.
$this->clickLink(t('Refresh'));
$this->assertText(t('Updated Instances.'));
// Make sure listing.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertText($add[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $add[$i]['name'],
]));
}
// Make sure detailed and edit view.
for ($i = 0, $num = 1; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++, $num++) {
// Confirm the detailed view.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/$num");
$this->assertLink(t('Edit'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/edit");
$this->assertNoLink(t('Start'));
$this->assertLink(t('Stop'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/stop");
$this->assertLink(t('Reboot'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/reboot");
$this->assertLink(t('Delete'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/terminate");
$this->assertNoLink(t('Associate Elastic IP'));
$this->assertLink(t('List AWS Cloud Instances'));
// Click 'Refresh'.
$this->clickLink(t('List AWS Cloud Instances'));
$this->assertResponse(200, t('Edit | List | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | List | Make sure w/o Warnings'));
// Confirm the edit view.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/$num/edit");
$this->assertNoLink(t('Edit'));
$this->assertNoLink(t('Start'));
$this->assertLink(t('Stop'));
$this->assertLink(t('Reboot'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/reboot");
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/stop");
$this->assertLink(t('Delete'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/terminate");
$this->assertNoLink(t('Associate Elastic IP'));
}
// Edit Instance information.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$num = $i + 1;
$this->createNetworkInterfaceTestEntity($i, '', '', $add[$i]['instance_id']);
$this->createElasticIpTestEntity($i);
// Change Instance Name in mock data.
$add[$i]['name'] = sprintf('instance-entity #%d - %s - %s', $i + 1, date('Y/m/d H:i:s'), $this->random->name(8, TRUE));
$this->updateInstanceMockData($i, $add[$i]['name']);
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
$this->assertResponse(200, t('Edit | List | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | List | Make sure w/o Warnings'));
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoText($add[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $add[$i]['name'],
]));
}
// Click 'Refresh'.
$this->clickLink(t('Refresh'));
$this->assertText(t('Updated Instances.'));
// Make sure listing.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertText($add[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $add[$i]['name'],
]));
}
// Make sure detailed and edit view.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$num = $i + 1;
// Confirm the detailed view.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/$num");
$this->assertLink(t('Edit'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/edit");
$this->assertLink(t('Start'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/start");
$this->assertNoLink(t('Stop'));
$this->assertNoLink(t('Reboot'));
$this->assertLink(t('Delete'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/terminate");
$this->assertLink(t('Associate Elastic IP'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/associate_elastic_ip");
// Confirm the edit view.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/$num/edit");
$this->assertNoLink(t('Edit'));
$this->assertLink(t('Start'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/start");
$this->assertNoLink(t('Stop'));
$this->assertNoLink(t('Reboot'));
$this->assertLink(t('Delete'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/terminate");
$this->assertLink(t('Associate Elastic IP'));
$this->assertLinkByHref("/clouds/aws_cloud/$cloud_context/instance/$num/associate_elastic_ip");
}
// Update tags for empty.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$num = $i + 1;
// Update tags.
$this->updateInstanceTagsInMockData($num - 1, 'Name', '', FALSE);
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertLink($add[$i]['name']);
}
// Click 'Refresh'.
$this->clickLink(t('Refresh'));
// Make sure listing.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoLink($add[$i]['name']);
$this->assertLink($add[$i]['instance_id']);
}
// Delete name tags.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$num = $i + 1;
// Update tags.
$this->updateInstanceTagsInMockData($num - 1, 'Name', '', TRUE);
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoLink($add[$i]['name']);
$this->assertLink($add[$i]['instance_id']);
}
// Click 'Refresh'.
$this->clickLink(t('Refresh'));
// Make sure listing.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoLink($add[$i]['name']);
$this->assertLink($add[$i]['instance_id']);
}
// Update tags.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$num = $i + 1;
$this->updateInstanceTagsInMockData($num - 1, 'Name', $add[$i]['name'], FALSE);
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoLink($add[$i]['name']);
}
// Click 'Refresh'.
$this->clickLink(t('Refresh'));
// Make sure listing.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertLink($add[$i]['name']);
}
// Delete Instances in mock data.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->deleteFirstInstanceMockData();
}
// Make sure listing.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance");
$this->assertResponse(200, t('Edit | List | HTTP 200: Instance #@num', ['@num' => $num]));
$this->assertNoText(t('Notice'), t('Edit | List | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Edit | List | Make sure w/o Warnings'));
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertText($add[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $add[$i]['name'],
]));
}
// Click 'Refresh'.
$this->clickLink(t('Refresh'));
$this->assertText(t('Updated Instances.'));
// Make sure listing.
for ($i = 0; $i < self::AWS_CLOUD_INSTANCE_REPEAT_COUNT; $i++) {
$this->assertNoText($add[$i]['name'],
t('Edit | List | Make sure w/ Listing: @name', [
'@name' => $add[$i]['name'],
]));
}
}
/**
* Test creating an image from an instance.
*/
public function testImageCreationFromInstance() {
$this->repeatTestImageCreationFromInstance(self::AWS_CLOUD_INSTANCE_REPEAT_COUNT);
}
/**
* Repeating test image creation from instance.
*
* @param int $max_test_repeat_count
* Max test repeating count.
*/
private function repeatTestImageCreationFromInstance($max_test_repeat_count = 1) {
$cloud_context = $this->cloudContext;
// IAM Roles.
$iam_roles = $this->createIamRolesRandomTestFormData();
$this->updateIamRolesMockData($iam_roles);
// Add an empty value to IAM roles.
$iam_roles = array_merge([[]], $iam_roles);
// Launch a new Instance.
$add = $this->createInstanceTestFormData($max_test_repeat_count);
for ($i = 0, $num = 1; $i < $max_test_repeat_count; $i++, $num++) {
// Create image.
$image = $this->createImageTestEntity($i, $add[$i]['image_id'], $cloud_context);
// Make sure if the image entity is created or not.
$this->drupalGet("/clouds/aws_cloud/${cloud_context}/image");
$this->assertResponse(200, t('HTTP 200: Image | The new AWS Cloud Image #@num', ['@num' => $num]));
$this->assertNoText(t('warning'), t('Image | Make sure w/o Warnings'));
$this->assertText($image->getName(), t('Image | Make sure w/ Image Name (TestEntity): @name', ['@name' => $image->getName()]));
$this->assertText($image->getImageId(), t('Image | Make sure w/ Image ID (TestEntity): @image_id', ['@image_id' => $image->getImageId()]));
$this->assertText($add[$i]['image_id'], t('Image | Make sure w/ Image ID (TestFormData): @image_id', ['@image_id' => $add[$i]['image_id']]));
// Setup cloud server template and instance.
$server_template = $this->createServerTemplateTestEntity($iam_roles, $image, $cloud_context);
// Make sure if the cloud_server_template entity is created or not.
$this->drupalGet("/clouds/design/server_template/${cloud_context}");
$this->assertResponse(200, t('HTTP 200: CloudServerTemplate | The new CloudServerTemplate #@num', ['@num' => $num]));
$this->assertNoText(t('warning'), t('CloudServerTemplate | Make sure w/o Warnings'));
$this->assertText($server_template->name->value,
t('CloudServerTemplate | Make sure w/ CloudServerTemplate Name: @name', [
'@name' => $server_template->name->value,
])
);
$this->addInstanceMockData($add[$i]['name'], $add[$i]['key_pair_name']);
$this->drupalPostForm("/clouds/design/server_template/$cloud_context/{$server_template->id()}/launch",
[],
t('Launch'));
$this->assertResponse(200, t('HTTP 200: Launch | The new Cloud Instance @num', ['@num' => $i]));
$this->assertNoText(t('Notice'), t('Launch | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Launch | Make sure w/o Warnings'));
// Make sure instances are available.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/instance/$num");
$this->assertResponse(200, t('HTTP 200: Instance created.'));
// Delete the image used to create instance.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
$this->clickLink('Delete');
$this->drupalPostForm($this->getUrl(),
[],
t('Delete'));
// Test image creation.
$image_id = 'ami-' . $this->getRandomAwsId();
$image_name = $this->random->name(8, TRUE);
$image_params = [
'image_name' => $image_name,
'no_reboot' => 0,
];
// Update the mock data then create the image.
$this->updateImageCreationMockData($image_id, $image_name, 'pending');
$this->drupalPostForm("/clouds/aws_cloud/$cloud_context/instance/$num/create_image",
$image_params,
t('Create Image'));
$this->assertText(t("The AWS Cloud Instance @label (@image_id) has been created.", [
'@image_id' => $image_id,
'@label' => $add[$i]['name'],
]));
// Make sure the image was created. Status should be pending.
// Click on the Image link from the image listing page.
$this->clickLink($image_name);
$this->assertResponse(200, t('HTTP 200: Image Entity.'));
$this->assertText($image_id, t('Image ID is present'));
$this->assertText('pending', t('Image created in pending state'));
// Go back to listing page. Make sure there is no delete link.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
$this->assertNoLink('Delete', t('Cannot delete image in pending state'));
// Update the image to 'available'. Then delete the image.
$this->updateImageCreationMockData($image_id, $image_name, 'available');
// Run cron job to update images state.
$key = \Drupal::state()->get('system.cron_key');
$this->drupalGet('/cron/' . $key);
$this->assertResponse(204);
// Go back into the main image.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
// Click into the image. Make sure the status is now available.
$this->clickLink($image_name);
$this->assertText('available', t('Image status is available.'));
// Go back to main listing page.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
// Delete the image.
$this->clickLink('Delete');
$this->drupalPostForm($this->getUrl(),
[],
t('Delete'));
$this->assertResponse(200, t('HTTP 200: Delete', [
'@num' => $i,
]));
$this->assertNoText(t('Notice'), t('Delete | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Delete | Make sure w/o Warnings'));
// Make sure image is deleted.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
$this->assertNoText($image_id, t('Image deleted'));
// Test "Failed" Image. Failed Images should be allowed to be deleted.
// Reset the image_id and image_name variables.
$image_id = 'ami-' . $this->getRandomAwsId();
$image_name = $this->random->name(8, TRUE);
$image_params = [
'image_name' => $image_name,
'no_reboot' => 0,
];
// Update the image so it is in failed state.
$this->updateImageCreationMockData($image_id, $image_name, 'failed');
$this->drupalPostForm("/clouds/aws_cloud/$cloud_context/instance/$num/create_image",
$image_params,
t('Create Image'));
$this->assertText(t("The AWS Cloud Instance @label (@image_id) has been created.", [
'@image_id' => $image_id,
'@label' => $add[$i]['name'],
]));
// Go to the main image page.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
// Make sure the status is now failed.
$this->clickLink($image_name);
$this->assertText('failed', t('Image status is failed'));
// Go to the main image page.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
// Delete the Failed image.
$this->clickLink('Delete');
$this->drupalPostForm($this->getUrl(),
[],
t('Delete'));
$this->assertResponse(200, t('HTTP 200: Delete', [
'@num' => $i,
]));
$this->assertNoText(t('Notice'), t('Delete | Make sure w/o Notice'));
$this->assertNoText(t('warning'), t('Delete | Make sure w/o Warnings'));
// Make sure image is deleted.
$this->drupalGet("/clouds/aws_cloud/$cloud_context/image");
$this->assertNoText($image_id, t('Image deleted'));
}
}
}
