3

我目前正在使用 Zend 框架并有一个上传文件表单。经过身份验证的用户可以上传文件,该文件将存储在应用程序的目录中,位置存储在数据库中。这样它就可以显示为可以下载的文件。

<a href="/upload-location/filename.pdf">Download</a>

但我注意到的是,同名文件会覆盖上传目录中的文件。没有错误消息,文件名也不会增加。所以我认为该文件必须被覆盖(或永远不会上传)。

在上传、移动或存储这些文件时,我应该注意哪些最佳做法?我是否应该始终重命名文件以使文件名始终唯一?

4

3 回答 3

9

通常,我们不使用用户指定的名称存储文件,而是使用我们(即我们的应用程序)选择的名称。

例如,如果用户上传my_file.pdf,我们会:

  • 在数据库中存储一行,包含:
    • id; 一个自动增量,主键——“ 123”,例如
    • 用户给出的名称;这样我们就可以在有人尝试下载文件时发送正确的名称
    • 文件的内容类型;application/pdf或类似的东西,例如。
    • “我们的”名称:file-123例如
  • 当有对带有 的文件的请求时id=123,我们知道应该获取 ( 'file-' . $id) 并发送哪个物理文件。
  • 我们可以使用我们存储在数据库中的名称为“另存为”对话框设置一些标题以将正确的“逻辑”名称发送到浏览器
  • 内容类型相同,顺便说一句

这样,我们确保:

  • 没有文件有任何“错误”的名称,因为我们是选择它的人,而不是客户
  • 没有覆盖:因为我们的文件名包括我们表的主键,这些文件名是唯一的
于 2009-12-10T19:31:53.280 回答
1

继续 Pascal MARTIN 的回答:

如果使用 id 作为名称,您还可以提出目录命名策略。我不再需要/somedir/part1ofID/part2OfID从文件系统中获取信息,/somedir/theWholeID但它可以让您从拆分 ID 以形成路径和文件名的方式中选择存储在同一目录中的文件数量。

下一个好处是,您用于将文件实际输出给用户的脚本可以选择用户是否有权查看文件。这当然需要将文件存储在默认情况下每个人都无法读取的地方。

您可能还想看看这个其他问题。不完全相关,但需要注意。

于 2009-12-10T19:47:55.477 回答
0

是的,您需要想出一种方法来唯一地命名它们。我已经看到了各种不同的策略,从基于原始文件名的哈希、db 记录的 pk 和上传时间戳,到某种类型的 slugging,再次基于其附加或相关记录的 db 记录中的各种字段。

于 2009-12-10T19:35:50.840 回答