c_pattle Posted March 25, 2011 Share Posted March 25, 2011 I'm having a bit of trouble using composition. I have a function in a class that uses composition. Here is that function. function emailDetails() { $this->to = "hello@example.com"; $this->subject = "Login Details"; $this->message = "Here are your login details"; return new emailClass($this); } Then in the "emailClass" the __construct function looks like this. function __construct(&$user){ $this->user=&$user; $this->to = $this->user->to; $this->from = "someone@example.com"; $this->subject = $this->user->subject; $this->message = $this->user->message; } This all works fine but my problem is that I then can't use the "emailClass" on it's own because it requires an instance of a class to be passed to it in it's construct. Is this a poor case of design on my part? Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/ Share on other sites More sharing options...
KevinM1 Posted March 26, 2011 Share Posted March 26, 2011 Well, first, if you're using PHP 5 you don't need to pass the User instance by reference. Objects are automatically passed by reference. But, yeah, your design is messed up. Your Email class shouldn't require a User to work, right? Logically, email is a utility service. It should be able to be used throughout your system. This is one of the reasons why I suggested turning it into a static class (all methods marked as static) in your previous thread on this subject. If you're determined to use composition, it makes more sense for the User to contain the Email. Why? Because it's the User which depends on the Email functionality being present. Email is a component (hence composition) of the User. Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/#findComment-1192351 Share on other sites More sharing options...
ignace Posted March 26, 2011 Share Posted March 26, 2011 Your design is FUBAR! You are assigning Email properties to your User. In DDD, when you have 2 objects that should work together, but passing either object to the other is awkward, use a Service. I'm not for the make all Email methods static approach as it creates a hard dependency between either User and Email or vice versa. Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/#findComment-1192471 Share on other sites More sharing options...
KevinM1 Posted March 26, 2011 Share Posted March 26, 2011 Can you give a code example of a Service? Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/#findComment-1192559 Share on other sites More sharing options...
ignace Posted March 26, 2011 Share Posted March 26, 2011 class PostOfficeService { public function send(Email $email, User $to) { $email->addTo($to->getEmailAddress()); $email->send(); } } Neither User nor Email now need to know about the other, providing greater flexibility in your design. Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/#findComment-1192651 Share on other sites More sharing options...
KevinM1 Posted March 27, 2011 Share Posted March 27, 2011 Ah, nice. Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/#findComment-1192711 Share on other sites More sharing options...
ignace Posted March 27, 2011 Share Posted March 27, 2011 Scratch that. The example is quiet lame, but the intention should be clear. Remove the dependency between either objects (Model:User and Infrastructure:Email). Quote Link to comment https://forums.phpfreaks.com/topic/231738-php-composition/#findComment-1192790 Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.