简体   繁体   中英

How to remove error message in file upload?

I am making a file upload using antd design and here we are allowing the user to upload only JPEG images.

Here we have set the rules to upload only maximum of 3 JPEG images.

rules={[
          { required: true },
          { max: 3, message: "Only 3 attachments are allowed", type: "array" }
        ]}

Issue:

Here when we upload 3 JPEG files, it is fine.

If we upload 4th file as JPEG , the error is showing which is also fine.

But when we upload 4th file as invalid file, the error still shows which is incorrect.

Steps to Reproduce:

-> Upload 3 JPEG files,

-> Upload 4th file which is in another format not JPEG .

If you observe the results, the uploaded file will be ignored in UI but we still see the error message as Only 3 attachments are allowed .

在此处输入图像描述

See the above image for better representation. Uploading 4th file as .html format and hence getting error in the modal popup which is correct but the rules error message (in text after last file) still displays even though there are only 3 files in the UI.

Working Sandbox:

编辑 antd-file-upload-validation-in-reactjs (forked)

I see the issue might be from the line 46 - 51 which has,

  const normFile = (e: any) => {
    if (Array.isArray(e)) {
      return e;
    }
    return e && e.fileList;
  };

The above line returns the uploaded files hidden even though it exceeds the limit.

Kindly please help me to resolve the above issue as I am stuck for long time and big thanks in advance.

The problem is that even you see three files in UI but the error that appears below the files because you are using antd form and anything that wrapped with <Form.Item> and having a name attribute, it is controlled by antd form. By passing fileList state to Upload component, this does not mean that you are controlling the fileList and you have exactly 3 files. To prove this, let me you give an example:

1. Upload 3 jpeg files and get the values of attachment using form.getFieldValue('attachment') . Expected Result: An array with 3 files, No Error Below the files

2. Upload one more jpeg or any file & check the attachment value with form.getFieldValue('attachment') Expected Result: An array of files with length 4 & it should be 3 files in the array according to you. Also an error that doesn't disappear.

There are two problems in your code.
Problem 1: As you said if you upload 4 file that is jpeg after uploading 3 jpeg files, i still see 4 files in UI.
Solution: Don't add more files in fileList if its already have 3 files. In beforeUpload, replace setFileList((prev) => [...prev, file]); with the following code:

setFileList((prev) => {
    if (prev.length < 3) {
        return [...prev, file];
    }
    return prev;
});

Second Problem: Error doesn't disappears even you have 3 files in UI.
Solution: You can use onChange Function. You can check if info.fileList have length greater than 3, then just replace the form attachment value with the original fileList. I set a timeout to show the error that you can upload 3 attachments and remove the error message after 2 second.

onChange: (info) => {
    if (info.fileList.length > 3) {
        setTimeout(() => form.setFieldsValue({ attachment: fileList as any }), 2000);
    }
}

Hope this solve your issue.

Complete Code

import { useState, useMemo } from 'react';
import { Upload, Button, message, Form } from 'antd';
import { UploadOutlined } from '@ant-design/icons';
import { UploadFile, UploadProps } from 'antd/lib/upload/interface';
import { RcFile } from 'rc-upload/lib/interface';

interface FormRule {
    title: string;
    attachment?: { file: RcFile; fileList: RcFile[] };
}

const Uploader = () => {
    const [fileList, setFileList] = useState<UploadFile<any>[]>([]);
    const [form] = Form.useForm<FormRule>();

    const validateFileType = ({ type, name }: UploadFile, allowedTypes: string[] = ['image/jpeg']) => {
        return allowedTypes.includes(type!);
    };

    const uploadProps = useMemo(
        () =>
            ({
                multiple: true,
                beforeUpload: (file: UploadFile) => {
                    const isAllowedType = validateFileType(file);
                    if (!isAllowedType) {
                        message.error(`${file.name} is not JPEG file`);
                        return false;
                    }
                    setFileList((prev) => {
                        if (prev.length < 3) {
                            return [...prev, file];
                        }
                        return prev;
                    });
                    return false;
                },
                onRemove: (file: UploadFile) => {
                    setFileList((prev) => prev.filter((item) => item.uid !== file.uid));
                },
                onChange: (info) => {
                    if (info.fileList.length > 3) {
                        setTimeout(() => form.setFieldsValue({ attachment: fileList as any }), 2000);
                    }
                }
            } as UploadProps),
        [fileList]
    );

    const onSubmit = async (data: FormRule) => {
        console.log('data');
    };

    const normFile = (e: any) => {
        if (Array.isArray(e)) {
            return e;
        }
        return e && e.fileList;
    };

    return (
        <Form form={form} onFinish={onSubmit} layout='vertical'>
            <Form.Item
                name='attachment'
                valuePropName='attachment'
                getValueFromEvent={normFile}
                rules={[{ required: true }, { max: 3, message: 'Only 3 attachments are allowed', type: 'array' }]}
            >
                <Upload {...uploadProps} fileList={fileList}>
                    <Button icon={<UploadOutlined />}>Upload JPEG only</Button>
                </Upload>
            </Form.Item>

            <Button type='primary' htmlType='submit'>
                Submit
            </Button>
        </Form>
    );
};

export default Uploader;

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM