Unit Test: Internal oppure public

In questo post, ti voglio spiegare come utilizzare dei metodi internal invece di public nel tuo codice sorgente senza andare a complicare la fase di test.

Non voglio spendere troppe parole, quindi passiamo subito al codice spiegando come ho strutturato la soluzione ed i miei due progetti all’interno.

  • MyIdea
  • MyIdea.Test

Semplice, vero?

Internal vs Public

All’interno di “MyIdea” ho tutta la logica dell’intero progetto. Nelle seguenti righe vi mostro una classe/ metodo “fake” scritto per l’articolo corrente:

1
2
3
4
internal class MyIdeaFakeClass
{
    public bool DoNothing() { return true; }
}

MyIdeaFakeClass mi occorre esclusivamente nel progetto corrente. La mia idea resta quella di tenerla internal e non esporla col public.

Unit Test

Mantendo la mia teoria appena scritta mi trovo davanti un problema nell’attimo in cui vado a scrivere il primo unit test.

1
2
3
4
5
6
7
[Fact]
public void DoNothingTest()
{
    MyIdeaFakeClass item = new MyIdeaFakeClass();
    var result = item.DoNothing();
    Assert.Equal(true, result);
}

Il motivo risulta molto semplice:

SeverityCodeDescription
ErrorCS0122‘MyIdeaFakeClass’ is inaccessible due to its protection level

Ops …

❌ ‘MyIdeaFakeClass’ is inaccessible due to its protection level

Come posso risolverlo?

Soluzione

Per risolvere questo tipo di problema posso comportarmi in due modi:

  • cambiare da internal a public (pessima idea)
  • modificare il file del progetto

Lo scopo di questo post è quello di mostrarti la seconda opzione. A questo punto non dovrai fare altro che editare il csproj ed aggiungere le seguenti righe:

1
2
3
4
5
<ItemGroup>
  <AssemblyAttribute Include="System.Runtime.CompilerServices.InternalsVisibleTo">
    <_Parameter1>MyIdea.Test</_Parameter1>
  </AssemblyAttribute>
</ItemGroup>

Una volta fatta la modifica ed effettuato il salvataggio del file non sarai più bloccato dall’errore CS0122 come in precedenza.

♻️ Conoscevi questo trucco? Condividilo con amici!