session_start();
if (isset($_SESSION["userid"]))
{
// Already have an account
// Get them out of here
Header("Location: index.php");
}
// Initialize Error variable
$reg_error = 0;
// Just so I didn't have to type $_POST to reference the input
if (isset($_POST["username"]))
{
$username = $_POST["username"];
}
if (isset($_POST["passphrase"]))
{
$password = $_POST["passphrase"];
}
// Check if given both username and password
if ((isset($username)) && (isset($password)))
{
// Check to make sure input matches page requirements
// Password field in HTML can also do this but
// HTML can be edited clientside and is thus unreliable for checking
if ((strlen($username) >= 6) && (strlen($password) >= 8))
{
require_once 'admin/config.php';
// Check the user doesn't already exist
$stmt1 = $con->prepare("SELECT * FROM users WHERE username = ?");
$stmt1->bind_param("s", $username);
$stmt1->execute();
$stmt1->store_result();
if (!(($stmt1->num_rows) > 0)) // User doesn't exist
{
// Start adding user to database
$options = [
// cost can be increased as server hardware improves
'cost' => 10,
];
$password_hash = password_hash($password, PASSWORD_DEFAULT, $options);
$stmt2 = $con->prepare("INSERT INTO users (username, password) VALUES (?, ?)");
$stmt2->bind_param("ss", $username, $password_hash);
$stmt2->execute();
$stmt2->close();
$stmt3 = $con->prepare("SELECT user_id FROM users WHERE username = ?");
$stmt3->bind_param("s", $username);
$stmt3->execute();
$stmt3->bind_result($userid);
$stmt3->store_result();
while ($stmt3->fetch())
{
$stmt4 = $con->prepare("INSERT INTO profiles (user_id, birthday, gender) VALUES (?, ?, 0)");
$date = date('Y-m-d');
$stmt4->bind_param("is", $userid, $date);
$stmt4->execute();
$stmt4->close();
}
$reg_error = 100; // User registered
}
else
{
$reg_error = 5; // User already registered
}
$stmt1->close();
$con->close();
}
else if (strlen($username) < 6)
{
$reg_error = 3; // Username too short
}
else if (strlen($password) < 8)
{
$reg_error = 4; // Password too short
}
}
else if (isset($username))
{
$reg_error = 1; // No password given
}
else if (isset($password))
{
$reg_error = 2; // No username given
}
Some other notes on registration:
- Since this is accessing the user database containing the passwords, it is important to make sure the page is secure. Usage of prepared statements here helps protect against SQL injection which could dump the whole table or even delete it.
- $reg_error is used to display an error to the user using switch/case statements and an echo.
- Since storing passwords in plaintext is insecure, the passwords are hashed before being inserted into the database using the password_hash() function in PHP. They can later be used for logging in via the password_verify() function.
- PASSWORD_DEFAULT is one of several options for encryption algorithms for the password_hash() function. In current versions, PASSWORD_DEFAULT uses the BCRYPT algorithm, which produces a string of about 70 characters. The password field has been made a 255 length VARCHAR field to compensate.
- There is no field for a salt while using the function since the function generates a salt automatically.
- The 'cost' variable for $options determines the complexity of the algorithm, with higher values requiring more powerful hardware. The value defaults to 10, but including it now makes it easier to expand later. A small amount of other options are available for $options, although they have no use for this project.
// Check if given both username and password
if ((isset($username)) && (isset($password)))
{
require_once 'admin/config.php';
// Verify the username actually exists
$stmt1 = $con->prepare("SELECT * FROM users WHERE username = ?");
$stmt1->bind_param("s", $username);
$stmt1->execute();
$stmt1->store_result();
if (($stmt1->num_rows) > 0)
{
// Fetch hashed password
$stmt2 = $con->prepare("SELECT password FROM users WHERE username = ?");
$stmt2->bind_param("s", $username);
$stmt2->execute();
$stmt2->bind_result($pass_hash);
$stmt2->store_result();
while ($stmt2->fetch())
{
// Verify password match
if (password_verify($password, $pass_hash))
{
// Fetch user ID to store in session
if ($stmt3 = $con->prepare("SELECT user_id FROM users WHERE username = ?"))
{
$stmt3->bind_param("s", $username);
$stmt3->execute();
$stmt3->bind_result($userid);
$stmt3->store_result();
while ($stmt3->fetch())
{
$_SESSION["userid"] = $userid;
$_SESSION["username"] = $username;
}
Header("Location: index.php");
$stmt3->close();
}
else echo "<p>Something went wrong.</p>" . htmlspecialchars($con->error);
}
}
$stmt2->close();
}
$stmt1->close();
$con->close();
} Other than adding variables to the session for use on other pages, there is not much else to comment on here.
I have also started work on the article part of the website. There's some basic functionality, supporting a text body, title and tagline, although there are still several problems to work out:
- Currently the idea is for an image header to be optional. I need to figure out a method to make the image header not display in HTML if the database entry for it does not exist.
- There is no way to insert paragraph breaks into the text body. While not a particular problem, it does hamper the presentation of the site. Looking into BB code might help produce a solution.
No comments:
Post a Comment