Get action name from within controller.php in the components - yii

Is there a way to get the current action name from within the Controller.php init function ?
Thanks

In general, you can call $this->action->id within descendant of the CController class.
Or you can use Yii::app()->controller->action->id through whole application.
But the method init() was called before the controller started to execute (see http://www.yiiframework.com/doc/api/1.1/CController#init-detail)
As you can see here: http://www.yiiframework.com/doc/api/1.1/CWebApplication#runController-detail actionID will be passed to method run() only after init():
$controller->init();
$controller->run($actionID);

As v2p said, after init() run, we can get the controller id by Yii::app()->controller,also behavior id by Yii::app()->controller->action->id;Another way: Yii::app()->getController()->getAction()->id;

Related

Access Views and Controllers which are under Sub folders for specific scenarios?

On my all actions methods I use this route attribute to use - sign.
[HttpPost]
[Route("lower-case-converter")]
public IActionResult Index(BassModel model)
Since I have many case converters I want to put them inside a folder called "CaseConverters". I made a folder in views folder called ""CaseConverters". Note that there are other tools too.
So I changed the route attribute like this
[Route("~/CaseConverters/lower-case-converter")]
Above not worked. So I changed it to
[Route("/CaseConverters/lower-case-converter")]
Still its not working. Note that i want to add this folder to Controllers folder too. How to acehve this?
To specify a route for lower-case-converter action inside your CaseConverters controller you can specify the route as follows, (I'm assuming CaseConverters is your controller. If yes It's better to use the correct naming convention. Ex: CaseConvertersController)
[Route("CaseConverters/lower-case-converter")]
You can also specify a route template for your controller class. as follows,
[Route("CaseConverters")]
public class CaseConvertersController : Controller
{
[Route("lower-case-converter")]
public IActionResult LowerCaseConverter()
{
//you implementation
}
}
For the above code route template for the action is CaseConverters/lower-case-converter. And also make sure use have used app.UseMvc() and MapRoute() methods inside Configure() method inside the startup.cs

onPropertyChanged - How to switch propertyId from external class

I have a model that extends BaseObservable. I have a view model that contains a reference to the model and subscribes to property changes within the model. How do I switch on the Model.propertyId from within the callback in the view model? In the sample below BR.assignedId is the property in the model. For example:
View Model
public void onPropertyChanged(Observable sender, int propertyId)
{
switch (propertyId)
{
case MyModel.BR.assignedId://compile error
notifyPropertyChanged(BR.assignedImage);
break;
}
}
I suggest you to read Observer pattern. The code above has Entities : Observer and Observable. Observer has an Observing method. Any class which wants to observe the 'Observable' needs to register itself as 'Observer'. Observable calls the observing method on the Observer and this is how the usual call back works. (names of classes and methods may be differnt , I used as per the intent and context)
Check 'ViewModel.java' class would be implementing some 'observer' interface which would be having the method 'onPropertyChanged ()'. you will have to set the object of ViewModel.java in Model.java. (check you should be having a method with a name like addPropertyChangeObserver (), though it may be differnt but similar method. Use this method to set the object of ViewModel.java in Model.java. Now Model.java would call the method 'onPropertyChanged' on ViewModel.java.
if you wish to modify something on the Model then check the sender parameter. You can add another method in the interface implemented by Model and can do modifications on Model using it or can simply typecast the sender after checking its type with instanceof and can perform the process on Model.java from the callback method.

Can we use Htmlhelper class in controller?

I am working on web api project, we have one htmlhelper class, where I see declarations that look like:
public static string GetCountryDomain(this System.Web.Mvc.HtmlHelper htmlHelper, Area area)
{
//body
}
Can I use method declared in helper class in my api method?
If Yes, then can someone explain how can I call that method from my controller?
Consider following example, wherein am calling method declared in helper from my controller.
HtmlHelper.GetCountryDomain(area_id);
can someone explain what first parameter I need to pass in order to call above method of HtmlHelper class?

groovy method scope when using a method reference

I have a groovy class that looks up a method reference and then invokes it. The method being invoked is a private method. When the actual class is an instance of the child class, it throws an error that it cannot find the private method, even though it is the public method in the parent that actually calls it.
In this case, I could obviously just call pMethod2() directly and that works, but I'm trying to understand why this doesn't work as written and if there's a way to correct it so it works.
class Parent {
def pMethod1() {
def m = this.&pMethod2
m() // this call fails if the calling class is of type Child
}
private def pMethod2() {}
public static void main(String[] args) {
new Child().pMethod1();
}
}
class Child extends Parent {}
It is a bit confusing, especially if you're used to C / C++. What you get when using the ".&" operator in Groovy is not an address, but an instance of MethodClosure.
The MethodClosure object contains an owner and a delegate object, which is used when resolving the method to call. In your example, the owner and delegate object will be "this", which is an instance of Child. The method to call is simply stored as a string.
So, the assignment
m = this.&pMethod2
is just a shorthand way of writing
m = new MethodClosure(this, "pMethod2")
When you invoke the m() closure, it will try to resolve (at runtime) the method by looking for methods named "pMethod2" in the owner and the delegate objects respectively. Since the owner and delegate is an instance of Child, it will not find private methods located in Parent.
To make your example work you must make sure that the method is visible to the owner and/or delegate of the closure.
This can be done several ways, for instance by changing the access modifier of pMethod2 to protected, or by creating the closure with an instance of Parent; something like this:
m = new Parent().&pMethod2
Note that is is irrelevant that you created the MethodClosure instance in a method where pMethod2 is actually visible. It is also irrelevant that you invoke the closure in a method where it is visible. The method is not visible to the owner or delegate of the MethodClosure, which is what is being used when resolving the method.

Zend_Form disable populate before isValid()

Im not able to disable populating values in Zend_Form .
I have my own form class. With hidden token element where I would like to dynamicaly setup random value every time the form is called (or reposted). I thought that setValue will make the job.
class MY_Form_Test extends Zend_Form {
public function init() {
...
$this->addElement('hidden', 'token');
$this->getElement('token')->setValue(uniqid('',true));
...
}
BUT: When I have simple controller like this. Zend automate populating old hidden values except to generate new one.
$form = new JC_Form_Test();
if($form->isValid($_POST)){
// Action ...
}
else{
// Error
}
SOLUTION: The only solution I found is to call setValue in Controler AND AFTER isValid method. eg. in Error block.
QUESTION: Is there any way to setup element values directly in form class OR disable populate values in form class or before isValid() is called?
I think it's the best way to do it.
I work much with Zend Framework and have my own library for overwrite some Zend classes.
It's not bad to change something, but don't do it directly within Zend Framework
SECOND SOLUTION: Second solution I found is to overload isValid() method in Form class. Like this. Then I dont need to put setValue() into every Controller.
class MY_Form_Test extends Zend_Form {
...
public function isValid($data){
// Propagate values
$valid = parent::isValid($data);
$this->getElement('token')->setValue(uniqid('',true));
return $valid;
}
Are there any other solution eg. some element option to do this job more simple?