{"id":12321,"date":"2014-03-16T18:11:11","date_gmt":"2014-03-16T12:41:11","guid":{"rendered":"http:\/\/www.tothenew.com\/blog\/?p=12321"},"modified":"2014-03-17T01:38:45","modified_gmt":"2014-03-16T20:08:45","slug":"applying-layout-to-template-at-runtime-in-grails-application","status":"publish","type":"post","link":"https:\/\/www.tothenew.com\/blog\/applying-layout-to-template-at-runtime-in-grails-application\/","title":{"rendered":"Applying layout to template at Runtime in Grails Application"},"content":{"rendered":"<p>There are use cases where we render the template from our action and update some div in the page using ajax.<br \/>\nThe downside of this approach is when the user hits the url directly in browser address bar and the UI get totally messed up.<\/p>\n<p><a href=\"\/blog\/wp-ttn-blog\/uploads\/2014\/03\/before.png\"><img decoding=\"async\" loading=\"lazy\" src=\"\/blog\/wp-ttn-blog\/uploads\/2014\/03\/before.png\" alt=\"\" title=\"before\" width=\"396\" height=\"109\" class=\"alignnone size-full\" \/><br \/>\nSo to fix this issue we need to apply the layout at runtime and its pretty easy in grails to do this, by writing the following code<br \/>\n[java]<br \/>\nrequest[GroovyPageLayoutFinder.LAYOUT_ATTRIBUTE] = &quot;main&quot;<br \/>\n[\/java]<br \/>\nTo make this more generic I created an annotation which will be applied to the Ajax actions. I also updated the filter to apply layout based on request xhr and the annotation is applied to action or not<\/p>\n<ul>\n<li>Create annotation in src\/groovy folder<br \/>\n[java]<br \/>\npackage com.sony.common.annotation<\/p>\n<p>import java.lang.annotation.ElementType<br \/>\nimport java.lang.annotation.Retention<br \/>\nimport java.lang.annotation.RetentionPolicy<br \/>\nimport java.lang.annotation.Target<\/p>\n<p>@Target([ElementType.METHOD])<br \/>\n@Retention(RetentionPolicy.RUNTIME)<br \/>\npublic @interface Ajaxed {<\/p>\n<p>    String layout() default &quot;main&quot;<\/p>\n<p>}<br \/>\n[\/java]\n<\/li>\n<li>Apply annotation to the controller method<br \/>\n[java]<br \/>\n@Ajaxed()<br \/>\n    def searchPlayers(PlayerSearchCO playerSearchCO) {<br \/>\n        List&lt;Player&gt; players = searchService.search(playerSearchCO)<br \/>\n        render(template: &#8216;players&#8217;, model: [players: players, teamParticipant: playerSearchCO.teamParticipant])<br \/>\n    }<br \/>\n[\/java]\n<\/li>\n<li>Add Filter to apply layout<br \/>\n[java]<br \/>\napplyLayoutForAjax(controller: &#8216;*&#8217;, action: &#8216;*&#8217;) {<br \/>\n            before = {<br \/>\n                if (controllerName &amp;&amp; actionName &amp;&amp; !request.xhr) {<br \/>\n                    def controllerClass = grailsApplication.controllerClasses.find { it.logicalPropertyName == controllerName }<br \/>\n                    def action = ApplicationContextHolder.resolveBean(controllerClass.fullName).class.declaredMethods.find { field -&gt; field.name == actionName }<br \/>\n                    def annotation = action ? action.getAnnotation(Ajaxed) : null<br \/>\n                    if (annotation) {<br \/>\n                        request[GroovyPageLayoutFinder.LAYOUT_ATTRIBUTE] = annotation.layout()<br \/>\n                    }<\/p>\n<p>                }<br \/>\n            }<br \/>\n        }<br \/>\n[\/java]\n<\/li>\n<\/ul>\n<p>and that&#8217;s it. Now your view will look something like this<br \/>\n<a href=\"\/blog\/wp-ttn-blog\/uploads\/2014\/03\/after.png\"><img decoding=\"async\" loading=\"lazy\" src=\"\/blog\/wp-ttn-blog\/uploads\/2014\/03\/after.png\" alt=\"\" title=\"after\" width=\"1176\" height=\"266\" class=\"alignnone size-full\" \/><\/p>\n","protected":false},"excerpt":{"rendered":"<p>There are use cases where we render the template from our action and update some div in the page using ajax. The downside of this approach is when the user hits the url directly in browser address bar and the UI get totally messed up. So to fix this issue we need to apply the [&hellip;]<\/p>\n","protected":false},"author":11,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"iawp_total_views":2},"categories":[7],"tags":[1353,96,1355,1354,785,1063],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/posts\/12321"}],"collection":[{"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/users\/11"}],"replies":[{"embeddable":true,"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/comments?post=12321"}],"version-history":[{"count":0,"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/posts\/12321\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/media?parent=12321"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/categories?post=12321"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.tothenew.com\/blog\/wp-json\/wp\/v2\/tags?post=12321"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}