【问题标题】:Why do I get a mongoose ValidationError?为什么我会收到 mongoose ValidationError?
【发布时间】:2017-05-20 12:44:47
【问题描述】:

我是 MEAN 堆栈的初学者,正在尝试学习以下教程:adrianmejia.com/blog/2014/10/01/creating-a-restful-api-tutorial-with-nodejs-and- mongodb/.我正在使用 Cloud 9 在线 IDE。

本教程的一部分涉及使用 curl 和 Postman 测试数据库 POST。我成功发布了一个 GET 请求,在本教程的这一点上,它为 med 提供了一个空数组。

我用 curl -XGET myc9urlhere:8080/todos - 成功(获取 [])

然后尝试curl -XPOST myc9urlhere:8080/todos -d 'name=Somename&completed=false&note=somenote' - 失败

stacktrace如下:

ValidationError: Todo validation failed
    at MongooseError.ValidationError (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/error/validation.js:23:11)
    at model.Document.invalidate (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/document.js:1486:32)
    at model.Document.set (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/document.js:753:10)
    at model._handleIndex (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/document.js:596:14)
    at model.Document.set (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/document.js:556:24)
    at model.Document (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/document.js:68:10)
    at model.Model (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/model.js:47:12)
    at new model (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/model.js:3250:13)
    at /home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/model.js:1864:51
    at /home/ubuntu/workspace/todo-api/node_modules/mongoose/node_modules/async/internal/parallel.js:27:9
    at eachOfArrayLike (/home/ubuntu/workspace/todo-api/node_modules/mongoose/node_modules/async/eachOf.js:57:9)
    at exports.default (/home/ubuntu/workspace/todo-api/node_modules/mongoose/node_modules/async/eachOf.js:9:5)
    at _parallel (/home/ubuntu/workspace/todo-api/node_modules/mongoose/node_modules/async/internal/parallel.js:26:5)
    at parallelLimit (/home/ubuntu/workspace/todo-api/node_modules/mongoose/node_modules/async/parallel.js:85:26)
    at /home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/model.js:1882:5
    at Function.create (/home/ubuntu/workspace/todo-api/node_modules/mongoose/lib/model.js:1852:17)

需要注意的是,我也曾使用 Chrome 扩展 Postman 进行过尝试。该教程说我必须使用x-www-form-urlencoded,它会返回相同的错误。见截图。如果我改用表单数据设置,我实际上成功地将一些数据插入数据库,但只是虚假的东西。请参阅第二个屏幕截图。

Postman fail

Postman form-data

我真的尝试过自己研究 - 也许本教程也不是最好的起点:)。下面我将详细介绍代码。

非常感谢您为解决此问题提供的任何帮助。

与教程相同,我为待办事项列表项创建了一个模型,如图所示 (Todo.js):

var mongoose = require('mongoose');

var TodoSchema = new mongoose.Schema({
  name: String,
  completed: Boolean,
  note: String
});

module.exports = mongoose.model('Todo', TodoSchema);

现在在我的快速路由文件 todos.js 中,我有以下代码:

var express = require('express');
var router = express();
//express.Router() was the original here, that failed on router.get
//as router was then undefined for some reason.

var Todo = require('../models/Todo.js');

/* GET /todos listing. */
router.get('/', function(req, res, next) {
  Todo.find(function (err, todos) {
    if (err) return next(err);
    res.json(todos);
  });
});

/* POST /todos */
router.post('/', function(req, res, next) {
  Todo.create(req.body, function (err, post) {
    if (err) return next(err);
    res.json(post);
  });
});

module.exports = router;

因为我不知道这里到底出了什么问题,所以我还将发布我的 app.js 的摘录,显示我的数据库连接

var routes = require('./routes/index');
var users = require('./routes/users');
var todos = require('./routes/todos');

var app = express();

// load mongoose package
var mongoose = require('mongoose');
// Use native Node promises
mongoose.Promise = global.Promise;
// connect to MongoDB
mongoose.connect('mongodb://'+process.env.IP+'/todo-api')
  .then(() =>  console.log('connection succesful'))
  .catch((err) => console.error(err));

app.use('/', routes);
app.use('/users', users);
app.use('/todos', todos);

以及生成的 package-json(我使用的是 Cloud 9 IDE)

{
  "name": "application-name",
  "version": "0.0.1",
  "private": true,
  "scripts": {
    "start": "node app.js"
  },
  "dependencies": {
    "ejs": "*",
    "express": "3.2.6",
    "mongoose": "^4.7.6"
  }
}

【问题讨论】:

    标签: angularjs node.js mongodb mongoose cloud9


    【解决方案1】:

    转到您目录中的数据文件夹。里面有一个文件 mongod.lock。删除它(您不需要 root 权限)只需使用 rm mongod.lock。回到主目录并输入 ./mongod。希望这能解决问题

    【讨论】:

      【解决方案2】:

      我认为您在这里遇到的主要问题是所有后置参数都是字符串。这对于你的TodoSchemanamenote 字段来说是好的,但是当涉及到completed 字段时会中断,因为它是布尔值。要解决此问题,请在创建 ToDo 条目之前尝试将字符串转换为布尔值。

      /* POST /todos */
      router.post('/', function(req, res, next) {
        req.body.completed = (req.body.completed === 'true');
        Todo.create(req.body, function (err, post) {
          if (err) return next(err);
          res.json(post);
        });
      });
      

      此外,虚假帖子有效的原因是您没有验证帖子数据。考虑确保通过您的路线输入的帖子数据包含所有必填字段,并且不包含任何危险内容。

      【讨论】:

      • 感谢您的回复。我已经尝试过您的建议,但问题仍然存在。我能够从请求正文中的名称、已完成和注释中提取正确的值。它们似乎都是正确的,除了似乎已完成的参数被缓存或其他东西,因为当我在客户端更改它时它不会立即在服务器端更改 - 它似乎将旧值存储了一段时间,这很奇怪.我还尝试通过 req.body.completed = true; 对 body 参数强制一个有效的布尔值;这也不会消除验证错误。
      猜你喜欢
      • 2022-06-16
      • 2023-04-05
      • 2016-08-21
      • 2014-07-04
      • 2020-06-06
      • 2018-12-26
      • 2021-03-05
      • 2013-07-13
      相关资源
      最近更新 更多