CastError: Cast to Number failed for value "undefined" (type string) at path

Hi everyone,

i am new to mongodb i have been doing a challange on freecodecamp that requires us to build an api that takes a url in entry and returns an object containing original url and short version. after if you try to get the short version in the api you get redirected to the original site. i have succeded to build the app localy however on replit i got this mongodb error CastError: Cast to Number failed for value “undefined” (type string) at path i could not find how to solve it.

below my code

// db schema,
const shortUrlSchema = new Schema({
    original_url: {
        type: String,
    },
    short_url: Number
})

const ShortUrl = mongoose.model('ShortUrl', shortUrlSchema)

// POST route

app.post('/api/shorturl', URLValidation, async (req, res, done) => {

    try {
        // adding the count for the URL 
        let dbEntries = await ShortUrl.find();
        let count = parseInt(dbEntries.length) + 1;

        // hadning the creation 
        const url = ShortUrl.create({
            original_url: req.body.host,
            short_url: count
        }, (err, data) => {
            if(err){
                console.log(err)
            }
            res.json({
                original_url: data.original_url,
                short_url: data.short_url
            });
            done(null, data);
        });
        
    } catch (error) {
        console.log(error)
    }
   
});

// GET route

app.get('/api/shorturl/:shorturl', async (req, res) => {
    try {
        const url = await ShortUrl.findOne({short_url: req.params.shorturl})
        res.redirect(301, url.original_url);
        
    } catch (error) {
        console.log(error)
    }
});

thanks for your help i really apprecite

Hi @Abdelhak_NASSEUR,
Try to change this line:

let dbEntries = await ShortUrl.find();

to:

let dbEntries = await ShortUrl.find().lean();

also, you may want to change this line:

const url = await ShortUrl.findOne({short_url: req.params.shorturl})

to:

const url = await ShortUrl.findOne({short_url: Number(req.params.shorturl)})

By the way, your solution has few problems:

  1. Calling the find method for just counting is not efficient, you better call the estimatedDocumentCount method.

  2. Concurrency is not supported (different calls to the post requests can get the same “shorturl”), a better approach will be to generate unique number in some way.

Goodluck,
Rafael,