sql: ODBC Reserved Keywords - mysql

I have a column named level in my mysql database.
I am trying to write an sql statment and one of the parameters is level of course. But I get an error. I know it's because I am using a protected word so how can I still use it in my statement. Do I put it inside commas or something?

From the comments
1052 - Column 'level' in where clause is ambiguous
The above error message is telling that more than one table has column named level and so you have to prefix level column with table alias of the table whose column level you want to compare in WHERE clause. In below query I am assuming you want schools table level column so use it like this s.level
SELECT u.ck_id,u.firstname, u.lastname, sc.class_description,
s.name, GROUP_CONCAT(correct)
FROM game_statistics gs
INNER JOIN users1 u ON u.id = gs.user_id
INNER JOIN school_classes sc ON sc.id = u.class_id
INNER JOIN schools s ON s.id = sc.school_id
WHERE game_type = 'exammultiple' AND gs.created_at >= '2018-03-01'
AND time >='40' AND s.`level` = '6'
GROUP BY user_id
ORDER By name ASC, class_description ASC
You can change to correct table alias as intended by you.

Related

Why am I getting a syntax error in mysql?

SELECT ID, Name
FROM Members
WHERE ID IN
(SELECT Member ID
FROM Team Member
WHERE Team ID IN
(SELECT ID
FROM Teams
WHERE Year = 2012 AND Country = 'Phillipines'))
When I input this query into phpmyadmin, I get error #1064 saying I do not have the correct syntax. How can resolve this?
The immediate error appears to be WHERE Team ID IN ... which should actually be WHERE TeamID IN .... There are also other similar errors. But, we can try rewriting your query using joins, so that it is more readable and maintainable:
SELECT m.ID, m.Name
FROM Members m
INNER JOIN TeamMember tm
ON m.ID = tm.MemberID
INNER JOIN Teams t
ON tm.TeamID = t.ID
WHERE
t.Year = 2012 AND t.Country = 'Phillipines';
In general, identifiers in SQL have to be a single word without any whitespace. If Team ID is actually a column name, then you would have to refer to it in MySQL using backticks. But, you should avoid doing this.
Your table Team Member and its columns Member ID and Team ID maybe mispelled.
I think you are using wrong variable name (Member ID) it should not have space in between Member and Id. in the same way (Team Member), (Team ID).
Please make sure you use the right name for column name and table name.
You can try below using join
SELECT a.ID, a.Name
FROM Members a inner join Team b on a.ID=b.MemberID
inner join Teams c on b.TeamID=c.ID
where c.Year = 2012 AND c.Country = 'Phillipines'

ID missing from one table, include it in the results anyway

In my mySQL database I have two tables called job_details and job_actions. In the job_details table, if I get the Detail_ID for Job_ID 41230, then I get five results. For example:
select Detail_ID from job_details where Job_ID = '41230';
What I want to do is use the same Job_ID to get the Percent_Complete for each Detail_ID from the job_actions table. For example, this yields only 4 records because not all of the Detail_IDs appear in this table:
select Detail_ID, Percent_Complete from job_actions where Job_ID = '41230';
I get the same four records when I try to join both tables:
select
details.Detail_ID,
actions.Percent_Complete
from
job_details details,
job_actions actions
where
details.Job_ID = '41230' and
details.Job_ID = actions.Job_ID and
details.Detail_ID = actions.Detail_ID;
I would like my output to include EVERY Detail_ID found in the job_details table, even if it is not found in the job_actions table. For example:
I know how to find the Detail_ID that is missing from the job_actions table, but not how to include it in the results. For example:
select details.Detail_ID from job_details details
left join job_actions actions using (Detail_ID)
where actions.Detail_ID IS NULL and details.Job_ID = '41230';
How can I include the Detail_ID 87679 in the results even though it is missing from the job_actions table?
Never use commas in the FROM clause. Always use proper, explicit, standard JOIN syntax.
You simply want a LEFT JOIN:
select details.Detail_ID, actions.Percent_Complete
from job_details details left join
job_actions actions
on details.Job_ID = actions.Job_ID and
details.Detail_ID = actions.Detail_ID
where details.Job_ID = 41230; -- I assume Job_ID is a number so the single quotes are not necessary
Since, you have wrote the syntax of joins but with older style with where clause that could turn into actually inner join or equi join.
So, use proper explicit join syntax with type of left join
select jd.Detail_ID, ja.Percent_Complete
from job_details jd left join job_actions ja on
ja.Job_ID = jd.Job_ID and
ja.Detail_ID = jd.Detail_ID
where jd.Job_ID = '41230';
You could also use subquery instead since you are looking for all Detail_ID from job_details table
select Detail_ID,
(select Percent_Complete from job_actions
where Job_ID = jd.Job_ID and
Detail_ID = jd.Detail_ID) as Percent_Complete -- Use limit with order by clause in case one or more Percent found.
from job_details jd
where Job_ID = '41230';
I suspect, if you have Job_ID as type of numeric then you don't need to use of quotes just use value (i.e. 41230)

