如何在上传后清除文件输入框文本?Laravel+Inertia.js+Vue3问题
问题解决:Inertia.js + Vue3 文件上传后表单重置但文件名残留
问题场景:使用Laravel 9 + Inertia.js + Vue3开发,按官方教程实现多文件上传后,调用formFiles.reset()或直接赋值formFiles.report_pdfs = [],页面不跳转,但文件输入框仍保留已上传的文件名。
核心原因
input[type="file"]的value属性是只读的,Inertia的useForm表单状态重置只会更新JS层面的变量,无法同步修改DOM中文件输入框的状态,所以文件名会残留。
解决方案1:通过Ref直接操作DOM元素
给文件输入框添加ref,上传成功后直接重置其value:
<template> <input type="file" multiple ref="reportFilesInput" @input="formFiles.report_pdfs = $event.target.files" > <button @click="uploadReportFiles">上传</button> </template> <script setup> import { ref } from 'vue'; import { useForm } from '@inertiajs/vue3'; const props = defineProps(['survey']); const reportFilesInput = ref(null); const formFiles = useForm({ report_pdfs: [] }); const uploadReportFiles = () => { formFiles.post(route('uploadReports', { surveyId: props.survey.id }), { preserveScroll: true, onSuccess: () => { formFiles.reset(); // 重置文件输入框 if (reportFilesInput.value) { reportFilesInput.value.value = ''; } }, }); }; </script>
解决方案2:通过Vue响应式Key强制重新渲染
给文件输入框绑定一个动态key,上传成功后更新key值,让Vue重新创建输入框元素,自然清空状态:
<template> <input type="file" multiple :key="fileInputKey" @input="formFiles.report_pdfs = $event.target.files" > <button @click="uploadReportFiles">上传</button> </template> <script setup> import { ref } from 'vue'; import { useForm } from '@inertiajs/vue3'; const props = defineProps(['survey']); const fileInputKey = ref(0); const formFiles = useForm({ report_pdfs: [] }); const uploadReportFiles = () => { formFiles.post(route('uploadReports', { surveyId: props.survey.id }), { preserveScroll: true, onSuccess: () => { formFiles.reset(); // 更新key触发重新渲染 fileInputKey.value += 1; }, }); }; </script>
说明
- 方案1直接操作DOM,代码简洁,适合简单场景;
- 方案2遵循Vue响应式机制,无需操作DOM,更符合Vue开发理念;
- 不建议使用
preserveState: false,会丢失表单外的其他页面状态,不符合需求。
内容的提问来源于stack exchange,提问作者codingdaddy
相关产品推荐
相关产品推荐

