mysql- get number of occurrences - php

Hi i am trying to get a mysql query working and need some help. I have 2 tables (staff, booking).
Staff table contains staff details
StaffID
First_name
Last_name
1
John
Doe
2
Mary
Doe
Booking table contains
BookingID
StaffID
Status
1
1
cancelled
2
1
cancelled
3
1
confirmed
4
2
cancelled
5
1
confirmed
I would like to get the count of confirmed/cancelled bookings for each staff but is having trouble getting it to work. My current query that I'm using is
Select staff.StaffID, staff.First_name, staff.Last_name, sum(booking.Status LIKE '$status') as Status
from staff, booking
where staff.StaffID = booking.ConvenerID
group by staff.StaffID
$status being cancelled or confirmed. With this query I'm only able to display a row if there is a status value, if a staff have no cancelled it does not display the row for that staff. How can I get the row to display even if the count of $status is 0.

You need a LEFT join of the tables:
SELECT s.StaffID, s.First_name, s.Last_name,
COALESCE(SUM(b.Status = ?), 0) AS counter
FROM staff s LEFT JOIN booking b
ON s.StaffID = b.StaffID
GROUP BY s.StaffID;
Replace ? with the status value that you want (there is no reason to use the operator LIKE because a simple = works fine).

Related

fetching details of user having same reporting email address using join or alias

I have two tables
tbl_user:
id fisrtname lastname
5 John Doe
6 Peter Parker
7 Will Smith
tbl_experience:
exp_id usr_id user_reporting_to
1 5 dev#abc.com
2 6 admin#abc.com
3 7 dev#abc.com
I want to fetch those record who have same reporting email address with where condition usr_id=5 because when i am login in to my page it creates the session of user id for e.g it is now 5 in where condition using join or alias
SELECT texperience.tbl_experience_report_to_email AS tbl_experience_report_to_email,
tuser.tbl_user_fname AS tbl_user_fname,
texperience.tbl_experience_designation AS tbl_experience_designation
FROM tbl_experience AS texperience,
tbl_user AS tuser
WHERE tuser.tbl_user_fname = tuser.tbl_experience_id
AND texperience.tbl_experience_report_to_email = texperience.tbl_experience_id
AND texperience.tbl_experience_user_id = 1
SELECT tbl_user.*, tbl_experience.user_reporting_to FROM tbl_user
LEFT JOIN tbl_experience ON (tbl_user.id=tbl_experience.usr_id)
LEFT JOIN (SELECT count(*) as total_user, user_reporting_to FROM tbl_experience GROUP BY user_reporting_to) as email_group ON
(email_group.user_reporting_to = tbl_experience.user_reporting_to) WHERE email_group.total_user > 1
Basically have a subquery that group all the email address and the joined table will return those users that have emails appearing more than once in the tbl_experience.

Creating Message System in PHP

