Impl: project requirements
This commit is contained in:
parent
671605c02d
commit
8072461ab2
125
index.js
125
index.js
@ -2,9 +2,59 @@ require("dotenv").config();
|
|||||||
const express = require("express");
|
const express = require("express");
|
||||||
const cors = require("cors");
|
const cors = require("cors");
|
||||||
const app = express();
|
const app = express();
|
||||||
|
const mongoose = require("mongoose");
|
||||||
|
const dns = require("dns");
|
||||||
|
|
||||||
// Basic Configuration
|
// Basic Configuration
|
||||||
const port = process.env.PORT || 3000;
|
const port = process.env.PORT || 3000;
|
||||||
|
const MONGODB_URI = process.env.MONGODB_URI || "";
|
||||||
|
|
||||||
|
mongoose.connect(MONGODB_URI, {
|
||||||
|
// @ts-ignore
|
||||||
|
useNewUrlParser: true,
|
||||||
|
useUnifiedTopology: true,
|
||||||
|
});
|
||||||
|
|
||||||
|
const urlSchema = new mongoose.Schema({
|
||||||
|
original: {
|
||||||
|
type: String,
|
||||||
|
unique: true,
|
||||||
|
},
|
||||||
|
short: { type: Number, unique: true },
|
||||||
|
});
|
||||||
|
|
||||||
|
const Url = mongoose.model("Url", urlSchema);
|
||||||
|
|
||||||
|
const counterSchema = new mongoose.Schema({
|
||||||
|
name: { type: String, unique: true },
|
||||||
|
seq: { type: Number, default: 0 },
|
||||||
|
});
|
||||||
|
|
||||||
|
const Counter = mongoose.model("Counter", counterSchema);
|
||||||
|
|
||||||
|
let shortUrlsCounter = 0;
|
||||||
|
|
||||||
|
Counter.findOne({ name: "shortUrl" })
|
||||||
|
.then((counter) => {
|
||||||
|
if (counter) {
|
||||||
|
shortUrlsCounter = counter.seq;
|
||||||
|
console.log(`Old counter: ${counter}`);
|
||||||
|
} else {
|
||||||
|
const shortUrlsCounterModel = new Counter({ name: "shortUrl" });
|
||||||
|
shortUrlsCounterModel
|
||||||
|
.save()
|
||||||
|
.then((counter) => {
|
||||||
|
if (counter) {
|
||||||
|
shortUrlsCounter = counter.seq;
|
||||||
|
console.log(`New counter: ${counter}`);
|
||||||
|
} else {
|
||||||
|
console.log(`Error: could not create a new counter`);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch((err) => console.log(err));
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch((err) => console.log(err));
|
||||||
|
|
||||||
app.use(cors());
|
app.use(cors());
|
||||||
|
|
||||||
@ -14,9 +64,80 @@ app.get("/", function (req, res) {
|
|||||||
res.sendFile(process.cwd() + "/views/index.html");
|
res.sendFile(process.cwd() + "/views/index.html");
|
||||||
});
|
});
|
||||||
|
|
||||||
|
app.use(express.urlencoded({ extended: false }));
|
||||||
|
|
||||||
// Your first API endpoint
|
// Your first API endpoint
|
||||||
app.get("/api/hello", function (req, res) {
|
app.post("/api/shorturl/", (req, res) => {
|
||||||
res.json({ greeting: "hello API" });
|
const original = req.body.url;
|
||||||
|
try {
|
||||||
|
const hostname = new URL(original).hostname;
|
||||||
|
dns.lookup(hostname, (err, addr, family) => {
|
||||||
|
if (err) {
|
||||||
|
console.log(`Invalid url:\n${err}`);
|
||||||
|
res.json({ error: "Invalid URL" });
|
||||||
|
} else {
|
||||||
|
Url.findOne({ original: original })
|
||||||
|
.then((url) => {
|
||||||
|
if (url)
|
||||||
|
return res.json({
|
||||||
|
original_url: original,
|
||||||
|
short_url: url?.short,
|
||||||
|
});
|
||||||
|
const urlModel = new Url({
|
||||||
|
original: original,
|
||||||
|
short: shortUrlsCounter++,
|
||||||
|
});
|
||||||
|
Counter.findOneAndUpdate(
|
||||||
|
{ name: "shortUrl" },
|
||||||
|
{ $set: { seq: shortUrlsCounter } },
|
||||||
|
{ new: true }
|
||||||
|
)
|
||||||
|
.then((counter) => {
|
||||||
|
if (counter)
|
||||||
|
console.log(`${counter?.name} updated to ${counter?.seq}`);
|
||||||
|
else {
|
||||||
|
console.log(`Could not find "shortUrl" counter in DB`);
|
||||||
|
return res.sendStatus(500);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch((err) => {
|
||||||
|
console.log(`Error updating shortUrl counter in DB:\n${err}`);
|
||||||
|
return res.sendStatus(500);
|
||||||
|
});
|
||||||
|
urlModel
|
||||||
|
.save()
|
||||||
|
.then((url) => {
|
||||||
|
if (url)
|
||||||
|
return res.json({
|
||||||
|
original_url: original,
|
||||||
|
short_url: url?.short,
|
||||||
|
});
|
||||||
|
console.log(`Unlikely scenario occurred!:\n${url}`);
|
||||||
|
res.sendStatus(500);
|
||||||
|
})
|
||||||
|
.catch((err) => {
|
||||||
|
console.log(`Inserting url to DB failed!:\n${err}`);
|
||||||
|
res.sendStatus(500);
|
||||||
|
});
|
||||||
|
})
|
||||||
|
.catch((err) => {
|
||||||
|
console.log(`Query failed!:\n${err}`);
|
||||||
|
res.sendStatus(500);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
} catch (err) {
|
||||||
|
res.json({ error: "Invalid URL" });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
app.get("/api/shorturl/:shorturl", (req, res) => {
|
||||||
|
const shorturl = Number(req.params.shorturl);
|
||||||
|
Url.findOne({ short: shorturl })
|
||||||
|
.then((url) => res.redirect(url.original))
|
||||||
|
.catch((err) =>
|
||||||
|
res.json({ error: "No short URL found for the given input" })
|
||||||
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
app.listen(port, function () {
|
app.listen(port, function () {
|
||||||
|
Loading…
Reference in New Issue
Block a user