Amazon web services 从Beanstalk/EC2 Web应用程序读取/写入S3图像
我有一个web应用程序(Linux EC2实例上由Elastic Beanstalk管理的PHP),允许用户上传图像 我担心的是,如果我上传我的代码,我将首先下载所有的图片,然后重新上传我的新代码,如果他们留在EC2。因此,显而易见的解决方案似乎是将映像目录移动到S3 到目前为止,我发现的方法是挂载驱动器或SDK。我发现,对于这两种方法,Elastic Beanstalk似乎都运行在写保护的驱动器位置,这会阻止我访问其他方法 例如,对于已装入的驱动器,我无法递归访问足够多的目录以访问已装入的驱动器。Beanstalk正在/var/app/current/中运行,安装的驱动器位于/var/s3-{bucket mount name}。如果我尝试访问它(../../s3-{bucket mount name}),它会在与我的应用程序相同的文件夹中查找它 当我按照SDK的说明操作时,我将其安装在ec2 user中。所以它位于/home/ec2 user/vendor/autoload.php,和以前一样,我也无法访问该文件夹(即使是从require语句中)Amazon web services 从Beanstalk/EC2 Web应用程序读取/写入S3图像,amazon-web-services,amazon-s3,amazon-ec2,amazon-elastic-beanstalk,Amazon Web Services,Amazon S3,Amazon Ec2,Amazon Elastic Beanstalk,我有一个web应用程序(Linux EC2实例上由Elastic Beanstalk管理的PHP),允许用户上传图像 我担心的是,如果我上传我的代码,我将首先下载所有的图片,然后重新上传我的新代码,如果他们留在EC2。因此,显而易见的解决方案似乎是将映像目录移动到S3 到目前为止,我发现的方法是挂载驱动器或SDK。我发现,对于这两种方法,Elastic Beanstalk似乎都运行在写保护的驱动器位置,这会阻止我访问其他方法 例如,对于已装入的驱动器,我无法递归访问足够多的目录以访问已装入的驱动
我该怎么办?我已经搜索并阅读了所有我能找到的似乎有用的东西,但我什么也没找到。我不完全明白你所说的在与你的应用程序相同的文件夹中查找是什么意思,但以下是我从基于PHP的web应用程序读取/写入S3文件的方法: 1) 为您的应用程序创建一个新bucket。此bucket可以与管理Elastic Beanstalk项目的bucket分开 2) 在您的bucket中,转到permissions->bucket policy并添加此策略以公开您的图像重要提示:将BUCKET\u名称替换为您的BUCKET的实际名称
{
"Id": "Policy1397632521960",
"Statement": [
{
"Sid": "Stmt1397633323327",
"Action": [
"s3:GetObject"
],
"Effect": "Allow",
"Resource": "arn:aws:s3:::BUCKET_NAME/*",
"Principal": {
"AWS": [
"*"
]
}
}
]
}
3) 使用Amazon SDK创建composer.json文件,并替换为所需的任何版本。将composer.json放在项目文件夹的根目录中。(当您上传项目代码时,Elastic Beanstalk为您发挥了神奇的作用,并将安装所有composer软件包)
4) 在处理文件上载的PHP文件的顶部包含此项
require __DIR__ . '/vendor/autoload.php';
use Aws\S3\S3Client;
5) 使用AWS PHP SDK创建S3Client对象。用正确的值替换\u密钥、\u密钥和\u BUCKET\u区域。同样,将其添加到同一文件中
$client = S3Client::factory(
[
'credentials' =>
[
'key' => 'YOUR_KEY',
'secret' => 'YOUR_SECRET'
],
'region' => 'YOUR_BUCKET_REGION',
'version' => 'latest'
]
);
6) 最后,在完成了所有有趣的设置之后,下面是当用户上传文件时,如何将图像对象放入S3。将BUCKET_NAME替换为BUCKET的确切名称,将FILE_NAME.JPG替换为S3上的目标文件名,将PATH/TO/TEMP_FILE.JPG替换为将映像存储在Elastic Beanstalk服务器上的临时路径
$client->putObject([
'Bucket' => 'BUCKET_NAME',
'Key' => 'FILE_NAME.JPG',
'Body' => fopen('PATH/TO/TEMP_FILE.JPG', 'rb'),
'ACL' => 'public-read'
]);
7) 好的,这样就可以处理文件写入。现在,一旦你想向用户显示上传的文件,你可以用一个普通的标签。同样,用正确的值替换所有大写字段:
<img src="https://s3-YOUR_BUCKET_REGION.amazonaws.com/BUCKET_NAME/FILE_NAME.JPG" alt="My S3 image">
8) 您现在应该有一个web应用程序,它具有对AmazonS3的图像写入/读取功能 这似乎奏效了,我比其他解决方案更喜欢它: 我使用的bucket权限策略只允许访问找到的特定URL: 这使我能够限制对图像的访问(至少在我能够尝试的范围内),但来自web主机的图像除外。我仍然会使用API来编写文件,如果出于某种原因,我发现我需要列出一个目录
至于我关于包含composer.json文件的部分,我开始上传它,而不是试图从代码中引用autoload.php文件。并对include路径使用DIR。如果没有克里斯蒂安的帮助,我是不会想到这两件事的。谢谢!我不是100%确定它能回答所有问题,但它帮助很大!我想我错过了一些你帮助点击的东西:1。我不必引用composer位置,我在代码中使用Json文件对其进行配置。2.如何处理s3端的权限。昨天晚上我刚刚弄清楚了URL访问权限,并看到了所需的权限(我认为授予ec2访问权限就足够了),但后来我不知道如何将其应用于所有人!再次感谢!没问题!如果还有什么不清楚的地方,只要提出来,我会尝试添加到我的答案中?或者我应该在Beanstalk中将它们设置为环境变量并动态引用它们?我不确定这是否有区别,或者一个比另一个更安全。我还希望在web服务器之外保持图像的私密性。据我所知,两者都应该是同等安全的。至于你的第二个问题,我建议你访问我所附的链接。你不能让你的网站上的图片是真正私有的,但是你可以让认证成为url的一部分。通过这种方式,它们被认为是足够私密的,以至于随机的人找不到它们:“Principal”:{“AWS”:[“*”]}的AWS部分是否意味着它只是经过身份验证的AWS用户?我理解文章中的一些内容,但并不真正理解如何实现它。
<img src="https://s3-YOUR_BUCKET_REGION.amazonaws.com/BUCKET_NAME/FILE_NAME.JPG" alt="My S3 image">