renoki-co/laravel-ec2-metadata

使用Laravel的Eloquent语法检索EC2元数据。

1.0.0 2022-02-03 20:50 UTC

README

CI codecov StyleCI Latest Stable Version Total Downloads Monthly Downloads License

使用Laravel的Eloquent语法检索EC2元数据。

🤝 支持

如果您在生产应用、演示、爱好项目、学校项目等中使用Renoki Co.的一个或多个开源包,请通过Github Sponsors赞助我们的工作。 📦

🚀 安装

您可以通过composer安装此包

composer require renoki-co/laravel-ec2-metadata

🙌 使用方法

此包旨在使您更容易实现自己的方法并保持简单,无需过多关注请求。

在以下简例中,您可以计算EC2 Spot实例终止前的秒数。

use Carbon\Carbon;
use RenokiCo\Ec2Metadata\Ec2Metadata;

if ($termination = Ec2Metadata::terminationNotice()) {
    // The instance is terminating...

    $secondsRemaining = Carbon::parse($termination['time'])->diffInSeconds(now());

    echo "The instance is terminating in {$secondsRemaining} seconds.";
}

设置版本

Ec2Metadata类的默认版本是latest,但为了避免API更改导致代码中断,请定义要运行的版本。

您可以在IMDSv2文档中查看可用版本的列表,在获取实例元数据的可用版本下。

use RenokiCo\Ec2Metadata\Ec2Metadata;

Ec2Metadata::version('2016-09-02');

调用自定义端点

IMDSv2 API相当复杂,您可以从Ec2Metadata类中使用一些函数,以便于操作。当您需要从未实现的端点检索数据时,您可以选择定义宏或使用get()getJson()函数以纯文本或JSON解码数组的形式检索。

以下是一个检索内核ID(在/meta-data/kernel-id下)的示例

use RenokiCo\Ec2Metadata\Ec2Metadata;

$kernelId = Ec2Metadata::get('kernel-id');

要检索JSON值,您可以调用getJson。只有在您调用的端点期望的响应将是JSON编码的情况下,这才会正常工作。

在实现中,terminationNotice使用getJson()检索响应

class Ec2Metadata
{
    public static function terminationNotice(): array
    {
        // Expected response is {"action": "terminate", "time": "2017-09-18T08:22:00Z"}
        return static::getJson('/spot/instance-action');
    }
}

除了使用get()getJson()之外,您还可以定义宏

use RenokiCo\Ec2Metadata\Ec2Metadata;

Ec2Metadata::macro('kernelId', function () {
    return static::get('kernel-id');
});

$kernelId = Ec2Metadata::kernelId();

测试您的代码

此包使用HTTP客户端,这是Laravel的一个功能,利用Guzzle,您可以通过模拟响应来处理和测试请求。

正确测试您的应用程序意味着您应该充分了解AWS EC2的IMDSv2 API,以便提供适当的响应。

在测试中推送响应时,请确保考虑到第一个调用将是令牌检索。

use Illuminate\Http\Client\Request;
use Illuminate\Support\Facades\Http;
use RenokiCo\Ec2Metadata\Ec2Metadata;

Http::fake([
    'http://169.254.169.254/*' => Http::sequence()
        ->push('some-token', 200)
        ->push('ami-1234', 200),
]);

$this->assertEquals('ami-1234', Ec2Metadata::ami());

Http::assertSentInOrder([
    function (Request $request) {
        return $request->method() === 'PUT' &&
            $request->url() === 'http://169.254.169.254/latest/api/token' &&
            $request->header('X-AWS-EC2-Metadata-Token-TTL-Seconds') === ['21600'];
    },
    function (Request $request) {
        return $request->method() === 'GET' &&
            $request->url() === 'http://169.254.169.254/latest/meta-data/ami-id' &&
            $request->header('X-AWS-EC2-Metadata-Token') === ['some-token'];
    },
]);

🐛 测试

vendor/bin/phpunit

🤝 贡献

有关详细信息,请参阅CONTRIBUTING

🔒 安全

如果您发现任何与安全相关的问题,请通过alex@renoki.org发送电子邮件,而不是使用问题跟踪器。

🎉 致谢