From 0a3f5d40f7c99795b65230f02ba5821ed6bab9e8 Mon Sep 17 00:00:00 2001
From: Artemy Egorov <59178854+artegoser@users.noreply.github.com>
Date: Mon, 24 Apr 2023 09:56:50 +0300
Subject: [PATCH] Mongodb migration (#3)
* feat: mongodb migration
* doc: update
* fix: limit for api usage
---
.env.example | 5 +-
changelog.md | 3 +-
core.js | 67 ++++++++++++++
index.js | 55 +++++-------
package-lock.json | 223 ++++++++++++++++++++++++++++++++++++++++++++++
package.json | 1 +
6 files changed, 316 insertions(+), 38 deletions(-)
create mode 100644 core.js
diff --git a/.env.example b/.env.example
index 212c23a..f0beadf 100644
--- a/.env.example
+++ b/.env.example
@@ -1,2 +1,3 @@
-PORT= 80 # port to listen on
-KEY= 'yoursecretkey' # key to encrypt notes on the server
\ No newline at end of file
+PORT=80 # port to listen on
+MONGO_URI="your mongo uri" # "mongodb+srv://xxxx:yyyy@domain/zzzz?retryWrites=true&w=majority"
+MONGO_DB="anopaper" # database name
\ No newline at end of file
diff --git a/changelog.md b/changelog.md
index 9e900da..3c8a028 100644
--- a/changelog.md
+++ b/changelog.md
@@ -19,10 +19,9 @@
- [ ] Local notes editing
- [ ] Publish local notes
-- [ ] Migration notes storage to mongodb
+- [x] Migration notes storage to mongodb
- [ ] Settings for publish notes, such as: delete after reading, number of reads before deleting.
-
# AnoPaper v1.0.0
- [x] MD Support (43d7601ea6ca7838f41beefc1d57dd4774e74add)
diff --git a/core.js b/core.js
new file mode 100644
index 0000000..ef4df5c
--- /dev/null
+++ b/core.js
@@ -0,0 +1,67 @@
+// Copyright (c) 2023 artegoser (Artemy Egorov)
+//
+// This program is free software: you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation, either version 3 of the License, or
+// (at your option) any later version.
+//
+// This program is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program. If not, see .
+
+const mongoClient = require("mongodb").MongoClient;
+const sha3 = require("js-sha3").sha3_512;
+
+class NotesCore {
+ constructor() {}
+ async connect() {
+ let connection = await mongoClient.connect(process.env.MONGO_URI, {
+ useNewUrlParser: true,
+ });
+
+ let db = connection.db(process.env.MONGO_DB);
+
+ this.notes = db.collection("notes");
+ }
+
+ async getNote(_id) {
+ try {
+ return await this.notes.findOne({ _id });
+ } catch {
+ return null;
+ }
+ }
+
+ async deleteNote(_id) {
+ try {
+ return await this.notes.deleteOne({ _id });
+ } catch {
+ return null;
+ }
+ }
+
+ async publishNote(note) {
+ try {
+ note._id = sha3(JSON.stringify(note));
+ note.time = Date.now();
+ note.pub = true;
+ note.pubTime = note.time;
+ await this.notes.updateOne(
+ { _id: note._id },
+ { $set: note },
+ { upsert: true }
+ );
+ return note._id;
+ } catch {
+ return null;
+ }
+ }
+}
+
+module.exports = {
+ NotesCore,
+};
diff --git a/index.js b/index.js
index e00770d..b60b603 100644
--- a/index.js
+++ b/index.js
@@ -15,15 +15,16 @@
along with this program. If not, see .
*/
-const sha3 = require("js-sha3").sha3_512;
const express = require("express");
const bodyParser = require("body-parser");
const isValidNote = require("./note_validator");
const fs = require("fs");
const path = require("path");
-const cryptojs = require("crypto-js");
const { Server } = require("socket.io");
const rateLimit = require("express-rate-limit");
+const { NotesCore } = require("./core");
+
+let core = new NotesCore();
require("dotenv").config();
@@ -33,7 +34,7 @@ const app = express(),
const limiter = rateLimit({
windowMs: 24 * 60 * 60 * 1000, // one day limit
- max: 10,
+ max: 50,
standardHeaders: true,
legacyHeaders: false,
});
@@ -82,42 +83,26 @@ io.on("connection", (socket) => {
app.use(bodyParser.json());
-app.post("/publish", limiter, function (req, res) {
+app.post("/publish", limiter, async (req, res) => {
if (isValidNote(req.body)) {
- let hash = sha3(JSON.stringify(req.body));
- req.body.time = Date.now();
- req.body.pub = true;
- req.body.pubTime = req.body.time;
+ let id = await core.publishNote(req.body);
- try {
- fs.writeFileSync(
- `./notes/${hash}.json`,
- cryptojs.AES.encrypt(
- JSON.stringify(req.body),
- process.env.KEY
- ).toString()
- );
- res.send({ id: hash });
- } catch {
- res.status(500).send("Failed to write file");
+ if (id) {
+ res.json({ id });
+ } else {
+ res.status(500).send("Publish failed!");
}
} else {
res.status(403).send("Invalid body!");
}
});
-app.get("/get-note/:delorno/:id", function (req, res) {
- let path = `./notes/${req.params.id}.json`;
- try {
- let data = JSON.parse(
- cryptojs.AES.decrypt(
- fs.readFileSync(path, "utf-8"),
- process.env.KEY
- ).toString(cryptojs.enc.Utf8)
- );
- res.send(data);
- if (req.params.delorno === "del") fs.unlinkSync(path);
- } catch {
+app.get("/get-note/:delorno/:id", async (req, res) => {
+ let note = await core.getNote(req.params.id);
+ if (note) {
+ res.json(note);
+ if (req.params.delorno === "del") await core.deleteNote(req.params.id);
+ } else {
res.status(404).send("There is no such note");
}
});
@@ -128,6 +113,8 @@ app.get("*", function (req, res) {
res.sendFile(path.join(__dirname, "./dist", "index.html"));
});
-server.listen(process.env.PORT, () => {
- console.log(`Listening on port ${process.env.PORT}`);
-});
+core.connect().then(() =>
+ server.listen(process.env.PORT, () => {
+ console.log(`Listening on port ${process.env.PORT}`);
+ })
+);
diff --git a/package-lock.json b/package-lock.json
index 25a6a72..09f76cd 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -18,6 +18,7 @@
"express-rate-limit": "^6.7.0",
"fuse.js": "^6.6.2",
"js-sha3": "^0.8.0",
+ "mongodb": "^5.3.0",
"openai": "^3.2.1",
"react": "^18.2.0",
"react-contenteditable": "^3.3.7",
@@ -1100,6 +1101,20 @@
"resolved": "https://registry.npmjs.org/@types/web/-/web-0.0.46.tgz",
"integrity": "sha512-ki0OmbjSdAEfvmy5AYWFpMkRsPW+6h4ibQ4tzk8SJsS9dkrrD3B/U1eVvdNNWxAzntjq6o2sjSia6UBCoPH+Yg=="
},
+ "node_modules/@types/webidl-conversions": {
+ "version": "7.0.0",
+ "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.0.tgz",
+ "integrity": "sha512-xTE1E+YF4aWPJJeUzaZI5DRntlkY3+BCVJi0axFptnjGmAoWxkyREIh/XMrfxVLejwQxMCfDXdICo0VLxThrog=="
+ },
+ "node_modules/@types/whatwg-url": {
+ "version": "8.2.2",
+ "resolved": "https://registry.npmjs.org/@types/whatwg-url/-/whatwg-url-8.2.2.tgz",
+ "integrity": "sha512-FtQu10RWgn3D9U4aazdwIE2yzphmTJREDqNdODHrbrZmmMqI0vMheC/6NE/J1Yveaj8H+ela+YwWTjq5PGmuhA==",
+ "dependencies": {
+ "@types/node": "*",
+ "@types/webidl-conversions": "*"
+ }
+ },
"node_modules/@vitejs/plugin-react": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/@vitejs/plugin-react/-/plugin-react-4.0.0.tgz",
@@ -1510,6 +1525,14 @@
"node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7"
}
},
+ "node_modules/bson": {
+ "version": "5.2.0",
+ "resolved": "https://registry.npmjs.org/bson/-/bson-5.2.0.tgz",
+ "integrity": "sha512-HevkSpDbpUfsrHWmWiAsNavANKYIErV2ePXllp1bwq5CDreAaFVj6RVlZpJnxK4WWDCJ/5jMUpaY6G526q3Hjg==",
+ "engines": {
+ "node": ">=14.20.1"
+ }
+ },
"node_modules/bytes": {
"version": "3.1.2",
"resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz",
@@ -3595,6 +3618,11 @@
"node": ">= 0.4"
}
},
+ "node_modules/ip": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/ip/-/ip-2.0.0.tgz",
+ "integrity": "sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ=="
+ },
"node_modules/ipaddr.js": {
"version": "1.9.1",
"resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz",
@@ -4447,6 +4475,12 @@
"node": ">= 0.6"
}
},
+ "node_modules/memory-pager": {
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/memory-pager/-/memory-pager-1.5.0.tgz",
+ "integrity": "sha512-ZS4Bp4r/Zoeq6+NLJpP+0Zzm0pR8whtGPf1XExKLJBAczGMnSi3It14OiNCStjQjM6NU1okjQGSxgEZN8eBYKg==",
+ "optional": true
+ },
"node_modules/merge-descriptors": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz",
@@ -5089,6 +5123,59 @@
"resolved": "https://registry.npmjs.org/mj-context-menu/-/mj-context-menu-0.6.1.tgz",
"integrity": "sha512-7NO5s6n10TIV96d4g2uDpG7ZDpIhMh0QNfGdJw/W47JswFcosz457wqz/b5sAKvl12sxINGFCn80NZHKwxQEXA=="
},
+ "node_modules/mongodb": {
+ "version": "5.3.0",
+ "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-5.3.0.tgz",
+ "integrity": "sha512-Wy/sbahguL8c3TXQWXmuBabiLD+iVmz+tOgQf+FwkCjhUIorqbAxRbbz00g4ZoN4sXIPwpAlTANMaGRjGGTikQ==",
+ "dependencies": {
+ "bson": "^5.2.0",
+ "mongodb-connection-string-url": "^2.6.0",
+ "socks": "^2.7.1"
+ },
+ "engines": {
+ "node": ">=14.20.1"
+ },
+ "optionalDependencies": {
+ "saslprep": "^1.0.3"
+ },
+ "peerDependencies": {
+ "@aws-sdk/credential-providers": "^3.201.0",
+ "mongodb-client-encryption": ">=2.3.0 <3",
+ "snappy": "^7.2.2"
+ },
+ "peerDependenciesMeta": {
+ "@aws-sdk/credential-providers": {
+ "optional": true
+ },
+ "mongodb-client-encryption": {
+ "optional": true
+ },
+ "snappy": {
+ "optional": true
+ }
+ }
+ },
+ "node_modules/mongodb-connection-string-url": {
+ "version": "2.6.0",
+ "resolved": "https://registry.npmjs.org/mongodb-connection-string-url/-/mongodb-connection-string-url-2.6.0.tgz",
+ "integrity": "sha512-WvTZlI9ab0QYtTYnuMLgobULWhokRjtC7db9LtcVfJ+Hsnyr5eo6ZtNAt3Ly24XZScGMelOcGtm7lSn0332tPQ==",
+ "dependencies": {
+ "@types/whatwg-url": "^8.2.1",
+ "whatwg-url": "^11.0.0"
+ }
+ },
+ "node_modules/mongodb-connection-string-url/node_modules/whatwg-url": {
+ "version": "11.0.0",
+ "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-11.0.0.tgz",
+ "integrity": "sha512-RKT8HExMpoYx4igMiVMY83lN6UeITKJlBQ+vR/8ZJ8OCdSiN3RwCq+9gH0+Xzj0+5IrM6i4j/6LuvzbZIQgEcQ==",
+ "dependencies": {
+ "tr46": "^3.0.0",
+ "webidl-conversions": "^7.0.0"
+ },
+ "engines": {
+ "node": ">=12"
+ }
+ },
"node_modules/mri": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz",
@@ -6308,6 +6395,18 @@
"resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="
},
+ "node_modules/saslprep": {
+ "version": "1.0.3",
+ "resolved": "https://registry.npmjs.org/saslprep/-/saslprep-1.0.3.tgz",
+ "integrity": "sha512-/MY/PEMbk2SuY5sScONwhUDsV2p77Znkb/q3nSVstq/yQzYJOH/Azh29p9oJLsl3LnQwSvZDKagDGBsBwSooag==",
+ "optional": true,
+ "dependencies": {
+ "sparse-bitfield": "^3.0.3"
+ },
+ "engines": {
+ "node": ">=6"
+ }
+ },
"node_modules/saxes": {
"version": "5.0.1",
"resolved": "https://registry.npmjs.org/saxes/-/saxes-5.0.1.tgz",
@@ -6430,6 +6529,15 @@
"url": "https://github.com/sponsors/ljharb"
}
},
+ "node_modules/smart-buffer": {
+ "version": "4.2.0",
+ "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz",
+ "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg==",
+ "engines": {
+ "node": ">= 6.0.0",
+ "npm": ">= 3.0.0"
+ }
+ },
"node_modules/socket.io": {
"version": "4.6.1",
"resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.6.1.tgz",
@@ -6500,6 +6608,19 @@
"node": ">=10.0.0"
}
},
+ "node_modules/socks": {
+ "version": "2.7.1",
+ "resolved": "https://registry.npmjs.org/socks/-/socks-2.7.1.tgz",
+ "integrity": "sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ==",
+ "dependencies": {
+ "ip": "^2.0.0",
+ "smart-buffer": "^4.2.0"
+ },
+ "engines": {
+ "node": ">= 10.13.0",
+ "npm": ">= 3.0.0"
+ }
+ },
"node_modules/source-map": {
"version": "0.6.1",
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
@@ -6527,6 +6648,15 @@
"url": "https://github.com/sponsors/wooorm"
}
},
+ "node_modules/sparse-bitfield": {
+ "version": "3.0.3",
+ "resolved": "https://registry.npmjs.org/sparse-bitfield/-/sparse-bitfield-3.0.3.tgz",
+ "integrity": "sha512-kvzhi7vqKTfkh0PZU+2D2PIllw2ymqJKujUcyPMd9Y75Nv4nPbGJZXNhxsgdQab2BmlDct1YnfQCguEvHr7VsQ==",
+ "optional": true,
+ "dependencies": {
+ "memory-pager": "^1.0.2"
+ }
+ },
"node_modules/speech-rule-engine": {
"version": "4.0.7",
"resolved": "https://registry.npmjs.org/speech-rule-engine/-/speech-rule-engine-4.0.7.tgz",
@@ -8192,6 +8322,20 @@
"resolved": "https://registry.npmjs.org/@types/web/-/web-0.0.46.tgz",
"integrity": "sha512-ki0OmbjSdAEfvmy5AYWFpMkRsPW+6h4ibQ4tzk8SJsS9dkrrD3B/U1eVvdNNWxAzntjq6o2sjSia6UBCoPH+Yg=="
},
+ "@types/webidl-conversions": {
+ "version": "7.0.0",
+ "resolved": "https://registry.npmjs.org/@types/webidl-conversions/-/webidl-conversions-7.0.0.tgz",
+ "integrity": "sha512-xTE1E+YF4aWPJJeUzaZI5DRntlkY3+BCVJi0axFptnjGmAoWxkyREIh/XMrfxVLejwQxMCfDXdICo0VLxThrog=="
+ },
+ "@types/whatwg-url": {
+ "version": "8.2.2",
+ "resolved": "https://registry.npmjs.org/@types/whatwg-url/-/whatwg-url-8.2.2.tgz",
+ "integrity": "sha512-FtQu10RWgn3D9U4aazdwIE2yzphmTJREDqNdODHrbrZmmMqI0vMheC/6NE/J1Yveaj8H+ela+YwWTjq5PGmuhA==",
+ "requires": {
+ "@types/node": "*",
+ "@types/webidl-conversions": "*"
+ }
+ },
"@vitejs/plugin-react": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/@vitejs/plugin-react/-/plugin-react-4.0.0.tgz",
@@ -8492,6 +8636,11 @@
"update-browserslist-db": "^1.0.10"
}
},
+ "bson": {
+ "version": "5.2.0",
+ "resolved": "https://registry.npmjs.org/bson/-/bson-5.2.0.tgz",
+ "integrity": "sha512-HevkSpDbpUfsrHWmWiAsNavANKYIErV2ePXllp1bwq5CDreAaFVj6RVlZpJnxK4WWDCJ/5jMUpaY6G526q3Hjg=="
+ },
"bytes": {
"version": "3.1.2",
"resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz",
@@ -10009,6 +10158,11 @@
"side-channel": "^1.0.4"
}
},
+ "ip": {
+ "version": "2.0.0",
+ "resolved": "https://registry.npmjs.org/ip/-/ip-2.0.0.tgz",
+ "integrity": "sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ=="
+ },
"ipaddr.js": {
"version": "1.9.1",
"resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz",
@@ -10595,6 +10749,12 @@
"resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz",
"integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ=="
},
+ "memory-pager": {
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/memory-pager/-/memory-pager-1.5.0.tgz",
+ "integrity": "sha512-ZS4Bp4r/Zoeq6+NLJpP+0Zzm0pR8whtGPf1XExKLJBAczGMnSi3It14OiNCStjQjM6NU1okjQGSxgEZN8eBYKg==",
+ "optional": true
+ },
"merge-descriptors": {
"version": "1.0.1",
"resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz",
@@ -10971,6 +11131,37 @@
"resolved": "https://registry.npmjs.org/mj-context-menu/-/mj-context-menu-0.6.1.tgz",
"integrity": "sha512-7NO5s6n10TIV96d4g2uDpG7ZDpIhMh0QNfGdJw/W47JswFcosz457wqz/b5sAKvl12sxINGFCn80NZHKwxQEXA=="
},
+ "mongodb": {
+ "version": "5.3.0",
+ "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-5.3.0.tgz",
+ "integrity": "sha512-Wy/sbahguL8c3TXQWXmuBabiLD+iVmz+tOgQf+FwkCjhUIorqbAxRbbz00g4ZoN4sXIPwpAlTANMaGRjGGTikQ==",
+ "requires": {
+ "bson": "^5.2.0",
+ "mongodb-connection-string-url": "^2.6.0",
+ "saslprep": "^1.0.3",
+ "socks": "^2.7.1"
+ }
+ },
+ "mongodb-connection-string-url": {
+ "version": "2.6.0",
+ "resolved": "https://registry.npmjs.org/mongodb-connection-string-url/-/mongodb-connection-string-url-2.6.0.tgz",
+ "integrity": "sha512-WvTZlI9ab0QYtTYnuMLgobULWhokRjtC7db9LtcVfJ+Hsnyr5eo6ZtNAt3Ly24XZScGMelOcGtm7lSn0332tPQ==",
+ "requires": {
+ "@types/whatwg-url": "^8.2.1",
+ "whatwg-url": "^11.0.0"
+ },
+ "dependencies": {
+ "whatwg-url": {
+ "version": "11.0.0",
+ "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-11.0.0.tgz",
+ "integrity": "sha512-RKT8HExMpoYx4igMiVMY83lN6UeITKJlBQ+vR/8ZJ8OCdSiN3RwCq+9gH0+Xzj0+5IrM6i4j/6LuvzbZIQgEcQ==",
+ "requires": {
+ "tr46": "^3.0.0",
+ "webidl-conversions": "^7.0.0"
+ }
+ }
+ }
+ },
"mri": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz",
@@ -11798,6 +11989,15 @@
"resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="
},
+ "saslprep": {
+ "version": "1.0.3",
+ "resolved": "https://registry.npmjs.org/saslprep/-/saslprep-1.0.3.tgz",
+ "integrity": "sha512-/MY/PEMbk2SuY5sScONwhUDsV2p77Znkb/q3nSVstq/yQzYJOH/Azh29p9oJLsl3LnQwSvZDKagDGBsBwSooag==",
+ "optional": true,
+ "requires": {
+ "sparse-bitfield": "^3.0.3"
+ }
+ },
"saxes": {
"version": "5.0.1",
"resolved": "https://registry.npmjs.org/saxes/-/saxes-5.0.1.tgz",
@@ -11903,6 +12103,11 @@
"object-inspect": "^1.9.0"
}
},
+ "smart-buffer": {
+ "version": "4.2.0",
+ "resolved": "https://registry.npmjs.org/smart-buffer/-/smart-buffer-4.2.0.tgz",
+ "integrity": "sha512-94hK0Hh8rPqQl2xXc3HsaBoOXKV20MToPkcXvwbISWLEs+64sBq5kFgn2kJDHb1Pry9yrP0dxrCI9RRci7RXKg=="
+ },
"socket.io": {
"version": "4.6.1",
"resolved": "https://registry.npmjs.org/socket.io/-/socket.io-4.6.1.tgz",
@@ -11952,6 +12157,15 @@
"debug": "~4.3.1"
}
},
+ "socks": {
+ "version": "2.7.1",
+ "resolved": "https://registry.npmjs.org/socks/-/socks-2.7.1.tgz",
+ "integrity": "sha512-7maUZy1N7uo6+WVEX6psASxtNlKaNVMlGQKkG/63nEDdLOWNbiUMoLK7X4uYoLhQstau72mLgfEWcXcwsaHbYQ==",
+ "requires": {
+ "ip": "^2.0.0",
+ "smart-buffer": "^4.2.0"
+ }
+ },
"source-map": {
"version": "0.6.1",
"resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
@@ -11969,6 +12183,15 @@
"resolved": "https://registry.npmjs.org/space-separated-tokens/-/space-separated-tokens-2.0.1.tgz",
"integrity": "sha512-ekwEbFp5aqSPKaqeY1PGrlGQxPNaq+Cnx4+bE2D8sciBQrHpbwoBbawqTN2+6jPs9IdWxxiUcN0K2pkczD3zmw=="
},
+ "sparse-bitfield": {
+ "version": "3.0.3",
+ "resolved": "https://registry.npmjs.org/sparse-bitfield/-/sparse-bitfield-3.0.3.tgz",
+ "integrity": "sha512-kvzhi7vqKTfkh0PZU+2D2PIllw2ymqJKujUcyPMd9Y75Nv4nPbGJZXNhxsgdQab2BmlDct1YnfQCguEvHr7VsQ==",
+ "optional": true,
+ "requires": {
+ "memory-pager": "^1.0.2"
+ }
+ },
"speech-rule-engine": {
"version": "4.0.7",
"resolved": "https://registry.npmjs.org/speech-rule-engine/-/speech-rule-engine-4.0.7.tgz",
diff --git a/package.json b/package.json
index 2f22b02..918257d 100644
--- a/package.json
+++ b/package.json
@@ -21,6 +21,7 @@
"express-rate-limit": "^6.7.0",
"fuse.js": "^6.6.2",
"js-sha3": "^0.8.0",
+ "mongodb": "^5.3.0",
"openai": "^3.2.1",
"react": "^18.2.0",
"react-contenteditable": "^3.3.7",