Skip to content

Commit

Permalink
Merge branch 'release/0.68.0'
Browse files Browse the repository at this point in the history
  • Loading branch information
Jericho committed Nov 2, 2023
2 parents 2a986c6 + 07393e9 commit 10f5c75
Show file tree
Hide file tree
Showing 14 changed files with 176 additions and 75 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,8 @@ public override async Task<ResultCodes> RunTestsAsync()
var logger = base.LoggerFactory.CreateLogger<ZoomWebSocketClient>();
var eventProcessor = new Func<Event, CancellationToken, Task>(async (webhookEvent, cancellationToken) =>
{
if (!cancellationToken.IsCancellationRequested)
{
logger.LogInformation("Processing {eventType} event...", webhookEvent.EventType);
await Task.Delay(1, cancellationToken).ConfigureAwait(false); // This async call gets rid of "CS1998 This async method lacks 'await' operators and will run synchronously".
}
logger.LogInformation("Processing {eventType} event...", webhookEvent.EventType);
await Task.Delay(1, cancellationToken).ConfigureAwait(false); // This async call gets rid of "CS1998 This async method lacks 'await' operators and will run synchronously".
});

// Configure cancellation (this allows you to press CTRL+C or CTRL+Break to stop the websocket client)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,9 @@
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Logzio.DotNet.NLog" Version="1.0.16" />
<PackageReference Include="Logzio.DotNet.NLog" Version="1.1.0" />
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="7.0.0" />
<PackageReference Include="NLog.Extensions.Logging" Version="5.3.4" />
<PackageReference Include="NLog.Extensions.Logging" Version="5.3.5" />
</ItemGroup>

<ItemGroup>
Expand Down
69 changes: 63 additions & 6 deletions Source/ZoomNet.UnitTests/Extensions/InternalTests.cs
Original file line number Diff line number Diff line change
@@ -1,11 +1,15 @@
using Shouldly;
using System;
using System.ComponentModel;
using System.Net;
using System.Net.Http;
using System.Runtime.Serialization;
using System.Text.Json.Serialization;
using System.Threading;
using System.Threading.Tasks;
using Xunit;
using ZoomNet.Models;
using ZoomNet.Utilities;

namespace ZoomNet.UnitTests.Extensions
{
Expand All @@ -30,7 +34,7 @@ public async Task ThrowsExceptionWhenExpectedRecordsAreMissing()
var response = new MockFluentHttpResponse(message, null, CancellationToken.None);

// Act
await Should.ThrowAsync<ArgumentException>(() => response.AsPaginatedResponse<UserCallLog>("call_logs")).ConfigureAwait(false);
await Should.ThrowAsync<ArgumentException>(() => response.AsPaginatedResponse<UserCallLog>("call_logs")).ConfigureAwait(true);
}

[Fact]
Expand All @@ -49,7 +53,7 @@ public async Task DoesNotThrowExceptionWhenRecordsAreMissingAndTotalRecordsIsZer
var response = new MockFluentHttpResponse(message, null, CancellationToken.None);

// Act
var paginatedResponse = await response.AsPaginatedResponse<UserCallLog>("call_logs").ConfigureAwait(false);
var paginatedResponse = await response.AsPaginatedResponse<UserCallLog>("call_logs").ConfigureAwait(true);

// Assert
paginatedResponse.PageCount.ShouldBe(0);
Expand Down Expand Up @@ -81,7 +85,7 @@ public async Task ThrowsExceptionWhenExpectedRecordsAreMissing()
var response = new MockFluentHttpResponse(message, null, CancellationToken.None);

// Act
await Should.ThrowAsync<ArgumentException>(() => response.AsPaginatedResponseWithToken<UserCallLog>("call_logs")).ConfigureAwait(false);
await Should.ThrowAsync<ArgumentException>(() => response.AsPaginatedResponseWithToken<UserCallLog>("call_logs")).ConfigureAwait(true);
}

[Fact]
Expand All @@ -102,7 +106,7 @@ public async Task DoesNotThrowExceptionWhenRecordsAreMissingAndTotalRecordsIsZer
var response = new MockFluentHttpResponse(message, null, CancellationToken.None);

// Act
var paginatedResponse = await response.AsPaginatedResponseWithToken<UserCallLog>("call_logs").ConfigureAwait(false);
var paginatedResponse = await response.AsPaginatedResponseWithToken<UserCallLog>("call_logs").ConfigureAwait(true);

// Assert
paginatedResponse.PageSize.ShouldBe(100);
Expand Down Expand Up @@ -132,7 +136,7 @@ public async Task ThrowsExceptionWhenExpectedRecordsAreMissing()
var response = new MockFluentHttpResponse(message, null, CancellationToken.None);

// Act
await Should.ThrowAsync<ArgumentException>(() => response.AsPaginatedResponseWithTokenAndDateRange<UserCallLog>("call_logs")).ConfigureAwait(false);
await Should.ThrowAsync<ArgumentException>(() => response.AsPaginatedResponseWithTokenAndDateRange<UserCallLog>("call_logs")).ConfigureAwait(true);
}

[Fact]
Expand All @@ -153,13 +157,66 @@ public async Task DoesNotThrowExceptionWhenRecordsAreMissingAndTotalRecordsIsZer
var response = new MockFluentHttpResponse(message, null, CancellationToken.None);

// Act
var paginatedResponse = await response.AsPaginatedResponseWithTokenAndDateRange<UserCallLog>("call_logs").ConfigureAwait(false);
var paginatedResponse = await response.AsPaginatedResponseWithTokenAndDateRange<UserCallLog>("call_logs").ConfigureAwait(true);

// Assert
paginatedResponse.PageSize.ShouldBe(100);
paginatedResponse.Records.ShouldBeEmpty();
paginatedResponse.TotalRecords.ShouldBe(0);
}
}

public class Enumconversion
{
public enum MyEnum
{
[EnumMember(Value = "One")]
First,

[MultipleValuesEnumMember(DefaultValue = "Two", OtherValues = new[] { "Second", "Alternative" })]
Second,

[JsonPropertyName("Three")]
Third,

[Description("Four")]
Fourth,

Fifth
}

[Theory]
[InlineData("one", MyEnum.First)]
[InlineData("two", MyEnum.Second)]
[InlineData("second", MyEnum.Second)]
[InlineData("alternative", MyEnum.Second)]
[InlineData("three", MyEnum.Third)]
[InlineData("four", MyEnum.Fourth)]
[InlineData("fifth", MyEnum.Fifth)]
public void ToEnum(string value, MyEnum expected)
{
// Act
var result = value.ToEnum<MyEnum>();

// Assert
result.ShouldBe(expected);
}

[Theory]
[InlineData(MyEnum.First, "One")]
[InlineData(MyEnum.Second, "Two")]
[InlineData(MyEnum.Third, "Three")]
[InlineData(MyEnum.Fourth, "Four")]
[InlineData(MyEnum.Fifth, "Fifth")]
public void ToEnumString(MyEnum value, string expected)
{
// Act
var result = value.ToEnumString();

// Assert
result.ShouldBe(expected);

}
}
}
}
2 changes: 2 additions & 0 deletions Source/ZoomNet.UnitTests/Json/ParticipantDeviceConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,8 @@ public void Write_multiple()
[InlineData("iOs", ParticipantDevice.IOS)]
[InlineData("H.323/SIP", ParticipantDevice.Sip)]
[InlineData("Windows", ParticipantDevice.Windows)]
[InlineData("WIN", ParticipantDevice.Windows)]
[InlineData("Zoom Rooms", ParticipantDevice.ZoomRoom)]
public void Read_single(string value, ParticipantDevice expectedValue)
{
// Arrange
Expand Down
2 changes: 1 addition & 1 deletion Source/ZoomNet.UnitTests/Resources/CloudRecordingsTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -516,7 +516,7 @@ public async Task GetRecordingsForUserAsync()
var recordings = new CloudRecordings(client);

// Act
var result = await recordings.GetRecordingsForUserAsync(userId, false, from, to, recordsPerPage, null, CancellationToken.None).ConfigureAwait(false);
var result = await recordings.GetRecordingsForUserAsync(userId, false, from, to, recordsPerPage, null, CancellationToken.None).ConfigureAwait(true);

// Assert
mockHttp.VerifyNoOutstandingExpectation();
Expand Down
4 changes: 2 additions & 2 deletions Source/ZoomNet.UnitTests/Resources/PhoneCallRecordings.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ public async Task GetRecordingAsync()
// Act
var result = await phone
.GetRecordingAsync(callId, CancellationToken.None)
.ConfigureAwait(false);
.ConfigureAwait(true);

// Assert
mockHttp.VerifyNoOutstandingExpectation();
Expand Down Expand Up @@ -62,7 +62,7 @@ public async Task GetRecordingTranscriptAsync()
// Act
var result = await phone
.GetRecordingTranscriptAsync(recordingId, CancellationToken.None)
.ConfigureAwait(false);
.ConfigureAwait(true);

// Assert
mockHttp.VerifyNoOutstandingExpectation();
Expand Down
6 changes: 3 additions & 3 deletions Source/ZoomNet.UnitTests/ZoomNet.UnitTests.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,10 @@
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="RichardSzalay.MockHttp" Version="6.0.0" />
<PackageReference Include="RichardSzalay.MockHttp" Version="7.0.0" />
<PackageReference Include="Shouldly" Version="4.2.1" />
<PackageReference Include="xunit" Version="2.5.0" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.5.0">
<PackageReference Include="xunit" Version="2.6.0" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.5.3">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers</IncludeAssets>
</PackageReference>
Expand Down
107 changes: 57 additions & 50 deletions Source/ZoomNet/Extensions/Internal.cs
Original file line number Diff line number Diff line change
Expand Up @@ -171,23 +171,19 @@ internal static async Task<string> ReadAsStringAsync(this HttpContent httpConten

// This is important: we must make a copy of the response stream otherwise we would get an
// exception on subsequent attempts to read the content of the stream
using (var ms = Utils.MemoryStreamManager.GetStream())
{
const int DefaultBufferSize = 81920;
await contentStream.CopyToAsync(ms, DefaultBufferSize, cancellationToken).ConfigureAwait(false);
ms.Position = 0;
using (var sr = new StreamReader(ms, encoding))
{
using var ms = Utils.MemoryStreamManager.GetStream();
const int DefaultBufferSize = 81920;
await contentStream.CopyToAsync(ms, DefaultBufferSize, cancellationToken).ConfigureAwait(false);
ms.Position = 0;
using var sr = new StreamReader(ms, encoding);
#if NET7_0_OR_GREATER
content = await sr.ReadToEndAsync(cancellationToken).ConfigureAwait(false);
content = await sr.ReadToEndAsync(cancellationToken).ConfigureAwait(false);
#else
content = await sr.ReadToEndAsync().ConfigureAwait(false);
content = await sr.ReadToEndAsync().ConfigureAwait(false);
#endif
}

// It's important to rewind the stream
if (contentStream.CanSeek) contentStream.Position = 0;
}
// It's important to rewind the stream
if (contentStream.CanSeek) contentStream.Position = 0;
}

return content;
Expand Down Expand Up @@ -525,54 +521,50 @@ internal static T GetPropertyValue<T>(this JsonElement element, string[] names)
internal static async Task<TResult[]> ForEachAsync<T, TResult>(this IEnumerable<T> items, Func<T, Task<TResult>> action, int maxDegreeOfParalellism)
{
var allTasks = new List<Task<TResult>>();
using (var throttler = new SemaphoreSlim(initialCount: maxDegreeOfParalellism))
using var throttler = new SemaphoreSlim(initialCount: maxDegreeOfParalellism);
foreach (var item in items)
{
foreach (var item in items)
{
await throttler.WaitAsync();
allTasks.Add(
Task.Run(async () =>
await throttler.WaitAsync();
allTasks.Add(
Task.Run(async () =>
{
try
{
try
{
return await action(item).ConfigureAwait(false);
}
finally
{
throttler.Release();
}
}));
}

var results = await Task.WhenAll(allTasks).ConfigureAwait(false);
return results;
return await action(item).ConfigureAwait(false);
}
finally
{
throttler.Release();
}
}));
}

var results = await Task.WhenAll(allTasks).ConfigureAwait(false);
return results;
}

internal static async Task ForEachAsync<T>(this IEnumerable<T> items, Func<T, Task> action, int maxDegreeOfParalellism)
{
var allTasks = new List<Task>();
using (var throttler = new SemaphoreSlim(initialCount: maxDegreeOfParalellism))
using var throttler = new SemaphoreSlim(initialCount: maxDegreeOfParalellism);
foreach (var item in items)
{
foreach (var item in items)
{
await throttler.WaitAsync();
allTasks.Add(
Task.Run(async () =>
await throttler.WaitAsync();
allTasks.Add(
Task.Run(async () =>
{
try
{
try
{
await action(item).ConfigureAwait(false);
}
finally
{
throttler.Release();
}
}));
}

await Task.WhenAll(allTasks).ConfigureAwait(false);
await action(item).ConfigureAwait(false);
}
finally
{
throttler.Release();
}
}));
}

await Task.WhenAll(allTasks).ConfigureAwait(false);
}

/// <summary>
Expand Down Expand Up @@ -764,6 +756,13 @@ internal static string ToEnumString<T>(this T enumValue)
internal static bool TryToEnumString<T>(this T enumValue, out string stringValue)
where T : Enum
{
var multipleValuesEnumMemberAttribute = enumValue.GetAttributeOfType<MultipleValuesEnumMemberAttribute>();
if (multipleValuesEnumMemberAttribute != null)
{
stringValue = multipleValuesEnumMemberAttribute.DefaultValue;
return true;
}

var enumMemberAttribute = enumValue.GetAttributeOfType<EnumMemberAttribute>();
if (enumMemberAttribute != null)
{
Expand Down Expand Up @@ -810,6 +809,14 @@ internal static bool TryToEnum<T>(this string str, out T enumValue)
{
var customAttributes = enumType.GetField(name).GetCustomAttributes(true);

// See if there's a matching 'MultipleValuesEnumMember' attribute
if (customAttributes.OfType<MultipleValuesEnumMemberAttribute>().Any(attribute => string.Equals(attribute.DefaultValue, str, StringComparison.OrdinalIgnoreCase) ||
(attribute.OtherValues ?? Array.Empty<string>()).Any(otherValue => string.Equals(otherValue, str, StringComparison.OrdinalIgnoreCase))))
{
enumValue = (T)Enum.Parse(enumType, name);
return true;
}

// See if there's a matching 'EnumMember' attribute
if (customAttributes.OfType<EnumMemberAttribute>().Any(attribute => string.Equals(attribute.Value, str, StringComparison.OrdinalIgnoreCase)))
{
Expand Down
2 changes: 2 additions & 0 deletions Source/ZoomNet/Json/ZoomNetJsonSerializerContext.cs
Original file line number Diff line number Diff line change
Expand Up @@ -137,6 +137,7 @@ namespace ZoomNet.Json
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallRecordingTranscriptTimelineFraction))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallRecordingTranscriptTimelineUser))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallRecordingType))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallUser))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneNumber))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneType))]
[JsonSerializable(typeof(ZoomNet.Models.PmiMeetingPasswordRequirementType))]
Expand Down Expand Up @@ -412,6 +413,7 @@ namespace ZoomNet.Json
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallRecordingTranscriptTimelineFraction[]))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallRecordingTranscriptTimelineUser[]))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallRecordingType[]))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneCallUser[]))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneNumber[]))]
[JsonSerializable(typeof(ZoomNet.Models.PhoneType[]))]
[JsonSerializable(typeof(ZoomNet.Models.PmiMeetingPasswordRequirementType[]))]
Expand Down
11 changes: 9 additions & 2 deletions Source/ZoomNet/Models/ParticipantDevice.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using System.Runtime.Serialization;
using ZoomNet.Utilities;

namespace ZoomNet.Models
{
Expand Down Expand Up @@ -28,7 +29,7 @@ public enum ParticipantDevice
/// <summary>
/// The participant joined via VoIP using a Windows device.
/// </summary>
[EnumMember(Value = "Windows")]
[MultipleValuesEnumMember(DefaultValue = "Windows", OtherValues = new[] { "WIN" })]
Windows,

/// <summary>
Expand All @@ -53,6 +54,12 @@ public enum ParticipantDevice
/// The participant joined via the web.
/// </summary>
[EnumMember(Value = "Web")]
Web
Web,

/// <summary>
/// The participant joined via a Zoom Room.
/// </summary>
[EnumMember(Value = "Zoom Rooms")]
ZoomRoom
}
}
Loading

0 comments on commit 10f5c75

Please sign in to comment.