2011-11-02 4 views
2

저는 기존 Oracle 데이터베이스를 사용하는 .Net 웹 개발자입니다. 과거에는 nHibernate와 같은 orm 도구로 작업했지만 여기서는 모든 데이터베이스 통신이 저장 프로 시저를 통해 수행되어야합니다. dba는 최종 사용자의 username/domain/ip를 포함하여 우리가 호출하는 모든 절차에 많은 관리 정보를 전달하라고 요청합니다. 그런 다음이 데이터는 프로 시저가 호출 될 때마다 사용 정보를 기록하는 다른 저장 프로 시저를 호출하는 데 사용됩니다.Oracle 저장 프로 시저 벤치마킹

저는 오라클이나 Pl/Sql에 능통하지 않으며 가능할 때마다 우수 사례를 준수하는 깨끗한 방식으로 .Net 코드를 작성하려고합니다. 추가 데이터를 모든 절차에 전달하는이 프로세스는 .Net과 Oracle 모두에서 지저분하고 지루합니다.

누구나 모든 오버 헤드없이 dba의 목표를 달성하는 더 좋은 방법을 알고 있습니까? 아니면 익숙해 져야하는 일을하는 표준 방법일까요?

+0

확실히 표준이 아니며 확실히 수행하지 않는 것이 좋습니다. 어떤 종류의 '추가'데이터 (예 : 사용자 이름 등)를 전달해야합니까? – Icarus

+0

예, 사용자 이름, 도메인, IP 주소를 전달해야합니다. – zaq

답변

3

모든 저장 프로 시저 호출에 추가 매개 변수를 전달하는 대신 컨텍스트를 사용합니다. 컨텍스트는 저장 프로 시저가 모두 참조 할 수있는 임의의 세션 수준 상태 데이터를 저장할 수있는 편리한 위치입니다.

예를 들어, 내 응용 프로그램에 대해 컨텍스트 MYAPP_CTX을 만들고 컨텍스트에서 원하는 모든 값을 설정할 수있는 간단한 패키지를 만들 수 있습니다.

SQL> create context myapp_ctx using ctx_pkg; 

Context created. 

SQL> create package ctx_pkg 
    2 as 
    3 procedure set_value(p_key in varchar2, p_value in varchar2); 
    4 end; 
    5/

Package created. 

SQL> create package body ctx_pkg 
    2 as 
    3 procedure set_value(p_key in varchar2, p_value in varchar2) 
    4 as 
    5 begin 
    6  dbms_session.set_context('MYAPP_CTX', p_key, p_value); 
    7 end; 
    8 end; 
    9/

Package body created. 

응용 프로그램이 연결 풀에서 연결을 가져 오면 모든 컨텍스트 정보를 한 번 설정하면됩니다.

SQL> begin 
    2 ctx_pkg.set_value('USERNAME', 'JCAVE'); 
    3 ctx_pkg.set_value('IP_ADDRESS', '192.168.17.34'); 
    4 end; 
    5/

PL/SQL procedure successfully completed. 

동일한 세션에서 후속 호출 및 쿼리는 컨텍스트에 저장된 값을 요청할 수 있습니다.

SQL> select sys_context('MYAPP_CTX', 'USERNAME') 
    2 from dual; 

SYS_CONTEXT('MYAPP_CTX','USERNAME') 
-------------------------------------------------------------------------------- 
JCAVE 

현실적으로, 당신은 거의 확실하게 연결이 문맥을 허용하는 실수 방지하기 위해 연결 풀에 반환 될 때 맥락에서 설정 한 값이 무엇이든지 취소 dbms_session.clear_context('MYAPP_CTX')라는 패키지에 clear_context 절차를 추가 할 것 한 세션의 정보가 다른 세션으로 유출 될 수 있습니다. 또한 'USERNAME'을 여러 곳으로 하드 코딩하지 않고 공통 키 (사용자 이름, IP 주소 등)를 설정하고 가져 오는 별도의 절차로 패키지를 디자인 할 수 있습니다. 단순화를 위해 하나의 일반 set_value 메서드를 사용했습니다.

+0

내가 누락되었을 수 있지만 여러 사용자가 동시에 세션에 액세스하는 경우 잠재적 인 동시성 문제가 발생할 수 있습니다. 예를 들어 두 번째 사용자 세션이 username/ip를 설정하고 첫 번째 사용자 세션이 사용자 이름을 묻는 저장 프로 시저를 호출하면 어떻게됩니까? 두 번째 세션에서 설정 한 사용자 이름을 반환하지 않습니까? – zaq

+1

@zaq - 컨텍스트는 (기본적으로) 데이터베이스 세션의 로컬입니다. 한 번에 한 명의 사용자 만 데이터베이스 세션을 사용할 수 있습니다 (연결 풀에서 연결을 검색 할 때 여러 중간 계층 세션이 데이터베이스 세션을 공유 할 수도 있음). 그렇기 때문에 일반적으로 연결 풀에 연결이 반환 될 때, 연결 풀에서 연결이 해제 될 때 또는 둘 모두에서 컨텍스트를 지울 수 있습니다. 두 개의 데이터베이스 세션은 각각의 컨텍스트에서 데이터의 개별 복사본을 가지므로 한 세션은 다른 세션 컨텍스트의 정보를 볼 수 없습니다. –

+0

감사합니다. – zaq

관련 문제