Skip to content

Commit 9863020

Browse files
committed
Add GitHub Action and thorough local mock testing suite for ECS
1 parent 52ba443 commit 9863020

4 files changed

Lines changed: 168 additions & 0 deletions

File tree

.github/workflows/tests.yml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,9 @@ jobs:
2929
command: composer install
3030
- name: Run Script
3131
run: vendor/bin/phpunit
32+
- name: Run ECS Mock Tests
33+
if: matrix.os == 'ubuntu-latest'
34+
run: bash tests/fixtures/local-ecs-test/run-local-ecs-test.sh
3235
test_lowest:
3336
runs-on: ubuntu-latest
3437
name: Test Prefer Lowest
@@ -46,3 +49,5 @@ jobs:
4649
command: composer update --prefer-lowest
4750
- name: Run Script
4851
run: vendor/bin/phpunit
52+
- name: Run ECS Mock Tests
53+
run: bash tests/fixtures/local-ecs-test/run-local-ecs-test.sh
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
<?php
2+
header('Content-Type: application/json');
3+
4+
$scenario = $_GET['scenario'] ?? 'success';
5+
6+
if ($scenario === 'server_error') {
7+
http_response_code(500);
8+
echo json_encode(['error' => 'Internal Server Error']);
9+
exit;
10+
}
11+
12+
if ($scenario === 'invalid_json') {
13+
echo '{ malformed JSON! ';
14+
exit;
15+
}
16+
17+
$response = [
18+
'Token' => 'MOCK_SESSION_TOKEN_789',
19+
'Expiration' => date('Y-m-d\TH:i:s\Z', strtotime('+1 hour'))
20+
];
21+
22+
if ($scenario === 'success') {
23+
$response['AccessKeyId'] = 'MOCK_ACCESS_KEY_123';
24+
$response['SecretAccessKey'] = 'MOCK_SECRET_KEY_456';
25+
} elseif ($scenario === 'missing_fields') {
26+
// Only return Token and Expiration, simulating a bad response without keys.
27+
}
28+
29+
echo json_encode($response);
Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
<?php
2+
require __DIR__ . '/../../../vendor/autoload.php';
3+
4+
use Google\Auth\CredentialSource\AwsNativeSource;
5+
use GuzzleHttp\Client;
6+
7+
echo "Starting thorough ECS mock testing suite...\n\n";
8+
9+
$client = new Client(['http_errors' => true]);
10+
$httpHandler = function ($request) use ($client) {
11+
return $client->send($request);
12+
};
13+
14+
$testsPassed = 0;
15+
$testsFailed = 0;
16+
17+
function runTestCase($name, $setupEnv, $assertion)
18+
{
19+
global $httpHandler, $testsPassed, $testsFailed;
20+
21+
echo "Running Test: $name... ";
22+
23+
// Clear potentially polluting env vars before setup
24+
putenv('AWS_CONTAINER_CREDENTIALS_FULL_URI');
25+
putenv('AWS_CONTAINER_CREDENTIALS_RELATIVE_URI');
26+
putenv('AWS_CONTAINER_AUTHORIZATION_TOKEN_FILE');
27+
28+
$setupEnv();
29+
30+
try {
31+
$result = AwsNativeSource::getSigningVarsFromEcs($httpHandler);
32+
$assertion($result, null);
33+
} catch (\Exception $e) {
34+
$assertion(null, $e);
35+
}
36+
}
37+
38+
// 1. Standard Success
39+
runTestCase('Success - Valid Credentials', function () {
40+
putenv('AWS_CONTAINER_CREDENTIALS_FULL_URI=http://127.0.0.1:8080/?scenario=success');
41+
}, function ($result, $exception) use (&$testsPassed, &$testsFailed) {
42+
if ($result && $result[0] === 'MOCK_ACCESS_KEY_123' && $result[1] === 'MOCK_SECRET_KEY_456') {
43+
echo "✅ PASS\n";
44+
$testsPassed++;
45+
} else {
46+
echo "❌ FAIL (Expected valid credentials array)\n";
47+
$testsFailed++;
48+
}
49+
});
50+
51+
// 2. Invalid Metadata Response (JSON Error)
52+
runTestCase('Error - Invalid JSON Response', function () {
53+
putenv('AWS_CONTAINER_CREDENTIALS_FULL_URI=http://127.0.0.1:8080/?scenario=invalid_json');
54+
}, function ($result, $exception) use (&$testsPassed, &$testsFailed) {
55+
if ($exception instanceof \UnexpectedValueException && strpos($exception->getMessage(), 'Invalid or missing ECS credentials') !== false) {
56+
echo "✅ PASS\n";
57+
$testsPassed++;
58+
} else {
59+
echo "❌ FAIL (Expected UnexpectedValueException)\n";
60+
$testsFailed++;
61+
}
62+
});
63+
64+
// 3. Missing Required Fields
65+
runTestCase('Error - Missing Fields in JSON', function () {
66+
putenv('AWS_CONTAINER_CREDENTIALS_FULL_URI=http://127.0.0.1:8080/?scenario=missing_fields');
67+
}, function ($result, $exception) use (&$testsPassed, &$testsFailed) {
68+
if ($exception instanceof \UnexpectedValueException && strpos($exception->getMessage(), 'Invalid or missing ECS credentials') !== false) {
69+
echo "✅ PASS\n";
70+
$testsPassed++;
71+
} else {
72+
echo "❌ FAIL (Expected UnexpectedValueException)\n";
73+
$testsFailed++;
74+
}
75+
});
76+
77+
// 4. Server Error (500)
78+
runTestCase('Error - HTTP 500 Server Error', function () {
79+
putenv('AWS_CONTAINER_CREDENTIALS_FULL_URI=http://127.0.0.1:8080/?scenario=server_error');
80+
}, function ($result, $exception) use (&$testsPassed, &$testsFailed) {
81+
if ($exception instanceof \GuzzleHttp\Exception\ServerException) {
82+
echo "✅ PASS\n";
83+
$testsPassed++;
84+
} else {
85+
echo "❌ FAIL (Expected Guzzle ServerException)\n";
86+
$testsFailed++;
87+
}
88+
});
89+
90+
// 5. Unreadable Token File
91+
runTestCase('Error - Unreadable Token File', function () {
92+
putenv('AWS_CONTAINER_CREDENTIALS_FULL_URI=http://127.0.0.1:8080/?scenario=success');
93+
putenv('AWS_CONTAINER_AUTHORIZATION_TOKEN_FILE=/path/to/nowhere/that/does/not/exist.txt');
94+
}, function ($result, $exception) use (&$testsPassed, &$testsFailed) {
95+
if ($exception instanceof \RuntimeException && strpos($exception->getMessage(), 'is not readable') !== false) {
96+
echo "✅ PASS\n";
97+
$testsPassed++;
98+
} else {
99+
echo "❌ FAIL (Expected RuntimeException for unreadable file)\n";
100+
$testsFailed++;
101+
}
102+
});
103+
104+
// 6. Bailout (No Environment Variables)
105+
runTestCase('Success - Bailout (No URIs Set)', function () {
106+
// We already clear the env vars in runTestCase.
107+
}, function ($result, $exception) use (&$testsPassed, &$testsFailed) {
108+
if ($result === null && $exception === null) {
109+
echo "✅ PASS\n";
110+
$testsPassed++;
111+
} else {
112+
echo "❌ FAIL (Expected null return)\n";
113+
$testsFailed++;
114+
}
115+
});
116+
117+
echo "\nTest Suite Complete. Passed: $testsPassed, Failed: $testsFailed\n";
118+
if ($testsFailed > 0) {
119+
exit(1);
120+
}
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
#!/bin/bash
2+
cd "$(dirname "$0")"
3+
4+
echo "Starting mock PHP server on port 8080..."
5+
php -S 127.0.0.1:8080 local-ecs-mock-server.php > /dev/null 2>&1 &
6+
SERVER_PID=$!
7+
8+
sleep 1
9+
echo "Running test client..."
10+
php local-ecs-test.php
11+
12+
echo "Cleaning up..."
13+
kill $SERVER_PID
14+
echo "Done!"

0 commit comments

Comments
 (0)