[tests] Improve detection of network problems to better ignore tests in case of network problems. (#19594)

* Add basic logic to detect network problems for NSErrors.
* Include better logging of NSError failures in the UrlConnectionTest.SendSynchronousRequest test.
* Misc code cleanup.
This commit is contained in:
Rolf Bjarne Kvinge 2023-12-14 15:53:13 +01:00 коммит произвёл GitHub
Родитель cf398ed770
Коммит eb80f66b6a
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
2 изменённых файлов: 48 добавлений и 6 удалений

Просмотреть файл

@ -137,10 +137,10 @@ partial class TestRuntime {
public static void IgnoreInCI (string message)
{
if (!IsInCI) {
Console.WriteLine ($"Not ignoring test ('{message}'), because not running in CI. BUILD_REVISION={Environment.GetEnvironmentVariable ("BUILD_REVISION")} BUILD_SOURCEVERSION={Environment.GetEnvironmentVariable ("BUILD_SOURCEVERSION")}");
Console.WriteLine ($"Not ignoring test, because not running in CI: {message}");
return;
}
Console.WriteLine ($"Ignoring test ('{message}'), because not running in CI. BUILD_REVISION={Environment.GetEnvironmentVariable ("BUILD_REVISION")} BUILD_SOURCEVERSION={Environment.GetEnvironmentVariable ("BUILD_SOURCEVERSION")}");
Console.WriteLine ($"Ignoring test, because not running in CI: {message}");
NUnit.Framework.Assert.Ignore (message);
}
@ -1480,6 +1480,16 @@ partial class TestRuntime {
IgnoreInCIIfDnsResolutionFailed (ex);
}
public static void IgnoreInCIIfBadNetwork (NSError? error)
{
if (error is null)
return;
IgnoreInCIIfNetworkConnectionLost (error);
IgnoreInCIIfNoNetworkConnection (error);
IgnoreInCIIfDnsResolutionFailed (error);
}
public static void IgnoreInCIIfDnsResolutionFailed (Exception ex)
{
var se = FindInner<System.Net.Sockets.SocketException> (ex);
@ -1498,6 +1508,11 @@ partial class TestRuntime {
IgnoreInCI ($"Ignored due to DNS resolution failure '{se.Message}'");
}
public static void IgnoreInCIIfDnsResolutionFailed (NSError error)
{
IgnoreNetworkError (error, CFNetworkErrors.CannotFindHost);
}
public static void IgnoreInCIIfForbidden (Exception ex)
{
IgnoreInCIfHttpStatusCodes (ex, HttpStatusCode.BadGateway, HttpStatusCode.GatewayTimeout, HttpStatusCode.ServiceUnavailable, HttpStatusCode.Forbidden);
@ -1529,14 +1544,40 @@ partial class TestRuntime {
public static void IgnoreInCIIfNetworkConnectionLost (Exception ex)
{
// <Foundation.NSErrorException: Error Domain=NSURLErrorDomain Code=-1005 "The network connection was lost." UserInfo ...
if (!(ex is NSErrorException nex))
return;
if (nex.Code != (nint) (long) CFNetworkErrors.NetworkConnectionLost)
IgnoreInCIIfNetworkConnectionLost (nex.Error);
}
public static void IgnoreInCIIfNetworkConnectionLost (NSError error)
{
// <Foundation.NSErrorException: Error Domain=NSURLErrorDomain Code=-1005 "The network connection was lost." UserInfo ...
IgnoreNetworkError (error, CFNetworkErrors.NetworkConnectionLost);
}
public static void IgnoreInCIIfNoNetworkConnection (NSError error)
{
// Error Domain=NSURLErrorDomain Code=-1009 "The Internet connection appears to be offline."
IgnoreNetworkError (error, CFNetworkErrors.NotConnectedToInternet);
}
static void IgnoreNetworkError (NSError error, params CFNetworkErrors [] errors)
{
if (error is null)
return;
IgnoreInCI ($"Ignored due to CFNetwork error {(CFNetworkErrors) (long) nex.Code}");
#if __WATCHOS__
if (error.Domain != NSError.NSUrlErrorDomain)
#else
if (error.Domain != NSError.NSUrlErrorDomain && error.Domain != NSError.CFNetworkErrorDomain)
#endif
return;
foreach (var e in errors) {
if (error.Code == (nint) (long) e)
IgnoreInCI ($"Ignored due to network error: {error}");
}
}
static T? FindInner<T> (Exception? ex) where T : Exception

Просмотреть файл

@ -55,7 +55,8 @@ namespace MonoTouchFixtures.Foundation {
using var url = new NSUrl (NetworkResources.MicrosoftUrl);
using var request = new NSUrlRequest (url);
using var data = NSUrlConnection.SendSynchronousRequest (request, out var response, out var error);
Assert.IsNull (error, "Error");
TestRuntime.IgnoreInCIIfBadNetwork (error);
Assert.IsNull (error, $"Error: {error?.Description}");
Assert.IsNotNull (data, "Data");
Assert.IsNotNull (response, "Response");
response?.Dispose ();