简体   繁体   English

Vue.js文件上载的选项404

[英]OPTIONS 404 on Vue.js file upload

I have defined cors in my express app and don't have this issue with most of the routes. 我已经在我的express应用中定义了cors,并且大多数路线都没有这个问题。 But, for a particular component that I use to upload images: 但是,对于我用来上传图像的特定组件:

<input type="file" class="form-control" @change="imageChagned">

<div  @click="postPhoto">Upload Photo</div>  

methods: 方法:

postPhoto: function() {
    console.log('sending photo');
    axios.post( this.BASE_URL + "/profile/addphoto", {
    file: this.image 
    }, this.jwt).then( (res) => { 
    console.log('after photo sent');
    this.image = '';
    console.log(res);
    })
      .catch( (error) => { 

        console.log(error);

      });

},

imageChagned(e) { 
    var reader = new FileReader();
    reader.readAsDataURL(e.target.files[0]);
    reader.onload = (e) => {
            this.image = e.target.result;    
        }
    } 

I get this error in browser: 我在浏览器中收到此错误:

OPTIONS http://127.0.0.1:3000/profile/addphoto 404 (Not Found)
dispatchXhrRequest @ xhr.js?b50d:178
xhrAdapter @ xhr.js?b50d:12
dispatchRequest @ dispatchRequest.js?5270:59
Promise.then (async)
request @ Axios.js?0a06:51
Axios.(anonymous function) @ Axios.js?0a06:71
wrap @ bind.js?1d2b:9
postPhoto @ AddPhoto.vue?0625:242
invoker @ vue.runtime.esm.js?2b0e:2023
fn._withTask.fn._withTask @ vue.runtime.esm.js?2b0e:1822
addphoto:1 Access to XMLHttpRequest at 'http://127.0.0.1:3000/profile/addphoto' from origin 'http://127.0.0.1:8080' has been blocked by CORS policy: Response to preflight request doesn't pass access control check: It does not have HTTP ok status.

here is the router that receives the post: 这是收到帖子的路由器:

  router.post('/addphoto',  checkAuth, (req, res)=> {

    console.log('add photo post received');
       let filename = Math.floor(Math.random() * 100000);
  let dir = './uploads/' + req.user.id;
    if (!fs.existsSync(dir)){
        fs.mkdirSync(dir);
    }   
    base64String = req.body.file;
    let str = base64String.split(';base64,');
    let base64Image = str[1];
    let extRaw = str[0];
    let ext = extRaw.split('/')[1].toLowerCase();
    let extArray = ['jpg', 'jpeg', 'png', 'gif'];
    const buffer = Buffer.from(base64String.substring(base64String.indexOf(',') + 1));
    fileSizeMB = buffer.length / 1e+6
    //Check file extension
    if (!extArray.includes(ext)) {
      res.status(403).json({msg: 'error: file extention not allowed'})
      return
    };

    //Check file size
    if(fileSizeMB > 5) {
      res.status(403).json({msg: 'error: file is too large'})
      return
    }

    let imgId =  filename + '.' + ext; 
    let filePath = dir + "/" + imgId;
    fs.writeFile( filePath, base64Image, {encoding: 'base64'}, function(err) {
      });
      const photoFields = {};
      photoFields.photos = []
      let p = {}

      p.imgId =  imgId  ;
      p.visible = 'all'
    User.findOne({ _id: req.user.id }).then(user => {
      if (!user.images.profileImg.length > 0 ) {
        user.images.profileImg = p.imgId;
      }

      user.images.photos.push(p);
      user.save().then(()=>{
        console.log('new photo is saved');
        res.json({ images: user.images });
      }).catch(err =>
      console.log(err)
      );

    });


  });

This problem bugs me for hours so really appreciate your hints to fix it. 这个问题困扰着我数小时,非常感谢您提出的修复建议。

The odd thing is that the component was working fine but it ceased to work after some small changes that I've made to my code. 奇怪的是,该组件运行良好,但是在我对代码进行了一些小的更改之后,该组件停止工作。

As the error indicates, there is no endpoint called /profile/addphoto for method OPTIONS . 如错误所示,方法OPTIONS没有名为/profile/addphoto终结点。 The route you posted would not be hit by an OPTIONS request, since you specified that it only receives POST . 因为您指定仅接收POST ,所以您发布的路由不会被OPTIONS请求打中。

The OPTIONS request is used to let the requester know how it is allowed to use your API, so simply return status 200 after setting the cors headers. OPTIONS请求用于让请求者知道如何使用您的API,因此只需在设置cors标头后返回状态200。 I usually do it by adding this to intercept any OPTIONS request made to the API. 我通常通过添加它来拦截对API所做的任何 OPTIONS请求来完成此操作。 Just add it somewhere in the beginning of the routing: 只需将其添加到路由的开头:

app.use(function(req, res, next) {
    res.set('Access-Control-Allow-Origin', '*');
    res.set('Access-Control-Allow-Headers', 'Origin, Accept, Content-Type, X-Requested-With, auth_token, X-CSRF-Token, Authorization');
    res.set('Access-Control-Allow-Methods', 'POST, GET, OPTIONS, DELETE, PUT, PATCH');
    res.set('Access-Control-Allow-Credentials', 'true');

    // intercept OPTIONS method
    if (req.method === 'OPTIONS') {
        return res.status(200).end();
    }

    next();
});

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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