1 <?php
2 /**
3 * Rights helper class file.
4 *
5 * Provides static functions for interaction with Rights from outside of the module.
6 *
7 * @author Christoffer Niska <cniska@live.com>
8 * @copyright Copyright © 2010 Christoffer Niska
9 * @since 0.9.1
10 */
11 class Rights
12 {
13 const PERM_NONE = 0;
14 const PERM_DIRECT = 1;
15 const PERM_INHERITED = 2;
16
17 private static $_m;
18 private static $_a;
19
20 /**
21 * Assigns an authorization item to a specific user.
22 * @param string $itemName the name of the item to assign.
23 * @param integer $userId the user id of the user for which to assign the item.
24 * @param string $bizRule business rule associated with the item. This is a piece of
25 * PHP code that will be executed when {@link checkAccess} is called for the item.
26 * @param mixed $data additional data associated with the item.
27 * @return CAuthItem the authorization item
28 */
29 public static function assign($itemName, $userId, $bizRule=null, $data=null)
30 {
31 $authorizer = self::getAuthorizer();
32 return $authorizer->authManager->assign($itemName, $userId, $bizRule, $data);
33 }
34
35 /**
36 * Revokes an authorization item from a specific user.
37 * @param string $itemName the name of the item to revoke.
38 * @param integer $userId the user id of the user for which to revoke the item.
39 * @return boolean whether the item was removed.
40 */
41 public static function revoke($itemName, $userId)
42 {
43 $authorizer = self::getAuthorizer();
44 return $authorizer->authManager->revoke($itemName, $userId);
45 }
46
47 /**
48 * Returns the roles assigned to a specific user.
49 * If no user id is provided the logged in user will be used.
50 * @param integer $userId the user id of the user for which roles to get.
51 * @param boolean $sort whether to sort the items by their weights.
52 * @return array the roles.
53 */
54 public static function getAssignedRoles($userId=null, $sort=true)
55 {
56 $user = Yii::app()->getUser();
57 if( $userId===null && $user->isGuest===false )
58 $userId = $user->id;
59
60 $authorizer = self::getAuthorizer();
61 return $authorizer->getAuthItems(CAuthItem::TYPE_ROLE, $userId, null, $sort);
62 }
63
64 /**
65 * Returns the base url to Rights.
66 * @return the url to Rights.
67 */
68 public static function getBaseUrl()
69 {
70 $module = self::module();
71 return Yii::app()->createUrl($module->baseUrl);
72 }
73
74 /**
75 * Returns the list of authorization item types.
76 * @return array the list of types.
77 */
78 public static function getAuthItemOptions()
79 {
80 return array(
81 CAuthItem::TYPE_OPERATION=>Rights::t('core', 'Operation'),
82 CAuthItem::TYPE_TASK=>Rights::t('core', 'Task'),
83 CAuthItem::TYPE_ROLE=>Rights::t('core', 'Role'),
84 );
85 }
86
87 /**
88 * Returns the name of a specific authorization item.
89 * @param integer $type the item type (0: operation, 1: task, 2: role).
90 * @return string the authorization item type name.
91 */
92 public static function getAuthItemTypeName($type)
93 {
94 $options = self::getAuthItemOptions();
95 if( isset($options[ $type ])===true )
96 return $options[ $type ];
97 else
98 throw new CException(Rights::t('core', 'Invalid authorization item type.'));
99 }
100
101 /**
102 * Returns the name of a specific authorization item in plural.
103 * @param integer $type the item type (0: operation, 1: task, 2: role).
104 * @return string the authorization item type name.
105 */
106 public static function getAuthItemTypeNamePlural($type)
107 {
108 switch( (int)$type )
109 {
110 case CAuthItem::TYPE_OPERATION: return Rights::t('core', 'Operations');
111 case CAuthItem::TYPE_TASK: return Rights::t('core', 'Tasks');
112 case CAuthItem::TYPE_ROLE: return Rights::t('core', 'Roles');
113 default: throw new CException(Rights::t('core', 'Invalid authorization item type.'));
114 }
115 }
116
117 /**
118 * Returns the route to a specific authorization item list view.
119 * @param integer $type the item type (0: operation, 1: task, 2: role).
120 * @return array the route.
121 */
122 public static function getAuthItemRoute($type)
123 {
124 switch( (int)$type )
125 {
126 case CAuthItem::TYPE_OPERATION: return array('authItem/operations');
127 case CAuthItem::TYPE_TASK: return array('authItem/tasks');
128 case CAuthItem::TYPE_ROLE: return array('authItem/roles');
129 default: throw new CException(Rights::t('core', 'Invalid authorization item type.'));
130 }
131 }
132
133 /**
134 * Returns the valid child item types for a specific type.
135 * @param string $type the item type (0: operation, 1: task, 2: role).
136 * @return array the valid types.
137 */
138 public static function getValidChildTypes($type)
139 {
140 switch( (int)$type )
141 {
142 // Roles can consist of any type of authorization items
143 case CAuthItem::TYPE_ROLE: return null;
144 // Tasks can consist of other tasks and operations
145 case CAuthItem::TYPE_TASK: return array(CAuthItem::TYPE_TASK, CAuthItem::TYPE_OPERATION);
146 // Operations can consist of other operations
147 case CAuthItem::TYPE_OPERATION: return array(CAuthItem::TYPE_OPERATION);
148 // Invalid type
149 default: throw new CException(Rights::t('core', 'Invalid authorization item type.'));
150 }
151 }
152
153 /**
154 * Returns the authorization item select options.
155 * @param mixed $type the item type (0: operation, 1: task, 2: role). Defaults to null,
156 * meaning returning all items regardless of their type.
157 * @param array $exclude the items to be excluded.
158 * @return array the select options.
159 */
160 public static function getAuthItemSelectOptions($type=null, $exclude=array())
161 {
162 $authorizer = self::getAuthorizer();
163 $items = $authorizer->getAuthItems($type, null, null, true, $exclude);
164 return self::generateAuthItemSelectOptions($items, $type);
165 }
166
167 /**
168 * Returns the valid authorization item select options for a model.
169 * @param mixed $parent the item type (0: operation, 1: task, 2: role). Defaults to null,
170 * meaning returning all items regardless of their type.
171 * @param CAuthItem $type the item for which to get the select options.
172 * @param array $exclude the items to be excluded.
173 * @return array the select options.
174 */
175 public static function getParentAuthItemSelectOptions(CAuthItem $parent, $type=null, $exclude=array())
176 {
177 $authorizer = self::getAuthorizer();
178 $items = $authorizer->getAuthItems($type, null, $parent, true, $exclude);
179 return self::generateAuthItemSelectOptions($items, $type);
180 }
181
182 /**
183 * Generates the authorization item select options.
184 * @param array $items the authorization items.
185 * @param mixed $type the item type (0: operation, 1: task, 2: role).
186 * @return array the select options.
187 */
188 protected static function generateAuthItemSelectOptions($items, $type)
189 {
190 $selectOptions = array();
191
192 // We have multiple types, nest the items under their types
193 if( $type!==(int)$type )
194 {
195 foreach( $items as $itemName=>$item )
196 $selectOptions[ self::getAuthItemTypeNamePlural($item->type) ][ $itemName ] = $item->getNameText();
197 }
198 // We have only one type
199 else
200 {
201 foreach( $items as $itemName=>$item )
202 $selectOptions[ $itemName ] = $item->getNameText();
203 }
204
205 return $selectOptions;
206 }
207
208 /**
209 * Returns the cross-site request forgery parameter
210 * to be placed in the data of Ajax-requests.
211 * An empty string is returned if csrf-validation is disabled.
212 * @return string the csrf parameter.
213 */
214 public static function getDataCsrf()
215 {
216 return ($csrf = self::getCsrfParam())!==null ? ', '.$csrf : '';
217 }
218
219 /**
220 * Returns the cross-site request forgery parameter for Ajax-requests.
221 * Null is returned if csrf-validation is disabled.
222 * @return string the csrf parameter.
223 */
224 public static function getCsrfParam()
225 {
226 if( Yii::app()->request->enableCsrfValidation===true )
227 {
228 $csrfTokenName = Yii::app()->request->csrfTokenName;
229 $csrfToken = Yii::app()->request->csrfToken;
230 return "'$csrfTokenName':'$csrfToken'";
231 }
232 else
233 {
234 return null;
235 }
236 }
237
238 /**
239 * @return string a string that can be displayed on your Web page
240 * showing Powered-by-Rights information.
241 */
242 public static function powered()
243 {
244 $module = self::module();
245 return 'Secured with <a href="http://www.yiiframework.com/extension/rights" rel="external">Rights</a> version '.$module->getVersion().'.';
246 }
247
248 /**
249 * @return RightsModule the Rights module.
250 */
251 public static function module()
252 {
253 if( isset(self::$_m)===false )
254 self::$_m = self::findModule();
255
256 return self::$_m;
257 }
258
259 /**
260 * Searches for the Rights module among all installed modules.
261 * The module will be found even if it's nested within another module.
262 * @param CModule $module the module to find the module in. Defaults to null,
263 * meaning that the application will be used.
264 * @return the Rights module.
265 */
266 private static function findModule(CModule $module=null)
267 {
268 if( $module===null )
269 $module = Yii::app();
270
271 if( ($m = $module->getModule('rights'))!==null )
272 return $m;
273
274 foreach( $module->getModules() as $id=>$c )
275 if( ($m = self::findModule( $module->getModule($id) ))!==null )
276 return $m;
277
278 return null;
279 }
280
281 /**
282 * @return RAuthorizer the authorizer component.
283 */
284 public static function getAuthorizer()
285 {
286 if( isset(self::$_a)===false )
287 self::$_a = self::module()->getAuthorizer();
288
289 return self::$_a;
290 }
291
292 /**
293 * Translates a message to the specified language.
294 * Wrapper class for setting the category correctly.
295 * @param string $category message category.
296 * @param string $message the original message.
297 * @param array $params parameters to be applied to the message using <code>strtr</code>.
298 * @param string $source which message source application component to use.
299 * @param string $language the target language.
300 * @return string the translated message.
301 */
302 public static function t($category, $message, $params=array(), $source=null, $language=null)
303 {
304 return Yii::t('RightsModule.'.$category, $message, $params, $source, $language);
305 }
306 }
307