I have 2 databases that have the same structure, but different data. Both are SQL 2005.
I am trying to find which of the Persons in Database A, exist in Database B. My best opportunity for match is to match on FirstName and LastName.
I only want to bring back a list of:
DatabaseA.Person DatabaseB.Person
Where: 1. I want all records from DatabaseA, even if there is not a match in Database B. 2. I only want records from DatabaseB where the FirstName/LastName match only one record in DatabaseB.
I have written a query, where I group by, but since I need to see more data than FirstName and LastName, I cannot bring it back without grouping it - which gives me many duplicates. What kind of query should I be using? Do I need to use a cursor?
Here is my query now, which sort of works - except I'm getting results for duplicates in DatabaseB and all I want to know about Database B is when FirstName/LastName matches to one distinct record and no others. My objective is to get a list of people that I know are the same person in 2 databases so that I can build a dictionary list of department code mappings between employees.
select
count(DatabaseAEmployee.id) as matchcount
, DatabaseAPerson.id as DatabaseAPersonid
, DatabaseAEmployee.DeptCode DatabaseADeptCode
, DatabaseAPerson.firstname as DatabaseAfirst
, DatabaseAPerson.lastname as DatabaseAlast
, DatabaseBPerson.id as DatabaseBPersonid
, DatabaseBEmployee.DeptCode as DatabaseBDeptCode
, DatabaseBPerson.firstname as DatabaseBfirst
, DatabaseBPerson.lastname as DatabaseBlast
, DatabaseAPerson.ssn as DatabaseAssn
, DatabaseBPerson.ssn as DatabaseBssn
, DatabaseAPerson.dateofbirth as DatabaseAdob
, DatabaseBPerson.dateofbirth as DatabaseBdob
FROM [DatabaseA].[dbo].Employee DatabaseAEmployee
LEFT OUTER JOIN [DatabaseA].[dbo].Person DatabaseAPerson
ON DatabaseAPerson.id = DatabaseAEmployee.id
LEFT OUTER JOIN [DatabaseB].[dbo].Person DatabaseBPerson
ON
DatabaseAPerson.firstname = DatabaseBPerson.firstname
AND
DatabaseAPerson.lastname = DatabaseBPerson.lastname
LEFT OUTER JOIN [DatabaseB].[dbo].Employee DatabaseBEmployee
on DatabaseBEmployee.id = DatabaseBPerson.id
group by
DatabaseAPerson.firstname
, DatabaseAPerson.lastname
, DatabaseAPerson.id
, DatabaseAEmployee.DeptCode
, DatabaseBPerson.id
, DatabaseBEmployee.DeptCode
, DatabaseBPerson.firstname
, DatabaseBPerson.lastname
, DatabaseBPerson.ssn
, DatabaseAPerson.ssn
, DatabaseBPerson.dateofbirth
, DatabaseAPerson.dateofbirth
Here's what I'm trying now, but I'm getting duplicates on the left side:
with UniqueMatchedPersons (Id, FirstName, LastName)
as (
select
p2.ID, p2.FirstName, p2.LastName
from
[DatabaseA].[dbo].[Employee] p1
INNER JOIN [DatabaseA].[dbo].[Person] p2 on p1.id = p2.id
inner join [DatabaseB].[dbo].[Person] p3
on p2.FirstName = p3.FirstName and p2.LastName = p3.LastName
INNER JOIN [DatabaseB].[dbo].[Employee] p4
on p3.id = p4.id
group by p2.ID, p2.FirstName, p2.LastName
having count(p2.ID) = 1
)
select p1.*, p2.*
from DatabaseA.dbo.Person p1
inner join UniqueMatchedPersons on p1.ID = UniqueMatchedPersons.ID
left outer join DatabaseB.dbo.Person p2
on p1.FirstName = p2.FirstName and p1.LastName = p2.LastName