From 0064cfef83d30f6908b3375bd85553b35d20eae0 Mon Sep 17 00:00:00 2001 From: Mika Rautanen Date: Sun, 3 Nov 2024 17:11:36 +0200 Subject: [PATCH] Fix unit queue requirements check and update tests --- .../Abstracts/AbstractUnitsController.php | 2 +- app/Services/BuildingQueueService.php | 4 +- app/Services/ObjectService.php | 2 +- app/Services/ResearchQueueService.php | 20 +++- app/Services/UnitQueueService.php | 2 +- tests/AccountTestCase.php | 68 ++++++++++- tests/Feature/BuildQueueCancelTest.php | 53 ++++++++- tests/Feature/BuildQueueTest.php | 34 ++++++ tests/Feature/ResearchQueueCancelTest.php | 53 ++++++++- tests/Feature/ResearchQueueTest.php | 43 ++++++- tests/Feature/UnitQueueTest.php | 109 ++++++++++++++++++ tests/Unit/BuildingQueueServiceTest.php | 71 ------------ tests/Unit/ObjectServiceTest.php | 73 +++--------- tests/Unit/PlanetServiceTest.php | 8 +- tests/Unit/ResearchQueueServiceTest.php | 71 ------------ 15 files changed, 392 insertions(+), 221 deletions(-) delete mode 100644 tests/Unit/BuildingQueueServiceTest.php delete mode 100644 tests/Unit/ResearchQueueServiceTest.php diff --git a/app/Http/Controllers/Abstracts/AbstractUnitsController.php b/app/Http/Controllers/Abstracts/AbstractUnitsController.php index 520b6f0d..e1909137 100644 --- a/app/Http/Controllers/Abstracts/AbstractUnitsController.php +++ b/app/Http/Controllers/Abstracts/AbstractUnitsController.php @@ -94,7 +94,7 @@ public function index(Request $request, PlayerService $player, ObjectService $ob $amount = $planet->getObjectAmount($object->machine_name); // Check requirements of this building - $requirements_met = $objects->objectRequirementsMet($object->machine_name, $planet, $player); + $requirements_met = $objects->objectRequirementsMet($object->machine_name, $planet, $player, 0, false); // Check if the current planet has enough resources to build this building. $enough_resources = $planet->hasResources($objects->getObjectPrice($object->machine_name, $planet)); diff --git a/app/Services/BuildingQueueService.php b/app/Services/BuildingQueueService.php index 6ab5cb98..68297853 100644 --- a/app/Services/BuildingQueueService.php +++ b/app/Services/BuildingQueueService.php @@ -84,8 +84,6 @@ public function add(PlanetService $planet, int $building_id): void { $build_queue = $this->retrieveQueue($planet); - $building = $this->objects->getObjectById($building_id); - // Max amount of buildings that can be in the queue in a given time. // TODO: refactor throw exception into a more user-friendly message. if ($build_queue->isQueueFull()) { @@ -93,6 +91,8 @@ public function add(PlanetService $planet, int $building_id): void throw new Exception('Maximum number of items already in queue.'); } + $building = $this->objects->getObjectById($building_id); + // Check if user satisifes requirements to build this object. // TODO: refactor throw exception into a more user-friendly message. $requirements_met = $this->objects->objectRequirementsMet($building->machine_name, $planet, $planet->getPlayer()); diff --git a/app/Services/ObjectService.php b/app/Services/ObjectService.php index bb8aca9f..0ba6272b 100644 --- a/app/Services/ObjectService.php +++ b/app/Services/ObjectService.php @@ -350,7 +350,7 @@ public function objectRequirementsMet(string $machine_name, PlanetService $plane $object_required = $this->getObjectByMachineName($requirement->object_machine_name); $check_queue = $queued; - // SKip queue check for research lab as it must be present for research objects + // Skip queue check for research lab as it must be present for research objects if ($object_required->machine_name === 'research_lab') { $check_queue = false; } diff --git a/app/Services/ResearchQueueService.php b/app/Services/ResearchQueueService.php index 5592810d..2261676b 100644 --- a/app/Services/ResearchQueueService.php +++ b/app/Services/ResearchQueueService.php @@ -116,21 +116,29 @@ public function retrieveFinishedForUser(PlayerService $player): \Illuminate\Supp */ public function add(PlayerService $player, PlanetService $planet, int $research_object_id): void { - $build_queue = $this->retrieveQueue($planet); + $research_queue = $this->retrieveQueue($planet); - // Max amount of buildings that can be in the queue at a given time. - if ($build_queue->isQueueFull()) { - // Max amount of build queue items already exist, throw exception. + // Max amount of research items that can be in the queue at a given time. + // TODO: refactor throw exception into a more user-friendly message. + if ($research_queue->isQueueFull()) { + // Max amount of research queue items already exist, throw exception. throw new Exception('Maximum number of items already in queue.'); } $object = $this->objects->getResearchObjectById($research_object_id); + // Check if user satisifes requirements to research this object. + // TODO: refactor throw exception into a more user-friendly message. + $requirements_met = $this->objects->objectRequirementsMet($object->machine_name, $planet, $planet->getPlayer()); + if (!$requirements_met) { + throw new Exception('Requirements not met to build this object.'); + } + // @TODO: add checks that current logged in user is owner of planet - // and is able to add this object to the building queue. + // and is able to add this object to the research queue. $current_level = $player->getResearchLevel($object->machine_name); - // Check to see how many other items of this building there are already + // Check to see how many other items of this technology there are already // in the queue, because if so then the level needs to be higher than that. $amount = $this->activeBuildingQueueItemCount($player, $research_object_id); $next_level = $current_level + $amount + 1; diff --git a/app/Services/UnitQueueService.php b/app/Services/UnitQueueService.php index 62918e93..03c6d77d 100644 --- a/app/Services/UnitQueueService.php +++ b/app/Services/UnitQueueService.php @@ -159,7 +159,7 @@ public function add(PlanetService $planet, int $object_id, int $requested_build_ $object = $this->objects->getUnitObjectById($object_id); // Check if user satisifes requirements to build this object. - $requirements_met = $this->objects->objectRequirementsMet($object->machine_name, $planet, $planet->getPlayer()); + $requirements_met = $this->objects->objectRequirementsMet($object->machine_name, $planet, $planet->getPlayer(), 0, false); // Sanity check: check if the planet has enough resources to build // the amount requested. If not, then adjust the ordered amount. diff --git a/tests/AccountTestCase.php b/tests/AccountTestCase.php index dbc63614..5ecb9ba2 100644 --- a/tests/AccountTestCase.php +++ b/tests/AccountTestCase.php @@ -384,7 +384,7 @@ protected function assertResourcesOnPage(TestResponse $response, Resources $reso } } - protected function assertObjectInQueue(TestResponse $response, string $machine_name, string $error_message = ''): void + protected function assertObjectInQueue(TestResponse $response, string $machine_name, int $level, string $error_message = ''): void { // Get object name from machine name. try { @@ -399,7 +399,7 @@ protected function assertObjectInQueue(TestResponse $response, string $machine_n if (!$responseContent) { $responseContent = ''; } - $condition1 = str_contains($responseContent, 'Cancel production of ' . $object->title); + $condition1 = str_contains($responseContent, 'Cancel production of ' . $object->title . ' level '. $level); $condition2 = str_contains($responseContent, 'do you really want to cancel ' . $object->title); $this->assertTrue($condition1 || $condition2, 'Neither of the expected texts were found in the response.'); } catch (Exception $e) { @@ -432,6 +432,70 @@ protected function assertObjectNotInQueue(TestResponse $response, string $machin } } + protected function assertEmptyBuildingQueue(TestResponse $response, string $error_message = ''): void + { + // Check if "no buildings being built" text is present on page. + try { + $responseContent = $response->getContent(); + if (!$responseContent) { + $responseContent = ''; + } + $condition = str_contains($responseContent, 'no building being built'); + $this->assertTrue($condition, 'expected text was not found in the response.'); + } catch (Exception $e) { + if (!empty($error_message)) { + $this->fail($error_message . '. Error: ' . $e->getMessage()); + } else { + $this->fail('Building queue is not empty. Error: ' . $e->getMessage()); + } + } + } + + protected function assertEmptyResearchQueue(TestResponse $response, string $error_message = ''): void + { + // Check if "no research done" text is present on page. + try { + $responseContent = $response->getContent(); + if (!$responseContent) { + $responseContent = ''; + } + $condition = str_contains($responseContent, 'no research done'); + $this->assertTrue($condition, 'expected text was not found in the response.'); + } catch (Exception $e) { + if (!empty($error_message)) { + $this->fail($error_message . '. Error: ' . $e->getMessage()); + } else { + $this->fail('Research queue is not empty. Error: ' . $e->getMessage()); + } + } + } + + protected function assertRequirementsNotMet(TestResponse $response, string $machine_name, string $error_message = ''): void + { + // Get object name from machine name. + try { + $object = $this->planetService->objects->getObjectByMachineName($machine_name); + } catch (Exception $e) { + $this->fail('Failed to get object by machine name: ' . $machine_name . '. Error: ' . $e->getMessage()); + } + + // Check if "Requirements are not met" text is present on page. + try { + $responseContent = $response->getContent(); + if (!$responseContent) { + $responseContent = ''; + } + $condition = str_contains($responseContent, $object->title.'
Requirements are not met!'); + $this->assertTrue($condition, 'expected text was not found in the response.'); + } catch (Exception $e) { + if (!empty($error_message)) { + $this->fail($error_message . '. Error: ' . $e->getMessage()); + } else { + $this->fail('Requirements are met. Error: ' . $e->getMessage()); + } + } + } + /** * Add a resource build request to the current users current planet. * @param string $machine_name diff --git a/tests/Feature/BuildQueueCancelTest.php b/tests/Feature/BuildQueueCancelTest.php index b23f0be3..0fcb9267 100644 --- a/tests/Feature/BuildQueueCancelTest.php +++ b/tests/Feature/BuildQueueCancelTest.php @@ -35,7 +35,7 @@ public function testBuildQueueCancelMultiple(): void Carbon::setTestNow($testTime); $response = $this->get('/resources'); - $this->assertObjectInQueue($response, 'metal_mine', 'Metal mine is expected in build queue but cannot be found.'); + $this->assertObjectInQueue($response, 'metal_mine', 3, 'Metal mine level 3 is expected in build queue but cannot be found.'); // Extract first and second number on page which looks like this where num1/num2 are ints: // "cancelProduction(num1,num2," @@ -95,7 +95,7 @@ public function testBuildQueueCancelRefundResources(): void $this->addResourceBuildRequest('metal_mine'); $response = $this->get('/resources'); - $this->assertObjectInQueue($response, 'metal_mine', 'Metal mine is not in build queue.'); + $this->assertObjectInQueue($response, 'metal_mine', 1, 'Metal mine level 1 is not in build queue.'); // Extract first and second number on page which looks like this where num1/num2 are ints: // "cancelProduction(num1,num2," @@ -149,7 +149,7 @@ public function testBuildQueueCancelSecondEntry(): void // Extract first and second number on page which looks like this where num1/num2 are ints: // "cancelbuilding(num1,num2," - $this->assertObjectInQueue($response, 'crystal_mine', 'Crystal mine is not in build queue.'); + $this->assertObjectInQueue($response, 'crystal_mine', 1, 'Crystal mine level 1 is not in build queue.'); // Extract the content from the response $pageContent = $response->getContent(); @@ -178,4 +178,51 @@ public function testBuildQueueCancelSecondEntry(): void $this->throwException(new BindingResolutionException('Less than two "cancelProduction" calls found.')); } } + + /** + * Tests building queue item is cancelled if requirements are not met. + */ + public function testCancelObjectMissingRequirements(): void + { + // Assert that build queue is empty + $response = $this->get('/facilities'); + $response->assertStatus(200); + + $this->assertEmptyBuildingQueue($response); + + // Add resource to build required facilities to planet + $this->planetAddResources(new Resources(5000, 5000, 5000, 0)); + + // Add required facilities to building queue + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('shipyard'); + + $response = $this->get('/facilities'); + $this->assertObjectInQueue($response, 'shipyard', 1, 'Shipyard level 1 is not in build queue.'); + + // Extract the first and second number from the first cancelbuilding call + $cancelProductionCall = $response->getContent(); + if (empty($cancelProductionCall)) { + $cancelProductionCall = ''; + } + $cancelProductionCall = explode('onclick="cancelbuilding(', $cancelProductionCall); + $cancelProductionCall = explode(',', $cancelProductionCall[1]); + $number1 = (int)$cancelProductionCall[0]; + $number2 = (int)$cancelProductionCall[1]; + + // Check if both numbers are integers. If not, throw an exception. + if (empty($number1) || empty($number2)) { + throw new BindingResolutionException('Could not extract the building queue ID from the page.'); + } + + // Cancel Robotics Factory level 1, this will cancel also Robotics Factory level 2 and Shipyard level 1 + $this->cancelFacilitiesBuildRequest($number1, $number2); + + // Assert that building queue is empty + $response = $this->get('/facilities'); + $response->assertStatus(200); + + $this->assertEmptyBuildingQueue($response); + } } diff --git a/tests/Feature/BuildQueueTest.php b/tests/Feature/BuildQueueTest.php index 1305a7f2..2d59b788 100644 --- a/tests/Feature/BuildQueueTest.php +++ b/tests/Feature/BuildQueueTest.php @@ -221,6 +221,40 @@ public function testBuildQueueFailUnfulfilledRequirements(): void $this->assertObjectLevelOnPage($response, 'fusion_plant', 0, 'Fusion Reactor has been built while player has not satisfied building requirements.'); } + /** + * Verify that shipyard can be queued when robotics factory is in queue. + * @throws Exception + */ + public function testBuildQueueFacilitiesShipyardQueuedRequirements(): void + { + // Set the current time to a specific moment for testing + $testTime = Carbon::create(2024, 1, 1, 12, 0, 0); + Carbon::setTestNow($testTime); + + // Add resource to build required facilities to planet + $this->planetAddResources(new Resources(5000, 5000, 5000, 0)); + + // Assert that building requirements for Shipyard are not met as Robotics Factory is missing + $response = $this->get('/facilities'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'shipyard', 'Shipyard building requirements not met.'); + + // Add Robotics Factory level 1 and 2 to build queue + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('robot_factory'); + + // Add Shipyard level 1 to queue + $this->addFacilitiesBuildRequest('shipyard'); + + // Verify the research is finished 10 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 10, 0); + Carbon::setTestNow($testTime); + + $response = $this->get('/facilities'); + $response->assertStatus(200); + $this->assertObjectLevelOnPage($response, 'shipyard', 1, 'Shipyard is not at level one 10 minutes after build request issued.'); + } + /** * Verify that building construction time is calculated correctly (higher than 0) * @throws Exception diff --git a/tests/Feature/ResearchQueueCancelTest.php b/tests/Feature/ResearchQueueCancelTest.php index 6cb5875c..04da5b1b 100644 --- a/tests/Feature/ResearchQueueCancelTest.php +++ b/tests/Feature/ResearchQueueCancelTest.php @@ -3,6 +3,7 @@ namespace Tests\Feature; use Exception; +use Illuminate\Contracts\Container\BindingResolutionException; use Illuminate\Support\Carbon; use Illuminate\Testing\TestResponse; use OGame\Models\Resources; @@ -39,7 +40,7 @@ public function testResearchQueueCancelMultiple(): void Carbon::setTestNow($testTime); $response = $this->get('/research'); - $this->assertObjectInQueue($response, 'energy_technology', 'Energy Technology is expected in build queue but cannot be found.'); + $this->assertObjectInQueue($response, 'energy_technology', 3, 'Energy Technology level 3 is expected in build queue but cannot be found.'); $this->pressCancelButtonOnPage($response); @@ -81,7 +82,7 @@ public function testResearchQueueCancelRefundResources(): void $response = $this->get('/research'); $response->assertStatus(200); - $this->assertObjectInQueue($response, 'energy_technology', 'Energy Technology is not in build queue.'); + $this->assertObjectInQueue($response, 'energy_technology', 1, 'Energy Technology level 1 is not in build queue.'); $this->pressCancelButtonOnPage($response); @@ -116,7 +117,7 @@ public function testBuildQueueCancelSecondEntry(): void $response = $this->get('/research'); $response->assertStatus(200); - $this->assertObjectInQueue($response, 'computer_technology', 'Computer Technology is not in build queue.'); + $this->assertObjectInQueue($response, 'computer_technology', 1, 'Computer Technology level 1 is not in build queue.'); // Extract the content from the response $pageContent = $response->getContent(); @@ -208,4 +209,50 @@ private function pressCancelButtonOnPage(TestResponse $response): void // Do POST to cancel build queue item: $this->cancelResearchBuildRequest($number1, $number2); } + + /** + * Tests research queue item is cancelled if requirements are not met. + */ + public function testCancelResearchMissingRequirements(): void + { + // Assert that research queue is empty + $response = $this->get('/research'); + $response->assertStatus(200); + + $this->assertEmptyResearchQueue($response); + + // Set facilities and add resources to planet that test requires. + $this->planetSetObjectLevel('research_lab', 2); + $this->planetAddResources(new Resources(5000, 5000, 5000, 0)); + + $this->addResearchBuildRequest('energy_technology'); + $this->addResearchBuildRequest('impulse_drive'); + + $response = $this->get('/research'); + $this->assertObjectInQueue($response, 'impulse_drive', 1, 'Impulse Drive 1 is not in research queue.'); + + // Extract the first and second number from the first cancelbuilding call + $cancelProductionCall = $response->getContent(); + if (empty($cancelProductionCall)) { + $cancelProductionCall = ''; + } + $cancelProductionCall = explode('onclick="cancelbuilding(', $cancelProductionCall); + $cancelProductionCall = explode(',', $cancelProductionCall[1]); + $number1 = (int)$cancelProductionCall[0]; + $number2 = (int)$cancelProductionCall[1]; + + // Check if both numbers are integers. If not, throw an exception. + if (empty($number1) || empty($number2)) { + throw new BindingResolutionException('Could not extract the building queue ID from the page.'); + } + + // Cancel Energy technology level 1, this will cancel also Impulse Drive level 1 + $this->cancelResearchBuildRequest($number1, $number2); + + // Assert that building queue is empty + $response = $this->get('/research'); + $response->assertStatus(200); + + $this->assertEmptyResearchQueue($response); + } } diff --git a/tests/Feature/ResearchQueueTest.php b/tests/Feature/ResearchQueueTest.php index 0fed0a5e..61a866fb 100644 --- a/tests/Feature/ResearchQueueTest.php +++ b/tests/Feature/ResearchQueueTest.php @@ -155,7 +155,7 @@ public function testResearchQueueCancelRefundResources(): void // Assert that resources have been actually deducted $this->assertResourcesOnPage($response, new Resources(0, 500, 0, 0)); // Assert that the research is in the queue - $this->assertObjectInQueue($response, 'energy_technology', 'Energy Technology is not in build queue.'); + $this->assertObjectInQueue($response, 'energy_technology', 1, 'Energy Technology level 1 is not in build queue.'); // Extract first and second number on page which looks like this where num1/num2 are ints: // "cancelProduction(num1,num2," @@ -198,4 +198,45 @@ public function testResearchProductionTime(): void $research_time = $this->planetService->getTechnologyResearchTime('energy_technology'); $this->assertGreaterThan(0, $research_time); } + + /** + * Verify that research lab requirement is working for research objects. + * @throws Exception + */ + public function testResearchLabRequirement(): void + { + // Set the current time to a specific moment for testing + $testTime = Carbon::create(2024, 1, 1, 12, 0, 0); + Carbon::setTestNow($testTime); + + // Add required resources for research to planet + $this->planetAddResources(new Resources(5000, 5000, 5000, 0)); + + // Assert that research requirements for Energy Technology are not met as Research Lab is missing + $response = $this->get('/research'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'energy_technology', 'Energy Technology research requirements not met.'); + + // Add Research Lab level 1 to build queue + $this->addFacilitiesBuildRequest('research_lab'); + + // Assert that research requirements for Energy Technology are not met as Research Lab is in build queue + $response = $this->get('/research'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'energy_technology', 'Energy Technology research requirements not met.'); + + // Verify that Energy Technology can be added to research queue 2 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 2, 0); + Carbon::setTestNow($testTime); + + $this->addResearchBuildRequest('energy_technology'); + + // Verify the research is finished 2 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 4, 0); + Carbon::setTestNow($testTime); + + $response = $this->get('/research'); + $response->assertStatus(200); + $this->assertObjectLevelOnPage($response, 'energy_technology', 1, 'Energy technology is not at level one 2 minutes after build request issued.'); + } } diff --git a/tests/Feature/UnitQueueTest.php b/tests/Feature/UnitQueueTest.php index dadd5bf4..bdb07bab 100644 --- a/tests/Feature/UnitQueueTest.php +++ b/tests/Feature/UnitQueueTest.php @@ -374,6 +374,115 @@ public function testUnitQueueInsufficientResources(): void $this->assertResourcesOnPage($response, new Resources(15500, 5500, 0, 0)); } + /** + * Verify that shipyard requirement is working for unit objects. + * @throws Exception + */ + public function testUnitQueueShipyardRequirement(): void + { + // Set the current time to a specific moment for testing + $testTime = Carbon::create(2024, 1, 1, 12, 0, 0); + Carbon::setTestNow($testTime); + + // Add required resources to planet + $this->planetAddResources(new Resources(5000, 5000, 5000, 0)); + + // Assert that build requirements for Solar Satellite are not met as Shipyard is missing + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'solar_satellite', 'Solar Satellite build requirements are met.'); + + // Add Shipyard level 1 with requisities to build queue + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('shipyard'); + + // Assert that build requirements for Solar Satellite are not met as Shipyard is in build queue + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'solar_satellite', 'Solar Satellite build requirements are met.'); + + // Verify that Solar Satellite can be added to unit queue 10 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 10, 0); + Carbon::setTestNow($testTime); + + $this->addShipyardBuildRequest('solar_satellite', 1); + + // Verify the building is finished 10 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 20, 0); + Carbon::setTestNow($testTime); + + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertObjectLevelOnPage($response, 'solar_satellite', 1, 'Solar Satellite build job is not finished yet 10 minute after build request issued.'); + } + + /** + * Verify that research requirements are working for unit objects. + * @throws Exception + */ + public function testUnitQueueResearchRequirement(): void + { + // Set the current time to a specific moment for testing + $testTime = Carbon::create(2024, 1, 1, 12, 0, 0); + Carbon::setTestNow($testTime); + + // Add required resources to planet + $this->planetAddResources(new Resources(5000, 5000, 5000, 0)); + + // Assert that build requirements for Light Fighter are not met + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'light_fighter', 'Light Fighter build requirements are met.'); + + // Add Shipyard and Research Lab to build queue + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('robot_factory'); + $this->addFacilitiesBuildRequest('shipyard'); + $this->addFacilitiesBuildRequest('research_lab'); + + // Verify the building is finished 10 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 10, 0); + Carbon::setTestNow($testTime); + + $response = $this->get('/facilities'); + $response->assertStatus(200); + $this->assertObjectLevelOnPage($response, 'research_lab', 1, 'Research Lab build job is not finished yet 10 minute after build request issued.'); + + // Assert that build requirements for Light Fighter are not met as Combustion Drive technology is missing + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'light_fighter', 'Light Fighter build requirements are met.'); + + // Add required technology to research queue + $this->addResearchBuildRequest('energy_technology'); + $this->addResearchBuildRequest('combustion_drive'); + + // Assert that build requirements for Light Fighter are not met as Combustion Drive technology is in build queue + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertRequirementsNotMet($response, 'light_fighter', 'Light Fighter build requirements are met.'); + + // Verify the research is finished 10 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 20, 0); + Carbon::setTestNow($testTime); + + $this->planetService->getPlayer()->updateResearchQueue(); + $response = $this->get('/research'); + $response->assertStatus(200); + $this->assertObjectLevelOnPage($response, 'combustion_drive', 1, 'Combustion Drive is not at level one 10 minutes after build request issued.'); + + $this->addShipyardBuildRequest('light_fighter', 1); + + // Verify the building is finished 10 minute later. + $testTime = Carbon::create(2024, 1, 1, 12, 30, 0); + Carbon::setTestNow($testTime); + + $response = $this->get('/shipyard'); + $response->assertStatus(200); + $this->assertObjectLevelOnPage($response, 'light_fighter', 1, 'Light Fighter build job is not finished yet 10 minute after build request issued.'); + } + /** * Verify that unit construction time is calculated correctly (higher than 0) * @throws BindingResolutionException diff --git a/tests/Unit/BuildingQueueServiceTest.php b/tests/Unit/BuildingQueueServiceTest.php deleted file mode 100644 index fa28bf18..00000000 --- a/tests/Unit/BuildingQueueServiceTest.php +++ /dev/null @@ -1,71 +0,0 @@ -building_queue = new BuildingQueueService($object_service); - } - - /** - * Tests object is found from building queue - */ - public function testIsObjectInBuildingQueue(): void - { - // Add level 3 shipyard to building queue - $queue = new BuildingQueue(); - $queue->planet_id = $this->planetService->getPlanetId(); - $queue->object_id = 21; - $queue->object_level_target = 3; - $queue->save(); - - $this->assertTrue($this->building_queue->objectInBuildingQueue($this->planetService, 'shipyard', 3)); - $this->assertFalse($this->building_queue->objectInBuildingQueue($this->planetService, 'shipyard', 4)); - $this->assertFalse($this->building_queue->objectInBuildingQueue($this->planetService, 'robot_factory', 3)); - } - - /** - * Tests building queue item is cancelled if requirements are not met. - */ - public function testCancelObjectMissingRequirements(): void - { - // Add level 2 robot factory to building queue - $queue_robot_factory = new BuildingQueue(); - $queue_robot_factory->planet_id = $this->planetService->getPlanetId(); - $queue_robot_factory->object_id = 14; - $queue_robot_factory->object_level_target = 2; - $queue_robot_factory->save(); - - // Add level 1 shipyard to building queue - $queue = new BuildingQueue(); - $queue->planet_id = $this->planetService->getPlanetId(); - $queue->object_id = 21; - $queue->object_level_target = 1; - $queue->save(); - - // Assert that shipyard is in building queue - $this->assertTrue($this->building_queue->objectInBuildingQueue($this->planetService, 'shipyard', 1)); - - // Cancel robot factory - $this->building_queue->cancel($this->planetService, $queue_robot_factory->id, 14); - $this->building_queue->cancelItemMissingRequirements($this->planetService); - - // Assert that shipyard is in building queue - $this->assertFalse($this->building_queue->objectInBuildingQueue($this->planetService, 'shipyard', 1)); - } -} diff --git a/tests/Unit/ObjectServiceTest.php b/tests/Unit/ObjectServiceTest.php index e104b6f1..575f6040 100644 --- a/tests/Unit/ObjectServiceTest.php +++ b/tests/Unit/ObjectServiceTest.php @@ -2,77 +2,42 @@ namespace Tests\Unit; -use OGame\Models\BuildingQueue; -use OGame\Models\Resources; use OGame\Services\ObjectService; -use Tests\AccountTestCase; +use Tests\UnitTestCase; -class ObjectServiceTest extends AccountTestCase +class ObjectServiceTest extends UnitTestCase { - protected ObjectService $object_service; - - /** - * Set up common test components. - */ - protected function setUp(): void - { - parent::setUp(); - - $this->object_service = new ObjectService(); - } - /** * Tests maximum building amount returns correct value. */ public function testGetObjectMaxBuildAmount(): void { + $object_service = new ObjectService(); + $this->createAndSetPlanetModel([]); + // Test with requirements not met - $max_build_amount = $this->object_service->getObjectMaxBuildAmount('plasma_turret', $this->planetService, false); + $max_build_amount = $object_service->getObjectMaxBuildAmount('plasma_turret', $this->planetService, false); $this->assertEquals(0, $max_build_amount); - // Test with object limited to one instance - $max_build_amount = $this->object_service->getObjectMaxBuildAmount('small_shield_dome', $this->planetService, true); + // Test with object limited to one instance per user + $max_build_amount = $object_service->getObjectMaxBuildAmount('small_shield_dome', $this->planetService, true); $this->assertEquals(1, $max_build_amount); + $this->createAndSetPlanetModel([ + 'small_shield_dome' => 1, + ]); + // Test with object limited to one instance which already exists - $this->planetSetObjectLevel('small_shield_dome', 1); - $max_build_amount = $this->object_service->getObjectMaxBuildAmount('small_shield_dome', $this->planetService, true); + $max_build_amount = $object_service->getObjectMaxBuildAmount('small_shield_dome', $this->planetService, true); $this->assertEquals(0, $max_build_amount); + $this->createAndSetPlanetModel([ + 'metal' => 24000, + 'crystal' => 6000 + ]); + // Test it calculates max amount correctly - $this->planetAddResources(new Resources(24000, 6000, 0, 0)); - $max_build_amount = $this->object_service->getObjectMaxBuildAmount('anti_ballistic_missile', $this->planetService, true); + $max_build_amount = $object_service->getObjectMaxBuildAmount('anti_ballistic_missile', $this->planetService, true); $this->assertEquals(3, $max_build_amount); } - - /** - * Tests object requirements are verified against prior levels, research and buildings - * including items in building and research queues. - */ - public function testObjectRequirementsMet(): void - { - // Assert that requirements are not met if prior levels doesn't exist - $this->assertFalse($this->object_service->objectRequirementsMet('robot_factory', $this->planetService, $this->planetService->getPlayer(), 2)); - - $this->planetSetObjectLevel('robot_factory', 1); - - // Assert that requirements are met if prior levels exists - $this->assertTrue($this->object_service->objectRequirementsMet('robot_factory', $this->planetService, $this->planetService->getPlayer(), 2)); - - // Assert that requirements are not met if requisites are missing - $this->assertFalse($this->object_service->objectRequirementsMet('missile_silo', $this->planetService, $this->planetService->getPlayer(), 1)); - - // Add to build queue - $queue = new BuildingQueue(); - $queue->planet_id = $this->planetService->getPlanetId(); - $queue->object_id = 21; - $queue->object_level_target = 1; - $queue->save(); - - // Assert that requirements are met if requisites are in build queue - $this->assertTrue($this->object_service->objectRequirementsMet('missile_silo', $this->planetService, $this->planetService->getPlayer(), 1)); - - // Assert that research requirements are not met if building requirements are not met - $this->assertFalse($this->object_service->objectRequirementsMet('computer_technology', $this->planetService, $this->planetService->getPlayer(), 1)); - } } diff --git a/tests/Unit/PlanetServiceTest.php b/tests/Unit/PlanetServiceTest.php index c58515e9..5c143fda 100644 --- a/tests/Unit/PlanetServiceTest.php +++ b/tests/Unit/PlanetServiceTest.php @@ -5,7 +5,6 @@ use Illuminate\Contracts\Container\BindingResolutionException; use OGame\Models\BuildingQueue; use OGame\Models\Enums\ResourceType; -use OGame\Models\Planet; use OGame\Models\Resources; use Tests\UnitTestCase; @@ -200,8 +199,9 @@ public function testGetPlanetBuildingCount(): void */ public function testIsBuildingObject(): void { - $planet = Planet::factory()->make(['id' => 1]); - $this->planetService->setPlanet($planet); + $this->createAndSetPlanetModel([ + 'id' => 1, + ]); // Add level 3 shipyard to building queue $queue = new BuildingQueue(); @@ -211,7 +211,5 @@ public function testIsBuildingObject(): void $queue->save(); $this->assertTrue($this->planetService->isBuildingObject('shipyard', 3)); - $this->assertFalse($this->planetService->isBuildingObject('shipyard', 4)); - $this->assertFalse($this->planetService->isBuildingObject('robot_factory', 3)); } } diff --git a/tests/Unit/ResearchQueueServiceTest.php b/tests/Unit/ResearchQueueServiceTest.php deleted file mode 100644 index f7888d20..00000000 --- a/tests/Unit/ResearchQueueServiceTest.php +++ /dev/null @@ -1,71 +0,0 @@ -research_queue = new ResearchQueueService($object_service); - } - - /** - * Tests object is found from research queue - */ - public function testIsObjectInResearchQueue(): void - { - // Add level 3 impulse drive to research queue - $queue = new ResearchQueue(); - $queue->planet_id = $this->planetService->getPlanetId(); - $queue->object_id = 117; - $queue->object_level_target = 3; - $queue->save(); - - $this->assertTrue($this->research_queue->objectInResearchQueue($this->planetService->getPlayer(), 'impulse_drive', 3)); - $this->assertFalse($this->research_queue->objectInResearchQueue($this->planetService->getPlayer(), 'impulse_drive', 4)); - $this->assertFalse($this->research_queue->objectInResearchQueue($this->planetService->getPlayer(), 'energy_technology', 4)); - } - - /** - * Tests research queue item is cancelled if requirements are not met. - */ - public function testCancelItemMissingRequirements(): void - { - // Add level 1 energy technology to research queue - $queue_energy_tech = new ResearchQueue(); - $queue_energy_tech->planet_id = $this->planetService->getPlanetId(); - $queue_energy_tech->object_id = 113; - $queue_energy_tech->object_level_target = 1; - $queue_energy_tech->save(); - - // Add level 1 impulse drive to research queue - $queue = new ResearchQueue(); - $queue->planet_id = $this->planetService->getPlanetId(); - $queue->object_id = 117; - $queue->object_level_target = 1; - $queue->save(); - - // Assert that impulse drive is in research queue - $this->assertTrue($this->research_queue->objectInResearchQueue($this->planetService->getPlayer(), 'impulse_drive', 1)); - - // Cancel energy technology - $this->research_queue->cancel($this->planetService->getPlayer(), $queue_energy_tech->id, 113); - $this->research_queue->cancelItemMissingRequirements($this->planetService->getPlayer(), $this->planetService); - - // Assert that impulse drive is in research queue - $this->assertFalse($this->research_queue->objectInResearchQueue($this->planetService->getPlayer(), 'impulse_drive', 1)); - } -}