【C#】単体テスト

Visual Studio

公式としては、1プロジェクトに対応して1つの単体テストプロジェクトを推奨
以下のような、TargetProjectについて考える。
namespace TargetProject
{
  internal class InternalClz
  {
    public void PublicAdd(int a, int b) => a + b;
    internal void InternalAdd(int a, int b) => a + b;
    private void PrivateAdd(int a, int b) => a + b;
  }
}
対象のプロジェクトのソリューションで右クリック⇒[追加]⇒[新しいプロジェクト]⇒[MSTestテストプロジェクト] (※.NET Coreの場合)でプロジェクト(UnitTestProject)を作成

アクセス修飾子

上記のクラスはinternalなので、他のプロジェクトから呼び出すことが出来ない。
そこで、TargetProjectを以下のように修正する
#if DEBUG
using System.Runtime.CompilerServices;
[assembly: InternalVisibleTo("UnitTestProject")
#endif
namespace TargetProject
{
  internal class InternalClz
  {
    public void PublicAdd(int a, int b) => a + b;
    internal void InternalAdd(int a, int b) => a + b;
    private void PrivateAdd(int a, int b) => a + b;
  }
}
上記を追加することによって、Debug時に、対象のクラスをUnitTestProjectプロジェクトから呼び出すことが出来る

private

方法はありそうだが、今回は調査しない。
privateメソッドについては、要否の議論もあるが、自分は必要と思っている。
単体テストでの確認方法は、アクセス可能な他のメソッドからの確認で、カバー出来ないのならば不適切という方針がしっくりきた。

実際にテストしてみる

以下のメソッドを作成
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace UnitTestProject
{
  [TestClass()]
  public class InternalClzTests{
    InternalClz internalClz = new InternalClz();
    
    [TestMethod()]
    public void PublicAddTest()
    {
      Assert.AreEqual(internalClz.PublicAdd(3, 4), 7); // Assert.AreEqual(結果,期待値) ①
    }
    
    [TestMethod()]
    public void InternalAddTest()
    {
      Assert.AreEqual(internalClz.InternalAdd(3, 4), 7); // ②
      Assert.AreEqual(internalClz.InternalAdd(4, 4), 7); // ③
    }
  }
}
テストの簡単な実行方法は、対象のプロジェクトで右クリック⇒[テストの実行]
上記の場合③がエラーのため、×が表示される。(Assert.AreEqual failed, Expected:<7>.Actual:<8>