CSP WIP add sessionid as well

This commit is contained in:
BIG2EYEZ
2024-01-21 16:07:27 +08:00
parent 74b610a7b8
commit 994aebf71d
18 changed files with 264 additions and 830 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 10 KiB

View File

@ -0,0 +1,58 @@
body {
font-family: 'Arial', sans-serif;
background-color: #f4f4f4;
margin: 0;
display: flex;
align-items: center;
justify-content: center;
height: 100vh;
}
h1 {
text-align: center;
color: #333;
}
form {
background-color: #fff;
padding: 20px;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
width: 300px;
}
label {
display: block;
margin-bottom: 8px;
color: #555;
}
input {
width: 100%;
padding: 8px;
margin-bottom: 16px;
border: 1px solid #ccc;
border-radius: 4px;
}
button {
background-color: #4caf50;
color: #fff;
padding: 10px;
border: none;
border-radius: 4px;
cursor: pointer;
width: 100%;
}
button:hover {
background-color: #45a049;
}
.error-message {
color: red;
margin-top: 10px;
}
.success-message {
color: green;
margin-top: 10px;
}

View File

@ -5,66 +5,7 @@
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Forgot Password - Your Website</title>
<style>
body {
font-family: 'Arial', sans-serif;
background-color: #f4f4f4;
margin: 0;
display: flex;
align-items: center;
justify-content: center;
height: 100vh;
}
h1 {
text-align: center;
color: #333;
}
form {
background-color: #fff;
padding: 20px;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
width: 300px;
}
label {
display: block;
margin-bottom: 8px;
color: #555;
}
input {
width: 100%;
padding: 8px;
margin-bottom: 16px;
border: 1px solid #ccc;
border-radius: 4px;
}
button {
background-color: #4caf50;
color: #fff;
padding: 10px;
border: none;
border-radius: 4px;
cursor: pointer;
width: 100%;
}
button:hover {
background-color: #45a049;
}
.error-message {
color: red;
margin-top: 10px;
}
.success-message {
color: green;
margin-top: 10px;
}
</style>
<link rel="stylesheet" href="forgot-password.css">
</head>
<body>
<div id="forgotPasswordForm">

View File

@ -1,107 +0,0 @@
document.addEventListener("DOMContentLoaded", async function () {
console.log("DOM Loaded");
// Extract data from sensorData
const sensorData = JSON.parse('<%- JSON.stringify(sensorData) %>');
console.log("Sensor Data:", sensorData);
// Fetch location names from the server
const locationNames = await fetch('/api/locations') // Adjust the API endpoint
.then(response => response.json())
.then(data => data.map(location => ({ id: location.id, name: location.name })))
.catch(error => console.error('Error fetching location names:', error));
// Group sensorData by locationid
const groupedData = groupBy(sensorData, 'locationid');
// Get the content div
const contentDiv = document.getElementById('content');
// Create a chart for each location
Object.keys(groupedData).forEach(locationId => {
const locationData = groupedData[locationId];
// Find the corresponding location name
const locationName = locationNames.find(location => location.id === parseInt(locationId, 10))?.name || `Unknown Location ${locationId}`;
// Create a container for the chart
const container = document.createElement('div');
container.className = 'chart-container';
// Create a title for the container with location name
const title = document.createElement('h4');
title.textContent = `Location: ${locationName}`;
container.appendChild(title);
// Get labels (Location IDs)
const labels = locationData.map(data => new Date(data.createdAt).toLocaleString('en-US', { timeZone: 'Asia/Singapore' }));
// Create datasets for each measurement
const datasets = [
{
label: 'CO',
data: locationData.map(data => data.measurement.co),
backgroundColor: 'rgba(255, 99, 132, 0.5)', // Red color
},
{
label: 'O3',
data: locationData.map(data => data.measurement.o3),
backgroundColor: 'rgba(54, 162, 235, 0.5)', // Blue color
},
{
label: 'NO2',
data: locationData.map(data => data.measurement.no2),
backgroundColor: 'rgba(255, 206, 86, 0.5)', // Yellow color
},
{
label: 'SO2',
data: locationData.map(data => data.measurement.so2),
backgroundColor: 'rgba(75, 192, 192, 0.5)', // Green color
},
];
// Create a canvas element for each location
const canvas = document.createElement('canvas');
canvas.width = 400;
canvas.height = 200;
// Append canvas to the container
container.appendChild(canvas);
// Append container to the content div
contentDiv.appendChild(container);
// Create a bar chart for each location
const ctx = canvas.getContext('2d');
new Chart(ctx, {
type: 'bar',
data: {
labels: labels,
datasets: datasets,
},
options: {
scales: {
x: {
beginAtZero: true,
},
y: {
beginAtZero: true,
},
},
},
});
});
// Helper function to group data by a specified key
function groupBy(arr, key) {
return arr.reduce((acc, obj) => {
const groupKey = obj[key];
acc[groupKey] = acc[groupKey] || [];
acc[groupKey].push(obj);
return acc;
}, {});
}
});

