Smart actions

I think it would be more consistent to find the appropriate action if the action list returned was slight modified like the following :



<?php


   return array(


      'action1'=>'Action1',


      'action2'=>'Action2',


      'action3'=>array(


         'class'=>'Action3',


         'name1'=>'value1',


         'name2'=>'value2',


      ),


      'w1.'=>'Widget1',


      'w2.'=>'Widget2',


      'w3.' =>array(


         'class'=>'Widget2',


         'action11'=>array(


            'name'=>'value',


         ),


      ),


   );





thoughts ?

nz

Seems reasonable to me. Any other suggestions or comments?

What would the method signature need to be on the widget side ? and would it return a similar response ?

nz

public static function actions() { return array(…) }

Yes, the returning value is similar. I call it action provider. As a result, this can be any class that defines a static actions() method. An action provider can contain other providers by listing them in its actions(). So this is a recursive definition.

Cool, that looks like the best of both worlds.

So in theory then widgets should provide a "prefix" attribute that they will use when encoding the url for an action. So when a developer builds a widget, if this widget includes other widgets would they need to define that widgets prefix like  <com:Widget4 prefix="$this->prefix.'w4.'" /> ? or could the specify simply <com:Widget4 prefix="w4" /> and the encodeUrl method would automatically append the controllers prefix to the widgets prefix (so the action looks like w1.w4.action11 in either case) ?

So a request like "w1.w4.action11" looks up the w2's action provider actions list. which then will try to match the "w4.action11", causing it to look up w4's action provider action list which will then direct the response to "action11"

Does this make sense ?

nz

The developer needs to set the prefix when embedding another widget in a widget. It's too expensive to ask createUrl to do this work.

Yes, your interpretation about 'w2.w4.action11' is correct.

Also, when configuring actions in either controllers or widgets, the original action IDs (without the prefix) should be used.

Performance-wise, this approach seems to be optimal. While the method is still a bit twisted, I think it is perhaps the best we can do.

Excellent, looks like a plan.

thanks

nz

Well, you're here discussing the same thing I've asked in a neighboor topic.

This approach you came to doesn't count one aspect. It still requires to declare widget's actions in the controller as well as placing widgets in the view. Note that we have CViewController with no code behind, and this is my situation. I don't want end-user to ever see PHP code to configure his website and plug certain functionality into a view. Moreover, everything except website views will be encoded by IonCube.

The actual problem is in the controller lifecycle:

  1. Init application

  2. Dispatch request

  3. Run controller

3.1. Run filters

3.2. Execute actions

3.3. Render certain view (and only here we know what widgets are used).

I offer to focus on better interaction of controller and a widget. For example, widget actions can be executed separately from controller actions. This may be implemented in CController::endWidget and CController::widget, for example.

What do you think, guys?

Yes, one of the main differences between Yii and Prado is in the lifecycle. The controller won't be able to know which widgets are used until they are being rendered. While this is certainly inconvenient in some scenarios, it offers the needed performance and also makes widget development much easier. The result is that the user of the widget needs to take more responsibility (still reasonable, however).

Okay, now things are clear. Will have to override stuff. Happily, much less overrides this time than with Prado. Thanks for great feedback.

Hi

What version is this change targeted for ?

Thanks

nz

It's already in 1.0.1

Awesomeo  ;D !

nz