봉봉의 개인 블로그
2017-05-24-P 본문
데이터베이스 트랜잭션(Database Transaction)
트랜잭션이란
한마디로 동시에 처리 되어야 할 것을 말한다
즉 성공과 실패가 분명해야하며 한가지 행동뿐만아니라 그안에 모든 내용이 성공과 실패를 같이하여야한다.
예를 들자면 송금 서비스 같은 기능에서는 송금과 입금이 동시에 일어나야 하기 때문에
송금부분에서는 delete 든 update 든 값이 일어나야 하며 입금에서는 insert나 update가 동시에 일어나야한다는 소리가 되는것이다 송금은 되고 입금이 안되었을경우에는 금액을 처리하는데 문제가 있기때문에
트랜잭션을 이용해 어느 한부분이라도 실패하거나 예외가 나는 부분이 생기게 되면 동시에 처리가 되어야 할 부분들 모두가 처리가 되지 않아야 하기 때문에 rollback이 일어나게 된다.
트랜잭션에서
동시에 이루어져야 할 처리가 성공적인 상태를 Commit 이라고하며
비성공적인 상태를 rollback 이라 한다.
Unions
unions 는 유사성이 있는것을 조회할때 사용된다
예를들어 Customers안에 id와 old 안에 id 가있다고 유사성이 있으므로 조회할수 있는것이다.
*Union All 은 중복은 허용하는 union이다.
*INTERSERCT 차집합 union이라고 생각하면된다.
Alias
Alias는 별명같은 것이다. 예를들면
select e.id c.id from customers e inner join old c
여기서 테이블명 customers 와 old의 뒤에 붙어있는 e와 c 가 별칭 즉, alias 인것이다.
INDEX
INDEX는 RDBMS에서 검색속도를 높이기 위해 사용하는 하나의 기술입니다.
INDEX는 색인입니다. 해당 TABLE의 컬럼을 색인화 하여 검색시 해당 TABLE의 레코드를
full scan하는게 아니라 색인화 되어있는 INDEX파일을 검색하여 검색속도를 빠르게 한다
이런 INDEX는 TREE구조로 색인화 하고 RDBMS에서 사용하는 INDEX는 Balance Search Tree 를 사용합니다. 실제로는 RDBMS에서 사용되는 B-Tree는 B-Tree에서 파생된 B+Tree를 사용한다고 한다.
INDEX를 해당컬럼에 주게 되면 초기 TABLE 생성시 만들어진 MYD,MYI,FRM 3개의 파일중에서 MYI에 해당컬럼을 색인화 하여 저장합니다. 물론 INDEX를 사용 안할시에는 MYI파일은 비어있습니다.
그래서 INDEC를 해당 컬럼에 만들게 되면 해당컬럼을 따로 인덱싱하여 MYI파일에 입력합니다. 그래서 사용자가 SELECT쿼리로 INDEC가 사용하는 쿼리를 사용시 해당 TABLE을 검색하는것이 아니라 빠른 TREE로 정리해둔 MYI파일의 내용을 검색합니다 만약 INDEC를 사용하지 않은 SELECT쿼리라면 해당 TABLE full scan하여 모두 검색합니다.
이는 책의 뒷부분에 찾아보기와 같은 의미로 정리해둔 단어중에서 원하는 단어를 찾아서 페이지수를 보고 쉽게 찾을수 있는 개념과 같습니다. 만약 이 찾아보기 없다면 처음부터 끝까지 모든 페이지를 보고 찾아야 할것이다.
TRUNCATE
TRUNCATE 는 TABLE을 비울때 사용된다.
하지만 여기서 delete와의 차이점을 찾자면 delete는 롤백대상이 될수있다 하지만 Truncate는 롤백없이 지우는것이다.
Using VIEW
VIEW는 가상테이블이다 뷰는 블로그에도 적혀잇으니 찾아보면 된다
사용하는 이유는 보안과 속도를 위해서 사용하며 용도에 맞춰서 사용이 가능하다
HAVING
having 은 Where 절이라고 생각하면되는데 group 의 where 절이다.
예를들면 select address , count(address) c
from customers group by address having c>1; 이런식으로 쿼리문을 작성할수 있다.
Wildcard
wildcard 는 like 와 비슷하다고 생각하면된다.
Functions
function 은 함수라고 생각하면도니다 즉 메서드 같은 존재라고 생각하면된다.
그런데 여기서 프로시저라는 것도 함수같은 역활을 한다
그둘의 차이점은 function은 리턴값이 있고 프로시저는 리턴값이 없다.
*트랜잭션 과 delete 그리고 like*
트랜잭션에 대해 잠깐 코드를 통해서 예를 보여주자면 먼저
위 사진과 같이 java 파일들과 wep 파일들을 생성해줍니다.
그후 먼저 list 를 먼저 뽑아주기 위해서
CustomersLike_Eun.jsp 에서 아래와 같이 문장을 채워줍니다.
위와같이 만들어줍니다
설명을 조금하자면 먼저 15번줄은 없어도 되는 문장이다 설명을 하자면 16번줄에서 CustomerDao 타입으로 customerdao 를 선언하고 생성자 메서드를 통해서 생성된 객체의 주소값을 객체참조변수에 할당합니다.
그후 arraylist 타입으로 list를 선언하고 그안에 값을 null; 적어놓은다음 18번줄에서
객체참조변수안에 할당된 주소값을 찾아가서 selectCustomerListAll 메서드를 호출합니다.
호출하고 받은 리턴도니 주소값을 list안에 할당합니다 그후 for문을 통해 Customer 타입으로 객체참조변수 c를 선언하고 list안에 배열의 숫자만큼 데이터를 출력합니다.
이때 41번줄과 같이 삭제 버튼을 만들어줍니다 삭제시 get 방식으로 id의 값을 넘겨줍니다.
그렇다면 customerdao 주소값안에 있는 selectCustomerListAll 메서드에 대해서 알아보자
위사진과 같이 작성되어있다 selectCustomerListAll 안은 위 사진과 같이 되어있다
쿼리문을 준비하고 쿼리를 실행한후 그 결과값을 get해서 Customer 타입생성된 객체 안에 값들을 set하고 주소값을 ArrayList<Customer>타입으로 선언된 returnList 안에 주소값을 추가해주는걸 rs.next의 값이 false가 나올때까지 반복하고 주소값들을 추가해서 담은 returnList 를 호출한곳으로 리턴해 화면에서 값들을 뿌려줍니다.
그후 다시 화면으로 돌아와 만약 삭제버튼을 눌럿을때 삭제되는 과정을 만들어 보겠다.
여기서 삭제를 그냥 만들지 않고 삭제하기전에 미리만들어놓은 oldid 테이블에 id의 값을 insert하고
delete문을 실행해 담고난다음 삭제하도록 만드는데 insert와 delete가 동시에 이루어져야 한다 만약 어느 한곳에서라도 문제가 발생되면 insert는 되었는데 삭제가 안되었을수도잇고 delete는 되엇는데 insert가 안되는 불상사가 벌어질수 있다. 즉 트랜잭션을 이용해 이 두가지의 행동을 같이 성공하던지 실패하던지를 만들어 줘야 한다는 말이다.
그러면 삭제 버튼을 눌럿을때 이동하는 jsp 파일 deleteCustomer.jsp안을 살펴보면
위 사진과 같이 코드가 들어가있다 설명을 조금하자면 먼저
17번문에서는 request.getParameter 로 받은 값은 무조건 String 타입 즉 문자 차입으로 넘어오고 우리가 사용해야할 id 의 값은 int 타입이기 때문에 Integer.parseInt 를 통해서 int 타입의 id 의 값안에 넣어주게 되면 된다
그후 CustomerService 타입으로 선언된 customerservice 객체참조변수안에 CustomerService 생성자메서드를 통해 생성된 객체의 주소값을 객체참조변수안에 할당합니다
그후 customerservice 안에 할당된 주소값을 찾아가서 customeroldidservice를 호출하게 되는데 이때 매개변수의 값으로 id의 값을 받아 메서드가 실행됩니다.
customerservice 안에 customeroldidservice를 살펴보면
위 사진과 같이 코드가 작성되어 있다
설명을 하자면 먼저 이 CustomerService 라는 클래스는 service의 역활을하고
잠깐 용어 설명을 하고가자면
먼저 모델1방식과 모델2방식이있다
모델1은 jsp와 service 와 DAO , DTO로 구성되어있다
먼저 화면 jsp에서 받아온 데이터를 java 쪽에서 처리하기전에 먼저 service로 넘어가고 service에서 DAO를 호출하고 DAO에서는 DTO를 이용해 데이터를 연산하고 리턴받은 값을 service로 보낸후 service에서는 다시 호출한곳 화면등으로 가서 값을 뿌려주게 되는것이다. 즉 jsp나 service에서 로직을 처리한다는것이다.
반면에 모델2는 처리를 jsp가 당담하는 모델 1방식과는 달리 jsp페이지와 서블릿,그리고 로직을 위한클래스가 나뉘어 져서 브라우저에 요청하게 되는것이다.
간단하게 말하자면 jsp는 화면으로써의 역활만하고 요청결과를 보여줄 흐름에대한 제어는 컨트롤러인 서블릿에서 담당하게된다 즉 서블릿에서 service계층을 관리하고 그 서비스에서는 DAO를 관리한다고 보면 편하고 그 DAO에서는 DTO를 가지고 일을한다고 보면되는것이다.
위사진과 같은 코드는 service 계층의 코드를 먼저 적고 try catch 문에서와 같이 DAO를 호출해 DAO를 관리하고 DAO가 연산한 리턴값을 받아서 처리를 하게 되는것이다.
이제 살펴보면 먼저 매개변수값으로 id의 값을 받고 자기 안에있는 CustomerDao 와 OldidDao 타입으로 선언된 객체참조변수안에 16,17번에서 각각 생성된 객체의 주소값을 각각 할당해줍니다.
그후 18번문에서 드라이버 로딩과 db를 연결해줍니다. db 연결과 관련된것은 따로 DBservice 안에 메서드화 시켜 따로 만들어줍니다
그후 try catch 문에서 conn.setAutoCommit을 통해 메서드 가 성공시 Commit이 일어나지 않게끔 Commit의 값을 false로 적어줘서 자동적으로 Commit이 일어나지 않게 만들어줍니다 만약 이문을 적지 않으면 insert 따로 deleteCustomer 이 따로 돌아간다고 봐도 무방하다. 그후 oldiddao 주소값안에 insert 메서드를 통해 oldid table안에 값을 insert 해주고 customerdao 주소값안에 deleteCustomer 메서드를 통해서 삭제하려는 값을 지워준후 아까 성공시 Commit(메서드가 성공햇다라는 뜻이다)이 일어나지 않게끔 만들어 놓았던 conn.setAutoCommit(false); 이걸 다시 23번문에서 Commit(); 통해서 다시 Commit을 활성화 하여 insert와 delete가 모두 성공햇을때만 Commit이 일어나게 만들어줍니다
만약 둘중하나라도 실패했으면 이 모든 과정이 이루어 져서는 안되기 때문에 catch 문에서 만약 예외등 문제가 발생하면 conn.rollback 을 통해서 이 과정 자체를 없었던 걸로 만들어버리는것이다.
즉 try catch 문이 실행되기 전상태로 다시 만들어준후 finally 를 통해서 실패하든 성공하든 conn의 값을 다시 반환 받도록 만들어줍니다.
그리고 두 메서드는 같은 conn의 값을 사용하여야 하기 때문에 conn 자체를 매개변수값으로 받아야한다.
여기서 필요한 메서드인 oldiddao 주소값안에 insert 부터 살펴 보겠다.
위 사진과 같이 코드가 적혀있다. 쿼리문을 작성해주고 매개변수 값으로 받은 conn 을통해서 쿼리문을 준비하고 받아온 id 의 값을 set 메서드를 통해 쿼리실행을 위한 준비를 한후 쿼리를 실행해줍니다.
그다음 또 필요한 메서드인 customerdao 주소값 안에 deleteCustomer 를 살펴 보면
위 코드와 같이 적혀있다
설명을 하자면 매개변수값으로 받아온 conn의 값을 통해 쿼리문을 준비하고 받아온 id 의 값을통해 set하고 준비한후에 쿼리를 실행하게 됩니다.
insert 와 deleteCustomer 모두 성공하게 되면 commit되게 되어 insert와 delete가 모두 성공하게 되어 oldid table 에는 값이 입력되고 customers table 안에는 값이 delete 되게 됩니다.
만약 둘중하나라도 예외등 문제가 발생하면 conn의 값을 rollback하여 처리되기 전으로 돌려버립니다.
'학원에서 배운것들 > TEA - P' 카테고리의 다른 글
2017-05-26-P (0) | 2017.05.26 |
---|---|
2017-05-25-P (0) | 2017.05.25 |
2017-05-22-P (0) | 2017.05.22 |
2017-05-19-P (0) | 2017.05.19 |
2017-05-18-P (0) | 2017.05.18 |