님께서 지금하고 있는 insert 방법이 지극히 정상적인 방법입니다. 특별한 이유가 없다면 그대로 사용하십시요.
다만 except로 잡아서 리턴 하기전에 tr1.Rollback 문장을 추가해야 합니다.
그리고, insert할 key가 이미 존재하는지를 확인하고 insert 할거면 unique 속성을 줄 이유가 없지 않습니까?
그러니 하시던 대로 하시는게 순리에 맞습니다.
브리오 님이 쓰신 글 :
: 안녕하세요. 아주 오랜만에 들어와서, 너무 기본적인 질문이 아닐지...
:
: Firebird 를 기반으로 웹 서버를 구축하고 있는데, 웹이다 보니 여러 사람이 동시에 접속할 수 있습니다. 아 웹서버는 Lazarus - Free Pascal 로 되어 있습니다.
:
: 질문은, 한 테이블의 Unique 로 정의된 field에 값을 넣고 싶은데, 기존에 있는 값을 입력하려 하면 당연히 안됩니다. 그래서, 지금은 일단 입력을 시도해 보고 안되면 except 에서 false 값을 return 하는 약간 무식한 방법을 사용하고 있습니다. 즉,
:
: function insertkey (key: string): boolean;
: begin
: tr1.starttransaction;
: try
: qr1.SQL.Text := 'insert into tablename (key) values (:key)';
: qr1.parambyname('key').AsString := key;
: qr1.execute;
: tr1.Commit;
: Result := true;
: except
: Result := False;
: end;
: end;
:
: 즉 이 함수에서 false 값을 return 받으면 새로운 값을 시도합니다. 이 방법으로, 일부러 기존에 있는 값을 입력 시도해 보면 문제가 없습니다.
:
: 그런데, 좀 무식해 보여서... 찾아보니 다음과 같이 Stored Procedure 나 execute block 을 쓰는 방법이 있네요.
:
: execute block (key varchar(40))
: as
: begin
: if (not exists(select key from tablename where key=:key)) /* 먼저 존재여부 체크하고 --> A */
: then
: insert into tablename(key) values (:key); /* 입력 --> B */
: end
:
: 이렇게 해당 key값을 갖는 record가 존재하는지 먼저 확인하고 입력을 합니다.
:
: 여기서 의문이 생기는데, 만약 A 단계에서는 나의 key 값이 없었는데 B를 실행하기 직전 다른 사람이 같은 key 값을 입력했을 가능성은 없는 건가요?
:
: firebird (나 또는 다른 Database)에서 하나의 stored procedure 가 실행되는 동안은 다른 것을 처리하지 않는다면 문제가 없고요.
: 그렇지 않고 중간에 값이 입력되어 있을 수 있다면 critical section 이나 그런 걸 사용해야 하는지
: 아니면 Database 에서 뭔가를 해 주면 되는지 등이 궁금합니다.
:
:
:
:
|