如何使用Axios和React更新文件

问题描述 投票:0回答:1

我用帖子/文章构建了一个api,现在我在前端工作。我在为现有帖子上传新照片时遇到问题。我尝试了两种最常用的照片方法,即formData和JSON Base64。两种方法Please upload a file, code: 400都收到相同的错误响应。我不确定哪里出了问题,因此我将提供所有相关文件。

articles.js(server)

exports.articlePhotoUpload = asyncHandler(async (req, res, next) => {
    const article = await Article.findById(req.params.id);

    if (!article) {
        return next(
            new ErrorResponse(`Article not found with id of ${ req.params.id }`, 404)
        );
    }

    //Make sure user is article owner || make sure user is admin
    if (article.user.toString() !== req.user.id || req.user.role !== 'admin') {
        return next(
            new ErrorResponse(
                `User ${ req.user.id } is not authorized to update this article`,
            )
        )
    }

    if (!req.files) {
        return next(new ErrorResponse(`Please upload a file`, 400))
    }

    const file = req.files.file;

    // Confirm the image is a photo
    if (!file.mimetype.startsWith('image')) {
        return next(new ErrorResponse(`Please upload an image file`, 400))
    }

    // Check File Size
    if (file.size > process.env.MAX_FILE_UPLOAD) {
        return next(
            new ErrorResponse(`Please upload an image less than ${ MAX_FILE_UPLOAD }`, 400)
        )
    }

    // Create custom filename
    file.name = `photo_${ article._id }${ path.parse(file.name).ext }`;

    file.mv(`${ process.env.FILE_UPLOAD_PATH }/${ file.name }`, async err => {
        if (err) {
            console.log(err);
            new ErrorResponse(`Problem with file upload`, 500);
        }

        await Article.findByIdAndUpdate(req.params.id, { photo: file.name });

        res.status(200).json({
            success: true,
            data: file.name
        });

    });

});

^以上功能是在服务器端触发错误消息的位置。

axios.js(客户端)

...
axios.defaults.baseURL = 'http://<<ip address>>/api/v1';
axios.defaults.headers.common['Authorization'] = 'Bearer ' + localStorage.getItem('auth');
axios.defaults.headers.post['Content-Type'] = 'application/json';


export const uploadPhoto = (id, data) => {
    return axios.put(`/articles/${ id }/photo`, {
        data
    })
}
...

^我有种感觉,我可以更好地格式化导出的函数。我可能在这里错过了一些东西。

UploadPhoto.jsx(JSON尝试)

const UploadPhoto = (props) => {
    const { register, handleSubmit } = useForm();
    const { state } = useStateMachine(updateAction);
    const [file, setFile] = useState(null);
    const [filename, setFilename] = useState(null);

    const onSubmit = async () => {
        const toBase64 = file => new Promise((resolve, reject) => {
            const reader = new FileReader();
            reader.readAsDataURL(file);
            reader.onload = () => resolve(reader.result);
            reader.onerror = error => reject(error);
            console.log(reader.result)
        });

        const data = {
            title: filename,
            file: await toBase64(file),
        }

        uploadPhoto(`5ea5e73044718d0b2c2ae5df`, data)
            .then(res => console.log(res))
            .catch(err => console.log(err.response.data.error))
    }

    const handleChange = (e) => {
        setFile(e.target.files[0]);
        setFilename(e.target.files[0].name);
    }

    return (
        <form onSubmit={handleSubmit(onSubmit)}>
            <h2>Cover Image</h2>
            <label>
                Select A File:
            </label>
            <img id="image" src="" alt="" />
            <input
                type="file"
                name="photo"
                ref={register}
                defaultValue={state.data.photo}
                onChange={handleChange}

            />
            <label htmlFor="">
                Filename
            </label>
            <input type="submit" />
        </form>
    )
}

export default withRouter(UploadPhoto);

UploadPhoto.jsx(formData尝试)

const onSubmit = () => {
        const formData = new FormData();
        formData.append("file", file);
        console.log(file)

        uploadPhoto(`5ea5e73044718d0b2c2ae5df`, formData)
            .then(res => console.log(res))
            .catch(err => console.log(err.response.data.error))
    }

这是我第一次构建自己的api,因此我将服务器代码放在这里。但是,我有90%的把握肯定是在客户端出错,很可能是在axios.js文件中。

javascript json reactjs axios form-data
1个回答
0
投票

让我们尝试这个例子:

const fileUpload = require('express-fileupload');
const app = express();

// enable files upload -- this should also make 'req.files' accessible
app.use(fileUpload({
    createParentPath: true
}));

您需要安装模块express-fileupload-> npm i express-fileupload

((来源:https://attacomsian.com/blog/uploading-files-nodejs-express

© www.soinside.com 2019 - 2024. All rights reserved.