我如何可以覆盖/更新,目前正由IIS服务的一个文件? [英] How can I overwrite/update a file that is currently being served by IIS?

查看:974
本文介绍了我如何可以覆盖/更新,目前正由IIS服务的一个文件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

问题:

我公司推出的,我对我们的内部网站举办每月通讯。我对通讯上传最新版本的作者的网页。一旦作者上传的最新简报,他发送一个广播电子邮件,宣布新的通讯。员工不约而同地检查新的通讯和发送反馈给笔者与需要进行修改。

My company puts out a monthly newsletter which I host on our internal website. I have a page for the author of the newsletter to upload the latest version. Once the author has uploaded the latest newsletter, he sends a broadcast email to announce the new newsletter. Employees invariably check the new newsletter and send feedback to the author with corrections that need to be made.

在笔者作出了必要的修改(通常发送广播邮件的一个小时内),他重访我的网页,并取代了最新版本的更新通讯。

Once the author has made the necessary corrections (typically within an hour of sending the broadcast email), he revisits my page and replaces the latest version with the updated newsletter.

紧随更换(或更新,​​如果你愿意)的通讯的,任何人试图访问它得到一个500 - 内部服务器错误

Immediately following the replacement (or update, if you will) of the newsletter, anyone attempting to access it gets a 500 - Internal Server Error.

