public class Entity {
public void Foo() { ... }
internal void Bar() { ... }
}
を考えてみましょう。今、このクラスをテストで(このアセンブリと他のアセンブリの両方で)模擬するためのインターフェイスを作成したいと思います。コードを次のように書き換えます。
public interface IEntity {
void Foo();
}
internal class Entity : IEntity {
public void Foo() { ... }
public void Bar() { ... }
}
ただし、これは別の問題を引き起こします。同じアセンブリ内の別の方法でクラスを使用する場合、私はもうBar
を呼び出すことはできません。
public class OtherClass {
public void SomeMethod(IEntity entity) {
entity.Bar(); // error!
}
}
このようなコードを書き換える:
public class OtherClass {
public void SomeMethod(IEntity entity) {
(entity as Entity).Bar(); // error in test!
}
}
トリガーユニットテストでエラーをトリガするSomeMethod
。同じアセンブリ内でinternal
のメソッドを引き続き使用できるようにコードを書き直すにはどうすればよいですか?パブリックメンバーのみを他のアセンブリに公開することはできますか?
更新:クラスOtherClass
は、直接ユーザーに公開されていないEntity
クラスの内部、上で動作する必要があるユーティリティクラスです。ただし、このクラス自体はユーザーに公開されているため、間接的にはEntity
の内部にアクセスできます。 SomeMethod
は、ユーザーがEntity
オブジェクトの内部状態を壊さないようにするために必要なチェックを実行するため、これが望ましいです。
インターフェイスを作成する代わりにメソッドを仮想にするのはなぜですか? – adrianm
@adrianm:私はまた、ユーザーのための明確なインターフェースを必要とするので、プライベート/内部メンバーと実装が混在することはありません。また、私はすべての依存プロジェクトを再構築することなく、将来的には別の実装を提供できるようにしたいと考えています。しかし、内部メンバーを扱うときに作成するすべての困難を考慮して、私は上記の利点にもかかわらずこのオプションを選択するかもしれません。 –