2010-08-24 9 views
6

Io cercherò di essere il più breve possibile, si prega di stare con me quiC'è un modo per non inviare un intero modulo Web quando si fa clic su un pulsante?

"A.jsf" -> bean gestito: fagioli "# {} bean.list": ci porterà a B.jsf

 <p:growl id="msgs" showDetail="true"/> 
     <h:form id="myform1" enctype="multipart/form-data"> 
      <p:panel header="Upload" style="font-size: 11px;"> 
       <h:panelGrid columns="2" cellpadding="10"> 
        <h:outputLabel value="Drawing:" /> 
        <p:fileUpload fileUploadListener="#{bean.handleFileUpload}" update="msgs" allowTypes="*.*;"/>       
       </h:panelGrid> 
       <p:commandButton ajax="false" immediate="true" id="back" value="Back" action="#{bean.list}"/> 
       <p:commandButton ajax="false" id="persist" value="Persist" action="#{bean.handleRevision}" /> 
      </p:panel> 
     </h:form> 

Poi il handleFileUpload()

 if(!upload){ 
      FacesMessage msg = new FacesMessage(FacesMessage.SEVERITY_ERROR, "Error", "You do not have permission to upload."); 
      FacesContext.getCurrentInstance().addMessage(null, msg); 
     } 
     ... 

"B.jsf" - bean> gestite: bean2

... 
<p:growl id="msgs" showDetail="true"/> 
... 

Quando faccio clic su upload, mi dà un messaggio di errore "Non hai il permesso di caricare". Che è buono. Ma poi quando faccio clic su "Indietro", che mi porterà a B.jsf, vedo il messaggio growl "Non hai il permesso di caricare". ancora. Quello che sembra accadere è che quando clicco su "Indietro", invio un'altra richiesta di modulo da caricare, che poi ha generato lo stesso messaggio di errore, che viene quindi visualizzato in B.jsf. C'è un modo per risolvere questo problema, oltre a mettere il pulsante "Indietro" in una forma vuota, perché ora ho due pulsanti in piedi uno sopra l'altro, invece di fianco a fianco. Io cerco di fare questo:

FacesContext.getCurrentInstance().addMessage("tom", msg); 

sperando che avrebbe inviato al componente con id = "tom", così poi il ringhio con id = msg, non otterrebbe il carico, ma senza fortuna. Provo a attivare il flag quando faccio clic sul pulsante Back, ma il modulo Web viene richiesto prima che venga richiamato il metodo che gestisce la navigazione back.

Non è così breve come io voglio che sia, perciò voglio scusarmi per questo: D

risposta

5

accanto mettere il pulsante "Indietro" in una forma vuota, perché ora ho due pulsanti in piedi sulla cima di ogni altro

Il codice HTML <form> è di default un block element. Gli elementi di blocco HTML sono stati posizionati di default in una nuova riga. In realtà vuoi renderlo un inline element. Puoi farlo usando display: inline; in CSS.

Torna al problema attuale, tuttavia mi sorprende che il metodo fileUploadListener venga chiamato nonostante immediate="true" nello p:commandButton. Ho provato a riprodurlo e posso confermarlo. Ma non mi aspetterei che succedesse.Normalmente il immediate="true" su un pulsante è la soluzione per saltare l'invio del modulo "intero" (almeno, saltare i componenti UIInput senza questo attributo). Ulteriori indagini mi hanno insegnato che lo non è affatto un componente UIInput e che il listener viene attivato durante la fase dei valori di richiesta di applicazione anziché durante la fase di validazione o aggiornamento dei valori del modello. Quindi questo comportamento è completamente prevedibile, ma è ancora una svista nel design.

Dal momento che l'p:fileUpload richiede ajax="false" sul componente p:commandButton, si può d'altra parte anche semplicemente rimuovere dal pulsante indietro in modo che spara una richiesta ajaxical e con la presente salta il fileUploadListener essere chiamato.

+0

Eliminare 'ajax =" false "' su 'p: commandButton' del pulsante' Indietro' impedisce a 'fileUploadListener' di essere richiamato, ma impedisce anche' flusso di navigazione'. Di conseguenza, il pulsante 'Indietro' non mi porta dove, tuttavia,' display: inline' funziona alla grande, grazie mille per aver trascorso del tempo su di esso, BalusC –

+0

Prego. – BalusC

2

In realtà, mettendo il pulsante in una forma diversa suona come una soluzione eccellente. Il motivo per cui i pulsanti non si allineano più è che il nuovo elemento <form> iniziale si avvia su una propria riga. Dovresti essere in grado di impedirlo aggiungendo form { display: inline; } al tuo file CSS.

Detto questo, se si dispone di alcuni messaggi di errore residui che si desidera eliminare, è possibile farlo nel metodo di inizializzazione del proprio bean di supporto (se ne esiste uno). I seguenti lavori: peachily

public void clearErrorMessages() { 
    //it may get messy to debug why messages are swallowed 
    logger.debug("clearing messages, coming from " + new Exception().getStackTrace()[1]); 

    Iterator iter = FacesContext.getCurrentInstance().getMessages(); 
    while (iter.hasNext()) { 
     FacesMessage msg = (FacesMessage) iter.next(); 
     logger.debug("clearing message: " + msg.getDetail()); 
     iter.remove(); 
    } 
} 

Lo svantaggio è che eventuali errori che si verificano tra la presentazione della forma e l'inizializzazione del backing bean della pagina di destinazione sono inghiottite.

+0

grazie. Provo questo ' Pulsante Invia Pulsante Indietro', ne ho ancora due in piedi uno sopra l'altro. Il metodo 'clearErrorMessages()', hai detto di metterlo nel metodo di inizializzazione del bean gestito di destinazione, beh il mio bean gestito di destinazione ha 'SessionScoped', quindi il costruttore sarà chiamato una sola volta quando l'applicazione prima caricherà, a meno che non ci siano alcuni tipo di annotazioni per rilevare quando la pagina si ricarica. –

Problemi correlati