diff --git a/src/Umbraco.Core/Attempt.cs b/src/Umbraco.Core/Attempt.cs
index eddd2c8785..0a8987726a 100644
--- a/src/Umbraco.Core/Attempt.cs
+++ b/src/Umbraco.Core/Attempt.cs
@@ -17,9 +17,9 @@ namespace Umbraco.Cms.Core
/// The type of the attempted operation result.
/// The result of the attempt.
/// The successful attempt.
- public static Attempt Succeed(TResult result)
+ public static Attempt Succeed(TResult? result)
{
- return Attempt.Succeed(result);
+ return Attempt.Succeed(result);
}
///
diff --git a/src/Umbraco.Core/AttemptOfTResult.cs b/src/Umbraco.Core/AttemptOfTResult.cs
index cebabe214b..ebe7d57d7f 100644
--- a/src/Umbraco.Core/AttemptOfTResult.cs
+++ b/src/Umbraco.Core/AttemptOfTResult.cs
@@ -10,7 +10,7 @@ namespace Umbraco.Cms.Core
public struct Attempt
{
// private - use Succeed() or Fail() methods to create attempts
- private Attempt(bool success, TResult result, Exception exception)
+ private Attempt(bool? success, TResult? result, Exception? exception)
{
Success = success;
Result = result;
@@ -20,22 +20,22 @@ namespace Umbraco.Cms.Core
///
/// Gets a value indicating whether this was successful.
///
- public bool Success { get; }
+ public bool? Success { get; }
///
/// Gets the exception associated with an unsuccessful attempt.
///
- public Exception Exception { get; }
+ public Exception? Exception { get; }
///
/// Gets the attempt result.
///
- public TResult Result { get; }
+ public TResult? Result { get; }
///
/// Gets the attempt result, if successful, else a default value.
///
- public TResult ResultOr(TResult value) => Success ? Result : value;
+ public TResult? ResultOr(TResult? value) => Success.HasValue && Success.Value ? Result : value;
// optimize, use a singleton failed attempt
private static readonly Attempt Failed = new Attempt(false, default(TResult), null);
@@ -54,7 +54,7 @@ namespace Umbraco.Cms.Core
///
/// The result of the attempt.
/// The successful attempt.
- public static Attempt Succeed(TResult result)
+ public static Attempt Succeed(TResult? result)
{
return new Attempt(true, result, null);
}
@@ -73,7 +73,7 @@ namespace Umbraco.Cms.Core
///
/// The exception causing the failure of the attempt.
/// The failed attempt.
- public static Attempt Fail(Exception exception)
+ public static Attempt Fail(Exception? exception)
{
return new Attempt(false, default(TResult), exception);
}
@@ -115,7 +115,7 @@ namespace Umbraco.Cms.Core
/// A value indicating whether the attempt is successful.
/// The result of the attempt.
/// The attempt.
- public static Attempt If(bool condition, TResult result)
+ public static Attempt If(bool condition, TResult? result)
{
return new Attempt(condition, result, null);
}
@@ -125,7 +125,7 @@ namespace Umbraco.Cms.Core
///
///
///
- public static implicit operator bool(Attempt a)
+ public static implicit operator bool?(Attempt a)
{
return a.Success;
}
diff --git a/src/Umbraco.Core/Extensions/AssemblyExtensions.cs b/src/Umbraco.Core/Extensions/AssemblyExtensions.cs
index cefaae5b86..aea0f847ab 100644
--- a/src/Umbraco.Core/Extensions/AssemblyExtensions.cs
+++ b/src/Umbraco.Core/Extensions/AssemblyExtensions.cs
@@ -23,8 +23,7 @@ namespace Umbraco.Extensions
{
return _rootDir;
}
-
- var codeBase = executingAssembly.CodeBase;
+ var codeBase = executingAssembly.Location;
var uri = new Uri(codeBase);
var path = uri.LocalPath;
var baseDirectory = Path.GetDirectoryName(path);
@@ -45,7 +44,7 @@ namespace Umbraco.Extensions
///
public static FileInfo GetAssemblyFile(this Assembly assembly)
{
- var codeBase = assembly.CodeBase;
+ var codeBase = assembly.Location;
var uri = new Uri(codeBase);
var path = uri.LocalPath;
return new FileInfo(path);
@@ -58,7 +57,7 @@ namespace Umbraco.Extensions
///
public static bool IsAppCodeAssembly(this Assembly assembly)
{
- if (assembly.FullName.StartsWith("App_Code"))
+ if (assembly.FullName!.StartsWith("App_Code"))
{
try
{
@@ -82,7 +81,7 @@ namespace Umbraco.Extensions
public static bool IsGlobalAsaxAssembly(this Assembly assembly)
{
//only way I can figure out how to test is by the name
- return assembly.FullName.StartsWith("App_global.asax");
+ return assembly.FullName!.StartsWith("App_global.asax");
}
///
@@ -90,12 +89,17 @@ namespace Umbraco.Extensions
///
///
///
- public static FileInfo GetAssemblyFile(this AssemblyName assemblyName)
+ public static FileInfo? GetAssemblyFile(this AssemblyName assemblyName)
{
var codeBase = assemblyName.CodeBase;
- var uri = new Uri(codeBase);
- var path = uri.LocalPath;
- return new FileInfo(path);
+ if (!string.IsNullOrEmpty(codeBase))
+ {
+ var uri = new Uri(codeBase);
+ var path = uri.LocalPath;
+ return new FileInfo(path);
+ }
+
+ return null;
}
}
diff --git a/src/Umbraco.Core/Extensions/ClaimsIdentityExtensions.cs b/src/Umbraco.Core/Extensions/ClaimsIdentityExtensions.cs
index 9b3674b07b..19d2de1c85 100644
--- a/src/Umbraco.Core/Extensions/ClaimsIdentityExtensions.cs
+++ b/src/Umbraco.Core/Extensions/ClaimsIdentityExtensions.cs
@@ -13,7 +13,7 @@ namespace Umbraco.Extensions
{
public static class ClaimsIdentityExtensions
{
- public static T GetUserId(this IIdentity identity)
+ public static T? GetUserId(this IIdentity identity)
{
var strId = identity.GetUserId();
var converted = strId.TryConvertTo();
@@ -27,11 +27,11 @@ namespace Umbraco.Extensions
///
/// The string value of the user id if found otherwise null
///
- public static string GetUserId(this IIdentity identity)
+ public static string? GetUserId(this IIdentity identity)
{
if (identity == null) throw new ArgumentNullException(nameof(identity));
- string userId = null;
+ string? userId = null;
if (identity is ClaimsIdentity claimsIdentity)
{
userId = claimsIdentity.FindFirstValue(ClaimTypes.NameIdentifier)
@@ -48,11 +48,11 @@ namespace Umbraco.Extensions
///
/// The string value of the user name if found otherwise null
///
- public static string GetUserName(this IIdentity identity)
+ public static string? GetUserName(this IIdentity identity)
{
if (identity == null) throw new ArgumentNullException(nameof(identity));
- string username = null;
+ string? username = null;
if (identity is ClaimsIdentity claimsIdentity)
{
username = claimsIdentity.FindFirstValue(ClaimTypes.Name)
@@ -70,7 +70,7 @@ namespace Umbraco.Extensions
///
/// The string value of the claim if found otherwise null
///
- public static string FindFirstValue(this ClaimsIdentity identity, string claimType)
+ public static string? FindFirstValue(this ClaimsIdentity identity, string claimType)
{
if (identity == null) throw new ArgumentNullException(nameof(identity));
@@ -100,7 +100,7 @@ namespace Umbraco.Extensions
///
/// Verified identity wrapped in a ClaimsIdentity with BackOfficeAuthentication type
/// True if ClaimsIdentity
- public static bool VerifyBackOfficeIdentity(this ClaimsIdentity identity, out ClaimsIdentity verifiedIdentity)
+ public static bool VerifyBackOfficeIdentity(this ClaimsIdentity identity, out ClaimsIdentity? verifiedIdentity)
{
if (identity is null)
{
@@ -119,7 +119,7 @@ namespace Umbraco.Extensions
}
}
- verifiedIdentity = identity.AuthenticationType == Constants.Security.BackOfficeAuthenticationType ? identity : new ClaimsIdentity(identity.Claims, Constants.Security.BackOfficeAuthenticationType);
+ verifiedIdentity = identity.AuthenticationType == Constants.Security.BackOfficeAuthenticationType ? identity : new ClaimsIdentity(identity.Claims, Constants.Security.BackOfficeAuthenticationType);
return true;
}
@@ -294,35 +294,44 @@ namespace Umbraco.Extensions
///
///
/// User ID as integer
- public static int GetId(this ClaimsIdentity identity) => int.Parse(identity.FindFirstValue(ClaimTypes.NameIdentifier), CultureInfo.InvariantCulture);
+ public static int? GetId(this ClaimsIdentity identity)
+ {
+ var firstValue = identity.FindFirstValue(ClaimTypes.NameIdentifier);
+ if (firstValue is not null)
+ {
+ int.Parse(firstValue, CultureInfo.InvariantCulture);
+ }
+
+ return null;
+ }
///
/// Get the real name belonging to the user from a ClaimsIdentity
///
///
/// Real name of the user
- public static string GetRealName(this ClaimsIdentity identity) => identity.FindFirstValue(ClaimTypes.GivenName);
+ public static string? GetRealName(this ClaimsIdentity identity) => identity.FindFirstValue(ClaimTypes.GivenName);
///
/// Get the username of the user from a ClaimsIdentity
///
///
/// Username of the user
- public static string GetUsername(this ClaimsIdentity identity) => identity.FindFirstValue(ClaimTypes.Name);
+ public static string? GetUsername(this ClaimsIdentity identity) => identity.FindFirstValue(ClaimTypes.Name);
///
/// Get the culture string from a ClaimsIdentity
///
///
/// Culture string
- public static string GetCultureString(this ClaimsIdentity identity) => identity.FindFirstValue(ClaimTypes.Locality);
+ public static string? GetCultureString(this ClaimsIdentity identity) => identity.FindFirstValue(ClaimTypes.Locality);
///
/// Get the security stamp from a ClaimsIdentity
///
///
/// Security stamp
- public static string GetSecurityStamp(this ClaimsIdentity identity) => identity.FindFirstValue(Constants.Security.SecurityStampClaimType);
+ public static string? GetSecurityStamp(this ClaimsIdentity identity) => identity.FindFirstValue(Constants.Security.SecurityStampClaimType);
///
/// Get the roles assigned to a user from a ClaimsIdentity
@@ -336,17 +345,20 @@ namespace Umbraco.Extensions
///
/// Adds or updates and existing claim.
///
- public static void AddOrUpdateClaim(this ClaimsIdentity identity, Claim claim)
+ public static void AddOrUpdateClaim(this ClaimsIdentity identity, Claim? claim)
{
if (identity == null)
{
throw new ArgumentNullException(nameof(identity));
}
- Claim existingClaim = identity.Claims.FirstOrDefault(x => x.Type == claim.Type);
- identity.TryRemoveClaim(existingClaim);
+ if (claim is not null)
+ {
+ Claim? existingClaim = identity.Claims.FirstOrDefault(x => x.Type == claim.Type);
+ identity.TryRemoveClaim(existingClaim);
- identity.AddClaim(claim);
+ identity.AddClaim(claim);
+ }
}
}
}
diff --git a/src/Umbraco.Core/Extensions/ContentVariationExtensions.cs b/src/Umbraco.Core/Extensions/ContentVariationExtensions.cs
index c6d6b2c557..4469683acb 100644
--- a/src/Umbraco.Core/Extensions/ContentVariationExtensions.cs
+++ b/src/Umbraco.Core/Extensions/ContentVariationExtensions.cs
@@ -289,10 +289,10 @@ namespace Umbraco.Extensions
/// Basically, exact is for one content type, or one property type, and !exact is for "all property types" of one content type.
/// Both and can be "*" to indicate "all of them".
///
- public static bool ValidateVariation(this ContentVariation variation, string culture, string segment, bool exact, bool wildcards, bool throwIfInvalid)
+ public static bool ValidateVariation(this ContentVariation variation, string? culture, string? segment, bool exact, bool wildcards, bool throwIfInvalid)
{
- culture = culture.NullOrWhiteSpaceAsNull();
- segment = segment.NullOrWhiteSpaceAsNull();
+ culture = culture?.NullOrWhiteSpaceAsNull();
+ segment = segment?.NullOrWhiteSpaceAsNull();
// if wildcards are disabled, do not allow "*"
if (!wildcards && (culture == "*" || segment == "*"))
diff --git a/src/Umbraco.Core/Extensions/DelegateExtensions.cs b/src/Umbraco.Core/Extensions/DelegateExtensions.cs
index 43e3c8947b..40ee011641 100644
--- a/src/Umbraco.Core/Extensions/DelegateExtensions.cs
+++ b/src/Umbraco.Core/Extensions/DelegateExtensions.cs
@@ -10,7 +10,7 @@ namespace Umbraco.Extensions
{
public static class DelegateExtensions
{
- public static Attempt RetryUntilSuccessOrTimeout(this Func> task, TimeSpan timeout, TimeSpan pause)
+ public static Attempt RetryUntilSuccessOrTimeout(this Func> task, TimeSpan timeout, TimeSpan pause)
{
if (pause.TotalMilliseconds < 0)
{
@@ -20,14 +20,14 @@ namespace Umbraco.Extensions
do
{
var result = task();
- if (result) { return result; }
+ if (result.Success.HasValue && result.Success.Value) { return result; }
Thread.Sleep((int)pause.TotalMilliseconds);
}
while (stopwatch.Elapsed < timeout);
- return Attempt.Fail();
+ return Attempt.Fail();
}
- public static Attempt RetryUntilSuccessOrMaxAttempts(this Func> task, int totalAttempts, TimeSpan pause)
+ public static Attempt RetryUntilSuccessOrMaxAttempts(this Func> task, int totalAttempts, TimeSpan pause)
{
if (pause.TotalMilliseconds < 0)
{
@@ -38,11 +38,11 @@ namespace Umbraco.Extensions
{
attempts++;
var result = task(attempts);
- if (result) { return result; }
+ if (result.Success.HasValue && result.Success.Value) { return result; }
Thread.Sleep((int)pause.TotalMilliseconds);
}
while (attempts < totalAttempts);
- return Attempt.Fail();
+ return Attempt.Fail();
}
}
}
diff --git a/src/Umbraco.Core/Extensions/DictionaryExtensions.cs b/src/Umbraco.Core/Extensions/DictionaryExtensions.cs
index 6227d506f3..906f12282e 100644
--- a/src/Umbraco.Core/Extensions/DictionaryExtensions.cs
+++ b/src/Umbraco.Core/Extensions/DictionaryExtensions.cs
@@ -53,8 +53,9 @@ namespace Umbraco.Extensions
/// If there is an item in the dictionary with the key, it will keep trying to update it until it can
///
public static bool TryUpdate(this ConcurrentDictionary dict, TKey key, Func updateFactory)
+ where TKey : notnull
{
- TValue curValue;
+ TValue? curValue;
while (dict.TryGetValue(key, out curValue))
{
if (dict.TryUpdate(key, updateFactory(curValue), curValue))
@@ -80,8 +81,9 @@ namespace Umbraco.Extensions
/// WARNING: If the value changes after we've retrieved it, then the item will not be updated
///
public static bool TryUpdateOptimisitic(this ConcurrentDictionary dict, TKey key, Func updateFactory)
+ where TKey : notnull
{
- TValue curValue;
+ TValue? curValue;
if (!dict.TryGetValue(key, out curValue))
return false;
dict.TryUpdate(key, updateFactory(curValue), curValue);
@@ -96,11 +98,12 @@ namespace Umbraco.Extensions
///
///
public static IDictionary ConvertTo(this IDictionary d)
+ where TKeyOut : notnull
{
var result = new Dictionary();
foreach (DictionaryEntry v in d)
{
- result.Add((TKeyOut)v.Key, (TValOut)v.Value);
+ result.Add((TKeyOut)v.Key, (TValOut)v.Value!);
}
return result;
}
@@ -115,11 +118,12 @@ namespace Umbraco.Extensions
///
///
public static IDictionary ConvertTo(this IDictionary d, Func keyConverter, Func valConverter)
+ where TKeyOut : notnull
{
var result = new Dictionary();
foreach (DictionaryEntry v in d)
{
- result.Add(keyConverter(v.Key), valConverter(v.Value));
+ result.Add(keyConverter(v.Key), valConverter(v.Value!));
}
return result;
}
@@ -205,7 +209,7 @@ namespace Umbraco.Extensions
///
///
///
- public static string GetValueAsString(this IDictionary d, TKey key)
+ public static string? GetValueAsString(this IDictionary d, TKey key)
=> d.ContainsKey(key) ? d[key]!.ToString() : string.Empty;
///
@@ -215,7 +219,7 @@ namespace Umbraco.Extensions
///
///
///
- public static string GetValueAsString(this IDictionary d, TKey key, string defaultValue)
+ public static string? GetValueAsString(this IDictionary d, TKey key, string defaultValue)
{
if (d.ContainsKey(key))
{
@@ -269,12 +273,13 @@ namespace Umbraco.Extensions
/// The default value.
/// The type
/// The entry
- public static TValue GetValueIgnoreCase(this IDictionary dictionary, string key, TValue defaultValue)
+ public static TValue GetValueIgnoreCase(this IDictionary dictionary, string? key, TValue
+ defaultValue)
{
key = dictionary.Keys.FirstOrDefault(i => i.InvariantEquals(key));
return key.IsNullOrWhiteSpace() == false
- ? dictionary[key]
+ ? dictionary[key!]
: defaultValue;
}
@@ -282,6 +287,7 @@ namespace Umbraco.Extensions
this IEnumerable enumerable,
Func syncKeySelector,
Func> asyncValueSelector)
+ where TKey : notnull
{
Dictionary dictionary = new Dictionary();
diff --git a/src/Umbraco.Core/Extensions/EnumerableExtensions.cs b/src/Umbraco.Core/Extensions/EnumerableExtensions.cs
index 6120c569d4..7abfcf0546 100644
--- a/src/Umbraco.Core/Extensions/EnumerableExtensions.cs
+++ b/src/Umbraco.Core/Extensions/EnumerableExtensions.cs
@@ -39,7 +39,7 @@ namespace Umbraco.Extensions
yield return item;
}
- public static IEnumerable> InGroupsOf(this IEnumerable source, int groupSize)
+ public static IEnumerable> InGroupsOf(this IEnumerable? source, int groupSize)
{
if (source == null)
throw new ArgumentNullException("source");
@@ -49,7 +49,7 @@ namespace Umbraco.Extensions
// following code derived from MoreLinq and does not allocate bazillions of tuples
- T[] temp = null;
+ T[]? temp = null;
var count = 0;
foreach (var item in source)
@@ -234,9 +234,8 @@ namespace Umbraco.Extensions
return sequence.Select(
x =>
{
- if (x is TActual)
+ if (x is TActual casted)
{
- var casted = x as TActual;
projection.Invoke(casted);
}
return x;
@@ -342,7 +341,7 @@ namespace Umbraco.Extensions
// this is to support filtering with multiple types
public static IEnumerable OfTypes(this IEnumerable contents, params Type[] types)
{
- return contents.Where(x => types.Contains(x.GetType()));
+ return contents.Where(x => types.Contains(x?.GetType()));
}
public static IEnumerable SkipLast(this IEnumerable source)
diff --git a/src/Umbraco.Core/Extensions/NameValueCollectionExtensions.cs b/src/Umbraco.Core/Extensions/NameValueCollectionExtensions.cs
index 1d9b093ef1..9ebc218929 100644
--- a/src/Umbraco.Core/Extensions/NameValueCollectionExtensions.cs
+++ b/src/Umbraco.Core/Extensions/NameValueCollectionExtensions.cs
@@ -9,11 +9,11 @@ namespace Umbraco.Extensions
{
public static class NameValueCollectionExtensions
{
- public static IEnumerable> AsEnumerable(this NameValueCollection nvc)
+ public static IEnumerable> AsEnumerable(this NameValueCollection nvc)
{
- foreach (string key in nvc.AllKeys)
+ foreach (string? key in nvc.AllKeys)
{
- yield return new KeyValuePair(key, nvc[key]);
+ yield return new KeyValuePair(key, nvc[key]);
}
}
@@ -22,7 +22,7 @@ namespace Umbraco.Extensions
return collection.Keys.Cast().Any(k => (string) k == key);
}
- public static T GetValue(this NameValueCollection collection, string key, T defaultIfNotFound)
+ public static T? GetValue(this NameValueCollection collection, string key, T defaultIfNotFound)
{
if (collection.ContainsKey(key) == false)
{
@@ -37,7 +37,7 @@ namespace Umbraco.Extensions
var result = val.TryConvertTo();
- return result.Success ? result.Result : defaultIfNotFound;
+ return result.Success.HasValue && result.Success.Value ? result.Result : defaultIfNotFound;
}
}
}
diff --git a/src/Umbraco.Core/Extensions/ObjectExtensions.cs b/src/Umbraco.Core/Extensions/ObjectExtensions.cs
index fae727b8f3..2013c35e24 100644
--- a/src/Umbraco.Core/Extensions/ObjectExtensions.cs
+++ b/src/Umbraco.Core/Extensions/ObjectExtensions.cs
@@ -22,9 +22,9 @@ namespace Umbraco.Extensions
///
public static class ObjectExtensions
{
- private static readonly ConcurrentDictionary NullableGenericCache = new ConcurrentDictionary();
- private static readonly ConcurrentDictionary InputTypeConverterCache = new ConcurrentDictionary();
- private static readonly ConcurrentDictionary DestinationTypeConverterCache = new ConcurrentDictionary();
+ private static readonly ConcurrentDictionary NullableGenericCache = new ConcurrentDictionary();
+ private static readonly ConcurrentDictionary InputTypeConverterCache = new ConcurrentDictionary();
+ private static readonly ConcurrentDictionary DestinationTypeConverterCache = new ConcurrentDictionary();
private static readonly ConcurrentDictionary AssignableTypeCache = new ConcurrentDictionary();
private static readonly ConcurrentDictionary BoolConvertCache = new ConcurrentDictionary();
@@ -61,7 +61,7 @@ namespace Umbraco.Extensions
///
/// The input.
///
- public static T SafeCast(this object input)
+ public static T? SafeCast(this object input)
{
if (ReferenceEquals(null, input) || ReferenceEquals(default(T), input)) return default;
if (input is T variable) return variable;
@@ -77,11 +77,11 @@ namespace Umbraco.Extensions
/// The
public static Attempt TryConvertTo(this object? input)
{
- Attempt result = TryConvertTo(input, typeof(T));
+ Attempt result = TryConvertTo(input, typeof(T));
- if (result.Success)
+ if (result.Success.HasValue && result.Success.Value)
{
- return Attempt.Succeed((T)result.Result);
+ return Attempt.Succeed((T?)result.Result);
}
if (input == null)
@@ -94,7 +94,7 @@ namespace Umbraco.Extensions
else
{
// sure, null can be any object
- return Attempt.Succeed((T)input);
+ return Attempt.Succeed((T)input!);
}
}
@@ -116,11 +116,11 @@ namespace Umbraco.Extensions
/// The input.
/// The type to convert to
/// The
- public static Attempt TryConvertTo(this object input, Type target)
+ public static Attempt TryConvertTo(this object? input, Type target)
{
if (target == null)
{
- return Attempt.Fail();
+ return Attempt.Fail();
}
try
@@ -130,11 +130,11 @@ namespace Umbraco.Extensions
// Nullable is ok
if (target.IsGenericType && GetCachedGenericNullableType(target) != null)
{
- return Attempt.Succeed(null);
+ return Attempt.Succeed(null);
}
// Reference types are ok
- return Attempt.If(target.IsValueType == false, null);
+ return Attempt.If(target.IsValueType == false, null);
}
var inputType = input.GetType();
@@ -148,7 +148,7 @@ namespace Umbraco.Extensions
// Check for string so that overloaders of ToString() can take advantage of the conversion.
if (target == typeof(string))
{
- return Attempt.Succeed(input.ToString());
+ return Attempt.Succeed(input.ToString());
}
// If we've got a nullable of something, we try to convert directly to that thing.
@@ -165,7 +165,7 @@ namespace Umbraco.Extensions
// TODO: Why the check against only bool/date when a string is null/empty? In what scenario can we convert to another type when the string is null or empty other than just being null?
if (string.IsNullOrEmpty(inputString) && (underlying == typeof(DateTime) || underlying == typeof(bool)))
{
- return Attempt.Succeed(null);
+ return Attempt.Succeed(null);
}
}
@@ -173,13 +173,13 @@ namespace Umbraco.Extensions
var inner = input.TryConvertTo(underlying);
// And if successful, fall on through to rewrap in a nullable; if failed, pass on the exception
- if (inner.Success)
+ if (inner.Success.HasValue && inner.Success.Value)
{
input = inner.Result; // Now fall on through...
}
else
{
- return Attempt.Fail(inner.Exception);
+ return Attempt.Fail(inner.Exception);
}
}
}
@@ -211,7 +211,7 @@ namespace Umbraco.Extensions
{
if (GetCachedCanConvertToBoolean(inputType))
{
- return Attempt.Succeed(CustomBooleanTypeConverter.ConvertFrom(input));
+ return Attempt.Succeed(CustomBooleanTypeConverter.ConvertFrom(input!));
}
}
@@ -224,7 +224,7 @@ namespace Umbraco.Extensions
var outputConverter = GetCachedTargetTypeConverter(inputType, target);
if (outputConverter != null)
{
- return Attempt.Succeed(outputConverter.ConvertFrom(input));
+ return Attempt.Succeed(outputConverter.ConvertFrom(input!));
}
if (target.IsGenericType && GetCachedGenericNullableType(target) != null)
@@ -243,10 +243,10 @@ namespace Umbraco.Extensions
}
catch (Exception e)
{
- return Attempt.Fail(e);
+ return Attempt.Fail(e);
}
- return Attempt.Fail();
+ return Attempt.Fail();
}
///
@@ -256,12 +256,12 @@ namespace Umbraco.Extensions
/// The input.
/// The type to convert to
/// The
- private static Attempt? TryConvertToFromString(this string input, Type target)
+ private static Attempt? TryConvertToFromString(this string input, Type target)
{
// Easy
if (target == typeof(string))
{
- return Attempt.Succeed(input);
+ return Attempt.Succeed(input);
}
// Null, empty, whitespaces
@@ -270,13 +270,13 @@ namespace Umbraco.Extensions
if (target == typeof(bool))
{
// null/empty = bool false
- return Attempt.Succeed(false);
+ return Attempt.Succeed(false);
}
if (target == typeof(DateTime))
{
// null/empty = min DateTime value
- return Attempt.Succeed(DateTime.MinValue);
+ return Attempt.Succeed(DateTime.MinValue);
}
// Cannot decide here,
@@ -296,25 +296,25 @@ namespace Umbraco.Extensions
{
if (int.TryParse(input, out var value))
{
- return Attempt.Succeed(value);
+ return Attempt.Succeed(value);
}
// Because decimal 100.01m will happily convert to integer 100, it
// makes sense that string "100.01" *also* converts to integer 100.
var input2 = NormalizeNumberDecimalSeparator(input);
- return Attempt.If(decimal.TryParse(input2, out var value2), Convert.ToInt32(value2));
+ return Attempt.If(decimal.TryParse(input2, out var value2), Convert.ToInt32(value2));
}
if (target == typeof(long))
{
if (long.TryParse(input, out var value))
{
- return Attempt.Succeed(value);
+ return Attempt.Succeed(value);
}
// Same as int
var input2 = NormalizeNumberDecimalSeparator(input);
- return Attempt.If(decimal.TryParse(input2, out var value2), Convert.ToInt64(value2));
+ return Attempt.If(decimal.TryParse(input2, out var value2), Convert.ToInt64(value2));
}
// TODO: Should we do the decimal trick for short, byte, unsigned?
@@ -323,7 +323,7 @@ namespace Umbraco.Extensions
{
if (bool.TryParse(input, out var value))
{
- return Attempt.Succeed(value);
+ return Attempt.Succeed(value);
}
// Don't declare failure so the CustomBooleanTypeConverter can try
@@ -334,38 +334,38 @@ namespace Umbraco.Extensions
switch (Type.GetTypeCode(target))
{
case TypeCode.Int16:
- return Attempt.If(short.TryParse(input, out var value), value);
+ return Attempt.If(short.TryParse(input, out var value), value);
case TypeCode.Double:
var input2 = NormalizeNumberDecimalSeparator(input);
- return Attempt.If(double.TryParse(input2, out var valueD), valueD);
+ return Attempt.If(double.TryParse(input2, out var valueD), valueD);
case TypeCode.Single:
var input3 = NormalizeNumberDecimalSeparator(input);
- return Attempt.If(float.TryParse(input3, out var valueF), valueF);
+ return Attempt.If(float.TryParse(input3, out var valueF), valueF);
case TypeCode.Char:
- return Attempt.If(char.TryParse(input, out var valueC), valueC);
+ return Attempt.If(char.TryParse(input, out var valueC), valueC);
case TypeCode.Byte:
- return Attempt.If(byte.TryParse(input, out var valueB), valueB);
+ return Attempt.If(byte.TryParse(input, out var valueB), valueB);
case TypeCode.SByte:
- return Attempt.If(sbyte.TryParse(input, out var valueSb), valueSb);
+ return Attempt.If(sbyte.TryParse(input, out var valueSb), valueSb);
case TypeCode.UInt32:
- return Attempt.If(uint.TryParse(input, out var valueU), valueU);
+ return Attempt.If(uint.TryParse(input, out var valueU), valueU);
case TypeCode.UInt16:
- return Attempt.If(ushort.TryParse(input, out var valueUs), valueUs);
+ return Attempt.If(ushort.TryParse(input, out var valueUs), valueUs);
case TypeCode.UInt64:
- return Attempt.If(ulong.TryParse(input, out var valueUl), valueUl);
+ return Attempt.If(ulong.TryParse(input, out var valueUl), valueUl);
}
}
else if (target == typeof(Guid))
{
- return Attempt.If(Guid.TryParse(input, out var value), value);
+ return Attempt.If(Guid.TryParse(input, out var value), value);
}
else if (target == typeof(DateTime))
{
@@ -375,34 +375,34 @@ namespace Umbraco.Extensions
{
case DateTimeKind.Unspecified:
case DateTimeKind.Utc:
- return Attempt.Succeed(value);
+ return Attempt.Succeed(value);
case DateTimeKind.Local:
- return Attempt.Succeed(value.ToUniversalTime());
+ return Attempt.Succeed(value.ToUniversalTime());
default:
throw new ArgumentOutOfRangeException();
}
}
- return Attempt.Fail();
+ return Attempt.Fail();
}
else if (target == typeof(DateTimeOffset))
{
- return Attempt.If(DateTimeOffset.TryParse(input, out var value), value);
+ return Attempt.If(DateTimeOffset.TryParse(input, out var value), value);
}
else if (target == typeof(TimeSpan))
{
- return Attempt.If(TimeSpan.TryParse(input, out var value), value);
+ return Attempt.If(TimeSpan.TryParse(input, out var value), value);
}
else if (target == typeof(decimal))
{
var input2 = NormalizeNumberDecimalSeparator(input);
- return Attempt.If(decimal.TryParse(input2, out var value), value);
+ return Attempt.If(decimal.TryParse(input2, out var value), value);
}
else if (input != null && target == typeof(Version))
{
- return Attempt.If(Version.TryParse(input, out var value), value);
+ return Attempt.If(Version.TryParse(input, out var value), value);
}
// E_NOTIMPL IPAddress, BigInteger
@@ -489,9 +489,9 @@ namespace Umbraco.Extensions
///
///
///
- public static IDictionary ToDictionary(this T o, params Expression>[] ignoreProperties)
+ public static IDictionary? ToDictionary(this T o, params Expression>[] ignoreProperties)
{
- return o.ToDictionary(ignoreProperties.Select(e => o.GetPropertyInfo(e)).Select(propInfo => propInfo.Name).ToArray());
+ return o?.ToDictionary(ignoreProperties.Select(e => o.GetPropertyInfo(e)).Select(propInfo => propInfo.Name).ToArray());
}
///
@@ -521,7 +521,7 @@ namespace Umbraco.Extensions
- internal static string ToDebugString(this object obj, int levels = 0)
+ internal static string? ToDebugString(this object? obj, int levels = 0)
{
if (obj == null) return "{null}";
try
@@ -589,7 +589,7 @@ namespace Umbraco.Extensions
///
///
///
- internal static Attempt TryConvertToXmlString(this object value, Type type)
+ internal static Attempt TryConvertToXmlString(this object value, Type type)
{
try
{
@@ -598,7 +598,7 @@ namespace Umbraco.Extensions
}
catch (NotSupportedException ex)
{
- return Attempt.Fail(ex);
+ return Attempt.Fail(ex);
}
}
@@ -608,7 +608,7 @@ namespace Umbraco.Extensions
///
/// The Type can only be a primitive type or Guid and byte[] otherwise an exception is thrown
///
- public static string ToXmlString(this object value, Type type)
+ public static string? ToXmlString(this object value, Type type)
{
if (value == null) return string.Empty;
if (type == typeof(string)) return (value.ToString().IsNullOrWhiteSpace() ? "" : value.ToString());
@@ -640,12 +640,12 @@ namespace Umbraco.Extensions
///
///
///
- public static string ToXmlString(this object value)
+ public static string? ToXmlString(this object value)
{
return value.ToXmlString(typeof (T));
}
- private static string GetEnumPropertyDebugString(object enumItem, int levels)
+ private static string? GetEnumPropertyDebugString(object enumItem, int levels)
{
try
{
@@ -657,7 +657,7 @@ namespace Umbraco.Extensions
}
}
- private static string GetPropertyDebugString(PropertyInfo propertyInfo, object obj, int levels)
+ private static string? GetPropertyDebugString(PropertyInfo propertyInfo, object obj, int levels)
{
try
{
@@ -683,7 +683,7 @@ namespace Umbraco.Extensions
// gets a converter for source, that can convert to target, or null if none exists
[MethodImpl(MethodImplOptions.AggressiveInlining)]
- private static TypeConverter GetCachedSourceTypeConverter(Type source, Type target)
+ private static TypeConverter? GetCachedSourceTypeConverter(Type source, Type target)
{
var key = new CompositeTypeTypeKey(source, target);
@@ -698,12 +698,13 @@ namespace Umbraco.Extensions
return InputTypeConverterCache[key] = converter;
}
- return InputTypeConverterCache[key] = null;
+ InputTypeConverterCache[key] = null;
+ return null;
}
// gets a converter for target, that can convert from source, or null if none exists
[MethodImpl(MethodImplOptions.AggressiveInlining)]
- private static TypeConverter GetCachedTargetTypeConverter(Type source, Type target)
+ private static TypeConverter? GetCachedTargetTypeConverter(Type source, Type target)
{
var key = new CompositeTypeTypeKey(source, target);
@@ -718,12 +719,13 @@ namespace Umbraco.Extensions
return DestinationTypeConverterCache[key] = converter;
}
- return DestinationTypeConverterCache[key] = null;
+ DestinationTypeConverterCache[key] = null;
+ return null;
}
// gets the underlying type of a nullable type, or null if the type is not nullable
[MethodImpl(MethodImplOptions.AggressiveInlining)]
- private static Type GetCachedGenericNullableType(Type type)
+ private static Type? GetCachedGenericNullableType(Type type)
{
if (NullableGenericCache.TryGetValue(type, out var underlyingType))
{
@@ -732,11 +734,12 @@ namespace Umbraco.Extensions
if (type.GetGenericTypeDefinition() == typeof(Nullable<>))
{
- Type underlying = Nullable.GetUnderlyingType(type);
+ Type? underlying = Nullable.GetUnderlyingType(type);
return NullableGenericCache[type] = underlying;
}
- return NullableGenericCache[type] = null;
+ NullableGenericCache[type] = null;
+ return null;
}
// gets an IConvertible from source to target type, or null if none exists
diff --git a/src/Umbraco.Core/Extensions/PublishedContentExtensions.cs b/src/Umbraco.Core/Extensions/PublishedContentExtensions.cs
index b241316242..3f1b60fa13 100644
--- a/src/Umbraco.Core/Extensions/PublishedContentExtensions.cs
+++ b/src/Umbraco.Core/Extensions/PublishedContentExtensions.cs
@@ -523,7 +523,7 @@ namespace Umbraco.Extensions
/// The level.
/// The nearest (in down-top order) ancestor of the content, at a level lesser or equal to the specified level.
/// Does not consider the content itself. May return null .
- public static IPublishedContent Ancestor(this IPublishedContent content, int maxLevel)
+ public static IPublishedContent? Ancestor(this IPublishedContent content, int maxLevel)
{
return content.EnumerateAncestors(false).FirstOrDefault(x => x.Level <= maxLevel);
}
@@ -535,7 +535,7 @@ namespace Umbraco.Extensions
/// The content type alias.
/// The nearest (in down-top order) ancestor of the content, of the specified content type.
/// Does not consider the content itself. May return null .
- public static IPublishedContent Ancestor(this IPublishedContent content, string contentTypeAlias)
+ public static IPublishedContent? Ancestor(this IPublishedContent content, string contentTypeAlias)
{
return content.EnumerateAncestors(false).FirstOrDefault(x => x.ContentType.Alias.InvariantEquals(contentTypeAlias));
}
@@ -547,7 +547,7 @@ namespace Umbraco.Extensions
/// The content.
/// The nearest (in down-top order) ancestor of the content, of the specified content type.
/// Does not consider the content itself. May return null .
- public static T Ancestor(this IPublishedContent content)
+ public static T? Ancestor(this IPublishedContent content)
where T : class, IPublishedContent
{
return content.Ancestors().FirstOrDefault();
@@ -562,7 +562,7 @@ namespace Umbraco.Extensions
/// The ancestor of the content, at the specified level and of the specified content type.
/// Does not consider the content itself. If the ancestor at the specified level is
/// not of the specified type, returns null .
- public static T Ancestor(this IPublishedContent content, int maxLevel)
+ public static T? Ancestor(this IPublishedContent content, int maxLevel)
where T : class, IPublishedContent
{
return content.Ancestors(maxLevel).FirstOrDefault();
@@ -586,7 +586,7 @@ namespace Umbraco.Extensions
/// The level.
/// The content or its nearest (in down-top order) ancestor, at a level lesser or equal to the specified level.
/// May or may not return the content itself depending on its level. May return null .
- public static IPublishedContent AncestorOrSelf(this IPublishedContent content, int maxLevel)
+ public static IPublishedContent? AncestorOrSelf(this IPublishedContent content, int maxLevel)
{
return content.EnumerateAncestors(true).FirstOrDefault(x => x.Level <= maxLevel);
}
@@ -598,7 +598,7 @@ namespace Umbraco.Extensions
/// The content type.
/// The content or its nearest (in down-top order) ancestor, of the specified content type.
/// May or may not return the content itself depending on its content type. May return null .
- public static IPublishedContent AncestorOrSelf(this IPublishedContent content, string contentTypeAlias)
+ public static IPublishedContent? AncestorOrSelf(this IPublishedContent content, string contentTypeAlias)
{
return content.EnumerateAncestors(true).FirstOrDefault(x => x.ContentType.Alias.InvariantEquals(contentTypeAlias));
}
@@ -610,7 +610,7 @@ namespace Umbraco.Extensions
/// The content.
/// The content or its nearest (in down-top order) ancestor, of the specified content type.
/// May or may not return the content itself depending on its content type. May return null .
- public static T AncestorOrSelf(this IPublishedContent content)
+ public static T? AncestorOrSelf(this IPublishedContent content)
where T : class, IPublishedContent
{
return content.AncestorsOrSelf().FirstOrDefault();
@@ -623,7 +623,7 @@ namespace Umbraco.Extensions
/// The content.
/// The level.
///
- public static T AncestorOrSelf(this IPublishedContent content, int maxLevel)
+ public static T? AncestorOrSelf(this IPublishedContent content, int maxLevel)
where T : class, IPublishedContent
{
return content.AncestorsOrSelf(maxLevel).FirstOrDefault();
@@ -817,17 +817,17 @@ namespace Umbraco.Extensions
return content.DescendantsOrSelf(variationContextAccessor, level, culture).OfType();
}
- public static IPublishedContent Descendant(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string? culture = null)
+ public static IPublishedContent? Descendant(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string? culture = null)
{
return content.Children(variationContextAccessor, culture).FirstOrDefault();
}
- public static IPublishedContent Descendant(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, int level, string? culture = null)
+ public static IPublishedContent? Descendant(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, int level, string? culture = null)
{
return content.EnumerateDescendants(variationContextAccessor, false, culture).FirstOrDefault(x => x.Level == level);
}
- public static IPublishedContent DescendantOfType(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string contentTypeAlias, string? culture = null)
+ public static IPublishedContent? DescendantOfType(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string contentTypeAlias, string? culture = null)
{
return content.EnumerateDescendants(variationContextAccessor, false, culture).FirstOrDefault(x => x.ContentType.Alias.InvariantEquals(contentTypeAlias));
}
@@ -849,12 +849,12 @@ namespace Umbraco.Extensions
return content;
}
- public static IPublishedContent DescendantOrSelf(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, int level, string? culture = null)
+ public static IPublishedContent? DescendantOrSelf(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, int level, string? culture = null)
{
return content.EnumerateDescendants(variationContextAccessor, true, culture).FirstOrDefault(x => x.Level == level);
}
- public static IPublishedContent DescendantOrSelfOfType(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string contentTypeAlias, string? culture = null)
+ public static IPublishedContent? DescendantOrSelfOfType(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string contentTypeAlias, string? culture = null)
{
return content.EnumerateDescendants(variationContextAccessor, true, culture).FirstOrDefault(x => x.ContentType.Alias.InvariantEquals(contentTypeAlias));
}
@@ -978,7 +978,7 @@ namespace Umbraco.Extensions
return content.Children(variationContextAccessor, culture).OfType();
}
- public static IPublishedContent FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string? culture = null)
+ public static IPublishedContent? FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string? culture = null)
{
return content.Children(variationContextAccessor, culture).FirstOrDefault();
}
@@ -986,28 +986,28 @@ namespace Umbraco.Extensions
///
/// Gets the first child of the content, of a given content type.
///
- public static IPublishedContent FirstChildOfType(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string contentTypeAlias, string? culture = null)
+ public static IPublishedContent? FirstChildOfType(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string contentTypeAlias, string? culture = null)
{
return content.ChildrenOfType(variationContextAccessor, contentTypeAlias, culture).FirstOrDefault();
}
- public static IPublishedContent FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, Func predicate, string? culture = null)
+ public static IPublishedContent? FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, Func predicate, string? culture = null)
{
return content.Children(variationContextAccessor, predicate, culture).FirstOrDefault();
}
- public static IPublishedContent FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, Guid uniqueId, string? culture = null)
+ public static IPublishedContent? FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, Guid uniqueId, string? culture = null)
{
return content.Children(variationContextAccessor, x => x.Key == uniqueId, culture).FirstOrDefault();
}
- public static T FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string? culture = null)
+ public static T? FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, string? culture = null)
where T : class, IPublishedContent
{
return content.Children(variationContextAccessor, culture).FirstOrDefault();
}
- public static T FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, Func predicate, string? culture = null)
+ public static T? FirstChild(this IPublishedContent content, IVariationContextAccessor variationContextAccessor, Func predicate, string? culture = null)
where T : class, IPublishedContent
{
return content.Children(variationContextAccessor, culture).FirstOrDefault(predicate);
@@ -1149,7 +1149,7 @@ namespace Umbraco.Extensions
///
/// This is the same as calling with maxLevel set to 1.
///
- public static IPublishedContent Root(this IPublishedContent content)
+ public static IPublishedContent? Root(this IPublishedContent content)
{
return content.AncestorOrSelf(1);
}
@@ -1165,7 +1165,7 @@ namespace Umbraco.Extensions
///
/// This is the same as calling with maxLevel set to 1.
///
- public static T Root(this IPublishedContent content)
+ public static T? Root(this IPublishedContent content)
where T : class, IPublishedContent
{
return content.AncestorOrSelf(1);
diff --git a/src/Umbraco.Core/Extensions/PublishedPropertyExtension.cs b/src/Umbraco.Core/Extensions/PublishedPropertyExtension.cs
index f9bca6effd..903633e9e4 100644
--- a/src/Umbraco.Core/Extensions/PublishedPropertyExtension.cs
+++ b/src/Umbraco.Core/Extensions/PublishedPropertyExtension.cs
@@ -38,7 +38,7 @@ namespace Umbraco.Extensions
}
var valueConverted = value.TryConvertTo();
- if (valueConverted)
+ if (valueConverted.Success.HasValue && valueConverted.Success.Value)
{
return valueConverted.Result;
}
@@ -63,7 +63,7 @@ namespace Umbraco.Extensions
}
var noValueConverted = noValue.TryConvertTo();
- if (noValueConverted)
+ if (noValueConverted.Success.HasValue && noValueConverted.Success.Value)
{
return noValueConverted.Result;
}
diff --git a/src/Umbraco.Core/Extensions/StringExtensions.cs b/src/Umbraco.Core/Extensions/StringExtensions.cs
index 69ccda66d5..3202b3a253 100644
--- a/src/Umbraco.Core/Extensions/StringExtensions.cs
+++ b/src/Umbraco.Core/Extensions/StringExtensions.cs
@@ -43,7 +43,7 @@ namespace Umbraco.Extensions
{
var nodeIds = path.Split(Constants.CharArrays.Comma, StringSplitOptions.RemoveEmptyEntries)
.Select(x => int.TryParse(x, NumberStyles.Integer, CultureInfo.InvariantCulture, out var output) ? Attempt.Succeed(output) : Attempt.Fail())
- .Where(x => x.Success)
+ .Where(x => x.Success ?? false)
.Select(x=>x.Result)
.Reverse()
.ToArray();
@@ -393,7 +393,7 @@ namespace Umbraco.Extensions
/// The enum try parse.
[SuppressMessage("Microsoft.Design", "CA1031:DoNotCatchGeneralExceptionTypes", Justification = "By Design")]
[SuppressMessage("Microsoft.Design", "CA1021:AvoidOutParameters", MessageId = "2#", Justification = "By Design")]
- public static bool EnumTryParse(this string strType, bool ignoreCase, out T result)
+ public static bool EnumTryParse(this string strType, bool ignoreCase, out T? result)
{
try
{
@@ -498,7 +498,7 @@ namespace Umbraco.Extensions
///
///
///
- public static string FromUrlBase64(this string input)
+ public static string? FromUrlBase64(this string input)
{
if (input == null) throw new ArgumentNullException(nameof(input));
@@ -522,9 +522,9 @@ namespace Umbraco.Extensions
/// The format.
/// The args.
///
- public static string InvariantFormat(this string format, params object[] args)
+ public static string InvariantFormat(this string? format, params object?[] args)
{
- return String.Format(CultureInfo.InvariantCulture, format, args);
+ return string.Format(CultureInfo.InvariantCulture, format ?? string.Empty, args);
}
///
@@ -548,7 +548,7 @@ namespace Umbraco.Extensions
/// The compare.
/// The compare to.
///
- public static bool InvariantEquals(this string compare, string compareTo)
+ public static bool InvariantEquals(this string compare, string? compareTo)
{
return String.Equals(compare, compareTo, StringComparison.InvariantCultureIgnoreCase);
}
@@ -590,9 +590,9 @@ namespace Umbraco.Extensions
///
///
///
- public static T ParseInto(this string val)
+ public static T? ParseInto(this string val)
{
- return (T)val.ParseInto(typeof(T));
+ return (T?)val.ParseInto(typeof(T));
}
///
@@ -601,7 +601,7 @@ namespace Umbraco.Extensions
///
///
///
- public static object ParseInto(this string val, Type type)
+ public static object? ParseInto(this string val, Type type)
{
if (string.IsNullOrEmpty(val) == false)
{
@@ -641,10 +641,15 @@ namespace Umbraco.Extensions
/// Refers to itself
/// String with the hash type. See remarks section of the CryptoConfig Class in MSDN docs for a list of possible values.
/// The hashed string
- private static string GenerateHash(this string str, string hashType)
+ private static string GenerateHash(this string str, string? hashType)
{
+ HashAlgorithm? hasher = null;
//create an instance of the correct hashing provider based on the type passed in
- var hasher = HashAlgorithm.Create(hashType);
+ if (hashType is not null)
+ {
+ hasher = HashAlgorithm.Create(hashType);
+ }
+
if (hasher == null) throw new InvalidOperationException("No hashing type found by name " + hashType);
using (hasher)
{
@@ -1184,7 +1189,7 @@ namespace Umbraco.Extensions
{
algorithm.TransformBlock(namespaceBytes, 0, namespaceBytes.Length, null, 0);
algorithm.TransformFinalBlock(nameBytes, 0, nameBytes.Length);
- hash = algorithm.Hash;
+ hash = algorithm.Hash!;
}
// most bytes from the hash are copied straight to the bytes of the new GUID (steps 5-7, 9, 11-12)
@@ -1221,7 +1226,7 @@ namespace Umbraco.Extensions
///
/// Turns an null-or-whitespace string into a null string.
///
- public static string NullOrWhiteSpaceAsNull(this string text)
+ public static string? NullOrWhiteSpaceAsNull(this string text)
=> string.IsNullOrWhiteSpace(text) ? null : text;
@@ -1236,7 +1241,7 @@ namespace Umbraco.Extensions
return string.IsNullOrWhiteSpace(path) == false
&& path.IndexOfAny(Path.GetInvalidPathChars().ToArray()) == -1
&& Path.IsPathRooted(path)
- && Path.GetPathRoot(path).Equals(Path.DirectorySeparatorChar.ToString(), StringComparison.Ordinal) == false;
+ && Path.GetPathRoot(path)?.Equals(Path.DirectorySeparatorChar.ToString(), StringComparison.Ordinal) == false;
}
// FORMAT STRINGS
diff --git a/src/Umbraco.Core/Extensions/TypeExtensions.cs b/src/Umbraco.Core/Extensions/TypeExtensions.cs
index 67a6dd1dce..272a80a69e 100644
--- a/src/Umbraco.Core/Extensions/TypeExtensions.cs
+++ b/src/Umbraco.Core/Extensions/TypeExtensions.cs
@@ -15,14 +15,14 @@ namespace Umbraco.Extensions
{
public static class TypeExtensions
{
- public static object GetDefaultValue(this Type t)
+ public static object? GetDefaultValue(this Type t)
{
return t.IsValueType
? Activator.CreateInstance(t)
: null;
}
- internal static MethodInfo GetGenericMethod(this Type type, string name, params Type[] parameterTypes)
+ internal static MethodInfo? GetGenericMethod(this Type type, string name, params Type[] parameterTypes)
{
var methods = type.GetMethods().Where(method => method.Name == name);
@@ -75,12 +75,12 @@ namespace Umbraco.Extensions
return true;
}
- public static IEnumerable GetBaseTypes(this Type type, bool andSelf)
+ public static IEnumerable GetBaseTypes(this Type? type, bool andSelf)
{
if (andSelf)
yield return type;
- while ((type = type.BaseType) != null)
+ while ((type = type?.BaseType) != null)
yield return type;
}
@@ -121,7 +121,7 @@ namespace Umbraco.Extensions
///
public static bool IsOfGenericType(this Type type, Type genericType)
{
- Type[] args;
+ Type[]? args;
return type.TryGetGenericArguments(genericType, out args);
}
@@ -132,7 +132,7 @@ namespace Umbraco.Extensions
///
///
///
- public static bool TryGetGenericArguments(this Type type, Type genericType, out Type[] genericArgType)
+ public static bool TryGetGenericArguments(this Type type, Type genericType, out Type[]? genericArgType)
{
if (type == null)
{
@@ -147,7 +147,7 @@ namespace Umbraco.Extensions
throw new ArgumentException("genericType must be a generic type");
}
- Func checkGenericType = (@int, t) =>
+ Func checkGenericType = (@int, t) =>
{
if (@int.IsGenericType)
{
@@ -313,34 +313,34 @@ namespace Umbraco.Extensions
return typeof(TInterface).IsAssignableFrom(type);
}
- public static TAttribute FirstAttribute(this Type type)
+ public static TAttribute? FirstAttribute(this Type type)
{
return type.FirstAttribute(true);
}
- public static TAttribute FirstAttribute(this Type type, bool inherit)
+ public static TAttribute? FirstAttribute(this Type type, bool inherit)
{
var attrs = type.GetCustomAttributes(typeof(TAttribute), inherit);
- return (TAttribute)(attrs.Length > 0 ? attrs[0] : null);
+ return (TAttribute?)(attrs.Length > 0 ? attrs[0] : null);
}
- public static TAttribute FirstAttribute(this PropertyInfo propertyInfo)
+ public static TAttribute? FirstAttribute(this PropertyInfo propertyInfo)
{
return propertyInfo.FirstAttribute(true);
}
- public static TAttribute FirstAttribute(this PropertyInfo propertyInfo, bool inherit)
+ public static TAttribute? FirstAttribute(this PropertyInfo propertyInfo, bool inherit)
{
var attrs = propertyInfo.GetCustomAttributes(typeof(TAttribute), inherit);
- return (TAttribute)(attrs.Length > 0 ? attrs[0] : null);
+ return (TAttribute?)(attrs.Length > 0 ? attrs[0] : null);
}
- public static IEnumerable MultipleAttribute(this PropertyInfo propertyInfo)
+ public static IEnumerable? MultipleAttribute(this PropertyInfo propertyInfo)
{
return propertyInfo.MultipleAttribute(true);
}
- public static IEnumerable MultipleAttribute(this PropertyInfo propertyInfo, bool inherit)
+ public static IEnumerable? MultipleAttribute(this PropertyInfo propertyInfo, bool inherit)
{
var attrs = propertyInfo.GetCustomAttributes(typeof(TAttribute), inherit);
return (attrs.Length > 0 ? attrs.ToList().ConvertAll(input => (TAttribute)input) : null);
@@ -389,8 +389,8 @@ namespace Umbraco.Extensions
var t = c;
while (t != typeof(object))
{
- if (t.IsGenericType && t.GetGenericTypeDefinition() == type) return true;
- t = t.BaseType;
+ if (t is not null && t.IsGenericType && t.GetGenericTypeDefinition() == type) return true;
+ t = t?.BaseType;
}
}
@@ -403,7 +403,7 @@ namespace Umbraco.Extensions
///
/// the source type
///
- public static Type GetEnumeratedType(this Type type)
+ public static Type? GetEnumeratedType(this Type type)
{
if (typeof(IEnumerable).IsAssignableFrom(type) == false)
return null;
@@ -420,7 +420,7 @@ namespace Umbraco.Extensions
return null;
}
- public static T GetCustomAttribute(this Type type, bool inherit)
+ public static T? GetCustomAttribute(this Type type, bool inherit)
where T : Attribute
{
return type.GetCustomAttributes(inherit).SingleOrDefault();
diff --git a/src/Umbraco.Core/Extensions/UriExtensions.cs b/src/Umbraco.Core/Extensions/UriExtensions.cs
index 858069edcf..52adbc6b67 100644
--- a/src/Umbraco.Core/Extensions/UriExtensions.cs
+++ b/src/Umbraco.Core/Extensions/UriExtensions.cs
@@ -154,7 +154,7 @@ namespace Umbraco.Extensions
return new Uri(baseUri.GetLeftPart(UriPartial.Authority) + uri.GetSafeAbsolutePath() + uri.GetSafeQuery());
}
- static string GetSafeQuery(this Uri uri)
+ static string? GetSafeQuery(this Uri uri)
{
if (uri.IsAbsoluteUri)
return uri.Query;
diff --git a/src/Umbraco.Core/Extensions/WaitHandleExtensions.cs b/src/Umbraco.Core/Extensions/WaitHandleExtensions.cs
index 6058ef2974..5cb7639497 100644
--- a/src/Umbraco.Core/Extensions/WaitHandleExtensions.cs
+++ b/src/Umbraco.Core/Extensions/WaitHandleExtensions.cs
@@ -15,11 +15,11 @@ namespace Umbraco.Extensions
public static Task WaitOneAsync(this WaitHandle handle, int millisecondsTimeout = Timeout.Infinite)
{
- var tcs = new TaskCompletionSource();
+ var tcs = new TaskCompletionSource();
var callbackHandleInitLock = new object();
lock (callbackHandleInitLock)
{
- RegisteredWaitHandle callbackHandle = null;
+ RegisteredWaitHandle? callbackHandle = null;
// ReSharper disable once RedundantAssignment
callbackHandle = ThreadPool.RegisterWaitForSingleObject(
handle,
@@ -34,7 +34,7 @@ namespace Umbraco.Extensions
{
// ReSharper disable once PossibleNullReferenceException
// ReSharper disable once AccessToModifiedClosure
- callbackHandle.Unregister(null);
+ callbackHandle?.Unregister(null);
}
},
/*state:*/ null,
diff --git a/src/Umbraco.Core/Extensions/XmlExtensions.cs b/src/Umbraco.Core/Extensions/XmlExtensions.cs
index aa3fe25eef..423039a86a 100644
--- a/src/Umbraco.Core/Extensions/XmlExtensions.cs
+++ b/src/Umbraco.Core/Extensions/XmlExtensions.cs
@@ -35,7 +35,7 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNodeList SelectNodes(this XmlNode source, string expression, IEnumerable variables)
+ public static XmlNodeList? SelectNodes(this XmlNode source, string expression, IEnumerable? variables)
{
var av = variables == null ? null : variables.ToArray();
return SelectNodes(source, expression, av);
@@ -53,7 +53,7 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNodeList SelectNodes(this XmlNode source, XPathExpression expression, IEnumerable variables)
+ public static XmlNodeList? SelectNodes(this XmlNode source, XPathExpression expression, IEnumerable? variables)
{
var av = variables == null ? null : variables.ToArray();
return SelectNodes(source, expression, av);
@@ -71,12 +71,12 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNodeList SelectNodes(this XmlNode source, string expression, params XPathVariable[] variables)
+ public static XmlNodeList? SelectNodes(this XmlNode source, string? expression, params XPathVariable[]? variables)
{
if (variables == null || variables.Length == 0 || variables[0] == null)
- return source.SelectNodes(expression);
+ return source.SelectNodes(expression ?? "");
- var iterator = source.CreateNavigator().Select(expression, variables);
+ var iterator = source.CreateNavigator()?.Select(expression ?? "", variables);
return XmlNodeListFactory.CreateNodeList(iterator);
}
@@ -92,12 +92,12 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNodeList SelectNodes(this XmlNode source, XPathExpression expression, params XPathVariable[] variables)
+ public static XmlNodeList SelectNodes(this XmlNode source, XPathExpression expression, params XPathVariable[]? variables)
{
if (variables == null || variables.Length == 0 || variables[0] == null)
return source.SelectNodes(expression);
- var iterator = source.CreateNavigator().Select(expression, variables);
+ var iterator = source.CreateNavigator()?.Select(expression, variables);
return XmlNodeListFactory.CreateNodeList(iterator);
}
@@ -113,7 +113,7 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNode SelectSingleNode(this XmlNode source, string expression, IEnumerable variables)
+ public static XmlNode? SelectSingleNode(this XmlNode source, string expression, IEnumerable? variables)
{
var av = variables == null ? null : variables.ToArray();
return SelectSingleNode(source, expression, av);
@@ -131,7 +131,7 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNode SelectSingleNode(this XmlNode source, XPathExpression expression, IEnumerable variables)
+ public static XmlNode? SelectSingleNode(this XmlNode source, XPathExpression expression, IEnumerable? variables)
{
var av = variables == null ? null : variables.ToArray();
return SelectSingleNode(source, expression, av);
@@ -149,12 +149,12 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNode SelectSingleNode(this XmlNode source, string expression, params XPathVariable[] variables)
+ public static XmlNode? SelectSingleNode(this XmlNode source, string expression, params XPathVariable[]? variables)
{
if (variables == null || variables.Length == 0 || variables[0] == null)
return source.SelectSingleNode(expression);
- return SelectNodes(source, expression, variables).Cast().FirstOrDefault();
+ return SelectNodes(source, expression, variables)?.Cast().FirstOrDefault();
}
///
@@ -169,7 +169,7 @@ namespace Umbraco.Extensions
/// value which itself is null , then variables are ignored.
/// The XPath expression should reference variables as $var .
///
- public static XmlNode SelectSingleNode(this XmlNode source, XPathExpression expression, params XPathVariable[] variables)
+ public static XmlNode? SelectSingleNode(this XmlNode source, XPathExpression expression, params XPathVariable[]? variables)
{
if (variables == null || variables.Length == 0 || variables[0] == null)
return source.SelectSingleNode(expression);
@@ -211,7 +211,7 @@ namespace Umbraco.Extensions
/////
/////
/////
- public static XmlNode ToXmlElement(this XContainer xElement)
+ public static XmlNode? ToXmlElement(this XContainer xElement)
{
var xmlDocument = new XmlDocument();
using (var xmlReader = xElement.CreateReader())
@@ -235,7 +235,7 @@ namespace Umbraco.Extensions
}
}
- public static T RequiredAttributeValue(this XElement xml, string attributeName)
+ public static T? RequiredAttributeValue(this XElement xml, string attributeName)
{
if (xml == null)
{
@@ -247,14 +247,14 @@ namespace Umbraco.Extensions
throw new InvalidOperationException($"{attributeName} not found in xml");
}
- XAttribute attribute = xml.Attribute(attributeName);
+ XAttribute? attribute = xml.Attribute(attributeName);
if (attribute is null)
{
throw new InvalidOperationException($"{attributeName} not found in xml");
}
Attempt result = attribute.Value.TryConvertTo();
- if (result.Success)
+ if (result.Success.HasValue && result.Success.Value)
{
return result.Result;
}
@@ -262,7 +262,7 @@ namespace Umbraco.Extensions
throw new InvalidOperationException($"{attribute.Value} attribute value cannot be converted to {typeof(T)}");
}
- public static T AttributeValue(this XElement xml, string attributeName)
+ public static T? AttributeValue(this XElement xml, string attributeName)
{
if (xml == null) throw new ArgumentNullException("xml");
if (xml.HasAttributes == false) return default(T);
@@ -270,15 +270,15 @@ namespace Umbraco.Extensions
if (xml.Attribute(attributeName) == null)
return default(T);
- var val = xml.Attribute(attributeName).Value;
+ var val = xml.Attribute(attributeName)?.Value;
var result = val.TryConvertTo();
- if (result.Success)
+ if (result.Success.HasValue && result.Success.Value)
return result.Result;
return default(T);
}
- public static T AttributeValue(this XmlNode xml, string attributeName)
+ public static T? AttributeValue(this XmlNode xml, string attributeName)
{
if (xml == null) throw new ArgumentNullException("xml");
if (xml.Attributes == null) return default(T);
@@ -286,15 +286,15 @@ namespace Umbraco.Extensions
if (xml.Attributes[attributeName] == null)
return default(T);
- var val = xml.Attributes[attributeName].Value;
+ var val = xml.Attributes[attributeName]?.Value;
var result = val.TryConvertTo();
- if (result.Success)
+ if (result.Success.HasValue && result.Success.Value)
return result.Result;
return default(T);
}
- public static XElement GetXElement(this XmlNode node)
+ public static XElement? GetXElement(this XmlNode node)
{
XDocument xDoc = new XDocument();
using (XmlWriter xmlWriter = xDoc.CreateWriter())
@@ -302,7 +302,7 @@ namespace Umbraco.Extensions
return xDoc.Root;
}
- public static XmlNode GetXmlNode(this XContainer element)
+ public static XmlNode? GetXmlNode(this XContainer element)
{
using (var xmlReader = element.CreateReader())
{
@@ -312,9 +312,15 @@ namespace Umbraco.Extensions
}
}
- public static XmlNode GetXmlNode(this XContainer element, XmlDocument xmlDoc)
+ public static XmlNode? GetXmlNode(this XContainer element, XmlDocument xmlDoc)
{
- return xmlDoc.ImportNode(element.GetXmlNode(), true);
+ var node = element.GetXmlNode();
+ if (node is not null)
+ {
+ return xmlDoc.ImportNode(node, true);
+ }
+
+ return null;
}
// this exists because
diff --git a/src/Umbraco.Core/Xml/XmlNodeListFactory.cs b/src/Umbraco.Core/Xml/XmlNodeListFactory.cs
index b0ab0dd3be..29797fc59a 100644
--- a/src/Umbraco.Core/Xml/XmlNodeListFactory.cs
+++ b/src/Umbraco.Core/Xml/XmlNodeListFactory.cs
@@ -23,7 +23,7 @@ namespace Umbraco.Cms.Core.Xml
/// The underlying XML store used to issue the query must be
/// an object inheriting , such as
/// .
- public static XmlNodeList CreateNodeList(XPathNodeIterator iterator)
+ public static XmlNodeList CreateNodeList(XPathNodeIterator? iterator)
{
return new XmlNodeListIterator(iterator);
}
@@ -34,12 +34,12 @@ namespace Umbraco.Cms.Core.Xml
private class XmlNodeListIterator : XmlNodeList
{
- readonly XPathNodeIterator _iterator;
+ readonly XPathNodeIterator? _iterator;
readonly IList _nodes = new List();
- public XmlNodeListIterator(XPathNodeIterator iterator)
+ public XmlNodeListIterator(XPathNodeIterator? iterator)
{
- _iterator = iterator.Clone();
+ _iterator = iterator?.Clone();
}
public override System.Collections.IEnumerator GetEnumerator()
@@ -47,7 +47,7 @@ namespace Umbraco.Cms.Core.Xml
return new XmlNodeListEnumerator(this);
}
- public override XmlNode Item(int index)
+ public override XmlNode? Item(int index)
{
if (index >= _nodes.Count)
@@ -73,7 +73,7 @@ namespace Umbraco.Cms.Core.Xml
///
private void ReadToEnd()
{
- while (_iterator.MoveNext())
+ while (_iterator is not null && _iterator.MoveNext())
{
var node = _iterator.Current as IHasXmlNode;
// Check IHasXmlNode interface.
@@ -92,7 +92,7 @@ namespace Umbraco.Cms.Core.Xml
{
while (_nodes.Count <= to)
{
- if (_iterator.MoveNext())
+ if (_iterator is not null && _iterator.MoveNext())
{
var node = _iterator.Current as IHasXmlNode;
// Check IHasXmlNode interface.
@@ -159,7 +159,7 @@ namespace Umbraco.Cms.Core.Xml
return true;
}
- object System.Collections.IEnumerator.Current
+ object? System.Collections.IEnumerator.Current
{
get
{