Prakash K
Prakash K

Reputation: 11698

How to get a valid Liferay Layout from a given URL

The requirement is simple:

Given a URL, how to determine to which Layout it corresponds to?

The reason I need to do this is for certain layouts which meet specific conditions I need to redirect them to a certain other layout based on the roles/usergroups of a User. I am using a filter hook to achieve this.

For eg:

All these are same layouts:

Then there are other URL patterns similar to these but are used to serve CSS, JS and images from themes and then there are friendly URLs for different assets, for example:

Currently I am getting the layout using string manipulation in the Filter hook, like getting the path element of the URL and then searching for friendly-url of the layout etc; but this approach seems to be error-prone at best.

It would be good to know how liferay handles all these scenarios, any pointers to the code or approach would help.

Thanks

Upvotes: 1

Views: 3983

Answers (3)

ACV
ACV

Reputation: 10562

This code allows to obtain the complete URL from the friendly URL that you have. Let's say you have a friendly URL of format /view/users, now you want to do a redirect from bean method. You will not be able to do context.redirect("/view/users"). You need complete URL, for this you can use this code. The advantage is that it finds the current groupID without hardcoding it. The first step is to obtain the theme. Next you obtain the layout of the destination page based on your friendly URL. Finally, from this Layout you get it's URL.

  1. ThemeDisplay theme = (ThemeDisplay) getPortletRequest().getAttribute(WebKeys.THEME_DISPLAY);
    
  2. final long GROUP_ID = theme.getLayout().getGroupId();
    Layout destinationLayout = LayoutLocalServiceUtil.getFriendlyURLLayout(GROUP_ID, false, friendlyUrl);`
    
  3. String completeUrl = PortalUtil.getLayoutFullURL(destinationLayout , theme);
    

    where getPortletRequest is:

    private PortletRequest getPortletRequest() {
        FacesContext facesContext = FacesContext.getCurrentInstance();
        Object obj = facesContext.getExternalContext().getRequest();
        if (obj instanceof PortletRequest) {
            PortletRequest pr = (PortletRequest) obj;
            return pr;
        }
        return null;
    }
    

Upvotes: 1

ethanbustad
ethanbustad

Reputation: 1742

If you're writing this logic inside of the processFilter method, you can get the Layout object directly from the request parameter, like:

import com.liferay.portal.kernel.util.WebKeys;
import com.liferay.portal.model.Layout;
...
Layout layout = (Layout)request.getAttribute(WebKeys.LAYOUT);

This doesn't allow you to get the Layout object only given a string URL, but if you're inside a filter hook, this is probably what you want to do.

Upvotes: 1

Artem Khojoyan
Artem Khojoyan

Reputation: 857

In the above example, the /home is a friendly url of your Layout. Second url takes to /home again just because the /home is a default public landing page. The third url takes again to home because it's a same url like in the first case but with some additional parameters (everything after '?').

You could look at:

LayoutLocalServiceUtil.fetchLayoutByFriendlyURL(long groupId, boolean privateLayout, String friendlyURL)

The "groupId" here is the Group which friendly url is "/guest". You can get that group using GroupLocalServiceUtil.fetchFriendlyURLGroup(long companyId, String friendlyURL).

The "privateLayout" here is false as long as the "/web" typically points to public area.

The "friendlyURL" here is your "/home".

Hope this helps!

Upvotes: 0

Related Questions