// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Specialized;
using System.IO;
using System.Net.Http.Formatting.Internal;
using System.Net.Http.Headers;
using System.Threading;
using System.Threading.Tasks;
namespace System.Net.Http
{
///
/// A implementation suited for use with HTML file uploads for writing file
/// content to a . The stream provider looks at the Content-Disposition header
/// field and determines an output based on the presence of a filename parameter.
/// If a filename parameter is present in the Content-Disposition header field then the body
/// part is written to a , otherwise it is written to a .
/// This makes it convenient to process MIME Multipart HTML Form data which is a combination of form
/// data and file content.
///
public class MultipartFormDataStreamProvider : MultipartFileStreamProvider
{
// pass around cancellation token through field to maintain backward compat.
private CancellationToken _cancellationToken;
///
/// Initializes a new instance of the class.
///
/// The root path where the content of MIME multipart body parts are written to.
public MultipartFormDataStreamProvider(string rootPath)
: base(rootPath)
{
FormData = HttpValueCollection.Create();
}
///
/// Initializes a new instance of the class.
///
/// The root path where the content of MIME multipart body parts are written to.
/// The number of bytes buffered for writes to the file.
public MultipartFormDataStreamProvider(string rootPath, int bufferSize)
: base(rootPath, bufferSize)
{
FormData = HttpValueCollection.Create();
}
///
/// Gets a of form data passed as part of the multipart form data.
///
public NameValueCollection FormData { get; private set; }
///
/// This body part stream provider examines the headers provided by the MIME multipart parser
/// and decides whether it should return a file stream or a memory stream for the body part to be
/// written to.
///
/// The parent MIME multipart HttpContent instance.
/// Header fields describing the body part
/// The instance where the message body part is written to.
public override Stream GetStream(HttpContent parent, HttpContentHeaders headers)
{
if (MultipartFormDataStreamProviderHelper.IsFileContent(parent, headers))
{
return base.GetStream(parent, headers);
}
return new MemoryStream();
}
///
/// Read the non-file contents as form data.
///
/// A representing the post processing.
public override Task ExecutePostProcessingAsync()
{
// This method predates support for cancellation, and we need to make sure it is always invoked when
// ExecutePostProcessingAsync is called for compatability.
return MultipartFormDataStreamProviderHelper.ReadFormDataAsync(Contents, FormData,
_cancellationToken);
}
///
/// Read the non-file contents as form data.
///
/// The token to monitor for cancellation requests.
/// A representing the post processing.
public override Task ExecutePostProcessingAsync(CancellationToken cancellationToken)
{
_cancellationToken = cancellationToken;
return ExecutePostProcessingAsync();
}
}
}