wake-up-neo.com

Was ist ein Mongoose-Fehler Die Umwandlung in ObjectId ist für den Wert XXX im Pfad "_id" fehlgeschlagen?

Wenn Sie eine Anfrage an /customers/41224d776a326fb40f000001 senden und ein Dokument mit _id41224d776a326fb40f000001 nicht vorhanden ist, ist docnull und ich gebe einen 404 zurück:

  Controller.prototype.show = function(id, res) {
    this.model.findById(id, function(err, doc) {
      if (err) {
        throw err;
      }
      if (!doc) {
        res.send(404);
      }
      return res.send(doc);
    });
  };

Wenn _id jedoch nicht mit dem übereinstimmt, was Mongoose als "Format" erwartet (ich nehme an), zum Beispiel mit GET /customers/foo, wird ein seltsamer Fehler zurückgegeben:

CastError: Die Umwandlung in ObjectId ist für den Wert "foo" im Pfad "_id" fehlgeschlagen.

Also, was ist dieser Fehler?

77
gremo

Die findById-Methode von Mongoose wandelt den id-Parameter in den Typ des _id-Felds des Modells um, damit dieses das entsprechende Dokument richtig abfragen kann. Dies ist eine ObjectId, aber "foo" ist keine gültige ObjectId, daher schlägt die Umwandlung fehl.

Dies passiert nicht bei 41224d776a326fb40f000001, da diese Zeichenfolge eine gültige ObjectId ist.

Um dies zu beheben, können Sie vor dem Aufruf von findById eine Prüfung hinzufügen, um zu prüfen, ob id eine gültige ObjectId ist oder nicht:

if (id.match(/^[0-9a-fA-F]{24}$/)) {
  // Yes, it's a valid ObjectId, proceed with `findById` call.
}
134
JohnnyHK

Verwenden Sie vorhandene Funktionen zur Überprüfung der ObjectID.

var mongoose = require('mongoose');
mongoose.Types.ObjectId.isValid('your id here');
29
xpepermint

Analysieren Sie diese Zeichenfolge als ObjectId?

Hier in meiner Bewerbung mache ich:

ObjectId.fromString( myObjectIdString );
10
gustavohenke

Sie können ObjectId.isValid auch wie folgt verwenden: 

if (!ObjectId.isValid(userId)) return Error({ status: 422 })
3
Ze Rubeus

Ich habe das gleiche Problem, das ich hinzufüge
_ id: String .in Schema, dann beginnt die Arbeit

1
s.babar

Dies ist eine alte Frage, Sie können jedoch auch das Paket "Express-Validator" verwenden, um die Anfrageparameter zu überprüfen

express-Validator Version 4 (aktuell):

validator = require('express-validator/check');

app.get('/show/:id', [

    validator.param('id').isMongoId().trim()

], function(req, res) {

    // validation result
    var errors = validator.validationResult(req);

    // check if there are errors
    if ( !errors.isEmpty() ) {
        return res.send('404');
    }

    // else 
    model.findById(req.params.id, function(err, doc) { 
        return res.send(doc);
    });

});

express-Validator Version 3:

var expressValidator = require('express-validator');
app.use(expressValidator(middlewareOptions));

app.get('/show/:id', function(req, res, next) {

    req.checkParams('id').isMongoId();

    // validation result
    req.getValidationResult().then(function(result) {

        // check if there are errors
        if ( !result.isEmpty() ) {
            return res.send('404');
        }

        // else
        model.findById(req.params.id, function(err, doc) {
            return res.send(doc);
        });

    });

});
1
YouneL
 if(mongoose.Types.ObjectId.isValid(userId.id)) {
        User.findById(userId.id,function (err, doc) {
            if(err) {
                reject(err);
            } else if(doc) {
                resolve({success:true,data:doc});
            } else {
                reject({success:false,data:"no data exist for this id"})

            }
        });
        } else {
            reject({success:"false",data:"Please provide correct id"});
        }

am besten ist es, die Gültigkeit zu prüfen

1
yogesh agrawal

Ich musste meine Routen über andere Routen verschieben, für die die Routenparameter gelten:

// require express and express router

const express = require("express");
const router = express.Router();

// move this `/post/like` route on top

router.put("/post/like", requireSignin, like);

// keep the route with route parameter `/:postId` below regular routes

router.get("/post/:postId", singlePost);
0
Ryan Dhungel

Die Art und Weise, wie ich dieses Problem behebe, ist die Umwandlung der ID in eine Zeichenfolge

