0

I am a beginner to C# and I am getting this error Argument 1: Cannot convert from 'string' to 'System.Action'. I honestly do not know how to fix this. if you could help me please tell me what I should add to my code to fix this error. I am basically writing a Unit Test that will test if the code is working correctly (the code is supposed to throw an exception). This is my code:

Unit Test Project File:

[TestMethod]
    public void ExceptionTest()
    {
        var test = new JumpingCode();
        Assert.ThrowsException<ArgumentException>(test.EmptyValue(null));
    }

The Class File:

namespace Jumping
{
    public class JumpingCode
    {
      public string EmptyValue(string some)
      {
          if (string.IsNullOrEmpty(some))
          {
            throw new ArgumentException("Name Cannot be null or empty");
          }

          return "Hello World";
      }

   }
}

I am basically testing a random throw. The Unit Test file is the one throwing the error messages. The error messages are on this line Assert.ThrowsException<ArgumentException>(test.EmptyValue(null)) the test.EmptyValue(null)is the text that is underlined. I honestly have no idea what is the problem. I know I am doing something wrong but I just don't know what. I don't know if this will change anything but I have never wrote a unit test for an exception before.

2 Answers2

4

You're passing the result of EmptyValue (a string) to Assert.ThrowsException but this method expects an Action to be validated.

You have to change this

Assert.ThrowsException<ArgumentException>(test.EmptyValue(null));

by this

Assert.ThrowsException<ArgumentException>(() => test.EmptyValue(null));
Claudio Redi
  • 67,454
  • 15
  • 130
  • 155
  • Your amazing thank you very much. Can you please explain to me how and why this works now? – Jakub Gaweł Sep 07 '17 at 19:12
  • In your code, you're passing the return value of `EmpyValue` to your `Assert` method, which is a `string`. But `Assert` requires a `Action` delegate (method call) as a parameter, which this lambda expression creates. For more info, click [here](https://msdn.microsoft.com/de-de/library/system.action(v=vs.110).aspx) and [here](https://stackoverflow.com/questions/4934544/lambda-expression-vs-anonymous-methods). – jAC Sep 07 '17 at 19:19
  • Assert.ThrowsException<...> expects an 'Action' Delegate (which does not return a result). Your 'EmptyValue' method is not compatible with an 'Action' because it returns a string. By encapsulation the method call in a lambda expression that discards the return type, you are actually passing an 'Action' to the Assert method. – Johan Donne Sep 07 '17 at 19:19
  • @jAC: Johan provided some extra information, let me know if it's still unclear. – Claudio Redi Sep 07 '17 at 19:23
0

Assert.Throws returns the exception that's thrown which lets you assert on the exception

So in case no exception is thrown, or an exception of the wrong type is thrown, the first Assert Throws assertion will fail.

BUT if an exception of the correct type is thrown then you can now assert on the actual exception that you've saved in the variable.

You have to write it like this

var ex = Assert.Throws<ArgumentNullException>(() => foo.Bar(null));

So in your case

var ext = Assert.ThrowsException<ArgumentException>(() =>test.EmptyValue(null));
napi15
  • 2,354
  • 2
  • 31
  • 55