I m trying to create message system where I want to list down the users with whom one has interacted with recent chat on top I know this question is duplicate as well but i cant figure out where the problem is
Here is my message table structure
user_message table
msgID sentBy sentTo message sentTime
1 3 1 Hii B 1493306882
2 3 1 Hi A 1493309615
1 1 3 Hmm 1493306882
2 1 3 Yeah 1493309615
and the query i tried is
QUERY
SELECT * FROM user_message_status LEFT JOIN users ON user_message_status.userID=users.userID
LEFT JOIN user_message ON user_message_status.msgID=user_message.msgID WHERE user_message_status.userID='".$_SESSION['userid']."'
GROUP BY user_message_status.msgID ORDER BY user_message.msgID DESC
PROBLEM:
1) When userA send msg to userB, userA name is printed in chat list instead of recipient(userB)
2) The amount of msg sent or receive equals to the number of users are listed in the chat.
user_message_status: table
msgstatusID msgID userID box read readTime
1 1 3 outbox 0 0
2 1 1 inbox 0 0
This is status table to read unread messages or delete
First update the query to the below:
SELECT *
FROM user_message_status s
LEFT JOIN users u USING userID
LEFT JOIN user_message m USING msgID
WHERE s.userID='".$_SESSION['userid']."'
GROUP BY user_message_status.msgID
ORDER BY user_message.msgID DESC
Because both tables have the same column names, to make you sql shorter and neater, you can use the USING function
Both LEFT JOIN users ON user_message_status.userID=users.userID and LEFT JOIN user_message ON user_message_status.msgID=user_message.msgID was changed. We then renamed the tables to just a single letter so you don't have to write the entire table name.
Also why your userA is sent is because, your query will return, lets say I am id '3',
msgstatusID msgID userID box read readTime
1 1 3 outbox 0 0
So from the joins, the user_message will return
msgID sentBy sentTo message sentTime
1 3 1 Hii B 1493306882
1 1 3 Hmm 1493306882
So you would have to use an if statement or turnary operation for the name and say:
if (sentBy == $_SESSION['userid'])
$name = sentTo;
else
$name = sentBy;
OR
$name = (sentBy == $_SESSION['userid']) ? sentTo : sentBy;
Basically to show the proper name of who you are talking to, you need to first check which column name to use
AS for problem 2, if you want to limit the amount then you need to add more condition. Maybe you only want outbox so you need to put AND box = 'outbox'
The below sql should help you out
SELECT
s.msgId
, m.message
, (
SELECT CONCAT(firstName, ' ', lastName)
FROM users
WHERE userId = CASE WHEN m.sentTo = s.userId
THEN m.sentBy
ELSE m.sentTo END
) AS chatWith
, m.sentTime
, s.read
FROM user_message_status s
LEFT JOIN user_message m USING (msgID)
WHERE s.userID='".$_SESSION['userid']."'
ORDER BY m.msgID DESC
Remove LEFT JOIN users u USING userID because it will be sub queried
s.msgID // used for deleteing the chat conversation
m.sentBy, m.sentTo, m.message, m.sentTime // all important data for your messages

Select from three tables

I have three tables where table_2 is the middle(connected) between table_1 and table_3
tables
table_id
...
...
table_rest
rest_id
table_id
...
rest
rest_id
...
...
And the query to select I use
SELECT m.table_id, table_name
FROM tables m
JOIN table_rest mr
ON m.table_id = mr.table_id
WHERE rest_id = '$rest_id'
What I need now is to join in this query another table reserv
id
...
status
To check if status is 0, 1,or 2 to not show me anything if there is no status this mean there is no record to show me. In other words this is resserved system where I show on screen few tables. If status is 0,1,2 thats mean the table is taken. If nothing is found for status this mean that there is no record for table and can be shown to user.
EDIT: Sample scenario
tables
table_id
1
2
3
4
5
rest
rest_id
1
2
table_rest
table_id | rest_id
1 2
2 2
3 2
4 2
5 2
So the query that is above will generate 5 tables for rest_id=2 and none for rest_id=1
So now I have another table
reserv
id | status
1 0
2 1
3 2
So in this table reserv currently are saved 3 tables. The idea is to show me other two whit id=4 and id=5 because they are not in table reserv and don't have any status.
Hope is a little bit more clear now.
You have to point from table reserv to which table is beign booked, let's call it reserv.table_id
SELECT m.table_id, table_name
FROM tables m
JOIN table_rest mr
ON m.table_id = mr.table_id
left join reserv
on reserv.table_id = m.id
WHERE rest_id = '$rest_id'
and reserv.status is null (*note)
*note use 'is' or 'is not' depending of your needs, as far as I read, first seems that you want !=, later that what you want is =
It's better if you provide sample data or sqlfiddle. Based on what I realize: Is this what you want:
select tables.table_id, rest.rest_id
from tables
left join table_rest on table_rest.table_id = tables.table_id
left join rest on rest.rest_id = table_rest.rest_id
where rest.rest_id = '$rest_id'
and tables.table_id not in (select id from reserv)

