Frage

I have a composite component 'schematic_question.xhtml':

<composite:interface>
<composite:attribute name="attributesString" />
<composite:attribute name="renderedSchematic" />
<composite:attribute name="action" targets="deleteQuestionButton" required="true" />
<composite:attribute name="questionIdToDelete" />
<composite:attribute name="parentToUpdate" />
<composite:attribute name="questionId" />
</composite:interface>

<composite:implementation>
<p:panelGrid id="#{cc.clientId}" columns="1"
    rendered="#{cc.attrs.renderedSchematic}"
    styleClass=" fullWidthNoMargin"
    style="padding:0px !important ; width:767px;">

    <p:panel style="background: #D3D3D3; margin-bottom: 20px;">

        <p:outputLabel
            value="#{msg.globalLabelQuestion}-#{msg.globalLabelId}: " />
        <p:outputLabel value="#{cc.attrs.questionId}"
            style="width: 30px; display:inline-block;" />

        <p:outputLabel style="padding-left:350px;"
            value="#{msg.globalLabelAttributes}: " />
        <p:outputLabel value="#{cc.attrs.attributesString}"
            style="width: 100px; display:inline-block;" />

        <p:outputLabel
            value="#{msg.globalLabelDeleteelement}:" />
        <p:commandLink id="deleteQuestionButton"  styleClass="noBorders" value="delete"
            icon="icon-close" title="#{msg.globalLabelDelete}" >
            <f:param name="questionIdToDelete"
                value="#{cc.attrs.questionIdToDelete}" />
        </p:commandLink>
    </p:panel>
</p:panelGrid>
</composite:implementation>

Now I create this composite component through java code:

private boolean createAndInsertSchematicInfosForQuestion(final QuestionDtoInt questionDto,
        final UIComponent parentElementId) {
    final Map<String, String> valueExpressions = new HashMap<String, String>();

    if (questionDto == null) {
        return false;
    }

    final String questionId = String.valueOf(questionDto.getId());

    final QuestionDtoWrapper wrapper = new QuestionDtoWrapper(questionDto);
    valueExpressions.put("action", "#{" + controllerClassName + ".deleteQuestion()}");
    valueExpressions.put("questionIdToDelete", questionId);
    valueExpressions.put("attributesString", wrapper.getAttributes());
    valueExpressions.put("renderedSchematic", "#{" + controllerClassName + ".schematicView}");
    valueExpressions.put("parentToUpdate", ":previewQuestionnaireElementsForm");
    valueExpressions.put("questionId", questionId);

    try {
        utils.includeCompositeComponent(parentElementId, "components", "schematic_question.xhtml",
                RandomStringUtils.randomAlphabetic(15), valueExpressions);
    } catch (final IOException e) {
        LOG.logError("Schematic question component could not be created", e);
        return false;
    }
    return true;
}

and insert it in a scroll panel that is in dialog with a form:

<p:dialog widgetVar="previewQuestionnaireDlg" modal="true"
    height="850" appendToBody="true" dynamic="true" width="880"
    closeOnEscape="false" resizable="false">
    <p:ajax event="close" update="previewQuestionnaireElementsForm"
        listener="#{previewQuestionnaireController.clearPreviewPanelChilds()}" />
    <h:form id="previewQuestionnaireElementsForm" prependId="false">
        <p:panelGrid id="previewQuestionnairePanelGrid" columns="1"
            styleClass="noBorders">
            <h1>#{msg.editquestionnaireLabelPreviewquestionnaire}</h1>
            <p:panelGrid id="schematicViewPanelGrid" columns="2">
                <h:outputText value="Schematische Ansicht " />
                <p:selectBooleanCheckbox
                    value="#{previewQuestionnaireController.schematicView}">
                    <p:ajax process="schematicViewPanelGrid"
                        update="questionnairePreviewPanel" />
                </p:selectBooleanCheckbox>
            </p:panelGrid>
            <br />
            <br />
            <p:scrollPanel id="questionnairePreviewPanel" style="height:640px; width:840px;" styleClass="noBorders" mode="native">

            </p:scrollPanel>

            <br />

            <p:commandButton value="#{msg.globalButtonClose}"
                action="#{previewQuestionnaireController.clearPreviewPanelChilds()}"
                update="previewQuestionnaireElementsForm" ajax="true"
                onclick="previewQuestionnaireDlg.hide();">
            </p:commandButton>
        </p:panelGrid>
    </h:form>
</p:dialog>

