Update permissions; Add user creation form

This commit is contained in:
Ninjdai 2023-12-07 10:58:13 +01:00
parent 407248710f
commit 651f870415
7 changed files with 87 additions and 38 deletions

View File

@ -3,7 +3,7 @@ import { permissionBits } from '../../../../utils/permissions.js';
export default { export default {
path: "/api/contacts/call", path: "/api/contacts/call",
requiresLogin: true, requiresLogin: true,
permissions: [permissionBits.CALL], permissions: permissionBits.CALL,
type: "post", type: "post",
async execute(request, response) { async execute(request, response) {
global.events.submitEvent.emit("call", request.body); global.events.submitEvent.emit("call", request.body);

View File

@ -1,15 +1,39 @@
import { permissionBits } from "../../../../utils/permissions.js";
export default { export default {
path: "/api/users/*", path: "/api/users(/*)?",
requiresLogin: true, requiresLogin: true,
permissions: permissionBits.ADMIN,
type: "post", type: "post",
async execute(request, response) { async execute(request, response) {
const path = request.originalUrl.split("/")[3]; const username = request.originalUrl.split("/")[3];
const operation = request.originalUrl.split("/")[4];
const args = request.body; const args = request.body;
switch(path) { switch (operation) {
case 'create': case "create":
if (
await global.database.users.findOne({
where: { username: username },
})
) return response.redirect("/dashboard/users/create?error=User already exists");
console.log(`Creating user ${username}`);
let permissions = Number(args.permissions);
if (isNaN(permissions)) {
permissions = 0;
for (const permissionBit of args.permissions) {
permissions += Number(permissionBit);
}
}
if(!(permissions & permissionBits.DEFAULT)) permissions ^= permissionBits.DEFAULT;
await global.database.users.create({
username: username,
password: args.password,
permissions: permissions,
});
break; break;
case 'delete': case "delete":
break; break;
} }
}, },
} };

View File

@ -5,7 +5,7 @@ import { permissionBits } from '../../../../utils/permissions.js';
export default { export default {
path: "/dashboard", path: "/dashboard",
requiresLogin: true, requiresLogin: true,
permissions: permissionBits.ADMIN, permissions: permissionBits.DEFAULT,
type: "get", type: "get",
async execute(request, response) { async execute(request, response) {
const res = await readFile(`${process.env.WWW}/dashboard/index.html`, "utf8") const res = await readFile(`${process.env.WWW}/dashboard/index.html`, "utf8")

View File

@ -1,14 +1,21 @@
import { readFile } from 'fs/promises'; import { readFile } from "fs/promises";
import { navbar } from '../../../../utils/navbar.js'; import { navbar } from "../../../../utils/navbar.js";
import { permissionBits } from '../../../../utils/permissions.js'; import { permissionBits } from "../../../../utils/permissions.js";
export default { export default {
path: "/dashboard/users/create", path: "/dashboard/users/create",
requiresLogin: true, requiresLogin: true,
permissions: permissionBits.ADMIN, permissions: permissionBits.ADMIN,
type: "get", type: "get",
async execute(request, response) { async execute(request, response, args) {
const res = await readFile(`${process.env.WWW}/dashboard/users/create.html`, "utf8") let res = await readFile(
`${process.env.WWW}/dashboard/users/create.html`,
"utf8",
);
if(args?.error) res += `
<script type="text/javascript">
alert("Erreur: ${args.error.replaceAll('%20', ' ')}");
</script>`;
response.send(res.replaceAll("<NAVBAR>", navbar(request.session))); response.send(res.replaceAll("<NAVBAR>", navbar(request.session)));
}, },
} };

View File

@ -6,7 +6,7 @@ import { permissionBits } from "../../../../utils/permissions.js";
export default { export default {
path: "/calls", path: "/calls",
requiresLogin: true, requiresLogin: true,
permissions: [permissionBits.CALL], permissions: permissionBits.CALL,
type: "get", type: "get",
async execute(request, response) { async execute(request, response) {
const res = await generateCallResponse(request.session); const res = await generateCallResponse(request.session);

48
web.js
View File

@ -23,23 +23,20 @@ async function launchWeb() {
app.post("*", async (request, response) => { app.post("*", async (request, response) => {
console.log("POST: " + request.originalUrl); console.log("POST: " + request.originalUrl);
if (!global.handler.post[request.originalUrl]) return; let handled = global.handler.post[request.originalUrl];
if (
global.handler.post[request.originalUrl].requiresLogin && if(!handled) for(const path of Object.keys(global.handler.post)) {
!request.session.user if(new RegExp(path).test(request.originalUrl)) handled = global.handler.post[path];
) { }
if (!handled) return console.log(request.originalUrl);
if (handled.requiresLogin && !request.session.user) {
return response.redirect("/login"); return response.redirect("/login");
} }
if ( if (handled.permissions) {
global.handler.post[request.originalUrl].permissions && if((handled.permissions & request.session.user.permissions) == 0) return response.status(403).send("Vous n'avez pas la permission d'effectuer cette action !");
global.handler.post[request.originalUrl].permissions.reduce(
(a, b) => a + b,
) &
(request.session.user.permissions == 0)
) {
return response.status(403);
} }
return await global.handler.post[request.originalUrl].execute( return await handled.execute(
request, request,
response, response,
); );
@ -49,12 +46,20 @@ async function launchWeb() {
const [path, args] = parseURL(request.originalUrl); const [path, args] = parseURL(request.originalUrl);
//console.log(parseURL(request.originalUrl)); //console.log(parseURL(request.originalUrl));
console.log(`GET: ${path}${args ? "?" + args : ""}`); console.log(`GET: ${path}${args ? "?" + args : ""}`);
let handled = global.handler.get[path];
if (!global.handler.get[path]) return; if(!handled) for(const path of Object.keys(global.handler.get)) {
if (global.handler.get[path].requiresLogin && !request.session.user) { if(new RegExp(path).test(request.originalUrl)) handled = global.handler.get[path];
}
if (!handled) return;
if (handled.requiresLogin && !request.session.user) {
return response.redirect("/login"); return response.redirect("/login");
} }
return await global.handler.get[path].execute(request, response, args); if (handled.permissions) {
if((handled.permissions & request.session.user.permissions) == 0) return response.status(403).send("Vous n'avez pas la permission d'accéder cette page !");
}
return await handled.execute(request, response, args);
}); });
const PORT = process.env.PORT || 3000; const PORT = process.env.PORT || 3000;
@ -66,7 +71,14 @@ async function launchWeb() {
function parseURL(URL) { function parseURL(URL) {
const spURL = URL.split("?"); const spURL = URL.split("?");
const path = spURL[0]; const path = spURL[0];
const args = spURL[1]; if(!spURL[1]) return [path, {}];
const args = {};
for (let i = 0; i < spURL[1].split("=").length; i+=2) {
const key = spURL[1].split("=")[i];
const val = spURL[1].split("=")[i+1];
args[key] = val;
}
return [path, args]; return [path, args];
} }

View File

@ -76,17 +76,23 @@ a {
text-align: center; text-align: center;
} }
</style> </style>
<script>
function setAction(form) {
form.action = `/api/users/${form.username.value}/create`;
return true;
}
</script>
</head> </head>
<body> <body>
<NAVBAR> <NAVBAR>
<form action="/api/users/create" method="post"> <form action="/api/users/:username/create" method="post" onsubmit="return setAction(this)">
<div class="container"> <div class="container">
<h1>Création de compte</h1> <h1>Création de compte</h1>
<p>Formulaire de création de compte.</p> <p>Formulaire de création de compte.</p>
<hr> <hr>
<label for="email"><b>Nom d'utilisateur</b></label> <label for="username"><b>Nom d'utilisateur</b></label>
<input type="text" placeholder="Entrez le nom d'utilisateur" name="email" id="email" required> <input type="text" placeholder="Entrez le nom d'utilisateur" name="username" id="username" required>
<label for="psw"><b>Mot de passe</b></label> <label for="psw"><b>Mot de passe</b></label>
<input type="password" placeholder="Mot de passe" name="password" id="psw" required> <input type="password" placeholder="Mot de passe" name="password" id="psw" required>
@ -95,7 +101,7 @@ a {
<input type="password" placeholder="Répétez le mot de passe" name="password-repeat" id="psw-repeat" required> <input type="password" placeholder="Répétez le mot de passe" name="password-repeat" id="psw-repeat" required>
<h4>Permissions</h4> <h4>Permissions</h4>
<label class="container">Appels <label class="container">Appels
<input type="checkbox" name="permissions_calls"> <input type="checkbox" name="permissions" value="2">
<span class="checkmark"></span> <span class="checkmark"></span>
</label> </label>
<!--<label class="container">Unused <!--<label class="container">Unused
@ -103,7 +109,7 @@ a {
<span class="checkmark"></span> <span class="checkmark"></span>
</label>--> </label>-->
<label class="container">Admin <label class="container">Admin
<input type="checkbox" name="permissions_admin"> <input type="checkbox" name="permissions" value="8">
<span class="checkmark"></span> <span class="checkmark"></span>
</label> </label>
<hr> <hr>