drupal: logged in status message? - drupal

when an user login in Drupal, the login block disappear from my pages.
I would like instead to keep it there with a message stating the user is logged in.
Something like this (with logout link): "Welcome Patrick. Logout"
thanks

The login-form will not work for not logged in-users.
What is easiest, is to make a new block (admin » build » blocks » new(tab))
Then set that block to show only for role "authenticated". That way, the block will work exact opposite from the user-login block, which shows only for role: anonymous.
You can add any custom text in there, as long as it is static text. If you want to include dynamic text, such as "Hello $username, you will have to go for the tip by Jeremy French: create a module with its own hook_block.

The login block is created by the follwing code from the user_block() function.
if (!$user->uid && !(arg(0) == 'user' && !is_numeric(arg(1)))) {
$block['subject'] = t('User login');
$block['content'] = drupal_get_form('user_login_block');
}
There is no code to display a message if you are logged in.
One simple way to do what you want would be to create a module which implements the above code in hook_block, and has an elese statement which displays what you want.

A quick way to solve your problem, is to create a new block with whatever you want in it, and only show it when the user is logged in. If you arrange the placement and style, it will look like the same block, even though they are different.
You can create the new block with a custom module or views.

Related

Can't render an action in base layout and execute it from child template

Am working on a Symfony2 application whose among its functions will allow the user to select to visit different sections of the site, and this from anywhere (any page) of the site. For simplifying let's say: when a user want to sort he/she choose from a drop down select form and submit.
I built the action and template with a test root to verify this function and this work (when I use directly the rendering of that sortAction() on my app_dev/test adress.
The issu is that when I try to make this action accessible from the general template (app/Resources/views/base.html) I can view the select form with default view, but when I select for a sort and try to Submit page relaods and return to the defaut view.
I use {% render "MycompanyMybundleBundle:Mycontroller:sort" %} in .../base.html and I want this action to work on (like) mysite/anypage this last extending bundle layout which (layout also extent base).
Can anyone help me?
The description of your problem isn't realy clear, but I think the problem lies at the form action. Do you've configured this action? You should leave it empty if you want to submit it to the same page.
Another solution would be to make use of the extending posibilities of Twig. Define the form as a block in the parent, and override it in the child.
http://twig.sensiolabs.org/doc/tags/extends.html
EDIT:
You could make the form action a block, that is what I mean...
<form action="{% block formAction %}defaulttargetpage.php{ %endblock% }"> <!-- formcontent --> </form>

FOSUserBundle: Change Password within actual project

I have successfully installed FOSUserBundle in my project and everything works as expected. However, I am struggling with how to implement it in my actual project.
I want to create the following setup:
A page displaying some user settings in one form (like newsletter subscription), the possibility to change the password in a second form and maybe also a third form to change the username.
The settings form as well as some more information is coming from an existing action in my controller and is working well.
I did try a few things but things are not really working out yet:
I copied some functionality from FOSUserBundle\Controller\ChangePasswordController\changePasswordAction() to my own action. This way I could get the change password form, create the view and pass it to my template.
I added the form to my template with {{ form_widget(form) }}. The form is being displayed and it's even working. I can change the password. However, the labels are being lost, simply reading Current, First, and Second. Also there is no error messaging showing up when the two new passwords don't match or are being left empty.
Over all I have the feeling I am probably doing this in a wrong way. Could you please help me how I should handle this task and point out where I am likely doing something stupid?
Here is the code of my action, reduced to what's important here:
# src/Acme/MyBundle/Controller/BackendController.php
public function accountAction(){
//pretty much a copy of FOSUserBundle\Controller\ChangePasswordController\changePasswordAction()
$user = $this->get('security.context')->getToken()->getUser();
$form = $this->container->get('fos_user.change_password.form');
$formHandler = $this->container->get('fos_user.change_password.form.handler');
$process = $formHandler->process($user);
if ($process) {
//password has been changed, response will be generated
}
//more stuff going on here
$moreStuff = ...
//render view
return $this->render('AcmeMyBundle:Backend:account.html.twig', array(
'form' => $form->createView(),
'moreStuff' => $moreStuff
));
}
IMO rendering more than one form in one action is not a good idea.
Always try to separate things and let an action handle only one feature.
In your twig template I suggest to use the render method :
{% render 'AcmeBundle:SomeAction' with{'param:param} %}
It will generate a GET request on the action provided with some params if needed.
Create one action that will render the twig template with subrequests :
// AcmeUserBundle:editAction
{% render 'AcmeUserBundle:changePasswordAction' %}
{% render 'AcmeUserBundle:settingsAction' %}
{% render 'AcmeUserBundle:profileAction' %}
And then you'll need to create one action per form.
For password and username modification you can also override FOSUserBundle views if your needs are only visual. If you need to add/remove a field on the form you will need to create a new service.
I sugget reading FOSUserBundle documentation about overriding :
https://github.com/FriendsOfSymfony/FOSUserBundle/blob/master/Resources/doc/index.md#next-steps

Changing menu links, if user is authenticated or not

I need to change the menu links on my website (and leave the same items names) depending on the user is a guest, or authenticated user.
What's the standard way to do it ?
thanks
You cannot dynamically change a menu item's path, because menu items are cached.
Still, AFAIK, there are two ways to get what you want. Both methods require you to create your menu items with hook_menu in a custom module (not from the Menu UI).
The first method is to create two menu items with identical names and set the access rules so that one is only available for logged guests, the other for authenticated users. Since Drupal will only show menu items that the user is allowed to access, only one will show up at any given moment. In Drupal core, you can see how the user module creates a menu item for anonymous users by looking at the /user/login path in user_menu().
The second method is to create a single menu item and check in the menu callback if the user is logged in. If the user is logged in, you serve one page, if not you serve another. In Drupal core, the /user path works like this. See user_page to see how the code works.
You can dynamically change a menu item's path - see hook_translated_menu_link_alter.
This hook is called before every menu item is rendered IF it has the property ['options']['alter'] = TRUE.
You can set this property to menu items using hook_menu_link_alter.
Example code would be:
function MY_MODULE_menu_link_alter(&$item) {
$item['options']['alter'] = TRUE;
}
function MY_MODULE_translated_menu_link_alter(&$item, $map) {
if($item['mlid']==89) {
$item['link_path'] .= 'my-new-path';
}
}
Instead of altering the link, you coudl create the menues twice: once with the links for regular users and once with the links for registered/admin/... users
You can put a menu into a block and set it to only allow registered users to see the one block and non-registered users the other block. Either by selecting the proper radio button from the Drupal menu within the block creation form or via PHP that will evaluate and depending on it's return value (TRUE/FALSE) displays it. I suggest to go with the first approach.
You can change the menu by using a combination of nodeaccess module and linking to the corresponding pages.
For example, by default guest users cannot access /logout. If you create a link in a menu to logout, it will only display if a user is logged in. With nodeaccess, simply create a node, visit the grant tab and uncheck/check "authenticated users" or "anonymous users" for that node.
http://drupal.org/project/nodeaccess
Cheers,

Check views display permission for user

A user might be in role X.
There exist a view, where display A is allowed for role X while display B is restricted.
How do i programmatically check whether a user belonging to role X can access the display or not?
What you should do, is to check the permission instead of the role using: user_access
Is there a specific reason why you want to do this programmatically? You can set access rules for Views displays in the Views UI:
Edit the view, select the display and look for "Access" in the "Basic settings" block. Click the value (default = "Untrestricted"), click the "Override" button to override the setting for that specific display and choose the settings you need.
Can be implemented inline in the theme, but better to break it up into module + theme. (assumes drupal-7) In your theme (node--contenttype.tpl.php) invoke a custom access method:
if (module_invoke('hottopicresearch', 'display_moderated_research_access_callback', 'update', $node)) {
Implement an this access callback in a module:
function hottopicsresearch_display_moderated_research_access_callback($permission, $node) {
And check roles
if (in_array("editorial board admin", $user->roles) || $user->uid == 1) {
and/or node access as noted in other answers:
if (!node_access($permission, $research_parent_node)) {
returning TRUE or FALSE.
This example gave access to people with 'editorial board admin' role and people who can write to the node. Nobody else can see the index. Of course this doesn't stop them accessing the node directly.

Drupal html user id

I'm using Drupal 6.16: I think I have a pretty simple question. How can I get the current user id and put it in a menu tab. What I would like to happen is when the user logs in and wants to change their name, email etc to click a menu tab. I image it would look something like this: http://domain.com/user/{userid}/edit
Thanks in advance!
msindle
That's more difficult than you would think, because menu items are cached. There is not a straightforward way to create dynamic menu items with the userID in it.
What you can do, is write a custom module and imitate the behavior of the 'user' path. With an implementation of hook_menu you create a menu item, with the path 'user/edit' (just like user_menu() creates $items['user']). Next you create a menu callback user_edit_page(), similar to user_page(), which gets the id of the current user and returns the user edit page:
function user_edit_page() {
global $user;
if ($user->uid) {
menu_set_active_item('user/'. $user->uid .'/edit');
return menu_execute_active_handler();
}
else {
return drupal_get_form('user_login');
}
}

Resources