1

I have this generic method:

        public void Send < TBiz, TEntity > (string serviceName, string pkName)
        where TEntity: class, IEntity
        where TBiz: class, BLL.Modules.INewSend 
        {
         var biz = DependencyFactory.Get < TBiz > ();
         var query = (biz.GetNotSent() as IEnumerable < TEntity > );
         NewSender < TBiz, TEntity > (serviceName, pkName, query);
        }

TEntity is my data model objects (I mean model of DB tables) and can be of any types (like cars, humans, flowers and so on) but all of them have the ID property. TEntity implements IEntity inteface. IEntity is an empty interface or can be an interface that has only ID implementation as below:

public interface IEntity
{
}

or

public interface IEntity {
 public int ID {
  get;
  set;
 }
}

TBiz is my business class that implements INewSend. INewSend is a simple interface that has 2 implementation:

public interface INewSend {
 void Send(long id, string userName);
 IEnumerable < IEntity > GetNotSent(); 
}

this code works fine but I am curious that in terms of Object Oriented Principles it is OK that TEntity class inherits the IEntity interface that is empty? I did this in order to pass different classes(all of these classes inherit the IEntity interface) to the Send method. The IEntity interface also can be an interface with an ID property but I think it does not change the question because the entities that implements this interface are in completely different types though all of them have the ID property.

Ondrej Tucny
  • 27,626
  • 6
  • 70
  • 90
A.Esdeki
  • 63
  • 7
  • 4
    There are reasons in either direction, making this question fairly opinion-based. From my perspective it´s fairly OK to have a marker-interface. – MakePeaceGreatAgain Feb 27 '20 at 09:24
  • 4
    Such interfaces are often called "*marker interfaces*" -- opinion is divided on whether they're a good thing. You should be able to find some different opinions by searching for that term – canton7 Feb 27 '20 at 09:25
  • 1
    Good question, except that it belongs to [Software engineering site](https://softwareengineering.stackexchange.com/) – jalsh Feb 27 '20 at 09:26
  • Annoyingly there's no option to vote to migrate to the Software Engineering SE site, so the only option is to vote to close as opinion-based. I think a question like this would be well-received on the Software Engineering SE site, though – canton7 Feb 27 '20 at 09:27
  • Marker interfaces are both good and bad depending on who you are, how you are using them, what your code reviewers like, and what day of the week it is on SO. I think it's more what your are doing with them, then a general rule – TheGeneral Feb 27 '20 at 09:32
  • 2
    This is not for SO, so I will leave a short answer in a comment. Yes marker-interface are common and are used all the time, but it's more common to use attributes for this. But for your IEntity it should have an Id because that's what an entity is a thing with an Id, it's probably better to use a different name if you don't want it to have an id. – Filip Cordas Feb 27 '20 at 09:33
  • 1
    The way you have it defined, anyone who implements ``INewSend` promises to be able to handle a list of entities that implement `IEntity`. Which gives them nothing to work with. The `IEntity` interface needs to expose enough for `Send` to do its job. Either that or you need another interface, e.g. `ISendable`. – John Wu Feb 27 '20 at 09:41

2 Answers2

3

in terms of Object Oriented Principles it is OK that TEntity class inherits the IEntity interface that is empty?

There are no OO principles that would say that having an empty interface / empty class / empty whatever else would be a bad or even prohibited thing.

From the OO perspective, interfaces and classes denote the (partial) identity of an object. Hence, and an interface does carry information by itself regardless it is or is not empty, i.e. it defines any members.

Using empty interfaces as so-called marker interface is a common practice, though there are other methods to represent the same intent, such as attributes, each of them having pros and cons. Unlike the validity of an empty interface from the OO perspective, which is a quite straightforward matter, whether to use marker interfaces or attributes in a particular scenario is opinion-based.

I did this in order to pass different classes(all of these classes inherit the IEntity interface) to the Send method.

In order to have a strongly-typed contract of the GetNotSent method, you'd have to provide at least some common-ancestor-like type anyway. Be it an interface (empty or not) or a common ancestor class is matter of your specific design.

The IEntity interface also can be an interface with an ID property but I think it does not change the question because the entities that implements this interface are in completely different types though all of them have the ID property.

The point of interface is to provide a view for “completely different types”. Hence, I'd try to specify out what are the common properties that have to be implemented by each class in order to “be an entity” and factor them out into the IEntity. That makes perfect sense. Then, the INewSend interface can make use of it and provide a more consistent contract:

public interface INewSend 
{
    void Send(IEntity entity, string userName); // pass entity instead of its ID
    IEnumerable <IEntity> GetNotSent(); 
}

_Note: For the sake of the example, I do assume that the id originally being passed into Send is an id of an entity.

Ondrej Tucny
  • 27,626
  • 6
  • 70
  • 90
0

It's ok, sometime I use an empty interface just to classify the entity.

KaMaHe
  • 413
  • 1
  • 7
  • 18