目前,我在InnoDB表中将图像(最大6MB)存储为BLOB。 随着数据量的增长,夜间备份越来越慢,阻碍了正常的性能。
因此,二进制数据需要转到文件系统。 (指向文件的指针将保存在数据库中。)
数据具有类似关系的树:
- main site
- user_0
- album_0
- album_1
- album_n
- user_1
- user_n
etc...
现在我希望数据通过目录结构均匀分布。我应该怎样做到这一点?
我想我可以尝试MD5('userId, albumId, imageId');
并将结果字符串切片以获取我的目录路径:
/var/imageStorage/f/347e/013b/c042/51cf/985f7ad0daa987d.jpeg
这样我就可以将第一个字符映射到服务器,并将目录结构均匀地分布在多个服务器上。
然而, 可以保持每个用户的图片组织,可能会将1张相册的图片分散到多个服务器上。
我的问题是:
以平衡的方式将图像数据存储在文件系统中的最佳方法是什么,同时将用户/相册数据保持在一起?
我在思考正确的方向吗?或者这是完全做事的错误方式?
更新
我将为最高级别的分割进行md5(user_id)
字符串切片。
然后将所有用户数据放在同一个存储桶中。这将确保数据的均匀分布,同时保持用户数据紧密存储。
/var - imageStorage - f/347e/013b - f347e013bc04251cf985f7ad0daa987d - 0 - album1_10 - picture_1.jpeg - 1 - album1_1 - picture_2.jpeg - picture_3.jpeg - album1_11 - picture_n.jpeg - n - album1_n
我想我会使用从后面拆分的albumId(我喜欢这个想法!),以保持每个目录的相册数量更小(尽管大多数用户不需要)。
谢谢!
答案 0 :(得分:23)
从后面拆分用户ID。 e.g。
UserID = 6435624
Path = /images/24/56/6435624
对于备份,您可以使用MySQL Replication并备份从站 数据库,以避免备份时出现问题(例如锁定)。
答案 1 :(得分:7)
关于将文件名分配到不同目录的一件事,如果你考虑将你的md5文件名拆分成不同的子目录(这通常是个好主意),我建议将完整的哈希保存为文件名,并将前几个字符复制为目录名称。通过这种方式,您可以更轻松地识别文件,例如当你必须移动目录时。
e.g。
abcdefgh.jpg - >一个/ AB / ABC / abcdefgh.jpg
如果您的文件名不是均匀分布的(不是哈希),请尝试选择一种获得均匀分布的分割方法,例如:最后一个字符,如果它是递增的用户ID
答案 2 :(得分:3)
我正在使用此策略给出唯一的图片ID
构建如下路径
17 >> 71 >> /71.jpg
163 >> 0361 >> /03/61.jpg
6978 >> 8796 >> /87/96.jpg
1687941 >> 01497861 >> /01/49/78/61.jpg
此方法可确保每个文件夹最多包含100张图片和100个子文件夹,并且负载均匀分布在最左侧的文件夹中。
此外,您只需要图片的ID到达文件,无需读取包含其他元数据的图片表。 用户数据确实不是紧密地存储在一起,ID-Path关系是可预测的,这取决于您的需求。