MySQL INNER JOIN using an OR whilst logging in - php

My table structure is as follows:
~ MEMBERS ~
UID (a-i)
NAME
EMAIL
~ COUPLES ~
UID_1
UID_2
PASSWORD
SALT
When a couple sign up, their UIDs get inserted in to the couples table, along with their joint password (and its salt). Now, when logging in, I need to join the tables so I can check the password for either user.
i.e. Find Email Address > See which Couple they are in > Check against Password
This is my current query:
$query = "SELECT * FROM MEMBERS m
INNER JOIN COUPLES c ON ((c.UID_1 = m.UID) OR (c.UID_2 = m.UID))
WHERE EMAIL = '$email'";
(I'm only using * for now as I can't figure out exactly what I need to select for the INNER JOIN to work.)
And the rest of the code on login-script.php is as follows:
$result = mysqli_query($con, $query);
if(mysqli_num_rows($result) == 0) {
header('Location: index.php?msg=error4');
exit();
}
$data = mysqli_fetch_array($result, MYSQL_ASSOC);
$hash = hash('sha256', $data['SALT'] . hash('sha256', $password));
if ($hash != $data['PASSWORD']) {
header('Location: index.php?msg=error5');
exit();
}
else {
echo "Logged in.";
}
?>
If I try and log in, the error message ?msg=error5 gets thrown, which means that the passwords do not match, but I cannot see a problem in that part of my code. I believe it's telling me they do not match because it's not looking in the right table/for the right data, which must be something wrong with my INNER JOIN.
Any help would be much appreciated.
EDIT: I realise now that it would have made a lot more sense to have just put the password and salt in to MEMBERS for both records so I'm only selecting from one table, but the deed is done and I'm curious to see if this is possible.

Actually, I tried your structure and code on http://www.w3schools.com/sql/trysql.asp?filename=trysql_select_all and this works for me:
SELECT * from members M JOIN couples C ON uid_1=Uid or uid_2=uid
WHERE email='youremail';
Perhaps the problem is that in the table there is more than 1 couple a person is actually in?
Like:
uid_1, uid_2, pass
1 2 xxx
1 3 yyy
You should either limit it on database side to unique columns or change code, because if you don't, you might be getting more than 1 row as result and you would need to check every couple's password against particular UID.

Related

How would I echo users who haven't confirmed their email

I know how to echo the number of users that have activated their email but it got a bit tricky when I wanted to echo the number of unverified users.
My register system assigns a key in the active column in the members table. If the user activates their email it goes from a random md5 string to 'Yes'
ex: https://imgur.com/a/83BUYTK
Anyways... this is what I got so far:
$result3 = mysqli_query($db, "SELECT * FROM `members` WHERE `active` = 'Yes'");
$unverified_users = mysqli_num_rows($result3);
I just dunno how to echo the number of unverified users instead of the verified users.
Any help is appreciated btw I'm a noob to PHP so go easy on me :P
Answer:
$result3 = mysqli_query($db, "SELECT * FROM members WHERE active != 'Yes'");
$unverified_users = mysqli_num_rows($result3);
I didn't know that != meant not equal to... my bad lol
Thanks to #Barmar
use count(*).
$unverified_users=$db->query("SELECT count(*) FROM members WHERE active != 'Yes'")->fetch_array()[0];
this should be faster than SELECT * because now the db only has to prepare 1 result, the number of matches, instead of preparing a number of results equal to the number of matches.

How to select data from a specific user using INNER JOIN