It is all displayed correct. But as soon as click on the button a NullPointerException occurres and the method is not called:

 #|2013-12-13T09:56:13.400+0100|SEVERE|glassfish3.1.2|javax.enterprise.system.container.web.com.sun.enterprise.web|_ThreadID=100;_ThreadName=Thread-14;|WebModule[/QuesT]FullAjaxExceptionHandler: An exception occurred during processing JSF ajax request. Error page '/views/errors/error.xhtml' will be shown.
 java.lang.NullPointerException
at javax.faces.component.UIComponentBase$AttributesMap.put(UIComponentBase.java:2414)
at javax.faces.component.UIComponentBase$AttributesMap.put(UIComponentBase.java:2283)
at com.sun.faces.el.CompositeComponentAttributesELResolver$ExpressionEvalMap.put(CompositeComponentAttributesELResolver.java:367)
at com.sun.faces.el.CompositeComponentAttributesELResolver$ExpressionEvalMap.put(CompositeComponentAttributesELResolver.java:287)
at javax.el.MapELResolver.setValue(MapELResolver.java:267)
at com.sun.faces.el.DemuxCompositeELResolver._setValue(DemuxCompositeELResolver.java:255)
at com.sun.faces.el.DemuxCompositeELResolver.setValue(DemuxCompositeELResolver.java:281)
at com.sun.el.parser.AstValue.setValue(AstValue.java:217)
at com.sun.el.ValueExpressionImpl.setValue(ValueExpressionImpl.java:291)
at org.jboss.weld.el.WeldValueExpression.setValue(WeldValueExpression.java:64)
at com.sun.faces.facelets.el.ContextualCompositeValueExpression.setValue(ContextualCompositeValueExpression.java:170)
at com.sun.faces.facelets.el.TagValueExpression.setValue(TagValueExpression.java:131)
at javax.faces.component.UIInput.updateModel(UIInput.java:818)
at javax.faces.component.UIInput.processUpdates(UIInput.java:735)
at javax.faces.component.UIComponentBase.processUpdates(UIComponentBase.java:1242)
at javax.faces.component.UIComponentBase.processUpdates(UIComponentBase.java:1242)
at javax.faces.component.UIComponentBase.processUpdates(UIComponentBase.java:1242)
at javax.faces.component.UIComponentBase.processUpdates(UIComponentBase.java:1242)
at javax.faces.component.UIComponentBase.processUpdates(UIComponentBase.java:1242)
at javax.faces.component.UIComponentBase.processUpdates(UIComponentBase.java:1242)
at javax.faces.component.UIForm.processUpdates(UIForm.java:281)
at com.sun.faces.context.PartialViewContextImpl$PhaseAwareVisitCallback.visit(PartialViewContextImpl.java:510)
at com.sun.faces.component.visit.PartialVisitContext.invokeVisitCallback(PartialVisitContext.java:183)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1590)
at javax.faces.component.UIForm.visitTree(UIForm.java:335)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1601)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1601)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1601)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1601)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1601)
at javax.faces.component.UIComponent.visitTree(UIComponent.java:1601)
at com.sun.faces.context.PartialViewContextImpl.processComponents(PartialViewContextImpl.java:376)
at com.sun.faces.context.PartialViewContextImpl.processPartial(PartialViewContextImpl.java:252)
at javax.faces.context.PartialViewContextWrapper.processPartial(PartialViewContextWrapper.java:183)
at javax.faces.context.PartialViewContextWrapper.processPartial(PartialViewContextWrapper.java:183)
at javax.faces.component.UIViewRoot.processUpdates(UIViewRoot.java:1229)
at com.sun.faces.lifecycle.UpdateModelValuesPhase.execute(UpdateModelValuesPhase.java:78)
at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101)
at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)
at org.apache.myfaces.extensions.cdi.jsf2.impl.listener.phase.CodiLifecycleWrapper.execute(CodiLifecycleWrapper.java:95)
at javax.faces.webapp.FacesServlet.service(FacesServlet.java:593)
at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1550)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:343)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:217)
at org.primefaces.webapp.filter.FileUploadFilter.doFilter(FileUploadFilter.java:79)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:256)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:217)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:279)
at org.apache.catalina.core.StandardContextValve.__invoke(StandardContextValve.java:175)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:655)
at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:595)
at org.apache.catalina.core.StandardHostValve.__invoke(StandardHostValve.java:161)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java)
at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:331)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:231)
at com.sun.enterprise.v3.services.impl.ContainerMapper$AdapterCallable.call(ContainerMapper.java:317)
at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:195)
at com.sun.grizzly.http.ProcessorTask.invokeAdapter(ProcessorTask.java:860)
at com.sun.grizzly.http.ProcessorTask.doProcess(ProcessorTask.java:757)
at com.sun.grizzly.http.ProcessorTask.process(ProcessorTask.java:1056)
at com.sun.grizzly.http.DefaultProtocolFilter.execute(DefaultProtocolFilter.java:229)
at com.sun.grizzly.DefaultProtocolChain.executeProtocolFilter(DefaultProtocolChain.java:137)
at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:104)
at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:90)
at com.sun.grizzly.http.HttpProtocolChain.execute(HttpProtocolChain.java:79)
at com.sun.grizzly.ProtocolChainContextTask.doCall(ProtocolChainContextTask.java:54)
at com.sun.grizzly.SelectionKeyContextTask.call(SelectionKeyContextTask.java:59)
at com.sun.grizzly.ContextTask.run(ContextTask.java:71)
at com.sun.grizzly.util.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:532)
at com.sun.grizzly.util.AbstractThreadPool$Worker.run(AbstractThreadPool.java:513)
at java.lang.Thread.run(Thread.java:724)
 |#]

