Yii::app()->user is wrong class within module?

Hi all,

I’m scratching my head on this one. Right now I’m expanding my app to dynamically build a top level menu from menu items provided by application modules. My authorizations are calculated based upon some data that is contained within a custom User class. I have a custom user class configured in my app:


'user' => array(

            'class' => 'MyCustomUserClass',

            'allowAutoLogin' => true,

        ),

When I access Yii::app()->user within most parts of the application, I get MyCustomUserClass. I am building out that module’s menu structure within the module’s init() function. However, I found that Yii::app()->user returns a CWebUser when used within an init(), instead of the expected MyCustomUserClass.

Is this a bug, or am I going about this the wrong way?

Okay, so it turns out that it’s kind of a bug, but probably expected behavior. After a lot of research and tracing the code, I narrowed it down to gii. When gii is loaded, it actually overrides the global user class and sets it to CWebUser - regardless of what you have in the config. This is hardcoded. There’s been some debate on changing this behavior but the Yii devs have stood their ground.

GiiModules.php, line 118:




Yii::app()->setComponents(array(

			'errorHandler'=>array(

				'class'=>'CErrorHandler',

				'errorAction'=>$this->getId().'/default/error',

			),

			'user'=>array(

				'class'=>'CWebUser', // THIS IS THE PROBLEM LINE

				'stateKeyPrefix'=>'gii',

				'loginUrl'=>Yii::app()->createUrl($this->getId().'/default/login'),

			),

			'widgetFactory' => array(

				'class'=>'CWidgetFactory',

				'widgets' => array()

			)

		), false);



The devs have stated that this is required to ensure gii works properly, but I might recommend a patch that allows gii to proceed with the app’s custom class if it’s derived from a base CWebUser class.

The reason why I ran in to this problem is because I loop through each module to query it for potential menu items - and in the process of doing do I’m calling Yii::app()->getModule(), which kicks off the module’s init().

I was able to resolve this issue for now by ensuring that I don’t call getModule on gii, and in production gii is disabled so it’s a non-issue there.

Hope this helps someone else in the future.