Example #1
0
        /// <summary>
        /// Applies new fragment received from client to the upload session.
        /// Returns a boolean: is the new fragment last in session
        /// </summary>
        /// <param name="file_total_length"></param>
        /// <param name="range_start"></param>
        /// <param name="range_end"></param>
        /// <param name="data"></param>
        /// <returns></returns>
        public async Task <bool> AddFragment(long file_total_length, long range_start, long range_end, byte[] data)
        {
            // check if fragment size exceeds server limit
            if (range_end - range_start > _fragmentSizeLimit)
            {
                throw new Bits.FragmentTooLarge(range_end - range_start);
            }

            // case new fragment is the first fragment in this session
            if (_expectedFileLength == -1)
            {
                _expectedFileLength = file_total_length;
            }

            if (LastRangeEnd + 1 < range_start) // case new fragment's range is not contiguous with the previous fragment, will cause the server to respond with status code 416
            {
                throw new Bits.InvalidFragment(LastRangeEnd, range_start);
            }
            if (LastRangeEnd + 1 > range_start) // case new fragment partially overlaps last fragment, BITS protocol states that server should treat only the non-overlapping part
            {
                range_start = LastRangeEnd + 1;
            }

            try
            {
                if (_stream.CanSeek)
                {
                    Console.WriteLine("Can seek");
                }
                else
                {
                    Console.WriteLine("Can't seek");
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);
                await OpenFile();
            }
            var stream = new PartialFileStream(_stream, range_start, range_end);
            await stream.WriteAsync(data, 0, (int)stream.Length, CancellationToken.None);

            await stream.FlushAsync();

            _fragments.Add(new Fragment
            {
                RangeStart = range_start,
                RangeEnd   = range_end
            });

            // case new fragment is the first fragment in this session,
            // we write the final uploaded data to file
            if (range_end + 1 == _expectedFileLength)
            {
                //await _file.WriteAsync(GetFinalDataFromFragments(), 0, 0);
                return(true);
            }

            return(false);
        }
Example #2
0
        public async Task <HttpResponseMessage> Stream(string fileName, string folder = "Published")
        {
            try
            {
                DirectoryEnum directory = folder == "Uploaded" ? DirectoryEnum.Uploaded : DirectoryEnum.Published;
                if (!await _fileProvider.Exists(fileName, directory))
                {
                    return(new HttpResponseMessage(HttpStatusCode.NotFound));
                }

                long totalSize = await _fileProvider.GetLengthAsync(fileName, directory);

                if (Request.Headers.Range != null)
                {
                    return(await CreateRangeResponse(Request, fileName, "application/octet-stream"));
                }

                ContentInfo contentInfo = GetContentInfoFromRequest(Request, totalSize);
                if (contentInfo == null)
                {
                    return(new HttpResponseMessage(HttpStatusCode.RequestedRangeNotSatisfiable));
                }
                Stream stream = new PartialFileStream(await _fileProvider.OpenRead(fileName, directory), contentInfo.From, contentInfo.To);
                HttpResponseMessage httpResponse = new HttpResponseMessage
                {
                    Content = new StreamContent(stream, StreamExtensions.BufferSize)
                };
                SetResponseHeaders(httpResponse, contentInfo, totalSize, fileName);
                return(httpResponse);
            }
            catch (Exception e)
            {
                var errorResponse = new HttpResponseMessage(HttpStatusCode.InternalServerError)
                {
                    Content = new StringContent(e.ToString())
                };
                return(errorResponse);
            }
        }