开发者

C# Best Practices: Unit Testing code that refers to utilizes other methods?

I have the following code:

    public static String GetHashString(this HashAlgorithm algorithm, Stream inputStream)
    {
        if (algorithm == null)
            throw new ArgumentNullError("algorithm");

        if (inputStream == null)
            throw new ArgumentNullError("inpu开发者_运维知识库tStream");

        Byte[] bytes = algorithm.ComputeHash(inputStream);

        //Convert the bytes into a hash string
        String result = ...;
        return result;
    }

I'm wondering a couple of things:

  1. Looking at the Microsoft.NET4 HashAlgorithm.ComputeHash(Stream inputStream) method I can see that there is an exception that could come back. Is it a best practice in this situation to wrap the line Byte[] bytes = algoirthm.ComputeHash(inputStream) with a try-catch block? I ask because it seems to me that if that line throws an exception I can let calls to my extension handle the error catching. Or, is it supposed to be try-catch wrapped with a simple throw.

  2. Also, when unit testing, do I unit test for ALL possible exceptions, including ones that could come from other method? Particularly in this case... is it best practice? In this situation I would only need to expect an ObjectDisposeException. But I'm wondering about situations where I call a method that could throw back 10 different exceptions. Since I'm not really changing my output based on these exceptions, I don't think it's necessary to unit test all different types of failures that lead to the same result. Am I right for thinking this?

  3. And lastly, I wonder if it's necessary to even check for inputStream being null if the HashAlgorithm.computeHash(Stream inputStream) method doesn't even do so.


remember that you should test your code and not the .NET Framework,

I would not put Byte[] bytes = algoirthm.ComputeHash(inputStream) in a try-catch block, the code who is calling your method will have to handle that.

When unit testing you could test some use case and make sure that with valid input no exceptions are thrown and with invalid input the excepted exceptions are thown.

I think your code is ok and exactly because .NET throws an exception if inputStream is null, you are doing this check and throwing ArgumentNullException if the calling code passes a null inputStream

Davide.


When unit testing this method, you want to ensure that given valid (correct) input you are getting correct (expected) output. You can't possibly handle every situation, so just handle the ones that are important and are likely to occur. You should handle invalid input gracefully (i.e. like when you threw exceptions for null input values) and test how your method handles invalid input.


  1. Do a try...catch only if you want to treat the exception somehow (even if that means throwing a new exception - but use the innerException parameter in that case). If there is nothing you can do in case of an exception, there is no need use it.
  2. To start thinking of every possible way some piece of code can go wrong is the way to madness. You must test all possible successful executions, you should test the most common errors, but sometimes you just can't test every possible situation. Use your own judgment.
  3. If it is impossible for a .NET method to return null, I guess it is ok to not test that possibility. BTW some tools (like ReSharper) could help you with that kind of decision.

Still about item 3, that kind of test you're doing is a precondition, and that style of programming is called Design by Contract. There is a new .NET framework that helps defining preconditions, postconditions and invariants - I guess you should take a look at it:

DevLabs: Code Contracts

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