1
cevincheung 2014-04-26 19:18:49 +08:00
discuz是这么干的:
在你下次发帖的时候,提示有未使用的附件,要求你处理并且必须处理。否则无法发帖。如果本次还是没使用,ok,下次还接着提示。 |
2
jsonline 2014-04-26 19:47:15 +08:00 via Android
最好不清空
|
3
bearcat001 2014-04-26 19:53:25 +08:00
看看这种思路行不?
上传后的图片在tmp目录中,确定文章提交了才把它移动到可用的位置,否则等系统自动清空 如果想要图片上传后预览,也可以弄一个链接地址用来显示图片,后端将其转换到临时目录中 |
4
ericls 2014-04-26 19:56:38 +08:00 via Android
楼主问出了困扰我多时的问题。。 谢谢楼主和楼上各位
|
5
leafgray 2014-04-26 19:57:15 +08:00
上传临时目录,保存时再移动到正式使用的目录。定时清临时目录。
==== 或者插入时都先不上传,保存时再上传----这个没有FileApi的话,可能就得控件了。。 一楼方法好像挺靠谱的。 |
6
imganquan 2014-04-26 19:59:16 +08:00 via iPhone
我这里也是先进入tmp目录,再移动到业务数据目录。
|
7
yakczh 2014-04-26 20:17:47 +08:00
把图片删了就没事了
|
8
julyclyde 2014-04-26 20:51:20 +08:00
weibo.COM解决这个问题的方案是:上传到图床,那是由另一个部门管理的
另外weibo.COM的发言条目删除后,其附件图不删除 |
9
vvniu OP @cevincheung 好办法,但是不怎么人性化,但是又感觉最有效
@bearcat001 @leafgray @imganquan 原来我也是这么想的,其实和我的设想大概都一个意思,但是要是一直都有人在发贴,怎么定时清理?然后在给图片加个时间字段?我觉得结合一楼的办法最好 @ericls 有什么问题大家分享呗 @julyclyde 那越堆越多咋办 |
10
raincious 2014-04-26 21:48:21 +08:00
(对高质量的网站来说)用户上传的任何东西都是有价值的,所以留着也无所谓。我个人是留着的(有一定怕麻烦的成分)
就楼主的要求来说,附件不应该在发帖前上传才是,可以利用FLASH或者HTML5(不知道可不可以)先显示一个缩略图,用户发布内容的时候,服务器一并处理附件。 |
11
ksc010 2014-04-26 22:12:05 +08:00
可能楼主觉得这样浪费存储空间什么的
我觉得这种情况下 可以不用管他上传了图片有没有使用 只要保证不重复上传就ok了 (存储时候每个资源的唯一性) |
12
lincanbin 2014-04-26 22:15:31 +08:00 via Android
上传时即将附件信息存进数据库,定时清理路径未在任何帖子中出现过的附件
另外附件数据表还要保存filesize和md5 防止重复上传 |
14
gfreezy 2014-04-26 23:09:18 +08:00 1
就这么丢着好了,实际环境中这种无效的图片比例很小。删除图片获得的好处(一点点的硬盘空间)远远比不上给系统增加的复杂性。
|
15
odirus 2014-04-26 23:38:40 +08:00
用户上传的数据很珍贵,应当重视。用户上传图片后服务器端“顺便”记录文件的MD5值,记录到缓存中,下次上传图片的时候再“顺便”计算一下MD5,如果发现命中缓存,说明文件已经存在,并检索出文件名。有些情况下特别有用,比如很多公司还没有自己的图床,也许会使用第三方的存储,针对热门的文件(比如豆瓣东西,会有很多重复的图片),可以减少很大的压力。
|
16
vvniu OP |
17
vvniu OP |
19
raincious 2014-04-26 23:56:20 +08:00
@vvniu 我的方式是将某一段时间内的文件用一个文件名存在FTP的同一个目录下(是的,用户将文件上传到应用程序服务器之后,服务器会将它处理好之后传到FTP上),比如这周上传的文件,这周内就不能传第二个一样的了(FTP操作的时候会跳过重复的文件)。
另外你可以实现一个统一的操作类来进行附件上传管理,比如每当用户上传一个文件之后,就将文件算好MD5,然后加到数据库中,如果之后又有一个一样的文件进来,直接拷贝数据库中的row然后改掉PK和上传者存回去就好了;而如果这是第一个出现在网站中的文件,就执行储存操作。 另外个人觉得,如果你的网站是公共形式的,没有私密的内容(比如个人隐私相册),没必要区分用户的附件空间。就像V2EX一样,你发表的所有内容都不属于你了。 |
22
odirus 2014-04-27 00:05:27 +08:00
@vvniu 查找一遍所有的文件md5可以采用缓存的方法,redis里面时间复杂度为常数,不过一个大的系统每次都要在全局范围内查找的话,最终整个缓存会无比庞大,甚至不可控,这个时候可以参考关系数据库中的分库思路,按照图片类型、时间段等进行分别缓存,保存在不同的缓存服务器上。运算量最大的地方就是服务器计算文件的MD5值。不过很多时候都可以在WEB前端计算,上传图片之前先查询该文件是否已经被上传过了,我想会好一些。
|
23
raincious 2014-04-27 00:07:08 +08:00
@vvniu 嗯……我可能没说清楚,我的意思是,将文件算好MD5之后的文件名放在按照时间周期算出的目录下。不是将时间作为文件名。刚着急上床所以打错了,特此更正下。
|
24
yueyoum 2014-04-27 00:27:41 +08:00
以前我的处理方式是:
简化一下 附件表 topic_attachment +------+---------+--------------+-----------+ | id | name | upload_date | topic_id | +------+---------+--------------+-----------+ 上传图片会先存入 topic_attachment 表, insert into topic_attachment (topic_id) values (0) 注意这里把 topic_id 设置为0 当帖子发布成功后,就把 topic_id 设置为当前发表的帖子ID。 如果 上传完附件 ,但是帖子没发表。 当下次打开网页的时候, 就把 select * from topic_attachment where topic_id = 0;的结果返回 并提示 这些附件 需要处理,如果不处理,多少天之后会删除。 用户如果顺着提示点进去,再发贴的时候,就可以勾选这些列出来的附件。 发表完,就把那些勾选的 attachment topic_id 设置为当前发布帖子的ID。 整个流程就是这样, 既方便了用户,也给予了明确提示(如果不处理,多少天要删除)。 顺便也清理了服务器上的无用文件。 ———————————————————————————————————————————————————————————————————— 如果现在让我重新设计, 我会用redis。 用户只要是在编辑帖子,javascript 就不停的 ajax post 帖子的内容到 server。 server 将这些内容塞进redis,当然post的文件还是存磁盘。 如果用户编辑到一半,关闭了浏览器,再打开帖子i编辑器的时候, javascript会向server 查询是否有帖子缓存在redis中,如果有,server会返回帖子内容, javascript自动填充, 这样就有了自动保存的功能。 当用户点击了发表按钮后,POST到server,server再去存mysql,清理redis。 如果用户编辑到一半,然后在也不打开帖子编辑了怎么办? 用定时任务来处理,比如对于已经缓存了1周的帖子,就清除,连同它的附件。 |
25
vvniu OP |
26
vvniu OP @yueyoum 刚刚看了下redis,感觉还是有必要学的,有什么好的(经验/文章/网站)指导一下吗?ps:基本不会用数据库,只会最简单的几个语句
|
27
xgod 2014-04-27 06:16:45 +08:00
先存储到临时tmp目录,保存数据库时进行从临时目录移动到正式目录,没有什么性能问题,临时目录基本不用删除,撤消带附件的记录占实际业务比例很小的,而且硬盘很便宜的,基本不用纠结。
|
28
ijse 2014-04-27 09:39:48 +08:00
楼上们说的很受用~~ 多谢大家。
我觉得保存用户正在编辑中的帖子,可以把内容保存在用户本地,比如用LocalStorage什么的,页面打开时检查本地存储的内容,如果有的话,可以提示恢复;这样用户在编辑时不必频繁与服务器通信。 对于用户上传的文件,一般也会先保存在系统临时目录中,等用户保存后再移动到存档目录中。 临时目录下的文件系统会自动清理,比如RHEL 默认会每30天清理一次旧文件,因此一般不必担心文件夹太大。 用户在上传文件前先发一个请求比对下md5是不错的方法,可以只检查最近一段时间内重复的文件,这样也可以节省用户上传文件的等待时间。 不过我还是习惯自己在确认文件没用的前提下自己清理。 |
29
learnshare 2014-04-27 11:15:39 +08:00
@bearcat001 +1
|
30
shinebay 2014-04-27 23:02:46 +08:00
把它C盘格式化了
|
31
lm902 2014-04-28 06:38:53 +08:00 via iPhone
图片缓存到浏览器local storage,点击发布才上传
|
33
leafgray 2014-04-28 12:07:58 +08:00
|
34
sun019 2014-04-28 14:50:09 +08:00
别走远了 discuz 的方法挺靠谱的 但是也要看用到什么场景了
|
35
zstxt1989 2014-04-29 09:35:21 +08:00
还是先上传到临时目录,保存时移动到存储区吧。
如果要建立附件归属关系,就得用dz的方法了。 |
36
lygmqkl 2014-04-29 21:42:29 +08:00
大数据时代 分开做个单独的图床就行了。。。。 不要那么洁癖。。。。
|