Solved

Query multiple tables (joins) for entries, but detecting missing entries

Posted on 2014-09-05
7
126 Views
Last Modified: 2014-09-05
I have a reporting system which our students are required to utilize.  I need to run a report off the database (which I developed) that links to an external database (our Student Information System).

My database doesn't use names, just student IDs.  I need to query the SIS for the student's first and last name.  Below is the query I am using -- which is working to give me all of the report entries and whether or not they were on-time or late.  What I am not getting are the missing entries.  We need to no if a student did not report at all for that week.  I feel like I'm close, but I'm not sure what I'm doing wrong.  I will include some sample data and the SQL query.

Query
WITH students (StudentID) AS
(
	SELECT n.soc_sec AS [StudentID]
	FROM [LINKEDSERVER].[SIS].[dbo].[name] n INNER JOIN [LINKEDSERVER].[SIS].[dbo].[nmcrs] c
		ON n.soc_sec = c.soc_sec
	WHERE c.course='REQU0007' AND c.enrollcode='EN' AND c.sch_yr='201415' AND c.semester='1'
),

reportstd (Report, ReportPeriod, LateOn) AS
(
	SELECT CONVERT(varchar(10),s.reportOpen,102) AS [Report],
		   CONVERT(varchar(10),s.reportBegin,102) + ' - ' + 
	       CONVERT(varchar(10),s.reportEnd,102) AS [ReportPeriod],
		   s.lateOn AS [LateOn]
	FROM reports s
	WHERE s.reportOpen BETWEEN '08/01/2014' AND GETDATE()
)

SELECT nm.soc_sec AS [StudentID],
	   nm.last_name AS [LastName],
	   nm.first_name AS [FirstName],
	   s.ReportPeriod,
	   s.Report,
	   [Status] = CASE
			WHEN r.submitted > s.LateOn THEN 'LATE'
			WHEN r.submitted < s.LateOn THEN 'ON TIME'
			WHEN r.submitted IS NULL THEN 'NO REPORT'
			END
FROM [LINKEDSERVER].[SIS].[dbo].[name] nm LEFT JOIN Reported r
	ON nm.soc_sec = r.student LEFT JOIN reportstd s
	ON r.csgTerm = s.Report
WHERE (r.student IN (SELECT StudentID FROM students) OR
	  r.student NOT IN (SELECT StudentID FROM students)) AND
	  ReportPeriod IS NOT NULL AND
	  Report IS NOT NULL
ORDER BY LastName, FirstName, s.Report

Open in new window


Sample Data
name.txt
reports.txt
reportstd.txt
students.txt
reported.txt
0
Comment
Question by:Shane Kahkola
  • 4
  • 3
7 Comments
 
LVL 10

Expert Comment

by:Ray
ID: 40306301
Your Inner Join in the 'with' section is eliminating those students who did not report at all.  Change it to a left join to get all student records.

This section MAY also be eliminating non reporters.
ReportPeriod IS NOT NULL AND
        Report IS NOT NULL


Indispensable tool for understanding joins . . .
http://www.codeproject.com/KB/database/Visual_SQL_Joins/Visual_SQL_JOINS_orig.jpg
0
 
LVL 10

Accepted Solution

by:
Ray earned 500 total points
ID: 40306308
This might be a silly question, but why are you doing this part (pasted below)?  It is effectively a non condition since it allows for all r.students whether they have a student ID or not.  If you are building this in some other application and need a 'placeholder' where you may or may not add 'and's, might I suggest replacing that piece with "Where 1=1"


WHERE (r.student IN (SELECT StudentID FROM students) OR
        r.student NOT IN (SELECT StudentID FROM students))
0
 
LVL 3

Author Comment

by:Shane Kahkola
ID: 40306314
Thank you, Ray, I will try your suggestions, and read the chart you posted.

The reason I did that last part was a desperation attempt to get all the records.  I really could not reiterate to you why I did it -- mainly because it doesn't make sense to me any more.
0
IT, Stop Being Called Into Every Meeting

Highfive is so simple that setting up every meeting room takes just minutes and every employee will be able to start or join a call from any room with ease. Never be called into a meeting just to get it started again. This is how video conferencing should work!

 
LVL 3

Author Comment

by:Shane Kahkola
ID: 40306595
I've requested that this question be closed as follows:

Accepted answer: 0 points for ccbbc_cs's comment #a40306314

for the following reason:

Ray, you were a God-send.

The chart and the questions led me in the right direction.  I finally did this, and got what I was looking for:

WITH students (StudentID,LastName,FirstName) AS
(
	SELECT n.soc_sec AS [StudentID],n.last_name AS [LastName],n.first_name AS [FirstName]
	FROM [LINKEDSERVER].[SIS].[dbo].[name] n INNER JOIN [LINKEDSERVER].[SIS].[dbo].[nmcrs] c
		ON n.soc_sec = c.soc_sec
	WHERE c.course='REQU0007' AND c.enrollcode='EN' AND c.sch_yr='201415' AND c.semester='1'
),

reportstd (Report, ReportPeriod, LateOn,ID) AS
(
	SELECT CONVERT(varchar(10),s.reportOpen,102) AS [Report],
		   CONVERT(varchar(10),s.reportBegin,102) + ' - ' + 
	       CONVERT(varchar(10),s.reportEnd,102) AS [ReportPeriod],
		   s.lateOn AS [LateOn],s.ID
	FROM reports s
	WHERE s.reportOpen BETWEEN '08/01/2014' AND GETDATE()
)

SELECT DISTINCT s.StudentID,
	   s.LastName,
	   s.FirstName,
	   [ReportPeriod] = CASE
				WHEN rs.ReportPeriod IS NULL THEN 'NEVER REPORTED'
				WHEN rs.ReportPeriod IS NOT NULL THEN rs.ReportPeriod
			     END,
	   [Report] = CASE
			WHEN rs.Report IS NULL THEN 'NEVER REPORTED'
			WHEN rs.Report IS NOT NULL THEN rs.Report
		       END,
	   rs.ID,
	   [Status] = CASE
			WHEN r.submitted > rs.LateOn THEN 'LATE'
			WHEN r.submitted < rs.LateOn THEN 'ON TIME'
			ELSE 'NO REPORT'
		      END
FROM reportstd rs LEFT JOIN Reported r
	ON rs.Report = r.csgTerm RIGHT JOIN students s 
	ON r.student = s.StudentID
ORDER BY LastName, FirstName, Report

Open in new window


This gave me the results I was looking to see.  Thanks again.
0
 
LVL 3

Author Closing Comment

by:Shane Kahkola
ID: 40306596
Ray, you were a God-send.

The chart and the questions led me in the right direction.  I finally did this, and got what I was looking for:

WITH students (StudentID,LastName,FirstName) AS
(
	SELECT n.soc_sec AS [StudentID],n.last_name AS [LastName],n.first_name AS [FirstName]
	FROM [LINKEDSERVER].[SIS].[dbo].[name] n INNER JOIN [LINKEDSERVER].[SIS].[dbo].[nmcrs] c
		ON n.soc_sec = c.soc_sec
	WHERE c.course='REQU0007' AND c.enrollcode='EN' AND c.sch_yr='201415' AND c.semester='1'
),

reportstd (Report, ReportPeriod, LateOn,ID) AS
(
	SELECT CONVERT(varchar(10),s.reportOpen,102) AS [Report],
		   CONVERT(varchar(10),s.reportBegin,102) + ' - ' + 
	       CONVERT(varchar(10),s.reportEnd,102) AS [ReportPeriod],
		   s.lateOn AS [LateOn],s.ID
	FROM reports s
	WHERE s.reportOpen BETWEEN '08/01/2014' AND GETDATE()
)

SELECT DISTINCT s.StudentID,
	   s.LastName,
	   s.FirstName,
	   [ReportPeriod] = CASE
				WHEN rs.ReportPeriod IS NULL THEN 'NEVER REPORTED'
				WHEN rs.ReportPeriod IS NOT NULL THEN rs.ReportPeriod
			     END,
	   [Report] = CASE
			WHEN rs.Report IS NULL THEN 'NEVER REPORTED'
			WHEN rs.Report IS NOT NULL THEN rs.Report
		       END,
	   rs.ID,
	   [Status] = CASE
			WHEN r.submitted > rs.LateOn THEN 'LATE'
			WHEN r.submitted < rs.LateOn THEN 'ON TIME'
			ELSE 'NO REPORT'
		      END
FROM reportstd rs LEFT JOIN Reported r
	ON rs.Report = r.csgTerm RIGHT JOIN students s 
	ON r.student = s.StudentID
ORDER BY LastName, FirstName, Report

Open in new window


This gave me the results I was looking to see.  Thanks again.
0
 
LVL 3

Author Comment

by:Shane Kahkola
ID: 40306603
I did something dumb here, but I don't know how to fix it.  I wanted to award you the points and I must have clicked on something wrong.
0
 
LVL 10

Expert Comment

by:Ray
ID: 40306819
Glad I could help in some way.
0

Featured Post

IT, Stop Being Called Into Every Meeting

Highfive is so simple that setting up every meeting room takes just minutes and every employee will be able to start or join a call from any room with ease. Never be called into a meeting just to get it started again. This is how video conferencing should work!

Join & Write a Comment

Suggested Solutions

SQL Server engine let you use a Windows account or a SQL Server account to connect to a SQL Server instance. This can be configured immediatly during the SQL Server installation or after in the Server Authentication section in the Server properties …
The Delta outage: 650 cancelled flights, more than 1200 delayed flights, thousands of frustrated customers, tens of millions of dollars in damages – plus untold reputational damage to one of the world’s most trusted airlines. All due to a catastroph…
Via a live example, show how to setup several different housekeeping processes for a SQL Server.
Using examples as well as descriptions, and references to Books Online, show the documentation available for datatypes, explain the available data types and show how data can be passed into and out of variables.

707 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

18 Experts available now in Live!

Get 1:1 Help Now