1

我设法在 IIS 7 上设置 modh264 工作得很好,伪流工作得很好。我无法让 jwplayer 伪流与中间的 httphandler 一起工作。我的意思是,只要您点击不同的位置,视频就会从头开始!如果我删除处理程序,伪流按预期工作。我的问题是防止人们直接访问我的视频(我不在乎他们是否通过浏览器缓存保存视频)。我必须通过 10k 字节的块加载,因为视频足够大以获取内存异常

这是我的 httphandler

public class DontStealMyMoviesHandler : IHttpHandler
{
    /// <summary>
    /// You will need to configure this handler in the web.config file of your 
    /// web and register it with IIS before being able to use it. For more information
    /// see the following link: http://go.microsoft.com/?linkid=8101007
    /// </summary>
    #region IHttpHandler Members

    public bool IsReusable
    {
        // Return false in case your Managed Handler cannot be reused for another request.
        // Usually this would be false in case you have some state information preserved per request.
        get { return true; }
    }

    public void ProcessRequest(HttpContext context)
    {
        HttpRequest req = context.Request;
        string path = req.PhysicalPath;
        string extension = null;
        string contentType = null;
        string fileName = "";
        if (req.UrlReferrer == null)
        {
            context.Response.Redirect("~/Home/");
        }
        else
        {
            fileName = "file.mp4";

            if (req.UrlReferrer.Host.Length > 0)
            {
                if (req.UrlReferrer.ToString().ToLower().Contains("/media/"))
                {
                    context.Response.Redirect("~/Home/");
                }
            }
        }

        extension = Path.GetExtension(req.PhysicalPath).ToLower();
        switch (extension)
        {
            case ".m4v":
            case ".mp4":
                contentType = "video/mp4";
                break;
            case ".avi":
                contentType = "video/x-msvideo";
                break;
            case ".mpeg":
                contentType = "video/mpeg";
                break;
            //default:
            //  throw new notsupportedexception("unrecognized video type.");
        }

        if (!File.Exists(path))
        {
            context.Response.Status = "movie not found";
            context.Response.StatusCode = 404;
        }
        else
        {
            try
            {
                //context.Response.Clear();
                //context.Response.AddHeader("content-disposition", "attachment; filename=file.mp4");
                //context.Response.ContentType = contentType;
                //context.Response.WriteFile(path, false);

                //if(HttpRuntime.UsingIntegratedPipeline)
                //    context.Server.TransferRequest(context.Request.Url.ToString(), true);
                //else
                //    context.RewritePath(context.Request.Url.AbsolutePath.ToString(), true);


                // Buffer to read 10K bytes in chunk:
                byte[] buffer = new Byte[10000];
                // Length of the file:
                int length;
                // Total bytes to read:
                long dataToRead;
                using (FileStream iStream = new FileStream(path, FileMode.Open, FileAccess.Read, FileShare.Read))
                {
                    // Total bytes to read:
                    dataToRead = iStream.Length;

                    context.Response.Clear();
                    context.Response.Cache.SetNoStore();
                    context.Response.Cache.SetLastModified(DateTime.Now);
                    context.Response.AppendHeader("Content-Type", contentType);
                    context.Response.AddHeader("Content-Disposition", "attachment; filename=" + fileName);
                    // Read the bytes.
                    while (dataToRead > 0)
                    {
                        // Verify that the client is connected.
                        if (context.Response.IsClientConnected)
                        {
                            // Read the data in buffer.
                            length = iStream.Read(buffer, 0, 10000);

                            // Write the data to the current output stream.
                            context.Response.OutputStream.Write(buffer, 0, length);

                            // Flush the data to the HTML output.
                            context.Response.Flush();

                            buffer = new Byte[10000];
                            dataToRead = dataToRead - length;
                        }
                        else
                        {
                            //prevent infinite loop if user disconnects
                            dataToRead = -1;
                        }
                    }
                }
            }
            catch (Exception e)
            {
                context.Response.Redirect("home");
            }
            finally
            {
                context.Response.Close();
            }
        }
    }

    #endregion
}

先感谢您

4

1 回答 1

0

我解决了创建一个 httpmodule 的问题,因为使用 httpHandler 我必须自己管理响应,导致伪流失败(文件完全加载到输出流中)。虽然这样,如果有人直接访问文件,我只做一个简单的重定向。我不明白为什么重定向到“~/”不起作用。

public class DontStealMyMoviesModule : IHttpModule
{
    public DontStealMyMoviesModule()
    {
    }
    public void Init(HttpApplication r_objApplication)
    {
        // Register our event handler with Application object.
        r_objApplication.PreSendRequestContent +=new EventHandler(this.AuthorizeContent);
    }

    public void Dispose()
    {

    }

    private void AuthorizeContent(object r_objSender, EventArgs r_objEventArgs)
    {
        HttpApplication objApp = (HttpApplication)r_objSender;
        HttpContext objContext = (HttpContext)objApp.Context;

        HttpRequest req = objContext.Request;

        if (Path.GetExtension(req.PhysicalPath).ToLower() != ".mp4") return;

        if (req.UrlReferrer == null)
        {
            objContext.Response.Redirect("/");
        }
    }
}
于 2014-07-01T16:32:08.580 回答