mysql - 在S3上托管文件并使用mysql

原文 标签 mysql database amazon-web-services amazon-s3

这个问题可能太笼统了,但是…
我想接受用户上传的图片并在s3上托管它们。最好的做法是什么?我在想:
mysql-创建一个包含所有图像元数据的表:
自动增量ID
上载程序的用户ID
指向它在s3中的位置的弹头或路径
其他图像元数据?(尺寸、宽度、高度等)
s3-创建一个新的bucket来保存图像
站点后端-处理上载的逻辑:
接受用户上传、验证文件等
可选地处理图像(调整大小、转换等)
上传到合适的s3 bucket w/a new random slug
如果成功,则向mysql表中添加新记录
——
这是使用s3作为带web服务的云提供商的标准实践吗?如何确保数据库和s3彼此保持更新?例如,如果从数据库中手动删除记录,会发生什么情况?我应该如何处理孤立的s3对象?或者另一方面,如果从s3中删除了一个图像,但没有在mysql表中相应的记录,该怎么办?这仅仅取决于我写一个脚本来验证两个系统之间的完整性吗?

最佳答案

查看get bucket/list objects调用返回的信息。
http://docs.aws.amazon.com/AmazonS3/latest/API/RESTBucketGET.html
特别是尺寸、上次修改和ETag。
上传时将这些保存在表中。
list objects返回关于bucket中对象的信息,对象按顺序列出,每个请求最多1000个对象,然后您可以继续执行上次的操作,执行下一个请求。
以每1000个请求0.005美元计算,您只需在8000个请求中审计一个包含800万个对象(例如我拥有的对象)的bucket,花费0.04美元。
etag特别重要,因为在PUT请求中,它会自动设置为对象主体的hex md5散列。(在多部分上传时,它是每个部分的连接二进制md5的十六进制md5,后跟部分的数量)。有了这些容易获取的信息和大小,您就有了一些需要协调的东西,并有了合理的保证,即bucket中的对象正是您所相信的对象。
然后编写一个获取对象列表的脚本,并定期与数据库进行比较。
想到的另一个重要的最佳实践是不要让分散的代码接触数据库和s3。把这两件事联系在一起的代码保留下来。
其他与一致性相关的想法…s3中的x-amz-meta-*用户定义的头非常有用;您可以在上传时设置它们,或者稍后通过带有修改元数据的api“将对象复制到自身”来修改它们。您可以为每个对象存储~8k元数据,例如将其与包含该对象的数据库行关联的id。此信息无法从“get bucket/list object”调用中获得,必须针对特定对象发送httpHEAD请求才能获取元数据…但是如果你想知道一个搁浅的bucket对象是从哪里来的,那么最好保存这些信息。请注意,任何被授权下载该对象的人都会在响应头中获得元数据的副本(如果他们正在查找,则很容易看到),因此,您应该在公共对象或广泛可用的对象上存储的唯一内容将是琐碎而不敏感的内容。x-amz-meta-image-id: 1337可能是安全的,如果知道图像id没有特别的后果。同样,如果它是一个调整大小的图像,存储原始源图像的md5或sha有助于编程验证“是”,“此图像”是“该图像”的调整大小的版本,即使有人获得了这个特定的元数据,它也没有任何实际意义,因为我们已经所有相关图片的权利。任何敏感或个人数据都不应为公共内容存储在那里,但在非公共对象上,元数据与对象本身一样安全。

相关文章:

javascript - 如何在循环中使用$ .data以正确显示每个div

php - Codeigniter中的数据库插入失败

wordpress - WordPress的永久链接不适用于AWS

mysql - MySQL IN运算符结果集顺序

mysql - 将3个表连接在一起-其中一个表返回空结果。如何在WHERE子句中忽略此表?

php - 如何在问题表中得到未回答的问题?

php - MySQL / PHP-文本格式

mysql - 您可以创建不是存储过程的通用脚本吗?

javascript - 与Javascript库互操作(即NPM软件包AWS Amplify)

python - 给定一个archive_id,我该如何将存档从AWS Glacier移至S3存储桶?