Пример #1
0
        private async Task CombineAsync(FlowRequestContext context, FlowRequest request)
        {
            var filePath = string.Concat(
                context.GetFilePathFunc(request),
                "/",
                context.GetFileName(request));

            var chunkPath      = context.GetChunkPathFunc(request);
            var chunkFilePaths = await _fileSystem.ListDirectoryAsync(chunkPath);

            using (var fileStream = await _fileSystem.OpenWriteAsync(filePath))
            {
                foreach (var file in chunkFilePaths)
                {
                    using (var sourceStream = await _fileSystem.OpenReadAsync(file))
                    {
                        await sourceStream.CopyToAsync(fileStream);
                    }
                }

                await fileStream.FlushAsync();
            }

            await _fileSystem.DeleteDirectoryAsync(chunkPath);
        }
Пример #2
0
 private static string GetChunkFilePath(FlowRequestContext context, FlowRequest request)
 {
     return(string.Concat(
                context.GetChunkPathFunc(request),
                "/",
                context.GetChunkFileName(request)));
 }
Пример #3
0
        public async Task <FlowRequest> ReadPostAsync(FlowRequestContext context, IFileSystem fileSystem)
        {
            var provider = new FlowTemporaryFileProvider(context, fileSystem);
            await context.HttpRequest.Content.ReadAsMultipartAsync(provider);

            var flowRequest = Create(provider.FormData);

            flowRequest.TemporaryFile = provider.TemporaryFiles.Single();

            return(flowRequest);
        }
Пример #4
0
        public async Task <HttpResponseMessage> HandleRequest(FlowRequestContext context)
        {
            if (context.HttpRequest.Method == HttpMethod.Get)
            {
                return(await HandleGetRequest(context));
            }

            if (context.HttpRequest.Method != HttpMethod.Post)
            {
                return(context.HttpRequest.CreateErrorResponse(
                           HttpStatusCode.BadRequest,
                           "Only GET and POST requests supported"));
            }

            return(await HandlePostRequest(context));
        }
Пример #5
0
        private async Task <HttpResponseMessage> HandlePostRequest(FlowRequestContext context)
        {
            // read request
            FlowRequest request = await _requestReader.ReadPostAsync(
                context,
                _fileSystem);

            // is valid request?
            if (!IsValidRequest(context, request))
            {
                await _fileSystem.DeleteAsync(request.TemporaryFile.Item1);

                return(context.HttpRequest.CreateErrorResponse(
                           HttpStatusCode.BadRequest,
                           "Invalid flow POST request"));
            }

            // upload temporary to chunks
            var chunkFilePath = GetChunkFilePath(context, request);

            using (Stream chunkStream = await _fileSystem.OpenWriteAsync(chunkFilePath))
            {
                using (Stream tempStream = await _fileSystem.OpenReadAsync(request.TemporaryFile.Item1))
                {
                    await tempStream.CopyToAsync(chunkStream);
                }
            }

            // delete temporary
            await _fileSystem.DeleteAsync(request.TemporaryFile.Item1);

            // if last chunk combine and move to files
            if (request.IsLastChunk)
            {
                await CombineAsync(context, request);
            }

            return(context.HttpRequest.CreateResponse(HttpStatusCode.OK));
        }
Пример #6
0
        private async Task <HttpResponseMessage> HandleGetRequest(FlowRequestContext context)
        {
            FlowRequest request = await _requestReader.ReadGetAsync(context.HttpRequest);

            if (!IsValidRequest(context, request))
            {
                return(context.HttpRequest.CreateErrorResponse(
                           HttpStatusCode.BadRequest,
                           "Invalid flow GET request"));
            }

            string filePath = GetChunkFilePath(context, request);

            if (!await _fileSystem.ExistsAsync(filePath))
            {
                return(context.HttpRequest.CreateErrorResponse(
                           HttpStatusCode.NoContent,
                           "No Content"));
            }

            return(context.HttpRequest.CreateResponse(HttpStatusCode.OK));
        }
Пример #7
0
        private bool IsValidRequest(FlowRequestContext context, FlowRequest request)
        {
            if (!request.FlowChunkNumber.HasValue ||
                !request.FlowChunkSize.HasValue ||
                !request.FlowTotalSize.HasValue)
            {
                return(false);
            }

            ulong chunkNumber = request.FlowChunkNumber.Value;
            ulong chunkSize   = request.FlowChunkSize.Value;
            ulong totalSize   = request.FlowTotalSize.Value;


            if (chunkNumber == 0 || chunkSize == 0 || totalSize == 0)
            {
                return(false);
            }

            double numberOfChunks =
                Math.Max(Math.Floor(request.FlowTotalSize.Value / (request.FlowChunkSize.Value * 1.0)), 1);

            if (chunkNumber > numberOfChunks)
            {
                return(false);
            }

            if (totalSize > context.MaxFileSize)
            {
                return(false);
            }

            if (chunkSize > context.MaxFileSize)
            {
                return(false);
            }

            return(true);
        }
Пример #8
0
 public FlowTemporaryFileProvider(FlowRequestContext context, IFileSystem fileSystem) : base(".")
 {
     _context       = context;
     _fileSystem    = fileSystem;
     TemporaryFiles = new List <Tuple <string, string> >();
 }