View File

@ -1,64 +0,0 @@
const express = require('express');
const router = express.Router();
const mysql = require('mysql');
// Replace with your MySQL connection details
const mysqlConfig = {
host: process.env.host,
user: process.env.user,
password: process.env.password,
database: process.env.database,
timezone: 'Z', // Set the timezone to UTC
};
const mysqlConnection = mysql.createConnection(mysqlConfig);
// Middleware to check if the user is authenticated
function isAuthenticated(req, res, next) {
if (req.session && req.session.authenticated) {
return next();
} else {
res.redirect('/login');
}
}
// InUsers route (renders the InUsers tab)
router.get('/', isAuthenticated, (req, res) => {
// Fetch all user data from the database
const userDataQuery = 'SELECT * FROM users';
mysqlConnection.query(userDataQuery, (error, userData) => {
if (error) {
console.error('Error fetching user data:', error);
res.status(500).send('Internal Server Error');
return;
}
// Render the inusers page with user data
res.render('inusers', { userData: userData });
});
});
// User Data route
router.get('/userdata', isAuthenticated, (req, res) => {
// Fetch all user data from the database
const userDataQuery = 'SELECT * FROM users';
mysqlConnection.query(userDataQuery, (error, userData) => {
if (error) {
console.error('Error fetching user data:', error);
res.status(500).send('Internal Server Error');
return;
}
// Render the user-data page with user data
res.render('user-data', { userData: userData });
});
});
// Edit User Data route
router.get('/edituserdata', isAuthenticated, (req, res) => {
res.render('edit-user-data');
});
module.exports = router;

View File

@ -7,7 +7,7 @@
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>In-House Users</title>
<link rel="stylesheet" href="/style.css">
<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/flatpickr/dist/flatpickr.min.css">
<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Open+Sans:wght@400;700&display=swap">
</head>
@ -173,19 +173,21 @@
</div>
<script>
<script nonce="<%= nonce %>">
const allUsers = <%- JSON.stringify(allUsers) %>;
const currentUsername = '<%= currentUsername %>';
const nonce = "<%= nonce %>"
console.log('Nonce:', nonce);
</script>
<script src="https://code.jquery.com/jquery-3.6.4.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/5.3.0/js/bootstrap.bundle.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/xlsx/0.17.4/xlsx.full.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/2.0.5/FileSaver.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/exceljs/4.2.1/exceljs.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/flatpickr/dist/flatpickr.min.js"></script>
<script src="inusers.js"></script>
<script src="https://code.jquery.com/jquery-3.6.4.min.js" nonce="<%= nonce %>"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/5.3.0/js/bootstrap.bundle.min.js" nonce="<%= nonce %>" ></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/xlsx/0.17.4/xlsx.full.min.js" nonce="<%= nonce %>"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/2.0.5/FileSaver.min.js" nonce="<%= nonce %>"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/exceljs/4.2.1/exceljs.min.js" nonce="<%= nonce %>"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/js/bootstrap.bundle.min.js" nonce="<%= nonce %>"></script>
<script src="https://cdn.jsdelivr.net/npm/flatpickr/dist/flatpickr.min.js" nonce="<%= nonce %>"></script>
<script src="inusers.js" nonce="<%= nonce %>"></script>
</body>

