diff --git a/dotnet/src/support/Events/EventFiringWebDriver.cs b/dotnet/src/support/Events/EventFiringWebDriver.cs index 974843dbce1e4..6ea8ebd24cc86 100644 --- a/dotnet/src/support/Events/EventFiringWebDriver.cs +++ b/dotnet/src/support/Events/EventFiringWebDriver.cs @@ -1322,7 +1322,7 @@ public TimeSpan PageLoad /// /// EventFiringWebElement allows you to have access to specific items that are found on the page /// - private class EventFiringWebElement : ITakesScreenshot, IWebElement, IWrapsElement, IWrapsDriver + private class EventFiringWebElement : ITakesScreenshot, IWebElement, IWrapsElement, IWrapsDriver, IEquatable { private readonly EventFiringWebDriver parentDriver; @@ -1761,17 +1761,22 @@ public Screenshot GetScreenshot() } /// - /// Determines whether the specified is equal to the current . + /// Determines whether the specified is equal to the current . /// - /// The to compare to the current . - /// if the specified is equal to the current ; otherwise, . - public override bool Equals(object obj) + /// The to compare to the current . + /// if the current is equal to the other parameter; otherwise, . + public override bool Equals(object? obj) { - if (obj is not IWebElement other) - { - return false; - } + return Equals(obj as IWebElement); + } + /// + /// Indicates whether the current is equal to another . + /// + /// An to compare with this . + /// if the current is equal to the parameter; otherwise, . + public bool Equals(IWebElement? other) + { if (other is IWrapsElement otherWrapper) { other = otherWrapper.WrappedElement; @@ -1793,7 +1798,7 @@ public override int GetHashCode() /// /// EventFiringShadowElement allows you to have access to specific shadow elements /// - private class EventFiringShadowRoot : ISearchContext, IWrapsDriver + private class EventFiringShadowRoot : ISearchContext, IWrapsDriver, IEquatable { private readonly EventFiringWebDriver parentDriver; @@ -1871,21 +1876,25 @@ public ReadOnlyCollection FindElements(By by) this.parentDriver.OnException(new WebDriverExceptionEventArgs(this.parentDriver, ex)); throw; } + } + /// + /// Determines whether the specified is equal to the current . + /// + /// The to compare to the current . + /// if the current is equal to the other parameter; otherwise, . + public override bool Equals(object? obj) + { + return Equals(obj as ISearchContext); } /// /// Determines whether the specified is equal to the current . /// - /// The to compare to the current . - /// if the specified is equal to the current ; otherwise, . - public override bool Equals(object obj) + /// The to compare to the current . + /// if the current is equal to the parameter; otherwise, . + public bool Equals(ISearchContext? other) { - if (obj is not ISearchContext other) - { - return false; - } - return WrappedSearchContext.Equals(other); } diff --git a/dotnet/src/webdriver/BiDi/BrowsingContext/BrowsingContext.cs b/dotnet/src/webdriver/BiDi/BrowsingContext/BrowsingContext.cs index add2a12b9c865..61328c73c444e 100644 --- a/dotnet/src/webdriver/BiDi/BrowsingContext/BrowsingContext.cs +++ b/dotnet/src/webdriver/BiDi/BrowsingContext/BrowsingContext.cs @@ -23,7 +23,7 @@ namespace OpenQA.Selenium.BiDi.BrowsingContext; -public sealed class BrowsingContext +public sealed class BrowsingContext : IEquatable { internal BrowsingContext(BiDi bidi, string id) { @@ -225,13 +225,16 @@ public Task OnNavigationCommittedAsync(Func public override bool Equals(object? obj) { - if (obj is BrowsingContext browsingContextObj) return browsingContextObj.Id == Id; + return Equals(obj as BrowsingContext); + } - return false; + public bool Equals(BrowsingContext? other) + { + return other is not null && string.Equals(Id, other.Id, StringComparison.Ordinal); } public override int GetHashCode() { - return Id.GetHashCode(); + return StringComparer.Ordinal.GetHashCode(Id); } } diff --git a/dotnet/src/webdriver/BiDi/Network/Collector.cs b/dotnet/src/webdriver/BiDi/Network/Collector.cs index 0a1f56a5064a5..2f97908e505d2 100644 --- a/dotnet/src/webdriver/BiDi/Network/Collector.cs +++ b/dotnet/src/webdriver/BiDi/Network/Collector.cs @@ -22,7 +22,7 @@ namespace OpenQA.Selenium.BiDi.Network; -public sealed class Collector : IAsyncDisposable +public sealed class Collector : IEquatable, IAsyncDisposable { private readonly BiDi _bidi; @@ -46,13 +46,16 @@ public async ValueTask DisposeAsync() public override bool Equals(object? obj) { - if (obj is Collector collectortObj) return collectortObj.Id == Id; + return Equals(obj as Collector); + } - return false; + public bool Equals(Collector? other) + { + return other is not null && string.Equals(Id, other.Id, StringComparison.Ordinal); } public override int GetHashCode() { - return Id.GetHashCode(); + return StringComparer.Ordinal.GetHashCode(Id); } } diff --git a/dotnet/src/webdriver/BiDi/Network/Intercept.cs b/dotnet/src/webdriver/BiDi/Network/Intercept.cs index c266f791efaa3..d1b6ebebd4600 100644 --- a/dotnet/src/webdriver/BiDi/Network/Intercept.cs +++ b/dotnet/src/webdriver/BiDi/Network/Intercept.cs @@ -24,7 +24,7 @@ namespace OpenQA.Selenium.BiDi.Network; -public sealed class Intercept : IAsyncDisposable +public sealed class Intercept : IEquatable, IAsyncDisposable { private readonly BiDi _bidi; @@ -112,13 +112,16 @@ public async ValueTask DisposeAsync() public override bool Equals(object? obj) { - if (obj is Intercept interceptObj) return interceptObj.Id == Id; + return Equals(obj as Intercept); + } - return false; + public bool Equals(Intercept? other) + { + return other is not null && string.Equals(Id, other.Id, StringComparison.Ordinal); } public override int GetHashCode() { - return Id.GetHashCode(); + return StringComparer.Ordinal.GetHashCode(Id); } } diff --git a/dotnet/src/webdriver/Cookie.cs b/dotnet/src/webdriver/Cookie.cs index 292757bf7652f..d625ee0e34ad6 100644 --- a/dotnet/src/webdriver/Cookie.cs +++ b/dotnet/src/webdriver/Cookie.cs @@ -30,7 +30,7 @@ namespace OpenQA.Selenium; /// Represents a cookie in the browser. /// [Serializable] -public class Cookie +public class Cookie : IEquatable { private readonly string cookieName; private readonly string cookieValue; @@ -330,32 +330,44 @@ public override string ToString() /// . public override bool Equals(object? obj) { - // Two cookies are equal if the name and value match - if (this == obj) - { - return true; - } + return Equals(obj as Cookie); + } - if (obj is not Cookie cookie) + /// + /// Indicates whether the current is equal to another . + /// + /// A to compare with this . + /// if the current is equal to the parameter; otherwise, . + /// Two cookies are equal if the and match. + public bool Equals(Cookie? other) + { + if (other is null) { return false; } - if (!this.cookieName.Equals(cookie.cookieName)) + if (ReferenceEquals(this, other)) { - return false; + return true; } - return string.Equals(this.cookieValue, cookie.cookieValue); + return string.Equals(this.cookieName, other.cookieName) + && string.Equals(this.cookieValue, other.cookieValue); } /// /// Serves as a hash function for a particular type. /// - /// A hash code for the current Object. + /// A hash code for the current , based on the and . public override int GetHashCode() { - return this.cookieName.GetHashCode(); + unchecked + { + int hash = 17; + hash = hash * 23 + this.cookieName.GetHashCode(); + hash = hash * 23 + this.cookieValue?.GetHashCode() ?? 0; + return hash; + } } private static string? StripPort(string? domain) diff --git a/dotnet/src/webdriver/InitializationScript.cs b/dotnet/src/webdriver/InitializationScript.cs index 6cf16079c68ac..ace8f0c03d890 100644 --- a/dotnet/src/webdriver/InitializationScript.cs +++ b/dotnet/src/webdriver/InitializationScript.cs @@ -27,7 +27,7 @@ namespace OpenQA.Selenium; /// /// Represents a JavaScript script that is loaded and run on every document load. /// -public class InitializationScript +public class InitializationScript : IEquatable { internal InitializationScript(string scriptId, string scriptName, string scriptSource) { @@ -59,7 +59,17 @@ internal InitializationScript(string scriptId, string scriptName, string scriptS /// if the current is equal to the other parameter; otherwise, . public override bool Equals(object? obj) { - return obj is InitializationScript other && this.ScriptId == other.ScriptId && this.ScriptName == other.ScriptName && this.ScriptSource == other.ScriptSource; + return Equals(obj as InitializationScript); + } + + /// + /// Indicates whether the current is equal to another of the same type. + /// + /// An to compare with this . + /// if the current is equal to the parameter; otherwise, . + public bool Equals(InitializationScript? other) + { + return other is not null && this.ScriptId == other.ScriptId && this.ScriptName == other.ScriptName && this.ScriptSource == other.ScriptSource; } /// diff --git a/dotnet/src/webdriver/Internal/Logging/ILogContext.cs b/dotnet/src/webdriver/Internal/Logging/ILogContext.cs index 24b90382ae7e7..38b6cbb399773 100644 --- a/dotnet/src/webdriver/Internal/Logging/ILogContext.cs +++ b/dotnet/src/webdriver/Internal/Logging/ILogContext.cs @@ -58,7 +58,7 @@ public interface ILogContext : IDisposable /// /// The specified logger instance to be checked. /// The specified log event level to be checked. - /// true if log messages emitting is enabled for the specified logger and log event level, otherwise false. + /// if log messages emitting is enabled for the specified logger and log event level, otherwise . internal bool IsEnabled(ILogger logger, LogEventLevel level); /// diff --git a/dotnet/src/webdriver/Internal/Logging/ILogger.cs b/dotnet/src/webdriver/Internal/Logging/ILogger.cs index c049a31cc820e..6a0b3de5a5a09 100644 --- a/dotnet/src/webdriver/Internal/Logging/ILogger.cs +++ b/dotnet/src/webdriver/Internal/Logging/ILogger.cs @@ -70,6 +70,6 @@ internal interface ILogger /// Checks whether logs emitting is enabled for this logger and a log event level. /// /// The specified log event level to be checked. - /// true if log messages emitting is enabled for the specified log event level, otherwise false. + /// if log messages emitting is enabled for the specified log event level, otherwise . bool IsEnabled(LogEventLevel level); } diff --git a/dotnet/src/webdriver/Remote/DesiredCapabilities.cs b/dotnet/src/webdriver/Remote/DesiredCapabilities.cs index e8990d39028c0..ef7d15797af84 100644 --- a/dotnet/src/webdriver/Remote/DesiredCapabilities.cs +++ b/dotnet/src/webdriver/Remote/DesiredCapabilities.cs @@ -28,7 +28,7 @@ namespace OpenQA.Selenium.Remote; /// /// Internal class to specify the requested capabilities of the browser for . /// -internal class DesiredCapabilities : IWritableCapabilities, IHasCapabilitiesDictionary +internal class DesiredCapabilities : IWritableCapabilities, IHasCapabilitiesDictionary, IEquatable { private readonly Dictionary capabilities = new Dictionary(); @@ -229,9 +229,9 @@ public void SetCapability(string capability, object capabilityValue) public override int GetHashCode() { int result; - result = this.BrowserName != null ? this.BrowserName.GetHashCode() : 0; - result = (31 * result) + (this.Version != null ? this.Version.GetHashCode() : 0); - result = (31 * result) + (this.Platform != null ? this.Platform.GetHashCode() : 0); + result = this.BrowserName?.GetHashCode() ?? 0; + result = (31 * result) + (this.Version?.GetHashCode() ?? 0); + result = (31 * result) + (this.Platform?.GetHashCode() ?? 0); return result; } @@ -245,23 +245,33 @@ public override string ToString() } /// - /// Compare two DesiredCapabilities and will return either true or false + /// Indicates whether the current is equal to another . /// - /// DesiredCapabilities you wish to compare - /// true if they are the same or false if they are not + /// you wish to compare. + /// if the current is equal to the other parameter; otherwise, . public override bool Equals(object? obj) { - if (this == obj) + return Equals(obj as DesiredCapabilities); + } + + /// + /// Indicates whether the current is equal to another . + /// + /// An to compare with this . + /// if the current is equal to the parameter; otherwise, . + public bool Equals(DesiredCapabilities? other) + { + if (other is null) { - return true; + return false; } - if (obj is not DesiredCapabilities other) + if (ReferenceEquals(this, other)) { - return false; + return true; } - if (this.BrowserName != null ? this.BrowserName != other.BrowserName : other.BrowserName != null) + if (this.BrowserName != other.BrowserName) { return false; } @@ -271,7 +281,7 @@ public override bool Equals(object? obj) return false; } - if (this.Version != null ? this.Version != other.Version : other.Version != null) + if (this.Version != other.Version) { return false; } diff --git a/dotnet/src/webdriver/Remote/ReadOnlyDesiredCapabilities.cs b/dotnet/src/webdriver/Remote/ReadOnlyDesiredCapabilities.cs index 40db2fb515b83..cf8e574a2e435 100644 --- a/dotnet/src/webdriver/Remote/ReadOnlyDesiredCapabilities.cs +++ b/dotnet/src/webdriver/Remote/ReadOnlyDesiredCapabilities.cs @@ -178,9 +178,9 @@ public IDictionary ToDictionary() public override int GetHashCode() { int result; - result = this.BrowserName != null ? this.BrowserName.GetHashCode() : 0; - result = (31 * result) + (this.Version != null ? this.Version.GetHashCode() : 0); - result = (31 * result) + (this.Platform != null ? this.Platform.GetHashCode() : 0); + result = this.BrowserName?.GetHashCode() ?? 0; + result = (31 * result) + (this.Version?.GetHashCode() ?? 0); + result = (31 * result) + (this.Platform?.GetHashCode() ?? 0); return result; } diff --git a/dotnet/src/webdriver/SessionId.cs b/dotnet/src/webdriver/SessionId.cs index dc94a67823fc5..1379bfdb88cf0 100644 --- a/dotnet/src/webdriver/SessionId.cs +++ b/dotnet/src/webdriver/SessionId.cs @@ -24,7 +24,7 @@ namespace OpenQA.Selenium; /// /// Provides a mechanism for maintaining a session for a test /// -public class SessionId +public class SessionId : IEquatable { private readonly string sessionOpaqueKey; @@ -63,6 +63,16 @@ public override int GetHashCode() /// if the values are equal; otherwise, . public override bool Equals(object? obj) { - return obj is SessionId otherSession && this.sessionOpaqueKey.Equals(otherSession.sessionOpaqueKey); + return Equals(obj as SessionId); + } + + /// + /// Indicates whether the current session ID value is the same as . + /// + /// The session to compare to. + /// if the values are equal; otherwise, . + public bool Equals(SessionId? other) + { + return other is not null && string.Equals(this.sessionOpaqueKey, other.sessionOpaqueKey); } } diff --git a/dotnet/src/webdriver/WebElement.cs b/dotnet/src/webdriver/WebElement.cs index f54f510c701a1..144c90f4d2401 100644 --- a/dotnet/src/webdriver/WebElement.cs +++ b/dotnet/src/webdriver/WebElement.cs @@ -33,7 +33,7 @@ namespace OpenQA.Selenium; /// /// A base class representing an HTML element on a page. /// -public class WebElement : IWebElement, IFindsElement, IWrapsDriver, ILocatable, ITakesScreenshot, IWebDriverObjectReference +public class WebElement : IWebElement, IFindsElement, IWrapsDriver, ILocatable, ITakesScreenshot, IWebDriverObjectReference, IEquatable { /// /// The property name that represents a web element in the wire protocol. @@ -652,18 +652,24 @@ public override int GetHashCode() } /// - /// Compares if two elements are equal + /// Indicates whether the current is equal to another object. /// - /// Object to compare against - /// A boolean if it is equal or not + /// An object to compare with this . + /// if the current is equal to the other parameter; otherwise, . public override bool Equals(object? obj) { - if (obj is not IWebElement other) - { - return false; - } + return Equals(obj as IWebElement); + } - if (obj is IWrapsElement objAsWrapsElement) + /// + /// Indicates whether the current is equal to another . + /// + /// An to compare with this . + /// if the current is equal to the parameter; otherwise, . + /// This method only returns if is or wraps a . + public bool Equals(IWebElement? other) + { + if (other is IWrapsElement objAsWrapsElement) { other = objAsWrapsElement.WrappedElement; }