I want to select data from a specific user. When he is logged in on the website he will see information related to him.
I'm using INNER JOIN and I need to select data related to his login or id.
Any account that I use to login, I can access all exercises registered =/
On this case I'm using an ID.
Is something wrong with the query?
I don't get any errors from PHP. Where can I put the WHERE clause?
Code:
<?php
$login = $_SESSION['login'];
$consulta = mysqli_query($conexao,"SELECT exercicios.nome_exercicio AS nome_exc,
exercicios.repeticoes_exercicio AS rep_exc,
exercicios.serie_exercicio AS serie_exc
FROM exercicios
INNER JOIN usuarios ON usuarios.id_usuario = exercicios.id_usuario WHERE exercicios.id_usuario = '5'");
if(mysqli_num_rows($consulta)> 0){
echo "<div class='table-responsive'><table class='table table-responsive'>
<tr><td>Nome</td><td>Repetições</td><td>Série</td></tr>";
while ($exercicio = mysqli_fetch_assoc($consulta))
{
print"<tr>
<td>$exercicio[nome_exc]</td>
<td>$exercicio[rep_exc]</td>
<td>$exercicio[serie_exc]</td>
</tr>";
}
echo " </table></div>";
}
else {
echo "<h3>Seu instrutor ainda não cadastrou exercícios</h3>";
}
?>
You are missed some important things, for example, what data are you storing in your session variable login?
$login = $_SESSION['login'];
When a user send the login data first time (for example email and password), you will search the data on the database (table accounts or users or the table you need) and then if exist you should store the user data on session (the id is the most important). So, when you need to access to the exercises of the user, you need only to specify the correct user id on the where condition like ($login in this example is an array with user data):
"SELECT .... FROM .... WHERE id = {$login['userId']}"
Hope this explanation will be enough to fix your problem.

Show query result for logged in user

I got some great help in my last question, someone directed me to go learn about database tables and stuff, since then I blasted through most of the things I was stuck on!
Unfortunately I've reached another problem which I can't seem to fix.
I can merge two tables and get results, but I can't seem to get the results of the user that is logged in. For example, I display the amount of 'gold' the user has at the top left corner, I have 7 users that have 100 gold assigned to them and I only want them to be seen when the user that the gold belongs to is logged in, if you get me? Here's what it looks like all the time, whether logged in or not: http://imgur.com/kgqgnPc
here's the code
$sql = 'SELECT `stats`.`id`, `stats`.`gold`, `users`.`id` FROM stats, users WHERE username = username';
$con=mysqli_connect("localhost","root","","game");
mysqli_select_db($con,'game');
$retval = mysqli_query($con,$sql);
if(! $retval )
{
die('Could not get data: ' . mysql_error());
}
while($row = mysqli_fetch_array($retval, MYSQL_ASSOC))
{
echo "Gold :{$row['gold']} <br> ".
"--------------------------------<br>";
I'm 90% sure it's to do with the "select/from/where" part but I've done lots of research and can't get it right :(
Database structure: http://imgur.com/DR40iv8 (Sorry, I don't know how to get it without the command line)
I see that you have the gold in one table and the users in another. The gold in the gold table should point to what user owns the gold. Like for example owner_id pointing to the users id. Then you should be able to do like this:
$sql = "SELECT stats.id, stats.gold, users.id, users.username FROM stats, users WHERE users.username = '$username' AND stats.owner_id = users.id";
This tells to find user with the username specified in $username, and the gold with owner_id the same as the users id matching that username.
Hope this helps
Try:
SELECT `stats`.`id`, `stats`.`gold`, `users`.`id` FROM stats, users WHERE stats.username = users.username
Because username is common to both tables (I assume), it's important to explicitly state which table username is coming from.
Edited to add:
You would still need to specify which username you want from the results of the joined tables.
$sql = 'SELECT `stats`.`id`, `stats`.`gold`, `users`.`id` FROM stats, users WHERE `stats`.username = `users`.username AND `users`.`'.$yourUserVariable.'`;

how to make login script from multiple table?

> i ve got 4 separate tables to store login data.
>>> tables are **admin_login staff_login >tutor_login student_login**.
>>>>>> my php registration form is storing data into this fields.
now i need some suggestion how i can make login script?.
I've got the login form ready.
For starters why have 4 tables? Why not have 1 with a login type field??
The general rules are the same for multiple tables as for one. You want to check for the username / email address, then check the passwords.
Start off querying your tables for the username email address. Count the results. If their is a result then check the password (with whatever if any encryption you're using) matches and log them in. If there are no results throw a message to the user saying there is no one matching that username / email, if the password doesn't match up then tell them that.
I'm not going to write it for you but here's the gist of it:
$query = mysql_query("CHECK FOR EMAIL ADDRESSES OR USERNAMES"); // Just query multiple tables if you're going to do it this way (I'd still use the one though)
$count = mysql_num_rows($query);
if ($count > 0) { // Email address exists
// Check the passwords match up
if (PASSWORDS MATCH) {
// Do your login here
} else {
// Password wrong error
}
} else {
// No username error here
}
You could work out something using UNION's but it would be better to re-factor the database to a single table with a field denoting if they are Admin/Tutor etc.
either you can use a join query first or you can have one unified table for all users with an accessLevel field like:
users-table:
username | passwordHash | accessLevel
---------+--------------+------------
abc | mnbdjhgs | admin
pqr | kfgjkfbb | stud
then you can simply check userdetails you get from the loin form like:
$result = $mysqli->query("SELECT passwordHash, accesslevel FROM users WHERE username = '{$username}' ");
if($result)
{ $data = $result->fetch_assoc();
if($data)
{ if($password === $data['passwordHash'])
{ //identify the user-type here..
$accesslevel = $data['accessLevel'];
//now u can do session initialization and other stuff..
}
}
}
else
{ //show wrong username or password messages
}

Joining tables in MySql with one common field but different values for the common field

how to join 3 tables with one common field like
table1:c_id,username,password,c_role
table2:p_id,username,password,c_role
table3:s_id,username,password,c_role
in this c_role field is common
here i assigned
enum '1' for c_role in table1
enum '2' for c_role in table2
enum '3' for c_role in table3
for giving rights to 3 different users like corres, principal and for a staff when they login..
Now when they login it should identify the user and take them to their page..
You should have one table that contains the following columns:
id (unique, primary), username, password, role (INT, would be assigned 1-3 for principal, staff or corre depending on the user)
Additionally
You could have another table called roles if you want set up like this:
id (unique, primary), title (options for title would be principal, staff, or corres)
When the user logs in just do something like
if($role == 1){
// redirect to principal page
}
elseif($role == 2){
// redirect to staff page
}
elseif($role == 3){
// redirect to corres page
}
I'm not certain but I believe this would work as well. Try this query.
(SELECT '1' AS role FROM table1 WHERE username = $username AND password = $password)
UNION ALL
(SELECT '2' AS role FROM table2 WHERE username = $username AND password = $password)
UNION ALL
(SELECT '3' AS role FROM table3 WHERE username = $username AND password = $password)
Assuming the user is only located in ONE of those three tables then it should match the username and password and find out which table the user is coming from. Then you can pull out the role by using
$role = $row['role'];
If the username/password combination is incorrect then $role would be empty or you could fetch the number of rows [using $iscorrectuser = mysql_num_rows($query)] where there is a match and the number of rows would be 0. You could then redirect the user trying to log in with a "Unsuccessful login" error message.
The only joins would be on username (and password ?) unless c_id, p_id and s_id are all the same id?
You can't join on role seeing as they are different in each table, aside from an utterly daft role = 1 in Table1 is the equivalent of role = 2 in table2.
Do you mean a union? As in you want
User Password Role
Fred Fr3d 1
Fred ??? 2
Fred ??? 3
Not sure what you are trying to achieve with this schema, but it breaks near every rule in the book, and doesn't seem to meet your needs....
Based on your comment, one way you might look at is.
Is
Users (UserID, UserName, Password etc) Key UserID
Roles (RoleID, RoleName etc) Key RoleID
UserRoles(UserID,RoleID) Key UserID,RoleID
You need to learn a bit about databases particularly normalisation, first three forms should do for most things.
Then
Select UserName, Password,RoleName From Users
inner join UserRoles on Users.UserID = UserRoles.UserID
inner join Roles on UserRoles.RoleID = Roles.RoleId
and such like become possible and efficient.
session and include functions are given:
session_start();
include("config.php");
if(isset($_POST['T_UserName']) && isset($_POST['T_Password']) && !empty($_POST['T_UserName']) && !empty($_POST['T_Password']))
{
username and password sent from form:
$T_UserName=$_POST['T_UserName'];
$T_Password=$_POST['T_Password'];
To protect MySQL injection:
$T_UserName = stripslashes($T_UserName);
$T_Password = stripslashes($T_Password);
$T_UserName= mysql_real_escape_string($T_UserName);
$T_Password = mysql_real_escape_string($T_Password);
$sql="SELECT * FROM login WHERE username='$T_UserName' and password='$T_Password'"; $result=mysql_query($sql);
Mysql_num_row is counting table row:
$count=mysql_num_rows($result);
If result matched $T_UserName and $T_Password, table row must be 1 row :
if($count==1)
{
Register $T_UserName, $T_Password and redirect to file "correspindex.php" :
session_register("T_UserName");
session_register("T_Password");
redirect to error page or display error message then :
if(isset($_POST['emp_role'])
{
$userinfo = mysql_fetch_assoc($sql);
$emp_role = $userinfo['emp_role'];
if($emp_role == 1)
{
header("location:corrrespondindex.php");
}
elseif($emp_role == 2 )
{
header("location:principalindex.php");
}
elseif($emp_role == 3)
{
header("location:staffindex.php");
}
closes out if the user DOES exist:
header("location:loginhome.php");
}
else
{
echo "Wrong Username or Password";
}
}
}
php is closed
this is the php code im getting so many error
i create 1table with id,username,password and role(ENUM,values as'1','2','3' –
any else shud i do in the code???

Categories