title: HTML5 video - ashx handler - seek
body: <p>I'm trying to use an ashx handler as an HTML5 video source. I can achieve this, but I can not move forward further on the video that what has already buffered.</p>
  
  <p>I can see on the network tab using a standard MP4 source that seeking forward creates another request, but using the handler it does not.</p>
  
  <p>Some of the videos are more than 1&nbsp;GB.</p>
  
  <p>This is what I have to get the videos working so far:</p>
  
  <pre><code>public void ProcessRequest(HttpContext context)
  {
      context.Response.Buffer = false;
      context.Response.ContentType = "video/mp4";
      FileInfo file = new FileInfo(path);
      int len = (int)file.Length, bytes;
      context.Response.AppendHeader("content-length", len.ToString());
      byte[] buffer = new byte[1024];
      Stream outStream = context.Response.OutputStream;
      using (Stream stream = File.OpenRead(path))
      {
          while (len &gt; 0 &amp;&amp; (bytes = stream.Read(buffer, 0, buffer.Length)) &gt; 0)
          {
              outStream.Write(buffer, 0, bytes);
              len -= bytes;
          }
      }
  }
  </code></pre>
  
  <p>Taken from Marck Gravells post <em><a href="https://stackoverflow.com/questions/608480/best-way-to-stream-files-in-asp-net">Best way to stream files in ASP.NET</a></em>:</p>
  
  <pre><code>&lt;video id="video-player" class="video-js vjs-default-skin" controls
       preload="auto" poster="MY_VIDEO_POSTER.jpg"
       data-setup="{}"&gt;
       &lt;source src="/Handlers/VideoHandler.ashx" type='video/mp4'&gt;
       &lt;p class="vjs-no-js"&gt;
          To view this video please enable JavaScript, and consider upgrading to a web browser that
          &lt;a href="http://videojs.com/html5-video-support/" target="_blank"&gt;supports HTML5 video&lt;/a&gt;
       &lt;/p&gt;
      &lt;/video&gt;
  </code></pre>
  
  <p>using video.js, but the same is happening if I call the handler directly in the browser.</p>
  
  <p>How can I fix this problem? It is more than likely I missing something simple.</p>
  
  <p><strong>UPDATE</strong></p>
  
  <p>After looking further I know now that I need 'Accept-Ranges'.</p>
  
  <p>I have now got</p>
  
  <pre><code>context.Response.ContentType = "video/mp4";
  
  var request = HttpContext.Current.Request;
  FileInfo file = new FileInfo(filePath);
  var responseLength = (int)file.Length;
  var buffer = new byte[1024];
  var startIndex = 0;
  
  if (request.Headers["Range"] != null)
  {
      var match = Regex.Match(request.Headers["Range"], @"bytes=(\d*)-(\d*)");
      startIndex = Parse&lt;int&gt;(match.Groups[1].Value);
      responseLength = (Parse&lt;int?&gt;(match.Groups[2].Value) + 1 ?? responseLength) - startIndex;
      context.Response.StatusCode = (int)HttpStatusCode.PartialContent;
      context.Response.Headers["Content-Range"] = "bytes " + startIndex + "-" + (startIndex + responseLength - 1) + "/" + responseLength;
  }
  
  context.Response.Headers["Accept-Ranges"] = "bytes";
  context.Response.Headers["Content-Length"] = responseLength.ToString();
  context.Response.Cache.SetCacheability(HttpCacheability.Public);
  
  context.Response.Buffer = false;
  </code></pre>
  
  <p>with help from <a href="https://stackoverflow.com/questions/5429947/supporting-resumable-http-downloads-through-an-ashx-handler">Supporting resumable HTTP-downloads through an ASHX handler?</a>, but now the write is giving me issues with the error</p>
  
  <blockquote>
    <p>HttpException was unhandled by user code
    The remote host closed the connection. The error code is 0x800704CD.</p>
  </blockquote>
  
  <p>I have tried:</p>
  
  <pre><code>using (Stream stream = File.OpenRead(filePath))
  {
  
      stream.Seek(startIndex, SeekOrigin.Begin);
      while ((responseLength - startIndex) &gt; 0 &amp;&amp; (bytes = stream.Read(buffer, 0, buffer.Length)) &gt; 0)
      {
          response.OutputStream.Write(buffer, 0, bytes);
          responseLength -= bytes;
      }
  }
  </code></pre>
  
  <p>and</p>
  
  <pre><code>using (Stream stream = File.OpenRead(filePath))
  {
      stream.Seek(startIndex, SeekOrigin.Begin);
      int bufferLength = buffer.Length, bytesRead;
      while (responseLength &gt; bufferLength &amp;&amp; (bytesRead = stream.Read(buffer, 0, bufferLength)) &gt; 0)
      {
          response.OutputStream.Write(buffer, 0, bytesRead);
          responseLength -= bytesRead;
      }
      while (responseLength &gt; 0 &amp;&amp; (bytesRead = stream.Read(buffer, 0, responseLength)) &gt; 0)
      {
          response.OutputStream.Write(buffer, 0, bytesRead);
          responseLength -= bytesRead;
      }
  }
  </code></pre>
  
  <p>How can I fix this problem?</p>