diff --git a/src/Microsoft.AspNetCore.Mvc.Core/HttpResponseStreamWriter.cs b/src/Microsoft.AspNetCore.Mvc.Core/HttpResponseStreamWriter.cs
deleted file mode 100644
index cb3e998256..0000000000
--- a/src/Microsoft.AspNetCore.Mvc.Core/HttpResponseStreamWriter.cs
+++ /dev/null
@@ -1,396 +0,0 @@
-// 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;
-using System.Buffers;
-using System.IO;
-using System.Text;
-using System.Threading.Tasks;
-using Microsoft.AspNetCore.Mvc.Core;
-
-namespace Microsoft.AspNetCore.Mvc
-{
- ///
- /// Writes to the using the supplied .
- /// It does not write the BOM and also does not close the stream.
- ///
- public class HttpResponseStreamWriter : TextWriter
- {
- private const int MinBufferSize = 128;
-
- ///
- /// Default buffer size.
- ///
- public const int DefaultBufferSize = 1024;
-
- private Stream _stream;
- private readonly Encoder _encoder;
- private readonly ArrayPool _bytePool;
- private readonly ArrayPool _charPool;
- private readonly int _charBufferSize;
-
- private byte[] _byteBuffer;
- private char[] _charBuffer;
-
- private int _charBufferCount;
-
- public HttpResponseStreamWriter(Stream stream, Encoding encoding)
- : this(stream, encoding, DefaultBufferSize)
- {
- }
-
- public HttpResponseStreamWriter(Stream stream, Encoding encoding, int bufferSize)
- {
- if (stream == null)
- {
- throw new ArgumentNullException(nameof(stream));
- }
-
- if (!stream.CanWrite)
- {
- throw new ArgumentException(Resources.HttpResponseStreamWriter_StreamNotWritable, nameof(stream));
- }
-
- if (encoding == null)
- {
- throw new ArgumentNullException(nameof(encoding));
- }
-
- _stream = stream;
- Encoding = encoding;
- _charBufferSize = bufferSize;
-
- if (bufferSize < MinBufferSize)
- {
- bufferSize = MinBufferSize;
- }
-
- _encoder = encoding.GetEncoder();
- _byteBuffer = new byte[encoding.GetMaxByteCount(bufferSize)];
- _charBuffer = new char[bufferSize];
- }
-
- public HttpResponseStreamWriter(
- Stream stream,
- Encoding encoding,
- int bufferSize,
- ArrayPool bytePool,
- ArrayPool charPool)
- {
- if (stream == null)
- {
- throw new ArgumentNullException(nameof(stream));
- }
-
- if (!stream.CanWrite)
- {
- throw new ArgumentException(Resources.HttpResponseStreamWriter_StreamNotWritable, nameof(stream));
- }
-
- if (encoding == null)
- {
- throw new ArgumentNullException(nameof(encoding));
- }
-
- if (bytePool == null)
- {
- throw new ArgumentNullException(nameof(bytePool));
- }
-
- if (charPool == null)
- {
- throw new ArgumentNullException(nameof(charPool));
- }
-
- _stream = stream;
- Encoding = encoding;
- _charBufferSize = bufferSize;
-
- _encoder = encoding.GetEncoder();
- _bytePool = bytePool;
- _charPool = charPool;
-
- _charBuffer = charPool.Rent(bufferSize);
-
- try
- {
- var requiredLength = encoding.GetMaxByteCount(bufferSize);
- _byteBuffer = bytePool.Rent(requiredLength);
- }
- catch
- {
- charPool.Return(_charBuffer);
- _charBuffer = null;
-
- if (_byteBuffer != null)
- {
- bytePool.Return(_byteBuffer);
- _byteBuffer = null;
- }
-
- throw;
- }
- }
-
- public override Encoding Encoding { get; }
-
- public override void Write(char value)
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (_charBufferCount == _charBufferSize)
- {
- FlushInternal(flushEncoder: false);
- }
-
- _charBuffer[_charBufferCount] = value;
- _charBufferCount++;
- }
-
- public override void Write(char[] values, int index, int count)
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (values == null)
- {
- return;
- }
-
- while (count > 0)
- {
- if (_charBufferCount == _charBufferSize)
- {
- FlushInternal(flushEncoder: false);
- }
-
- CopyToCharBuffer(values, ref index, ref count);
- }
- }
-
- public override void Write(string value)
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (value == null)
- {
- return;
- }
-
- var count = value.Length;
- var index = 0;
- while (count > 0)
- {
- if (_charBufferCount == _charBufferSize)
- {
- FlushInternal(flushEncoder: false);
- }
-
- CopyToCharBuffer(value, ref index, ref count);
- }
- }
-
- public override async Task WriteAsync(char value)
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (_charBufferCount == _charBufferSize)
- {
- await FlushInternalAsync(flushEncoder: false);
- }
-
- _charBuffer[_charBufferCount] = value;
- _charBufferCount++;
- }
-
- public override async Task WriteAsync(char[] values, int index, int count)
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (values == null)
- {
- return;
- }
-
- while (count > 0)
- {
- if (_charBufferCount == _charBufferSize)
- {
- await FlushInternalAsync(flushEncoder: false);
- }
-
- CopyToCharBuffer(values, ref index, ref count);
- }
- }
-
- public override async Task WriteAsync(string value)
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (value == null)
- {
- return;
- }
-
- var count = value.Length;
- var index = 0;
- while (count > 0)
- {
- if (_charBufferCount == _charBufferSize)
- {
- await FlushInternalAsync(flushEncoder: false);
- }
-
- CopyToCharBuffer(value, ref index, ref count);
- }
- }
-
- // We want to flush the stream when Flush/FlushAsync is explicitly
- // called by the user (example: from a Razor view).
-
- public override void Flush()
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- FlushInternal(flushEncoder: true);
- }
-
- public override Task FlushAsync()
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- return FlushInternalAsync(flushEncoder: true);
- }
-
- protected override void Dispose(bool disposing)
- {
- if (disposing && _stream != null)
- {
- try
- {
- FlushInternal(flushEncoder: true);
- }
- finally
- {
- _stream = null;
-
- if (_bytePool != null)
- {
- _bytePool.Return(_byteBuffer);
- _byteBuffer = null;
- }
-
- if (_charPool != null)
- {
- _charPool.Return(_charBuffer);
- _charBuffer = null;
- }
- }
- }
- }
-
- // Note: our FlushInternal method does NOT flush the underlying stream. This would result in
- // chunking.
- private void FlushInternal(bool flushEncoder)
- {
- if (_charBufferCount == 0)
- {
- return;
- }
-
- var count = _encoder.GetBytes(
- _charBuffer,
- 0,
- _charBufferCount,
- _byteBuffer,
- 0,
- flush: flushEncoder);
-
- if (count > 0)
- {
- _stream.Write(_byteBuffer, 0, count);
- }
-
- _charBufferCount = 0;
- }
-
- // Note: our FlushInternalAsync method does NOT flush the underlying stream. This would result in
- // chunking.
- private async Task FlushInternalAsync(bool flushEncoder)
- {
- if (_charBufferCount == 0)
- {
- return;
- }
-
- var count = _encoder.GetBytes(
- _charBuffer,
- 0,
- _charBufferCount,
- _byteBuffer,
- 0,
- flush: flushEncoder);
-
- if (count > 0)
- {
- await _stream.WriteAsync(_byteBuffer, 0, count);
- }
-
- _charBufferCount = 0;
- }
-
- private void CopyToCharBuffer(string value, ref int index, ref int count)
- {
- var remaining = Math.Min(_charBufferSize - _charBufferCount, count);
-
- value.CopyTo(
- sourceIndex: index,
- destination: _charBuffer,
- destinationIndex: _charBufferCount,
- count: remaining);
-
- _charBufferCount += remaining;
- index += remaining;
- count -= remaining;
- }
-
- private void CopyToCharBuffer(char[] values, ref int index, ref int count)
- {
- var remaining = Math.Min(_charBufferSize - _charBufferCount, count);
-
- Buffer.BlockCopy(
- src: values,
- srcOffset: index * sizeof(char),
- dst: _charBuffer,
- dstOffset: _charBufferCount * sizeof(char),
- count: remaining * sizeof(char));
-
- _charBufferCount += remaining;
- index += remaining;
- count -= remaining;
- }
- }
-}
diff --git a/src/Microsoft.AspNetCore.Mvc.Core/Infrastructure/HttpRequestStreamReader.cs b/src/Microsoft.AspNetCore.Mvc.Core/Infrastructure/HttpRequestStreamReader.cs
deleted file mode 100644
index 66b7773344..0000000000
--- a/src/Microsoft.AspNetCore.Mvc.Core/Infrastructure/HttpRequestStreamReader.cs
+++ /dev/null
@@ -1,438 +0,0 @@
-// 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;
-using System.Buffers;
-using System.Diagnostics;
-using System.IO;
-using System.Text;
-using System.Threading.Tasks;
-using Microsoft.AspNetCore.Mvc.Core;
-
-namespace Microsoft.AspNetCore.Mvc.Infrastructure
-{
- public class HttpRequestStreamReader : TextReader
- {
- private const int DefaultBufferSize = 1024;
- private const int MinBufferSize = 128;
- private const int MaxSharedBuilderCapacity = 360; // also the max capacity used in StringBuilderCache
-
- private Stream _stream;
- private readonly Encoding _encoding;
- private readonly Decoder _decoder;
-
- private readonly ArrayPool _bytePool;
- private readonly ArrayPool _charPool;
-
- private readonly int _byteBufferSize;
- private byte[] _byteBuffer;
- private char[] _charBuffer;
-
- private int _charBufferIndex;
- private int _charsRead;
- private int _bytesRead;
-
- private bool _isBlocked;
-
- public HttpRequestStreamReader(Stream stream, Encoding encoding)
- : this(stream, encoding, DefaultBufferSize)
- {
- }
-
- public HttpRequestStreamReader(Stream stream, Encoding encoding, int bufferSize)
- {
- if (stream == null)
- {
- throw new ArgumentNullException(nameof(stream));
- }
-
- if (!stream.CanRead)
- {
- throw new ArgumentException(Resources.HttpRequestStreamReader_StreamNotReadable, nameof(stream));
- }
-
- if (encoding == null)
- {
- throw new ArgumentNullException(nameof(encoding));
- }
-
- _stream = stream;
- _encoding = encoding;
- _decoder = encoding.GetDecoder();
-
- if (bufferSize < MinBufferSize)
- {
- bufferSize = MinBufferSize;
- }
-
- _byteBufferSize = bufferSize;
- _byteBuffer = new byte[bufferSize];
- var maxCharsPerBuffer = encoding.GetMaxCharCount(bufferSize);
- _charBuffer = new char[maxCharsPerBuffer];
- }
-
- public HttpRequestStreamReader(
- Stream stream,
- Encoding encoding,
- int bufferSize,
- ArrayPool bytePool,
- ArrayPool charPool)
- {
- if (stream == null)
- {
- throw new ArgumentNullException(nameof(stream));
- }
-
- if (!stream.CanRead)
- {
- throw new ArgumentException(Resources.HttpRequestStreamReader_StreamNotReadable, nameof(stream));
- }
-
- if (encoding == null)
- {
- throw new ArgumentNullException(nameof(encoding));
- }
-
- if (bytePool == null)
- {
- throw new ArgumentNullException(nameof(bytePool));
- }
-
- if (charPool == null)
- {
- throw new ArgumentNullException(nameof(charPool));
- }
-
- if (bufferSize <= 0)
- {
- throw new ArgumentOutOfRangeException(nameof(bufferSize));
- }
-
- _stream = stream;
- _encoding = encoding;
- _byteBufferSize = bufferSize;
- _bytePool = bytePool;
- _charPool = charPool;
-
- _decoder = encoding.GetDecoder();
-
- _byteBuffer = _bytePool.Rent(bufferSize);
-
- try
- {
- var requiredLength = encoding.GetMaxCharCount(bufferSize);
- _charBuffer = _charPool.Rent(requiredLength);
- }
- catch
- {
- _bytePool.Return(_byteBuffer);
- _byteBuffer = null;
-
- if (_charBuffer != null)
- {
- _charPool.Return(_charBuffer);
- _charBuffer = null;
- }
- }
- }
-
-#if dnx451
- public override void Close()
- {
- Dispose(true);
- }
-#endif
-
- protected override void Dispose(bool disposing)
- {
- if (disposing && _stream != null)
- {
- _stream = null;
-
- if (_bytePool != null)
- {
- _bytePool.Return(_byteBuffer);
- _byteBuffer = null;
- }
-
- if (_charPool != null)
- {
- _charPool.Return(_charBuffer);
- _charBuffer = null;
- }
- }
-
- base.Dispose(disposing);
- }
-
- public override int Peek()
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (_charBufferIndex == _charsRead)
- {
- if (_isBlocked || ReadIntoBuffer() == 0)
- {
- return -1;
- }
- }
-
- return _charBuffer[_charBufferIndex];
- }
-
- public override int Read()
- {
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (_charBufferIndex == _charsRead)
- {
- if (ReadIntoBuffer() == 0)
- {
- return -1;
- }
- }
-
- return _charBuffer[_charBufferIndex++];
- }
-
- public override int Read(char[] buffer, int index, int count)
- {
- if (buffer == null)
- {
- throw new ArgumentNullException(nameof(buffer));
- }
-
- if (index < 0)
- {
- throw new ArgumentOutOfRangeException(nameof(index));
- }
-
- if (count < 0 || index + count > buffer.Length)
- {
- throw new ArgumentOutOfRangeException(nameof(count));
- }
-
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- var charsRead = 0;
- while (count > 0)
- {
- var charsRemaining = _charsRead - _charBufferIndex;
- if (charsRemaining == 0)
- {
- charsRemaining = ReadIntoBuffer();
- }
-
- if (charsRemaining == 0)
- {
- break; // We're at EOF
- }
-
- if (charsRemaining > count)
- {
- charsRemaining = count;
- }
-
- Buffer.BlockCopy(
- _charBuffer,
- _charBufferIndex * 2,
- buffer,
- (index + charsRead) * 2,
- charsRemaining * 2);
- _charBufferIndex += charsRemaining;
-
- charsRead += charsRemaining;
- count -= charsRemaining;
-
- // If we got back fewer chars than we asked for, then it's likely the underlying stream is blocked.
- // Send the data back to the caller so they can process it.
- if (_isBlocked)
- {
- break;
- }
- }
-
- return charsRead;
- }
-
- public override async Task ReadAsync(char[] buffer, int index, int count)
- {
- if (buffer == null)
- {
- throw new ArgumentNullException(nameof(buffer));
- }
-
- if (index < 0)
- {
- throw new ArgumentOutOfRangeException(nameof(index));
- }
-
- if (count < 0 || index + count > buffer.Length)
- {
- throw new ArgumentOutOfRangeException(nameof(count));
- }
-
- if (_stream == null)
- {
- throw new ObjectDisposedException("stream");
- }
-
- if (_charBufferIndex == _charsRead && await ReadIntoBufferAsync() == 0)
- {
- return 0;
- }
-
- var charsRead = 0;
- while (count > 0)
- {
- // n is the characters available in _charBuffer
- var n = _charsRead - _charBufferIndex;
-
- // charBuffer is empty, let's read from the stream
- if (n == 0)
- {
- _charsRead = 0;
- _charBufferIndex = 0;
- _bytesRead = 0;
-
- // We loop here so that we read in enough bytes to yield at least 1 char.
- // We break out of the loop if the stream is blocked (EOF is reached).
- do
- {
- Debug.Assert(n == 0);
- _bytesRead = await _stream.ReadAsync(
- _byteBuffer,
- 0,
- _byteBufferSize);
- if (_bytesRead == 0) // EOF
- {
- _isBlocked = true;
- break;
- }
-
- // _isBlocked == whether we read fewer bytes than we asked for.
- _isBlocked = (_bytesRead < _byteBufferSize);
-
- Debug.Assert(n == 0);
-
- _charBufferIndex = 0;
- n = _decoder.GetChars(
- _byteBuffer,
- 0,
- _bytesRead,
- _charBuffer,
- 0);
-
- Debug.Assert(n > 0);
-
- _charsRead += n; // Number of chars in StreamReader's buffer.
- }
- while (n == 0);
-
- if (n == 0)
- {
- break; // We're at EOF
- }
- }
-
- // Got more chars in charBuffer than the user requested
- if (n > count)
- {
- n = count;
- }
-
- Buffer.BlockCopy(
- _charBuffer,
- _charBufferIndex * 2,
- buffer,
- (index + charsRead) * 2,
- n * 2);
-
- _charBufferIndex += n;
-
- charsRead += n;
- count -= n;
-
- // This function shouldn't block for an indefinite amount of time,
- // or reading from a network stream won't work right. If we got
- // fewer bytes than we requested, then we want to break right here.
- if (_isBlocked)
- {
- break;
- }
- }
-
- return charsRead;
- }
-
- private int ReadIntoBuffer()
- {
- _charsRead = 0;
- _charBufferIndex = 0;
- _bytesRead = 0;
-
- do
- {
- _bytesRead = _stream.Read(_byteBuffer, 0, _byteBufferSize);
- if (_bytesRead == 0) // We're at EOF
- {
- return _charsRead;
- }
-
- _isBlocked = (_bytesRead < _byteBufferSize);
- _charsRead += _decoder.GetChars(
- _byteBuffer,
- 0,
- _bytesRead,
- _charBuffer,
- _charsRead);
- }
- while (_charsRead == 0);
-
- return _charsRead;
- }
-
- private async Task ReadIntoBufferAsync()
- {
- _charsRead = 0;
- _charBufferIndex = 0;
- _bytesRead = 0;
-
- do
- {
-
- _bytesRead = await _stream.ReadAsync(
- _byteBuffer,
- 0,
- _byteBufferSize).ConfigureAwait(false);
- if (_bytesRead == 0)
- {
- // We're at EOF
- return _charsRead;
- }
-
- // _isBlocked == whether we read fewer bytes than we asked for.
- _isBlocked = (_bytesRead < _byteBufferSize);
-
- _charsRead += _decoder.GetChars(
- _byteBuffer,
- 0,
- _bytesRead,
- _charBuffer,
- _charsRead);
- }
- while (_charsRead == 0);
-
- return _charsRead;
- }
- }
-}
\ No newline at end of file
diff --git a/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpRequestStreamReaderFactory.cs b/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpRequestStreamReaderFactory.cs
index 0e2cc41fe3..d006ebcb54 100644
--- a/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpRequestStreamReaderFactory.cs
+++ b/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpRequestStreamReaderFactory.cs
@@ -5,7 +5,7 @@ using System;
using System.Buffers;
using System.IO;
using System.Text;
-using Microsoft.AspNetCore.Mvc.Infrastructure;
+using Microsoft.AspNetCore.WebUtilities;
namespace Microsoft.AspNetCore.Mvc.Internal
{
diff --git a/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpResponseStreamWriterFactory.cs b/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpResponseStreamWriterFactory.cs
index 4ea586adf5..4d66f3af3a 100644
--- a/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpResponseStreamWriterFactory.cs
+++ b/src/Microsoft.AspNetCore.Mvc.Core/Internal/MemoryPoolHttpResponseStreamWriterFactory.cs
@@ -5,6 +5,7 @@ using System;
using System.Buffers;
using System.IO;
using System.Text;
+using Microsoft.AspNetCore.WebUtilities;
namespace Microsoft.AspNetCore.Mvc.Internal
{
diff --git a/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx b/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx
index cd6bcce648..7a5bf847d5 100644
--- a/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx
+++ b/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx
@@ -313,12 +313,6 @@
The supplied URL is not local. A URL with an absolute path is considered local if it does not have a host/authority part. URLs using virtual paths ('~/') are also local.
-
- The stream must support reading.
-
-
- The stream must support writing.
-
The argument '{0}' is invalid. Empty or null formats are not supported.
diff --git a/src/Microsoft.AspNetCore.Mvc.ViewFeatures/ViewComponentResult.cs b/src/Microsoft.AspNetCore.Mvc.ViewFeatures/ViewComponentResult.cs
index 3e29a5c8de..feb16b3b8f 100644
--- a/src/Microsoft.AspNetCore.Mvc.ViewFeatures/ViewComponentResult.cs
+++ b/src/Microsoft.AspNetCore.Mvc.ViewFeatures/ViewComponentResult.cs
@@ -12,6 +12,7 @@ using Microsoft.AspNetCore.Mvc.Rendering;
using Microsoft.AspNetCore.Mvc.ViewEngines;
using Microsoft.AspNetCore.Mvc.ViewFeatures;
using Microsoft.AspNetCore.Mvc.ViewFeatures.Internal;
+using Microsoft.AspNetCore.WebUtilities;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
diff --git a/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpResponseStreamWriterTest.cs b/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpResponseStreamWriterTest.cs
deleted file mode 100644
index c8b349d6f3..0000000000
--- a/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpResponseStreamWriterTest.cs
+++ /dev/null
@@ -1,462 +0,0 @@
-// 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;
-using System.Buffers;
-using System.IO;
-using System.Text;
-using System.Threading;
-using System.Threading.Tasks;
-using Microsoft.AspNetCore.Testing;
-using Xunit;
-
-namespace Microsoft.AspNetCore.Mvc
-{
- public class HttpResponseStreamWriterTest
- {
- [Fact]
- public async Task DoesNotWriteBOM()
- {
- // Arrange
- var memoryStream = new MemoryStream();
- var encodingWithBOM = new UTF8Encoding(encoderShouldEmitUTF8Identifier: true);
- var writer = new HttpResponseStreamWriter(memoryStream, encodingWithBOM);
- var expectedData = new byte[] { 97, 98, 99, 100 }; // without BOM
-
- // Act
- using (writer)
- {
- await writer.WriteAsync("abcd");
- }
-
- // Assert
- Assert.Equal(expectedData, memoryStream.ToArray());
- }
-
-#if DNX451
- [Fact]
- public async Task DoesNotFlush_UnderlyingStream_OnClosingWriter()
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- await writer.WriteAsync("Hello");
- writer.Close();
-
- // Assert
- Assert.Equal(0, stream.FlushCallCount);
- Assert.Equal(0, stream.FlushAsyncCallCount);
- }
-#endif
-
- [Fact]
- public async Task DoesNotFlush_UnderlyingStream_OnDisposingWriter()
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- await writer.WriteAsync("Hello");
- writer.Dispose();
-
- // Assert
- Assert.Equal(0, stream.FlushCallCount);
- Assert.Equal(0, stream.FlushAsyncCallCount);
- }
-
-#if DNX451
- [Fact]
- public async Task DoesNotClose_UnderlyingStream_OnDisposingWriter()
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- await writer.WriteAsync("Hello");
- writer.Close();
-
- // Assert
- Assert.Equal(0, stream.CloseCallCount);
- }
-#endif
-
- [Fact]
- public async Task DoesNotDispose_UnderlyingStream_OnDisposingWriter()
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- await writer.WriteAsync("Hello world");
- writer.Dispose();
-
- // Assert
- Assert.Equal(0, stream.DisposeCallCount);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public async Task FlushesBuffer_OnClose(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
- await writer.WriteAsync(new string('a', byteLength));
-
- // Act
-#if DNX451
- writer.Close();
-#else
- writer.Dispose();
-#endif
-
- // Assert
- Assert.Equal(0, stream.FlushCallCount);
- Assert.Equal(0, stream.FlushAsyncCallCount);
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public async Task FlushesBuffer_OnDispose(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
- await writer.WriteAsync(new string('a', byteLength));
-
- // Act
- writer.Dispose();
-
- // Assert
- Assert.Equal(0, stream.FlushCallCount);
- Assert.Equal(0, stream.FlushAsyncCallCount);
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Fact]
- public void NoDataWritten_Flush_DoesNotFlushUnderlyingStream()
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- writer.Flush();
-
- // Assert
- Assert.Equal(0, stream.FlushCallCount);
- Assert.Equal(0, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public void FlushesBuffer_ButNotStream_OnFlush(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
- writer.Write(new string('a', byteLength));
-
- var expectedWriteCount = Math.Ceiling((double)byteLength / HttpResponseStreamWriter.DefaultBufferSize);
-
- // Act
- writer.Flush();
-
- // Assert
- Assert.Equal(0, stream.FlushCallCount);
- Assert.Equal(expectedWriteCount, stream.WriteCallCount);
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Fact]
- public async Task NoDataWritten_FlushAsync_DoesNotFlushUnderlyingStream()
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- await writer.FlushAsync();
-
- // Assert
- Assert.Equal(0, stream.FlushAsyncCallCount);
- Assert.Equal(0, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public async Task FlushesBuffer_ButNotStream_OnFlushAsync(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
- await writer.WriteAsync(new string('a', byteLength));
-
- var expectedWriteCount = Math.Ceiling((double)byteLength / HttpResponseStreamWriter.DefaultBufferSize);
-
- // Act
- await writer.FlushAsync();
-
- // Assert
- Assert.Equal(0, stream.FlushAsyncCallCount);
- Assert.Equal(expectedWriteCount, stream.WriteAsyncCallCount);
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public void WriteChar_WritesToStream(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- using (writer)
- {
- for (var i = 0; i < byteLength; i++)
- {
- writer.Write('a');
- }
- }
-
- // Assert
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public void WriteCharArray_WritesToStream(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- using (writer)
- {
- writer.Write((new string('a', byteLength)).ToCharArray());
- }
-
- // Assert
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public async Task WriteCharAsync_WritesToStream(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- using (writer)
- {
- for (var i = 0; i < byteLength; i++)
- {
- await writer.WriteAsync('a');
- }
- }
-
- // Assert
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Theory]
- [InlineData(1023)]
- [InlineData(1024)]
- [InlineData(1050)]
- [InlineData(2048)]
- public async Task WriteCharArrayAsync_WritesToStream(int byteLength)
- {
- // Arrange
- var stream = new TestMemoryStream();
- var writer = new HttpResponseStreamWriter(stream, Encoding.UTF8);
-
- // Act
- using (writer)
- {
- await writer.WriteAsync((new string('a', byteLength)).ToCharArray());
- }
-
- // Assert
- Assert.Equal(byteLength, stream.Length);
- }
-
- [Theory]
- [InlineData("你好世界", "utf-16")]
-#if !DNXCORE50
- // CoreCLR does not like shift_jis as an encoding.
- [InlineData("こんにちは世界", "shift_jis")]
-#endif
- [InlineData("హలో ప్రపంచ", "iso-8859-1")]
- [InlineData("வணக்கம் உலக", "utf-32")]
- public async Task WritesData_InExpectedEncoding(string data, string encodingName)
- {
- // Arrange
- var encoding = Encoding.GetEncoding(encodingName);
- var expectedBytes = encoding.GetBytes(data);
- var stream = new MemoryStream();
- var writer = new HttpResponseStreamWriter(stream, encoding);
-
- // Act
- using (writer)
- {
- await writer.WriteAsync(data);
- }
-
- // Assert
- Assert.Equal(expectedBytes, stream.ToArray());
- }
-
- [Theory]
- [InlineData('ん', 1023, "utf-8")]
- [InlineData('ん', 1024, "utf-8")]
- [InlineData('ん', 1050, "utf-8")]
- [InlineData('你', 1023, "utf-16")]
- [InlineData('你', 1024, "utf-16")]
- [InlineData('你', 1050, "utf-16")]
-#if !DNXCORE50
- // CoreCLR does not like shift_jis as an encoding.
- [InlineData('こ', 1023, "shift_jis")]
- [InlineData('こ', 1024, "shift_jis")]
- [InlineData('こ', 1050, "shift_jis")]
-#endif
- [InlineData('హ', 1023, "iso-8859-1")]
- [InlineData('హ', 1024, "iso-8859-1")]
- [InlineData('హ', 1050, "iso-8859-1")]
- [InlineData('வ', 1023, "utf-32")]
- [InlineData('வ', 1024, "utf-32")]
- [InlineData('வ', 1050, "utf-32")]
- public async Task WritesData_OfDifferentLength_InExpectedEncoding(
- char character,
- int charCount,
- string encodingName)
- {
- // Arrange
- var encoding = Encoding.GetEncoding(encodingName);
- string data = new string(character, charCount);
- var expectedBytes = encoding.GetBytes(data);
- var stream = new MemoryStream();
- var writer = new HttpResponseStreamWriter(stream, encoding);
-
- // Act
- using (writer)
- {
- await writer.WriteAsync(data);
- }
-
- // Assert
- Assert.Equal(expectedBytes, stream.ToArray());
- }
-
- // None of the code in HttpResponseStreamWriter differs significantly when using pooled buffers.
- //
- // This test effectively verifies that things are correctly constructed and disposed. Pooled buffers
- // throw on the finalizer thread if not disposed, so that's why it's complicated.
- [Fact]
- public void HttpResponseStreamWriter_UsingPooledBuffers()
- {
- // Arrange
- var encoding = Encoding.UTF8;
- var stream = new MemoryStream();
-
- var expectedBytes = encoding.GetBytes("Hello, World!");
-
- using (var writer = new HttpResponseStreamWriter(
- stream,
- encoding,
- 1024,
- ArrayPool.Shared,
- ArrayPool.Shared))
- {
- // Act
- writer.Write("Hello, World!");
- }
-
- // Assert
- Assert.Equal(expectedBytes, stream.ToArray());
- }
-
- private class TestMemoryStream : MemoryStream
- {
- public int FlushCallCount { get; private set; }
-
- public int FlushAsyncCallCount { get; private set; }
-
- public int CloseCallCount { get; private set; }
-
- public int DisposeCallCount { get; private set; }
-
- public int WriteCallCount { get; private set; }
-
- public int WriteAsyncCallCount { get; private set; }
-
- public override void Flush()
- {
- FlushCallCount++;
- base.Flush();
- }
-
- public override Task FlushAsync(CancellationToken cancellationToken)
- {
- FlushAsyncCallCount++;
- return base.FlushAsync(cancellationToken);
- }
-
- public override void Write(byte[] buffer, int offset, int count)
- {
- WriteCallCount++;
- base.Write(buffer, offset, count);
- }
-
- public override Task WriteAsync(byte[] buffer, int offset, int count, CancellationToken cancellationToken)
- {
- WriteAsyncCallCount++;
- return base.WriteAsync(buffer, offset, count, cancellationToken);
- }
-
-#if DNX451
- public override void Close()
- {
- CloseCallCount++;
- base.Close();
- }
-#endif
-
- protected override void Dispose(bool disposing)
- {
- DisposeCallCount++;
- base.Dispose(disposing);
- }
- }
- }
-}
diff --git a/test/Microsoft.AspNetCore.Mvc.Core.Test/Infrastructure/HttpResponseStreamReaderTest.cs b/test/Microsoft.AspNetCore.Mvc.Core.Test/Infrastructure/HttpResponseStreamReaderTest.cs
deleted file mode 100644
index 4a3f1b4440..0000000000
--- a/test/Microsoft.AspNetCore.Mvc.Core.Test/Infrastructure/HttpResponseStreamReaderTest.cs
+++ /dev/null
@@ -1,226 +0,0 @@
-// 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;
-using System.Collections.Generic;
-using System.IO;
-using System.Text;
-using System.Threading.Tasks;
-using Xunit;
-
-namespace Microsoft.AspNetCore.Mvc.Infrastructure
-{
- public class HttpResponseStreamReaderTest
- {
- private static readonly char[] CharData = new char[]
- {
- char.MinValue,
- char.MaxValue,
- '\t',
- ' ',
- '$',
- '@',
- '#',
- '\0',
- '\v',
- '\'',
- '\u3190',
- '\uC3A0',
- 'A',
- '5',
- '\r',
- '\uFE70',
- '-',
- ';',
- '\r',
- '\n',
- 'T',
- '3',
- '\n',
- 'K',
- '\u00E6',
- };
-
- [Fact]
- public static async Task ReadToEndAsync()
- {
- // Arrange
- var reader = new HttpRequestStreamReader(GetLargeStream(), Encoding.UTF8);
-
- var result = await reader.ReadToEndAsync();
-
- Assert.Equal(5000, result.Length);
- }
-
- [Fact]
- public static void TestRead()
- {
- // Arrange
- var reader = CreateReader();
-
- // Act & Assert
- for (var i = 0; i < CharData.Length; i++)
- {
- var tmp = reader.Read();
- Assert.Equal((int)CharData[i], tmp);
- }
- }
-
- [Fact]
- public static void TestPeek()
- {
- // Arrange
- var reader = CreateReader();
-
- // Act & Assert
- for (var i = 0; i < CharData.Length; i++)
- {
- var peek = reader.Peek();
- Assert.Equal((int)CharData[i], peek);
-
- reader.Read();
- }
- }
-
- [Fact]
- public static void EmptyStream()
- {
- // Arrange
- var reader = new HttpRequestStreamReader(new MemoryStream(), Encoding.UTF8);
- var buffer = new char[10];
-
- // Act
- var read = reader.Read(buffer, 0, 1);
-
- // Assert
- Assert.Equal(0, read);
- }
-
- [Fact]
- public static void Read_ReadAllCharactersAtOnce()
- {
- // Arrange
- var reader = CreateReader();
- var chars = new char[CharData.Length];
-
- // Act
- var read = reader.Read(chars, 0, chars.Length);
-
- // Assert
- Assert.Equal(chars.Length, read);
- for (var i = 0; i < CharData.Length; i++)
- {
- Assert.Equal(CharData[i], chars[i]);
- }
- }
-
- [Fact]
- public static async Task Read_ReadInTwoChunks()
- {
- // Arrange
- var reader = CreateReader();
- var chars = new char[CharData.Length];
-
- // Act
- var read = await reader.ReadAsync(chars, 4, 3);
-
- // Assert
- Assert.Equal(read, 3);
- for (var i = 0; i < 3; i++)
- {
- Assert.Equal(CharData[i], chars[i + 4]);
- }
- }
-
- [Fact]
- public static void ReadLine_ReadMultipleLines()
- {
- // Arrange
- var reader = CreateReader();
- var valueString = new string(CharData);
-
- // Act & Assert
- var data = reader.ReadLine();
- Assert.Equal(valueString.Substring(0, valueString.IndexOf('\r')), data);
-
- data = reader.ReadLine();
- Assert.Equal(valueString.Substring(valueString.IndexOf('\r') + 1, 3), data);
-
- data = reader.ReadLine();
- Assert.Equal(valueString.Substring(valueString.IndexOf('\n') + 1, 2), data);
-
- data = reader.ReadLine();
- Assert.Equal((valueString.Substring(valueString.LastIndexOf('\n') + 1)), data);
- }
-
- [Fact]
- public static void ReadLine_ReadWithNoNewlines()
- {
- // Arrange
- var reader = CreateReader();
- var valueString = new string(CharData);
- var temp = new char[10];
-
- // Act
- reader.Read(temp, 0, 1);
- var data = reader.ReadLine();
-
- // Assert
- Assert.Equal(valueString.Substring(1, valueString.IndexOf('\r') - 1), data);
- }
-
- [Fact]
- public static async Task ReadLineAsync_MultipleContinuousLines()
- {
- // Arrange
- var stream = new MemoryStream();
- var writer = new StreamWriter(stream);
- writer.Write("\n\n\r\r\n");
- writer.Flush();
- stream.Position = 0;
-
- var reader = new HttpRequestStreamReader(stream, Encoding.UTF8);
-
- // Act & Assert
- for (var i = 0; i < 4; i++)
- {
- var data = await reader.ReadLineAsync();
- Assert.Equal(string.Empty, data);
- }
-
- var eol = await reader.ReadLineAsync();
- Assert.Null(eol);
- }
-
- private static HttpRequestStreamReader CreateReader()
- {
- var stream = new MemoryStream();
- var writer = new StreamWriter(stream);
- writer.Write(CharData);
- writer.Flush();
- stream.Position = 0;
-
- return new HttpRequestStreamReader(stream, Encoding.UTF8);
- }
-
- private static MemoryStream GetSmallStream()
- {
- var testData = new byte[] { 72, 69, 76, 76, 79 };
- return new MemoryStream(testData);
- }
-
- private static MemoryStream GetLargeStream()
- {
- var testData = new byte[] { 72, 69, 76, 76, 79 };
- // System.Collections.Generic.
-
- var data = new List();
- for (var i = 0; i < 1000; i++)
- {
- data.AddRange(testData);
- }
-
- return new MemoryStream(data.ToArray());
- }
- }
-}
diff --git a/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpRequestStreamReaderFactory.cs b/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpRequestStreamReaderFactory.cs
index 2f69699c17..cd4d765ea1 100644
--- a/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpRequestStreamReaderFactory.cs
+++ b/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpRequestStreamReaderFactory.cs
@@ -3,8 +3,8 @@
using System.IO;
using System.Text;
-using Microsoft.AspNetCore.Mvc.Infrastructure;
using Microsoft.AspNetCore.Mvc.Internal;
+using Microsoft.AspNetCore.WebUtilities;
namespace Microsoft.AspNetCore.Mvc
{
diff --git a/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpResponseStreamWriterFactory.cs b/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpResponseStreamWriterFactory.cs
index 3e94372062..3b48544ff9 100644
--- a/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpResponseStreamWriterFactory.cs
+++ b/test/Microsoft.AspNetCore.Mvc.TestCommon/TestHttpResponseStreamWriterFactory.cs
@@ -4,6 +4,7 @@
using System.IO;
using System.Text;
using Microsoft.AspNetCore.Mvc.Internal;
+using Microsoft.AspNetCore.WebUtilities;
namespace Microsoft.AspNetCore.Mvc
{
diff --git a/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewFeatures/ViewExecutorTest.cs b/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewFeatures/ViewExecutorTest.cs
index 63bdf73e63..2f9651dd75 100644
--- a/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewFeatures/ViewExecutorTest.cs
+++ b/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewFeatures/ViewExecutorTest.cs
@@ -16,6 +16,7 @@ using Microsoft.AspNetCore.Mvc.Rendering;
using Microsoft.AspNetCore.Mvc.TestCommon;
using Microsoft.AspNetCore.Mvc.ViewEngines;
using Microsoft.AspNetCore.Routing;
+using Microsoft.AspNetCore.WebUtilities;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Net.Http.Headers;
using Moq;
@@ -338,7 +339,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures
// Assert
stream.Verify(s => s.FlushAsync(It.IsAny()), Times.Never());
stream.Verify(
- s => s.WriteAsync(It.IsAny(), It.IsAny(), It.IsAny(), It.IsAny()),
+ s => s.WriteAsync(It.IsAny(), It.IsAny(), It.IsAny(), It.IsAny()),
Times.Exactly((int)expectedWriteCallCount));
stream.Verify(s => s.Write(It.IsAny(), It.IsAny(), It.IsAny()), Times.Never());
}
diff --git a/test/Microsoft.AspNetCore.Mvc.WebApiCompatShimTest/TestHttpResponseStreamWriterFactory.cs b/test/Microsoft.AspNetCore.Mvc.WebApiCompatShimTest/TestHttpResponseStreamWriterFactory.cs
index 38ef3c702c..3b48544ff9 100644
--- a/test/Microsoft.AspNetCore.Mvc.WebApiCompatShimTest/TestHttpResponseStreamWriterFactory.cs
+++ b/test/Microsoft.AspNetCore.Mvc.WebApiCompatShimTest/TestHttpResponseStreamWriterFactory.cs
@@ -3,8 +3,8 @@
using System.IO;
using System.Text;
-using Microsoft.AspNetCore.Mvc.Infrastructure;
using Microsoft.AspNetCore.Mvc.Internal;
+using Microsoft.AspNetCore.WebUtilities;
namespace Microsoft.AspNetCore.Mvc
{