如何使用react-final-form创建基于类组件的文件上传字段?
问题根因
你调试拿到的无效垃圾链接是浏览器出于安全策略返回的虚假本地路径/临时blob预览地址,本质是你没有正确从文件输入框的files属性中获取真实File对象,而是错误读取了value属性,或是把本地预览用的blob地址当成了有效上传内容。
类组件实现方案
1. 封装自定义类组件文件上传字段
import React, { Component } from 'react'; import { Field } from 'react-final-form'; class FileInput extends Component { handleChange = (e) => { const { input: { onChange } } = this.props; // 核心:获取真实File对象,而非读取e.target.value const selectedFile = e.target.files[0]; onChange(selectedFile); } render() { const { input: { value, ...restInput }, meta: { touched, error } } = this.props; return ( <div> <input type="file" {...restInput} onChange={this.handleChange} /> {touched && error && <span style={{color: 'red'}}>{error}</span>} {/* 可选:文件预览,这里生成的blob链接仅用于本地展示 */} {value && <img src={URL.createObjectURL(value)} alt="预览" style={{width: '100px'}} />} </div> ) } }
2. 在表单中使用该字段
import React, { Component } from 'react'; import { Form } from 'react-final-form'; class MyForm extends Component { onSubmit = async (values) => { // 提交时必须用FormData封装数据,不能直接传JSON const formData = new FormData(); // 把文件对象append到FormData中,第一个参数是后端约定的文件字段名 formData.append('uploadFile', values.uploadFile); // 其他普通字段也可以append进去 formData.append('otherField', values.otherField); // 发请求示例,不要手动设置Content-Type,浏览器会自动生成带boundary的正确值 const res = await fetch('/你的上传接口地址', { method: 'POST', body: formData }); const result = await res.json(); console.log('上传结果', result); } render() { return ( <Form onSubmit={this.onSubmit} initialValues={{}} render={({ handleSubmit }) => ( <form onSubmit={handleSubmit}> <Field name="uploadFile" component={FileInput} /> <button type="submit">提交</button> </form> )} /> ) } }
关键注意事项
- 不要读取文件输入框的
value属性,该属性返回的是浏览器伪造的虚假路径,没有实际作用 URL.createObjectURL生成的blob链接仅用于本地预览,禁止作为文件内容上传到后端- 提交文件必须使用
FormData封装请求体,不要使用普通JSON格式提交
内容的提问来源于stack exchange,提问作者user3697484
相关产品推荐
相关产品推荐