我的IT人获取文件删除(一旦文件被删除,通讯作者可以重新上传更正后的副本,它工作正常。

My IT guy who maintains the server cannot delete/rename/move the file because of a permissions error and has to do a lot of convoluted things to get the file deleted (and once the file is deleted, the author of the newsletter can re-upload the corrected copy and it works fine.

我的IT人,我是pretty确保问题从我试图替换该文件,而IIS正在积极将其投放到用户(我认为的,认为我有codeD茎对发生的事情)。

My IT guy and I are pretty sure that the problem stems from that I'm trying to replace the file while IIS is actively serving it to users (which I thought of and thought that I had coded against happening).

运行更换code是如下:

The code that runs the replacement is as follows:

Protected Sub ReplaceLatestNewsletter()
    Dim dr As DataRow
    Dim sFile As String
    Dim mFileLock As Mutex

    Try
        If Me.Archives.Rows.Count > 0 Then
            dr = Me.Archives.Rows(0)
            sFile = dr("File").ToString

            If dr("Path").ToString.Length > 0 Then
                mFileLock = New Mutex(True, "MyMutexToPreventReadsOnOverwrite")

                Try
                    mFileLock.WaitOne()
                    System.IO.File.Delete(dr("Path").ToString)
                Catch ex As Exception
                    lblErrs.Text = ex.ToString
                Finally
                    mFileLock.ReleaseMutex()
                End Try
            End If

            fuNewsletter.PostedFile.SaveAs(Server.MapPath("~/Newsletter/archives/" & sFile))
        End If
    Catch ex As Exception
        lblErrs.Text = ex.ToString
    End Try

    dr = Nothing
    sFile = Nothing
    mFileLock = Nothing
End Sub

我想到了互斥将采取这种照顾(虽然经过重新阅读文档,我不知道我其实可以用它就像我想)。

I thought the Mutex would take care of this (although after re-reading documentation I'm not sure I can actually use it like I'm trying to). Other comments on the code above:


  • Me.Archives 数据表保存在的ViewState

  • 博士(文件)。的ToString 是文件名(无路径)

  • 博士(路径)的ToString 是完全本地计算机路径和文件名(如C:\\ APP_ROOT \\通讯\\档案\\ 20120214.pdf')。

  • 时事通讯的文件名设置为YYYYMMDD.pdf其中YYYYMMDD是上传的日期(格式)。

  • Me.Archives is a DataTable stored in ViewState
  • dr("File").ToString is the filename (no path)
  • dr("Path").ToString is the full local machine path and filename (i.e., 'C:\App_Root\Newsletters\archives\20120214.pdf')
  • The filenames of the newsletters are set to "YYYYMMDD.pdf" where YYYYMMDD is the date (formatted) of the upload.

在任何情况下,我是pretty确保$ C $上面c是的的文件上建立一个排它锁,以使文件可以被安全地覆盖。

In any case, I'm pretty sure that the code above is not establishing an exclusive lock on the file so that the file can be overwritten safely.

最后,我想确保在发生以下情况:

Ultimately, I would like to make sure that the following happens:


  1. 如果IIS现任文件,等到IIS已服完它。

  2. IIS之前可以再次提供服务的文件,该文件确立的排他锁,这样其他进程,线程,用户(等)无法读取或写入文件。

  3. 删除该文件完全谱写新的文件来替换或用新的内容覆盖现有文件。

  4. 删除独占锁定,使用户可以再次访问该文件。

建议?

另外,我可以使用互斥来获得在Windows文件系统中的文件的互斥锁?

Also, can I use a Mutex to get a mutually exclusive lock on a file in the Windows filesystem?

感谢您提前为您的帮助和建议。

Thank you in advance for your assistance and advice.

编辑:

这对于产生的通讯链路是基于物理文件名中的方法。所使用的方法是:

The way that the links for the newsletter are generated is based on the physical filename. The method used is:


  1. 即可在档案目录中的所有PDF文件。对于每一个文件:

  2. 从文件名解析出版日期。

  3. 保存日期,文件路径,文件名,并在的DataTable在的DataRow 每个文件网址

  4. 排序数据表按日期(降序)。

  5. 输出的第一行作为当前的问题。

  6. 输出所有后续行作为按年份和月份举办的档案。

  1. Get all PDF files in the "archives" directory. For each file:
  2. Parse the date of publication from the filename.
  3. Store the date, the path to the file, the filename, and a URL to each file in a DataRow in a DataTable
  4. Sort the DataTable by date (descending).
  5. Output the first row as the current issue.
  6. Output all subsequent rows as "archives" organized by year and month.

更新

在代替不能够当该文件中的所有现有的请求已经完成辨别的,我把在第一部分细看@ Justin的回答(你的互斥将仅当从读取过程产生作用文件也得到相同的互斥。)

In lieu of not being able to discern when all existing requests for that file have completed, I took a closer look at the first part of @Justin's answer ("your mutex will only have an effect if the process that reads from the file also obtains the same mutex.")

这使我<一个href=\"http://stackoverflow.com/questions/2593932/configure-iis7-to-server-static-content-through-asp-net-runtime\">Configure IIS7通过ASP.NET运行时服务器静态内容,并在接受的答案链接的文章。

This led me to Configure IIS7 to server static content through ASP.NET Runtime and the linked article in the accepted answer.

为此,我实现了一个处理程序,所有的PDF文件的工具新的mutex(真,MyMutexTo preventReadsOnOverwrite)来确保它只有一个线程在任何特定时间正在做与PDF东西

To that end, I have implemented a handler for all PDF files which implements New Mutex(True, "MyMutexToPreventReadsOnOverwrite") to ensure that only one thread is doing something with the PDF at any given time.

感谢您的回答,@Justin。虽然我不拉闸使用你的建议的执行情况,你的答案指着我推向一个可以接受的解决方案。

Thank you for you answer, @Justin. While I did not wind up using the implementation you suggested, your answer pointed me towards an acceptable solution.

推荐答案

您互斥才会有效果,如果从文件中读取的过程中也得到相同的互斥。什么是用于提供该文件的方法是什么?是ASP.Net使用或者这只是一个静态文件?

Your mutex will only have an effect if the process that reads from the file also obtains the same mutex. What is the method used to serve up the file? Is ASP.Net used or is this just a static file?

我的工作流程将是一个有点不同:

My workflow would be a little different:


  1. 写入新的通讯到文件

  2. 有IIS服务启动了新的文件,而不是旧的给定的URL通讯

  3. 删除旧文件,一旦该文件的所有现有请求已完成

这不需要上锁,也意味着我们不需要等到当前文件请求完成(的东西,如果人们不断制造新的请求从而可能采取无限期量)。唯一感兴趣的是第2步,这将取决于文件是如何服务 - 最简单的方法很可能是要么建立一个HTTP重定向或使用URL重写

This requires no locking and also means that we don't need to wait for requests for the current file be completed (something which could potentially take an indefinite amount of time if people keep on making new requests). The only interesting bit is step 2 which will depend on how the file is served - the easiest way would probably be to either set up a HTTP redirect or use URL rewriting

一个HTTP重定向是服务器告诉客户端在不同的地方看,当它获取给定资源的请求,使浏览器的URL自动更新以适应新的位置。例如,如果用户请求 HTTP://server/20120221.pdf 然后他们可以被自动重定向到另一个网址,如的http://服务器/20120221_v2.pdf (在浏览器中显示的URL会改变但他们需要键入URL不会)。

A HTTP Redirect is where the server tells the client to look in a different place when it gets a request for a given resource so that the browser URL is automatically updated to match the new location. For example if the user requested http://server/20120221.pdf then they could be automatically redirected to another URL such as http://server/20120221_v2.pdf (the URL shown in the browser would change however the URL they need to type in would not).

您可以在IIS 7中使用 HTT predirect 配置元素,例如:

You can do this in IIS 7 using the httpRedirect configuration element, for example:

<configuration>
   <system.webServer>
      <httpRedirect enabled="true" exactDestination="true" httpResponseStatus="Found">
         <!-- Note that I needed to add a * in for IIS to accept the wildcard even though it isn't used in this case -->
         <add wildcard="*20120221.pdf" destination="20120221_v2.pdf" />
      </httpRedirect>
   </system.webServer>
</configuration>

所链接的页面显示如何从ASP.Net更改这些设置

The linked page shows how to change these settings from ASP.Net

或者IIS可以设置为自动服务于一个不同的文件给定URL的内容,而客户端(浏览器)曾经认识的差异。这就是所谓的URL重写,可以在IIS中使用类似此内容做但它确实需要额外的组件被安装到IIS工作。

Alternatively IIS can be set up to automatically serve up the content of a different file for a given URL without the client (the browser) ever knowing the difference. This is called URL rewriting and can be done in IIS using something like this however it does require that additional components be installed to IIS to work.

使用HTTP重定向可能是最简单的方法。

Using a HTTP Redirect is probably the easiest method.

这篇关于我如何可以覆盖/更新,目前正由IIS服务的一个文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