You can do the basic comparison as:
select name, country,
(case when sum(which = 'src') > 0 and sum(which = 'tgt') then 'DROPPED'
when sum(which = 'src') = 0 and sum(which = 'tgt') then 'NEW'
end) as OP
from ((select 'src' as which, name, country
from tableA
) union all
(select 'tgt', name, country
from tableB
)
) ab
group by name, country;
But that doesn't give you column-by-column comparisons. That is a bit more difficult. Let me assume that Name
is unique, so it can be used as a key. The following does the comparison, but produces one row per name:
select name,
(case when src.country is null then dest.country
when tgt.country is null then tgt.country
when src.country = tgt.country then dest.country
else (src.country, '-->', tgt.country)
end) as country,
(case when src.country is null then 'new'
when tgt.country is null then 'dropped'
when src.country = tgt.country then 'same'
else 'changed'
end) as country,
from (select name from TableA union select name from TableB
) names left outer join
TableA src
on names.name = src.name left outer join
TableB tgt
on names.name = tgt.name;
Getting multiple rows for each name when the value in a column changes seems more difficult, although it too would be possible.