Update: I’ve tried lots of different things, but I keep getting the same error.
Initially I used a count variable which increased by 1 each time it was assigned to an id field in the database but then I thought that because the app restarts with each edit / when glitch starts up this might be causing the problem, so I replaced this with a random string generator (and tried to implement a check to be sure the generated random string wasn’t already used for an id in the db) but I get the same issue when trying to add new links to the db. I’ve cleared the db of collections (via the mongo atlas gui) but it still won’t work.
This is from the logs -
Node.js listening ...
true
link NOT found in db, adding new link
Error: { MongoError: E11000 duplicate key error collection: test.links index: short_1 dup key: { short: null }
at Function.create (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/core/error.js:43:12)
at toError (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/utils.js:149:22)
at coll.s.topology.insert (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/operations/common_functions.js:265:39)
at handler (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/core/sdam/topology.js:913:24)
at fn (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/cmap/connection_pool.js:352:13)
at handleOperationResult (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/core/sdam/server.js:487:5)
at MessageStream.messageHandler (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/cmap/connection.js:270:5)
at MessageStream.emit (events.js:189:13)
at processIncomingData (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/cmap/message_stream.js:144:12)
at MessageStream._write (/rbd/pnpm-volume/d123e99f-b53a-45f7-b36b-711777fa44bd/node_modules/.registry.npmjs.org/mongodb/3.5.5/node_modules/mongodb/lib/cmap/message_stream.js:42:5)
at doWrite (_stream_writable.js:410:12)
at writeOrBuffer (_stream_writable.js:394:5)
at MessageStream.Writable.write (_stream_writable.js:294:11)
at TLSSocket.ondata (_stream_readable.js:689:20)
at TLSSocket.emit (events.js:189:13)
at addChunk (_stream_readable.js:284:12)
driver: true,
name: 'MongoError',
index: 0,
code: 11000,
keyPattern: { short: 1 },
keyValue: { short: null },
errmsg:
'E11000 duplicate key error collection: test.links index: short_1 dup key: { short: null }',
[Symbol(mongoErrorContextSymbol)]: {} }
So I know that it is error-ing at my link.save expression.
And then this is my code:
"use strict";
var express = require("express");
var mongo = require("mongodb");
var mongoose = require("mongoose");
var cors = require("cors");
var app = express();
// Basic Configuration
var port = process.env.PORT || 3000;
// -> this project needs a db !! 💾
mongoose.connect(process.env.DB_URI, {
useNewUrlParser: true,
useUnifiedTopology: true
});
// Create link schema and include a pre-save which auto increments the count and assigns it to the link _id
const linkSchema = new mongoose.Schema({
_id: { type: String },
link: "",
created_at: ""
});
const Link = mongoose.model("Link", linkSchema);
app.use(cors());
// -> this project needs to parse POST bodies !! 📧
// you should mount the body-parser here
const bodyParser = require("body-parser");
app.use(bodyParser.urlencoded({ extended: true }));
app.use("/public", express.static(process.cwd() + "/public"));
app.get("/", function(req, res) {
res.sendFile(process.cwd() + "/views/index.html");
});
// your first API endpoint...
app.get("/api/hello", function(req, res) {
res.json({ greeting: "hello API" });
});
// -> Functionality 💪
app.post("/api/shorturl/new", (req, res) => {
// Check getting data & assign to variable
let data = req.body.url;
// console.log(data);
let urlRegex = /^(http:\/\/www\.|https:\/\/www\.|http:\/\/|https:\/\/)?[a-z0-9]+([\-\.]{1}[a-z0-9]+)*\.[a-z]{2,5}(:[0-9]{1,5})?(\/.*)?$/;
// Attempted to add id check to be sure assigned id is unique - may add when app actually functional
// let shortUrlId = makeid();
// let uniqueIdTest = false;
// while (!uniqueIdTest) {
// uniqueIdTest = Link.findOne({ _id: shortUrlId }, (err, doc) => {
// if (err) {
// console.log('Unique ID -> continue')
// return true;
// }
// if (doc) {
// console.log('ID not unique -> assigning new ID')
// shortUrlId = makeid();
// return shortUrlId;
// }
// })
// };
// Check if data is a valid URL 🔗 - if not: res.json error object
console.log(urlRegex.test(data));
if (!urlRegex.test(data)) {
res.json({ error: "invalid URL" });
} else {
Link.findOne({ link: data }, (err, doc) => {
if (doc) {
console.log("link found in db");
res.json({
original_url: data,
short_url: doc._id
});
} else {
console.log("link NOT found in db, adding new link");
let id = makeid();
//Link.findOne({ _id: id }, (err, doc) => {
//if(err) {
let link = new Link({
_id: id,
link: data,
created_at: new Date()
});
link.save(err, doc => {
if (err) return console.error("Error: ", err);
console.log(doc);
res.json({
original_url: data,
short_url: link._id
});
});
}
});
}
});
app.get("/:id", (req, res) => {
let id = req.params.id;
Link.findOne({ _id: id }, (err, doc) => {
if (doc) {
res.redirect(doc.link);
} else {
res.redirect("/");
}
});
});
app.get("/api/shorturl/new", (req, res) => {
res.json({ hello: "hi there..." });
});
app.listen(port, function() {
console.log("Node.js listening ...");
});
// Function for random id ->
function makeid() {
//makes a random shortened ID
let randomText = "";
//make alphanumeric
let possible =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
for (let i = 0; i < 5; i++) {
randomText += possible.charAt(Math.floor(Math.random() * possible.length));
}
return randomText;
}
I’ve been stuck on this for a long while now and I’m not sure where I’m going wrong - if anyone can help please do so?
Thanks,
Z