· 4 years ago · Mar 27, 2021, 11:26 AM
1<?php
2 // This checks if a current session is active when the user accesses this page
3 // if so, redirect the user to the members.php page
4 // this is done so that the user is unable to login while
5 // a current session is active, as it should be
6 session_start();
7 if(!empty($_SESSION['username'])) {
8 header("Location: members.php");
9 }
10 else {
11 session_destroy();
12 }
13?>
14
15<html>
16 <head>
17 <title>Login Page</title>
18 </head>
19 <style>
20 h1 {
21 font-family: Arial, sans-serif;
22 }
23 </style>
24 <body>
25 <h1>Login</h2>
26 <!-- form for user to input information in order to login -->
27 <form name="login" method="POST" action="login.php">
28 Username (Email Address): <input name="username" type="text"><br>
29 Password: <input name="password" type="password"><br>
30 <input type="submit" name="submit" value="Login">
31 </form>
32
33 <?php
34 /* includes "dbconnect.php", which is responsible for connecting
35 * to the PHPMyAdmin database */
36 include('dbconnect.php');
37
38 // Forces the timezone to BST - USBWebserver uses Paris timezone (GMT+1)
39 date_default_timezone_set("Europe/London");
40
41 //Starts a function responsible for page statistics - see section down below in this script
42 AddVisit();
43
44 /* the user's input, which is stored in the global post variabes are assigned to local variables for use
45 * this stores the username and password
46 * this will only assign data to the local variables if the global post variables are not empty
47 * meaning the user has to submit input first.
48 * this also prevents an error from occurring when entering the page */
49 if(isset($_POST['submit'])) {
50 $username = $_POST['username'];
51 $password = $_POST['password'];
52 // executes a CheckValidation function that i defined myself - see below
53 CheckValidation();
54 }
55
56 /*
57 This function contains multiple checks using if statements for validation
58 This is only executed after an input is available within the global post variables (when the user clicks submit)
59 */
60
61 function CheckValidation() {
62 // global variables to pass variables from out of the function scope to within its scope
63 global $username;
64 global $password;
65 global $dbconnect;
66
67 // Regular expression used to validate and check if the username field is in the format of an email
68 $emailRegex = '/^[a-z\d\._-]+@([a-z\d-]+\.)+[a-z]{2,6}$/i';
69
70 // This is an error message that gets displayed when a validation check fails..
71 // ..when tested against the user's input
72 $invalidnotEmail = "Username must be in the format of an email address.\n";
73 $invalidEmptyFields = "One or more fields left empty. Please enter data on all required fields.\n";
74 $invalidLogin = "Username or password incorrect. Please try again with the correct user credentials.\n";
75
76 // $logPath contains the location of the error_log.txt file, used to log errors when it occurs
77 // $logFormat contains the general format of the errors that will be written into the error_log.txt file
78 // this will be concatenated with one of the error messages above to form a coherent and informative error message
79 $logPath = "logs/error_log.txt";
80 $logFormat = "[". date("d/m/y") . " " . date("h:i:s A") . "] " . "(Client: " . $_SERVER['REMOTE_ADDR'] . ") [ERROR]: ";
81
82 // This checks if any of the variables that contains the data from the global post variables are empty
83 // if so, it means that the user has left one or more fields empty when clicking the submit button
84 // also writes error into error_log.txt
85 if(empty($username) || empty($password)) {
86 echo $invalidEmptyFields;
87 $errorMessage = $logFormat . $invalidEmptyFields;
88 $file = fopen($logPath, 'a');
89 fwrite($file, $errorMessage);
90 fclose($file);
91 return;
92 }
93
94 // $sql contains an SQL query which selects all cells from the userinfo table, under the username field..
95 //..which is equal to the value/data stored in $username AND checks if all cells under password are equal to $password
96 // $results executes the SQL query in $sql by using the mysqli_query() function which also takes in the database connection..
97 //..established in dbconnect.php. $results can be used to evaluate whether the query was executed or not
98 $sql = "select * from userinfo where username = '$username' && password = '$password'";
99 $results = mysqli_query($dbconnect, $sql);
100
101 // if the query fails to execute, an error is written to error_log.txt
102 if(!$results) {
103 $errorMessage = $logFormat . mysqli_error($dbconnect) . "\n";
104 $file = fopen($logPath, 'a');
105 fwrite($file, $errorMessage);
106 fclose($file);
107 die("Database connection failed: " . mysqli_error($dbconnect));
108 return;
109 }
110
111 // $results contains the result of the query
112 // $num uses the mysqli_num_rows checks how many rows have been selected to fulfill the query
113 $num = mysqli_num_rows($results);
114
115 // This validation rule checks if the username is in the format of an email
116 // preg_match takes in a regular expression defined in $emailRegex and a string to validate with
117 // if !preg_match, this means that $username is not in an email format
118 // the error message is displayed to the user, and is written in error_log.txt
119 // a return statement is used to terminate the function
120 if(!preg_match($emailRegex, $username)) {
121 echo $invalidnotEmail;
122
123 $errorMessage = $logFormat . $invalidnotEmail;
124 $file = fopen($logPath, 'a');
125 fwrite($file, $errorMessage);
126 fclose($file);
127 return;
128 }
129
130 // if $num == 1, the row containing BOTH the username and password exists within the database
131 // this means that the user's input is verified and will be redirected to the members.php page
132 if($num == 1) {
133 //executes a query that selects the user's name from the table, according to their username and password
134 $sql = "SELECT firstname, surname from userinfo WHERE username = '$username' && password = '$password'";
135 $results = mysqli_query($dbconnect, $sql);
136
137 if(!$results) {
138 $errorMessage = $logFormat . mysqli_error($dbconnect) . "\n";
139 $file = fopen($logPath, 'a');
140 fwrite($file, $errorMessage);
141 fclose($file);
142 die("Database connection failed: " . mysqli_error($dbconnect));
143 exit();
144 }
145
146 //assign all of the results from the query into a variable, which stores them into an associative array
147 $fields = mysqli_fetch_array($results);
148
149 // a login session starts, and stores the username into the 'username' session variable
150 // also stores the user's details from the query
151 session_start();
152 $_SESSION['username'] = $username;
153 $_SESSION['firstname'] = $fields['firstname'];
154 $_SESSION['surname'] = $fields['surname'];
155
156 // header redirects user to members.php
157 header("Location: members.php");
158 }
159 else {
160 echo $invalidLogin;
161 $errorMessage = $logFormat . $invalidLogin;
162 $file = fopen($logPath, 'a');
163 fwrite($file, $errorMessage);
164 fclose($file);
165 }
166 return;
167 }
168
169 function AddVisit() {
170 // file location of the txt file which contains the amount of times register.php has been visited
171 $statsPath = "logs/login.txt";
172
173
174 // opens the file at $statsPath with the 'read' open mode
175 $file = fopen($statsPath, 'r+');
176
177 // checks if the filesize of reg.txt is 0
178 // this means that no data is entered, and so by default 0 must be entered
179 // this is necessary in order to increment this value by 1 every time register.php is visited
180 // otherwise, no value exists within the text file to be incremented
181
182 if(filesize($statsPath) == 0) {
183 fwrite($file, 0);
184 }
185
186 // this function is required to instantly increment 0 to 1
187 // otherwise, the file only increments 0 to 1 on the second visit to the page - which is incorrect.
188 clearstatcache();
189
190 // this takes the value stored within reg.txt and stores it in $currentNumberOfVisits
191 // this will be used to increment the value stored in the file, and then rewriting the file with it
192 // this will effectively create a system that increments a value every time a page gets visited
193 // only executes if the filesize of the file is greater than 0 - meaning there is a value stored in it
194 if(filesize($statsPath) > 0) {
195 $currentNumberOfVisits = fread($file, filesize($statsPath));
196 fclose($file);
197
198 // opens the file with the 'write' open mode, overwriting any content
199 // takes the value stored in $currentNumberOfVisits, adds 1 to it and then writes it in reg.txt
200 $file = fopen($statsPath, 'w');
201 fwrite($file, $currentNumberOfVisits + 1);
202 fclose($file);
203 }
204 }
205
206 ?>
207 <br><br>
208 <a href="index.html">Back to Index Page</a>
209 </body>
210</html>
211