Subscriptions Notifications App: Create a PHP app that reads subscriber list from a database and sends them a notification.
The Project history follows is as follows. Each step is represented by the corresponding v-tag in git i.e. 1 is v1, 2 is v2 and so on.
- Procedural code:
- send_mail() function sends mail to senders
- Object-oriented code:
- Create a Mailer class to send mail**
- Create constructor to initialize smtp, host and port details
- Move the logging logic in send_mail to sendMail() method of Mailer class
- Move mailer class to src folder for psr-4 standardizing
- Add autoloading code in composer.json
- Create src/Mailer.php and move the Mailer class to it
- Initialize and use Mailer class in app.php
- Create SubscriberManager class:
- Initialize PDO in constructor
- Keep the application logic in notifySubsriber() method
- Application logic: get subscriber and call Mailer->sendMail()
- Create a Mailer class to send mail**
- Move config to config.php:
- Create config.php and Move mailer config and DSN to configuration
- Require config.php in app.php
- Pass config to objects
- Remove config from SubscriberManager
- Challenges:
- SubscriberManager needs to know the implementation details of Mailer
- Can't mock test SubscriberManager
- This is where the concept of DI comes in
- Use constructor DI**
- Move Instantiation of PDO and Mailer from SubscriberManager.php to app.php and pass both to sendMail() method.
- This allows SubscriberManager to no more be concerned with the instantiation logic of Mailer.
- Can be unit tested by passing mock PDO & Mailer objects to constructor.
- Switch to method DI
- Move $mailer & $pdo injection from constructor to method
- Remove constructor and protected $mailer and $pdo from SubscriberManager
- Switch back to constructor DI
- Talk about services and service container.
- Use pimple container:
- Use composer to add pimple/pimple to project: https://packagist.org/packages/pimple/pimple
- Add PDO, Mailer & SubscriberManager services to container. (Syntax from above link)
- Add config to container in config.php and use them in app.php for service instantiation
- Move services to a separate file:
- Move all services to service.php and include it in app.php
- Extra: Add a Notifier interface