Page 1 of 2 12 Last
  • Jump to page:
    #1
  1. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175

    Catchable fatal error: Argument 1 passed to A::__construct() must implement interface


    Hi;

    I am at the edge of getting in to containers, still need to clarify s few things

    1. Is code 1 considered a good design or still sucking?
    2. Code 1 is much longer than code 2. Is it preferred to have longer code with no dependencies rather than shorter code with coupling?
    3. In code 1 I am still passing an instance of class B. Really what is the benefit of class B implementing some interface?
      If it does not implement the interface I get this the Catchable fatal error. What is so good about it? I understand and wrote this code and can apply this concept to any class couplings but don't really get the point of engaging an interface!
    4. Is this the main reason interfaces exist? To force some structure so the instance passed to another class must have that structure? Ehh, not really sure why making things more complex.
    5. Code 2 is much smaller and does exact same thing. Is coupling really that big disadvantage so we rather make the code twice larger, add files, eat beans etc?


    God bless America and Fiji


    Code 1
    PHP Code:
    <?php 
    class A
        
    {
            private 
    $method;
            private 
    $D;
            public function 
    __construct(D $D)
                {
                    
    $this->$D;
                    
    $this->method $this->D;
                }
            public function 
    pay($id)
                {
                    return 
    $this->method->foo($id);
                }
        }


    class 

        
    {
            public function 
    foo($arg)
                {
                    return 
    $this;
                }
        }

    class 
    implements D
        
    {
            public function 
    foo($arg)
                {
                    return 
    $this;
                }
        }    

    interface 

        
    {
            public function 
    foo($arg);
        }        

    $object = new A(new B);
    var_dump($object->pay(3400));    

    ?>


    Code 2

    PHP Code:
    <?php 
    class A
        
    {
            private 
    $method;
            public function 
    pay($id)
                {
                    
    $this->method = new B();
                    return 
    $this->method->foo($id);
                }
        }

    class 
    B
        
    {
            public function 
    foo($arg)
                {
                    return 
    $this;
                }
        }    

    $object = new A();
    var_dump($object->pay(3400));    
    ?>
  2. #2
  3. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    15,966
    Rep Power
    9615
    1. Depends what it's supposed to do. All I get from it is something paying something else.

    2. Length is a side-effect of the design, not something that should be considered in its own right. Short code may be too tightly coupled, longer code may be more flexible, and even longer code could be stupidly overcomplicated.

    3. The benefit is knowing for sure that the instance passed in is compatible with your code. Otherwise you don't know. The error is telling you that your code required a specific type of class/interface and that the code calling it violated that requirement.

    4. As a very brief description, yes. As for complexity, going with interfaces shows that you're considering the future rather than hacking out whatever code you can now to get it working. Six months down the road, if you discover that you need more than just the B class, refactoring your application is going to suck so much more than getting it right now.

    5. No, it does not do the exact same thing. It doesn't let me control who gets paid. It doesn't let me design my own class. It does not lend itself to testing. You might not care about those things now but hopefully you'll learn to.
  4. #3
  5. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Hi;


    Originally Posted by requinix
    5. It doesn't let me control who gets paid. It doesn't let me design my own class. It does not lend itself to testing.
    Do you see these limitations in code 1?


    Also I know I may not make sense but in code 1, is $object = new A(new B); avoidable?

    Kisses and hugs
    Last edited by English Breakfast Tea; May 7th, 2014 at 09:19 PM.
  6. #4
  7. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    15,966
    Rep Power
    9615
    Originally Posted by English Breakfast Tea
    Do you see these limitations in code 1?
    Nope. The first code allows me to pass in any particular "payee" that I want.
    - Who gets paid? Whichever class I decide.
    - Design my own class? I can do whatever I want... so long as it implements the D interface.
    - Lend itself to testing? Yes because (again) I can use whatever class I want, such as a class that logs calls to foo() so I can see what's happening.
  8. #5
  9. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Originally Posted by requinix
    Nope. The first code allows me to pass in any particular "payee" that I want.
    - Who gets paid? Whichever class I decide.
    - Design my own class? I can do whatever I want... so long as it implements the D interface.
    - Lend itself to testing? Yes because (again) I can use whatever class I want, such as a class that logs calls to foo() so I can see what's happening.

    See Requnix. I wrote both codes myself from scratch. I understand the concept. I think the next thing I need to learn is containers. What do you think about PHP-DI - The Dependency Injection Container for humans?

    Thank you and very curious about your strange taste in submissive Asian girl's avatars.
  10. #6
  11. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    15,966
    Rep Power
    9615
    Originally Posted by English Breakfast Tea
    I'm entirely the wrong person to ask for opinions of third-party libraries.

    Originally Posted by English Breakfast Tea
    Thank you and very curious about your strange taste in submissive Asian girl's avatars.
    Submissive? This one has 66 different personalities. The one I just retired was psychotic and extremely violent (but I don't blame you for not noticing the blood dripping from her mouth).
  12. #7
  13. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Originally Posted by requinix
    Submissive? This one has 66 different personalities. The one I just retired was psychotic and extremely violent (but I don't blame you for not noticing the blood dripping from her mouth).
    Come do a Vipasana course with me . Your avatars will change xo
  14. #8
  15. No Profile Picture
    Contributing User
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Dec 2004
    Posts
    3,082
    Rep Power
    379
    i think if he met you, few other things will change!
  16. #9
  17. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Originally Posted by paulh1983
    i think if he met you, few other things will change!
    What do you mean?

    Comments on this post

    • paulh1983 agrees : nothing, it was a joke.. :)
  18. #10
  19. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Originally Posted by requinix
    Length is a side-effect of the design, not something that should be considered in its own right. Short code may be too tightly coupled, longer code may be more flexible, and even longer code could be stupidly overcomplicated.

    Requinix 1 thing that concerns me is the way I instantiate these classes. I know you say it is correct design but t just doesn't look right.

    PHP Code:
    $object = new A(new B(new E())); 
    Which is 1 way of implementing this:


    bbc5f715bc2fccf674fbfe68d1ad1f2c390b71de96.png

    Yes the code is flexible and not coupled but is it really supposed to look like that? This kind of instantiating can get really messy. I am dealing with a code that has a lot more dependencies. I don't think its cool to write 5 lines of injection is it?

    Here is the whole lot.

    PHP Code:
    <?php 
    class A
        
    {
            private 
    $method;
            
            private 
    $D;

            public function 
    __construct(D $D)
                {
                    
    $this->$D;
                    
    $this->method $this->D;
                }
            public function 
    pay($id)
                {
                    return 
    $this->method->foo($id);
                }
        }


    class 
    implements D
        
    {
            private 
    $dependency;
            public function 
    __construct(E $E)
                {
                    
    $this->dependency $E;
                }
            public function 
    foo($arg)
                {
                    return 
    $this->dependency;
                }
        }

    class 
    implements D
        
    {
            public function 
    foo($arg)
                {
                    return 
    $this;
                }
        }    

    interface 

        
    {
            public function 
    foo($arg);
        }

    class 
    implements F
        
    {
            public function 
    __construct()
                {
                    return 
    $this;
                }
        }

    interface 
    F
        
    {
            public function 
    __construct();
        }        


    $object = new A(new B(new E()));
    var_dump($object->pay(3400));    

    ?>

    I checked Pimple as you said,,,same deal, lots of code. I like injection better really.
    PHP Code:
    $container = new Pimple();
    $container['oauth'] = function($c) {
        return new 
    OAuth();
    };
    $container['db'] = function($c) {
        return new 
    DB();
    };
    $container['tweet_service'] = function($c) {
        
    $twService = new TwitterService();
        
    $twService->setDB($c['db']);
        
    $twService->setOauth($c['oauth']);
        return 
    $twService;
    };
    $container['social_feeds'] = function($c) {
        
    $socialFeeds = new SocialFeeds();
        
    $socialFeeds->setTwitterService($c['tweet_service']);
        return 
    $socialFeeds;
    };
     
    $socialFeeds $container['social_feeds'];
    $socialFeeds->getSocialFeeds(); 


    My final goal is to fix this biatch:

    PHP Code:
    <?php
    class SendCampaign extends BaseController {
        public function 
    __construct()
            {
                
    $this->beforeFilter('login_check');    
            }
        public function 
    send($id)
            {
                
                
                
    //Set data
                
    $data['name'] = $name ucfirst(Input::get('name')); 
                
    $data['email'] = $email Input::get('email');
                
    $data['receiver'] = Input::get('email');
                
    $time_sent time();
                
                
    //Validate posted data
                
    $validator Validator::make(
                       array(
    'email' =>$email ),
                       array(
    'email' => array('required''email'))
                    );
                if (
    $validator->fails())
                    {
                       
    Session::put('campaign_sent''<p class="text-error">Invalid email address</p>');
                       return 
    Redirect::to('email');
                    }
                
                
    //Load campaign
                
    $results Campaign::find($id);
                
    $view_file $results->view_file;

                
    //Attach deals
                
                
    if(is_array(Input::get('deals')))
                    {
                        
    $in "(";
                        foreach(
    Input::get('deals') as $val)
                            {
                                
    $in .= $val.",";
                            }
                        
    $in substr($in0, -1);    
                        
    $in .= ")";    
                        echo 
    $in;

                        
    $data['deals']="";

                        
    $deals DB::select('SELECT  domain_deals.id AS DID,
                        domain_deals.title AS DT,
                        domain_deals.status AS DSTAT,
                        domain_deals.original_value AS OV,
                        domain_deals.end_date AS end_date,
                        domain_deals.deal_value AS DV
                        FROM domain_deals INNER JOIN
                        domain_business ON domain_business.id = domain_deals.business_id
                        WHERE domain_deals.id IN '
    .$in.' GROUP BY domain_deals.id
                                                '
    );


                        
    $data['deals'] .= "<table><tr>";
                        foreach(
    $deals as $val =>$row)
                            {
                                
    $seconds_left strtotime($row->end_date) - time();
                                
    $days_left floor($seconds_left/(3600*24));
                                if(
    $days_left<0){ $days_left 0;}
                                
    $discount round(($row->DV*100)/$row->OV);
                                
    $discount 100 $discount;
                                
    $data['deals'] .= "<td>
                                
                                    <table style = \"float:left; width:350px;\">
                                        <tr><td colspan = \"2\"><a href = \"http://www.domain.com.au/details/show/"
    .$row->DID."\"><img src = 'http://domain.com.au/uploads/".$row->DID.".jpg' width=\"250px\" height = \"250px\" style = \"-moz-border-radius: 10px; border-radius: 10px;\"></a></td></tr>
                                        <tr><td colspan = \"2\"><a style = \"; text-decoration:none;\" href = \"http://www.domain.com.au/details/show/"
    .$row->DID."\"><strong style = \"font-family:Arial; font-size:16px; text-decoration:none;\">".$row->DT."</strong></a></td></tr>
                                        <tr>
                                            <td colspan = \"2\" style=\"border-bottom:1px solid #cccccc\"><br /><strong style = \"color: #ED2930; margin:0; padding:0;
                                                font-family: Arial,Helvetica,sans-serif;
                                                font-size: 16px;
                                                font-weight: bold;\">$"
    .$row->DV."
                                                </strong>&nbsp;&nbsp;&nbsp;
                                                <strong style = \"color: #202020; margin:0; padding:0; text-decoration:line-through;
                                                font-family: Arial,Helvetica,sans-serif;
                                                font-size: 16px;
                                                font-weight: bold;\">$"
    .$row->OV."
                                                </strong><br /><br />
                                            </td>
                                        </tr>
                                        <tr>
                                            <td><br />
                                                <span style = \"color: #444444; margin:0; padding:0;
                                                font-family: Arial,Helvetica,sans-serif;
                                                font-size: 14px;\"><img src = \"http://domain.com.au/images/clock-image.png\">&nbsp;"
    .$days_left." days Left
                                                </span>&nbsp;&nbsp;&nbsp;
                                            </td>
                                            <td align = \"right;\">    
                                                <span style = \"color: #444444; 
                                                font-family: Arial,Helvetica,sans-serif;
                                                font-size: 14px;
                                                \"><img src = \"http://domain.com.au/images/voucher-image.png\">&nbsp;"
    .$discount."% discount
                                                </span>
                                            </td>
                                        </tr>


                                            </table>
                                                
                                            </td>"
    ;
                            }    
                        
    $data['deals'] .= "</tr></table>";    
                        
    //exit();
                        

                        
                    
    }
                else
                    {
                        
    $data['deals'] = "";
                    }        
                                                
                
    //echo $data['deals'];exit();    
                //Load sende'r signature details signature
                
    $sender_id Session::get('id');
                
    $sender_details Admin::find($sender_id);
                
    $data['sender_name'] = ucwords($sender_details->name);
                
    $data['sender_email'] = $sender_details->email;
                
    $data['position'] = $sender_details->position;
                
    $data['mobile'] = $sender_details->mobile;
                
    $data['phone'] = $sender_details->phone

                
    //Check if view exists
                
    if (!View::exists($view_file))
                    {
                         
    Session::put('campaign_sent''<p class="text-error">The email template you are trying to send does not exists!</p>');
                       return 
    Redirect::to('email');
                    }    
                
                
    //Send email
                
    Mail::send($view_file$data, function($message)
                    {
                        
    $message->to(Input::get('email'), Input::get('name'));
                        
    $message->from('support@domain.com''domain Support');
                        
    $message->cc('pmdg3@yahoo.com''Behnam');
                        
    $message->subject(Input::get('email_title'));
                    });
                
                
    //Save report   domain_campaign_sent table
                
    $CampaignReport = new CampaignReport;
                
    $CampaignReport->name $name;
                
    $CampaignReport->email $email;
                
    $CampaignReport->campaign_id $id;
                
    $CampaignReport->time_sent $time_sent;
                
    $CampaignReport->save();

                
                
                



                
                
    //If member already not in this mailing list 
                
    $results DB::select('select * from domain_individual_campaign_signup where email = ?', array($email));
                
                if(
    count($results)==0)
                    {
                        
    //Save new member
                        
    $CampaignSignup = new CampaignSignup;
                        
    $CampaignSignup->name $name;
                        
    $CampaignSignup->email $email;
                        
    $CampaignSignup->campaign_id $id;
                        
    $CampaignSignup->time_sent $time_sent;
                        
    $CampaignSignup->save();
                    }    

                
                
    //If member already not exists
                
    $results DB::select('select * from domain_mailinglist_member where email = ? AND mailing_list_id = ?', array(Input::get('email'), Input::get('mailinglist_id')));
                if(
    count($results)==0)
                    {
                        
    //Sign this user to domain_IC_MLG table //
                        
    $ICSML = new ICSML;
                        
    $ICSML->mailing_list_id Input::get('mailinglist_id');
                        
    $ICSML->email Input::get('email');
                        
    $ICSML->save();
                    }
                

                
    //Redirect 
                
    Session::put('campaign_sent''<p class="text-error">Campaign sent successfully</p>');
                return 
    Redirect::to('email');
            }    
    }
    I know Laravel takes care of all that but I like to know the rules rather than just using Lara. Made that mistake with CI.

    Thanks
  20. #11
  21. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    15,966
    Rep Power
    9615
    First, you asked me to choose between code using DI and code not using DI. I chose the one using it. I did not say you have you use that specific implementation of DI.

    Second, the new/new/new, the Pimple way, and the one from earlier I'm too lazy to scroll up, are all DI. The difference between them is the syntax to accomplish it. For places where there's only one or two dependencies the manual route is pretty easy, and certainly less work to set up, but if you're dealing with many then you probably want a framework to go with it. Pimple is one such framework, and if it does the things you need it to do then go for it.
  22. #12
  23. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Requnix what is your comment on making the flow chart first and then write the code? I accidentally thought I do a chart and now find it a lot more easier to understand and follow. Is it the right way to design code? First the charts and then the code? Is it how you do it?

    Thanks
  24. #13
  25. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    15,966
    Rep Power
    9615
    Do whatever works best for you. No, really. This is one of those questions that are not about how to Do It Right but about how to do it the best way for you. (It's a little different with teams, though, but that's more to do with documentation.)
    For some people it helps to have the flowchart first while other people think better when they're in the code. Though I personally don't really do flowcharts much - I can see it all in my head just fine thank you - basically I belong in the first group.
  26. #14
  27. A Change of Season
    Devshed Loyal (3000 - 3499 posts)

    Join Date
    Mar 2004
    Location
    Next Door
    Posts
    3,014
    Rep Power
    175
    Requnix, using interface like that is " Strategy Design Pattern"! I didn't know that!

    I wonder what would be the difference if I use an abstract class instead of an Interface. It could gonna explode my computer.
  28. #15
  29. Forgotten Moderator
    Devshed Supreme Being (6500+ posts)

    Join Date
    Mar 2007
    Location
    Washington, USA
    Posts
    15,966
    Rep Power
    9615
    Originally Posted by English Breakfast Tea
    Requnix, using interface like that is " Strategy Design Pattern"! I didn't know that!
    Bah. I stopped caring about the names a long time ago - there's a design pattern for, like, everything.

    Originally Posted by English Breakfast Tea
    I wonder what would be the difference if I use an abstract class instead of an Interface. It could gonna explode my computer.
    Interfaces are more flexible because you have complete freedom over the classes and inheritance. On the other hand abstract classes help a lot if you need an "interface" but all the implementations would have a lot of the same code and you don't want to have to copy that everywhere*.

    You know you don't have to choose, right? Por qué no los dos? Make an interface, reference that in the places that need it, make a (possibly abstract) base class for the interface kinda like it were the default implementation, then extend that base class for any additional work that you may need to do.

    * 5.4's traits are another, less OOP way of solving that particular problem.
    Last edited by requinix; May 10th, 2014 at 05:08 AM.
Page 1 of 2 12 Last
  • Jump to page:

IMN logo majestic logo threadwatch logo seochat tools logo