Add directory API endpoints
This commit is contained in:
parent
11592d8bd1
commit
af1eaa3a57
88
index.js
88
index.js
|
|
@ -708,6 +708,94 @@ app.delete('/api/v1/user/directory/:number', (req, res) => { // Delete a directo
|
|||
});
|
||||
});
|
||||
|
||||
// User directory management via API key, for automated scripts
|
||||
app.post('/api/v1/user/dir/newEntry', async (req, res) => {
|
||||
const apiKey = req.headers['authorization'] ? req.headers['authorization'].replace('Bearer ', '') : null;
|
||||
if (!apiKey) {
|
||||
res.status(401).json({ error: 'API Key is required!' });
|
||||
return;
|
||||
}
|
||||
|
||||
const routeData = await pool.query("SELECT * FROM routes WHERE apiKey = ?", [apiKey]);
|
||||
if (!routeData || routeData.length === 0) {
|
||||
res.status(401).json({ error: 'Unauthorized' });
|
||||
return;
|
||||
}
|
||||
|
||||
const route = routeData[0];
|
||||
var number = Number(req.body.number);
|
||||
var name = String(req.body.name);
|
||||
if (!number || !name) {
|
||||
res.status(400).json({ error: 'Bad Request' });
|
||||
return;
|
||||
}
|
||||
if (number < route.block_start || number > route.block_start + route.block_length) {
|
||||
res.status(403).json({ error: 'Forbidden' });
|
||||
return;
|
||||
}
|
||||
|
||||
// Remove html
|
||||
name = require("escape-html")(name);
|
||||
// If number already exists, update, otherwise insert
|
||||
pool.query('SELECT * FROM directory WHERE number = ? AND route = ?', [number, route.id]).then((rows) => {
|
||||
const row = rows[0];
|
||||
if (row) {
|
||||
pool.query('UPDATE directory SET name = ? WHERE number = ? AND route = ?',
|
||||
[name, number, route.id]).then(() => {
|
||||
res.json({ message: 'Updated' });
|
||||
}
|
||||
).catch(err => {
|
||||
console.error('Error updating directory entry:', err);
|
||||
res.status(500).json({ error: 'Internal server error' });
|
||||
});
|
||||
} else {
|
||||
pool.query('INSERT INTO directory (number, name, route) VALUES (?, ?, ?)',
|
||||
[number, name, route.id]).then(() => {
|
||||
res.status(201).json({ message: 'Created' });
|
||||
}
|
||||
).catch(err => {
|
||||
console.error('Error creating directory entry:', err);
|
||||
res.status(500).json({ error: 'Internal server error' });
|
||||
});
|
||||
}
|
||||
}).catch(err => {
|
||||
console.error('Error checking for existing directory entry:', err);
|
||||
res.status(500).json({ error: 'Internal server error' });
|
||||
});
|
||||
});
|
||||
|
||||
app.delete('/api/v1/user/dir/deleteEntry/:number', async (req, res) => {
|
||||
const apiKey = req.headers['authorization'] ? req.headers['authorization'].replace('Bearer ', '') : null;
|
||||
if (!apiKey) {
|
||||
res.status(401).json({ error: 'API Key is required!' });
|
||||
return;
|
||||
}
|
||||
|
||||
const routeData = await pool.query("SELECT * FROM routes WHERE apiKey = ?", [apiKey]);
|
||||
if (!routeData || routeData.length === 0) {
|
||||
res.status(401).json({ error: 'Unauthorized' });
|
||||
return;
|
||||
}
|
||||
|
||||
const route = routeData[0];
|
||||
const number = Number(req.params.number);
|
||||
if (!number) {
|
||||
res.status(400).json({ error: 'Bad Request' });
|
||||
return;
|
||||
}
|
||||
// Check that the number is within the block range for the current user
|
||||
if (number < route.block_start || number > route.block_start + route.block_length) {
|
||||
res.status(403).json({ error: 'Forbidden' });
|
||||
return;
|
||||
}
|
||||
pool.query('DELETE FROM directory WHERE number = ? AND route = ?', [number, route.id]).then(() => {
|
||||
res.status(200).json({ message: 'Deleted' });
|
||||
}).catch(err => {
|
||||
console.error('Error deleting directory entry:', err);
|
||||
res.status(500).json({ error: 'Internal server error' });
|
||||
});
|
||||
});
|
||||
|
||||
// == END USER ROUTES ==
|
||||
|
||||
// == Directory routes == (unauthenticated)
|
||||
|
|
|
|||
31
package-lock.json
generated
31
package-lock.json
generated
|
|
@ -11,7 +11,7 @@
|
|||
"dependencies": {
|
||||
"bcrypt": "^5.1.1",
|
||||
"connect-sqlite": "^0.0.1",
|
||||
"dotenv": "^16.4.7",
|
||||
"dotenv": "^16.6.1",
|
||||
"ejs": "^3.1.10",
|
||||
"escape-html": "^1.0.3",
|
||||
"express": "^4.21.2",
|
||||
|
|
@ -734,9 +734,9 @@
|
|||
}
|
||||
},
|
||||
"node_modules/dotenv": {
|
||||
"version": "16.4.7",
|
||||
"resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.4.7.tgz",
|
||||
"integrity": "sha512-47qPchRCykZC03FhkYAhrvwU4xDBFIj1QPqaarj6mdM/hgUzfPHcpkHJOn3mJAufFeeAxAzeGsr5X0M4k6fLZQ==",
|
||||
"version": "16.6.1",
|
||||
"resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.6.1.tgz",
|
||||
"integrity": "sha512-uBq4egWHTcTt33a72vpSG0z3HnPuIl6NqYcTrKEg2azoEyl2hpW0zqlxysq2pK9HlDIHyHyakeYaYnSAwd8bow==",
|
||||
"license": "BSD-2-Clause",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
|
|
@ -795,29 +795,6 @@
|
|||
"node": ">= 0.8"
|
||||
}
|
||||
},
|
||||
"node_modules/encoding": {
|
||||
"version": "0.1.13",
|
||||
"resolved": "https://registry.npmjs.org/encoding/-/encoding-0.1.13.tgz",
|
||||
"integrity": "sha512-ETBauow1T35Y/WZMkio9jiM0Z5xjHHmJ4XmjZOq1l/dXz3lr2sRn87nJy20RupqSh1F2m3HHPSp8ShIPQJrJ3A==",
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"dependencies": {
|
||||
"iconv-lite": "^0.6.2"
|
||||
}
|
||||
},
|
||||
"node_modules/encoding/node_modules/iconv-lite": {
|
||||
"version": "0.6.3",
|
||||
"resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz",
|
||||
"integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==",
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"dependencies": {
|
||||
"safer-buffer": ">= 2.1.2 < 3.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/end-of-stream": {
|
||||
"version": "1.4.4",
|
||||
"resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz",
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@
|
|||
"dependencies": {
|
||||
"bcrypt": "^5.1.1",
|
||||
"connect-sqlite": "^0.0.1",
|
||||
"dotenv": "^16.4.7",
|
||||
"dotenv": "^16.6.1",
|
||||
"ejs": "^3.1.10",
|
||||
"escape-html": "^1.0.3",
|
||||
"express": "^4.21.2",
|
||||
|
|
|
|||
Loading…
Reference in a new issue