본문 바로가기
web project

제품&판매 관리 시스템 : 부서별로 상충하는 요구사항 반영 (1)

by kuah_ 2022. 10. 13.

 

 

 

[ 운영상 이슈 1 ] 제품&판매 관리 시스템 : 삭제, 수정 히스토리 테이블 생성 및 관리

[ 운영상 이슈 2 ] 제품&판매 관리 시스템 : 히스토리 테이블에 trigger 생성

[ 운영상 이슈 3 ] 

2022.10.06 - 1

<요구사항>

- sales 테이블의 row를 최대한 줄이길 바라는 부서가 있고, 모두 보존하길 원하는 부서가 있다.

- 두 부서 모두를 만족시킬 수 있는 솔루션에 대한 토론

- 사전에 외래키를 설정하는 방법을 학습했으므로 이를 활용해도 됨.

 

 

<1조 회의결과 (학습자 A, B, C)>

- A : 상황에 따라 다르게 대응하려면 메뉴에서 선택하게
                  제품 삭제 시 판매 기록까지 삭제할 것인지 선택지를 제공해야한다.

- B : sales_history를 생성해서 삭제된 거래 내역도 복구할 수 있도록 한다.

- C : 부서마다 다른 권한을 부여하여 전체 내역 조회를 원하는 부서의 경우 sales_history를 조회할 수 있도록 한다.

 

* 종합 의견 : 백업 테이블(sales_history)을 생성하여 해당 정보를 조회 및 복구하는 옵션을 부여하는 방식을 제안.

 

 

<2조 회의결과 (학습자 D, E, 나)>

- 나 : 정리하면 외래키 지정 여부, cascade 옵션 지정 여부를 결정해야 될 것 같다.

- E : 즉, 아래와 같다.

                   외래키 o -> 제품삭제 x, 판매삭제x
                   외래키 o -> 제품삭제 o, 판매삭제o (cascade)
                   외래키 x -> 제품삭제 o, 판매삭제x

                   외래키 x -> 제품삭제 x, 판매삭제x

- D : cascade delete을 설정하고 삭제된 row는 sales_history테이블을 별도로 생성하여 기록한다.

                   product 테이블의 row만 삭제를 원할 경우에는 foreign key를 disable 하는 방식을 활용한다.

- 나 : sales_history 테이블은 생성하되 외래키를 지정하지 않고 cascade 기능은 프로그램으로 구현한다.

         product를 자유롭게 삭제하기 위함이며, foreign key를 때에 따라 disable 하는 것은 불필요하다고 생각한다.

- E : cascade delete 설정을 하지 않으면 제품 테이블에서 삭제된 제품이 sales테이블에서는 삭제되지 않아 무결성 해친다.

 

* 종합 의견 : cascade delete를 설정하고 sales_history 테이블을 운영하여 sales 테이블에서 삭제된 정보를 별도로 저장한다.

                     전체 정보 출력을 원할 시에는 sales_history 테이블과 sales 테이블을 합쳐서 출력한다.

 

 

 

2022.10.06 - 2

<요구사항>

- 이전 학습자와 다른조 학습자들의 자료를 참고하여 2차 회의

- 네가지 솔루션 (내가 정리한것)

1. 외래키 제약조건을 걸지 않고 별도의 복제 테이블을 운영

2. 평소에는 외래키 제약조건을 활성화하여 판매 등록할 때는 

    product 테이블에 등록이 되어있는 제품코드만 등록 가능하도록 하고 제품 코드를 삭제할 때는 외래키를 해제하는 방법

3. sales_history 테이블 운영

4. 삭제 여부를 가리는 컬럼을 추가

 

 

<2조 회의결과(학습자 D, E, 나)>

- 나 : 1번 솔루션은 데이터 중복이 많다. DBMS를 사용하는 이유는 데이터 중복을 줄이기 위함이라고 생각한다.

- D, E : 시스템 제작 기간이 짧은 경우에는 외래키를 사용하는 2번 솔루션도 유리할 수 있다.

- E : 컬럼을 추가하는 방법은 조회 속도를 저하시킬 것 같다.

 

* 종합 의견 : 외래키와 cascade delete를 적용하여 product테이블에서 제품 삭제 시 sales 테이블의 해당 제품들도 삭제한다.

                     sales_history 테이블을 생성하여 sales 테이블에서 삭제된 로우를 별도로 저장한다.

 

 

 

2022.10.07

<요구사항>

- 솔루션으로 기대되는 결과 : 판매정보 유지와 삭제 두 가지 상황을 모두 반영하는 시스템 구현

- 어떤 솔루션을 채택해야 가장 유리할지 토론

 

 

<2조 회의결과(학습자 D, E, 나)>

- 나 : sales_history 테이블을 생성하여 삭제된 판매 데이터를 저장하고
        외래키 및 cascade delete를 설정하여 product를 참조하는 sales 테이블의 row도 삭제한다.

- D : sales 테이블의 유지용 테이블을 생성하여 기존 sales 테이블에서는 삭제가 일어나지 않게 하고
       삭제를 원할 시에는 별도의 유지용 테이블에서 삭제한다.

- 나 : DBMS의 장점 중 '데이터 중복 최소화'가 있는데 이를 위반한다고 생각한다.

- E : 외래키를 지정하지 말고 제품이 삭제되어도 해당 제품코드를 참조하는 판매 정보는 삭제하지 않는다.

        검색하다보니 커뮤니티에 외래키를 지양한다는 말이 많더라.