If I change the composite to

<composite:attribute name="actionDelete" />

and add the method-string to the action

 action="#{cc.attrs.actionDelete}" immediate="true"

The method is called but I get this exception:

      #|2013-12-12T17:48:16.169+0100|SEVERE|glassfish3.1.2|javax.enterprise.system.container.web.com.sun.enterprise.web|_ThreadID=102;_ThreadName=Thread-14;|WebModule[/QuesT]    FullAjaxExceptionHandler:     An exception occurred during processing JSF ajax request. Error page '/views/errors/error.xhtml' will be shown.    
javax.faces.FacesException: Unable to resolve composite component from using page using EL expression '#{cc.attrs.deleteAction}'
at com.sun.faces.facelets.tag.TagAttributeImpl$AttributeLookupMethodExpression.invoke(TagAttributeImpl.java:444)
at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:88)
at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102)
at org.apache.myfaces.extensions.cdi.jsf.impl.security.SecurityViolationAwareActionListener.processAction(SecurityViolationAwareActionListener.java:56)
at org.apache.myfaces.extensions.cdi.jsf.impl.config.view.ViewControllerActionListener.processAction(ViewControllerActionListener.java:68)
at org.apache.myfaces.extensions.cdi.jsf.impl.listener.action.CodiActionListener.processAction(CodiActionListener.java:58)
at javax.faces.component.UICommand.broadcast(UICommand.java:315)
at javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:794)
at javax.faces.component.UIViewRoot.processDecodes(UIViewRoot.java:935)
at com.sun.faces.lifecycle.ApplyRequestValuesPhase.execute(ApplyRequestValuesPhase.java:78)
at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101)
at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118)
at org.apache.myfaces.extensions.cdi.jsf2.impl.listener.phase.CodiLifecycleWrapper.execute(CodiLifecycleWrapper.java:95)
at javax.faces.webapp.FacesServlet.service(FacesServlet.java:593)
at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1550)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:343)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:217)
at org.primefaces.webapp.filter.FileUploadFilter.doFilter(FileUploadFilter.java:79)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:256)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:217)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:279)
at org.apache.catalina.core.StandardContextValve.__invoke(StandardContextValve.java:175)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:655)
at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:595)
at org.apache.catalina.core.StandardHostValve.__invoke(StandardHostValve.java:161)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java)
at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:331)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:231)
at com.sun.enterprise.v3.services.impl.ContainerMapper$AdapterCallable.call(ContainerMapper.java:317)
at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:195)
at com.sun.grizzly.http.ProcessorTask.invokeAdapter(ProcessorTask.java:860)
at com.sun.grizzly.http.ProcessorTask.doProcess(ProcessorTask.java:757)
at com.sun.grizzly.http.ProcessorTask.process(ProcessorTask.java:1056)
at com.sun.grizzly.http.DefaultProtocolFilter.execute(DefaultProtocolFilter.java:229)
at com.sun.grizzly.DefaultProtocolChain.executeProtocolFilter(DefaultProtocolChain.java:137)
at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:104)
at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:90)
at com.sun.grizzly.http.HttpProtocolChain.execute(HttpProtocolChain.java:79)
at com.sun.grizzly.ProtocolChainContextTask.doCall(ProtocolChainContextTask.java:54)
at com.sun.grizzly.SelectionKeyContextTask.call(SelectionKeyContextTask.java:59)
at com.sun.grizzly.ContextTask.run(ContextTask.java:71)
at com.sun.grizzly.util.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:532)
at com.sun.grizzly.util.AbstractThreadPool$Worker.run(AbstractThreadPool.java:513)
at java.lang.Thread.run(Thread.java:724)
 |#]