ich mag es ausgefallen mit Backtick: `${id}`

dies sollte das Problem ohne zusätzlichen Aufwand beheben

0
AiU

Ich ging zu einer Anpassung der @ gustavohenke-Lösung und implementierte cast ObjectId in einen try-catch um den ursprünglichen Code gewickelt , um den Ausfall des ObjectId-Castings als Validierungsmethode zu nutzen.

Controller.prototype.show = function(id, res) {
  try {
    var _id = mongoose.Types.ObjectId.fromString(id);



    // the original code stays the same, with _id instead of id:

    this.model.findById(_id, function(err, doc) {
      if (err) {
        throw err;
      }
      if (!doc) {
        res.send(404);
      }
      return res.send(doc);
    });



  } catch (err) {
    res.json(404, err);
  }
};
0
Charney Kaye

Verwenden Sie immer mongoose.Types.ObjectId('your id')für Bedingungen in Ihrer Abfrage, um das ID-Feld zu überprüfen, bevor Sie die Abfrage ausführen, da Ihre App nicht abstürzt.

0
Suman

ObjectId besteht aus folgenden Dingen.

  1. ein 4-Byte-Wert, der die Sekunden seit der Unix-Epoche darstellt
  2. ein zufälliger 5-Byte-Wert (Maschinen-ID 3 Byte und Prozessor-ID 2 Byte)
  3. ein 3-Byte-Zähler, beginnend mit einem zufälligen Wert

Die korrekte Methode für die Validierung der objectId ist die Verwendung der statischen Methode aus der ObjectId-Klasse.

mongoose.Types.ObjectId.isValid (sample_object_id)

0
Sushil Kadu

ODER Sie können das tun

var ObjectId = require('mongoose').Types.ObjectId; var objId = new ObjectId( (param.length < 12) ? "123456789012" : param );

wie hier erwähnt Mongoose's find-Methode mit $ oder Bedingung funktioniert nicht richtig

0
Madhu Kumar

Erkennen und Korrigieren des ObjectID-Fehlers

Ich bin auf dieses Problem gestoßen, als ich versuchte, einen Gegenstand mit Mungo zu löschen, und habe den gleichen Fehler erhalten. Nachdem ich mir die Rückgabe-Zeichenfolge angesehen hatte, stellte ich fest, dass die zurückgegebene Zeichenfolge einige zusätzliche Leerzeichen enthält, die den Fehler für mich verursacht haben. Daher habe ich einige der hier angegebenen Antworten angewendet, um die fehlerhafte ID zu ermitteln, und dann die zusätzlichen Leerzeichen aus der Zeichenfolge entfernt. Hier ist der Code, mit dem ich das Problem endgültig gelöst habe.

const mongoose = require("mongoose");
mongoose.set('useFindAndModify', false);  //was set due to DeprecationWarning: Mongoose: `findOneAndUpdate()` and `findOneAndDelete()` without the `useFindAndModify`



app.post("/delete", function(req, res){
  let checkedItem = req.body.deleteItem;
  if (!mongoose.Types.ObjectId.isValid(checkedItem)) {
    checkedItem = checkedItem.replace(/\s/g, '');
  }

  Item.findByIdAndRemove(checkedItem, function(err) {
    if (!err) {
      console.log("Successfully Deleted " + checkedItem);
        res.redirect("/");
      }
    });
});

Dies hat bei mir funktioniert und ich gehe davon aus, dass andere Elemente in ähnlicher Weise entfernt werden können, wenn sie in der Rückgabezeichenfolge angezeigt werden.

Ich hoffe das hilft.

0
Jim Bray
//Use following to check if the id is a valid ObjectId?

var valid = mongoose.Types.ObjectId.isValid(req.params.id);
if(valid)
{
  //process your code here
} else {
  //the id is not a valid ObjectId
}
0
Brajalal Pal

Zeichenkette in ObjectId umwandeln

import mongoose from "mongoose"; // ES6 or above
const mongoose = require('mongoose'); // ES5 or below

let userid = _id
console.log(mongoose.Types.ObjectId(userid)) //5c516fae4e6a1c1cfce18d77
0
WasiF

Wenn jemand auf dieses Problem stößt, wurde es für mich dadurch gelöst, dass ich von einem einfachen Anführungszeichen in "erforderlich" zu "erforderlich" wechselte.

Anstatt:

const something = require('./models/something');

benutzen:

const something = require(`./models/something`);

Weiß, es klingt lustig, aber es funktioniert tatsächlich.

0
Yossi Saadi