- 나 : https://burndogfather.tistory.com/258 이런 '외래키를 사용하지 않는 이유'에 대한 글도 꽤 많았다.

        외래키를 사용하려면 추후에 외래키 조건을 위반하는 일이 발생하지 않을지 고려해야 할 것 같다.

- E : 유지보수를 고려한다면 외래키를 설정하지 않는 것이 좋을 것 같다.

 

* 종합 의견 : 외래키 설정을 하지 않고 현재 설계된 DB를 최대한 활용한다.

 

 

 

2022.10.11

<요구사항 1>

- 조원 모두가 합의하는 솔루션을 제출한다.

- 다른 조원이 누구에게 질문해도 공통된 답변을 할 수 있도록 모든 팀원의 이해도가 높아야한다.

 

 

<2조 회의결과(학습자 D, E, 나)>

- E : sales_history를 생성하는 대신 수정 등의 정보를 저장하여 추후 필요시 제공하는 것도 괜찮을 것 같다.

- 나 : 현재 요구사항은 데이터 삭제에 중점을 두고 있기 때문에 추후에 sales_history 테이블이 필요하다면
        그때 생성해도 될 것 같다.

 

* 종합 의견1 : 외래키 설정은 하지 않고 별도의 테이블 생성도 하지 않는다.

                       즉, product 테이블에서 제품이 삭제되어도 같은 제품코드를 가진 sales의 row는 삭제되지 않는다.

 

- D : 그렇다면 (의미상)삭제된 sales의 row를 가져올 땐 product_history 테이블의 '삭제' row를 가져와야 하는데,

        서브쿼리를 활용하면 될 것 같다.

- 나 : 서브쿼리는 결과로 1개의 row만 리턴해야하는데, product_history 테이블의 '삭제' row가 한개일 가능성은 

         희박하므로 어려울 것 같다.

- D : trigger로 하는 방식은 어떤가?

- 나 : trigger는 특정 작업이 발생했을 때(방아쇠를 당김) 실행되는 작업(발사)이므로 데이터를 끌고 오는 것은

         어떤 작업에 대한 부족 작업이 아니기 때문에 trigger로 구현하기는 부적합할 것으로 예상된다.

- E : 먼저 product_history에서 삭제된 row를 조회하고 sales 테이블의 조회 내역에서 제외하고 출력하는 방법은?

- 나 : 찾아보니까 쿼리를 두번 반영하는 것 보다는 한문장 내에서 join하는게 대체적으로 속도가 빠르다고 한다.

- E : inner join과 right join같은 것들을 활용하면 될 것 같다.

 

* 종합 의견2 : 특정 데이터를 출력할 때는 테이블간의 join을 활용하자.

 

 

<요구사항2>

- 1조 의견 : product 테이블을 참조하는 sales 테이블을 유지 테이블과 삭제 테이블 두 가지로 운영한다.

                  insert할 때, 두 테이블 모두에 insert 되고 삭제를 원할 시에는 삭제 테이블에서만 삭제한다.

- 2조 의견 : 외래키를 설정하지 않고 삭제된 정보가 필요할 경우에는 join을 활용하여 출력한다.

- 다른 조의 의견에 대해서 질문을 하고 자신의 조에 대한 질문에 답변한다.

 

 

<1조 의견 질답>

Q. E : 판매 정보가 제품 정보보다 훨씬 많을텐데, 판매테이블을 두개 운영하면 정보 중복이 발생해서 비효율적이지 않은가?

A. 삭제 테이블은 유지 테이블보다 row의 개수가 적을 것이므로 낭비라고 보기 어렵다.

 

Q. 나 : 삭제 테이블에서 삭제를 할 때 외래키를 off 할거라면 외래키를 꼭 지정해야 하는 이유가 있나?

A. 유지 테이블과 삭제 테이블이 product 테이블에 연결되어 있도록 하고, 일관성을 위해서도 설정한다.

 

Q. D : 외래키를 해제한 사이에 다른 데이터가 insert 되어 무결성을 해친다거나 할 우려는 없나?

A. 데이터 변조에 대한 우려를 고민했으나, 리스크가 크지는 않을 것으로 예상되어 해당 의견을 유지했다. 

 

 

<2조 의견 질답>

Q.  외래키를 사용하지 않는가?

A. E : 구글링해보니 현업에서 사용하지 않는 이유들이 다수 나오고,

         기존 시스템의 변경을 최소화하기 위해서도 외래키를 배제했다.

    D : 외래키가 있으면 트리거 작동이 불가능하다.

 

Q. join을 활용할 경우 판매 정보가 많아지면 시간이 많이 소요될 것 같다.

A. 나 : 해당 이슈는 인지하고 있다. 하지만 테이블의 개수를 줄여 저장공간 차지를 줄이는 방법을 택했다.

 

 

<나의 개인 의견>

의견의 좋고 나쁨으로 갈리기 보다는, 환경과 업무 활용도를 파악하기 전엔 결론 내기 어려울 것 같다.

join으로 인해 조회 속도가 느려지느냐, 추가 테이블로 인해 저장 공간을 더 차지하느냐 차이인 것 같다. 

조회가 빈번하게 일어나는 테이블일 경우 추가 테이블 방식이, 빈번하지 않을 경우 join 방식이 나을 것이다.

 

- 선생님 첨삭 : 클라우드 환경에서는 저장공간을 덜 차지하는 것이 좋은 솔루션일 것이고,

                        온프레미스 환경에서는 쿼리 속도가 빠른 것이 좋은 솔루션일 것이다.

                        어느 방법이 더 나을지는 환경에 따라 차이가 있다.

 

 

 

 

댓글