Now my Question: Why are there these exceptions, but more important is this generally possible (Composite component + dynamically adding + action-method)?

War es hilfreich?

Lösung

I never found a working solution. So I looked for another and found the conditional EL-Language:

<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:p="http://primefaces.org/ui"
xmlns:composite="http://java.sun.com/jsf/composite"
xmlns:c="http://java.sun.com/jsp/jstl/core"
xmlns:qt="http://java.sun.com/jsf/composite/components">

<composite:interface>
<composite:attribute name="questionnaireElement" type="java.util.List"
    required="true" />
<composite:attribute name="deleteQuestionAction"
    method-signature="void f()" />
<composite:attribute name="deleteInfoelementAction"
    method-signature="void f()" />
<composite:attribute name="deleteHeadelementAction"
    method-signature="void f()" />
<composite:attribute name="renderedSchematic" required="true" />
<composite:attribute name="preview" />
<composite:attribute name="parentForm" />
</composite:interface>

<composite:implementation>
<c:forEach var="element" items="#{cc.attrs.questionnaireElement}">
        <c:choose>
            <c:when test="#{element.question}">
                <p:panelGrid id="F#{element.id}" columns="1">
                    <qt:schematic_question attributesString="#{element.attributes}"
                        renderedSchematic="#{cc.attrs.renderedSchematic}"
                        questionId="#{element.id}"
                        deleteAction="#{cc.attrs.deleteQuestionAction}"
                        parentToUpdate="#{cc.attrs.parentForm}" />
                    <qt:question
                        label="#{element.getLanguageDependentName(localeBean)}" />
                    <c:if test="#{element.answer.isAnswerTypeFreetext()}">
                        <qt:answer_freetext
                            labelFreetext="#{element.answer.getDescriptionForCurrentLanguage(localeBean.locale)}" />
                    </c:if>
                    <c:if test="#{element.answer.isAnswerTypeBi()}">
                        <qt:answer_bioptions
                            disabled="#{cc.attrs.preview}"
                            btnNoOpinion="#{msg.antwortpoolButtoitemNoOpinion}"
                            labelBIOpts="#{element.answer.getDescriptionForCurrentLanguage(localeBean.locale)}" />
                    </c:if>
                    <c:if test="#{element.answer.isAnswerTypeYesNo()}">
                        <qt:answer_yesno
                            disabled="#{cc.attrs.preview}"
                            labelYesNo="#{element.answer.getDescriptionForCurrentLanguage(localeBean.locale)}" />
                    </c:if>
                    <c:if test="#element.answer.isAnswerTypeFormat()}">
                        <qt:answer_format
                            labelFormat="#{element.answer.getDescriptionForCurrentLanguage(localeBean.locale)}" />
                    </c:if>
                    <qt:separator />
                </p:panelGrid>
            </c:when>
            <c:when test="#{element.infoelement}">
                <p:panelGrid id="I#{element.id}" columns="1">
                    <qt:schematic_infoelement
                        deleteAction="#{cc.attrs.deleteInfoelementAction}"
                        infoelementId="#{element.id}"
                        parentToUpdate="#{cc.attrs.parentForm}"
                        renderedSchematic="#{cc.attrs.renderedSchematic}" />
                    <qt:infoelement
                        label="#{element.getLanguageDependentName(localeBean)}" />
                    <qt:separator />
                </p:panelGrid>
            </c:when>
            <c:when test="#{element.headelement}">
                <p:panelGrid id="K#{element.id}" columns="1">
                    <qt:schematic_headelement
                        deleteAction="#{cc.attrs.deleteHeadelementAction}"
                        headelementId="#{element.id}"
                        parentToUpdate="#{cc.attrs.parentForm}"
                        renderedSchematic="#{cc.attrs.renderedSchematic}" />
                    <qt:headelement
                        label="#{element.getLanguageDependentName(localeBean)}" />
                    <qt:separator />
                </p:panelGrid>
            </c:when>
        </c:choose>
    </c:forEach>
</composite:implementation>
</html>

It does it job even faster and cleaner.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top