I have made a custom afterFind function in a model, but I just want it to execute it if NOT in admin mode.
public function afterFind($results) {
if(Configure::read('Routing.admin')){
return $results;
}else{
return $this->locale(&$results);
}
}
But it doesn't seems to work. I'm thinking this might not be possible. Any idea?
checking on the core Configure settings doesnt make sense to me.
besides the fact that that 'Routing.admin' is deprecated - its Prefix.admin.
it only stores the prefixes that cake uses.
If you really want to you can store the information in configure::read() in beforeFilter() of your AppController and read it from your model again.
But it would need to something that does not conflict with your settings.
So if you use Prefix you probably could use Routing again:
//beforeFilter - prior to any model find calls!
$isAdmin = !empty($this->params['admin']);
Configure::write('Routing.admin', $isAdmin);
the other option you always have is to pass the information on to the model.
Router::getParam('prefix', true) gives you current request prefix value.
public function afterFind($results, $primary = false) {
return Router::getParam('prefix', true) == 'admin' ? $results : $this->locale(&$results);
}
Tested with Cake 2.4.
Related
I have an application in which we give a very friendly interface for managing data. This is done through many controllers' add/edit/view functions. But now the requirement has come that we should have "super admins" able to edit anything, and scaffolding will give them a quick and dirty manner of changing data. Since scaffolding uses add/edit/view by default, I've unintentionally overwritten the ability to scaffold.
I can't just go and change all my calls to edit/add for our "user friendly" data managing. So I want to essentially ignore the add/edit/view when, for example, a user has a flag of "yes, please let me scaffold". I imagined it would be something like:
public function edit($id) {
if (admin_user) {
$scaffold;
} else {
[user-friendly version code]
}
}
But no dice. How can I achieve what I want?
suppose you already have admin users and you want to scaffold only super-user:
Also suppose you store the information about beeing a super-user or not in a column named super in the users table
in your core.php
Configure::write('Routing.prefixes', array('admin', 'super));
in your appController
public $scaffold = 'super';
beforFilter() {
if($this->Auth->user('super') && !isset($this->params['super'])
$this->redirect(array('super' => true));
}
Now I can't try this code but the idea should work.
edit: we need to check if we are already in a super_action to avoid infinite redirect
I am working with CakePhp 2.x. I have three Columns:
User | Course | UserCourseRole
Each user can edit multiple courses and one course can be edited by multiple users. So far so good.
If a user wants to see an index of all the courses i want to show a 'edit'-link only next to the courses which he can in fact edit.
How can i realize this? I figured i would have to set some sort of extra field inside the CourseController and check for this field inside the view. Is this the right way to go?
My current Code is
CourseController.php
...
public function index() {
$courses = $this->Course->find('all', array('recursive' => 2));
$this->set('courses', $courses);
}
...
Courses/index.ctp
<!-- File: /app/View/Courses/index.ctp -->
...
<?php foreach ($courses as $course):?>
...
<?php
echo $this->Html->link('edit', array('action' => 'edit', $course['Course']['id']));
?>
...
In beforeRender() or beforeFilter() set $this->Auth->user() as a variable to the view, for example as userData.
$this->set('userData', $this->Auth->user());
Implement a (auth)helper that uses that variable (you can make it configurable as a helper setting) and do your checks like:
if ($this->Auth->hasRole($course['Course']['role']) { /* ... */ }
if ($this->Auth->isLoggedIn() { /* ... */ }
if ($this->Auth->isMe($course['Course']['user_id']) { /* ... */ }
Implement the hasRole() method according to whatever your specific requirements are.
Doing this as helper as a bunch of advantages, it is easy to reuse, overload and adapt to whatever your checks are and you don't use a component in a view plus that you should avoid calling statics and singletons a lot in your app. Also it is pretty easy to read and understand what the code does.
I think the good idea is set some variable or constans after logged (if user has privileges) and uses if statement for check.
if($allow === true) {
echo $html->link('Edit',...
}
or use AuthComponent::user() in Views.
This idea it's not good if we can many kind of admins (admin, moderator, reviewier, etc.)
Maybe someone will have a better solution
Please help, this is my first plugin I'm writing and I'm completely lost. I'm trying to write and update information in a table in a joomla database using my custom giveBadge() function. The functions receives two different variables, the first variable is the $userID and the second one is the digit 300 which I pass at the bottom of the class using giveBadge(300). At the same comparing the $userID in the Joomla database to ensure that the number 300 is given to the current user logged in the Joomla site.
Thanks in advance.
<?php
defined('JPATH_BASE') or die;
class plgUserBadge extends JPlugin
{
public function onUserLogin () {
$user =& JFactory::getUser();
$userID =& user->userID;
return $userID;
}
public function giveBadge ($userID, &$badgeID) {
// Get a db connection.
$db = JFactory::getDbo();
// Create a new query object.
$query = $db->getQuery(true);
// Fields to update.
$fields = array(
'profile_value=\'Updating custom message for user 1001.\'',
'ordering=2');
// Conditions for which records should be updated.
$conditions = array(
'user_id='.$userID,
'profile_key=\'custom.message\'');
$query->update($db->quoteName('#__user_badges'))->set($fields)->where($conditions);
$db->setQuery($query);
try {
$result = $db->query();
} catch (Exception $e) {
// Catch the error.
}es = array(1001, $db->quote('custom.message'), $db->quote('Inserting a record using insert()'), 1);
}
}
giveBadge(300); //attaches to $badgeID
?>
Here is not going well with your code:
You can drop the assign by reference in all your code (&) - you really don't need it, in 99% of the cases.
Use an IDE (for example Eclipse with PDT). At the top of your code you have & user->userID; Any IDE will spot your error and also other things in your code.
Study existing plugins to understand how they work. Here is also the documentation on plugins.
The method onUserLogin() will automatically be called by Joomla when the specific event is triggered (when your plugin is activated). Check with a die("My plugin was called") to see if your plugin is really called
inside onUserLogin() you do all your business logic. You are not supposed to return something, just return true. Right now your method does absolutely nothing. But you can call $this->giveBadge() to move the logic to another method.
I thought this would be a relatively common thing to do, but I can't find examples anywhere, and the Cookbook's section on find() was not clear in the slightest on the subject. Maybe it's just something that's so simple Cake assumes you can just do it on your own.
All I'm looking to do here is retrieve a User's name (not the currently logged-in user…a different one) in Cake based on their ID passed to my by an array in the view.
Here's what I've got in the controller:
public function user_lookup($userID){
$this->User->flatten = false;
$this->User->recursive = 1;
$user = $this->User->find('first', array('conditions' => $userID));
//what now?
}
At this point, I don't even know if I'm on the right track…I assume this will return an array with the User's data, but how do I handle those results? How do I know what the array's gonna look like? Do I just return($cakeArray['first'].' '.$cakeArray['last'])? I dunno…
Help?
You need to use set to take the returned data, and make it accessible as a variable in your views. set is the main way you send data from your controller to your view.
public function user_lookup($userID){
$this->User->flatten = false;
$this->User->recursive = 1;
// added - minor improvement
if(!$this->User->exists($userID)) {
$this->redirect(array('action'=>'some_place'));
// the requested user doesn't exist; redirect or throw a 404 etc.
}
// we use $this->set() to store the data returned.
// It will be accessible in your view in a variable called `user`
// (or what ever you pass as the first parameter)
$this->set('user', $this->User->find('first', array('conditions' => $userID)));
}
// user_lookup.ctp - output the `user`
<?php echo $user['User']['username']; // eg ?>
<?php debug($user); // see what's acutally been returned ?>
more in the manual (this is fundamental cake stuff so might be worth having a good read)
I am creating an application in which I am using two plugins.
For future use I want to check whether the two plugins are being used together or separately.
I need to check if the model exists and if so perform some logic and if not - not.
If I try if($this->loadModel('Model')) { etc }
I get an error saying the model does not exist which is what I want but I don't want an error which prevents the logic from proceeding.
Basically I want:
if(Model->exists()) { do->this }
else { do->somethingelse }
I tried using the php function class_exists() but that returns false regardless of whether the Model exists or not.
I would use App::objects('model') as of 2.x (Not sure when this was implemented).
class AppController extents Controller {
private function _modelExists($modelName){
$models = App::objects('model');
return in_array($modelName,$models);
}
}
//Somewhere in your logic
if($this->_modelExists('SomeModel')){
//do model exists logic
} else {
//do other logic
}
*Note that App::objects('model') will not include models from plugins. You could do:
$models = array_merge(
App::objects('model'),
App::objects('MyPlugin.model')
);
You can also do this with pure php as follows
if(class_exists('SomeModel')){
//do model exists logic
} else {
//do other logic
}
// The pitfall of this approach, is that it will not assure
// that `SomeModel is a decedent of the `Model` class.
You can do this :
$model = ClassRegistry::init("User");
if $model is null this means that the User model does not exist
You can do this from every where in the code