View File

@ -33,7 +33,7 @@ $(document).ready(function () {
$('#logsContainer').hide();
$('#additional-text').hide();
$('#additional-text2').hide();
$('#additional-text2').hide();
$('#additional-text3').hide();
});
$('#searchUserButton').on('click', function () {
@ -124,6 +124,7 @@ $('#searchResultsList').on('click', '.deleteUserButton', function () {
headers: {
'Content-Type': 'application/json',
},
credentials: 'include', // Include cookies in the request
body: JSON.stringify({ csrfToken }), // Include CSRF token in the request body
})
.then(response => {
@ -243,8 +244,8 @@ function resetFormFields() {
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
credentials: 'include', // Include cookies in the request
body: JSON.stringify({
name: name,
username: username,
@ -330,6 +331,7 @@ $('#resetPasswordForm').on('submit', function (e) {
headers: {
'Content-Type': 'application/json',
},
credentials: 'include', // Include cookies in the request
body: JSON.stringify({
username: username,
password: password,
@ -356,8 +358,6 @@ $('#resetPasswordForm').on('submit', function (e) {
$('#resetPassword').val('');
$('#resetConfirmPassword').val('');
// You might want to hide the reset password form after submission
$('#resetPasswordFormContainer').hide();
})
.catch(error => {
// Handle 404 error separately to show an alert

67
Sean/views/login.css Normal file
View File

@ -0,0 +1,67 @@
body {
font-family: 'Arial', sans-serif;
background-color: #f4f4f4;
margin: 0;
display: flex;
align-items: center;
justify-content: center;
height: 100vh;
}
.login-container {
background-color: #fff;
padding: 20px;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
width: 300px;
margin: auto; /* Center the container horizontally */
}
h1 {
text-align: center;
color: #333;
}
form {
margin-top: 20px;
}
label {
display: block;
margin-bottom: 8px;
color: #555;
}
input {
width: calc(100% - 16px); /* Adjust the width and center the input */
padding: 8px;
margin-bottom: 16px;
border: 1px solid #ccc;
border-radius: 4px;
}
button {
background-color: #4caf50;
color: #fff;
padding: 10px;
border: none;
border-radius: 4px;
cursor: pointer;
width: 100%;
}
button:hover {
background-color: #45a049;
}
.reset-link-container {
text-align: center;
margin-top: 10px;
}
.reset-link {
color: #4caf50;
text-decoration: underline;
cursor: pointer;
}

View File

@ -4,75 +4,7 @@
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Login - Eco Saver</title>
<style>
body {
font-family: 'Arial', sans-serif;
background-color: #f4f4f4;
margin: 0;
display: flex;
align-items: center;
justify-content: center;
height: 100vh;
}
.login-container {
background-color: #fff;
padding: 20px;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
width: 300px;
margin: auto; /* Center the container horizontally */
}
h1 {
text-align: center;
color: #333;
}
form {
margin-top: 20px;
}
label {
display: block;
margin-bottom: 8px;
color: #555;
}
input {
width: calc(100% - 16px); /* Adjust the width and center the input */
padding: 8px;
margin-bottom: 16px;
border: 1px solid #ccc;
border-radius: 4px;
}
button {
background-color: #4caf50;
color: #fff;
padding: 10px;
border: none;
border-radius: 4px;
cursor: pointer;
width: 100%;
}
button:hover {
background-color: #45a049;
}
.reset-link-container {
text-align: center;
margin-top: 10px;
}
.reset-link {
color: #4caf50;
text-decoration: underline;
cursor: pointer;
}
</style>
<link rel="stylesheet" href="login.css">
</head>
<body>
<div class="login-container">

View File

@ -1,146 +0,0 @@
@import url('https://fonts.googleapis.com/css2?family=Poppins:wght@200;300;400;500;600;700&display=swap');
*{
margin: 0;
padding: 0;
box-sizing: border-box;
font-family: 'Poppins',sans-serif;
}
body{
height: 100vh;
display: flex;
justify-content: center;
align-items: center;
padding: 10px;
background: linear-gradient(135deg, #71b7e6, #9b59b6);
}
.container{
max-width: 700px;
width: 100%;
background-color: #fff;
padding: 25px 30px;
border-radius: 5px;
box-shadow: 0 5px 10px rgba(0,0,0,0.15);
}
.container .title{
font-size: 25px;
font-weight: 500;
position: relative;
}
.container .title::before{
content: "";
position: absolute;
left: 0;
bottom: 0;
height: 3px;
width: 30px;
border-radius: 5px;
background: linear-gradient(135deg, #71b7e6, #9b59b6);
}
.content form .user-details{
display: flex;
flex-wrap: wrap;
justify-content: space-between;
margin: 20px 0 12px 0;
}
form .user-details .input-box{
margin-bottom: 15px;
width: calc(100% / 2 - 20px);
}
form .input-box span.details{
display: block;
font-weight: 500;
margin-bottom: 5px;
}
.user-details .input-box input{
height: 45px;
width: 100%;
outline: none;
font-size: 16px;
border-radius: 5px;
padding-left: 15px;
border: 1px solid #ccc;
border-bottom-width: 2px;
transition: all 0.3s ease;
}
.user-details .input-box input:focus,
.user-details .input-box input:valid{
border-color: #9b59b6;
}
form .gender-details .gender-title{
font-size: 20px;
font-weight: 500;
}
form .category{
display: flex;
width: 80%;
margin: 14px 0 ;
justify-content: space-between;
}
form .category label{
display: flex;
align-items: center;
cursor: pointer;
}
form .category label .dot{
height: 18px;
width: 18px;
border-radius: 50%;
margin-right: 10px;
background: #d9d9d9;
border: 5px solid transparent;
transition: all 0.3s ease;
}
#dot-1:checked ~ .category label .one,
#dot-2:checked ~ .category label .two,
#dot-3:checked ~ .category label .three{
background: #9b59b6;
border-color: #d9d9d9;
}
form input[type="radio"]{
display: none;
}
form .button{
height: 45px;
margin: 35px 0
}
form .button input{
height: 100%;
width: 100%;
border-radius: 5px;
border: none;
color: #fff;
font-size: 18px;
font-weight: 500;
letter-spacing: 1px;
cursor: pointer;
transition: all 0.3s ease;
background: linear-gradient(135deg, #71b7e6, #9b59b6);
}
form .button input:hover{
/* transform: scale(0.99); */
background: linear-gradient(-135deg, #71b7e6, #9b59b6);
}
@media(max-width: 584px){
.container{
max-width: 100%;
}
form .user-details .input-box{
margin-bottom: 15px;
width: 100%;
}
form .category{
width: 100%;
}
.content form .user-details{
max-height: 300px;
overflow-y: scroll;
}
.user-details::-webkit-scrollbar{
width: 5px;
}
}
@media(max-width: 459px){
.container .content .category{
flex-direction: column;
}
}

50
Sean/views/otp.css Normal file
View File

@ -0,0 +1,50 @@
body {
font-family: Arial, sans-serif;
background-color: #f4f4f4;
text-align: center;
margin: 50px;
}
h2 {
color: #333;
}
form {
max-width: 300px;
margin: 20px auto;
padding: 20px;
background-color: #fff;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
}
label {
display: block;
margin-bottom: 8px;
color: #333;
}
input {
width: 100%;
padding: 10px;
margin-bottom: 20px;
box-sizing: border-box;
}
button {
background-color: #4caf50;
color: #fff;
padding: 10px 15px;
border: none;
border-radius: 4px;
cursor: pointer;
}
button:hover {
background-color: #45a049;
}
.error {
color: red;
margin-top: 10px;
}

View File

@ -4,58 +4,7 @@
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Enter OTP</title>
<style>
body {
font-family: Arial, sans-serif;
background-color: #f4f4f4;
text-align: center;
margin: 50px;
}
h2 {
color: #333;
}
form {
max-width: 300px;
margin: 20px auto;
padding: 20px;
background-color: #fff;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
}
label {
display: block;
margin-bottom: 8px;
color: #333;
}
input {
width: 100%;
padding: 10px;
margin-bottom: 20px;
box-sizing: border-box;
}
button {
background-color: #4caf50;
color: #fff;
padding: 10px 15px;
border: none;
border-radius: 4px;
cursor: pointer;
}
button:hover {
background-color: #45a049;
}
.error {
color: red;
margin-top: 10px;
}
</style>
<link rel="stylesheet" href="otp.css">
</head>
<body>
<h2>Enter OTP</h2>

View File

@ -1,162 +0,0 @@
/* Responsive CSS Here */
@media screen and (max-width: 950px) {
.nav-img {
height: 25px;
}
.nav-option {
gap: 30px;
}
.nav-option h3 {
font-size: 15px;
}
.report-topic-heading,
.item1,
.items {
width: 800px;
}
}
@media screen and (max-width: 850px) {
.nav-img {
height: 30px;
}
.nav-option {
gap: 30px;
}
.nav-option h3 {
font-size: 20px;
}
.report-topic-heading,
.item1,
.items {
width: 700px;
}
.navcontainer {
width: 100vw;
position: absolute;
transition: all 0.6s ease-in-out;
top: 0;
left: -100vw;
}
.nav {
width: 100%;
position: absolute;
}
.navclose {
left: 00px;
}
.searchbar {
display: none;
}
.main {
padding: 40px 30px 30px 30px;
}
.searchbar2 {
width: 100%;
display: flex;
margin: 0 0 40px 0;
justify-content: center;
}
.searchbar2 input {
width: 250px;
height: 42px;
border-radius: 50px 0 0 50px;
background-color: var(--background-color3);
padding: 0 20px;
font-size: 15px;
border: 2px solid var(--secondary-color);
}
}
@media screen and (max-width: 490px) {
.message {
display: none;
}
.logosec {
width: 100%;
justify-content: space-between;
}
.logo {
font-size: 20px;
}
.menuicn {
height: 25px;
}
.nav-img {
height: 25px;
}
.nav-option {
gap: 25px;
}
.nav-option h3 {
font-size: 12px;
}
.nav-upper-options {
gap: 15px;
}
.recent-Articles {
font-size: 20px;
}
.report-topic-heading,
.item1,
.items {
width: 550px;
}
}
@media screen and (max-width: 400px) {
.recent-Articles {
font-size: 17px;
}
.view {
width: 60px;
font-size: 10px;
height: 27px;
}
.report-header {
height: 60px;
padding: 10px 10px 5px 10px;
}
.searchbtn img {
height: 20px;
}
}
@media screen and (max-width: 320px) {
.recent-Articles {
font-size: 12px;
}
.view {
width: 50px;
font-size: 8px;
height: 27px;
}
.report-header {
height: 60px;
padding: 10px 5px 5px 5px;
}
.t-op {
font-size: 12px;
}
.t-op-nextlvl {
font-size: 10px;
}
.report-topic-heading,
.item1,
.items {
width: 300px;
}
.report-body {
padding: 10px;
}
.label-tag {
width: 70px;
}
.searchbtn {
width: 40px;
}
.searchbar2 input {
width: 180px;
}
}

View File

@ -1,10 +0,0 @@
<!-- setup-mfa.ejs (or your template engine's file) -->
<h2>Setup Multi-Factor Authentication</h2>
<p>Scan the QR code below with your authenticator app:</p>
<img src="<%= qrCodeDataUri %>" alt="QR Code">
<form action="/setup-mfa" method="post">
<label for="mfaCode">Enter MFA Code:</label>
<input type="text" id="mfaCode" name="mfaCode" required>
<button type="submit">Verify and Save</button>
</form>