#1052 - Column 'status' in field list is ambiguous

SELECT
repeats.id,user_id,deposit_id,repeat_time,made_time,rebeat,status,created_at,updated_at
FROM repeats
INNER JOIN users ON users.id = repeats.user_id
I am trying to merge two tables; users and repeats, but it is giving following error.
Error
SQL query: Documentation
SELECT repeats.id
,user_id
,deposit_id
,repeat_time
,made_time
,rebeat
,status
,created_at
,updated_at
FROM repeats
INNER JOIN users
ON users.id = repeats.id
LIMIT 0, 25
MySQL said: Documentation
#1052 - Column 'status' in field list is ambiguous
Both your repeats and users tables seem to have a status column. You need to fully qualify the column in your query. E.g.:
SELECT repeats.id,
user_id,
deposit_id,
repeat_time,
made_time,
rebeat,
repeats.status, -- Or users.status, depending on what you need
created_at,
updated_at
FROM repeats
INNER JOIN users ON users.id = repeats.user_id
Whenever you have more than one table in a query, you should also qualify the column names. Another good practice is to use table aliases that are abbreviations for the table names.
I don't know what your data looks like, but the query would be something like:
SELECT r.id, r.user_id, r.deposit_id, r.repeat_time, r.made_time, r.rebeat,
u.status, u.created_at, u.updated_at
FROM repeats r INNER JOIN
users u
ON u.id = r.user_id;
This is just a guess. You have to correctly qualify the names.

My SQL query is returning results but they are repeated ~50 times. I don't understand why

The query I'm using calls on a few tables in the database and works fine. However, when I add line 10 to the mix it returns 50 or more repeated results. I'm still somewhat new to SQL and Sequel Pro so I'm sure the solution isn't too complicated but I am truly stumped right now.
Here is the code:
SELECT c.first_name, c.last_name, ca.company, ca.city, ca.state, ct.certificate_number, ct.certificate_date
FROM customer c, customer_type ctype, cust_address ca, certification ct, cust_prof_cert cp
WHERE ca.id_customer = c.id_customer LIKE cp.prof_cert_id_prof_cert
AND c.customer_type_id_customer_type = ctype.id_customer_type
AND ct.customer_id_customer = c.id_customer
AND ca.id_customer = c.id_customer
AND ctype.customer_type IN('CIRA','CIRA, CDBV')
AND ct.course_type_id_course_type = 1
AND ct.certificate_number IS NOT NULL
AND cp.prof_cert_id_prof_cert = "1"
ORDER BY ct.certificate_number ASC, c.last_name ASC;
Thank you for your time.
By Doing your SQL like that you are not relating the data, just selecting it. I would recommend changing your SQL to use JOINS.
SELECT Orders.OrderID, Customers.CustomerName, Orders.OrderDate
FROM Orders
INNER JOIN Customers
ON Orders.CustomerID=Customers.CustomerID;
Here is an article that might be able to help you a bit: w3schools, Joins
Here's your query using the SQL92 syntax for joins. You should use this syntax instead of the SQL89 "comma-style" joins.
SELECT c.first_name, c.last_name, ca.company, ca.city, ca.state,
ct.certificate_number, ct.certificate_date
FROM customer AS c
INNER JOIN customer_type AS ctype ON c.customer_type_id_customer_type = ctype.id_customer_type
INNER JOIN cust_address AS ca ON ca.id_customer = c.id_customer
INNER JOIN certification AS ct ON ct.customer_id_customer = c.id_customer
INNER JOIN cust_prof_cert AS cp -- what's this join condition?
WHERE ca.id_customer = c.id_customer LIKE cp.prof_cert_id_prof_cert
AND ctype.customer_type IN('CIRA','CIRA, CDBV')
AND ct.course_type_id_course_type = 1
AND ct.certificate_number IS NOT NULL
AND cp.prof_cert_id_prof_cert = '1'
ORDER BY ct.certificate_number ASC, c.last_name ASC;
A few weird things I notice in this query:
The first term in the WHERE clause is strange. You should know that LIKE has higher precedence than = so this might not be doing what you think it's doing. It's as if you wrote
WHERE ca.id_customer = (c.id_customer LIKE cp.prof_cert_id_prof_cert)
Which means evaluate the LIKE and produce a 0 or a 1 to represent the boolean condition. Then look for a ca.id_customer matching that 0 or 1.
Given that strange term, I can find no other join condition for the cp table. The default join if you give no restriction for it is that every row matches every row in the joined tables. So if you have 50 rows where cp.prof_cert_id_prof_cert = 1, then it will effectively multiply the results from the rest of the joined tables by 50.
This is called a Cartesian product, or in MySQL parlance it's counted in SHOW STATUS as a Full join.
ctype.customer_type IN('CIRA','CIRA, CDBV') You have quoted the second and third strings together. Basically, this means you are trying to match the column against two strings, one of which happens to contain a comma.
You probably meant to write ctype.customer_type IN('CIRA','CIRA','CDBV') so the column may match any of these three values.
I would suggest not querying multiple tables in your FROM clause, I believe this is the cause of your duplicate rows. If you separate out the tables into separate inner or left joins, (whichever you need) you should be able to match which ever keys in each table manually, instead of having SQL attempt to automatically do this.

Order of WHERE clause is affecting result

I have some strange problem with one select.
Is it possible that the order in WHERE clause can influence the result?
Here is my select:
select u.userName, u.fullName, g.uuid as groupUuid, g.name as `group`,
m.number as module, count(distinct b.uuid) as buildCount, max(b.datetime),
count(distinct e.buildId) as errorBuildCount, e.id as errorId
from User u
inner join GROUP_USER GU on GU.user_id = u.id
inner join `Group` g on g.id = GU.group_id
inner join Course c on c.id = g.courseId
left outer join Build b on b.userId = u.id
left outer join Module m on m.id = b.moduleId
left outer join Error e on e.buildId = b.id
where c.uuid = 'HMUUcabR1S4GRTIwt3wWxzCO' and g.uuid = 'abcdefghijklmnopqrstuvwz'
group by u.userName,m.number,c.uuid, g.uuid
order by g.id asc, u.fullName asc, m.number asc
this will reproduce this result:
http://dl.dropbox.com/u/4892450/sqlSelectProblem/select1.PNG
When I use this condition:
where g.uuid = 'abcdefghijklmnopqrstuvwz' and c.uuid = 'HMUUcabR1S4GRTIwt3wWxzCO'
(different order) I get a different result (see errorId column):
http://dl.dropbox.com/u/4892450/sqlSelectProblem/select2.PNG
Could you please help me? Is the whole select wrong, or can it be a mysql bug?
The only difference between the results is an errorId column. Ungrouped and unaggregated columns are not allowed by sql standard (sql-92 standard, check out the link) and will not even run in most db engines. So, engine's behavior in this situation is not specified. Accoding to docs (thanks to Marcus Adams):
MySQL extends the use of GROUP BY so that the select list can refer to nonaggregated columns not named in the GROUP BY clause. This means that the preceding query is legal in MySQL. You can use this feature to get better performance by avoiding unnecessary column sorting and grouping. However, this is useful primarily when all values in each nonaggregated column not named in the GROUP BY are the same for each group. The server is free to choose any value from each group, so unless they are the same, the values chosen are indeterminate.
You can get errorId as an aggregate value:
MAX(e.id) as errorId
or include it in GROUP BY list:
group by u.userName,m.number,c.uuid, g.uuid,e.Id
Then your query results should be stable.
Further reading:
Why does MySQL add a feature that conflicts with SQL standards? - detailed explanation of differences between sql standard and mysql implementation. (Thanks to GarethD)
You've got two different JOIN trees in your code, essentially:
user
/ \
group_user build
/ \
group module
| |
course error
such a construct leads to undefined results, especially if the results of the joins in one branch has a different number of matching records than in the other branch. MySQL has to try and fill in the missing bits, and guesses. Changing the order of your WHERE clause can and WILL change the full results because you're changing the way mysql does its guesses.
Group by all columns before aggregation. Best Practices...IN MOST CASES. and could very possibly be distorting your answers...