代码之家  ›  专栏  ›  技术社区  ›  Tom DeMille

将文件存储为数据库中的字节数组,是否存在安全风险?

  •  1
  • Tom DeMille  · 技术社区  · 16 年前

    我们有一个允许用户上传文件的ASP.NET应用程序,这些文件保存到临时磁盘位置,然后附加到一个记录并保存在数据库中。

    我的问题与安全和/或病毒问题有关。这种方法有安全漏洞吗?如果病毒从未执行(文件保存,然后使用文件流打开,转换为字节数组并保存到数据库),它会造成危害。

    稍后,当需要该文件时,我们将该文件流回到用户。

    文件保存到Web服务器上的文件夹中,如下所示:

    context.Request.Files[0].SaveAs(); (位置是app_data/files下的文件夹)

    稍后,当同一个用户创建一个记录时,我们从磁盘中获取该文件并将其存储在数据库中,如下所示:

    FileStream fileStream = File.OpenRead(currentFilePath);
    byte[] ba = new byte[fileStream.Length];
    int len = fileStream.Read(ba, 0, ba.Length);
    //ba saved to DB here as varbinary(max)
    

    我们限制可以上载到此列表的文件:

    List<string> supportedExtensions = new List<string>(10) {".txt", ".xls", ".xlsx", ".doc", ".docx", ".eps", ".jpg", ".jpeg", ".gif", ".png", ".bmp", ".rar", ".zip", ".rtf", ".csv", ".psd", ".pdf" };
    

    文件将以如下方式流回到用户的Web浏览器:

    //emA = entity object loaded from DB
    context.Response.AppendHeader("Content-Disposition", "inline; filename=\"" + emA.FileName + "\"");
    
    context.Response.AddHeader("Content-Type", emA.ContentType);
    context.Response.BinaryWrite(emA.FileContent);
    
    3 回复  |  直到 16 年前
        1
  •  3
  •   David    16 年前

    接受来自未知用户的文件时总是存在安全风险。任何人都可能在Office文档中的vba(Visual Basic for Applications)中编写病毒。

    与直接将它们保存在文件系统或数据库中相比,您的方法或多或少存在安全风险。 除了一个问题…

    如果文件保存到磁盘上,则可以使用传统的病毒扫描程序进行扫描。据我所知,大多数病毒扫描器不扫描以字节数组形式存储在数据库中的文件。

    如果是我的服务器,我会出于性能原因而不是安全原因将它们存储在文件系统中,而且您可以打赌,如果我允许潜在的危险文件,如Office文档、可执行文件等,我会让病毒扫描程序对它们进行扫描。

        2
  •  1
  •   IrishChieftain    16 年前

    让您的用户在允许上传文件之前创建登录名。这种未经检查的访问是闻所未闻的…并不是说这本身就是一个解决方案,而是像所有好的安全系统一样,它可以形成一个额外的层:—)

        3
  •  1
  •   AnthonyWJones    16 年前

    我看不出有比把文件保存到磁盘上更大的安全风险了。这里的风险通常与存储数据的位置无关,因为正如您已经指出的,存储的文件不会被执行。

    风险通常在于数据的传输方式。蠕虫会利用这种环境,将系统中刚传输的数据视为代码,并开始执行。这种利用并不要求存在传输“文件”的任何感觉,在过去,一个特殊格式的URL就足够了。

    也就是说,我从来没有理解将大型二进制数据存储在SQL数据库中的愿望。为什么不将文件保存在磁盘上,并将文件路径存储在数据库中呢?然后,您可以使用诸如writefile或url re-writing之类的功能让IIS做它擅长的事情。