Single Responsibility Principle (SRP) - S.O.L.I.D. Framework
The S.O.L.I.D. Framework and its principles are an approach to deal with the most software design issues.Ā Robert C. Martin, or better known as Uncle Bob in the industry, created those principles in the 1990’s. In this and the next blog posts I am covering every single principle in its own dedicated post, starting with the Single Responsibility Principle (SRP) here.
The SRP simplified says “Every software module should have only one reason to change“.
What does this means?
It means that a class should only have one job to do and it should be related to a single purpose, butĀ a single class can have multiple methods and members and it’s not restricted to one single function. The complete opposite of the SRP would be an implemenation like an swiss army knife – a object who has all methods and functions in it and one change would effect all the other parts.
If we look at the following example within the AccountManager there are two methods. The first registers an account and calls the second method which will send an email. But the SendEmail Method has nothing to do with the Account in general – so there we have an violation of theĀ Single Responsibility Principle.
public class AccountManager { public void Register(string name, string email, string password) { Contract.Requires<ArgumentException>(!string.IsNullOrEmpty(name)); Contract.Requires<ArgumentException>(!string.IsNullOrEmpty(email)); Contract.Requires<ArgumentException>(!string.IsNullOrEmpty(password)); var account = new Account(name, email, password); SendEmail(new Email("[email protected]", email) { Subject = "Confirmation of your Registration." }); } public bool SendEmail(Email message) { _smtpClient.Send(message); } }
By moving the EmailService to its own class we can minimize theĀ responsibility of the AccountManager class to its origin – to manage the Account without any other methods orĀ responsibilities.
public class AccountManager { EmailService emailservice; public AccountManager(EmailService emailservice) { this.emailservice = emailservice; } public void Register(string name, string email, string password) { Contract.Requires<ArgumentException>(!string.IsNullOrEmpty(name)); Contract.Requires<ArgumentException>(!string.IsNullOrEmpty(email)); Contract.Requires<ArgumentException>(!string.IsNullOrEmpty(password)); var account = new Account(name, email, password); this.emailservice.SendEmail(new Email("[email protected]", email) { Subject = "Confirmation of your Registration." }); } } public class EmailService { SmtpClient smtpClient; public EmailService(SmtpClient smtpClient) { this.smtpClient = smtpClient; } public bool SendEmail(Email message) { smtpClient.Send(message); } }
This is an very easy way to show the meaning and implemenation of the SRP.