Search code examples
c#abstract-class

create logic in each method that derived from abstract class


I test to create a abstract class that send send email in 2 different ways, either by POP or Office 365. This is what I got so far...

        var ee = new Mailer(new PopMail("test"));
        ee.Execute();


abstract class EmailHandler
{
    public string Server = "smtp.server.com";
    public string Port = "25";
    public string Message;
    public MailMessage msg = new MailMessage();

    protected EmailHandler(string message)
    {
        Message = message;
    }

    public abstract void Send();
}

class PopMail : EmailHandler
{
    public PopMail(string message) : base(message)
    {
    }

    public override void Send()
    {
        Console.WriteLine("Send pop mail");
    }
}
class Office365Mail : EmailHandler
{
    public Office365Mail(string message) : base(message)
    {
    }

    public override void Send()
    {
        Console.WriteLine("Send Office 365 mail");
    }
}

class Mailer
{
    private EmailHandler _msg;
    public Mailer(EmailHandler msg)
    {
        _msg = msg;
    }

    public void Execute()
    {
        _msg.Send();
    }
}

My question is, should I create a new MailMessage in each public override void Send() for PopMail and Office365Mail or where do I the send mail functionality?


Solution

  • The consumer shouldn't care about whether he uses the Office365Mail or PopMail class. The reason you create the abstract class and the classes that inherit it is to hide the implementation from the consumer. Apart from instantiating it they shouldn't differ which makes it easy to switch from one to another.

    Using your example it could look like this:

    abstract class EmailHandler
    {
        //some properties that are used by all inherited classes
    
        public abstract void Send(MailMessage message);
    }
    
    
    class Office365Mail : EmailHandler
    {
        //possibly a constructor that takes o365 specific settings
    
        public override void Send(MailMessage message)
        {
            // code for sending message
        }
    }
    
    public record MailMessage
    {
        public string From { get; set; }
        public string To { get; set; }
        public string Subject { get; set; }
        public string Body { get; set; }
    }
    

    Now to implement the class in your code:

    EmailHandler mailClient = new Office365Mail();
    
    //as you see apart from instantiating it there's no difference in usage
    var message = new MailMessage()
    {
        From = "me@stackoverflow.com",
        To = "you@stackoverflow.com",
        Subject = "Hey",
        Body = "This is an example",
    };
    mailClient.Send(message);