12

fileLimit はもう primefaces 3.4 には存在しないので、バリデーターを実装する回避策を試みています。問題は、validate メソッドが呼び出されないことです。それが私のバリデータです:

@FacesValidator(value ="fileLimitValidator")
public class FileLimitValidator implements Validator {

    @Override
    public void validate(final FacesContext context, final UIComponent component,
            final Object value) throws ValidatorException {

        final String fileLimit = (String)component.getAttributes().get("fileLimit");
        final String size = (String)component.getAttributes().get("size");

        if (fileLimit!=null && size!=null) {
            if (Integer.valueOf(size) >= Integer.valueOf(fileLimit)) {
                FacesUtils.throwErrorExceptionFromComponent(component,"fichero_confidencialidad_error");
            }
        }
    }
}

そして私のfaceletで試しました:

    <p:fileUpload id="#{id}FileUpload"
        fileUploadListener="#{bean[metodoTratarFichero]}" mode="advanced"
        multiple="true" allowTypes="#{allowTypes}" showButtons="false"
        update="#{id}ListaDocs #{id}MsgError" auto="true"
        label="#{fileuploadmsg.label_boton}"
        invalidFileMessage="#{fileuploadmsg.tipo_incorrecto}" >

        <f:validator validatorId="fileLimitValidator"/>
        <f:attribute name="fileLimit" value="#{fileLimit}"/>
        <f:attribute name="size" value="#{listaDocumentos.size}"/>
    </p:fileUpload>

と:

    <p:fileUpload id="#{id}FileUpload"
        fileUploadListener="#{bean[metodoTratarFichero]}" mode="advanced"
        multiple="true" allowTypes="#{allowTypes}" showButtons="false"
        update="#{id}ListaDocs #{id}MsgError" auto="true"
        label="#{fileuploadmsg.label_boton}"
        invalidFileMessage="#{fileuploadmsg.tipo_incorrecto}" 
        validator="fileLimitValidator">

        <f:attribute name="fileLimit" value="#{fileLimit}"/>
        <f:attribute name="size" value="#{listaDocumentos.size}"/>
    </p:fileUpload>

と:

    <p:fileUpload id="#{id}FileUpload"
        fileUploadListener="#{bean[metodoTratarFichero]}" mode="advanced"
        multiple="true" allowTypes="#{allowTypes}" showButtons="false"
        update="#{id}ListaDocs #{id}MsgError" auto="true"
        label="#{fileuploadmsg.label_boton}"
        invalidFileMessage="#{fileuploadmsg.tipo_incorrecto}" 
        validator="#{fileLimitValidator}">

        <f:attribute name="fileLimit" value="#{fileLimit}"/>
        <f:attribute name="size" value="#{listaDocumentos.size}"/>
    </p:fileUpload>

と:

    <p:fileUpload id="#{id}FileUpload"
        fileUploadListener="#{bean[metodoTratarFichero]}" mode="advanced"
        multiple="true" allowTypes="#{allowTypes}" showButtons="false"
        update="#{id}ListaDocs #{id}MsgError" auto="true"
        label="#{fileuploadmsg.label_boton}"
        invalidFileMessage="#{fileuploadmsg.tipo_incorrecto}" 
        validator="#{fileLimitValidator.validate}">

        <f:attribute name="fileLimit" value="#{fileLimit}"/>
        <f:attribute name="size" value="#{listaDocumentos.size}"/>
    </p:fileUpload>

ただし、validate メソッドは呼び出されません。それを行う正しい方法は何ですか?

4

2 に答える 2

17

FileUploadおよびソースコードによるとFileUploadRenderer、バリデーターはが使用された場合にのみ呼び出されますmode="simple"(注:これにはajax="false"onコマンドが必要です)。詳細モードでは、アップロードされたファイルがコンポーネントの送信された値として設定されないためnull、listenerメソッドが呼び出されるまでファイルは残ります。送信された値がである限りnull、バリデーターは呼び出されません。

これが意図的なものかどうかはわかりません。UploadedFile理論的には、送信された値として設定し、バリデーターにそれを信頼させることが可能であるはずです。PrimeFacesIssueTrackerで拡張レポートを作成することをお勧めします。

その間、それは悪い習慣であるにもかかわらず、あなたの最善の策は実際にfileUploadListenerメソッドで検証を実行することです。FacesContext次のような方法で、検証の失敗と顔の追加メッセージをトリガーできます。

if (fail) {
    context.validationFailed();
    context.addMessage(event.getComponent().getClientId(context), new FacesMessage(
        FacesMessage.SEVERITY_ERROR, messageSummary, messageDetail));
}

<p:fileUpload>それ以外の場合は、送信された値を設定するカスタムレンダラーを作成する必要がありますdecode()(ただし、実際に機能することを保証するものではありません。特定の問題に遭遇する可能性があります。 PrimeFacesが最初にそのように実装しなかった理由)。

ちなみに、1回目と2回目のバリデーターの試みは正しいです。@ManagedBean3番目の試行は、の代わりに使用した場合にのみ機能します@FacesValidatorこれは、の注入@EJBが必須である場合によく実行されます。これは、では不可能です@FacesValidator)。4回目の試行は無効です。

于 2012-12-13T20:39:06.983 に答える
3

高度なモード (ajax) で必要な primefaces ファイルのアップロードを検証するには、これを使用できます。

<f:metadata>
    <f:event listener="#{bean.processValidations()}" type="postValidate" />
</f:metadata>

メソッドの実装は、次のbean.processValidations()ようなものになります。

public void processValidations() {
        FacesContext context = FacesContext.getCurrentInstance();
        UIInput fileUploadComponent = fileUploadsBean.getFileUploadComponent();
        if (fileUploadComponent!=null && !isFileUploaded()) {
            fileUploadComponent.setValid(false);
            context.addMessage(fileUploadComponent.getClientId(context), new FacesMessage(FacesMessage.SEVERITY_ERROR, messageSummary, messageDetail));
            context.validationFailed();
        }
    }

fileUploadsBeanメソッドが定義された Bean に注入する REQUEST スコープの CDI Bean (標準の JSF ManagedBeans では機能しません) はどこにprocessValidations()あり、メソッドfileUploadsBean.getFileUploadComponent()は primefaces ファイルアップロードコンポーネントを返します (<p:fileUpload binding="#{fileUploadsBean.fileUploadComponent}" ...>そのために使用します)。このメソッドisFileUploaded()は、ファイルがアップロードされたかどうかを判断します (おそらく、fileUploadListener から入力したメンバー変数の null チェックだけです)。

ファイルのアップロード ボタンを強調表示する場合は、もちろん条件付きで styleClass を追加できます。これを使用して、たとえば赤い境界線を追加できます。

styleClass="#{fileUploadsBean.fileUploadComponent.valid ? '' : 'validationFailed'}"

その結果、primefaces ファイルのアップロードの検証失敗メッセージが、他のすべての jsf 検証メッセージと共に表示されます。検証メッセージの順序を維持することに問題がある可能性があります (常に最後になります) が、ユーザーがさまざまなフィールドからのすべての標準 jsf 検証メッセージとバッキング Bean でのアクションを処理した後、失敗したアップロード ファイルの検証を表示するよりも優れています。やっとたどり着きました。

于 2015-11-10T16:23:51.060 に答える