Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Backend For Register Page #108

Closed
wants to merge 3 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
.env
/node_modules
2 changes: 2 additions & 0 deletions Server/api/.env.sample
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
MONGO_URI="mongo_db_url"
JWT_SECRET="Your_JWT-SECRET_KEY"
20 changes: 20 additions & 0 deletions Server/api/app.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@

import express from 'express';
import cors from 'cors';
import bodyParser from 'body-parser';
import authRoutes from '../routes/authRoutes.js';

const app = express();

// Middleware
app.use(cors());
app.use(express.json({ limit: '16kb' }));
app.use(express.urlencoded({ extended: true, limit: '16kb' }));
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));


// Routes
app.use('/api/v1/auth', authRoutes); // Authentication routes

export { app };
24 changes: 24 additions & 0 deletions Server/api/dbconnect.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import mongoose from 'mongoose';
import dotenv from 'dotenv'

dotenv.config()
// Database connection
export const dbConnect = async () => {
const url = process.env.MONGO_URI;

if (!url) {
console.error('No URL received from env. Check .env file path.');
process.exit(1);
}

try {
await mongoose.connect(url, {
useNewUrlParser: true,
useUnifiedTopology: true,
});
console.log('MongoDB connected');
} catch (err) {
console.error('Database connection error:', err);
process.exit(1); // Exit process with failure
}
};
20 changes: 20 additions & 0 deletions Server/api/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import dotenv from 'dotenv';
import { dbConnect } from './dbconnect.js';
import { app } from './app.js';

// Load environment variables
dotenv.config();

console.log('Starting app. MONGO_URI:', process.env.MONGO_URI);

// Connect to the database and start the server
dbConnect()
.then(() => {
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => {
console.log(`App is running on port ${PORT} and DB connected`);
});
})
.catch((err) => {
console.error('Database connection failed:', err);
});
81 changes: 81 additions & 0 deletions Server/controller/authController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
import jwt from 'jsonwebtoken';
import User from '../models/User.js';

// User Registration
export const registerUser = async (req, res) => {
const { username, email, password, dob, location } = req.body;

// Check for required fields
if (!username || !email || !password) {
return res.status(400).send({ error: "Username, email, and password are required." });
}

try {
// Check if the user already exists
const userExists = await User.findOne({ email });

if (userExists) {
return res.status(400).send({ message: 'User already exists' });
}

// Create a new user
const user = new User({
username,
email,
password,
dob, // Optional field
location, // Optional field
});

await user.save();
console.log('User saved successfully');

// Generate JWT token
const token = jwt.sign({ id: user._id }, "THIS_IS_A_JWT_SECRET", {
expiresIn: '1h',
});

// Respond with success message and token
res.status(201).send({
message: 'User created successfully',
token,
});
} catch (error) {
console.error('Error during user registration:', error);
res.status(500).send({ message: 'Server error', error: error.message });
}
};

// User Login
export const loginUser = async (req, res) => {
const { email, password } = req.body;

try {
const user = await User.findOne({ email });

if (!user) {
console.log("User does not exist");
return res.status(400).send({ message: 'Invalid credentials user' });
}

const isPasswordMatch = await user.matchPassword(password);

if (!isPasswordMatch) {
console.log("Password doesn't match");
return res.status(400).send({ message: 'Invalid credentials password' });
}

const token = jwt.sign({ id: user._id }, "THIS_IS_A_JWT_SECRET", {
expiresIn: '1h',
});

res.send({
message: 'Login successful',
token,
});
} catch (error) {
console.error('Error during user login:', error);
res.status(500).send({ message: 'Server error', error: error.message });
}
};

42 changes: 42 additions & 0 deletions Server/middleware/auth.middleware.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import jwt from 'jsonwebtoken';

const authUser = async (req, res, next) => {
try {
// Extract the Authorization header
const authHeader = req.headers.authorization; // Note: Headers are case-insensitive

if (!authHeader) {
return res.status(401).json({ error: "No token found. Please log in first." });
}

// Split the Bearer token
const token = authHeader.split(' ')[1]; // Assumes format: "Bearer token"

if (!token) {
return res.status(401).json({ error: "Malformed token. Authorization failed." });
}

// Verify the token
const decoded = jwt.verify(token, "THIS_IS_A_JWT_SECRET"); // Replace with your secret key

// Add user data to request for downstream handlers
req.user = decoded;

// Pass control to the next middleware or route handler
next();
} catch (error) {
console.error("Error verifying token:", error.message);

// Handle specific JWT errors
if (error.name === 'TokenExpiredError') {
return res.status(401).json({ error: "Token expired. Please log in again." });
} else if (error.name === 'JsonWebTokenError') {
return res.status(401).json({ error: "Invalid token. Authorization failed." });
}

// Catch-all for unexpected errors
res.status(500).json({ error: "Internal server error during authentication." });
}
};

export {authUser};
55 changes: 55 additions & 0 deletions Server/models/User.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
import mongoose from 'mongoose';
import bcrypt from 'bcryptjs';

// User schema
const userSchema = new mongoose.Schema({
username: {
type: String,
required: true,
unique: true,
},
email: {
type: String,
required: true,
unique: true,
},
password: {
type: String,
required: true,
},
inSightsCount: {
type: Number,
default: 0,
},
createdOn: {
type: Date,
default: Date.now, // Automatically set to the current date and time
},
dob: {
type: Date, // Date of Birth field
required: false, // Optional field
},
location: {
type: String, // Can store city, state, or country
required: false, // Optional field
},
});

// Hash password before saving
userSchema.pre('save', async function (next) {
if (!this.isModified('password')) {
return next();
}
const salt = await bcrypt.genSalt(10);
this.password = await bcrypt.hash(this.password, salt);
next();
});

// Method to compare password for login
userSchema.methods.matchPassword = async function (enteredPassword) {
return await bcrypt.compare(enteredPassword, this.password);
};

const User = mongoose.model('User', userSchema);

export default User;
11 changes: 11 additions & 0 deletions Server/routes/authRoutes.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import express from 'express';
import { registerUser, loginUser } from '../controller/authController.js';
const router = express.Router();

// Register Route
router.post('/signup', registerUser);

// Login Route
router.post('/login', loginUser);

export default router;
42 changes: 42 additions & 0 deletions js/signup.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
document.addEventListener('DOMContentLoaded', function() {
const signupForm = document.getElementById('signupForm');
if (signupForm) {
signupForm.addEventListener('submit', handleSignupSubmit);
}
});

function handleSignupSubmit(event) {
event.preventDefault(); // Prevent the default form submission

const username = document.getElementById('username').value;
const email = document.getElementById('email').value;
const password = document.getElementById('password').value;
const confirmPassword = document.getElementById('confirmPassword').value;

if (password !== confirmPassword) {
alert('Passwords do not match');
return;
}

const formData = { username, email, password };

// fetch('https://insight-sync-u1bq.vercel.app/api/v1/auth/signup', {
fetch('http://localhost:3000/api/v1/auth/signup', {

method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(formData),
})
.then(response => response.json())
.then(data => {
if (data.token) {
alert('Signup successful! You are now logged in.');
localStorage.setItem('authToken', data.token);
window.location.href = '/SCD-Profile-Score/';
} else {
alert('Signup failed: ' + data.message);
}
})
.catch(error => console.error('Error:', error));
}

Loading
Loading