mirror of
https://github.com/VSadov/Satori.git
synced 2025-06-09 17:44:48 +09:00
Add MediaType to BinaryData (#89605)
* Add BinaryData.ContentType * PR fb * Fix ctor formatting * Add null validation for stream overloads * Use Theory for tests * More test updates * couple more test cases for defaulting application/json * more test clean up --------- Co-authored-by: Alexander Radchenko <radchenkosasha@gmail.com>
This commit is contained in:
parent
4448e41d11
commit
99503f1cff
3 changed files with 314 additions and 23 deletions
|
@ -10,26 +10,35 @@ namespace System
|
|||
public partial class BinaryData
|
||||
{
|
||||
public BinaryData(byte[] data) { }
|
||||
public BinaryData(byte[] data, string? mediaType) { }
|
||||
[System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute("JSON serialization and deserialization might require types that cannot be statically analyzed and might need runtime code generation.")]
|
||||
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute("JSON serialization and deserialization might require types that cannot be statically analyzed.")]
|
||||
public BinaryData(object? jsonSerializable, System.Text.Json.JsonSerializerOptions? options = null, System.Type? type = null) { }
|
||||
public BinaryData(object? jsonSerializable, System.Text.Json.Serialization.JsonSerializerContext context, System.Type? type = null) { }
|
||||
public BinaryData(System.ReadOnlyMemory<byte> data) { }
|
||||
public BinaryData(System.ReadOnlyMemory<byte> data, string? mediaType) { }
|
||||
public BinaryData(string data) { }
|
||||
public BinaryData(string data, string? mediaType) { }
|
||||
public static System.BinaryData Empty { get { throw null; } }
|
||||
public bool IsEmpty { get { throw null; } }
|
||||
public int Length { get { throw null; } }
|
||||
public string? MediaType { get { throw null; } }
|
||||
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never)]
|
||||
public override bool Equals([System.Diagnostics.CodeAnalysis.NotNullWhenAttribute(true)] object? obj) { throw null; }
|
||||
public static System.BinaryData FromBytes(byte[] data) { throw null; }
|
||||
public static System.BinaryData FromBytes(byte[] data, string? mediaType) { throw null; }
|
||||
public static System.BinaryData FromBytes(System.ReadOnlyMemory<byte> data) { throw null; }
|
||||
public static System.BinaryData FromBytes(System.ReadOnlyMemory<byte> data, string? mediaType) { throw null; }
|
||||
[System.Diagnostics.CodeAnalysis.RequiresDynamicCodeAttribute("JSON serialization and deserialization might require types that cannot be statically analyzed and might need runtime code generation.")]
|
||||
[System.Diagnostics.CodeAnalysis.RequiresUnreferencedCodeAttribute("JSON serialization and deserialization might require types that cannot be statically analyzed.")]
|
||||
public static System.BinaryData FromObjectAsJson<T>(T jsonSerializable, System.Text.Json.JsonSerializerOptions? options = null) { throw null; }
|
||||
public static System.BinaryData FromObjectAsJson<T>(T jsonSerializable, System.Text.Json.Serialization.Metadata.JsonTypeInfo<T> jsonTypeInfo) { throw null; }
|
||||
public static System.BinaryData FromStream(System.IO.Stream stream) { throw null; }
|
||||
public static System.BinaryData FromStream(System.IO.Stream stream, string? mediaType) { throw null; }
|
||||
public static System.Threading.Tasks.Task<System.BinaryData> FromStreamAsync(System.IO.Stream stream, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) { throw null; }
|
||||
public static System.Threading.Tasks.Task<System.BinaryData> FromStreamAsync(System.IO.Stream stream, string? mediaType, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) { throw null; }
|
||||
public static System.BinaryData FromString(string data) { throw null; }
|
||||
public static System.BinaryData FromString(string data, string? mediaType) { throw null; }
|
||||
[System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never)]
|
||||
public override int GetHashCode() { throw null; }
|
||||
public static implicit operator System.ReadOnlyMemory<byte> (System.BinaryData? data) { throw null; }
|
||||
|
@ -42,6 +51,7 @@ namespace System
|
|||
public T? ToObjectFromJson<T>(System.Text.Json.Serialization.Metadata.JsonTypeInfo<T> jsonTypeInfo) { throw null; }
|
||||
public System.IO.Stream ToStream() { throw null; }
|
||||
public override string ToString() { throw null; }
|
||||
public System.BinaryData WithMediaType(string? mediaType) { throw null; }
|
||||
}
|
||||
}
|
||||
namespace System.Text.Json.Serialization
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
using System.ComponentModel;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using System.IO;
|
||||
using System.Net.Mime;
|
||||
using System.Text;
|
||||
using System.Text.Json;
|
||||
using System.Text.Json.Serialization;
|
||||
|
@ -21,6 +22,7 @@ namespace System
|
|||
{
|
||||
private const string JsonSerializerRequiresDynamicCode = "JSON serialization and deserialization might require types that cannot be statically analyzed and might need runtime code generation.";
|
||||
private const string JsonSerializerRequiresUnreferencedCode = "JSON serialization and deserialization might require types that cannot be statically analyzed.";
|
||||
private const string MediaTypeApplicationJson = "application/json";
|
||||
|
||||
/// <summary>
|
||||
/// The backing store for the <see cref="BinaryData"/> instance.
|
||||
|
@ -44,6 +46,12 @@ namespace System
|
|||
/// <returns><see langword="true" /> if the data is empty (that is, its <see cref="Length" /> is 0); otherwise, <see langword="false" />.</returns>
|
||||
public bool IsEmpty => _bytes.IsEmpty;
|
||||
|
||||
/// <summary>
|
||||
/// Gets the MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.
|
||||
/// </summary>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public string? MediaType { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the
|
||||
/// provided byte array.
|
||||
|
@ -54,38 +62,52 @@ namespace System
|
|||
_bytes = data ?? throw new ArgumentNullException(nameof(data));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the provided byte array
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <param name="data">The array to wrap.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public BinaryData(byte[] data, string? mediaType) : this(data)
|
||||
{
|
||||
MediaType = mediaType;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by serializing the provided object to JSON
|
||||
/// using <see cref="JsonSerializer"/>.
|
||||
/// and sets <see cref="MediaType"/> to "application/json".
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializable">The object that will be serialized to JSON using
|
||||
/// <see cref="JsonSerializer"/>.</param>
|
||||
/// <param name="options">The options to use when serializing to JSON.</param>
|
||||
/// <param name="type">The type to use when serializing the data. If not specified, <see cref="object.GetType"/> will
|
||||
/// be used to determine the type.</param>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
[RequiresDynamicCode(JsonSerializerRequiresDynamicCode)]
|
||||
[RequiresUnreferencedCode(JsonSerializerRequiresUnreferencedCode)]
|
||||
public BinaryData(object? jsonSerializable, JsonSerializerOptions? options = default, Type? type = default)
|
||||
public BinaryData(object? jsonSerializable, JsonSerializerOptions? options = default, Type? type = default) : this(
|
||||
JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, type ?? jsonSerializable?.GetType() ?? typeof(object), options),
|
||||
MediaTypeApplicationJson)
|
||||
{
|
||||
type ??= jsonSerializable?.GetType() ?? typeof(object);
|
||||
|
||||
_bytes = JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, type, options);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by serializing the provided object to JSON
|
||||
/// using <see cref="JsonSerializer"/>.
|
||||
/// using <see cref="JsonSerializer"/>
|
||||
/// and sets <see cref="MediaType"/> to "application/json".
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializable">The object that will be serialized to JSON using
|
||||
/// <see cref="JsonSerializer"/>.</param>
|
||||
/// <param name="context">The <see cref="JsonSerializerContext" /> to use when serializing to JSON.</param>
|
||||
/// <param name="type">The type to use when serializing the data. If not specified, <see cref="object.GetType"/> will
|
||||
/// be used to determine the type.</param>
|
||||
public BinaryData(object? jsonSerializable, JsonSerializerContext context, Type? type = default)
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public BinaryData(object? jsonSerializable, JsonSerializerContext context, Type? type = default) : this(
|
||||
JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, type ?? jsonSerializable?.GetType() ?? typeof(object), context),
|
||||
MediaTypeApplicationJson)
|
||||
{
|
||||
type ??= jsonSerializable?.GetType() ?? typeof(object);
|
||||
|
||||
_bytes = JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, type, context);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -98,6 +120,18 @@ namespace System
|
|||
_bytes = data;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the provided bytes
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <param name="data">Byte data to wrap.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public BinaryData(ReadOnlyMemory<byte> data, string? mediaType) : this(data)
|
||||
{
|
||||
MediaType = mediaType;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from a string by converting
|
||||
/// the string to bytes using the UTF-8 encoding.
|
||||
|
@ -113,6 +147,19 @@ namespace System
|
|||
_bytes = Encoding.UTF8.GetBytes(data);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from a string by converting
|
||||
/// the string to bytes using the UTF-8 encoding
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <param name="data">The string data.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public BinaryData(string data, string? mediaType) : this(data)
|
||||
{
|
||||
MediaType = mediaType;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the provided
|
||||
/// <see cref="ReadOnlyMemory{Byte}"/>.
|
||||
|
@ -121,6 +168,18 @@ namespace System
|
|||
/// <returns>A wrapper over <paramref name="data"/>.</returns>
|
||||
public static BinaryData FromBytes(ReadOnlyMemory<byte> data) => new BinaryData(data);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the provided
|
||||
/// <see cref="ReadOnlyMemory{Byte}"/>
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <param name="data">Byte data to wrap.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <returns>A wrapper over <paramref name="data"/>.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public static BinaryData FromBytes(ReadOnlyMemory<byte> data, string? mediaType)
|
||||
=> new BinaryData(data, mediaType);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the provided
|
||||
/// byte array.
|
||||
|
@ -129,6 +188,17 @@ namespace System
|
|||
/// <returns>A wrapper over <paramref name="data"/>.</returns>
|
||||
public static BinaryData FromBytes(byte[] data) => new BinaryData(data);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the provided byte array
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <param name="data">The array to wrap.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <returns>A wrapper over <paramref name="data"/>.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public static BinaryData FromBytes(byte[] data, string? mediaType)
|
||||
=> new BinaryData(data, mediaType);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from a string by converting
|
||||
/// the string to bytes using the UTF-8 encoding.
|
||||
|
@ -137,6 +207,18 @@ namespace System
|
|||
/// <returns>A value representing the UTF-8 encoding of <paramref name="data"/>.</returns>
|
||||
public static BinaryData FromString(string data) => new BinaryData(data);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from a string by converting
|
||||
/// the string to bytes using the UTF-8 encoding
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <param name="data">The string data.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Text.Plain"/>.</param>
|
||||
/// <returns>A value representing the UTF-8 encoding of <paramref name="data"/>.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public static BinaryData FromString(string data, string? mediaType)
|
||||
=> new BinaryData(data, mediaType);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from the specified stream.
|
||||
/// The stream is not disposed by this method.
|
||||
|
@ -153,6 +235,25 @@ namespace System
|
|||
return FromStreamAsync(stream, async: false).GetAwaiter().GetResult();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from the specified stream
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// The stream is not disposed by this method.
|
||||
/// </summary>
|
||||
/// <param name="stream">Stream containing the data.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <returns>A value representing all of the data remaining in <paramref name="stream"/>.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public static BinaryData FromStream(Stream stream, string? mediaType)
|
||||
{
|
||||
if (stream is null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(stream));
|
||||
}
|
||||
|
||||
return FromStreamAsync(stream, async: false, mediaType).GetAwaiter().GetResult();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from the specified stream.
|
||||
/// The stream is not disposed by this method.
|
||||
|
@ -167,10 +268,32 @@ namespace System
|
|||
throw new ArgumentNullException(nameof(stream));
|
||||
}
|
||||
|
||||
return FromStreamAsync(stream, async: true, cancellationToken);
|
||||
return FromStreamAsync(stream, async: true, cancellationToken: cancellationToken);
|
||||
}
|
||||
|
||||
private static async Task<BinaryData> FromStreamAsync(Stream stream, bool async, CancellationToken cancellationToken = default)
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance from the specified stream
|
||||
/// and sets <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// The stream is not disposed by this method.
|
||||
/// </summary>
|
||||
/// <param name="stream">Stream containing the data.</param>
|
||||
/// <param name="mediaType">MIME type of this data, e.g. <see cref="MediaTypeNames.Application.Octet"/>.</param>
|
||||
/// <param name="cancellationToken">A token that may be used to cancel the operation.</param>
|
||||
/// <returns>A value representing all of the data remaining in <paramref name="stream"/>.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public static Task<BinaryData> FromStreamAsync(Stream stream, string? mediaType,
|
||||
CancellationToken cancellationToken = default)
|
||||
{
|
||||
if (stream is null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(stream));
|
||||
}
|
||||
|
||||
return FromStreamAsync(stream, async: true, mediaType, cancellationToken);
|
||||
}
|
||||
|
||||
private static async Task<BinaryData> FromStreamAsync(Stream stream, bool async,
|
||||
string? mediaType = default, CancellationToken cancellationToken = default)
|
||||
{
|
||||
const int CopyToBufferSize = 81920; // the default used by Stream.CopyToAsync
|
||||
int bufferSize = CopyToBufferSize;
|
||||
|
@ -203,36 +326,46 @@ namespace System
|
|||
{
|
||||
stream.CopyTo(memoryStream, bufferSize);
|
||||
}
|
||||
return new BinaryData(memoryStream.GetBuffer().AsMemory(0, (int)memoryStream.Position));
|
||||
return new BinaryData(memoryStream.GetBuffer().AsMemory(0, (int)memoryStream.Position), mediaType);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by serializing the provided object using
|
||||
/// the <see cref="JsonSerializer"/>.
|
||||
/// the <see cref="JsonSerializer"/>
|
||||
/// and sets <see cref="MediaType"/> to "application/json".
|
||||
/// </summary>
|
||||
/// <typeparam name="T">The type to use when serializing the data.</typeparam>
|
||||
/// <param name="jsonSerializable">The data to use.</param>
|
||||
/// <param name="options">The options to use when serializing to JSON.</param>
|
||||
/// <returns>A value representing the UTF-8 encoding of the JSON representation of <paramref name="jsonSerializable" />.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
[RequiresDynamicCode(JsonSerializerRequiresDynamicCode)]
|
||||
[RequiresUnreferencedCode(JsonSerializerRequiresUnreferencedCode)]
|
||||
public static BinaryData FromObjectAsJson<T>(T jsonSerializable, JsonSerializerOptions? options = default)
|
||||
{
|
||||
byte[] buffer = JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, typeof(T), options);
|
||||
return new BinaryData(buffer);
|
||||
}
|
||||
=> new BinaryData(JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, options), MediaTypeApplicationJson);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by serializing the provided object using
|
||||
/// the <see cref="JsonSerializer"/>.
|
||||
/// the <see cref="JsonSerializer"/>
|
||||
/// and sets <see cref="MediaType"/> to "application/json".
|
||||
/// </summary>
|
||||
/// <typeparam name="T">The type to use when serializing the data.</typeparam>
|
||||
/// <param name="jsonSerializable">The data to use.</param>
|
||||
/// <param name="jsonTypeInfo">The <see cref="JsonTypeInfo"/> to use when serializing to JSON.</param>
|
||||
/// <returns>A value representing the UTF-8 encoding of the JSON representation of <paramref name="jsonSerializable" />.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public static BinaryData FromObjectAsJson<T>(T jsonSerializable, JsonTypeInfo<T> jsonTypeInfo)
|
||||
=> new BinaryData(JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, jsonTypeInfo));
|
||||
=> new BinaryData(JsonSerializer.SerializeToUtf8Bytes(jsonSerializable, jsonTypeInfo), MediaTypeApplicationJson);
|
||||
|
||||
/// <summary>
|
||||
/// Creates a <see cref="BinaryData"/> instance by wrapping the same data
|
||||
/// and changed <see cref="MediaType"/> to <see pref="mediaType"/> value.
|
||||
/// </summary>
|
||||
/// <returns>A wrapper over the same data with specified <see cref="MediaType"/>.</returns>
|
||||
/// <seealso cref="MediaTypeNames"/>
|
||||
public BinaryData WithMediaType(string? mediaType)
|
||||
=> new BinaryData(_bytes, mediaType);
|
||||
|
||||
/// <summary>
|
||||
/// Converts the value of this instance to a string using UTF-8.
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Net.Mime;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
using System.Text.Json;
|
||||
|
@ -16,6 +17,7 @@ namespace System.Tests
|
|||
{
|
||||
public partial class BinaryDataTests
|
||||
{
|
||||
|
||||
[Fact]
|
||||
public void CanCreateBinaryDataFromBytes()
|
||||
{
|
||||
|
@ -23,6 +25,9 @@ namespace System.Tests
|
|||
BinaryData data = BinaryData.FromBytes(payload);
|
||||
Assert.Equal(payload, data.ToArray());
|
||||
|
||||
data = new BinaryData(payload);
|
||||
Assert.Equal(payload, data.ToArray());
|
||||
|
||||
MemoryMarshal.TryGetArray<byte>(payload, out ArraySegment<byte> array);
|
||||
Assert.Same(payload, array.Array);
|
||||
|
||||
|
@ -44,15 +49,95 @@ namespace System.Tests
|
|||
Assert.True(emptySpan.IsEmpty);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(null)]
|
||||
[InlineData("")]
|
||||
[InlineData(MediaTypeNames.Application.Soap)]
|
||||
public void CanCreateBinaryDataFromBytesWithMediaType(string? mediaType)
|
||||
{
|
||||
byte[] payload = "some data"u8.ToArray();
|
||||
BinaryData data = new BinaryData(payload, mediaType);
|
||||
Assert.Equal(payload, data.ToArray());
|
||||
Assert.Equal(mediaType, data.MediaType);
|
||||
MemoryMarshal.TryGetArray(data.ToMemory(), out ArraySegment<byte> array);
|
||||
Assert.Same(payload, array.Array);
|
||||
|
||||
data = BinaryData.FromBytes(payload, mediaType);
|
||||
Assert.Equal(payload, data.ToArray());
|
||||
Assert.Equal(mediaType, data.MediaType);
|
||||
MemoryMarshal.TryGetArray(data.ToMemory(), out array);
|
||||
Assert.Same(payload, array.Array);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(null)]
|
||||
[InlineData("")]
|
||||
[InlineData(MediaTypeNames.Application.Soap)]
|
||||
public void CanCreateBinaryDataFromReadOnlyMemoryWithMediaType(string? mediaType)
|
||||
{
|
||||
byte[] payload = "some data"u8.ToArray();
|
||||
ReadOnlyMemory<byte> rom = payload;
|
||||
BinaryData data = new BinaryData(rom, mediaType);
|
||||
Assert.Equal(payload, data.ToArray());
|
||||
Assert.Equal(mediaType, data.MediaType);
|
||||
MemoryMarshal.TryGetArray(data.ToMemory(), out ArraySegment<byte> array);
|
||||
Assert.Same(payload, array.Array);
|
||||
|
||||
data = BinaryData.FromBytes(rom, mediaType);
|
||||
Assert.Equal(payload, data.ToArray());
|
||||
Assert.Equal(mediaType, data.MediaType);
|
||||
MemoryMarshal.TryGetArray(data.ToMemory(), out array);
|
||||
Assert.Same(payload, array.Array);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void CanCreateBinaryDataFromString()
|
||||
{
|
||||
string payload = "some data";
|
||||
BinaryData data = new BinaryData(payload);
|
||||
Assert.Equal(payload, data.ToString());
|
||||
Assert.Null(data.MediaType);
|
||||
|
||||
data = BinaryData.FromString(payload);
|
||||
Assert.Equal(payload, data.ToString());
|
||||
Assert.Null(data.MediaType);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(null)]
|
||||
[InlineData("")]
|
||||
[InlineData(MediaTypeNames.Application.Soap)]
|
||||
public void CanCreateBinaryDataFromStringWithMediaType(string? mediaType)
|
||||
{
|
||||
string payload = "some data";
|
||||
|
||||
BinaryData data = new BinaryData(payload, mediaType);
|
||||
Assert.Equal(payload, data.ToString());
|
||||
Assert.Same(mediaType, data.MediaType);
|
||||
|
||||
data = BinaryData.FromString(payload, mediaType);
|
||||
Assert.Equal(payload, data.ToString());
|
||||
Assert.Same(mediaType, data.MediaType);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(null)]
|
||||
[InlineData("")]
|
||||
[InlineData(MediaTypeNames.Application.Soap)]
|
||||
public void CanConstructNewInstanceWithMediaType(string? mediaType)
|
||||
{
|
||||
byte[] payload = "some data"u8.ToArray();
|
||||
|
||||
BinaryData data = new BinaryData(payload, mediaType);
|
||||
|
||||
BinaryData withMedia = data.WithMediaType(MediaTypeNames.Application.Soap);
|
||||
Assert.Same(mediaType, data.MediaType); // shouldn't changed
|
||||
Assert.NotNull(withMedia);
|
||||
Assert.NotSame(data, withMedia); // should be new instance
|
||||
Assert.Same(MediaTypeNames.Application.Soap, withMedia.MediaType);
|
||||
|
||||
MemoryMarshal.TryGetArray(withMedia.ToMemory(), out ArraySegment<byte> array);
|
||||
Assert.Same(payload, array.Array);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
@ -143,6 +228,37 @@ namespace System.Tests
|
|||
Assert.NotEqual(buffer, data.ToMemory().ToArray());
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(null)]
|
||||
[InlineData("")]
|
||||
[InlineData(MediaTypeNames.Application.Soap)]
|
||||
public async Task CanCreateBinaryDataFromStreamWithMediaType(string? mediaType)
|
||||
{
|
||||
byte[] buffer = "some data"u8.ToArray();
|
||||
using MemoryStream stream = new MemoryStream(buffer, 0, buffer.Length, true, true);
|
||||
BinaryData data = BinaryData.FromStream(stream, mediaType);
|
||||
Assert.Equal(buffer, data.ToArray());
|
||||
Assert.Equal(mediaType, data.MediaType);
|
||||
|
||||
byte[] output = new byte[buffer.Length];
|
||||
var outputStream = data.ToStream();
|
||||
outputStream.Read(output, 0, (int) outputStream.Length);
|
||||
Assert.Equal(buffer, output);
|
||||
|
||||
stream.Position = 0;
|
||||
data = await BinaryData.FromStreamAsync(stream, mediaType);
|
||||
Assert.Equal(buffer, data.ToArray());
|
||||
Assert.Equal(mediaType, data.MediaType);
|
||||
|
||||
outputStream = data.ToStream();
|
||||
outputStream.Read(output, 0, (int)outputStream.Length);
|
||||
Assert.Equal(buffer, output);
|
||||
|
||||
//changing the backing buffer should not affect the BD instance
|
||||
buffer[3] = (byte)'z';
|
||||
Assert.NotEqual(buffer, data.ToMemory().ToArray());
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task CanCreateBinaryDataFromLongStream()
|
||||
{
|
||||
|
@ -338,6 +454,7 @@ namespace System.Tests
|
|||
Assert.Equal(payload.B, model.B);
|
||||
Assert.Equal(payload.C, model.C);
|
||||
Assert.Equal(payload.D, model.D);
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -346,23 +463,35 @@ namespace System.Tests
|
|||
{
|
||||
BinaryData data = new BinaryData(jsonSerializable: null);
|
||||
Assert.Null(data.ToObjectFromJson<object>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = new BinaryData(jsonSerializable: null, context: new TestModelJsonContext());
|
||||
Assert.Null(data.ToObjectFromJson<object>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = BinaryData.FromObjectAsJson<object>(null);
|
||||
Assert.Null(data.ToObjectFromJson<object>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = new BinaryData(jsonSerializable: null, type: typeof(TestModel));
|
||||
Assert.Null(data.ToObjectFromJson<TestModel>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = new BinaryData(jsonSerializable: null);
|
||||
Assert.Null(data.ToObjectFromJson<TestModel>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = new BinaryData(jsonSerializable: null, type: null);
|
||||
Assert.Null(data.ToObjectFromJson<TestModel>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = BinaryData.FromObjectAsJson<TestModel>(null);
|
||||
Assert.Null(data.ToObjectFromJson<TestModel>());
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
|
||||
data = BinaryData.FromObjectAsJson<TestModel>(null, TestModelJsonContext.Default.TestModel);
|
||||
Assert.Null(data.ToObjectFromJson<TestModel>(TestModelJsonContext.Default.TestModel));
|
||||
Assert.Equal("application/json", data.MediaType);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
@ -371,8 +500,14 @@ namespace System.Tests
|
|||
var ex = Assert.Throws<ArgumentNullException>(() => BinaryData.FromStream(null));
|
||||
Assert.Contains("stream", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => BinaryData.FromStream(null, null));
|
||||
Assert.Contains("stream", ex.Message);
|
||||
|
||||
ex = await Assert.ThrowsAsync<ArgumentNullException>(() => BinaryData.FromStreamAsync(null));
|
||||
Assert.Contains("stream", ex.Message);
|
||||
|
||||
ex = await Assert.ThrowsAsync<ArgumentNullException>(() => BinaryData.FromStreamAsync(null, null));
|
||||
Assert.Contains("stream", ex.Message);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
@ -382,8 +517,14 @@ namespace System.Tests
|
|||
var ex = Assert.Throws<ArgumentNullException>(() => new BinaryData(payload));
|
||||
Assert.Contains("data", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => new BinaryData(payload, null));
|
||||
Assert.Contains("data", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => BinaryData.FromString(payload));
|
||||
Assert.Contains("data", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => BinaryData.FromString(payload, null));
|
||||
Assert.Contains("data", ex.Message);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
@ -393,8 +534,14 @@ namespace System.Tests
|
|||
var ex = Assert.Throws<ArgumentNullException>(() => new BinaryData(payload));
|
||||
Assert.Contains("data", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => new BinaryData(payload, null));
|
||||
Assert.Contains("data", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => BinaryData.FromBytes(null));
|
||||
Assert.Contains("data", ex.Message);
|
||||
|
||||
ex = Assert.Throws<ArgumentNullException>(() => BinaryData.FromBytes(null, null));
|
||||
Assert.Contains("data", ex.Message);
|
||||
}
|
||||
|
||||
[ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsNotBuiltWithAggressiveTrimming))]
|
||||
|
@ -452,7 +599,7 @@ namespace System.Tests
|
|||
{
|
||||
a
|
||||
};
|
||||
// hashcodes of a and b should not match since instances are different.
|
||||
// hash codes of a and b should not match since instances are different.
|
||||
Assert.DoesNotContain(b, set);
|
||||
|
||||
BinaryData c = BinaryData.FromBytes("some data"u8.ToArray());
|
||||
|
@ -604,6 +751,7 @@ namespace System.Tests
|
|||
public void EmptyIsEmpty()
|
||||
{
|
||||
Assert.Equal(Array.Empty<byte>(), BinaryData.Empty.ToArray());
|
||||
Assert.Null(BinaryData.Empty.MediaType);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue