2012-11-06 4 views
0

하루에 두 번 이상 실행해야하는 쿼리가 있습니다. 이 쿼리는 데이터베이스에서 다른 데이터베이스로 데이터를 가져 오는 것입니다.테이블에서 테이블로 데이터를 가져올 때 삽입, 업데이트, 삭제하는 방법은 무엇입니까?

목표 테이블 구조는 다음

Id Date  Department Location PersonId Starttime  EndTime  State 
1 2012-01-01  2   5  200  12:00:00.000 15:00:00.000 2 

애플리케이션은 또한 목표 테이블에 데이터를 삽입 할 수있다. 이 레코드가 다른 상태의 원본 (임시 테이블) 테이블에있는 경우에도 응용 프로그램에서 삽입 한 레코드가 업데이트되지 않을 수 있습니다.

가능한 한 솔루션을 만들었습니다. 내가 확인할 수 있도록 두 번째 상태로 목표 테이블에 새 열을 작성합니다.

Id Date  Department Location PersonId Starttime  EndTime  State StateSource 
1 2012-01-01  2   5  200  12:00:00.000 15:00:00.000 2  2 

일부 요구 사항 : 기록은 StateSource보다 응용 프로그램 추가

경우 NULL이됩니다. 이 레코드를 소스 테이블에서 다시 삭제하거나 업데이트하거나 삽입 할 수 없다는 것을 의미합니다.

레코드가 상태 값과 StateSource 값보다 다른 응용 프로그램에 의해 업데이트되는 경우. 이 경우이 레코드를 업데이트하지 않습니다.

소스 테이블과 대상 테이블의 상태가 같지 않고 대상 테이블의 값이 StateSource 인 경우 업데이트 할 예정입니다.

대상 테이블에 레코드가 없으면 레코드를 삽입합니다. 레코드가 이미 존재하는 경우 삽입하지 마십시오 (첫 번째 실행에서 응용 프로그램 또는 내 쿼리에 의해 추가 된 경우).

레코드가 내 소스 테이블 및 State StateSource에 없으면 대상에서 레코드를 삭제합니다.

이미 다음과 같은 쿼리가 있습니다. 3 문장을 만들기로했습니다.

--Delete Statement first 
Delete from t 
from TargetTable t LEFT JOIN SourceTable s ON t.Id=s.Id 
and t.Date=s.Date 
and t.departments=s.Department 
and t.PersonId=s.PersonId 
and t.State=t.StateSource 

--Just delete if a date is no more exists from the source table and this records is NOT 
--changed by the application (t.State=t.StateSource) 


--Update statement second 
Update t 
set t.State = s.State 
From Targettable t INNER JOIN SourceTable s ON t.Id=s.Id 
and t.Date=s.Date 
and t.departments=s.Department 
and t.PersonId=s.PersonId 

The problem here is: 
--when I have State 2 already in the targettable and in my sourcetable i have 
--another state then the state in the targettable changes. This would not be the case. 


--Insert Statement thirth 

insert into TargetTable (Id, Date, Department, Location, PersonId, Starttime, EndTime,State, StateSource) 
select Id, Date, Department, Location, PersonId, Starttime, EndTime,State, StateSource 
from SourceTable s 
WHERE Date not in (select Date 
        from TargetTable t 
        where t.id=s.id 
        and t.PersonId=s.PersonId 
        and t.date=s.date 
        and t.department=s.department)  

--I have no idea about how the insert should be because the application also can 
--insert records. When a record exists then no insert. What to do with the State? 

응용 프로그램에 의해 변경된 상태가 중요하다는 것을 기억하십시오.

누구나 원하는 결과를 얻을 수 있습니까?

+0

응용 프로그램이 삽입/업데이트되지 않은 모든 데이터를 삭제하는 중 ... 응용 프로그램이 삽입/업데이트 된 상태의 모든 변경 ... 누른 다음 삽입 모든 것은 응용 프로그램이 삽입/업데이트되지 않은 상태입니다. 귀하의 상태 필드는 그것이 언제 있었는지를 의미합니다. 업데이트 된? 업데이트 버전을 좋아하세요? – Frederic

답변

0

당신이 ... ... 이런 식으로 뭔가를 병합 문을 사용할 수 있습니다 내가 더 도움이

with target_T as (select * from UR_TARGET_TABLE 
        where statesource is not null) -- to dont change the data inserted from application... 
merge target_T as TARGET 
using UR_SOURCE_TABLE as SOURCE 
on SOURCE.id = TARGET.id -- id is unique? anyway, put your primary key here... 

when matched and TARGET.state = TARGET.statesource then --if inserted/updated from application, will not change data 
update set TARGET.state = SOURCE.state 
      ,TARGET.statesource = SOURCE.state --important update it together to be different from an application update 
     --, other collumns that you have to set... 

--should use another when matched then update if need to change something on inserted/updated from application data 


when not matched by TARGET then 
     insert (Id, Date, Department, Location, PersonId, Starttime, EndTime,State, StateSource) 
     values(SOURCE.Id, SOURCE.Date, SOURCE.Department, SOURCE.Location, SOURCE.PersonId, SOURCE.Starttime, SOURCE.EndTime,SOURCE.State, SOURCE.StateSource); 

당신이 당신의 테이블을 선언하고 일부 데이터를 삽입과 샘플을 설정하면 ... 실제로 작동하는 코드가 있습니다. ...

관련 문제