I have a customer table and want to find duplicate entries from submission table and show it in customer table in new field

I have a customer table and want to find duplicate entries from submission table and show it in customer table in new field (like in final table)
Customer table
id email
1 abc#gmail.com
3 xyz#gmail.com
4 ymz#gmail.com
Submission table
id Submitteduser
1 abc#gmail.com
2 abc#gmail.com
3 xyz#gmail.com
4 ymz#gmail.com
Final table
id email count
1 abc#gmail.com 2
3 xyz#gmail.com 1
4 ymz#gmail.com 1
help me to make this query
Try this query: Click Here For Fiddle
SELECT a.id, a.email, COUNT(b.Submitteduser) FROM Customer AS a
JOIN Submission AS b
ON a.email = b.Submitteduser
GROUP BY b.Submitteduser
you can use the following query
select Submission.id, Customer.email, count(Customer.*) from Customer inner join Submission on (email = Submitteduser) group by Submission.Submitteduser

PHP MySQL Query

Currently I have 3 MySQL tables, one filed with the users information, one with their course history and the last one filled with their reward history.
I am attempting to create a "rewards" program if you will, using these two databases and a PHP script. As far as the reward requirements, I have 2 arrays setup for the two types of rewards:
//Pen Reward with course A & B required
$pen=array("a","b")
//Cup Reward with course B & C required
$cup=array("b","c")
I can't figure out how to first query for all user IDs, then go through their history. If they match the requirements set above, then to update the reward table to 1 (to show that they received the award)
UsersDB
userid name
----------------
1 bill
2 john
3 steve
HistoryDB
userid courseid
------------------
1 a
1 b
2 b
3 a
3 c
RewardHistoryDB
userid pen cup
---------------------
1 0 0
2 0 0
3 0 0
Ideally it after the PHP script runs, it would update the RewardHistoryDB to reflect that user 1 received a pen, and user 3 received a cup.(the DB would look like this:)
RewardHistoryDB (after)
userid pen cup
---------------------
1 1 0
2 0 0
3 0 1
Here is the PHP code I am using right now (not complete):
$userid=array();
$i=0;
//Find All users
$result = mysqli_query($con,"SELECT userid FROM usersdb")
while ($row = mysqli_fetch_array($result)){
$universityid[$i]=$row['universityid'];
$i++;
}
//Find History
$courseid=array();
foreach ($userid as $userid1){
$result = mysqli_query($con,"SELECT courseid FROM historydb WHERE userid='".$userid1."'");
while ($row = mysqli_fetch_array($result)){
$courseid[]=$row;
}
}
//Update Reward DB
//Don't even know where to start...
Any help would be greatly appreciated.
If you have any questions, please let me know.
Thank you in advanced!
http://sqlfiddle.com/#!2/1a96b/1/0
You can do this just as queries and without doing any logic in PHP
update RewardHistoryDB
set Pen = 1
where UserID in (
select UserID
from HistoryDB
where CourseID in ('A','B')
group by UserID
having count(UserID)=2);
update RewardHistoryDB
set Cup = 1
where UserID in (
select UserID
from HistoryDB
where CourseID in ('B','C')
group by UserID
having count(UserID)=2);
Or you can even do it in one, large statement...
update RewardHistoryDB
left outer join (
select UserID as Pens_UserID
from HistoryDB
where CourseID in ('A','B')
group by UserID
having count(UserID)=2 ) as Pens
on RewardHistoryDB.UserID = Pens.Pens_UserID
left outer join (
select UserID as Cups_UserID
from HistoryDB
where CourseID in ('B','C')
group by UserID
having count(UserID)=2 ) as Cups
on RewardHistoryDB.UserID = Cups.Cups_UserID
set Pen = case when Pens.Pens_UserID is not null then 1 else 0 end,
Cup = case when Cups.Cups_UserID is not null then 1 else 0 end

Categories