Fix discrepancies in unicode handling between ConsoleWriter and Console.Write(...)

This commit is contained in:
Tyrrrz
2021-04-21 03:16:18 +03:00
parent 28097afc1e
commit d676b5832e
3 changed files with 67 additions and 7 deletions

View File

@@ -17,7 +17,7 @@ namespace CliFx.Infrastructure
/// Initializes an instance of <see cref="ConsoleReader"/>.
/// </summary>
public ConsoleReader(IConsole console, Stream stream, Encoding encoding)
: base(stream, encoding, false)
: base(stream, encoding, false, 4096)
{
Console = console;
}
@@ -33,7 +33,11 @@ namespace CliFx.Infrastructure
public partial class ConsoleReader
{
internal static ConsoleReader Create(IConsole console, Stream? stream) =>
new(console, stream is not null ? Stream.Synchronized(stream) : Stream.Null);
internal static ConsoleReader Create(IConsole console, Stream? stream) => new(
console,
stream is not null
? Stream.Synchronized(stream)
: Stream.Null
);
}
}

View File

@@ -1,5 +1,6 @@
using System.IO;
using System.Text;
using CliFx.Utils;
namespace CliFx.Infrastructure
{
@@ -17,7 +18,7 @@ namespace CliFx.Infrastructure
/// Initializes an instance of <see cref="ConsoleWriter"/>.
/// </summary>
public ConsoleWriter(IConsole console, Stream stream, Encoding encoding)
: base(stream, encoding)
: base(stream, encoding, 256)
{
Console = console;
}
@@ -26,14 +27,18 @@ namespace CliFx.Infrastructure
/// Initializes an instance of <see cref="ConsoleWriter"/>.
/// </summary>
public ConsoleWriter(IConsole console, Stream stream)
: this(console, stream, System.Console.OutputEncoding)
: this(console, stream, System.Console.OutputEncoding.WithoutPreamble())
{
}
}
public partial class ConsoleWriter
{
internal static ConsoleWriter Create(IConsole console, Stream? stream) =>
new(console, stream is not null ? Stream.Synchronized(stream) : Stream.Null) {AutoFlush = true};
internal static ConsoleWriter Create(IConsole console, Stream? stream) => new(
console,
stream is not null
? Stream.Synchronized(stream)
: Stream.Null
) {AutoFlush = true};
}
}

View File

@@ -0,0 +1,51 @@
using System;
using System.Diagnostics.CodeAnalysis;
using System.Text;
namespace CliFx.Utils
{
// Adapted from:
// https://github.com/dotnet/runtime/blob/01b7e73cd378145264a7cb7a09365b41ed42b240/src/libraries/Common/src/System/Text/ConsoleEncoding.cs
internal class NoPreambleEncoding : Encoding
{
private readonly Encoding _underlyingEncoding;
public NoPreambleEncoding(Encoding underlyingEncoding) =>
_underlyingEncoding = underlyingEncoding;
public override byte[] GetPreamble() =>
Array.Empty<byte>();
[ExcludeFromCodeCoverage]
public override int GetByteCount(char[] chars, int index, int count) =>
_underlyingEncoding.GetByteCount(chars, index, count);
[ExcludeFromCodeCoverage]
public override int GetBytes(char[] chars, int charIndex, int charCount, byte[] bytes, int byteIndex) =>
_underlyingEncoding.GetBytes(chars, charIndex, charCount, bytes, byteIndex);
[ExcludeFromCodeCoverage]
public override int GetCharCount(byte[] bytes, int index, int count) =>
_underlyingEncoding.GetCharCount(bytes, index, count);
[ExcludeFromCodeCoverage]
public override int GetChars(byte[] bytes, int byteIndex, int byteCount, char[] chars, int charIndex) =>
_underlyingEncoding.GetChars(bytes, byteIndex, byteCount, chars, charIndex);
[ExcludeFromCodeCoverage]
public override int GetMaxByteCount(int charCount) =>
_underlyingEncoding.GetMaxByteCount(charCount);
[ExcludeFromCodeCoverage]
public override int GetMaxCharCount(int byteCount) =>
_underlyingEncoding.GetMaxCharCount(byteCount);
}
internal static class NoPreambleEncodingExtensions
{
public static Encoding WithoutPreamble(this Encoding encoding) =>
encoding.GetPreamble().Length > 0
? new NoPreambleEncoding(encoding)
: encoding;
}
}