public static void ExecuteViaReflection_void___Should_execute_the_operation___When_called()
        {
            // Arrange
            var operation1Counter = 4;
            var operation2Counter = 10;

            var operation1 = new SiblingOperation1
            {
                ActionToRun = () => operation1Counter++,
            };

            var operation2 = new SiblingOperation2
            {
                ActionToRun = () => operation2Counter++,
            };

            var protocol = new SiblingOperationProtocol();

            // Act, Assert
            protocol.ExecuteViaReflection(operation1);
            operation1Counter.AsTest().Must().BeEqualTo(5);

            protocol.ExecuteViaReflection(operation2);
            operation2Counter.AsTest().Must().BeEqualTo(11);

            protocol.ExecuteViaReflection(operation1);
            operation1Counter.AsTest().Must().BeEqualTo(6);
        }
        public static void ExecuteViaReflection_TResult___Should_execute_the_operation___When_called()
        {
            // Arrange
            var operation1 = new SiblingOperation3
            {
                Value = 4,
            };

            var operation2 = new SiblingOperation4
            {
                Value = 6,
            };

            var operation3 = new SiblingOperation3
            {
                Value = 1,
            };

            var protocol = new SiblingOperationProtocol();

            // Act
            var actual1 = protocol.ExecuteViaReflection <int>(operation1);
            var actual2 = protocol.ExecuteViaReflection <int>(operation2);
            var actual3 = protocol.ExecuteViaReflection <int>(operation3);

            // Assert
            actual1.AsTest().Must().BeEqualTo(5);
            actual2.AsTest().Must().BeEqualTo(8);
            actual3.AsTest().Must().BeEqualTo(2);
        }
        public static void ExecuteViaReflection_void___Should_throw_ArgumentException___When_protocol_cannot_execute_operation()
        {
            // Arrange
            var operation = new DummyVoidOperation();

            var protocol1 = new ProtocolWithNoOperations();
            var protocol2 = new SiblingOperationProtocol();

            // Act
            var actual1 = Record.Exception(() => protocol1.ExecuteViaReflection(operation));
            var actual2 = Record.Exception(() => protocol2.ExecuteViaReflection(operation));

            // Assert
            actual1.AsTest().Must().BeOfType <ArgumentException>();
            actual1.Message.AsTest().Must().ContainString(Invariant($"The specified '{nameof(ProtocolExtensionsTest)}.{nameof(ProtocolWithNoOperations)}' protocol does not have a void Execute method with a single parameter that the specified '{nameof(ProtocolExtensionsTest)}.{nameof(DummyVoidOperation)}' operation is assignable to."));

            actual2.AsTest().Must().BeOfType <ArgumentException>();
            actual2.Message.AsTest().Must().ContainString(Invariant($"The specified '{nameof(ProtocolExtensionsTest)}.{nameof(SiblingOperationProtocol)}' protocol does not have a void Execute method with a single parameter that the specified '{nameof(ProtocolExtensionsTest)}.{nameof(DummyVoidOperation)}' operation is assignable to."));
        }