2015-06-26 1 views
0

Я разрабатываю пользовательский taglib в Grails, который должен знать о родительском теге. Так что, если у меня есть что-то подобное в GSP:Найти родительский тег в Grails custom taglib

<a href="#"> 
    <my:tag blabla="blabla"/> 
</a> 

затем осуществление моей: тег должен быть в состоянии выяснить, что она заключена внутри тега «а» и не что-то другое.
Это можно сделать так:
1. Узнайте, какой тег является родительским?
2. Измените атрибуты родительских тегов?

+3

Невозможно (без действительно уродливых и сложных хаков) –

+0

«Невозможно (без действительно уродливых и сложных хаков)» - @IgorArtamonov Я не согласен с этим. Это не требует взлома. Вы можете сделать это простым способом со счетчиком стека, который отслеживает, когда теги вложены внутри других тегов. См. Мой ответ ниже. –

+0

См. Комментарий ИгоряАртамонова к моему ответу ниже. Я стою исправлено. Я неправильно понял вопрос. Я думал, что вы хотите отслеживать, когда тег GSP был вложен внутри другого тега GSP. Это не то, о чем говорится в этом вопросе. Моя ошибка, и я приношу свои извинения за шум. –

ответ

0

EDIT - Ответ здесь не отвечает на вопрос, как было задано. См. Комментарии для объяснения. Я собираюсь оставить ответ здесь, потому что удаление этого дела сделает все эти комментарии непонятными, но ответ здесь не является верным ответом на вопрос, как было задано. Прошу прощения за шум.

Невозможно изменить атрибуты родительских тегов, но это не будет хорошей идеей. Существует почти наверняка лучший способ добиться того, что это заставляет вас делать это. Тем не менее, желая узнать, является ли тег вложенным в другой конкретный тег, вполне разумно, что нужно делать, и есть простые способы сделать это. Один из способов заключается в том, что ваш родительский тег может хранить некоторое состояние в pageScope, и дочерний тег может опросить это значение, чтобы определить, вызвано ли оно внутри родителя. Вы могли бы использовать только логический флаг, но это было бы проблематично, если бы вас беспокоили множественные уровни вложенности. Счетчик может отслеживать произвольную глубину.

Что-то вроде следующего должно работать.

TagLib:

// grails-app/taglib/demo/DemoTagLib.groovy 
package demo 

class DemoTagLib { 

    static namespace = 'demo' 

    def someParentTag = { attrs, body -> 
     def depthCounter = pageScope.someParentTagDepthCounter ?: 0 
     pageScope.someParentTagDepthCounter = ++depthCounter 

     out << body() 

     pageScope.someParentTagDepthCounter = --depthCounter 
    } 

    def someChildTag = { attrs, body -> 
     // This tag will only render its body if the tag invocation 
     // is nested inside of a someParentTag parent. This just 
     // demonstrates one way that a tag can discover if it is 
     // nested inside of some other specific tag. 
     if(pageScope.someParentTagDepthCounter) { 
      out << body() 
     } 
    } 
} 

Тест блок:

// src/test/groovy/demo/DemoTagLibSpec.groovy 
package demo 

import grails.test.mixin.TestFor 
import spock.lang.Specification 

@TestFor(DemoTagLib) 
class DemoTagLibSpec extends Specification { 

    void "test something"() { 
     expect: 'when someChildTag is not wrapped in someParentTag then the someChildTag body is not rendered' 
     applyTemplate('Heading <demo:someChildTag>Body</demo:someChildTag>') == 'Heading ' 

     and: 'when someChildTag is wrapped in someParentTag then the someChildTag body is rendered' 
     applyTemplate('Heading <demo:someParentTag><demo:someChildTag>Body</demo:someChildTag></demo:someParentTag>') == 'Heading Body' 

     and: 'when multiple someChildTags are nested in multiple levels of someParentTags, their bodies are rendered' 
     applyTemplate('Heading <demo:someParentTag><demo:someChildTag>First Child<demo:someParentTag> <demo:someChildTag>Second Child</demo:someChildTag></demo:someParentTag></demo:someChildTag></demo:someParentTag>') == 'Heading First Child Second Child' 
    } 
} 

Я надеюсь, что помогает.