ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 소프트웨어 공학(4) - 테스트와 유지보수
    Computer Science/SW Engineering 2021. 12. 15. 20:52

    소프트웨어 테스팅

    프로그램 테스트

    • 의도적으로 프로그램을 사용하기 전 결함을 발견하는 것이다.
    • 인공적인 데이터를 사용한다.
    • 테스트는 테스트에 한해서만 에러를 보여준다.
      • 전체를 보여주는 것이 아니다.
    • V&V가 테스트의 대부분이다.
    • 테스트 대상
      • 소프트웨어 요구사항
      • 에러/실수
      • 결함/버그 → 검증 단계에서 주로 발생
      • 실패 (결함의 결과)
        • 모든 결함이 실패를 만들지는 않는다.
    • 검증 및 확인
      • Verifacation
        • 요구사항 명세대로 만들었는지 확인
        • 모든 요구사항마다 1개 이상의 테스트가 존재해야한다.
      • Validation
        • 사용자의 실 요구에 잘 맞는지 확인
        • 의도적으로 결함을 드러내도록 테스트한다.
        • 시스템이 사용되는 상황을 예상해서 테스트 케이스를 작성한다. → 의도대로 동작하는지?
        • validation test
          • 시스템의 정확한 수행 여부를 테스트 함.
          • 정상 데이터 활용
        • defect test
          • 부정화간 데이터를 탐색하고 입력
    • 소프트웨어 인스펙션(점검)
      • Inspection
        • 정적 확인 → 코드분석, 설계 분석
        • 도구 기반의 문서와 코드 분석
      • Testing
        • 동적 확인 → 시스템 기능, 행동, 상호작용 점검
        • 테스트 데이터를 활용
    • 테스트 케이스
      • 기능이 추가되거나 수정되지 않는 이상 그대로 사용한다.
      • 예상 결과와 실제 결과를 비교하여 보고서를 작성하고 에러를 수정한다.
    • 테스트 단계
      • 개발 테스트
        • 시스템 개발 중 버그와 결함을 찾기 위해 테스트
      • 릴리즈 테스트
        • 별도의 테스트 팀이 완성 버전을 릴리즈 하기 전에 테스트
        • 요구사항에 맞는지 점검한다.
      • 사용자 테스트
        • 사용자들이 실제 사용 환경에서 동작하는지 확인한다.
        • Acceptance 테스팅은 사용자 테스트의 한 유형이다.
          • 이 테스트를 통해 소프트웨어를 전달 받을지 결정한다.

    개발 테스트

    • 시스템 개발 팀에 의해 수행 되는 모든 테스트
      • 유닛 테스트
        • 메서드나 객체, 속성 등의 기능 테스트를 수행한다.
        • 테스트 대상은 개별적인 기능-동작에 대해 테스트한다.
        • 객체클래스 테스팅
          • 모든 메서드, 속성과 가능한 상태에 대해 테스트한다.
            • 상태 변화 순서도 테스트 해야된다.
          • 상속 등으로 인해 부모-자식 간의 경계가 불분명하다.
            • 테스트 난이도 상승
        • 테스트 자동화
          • JUnit 등을 활용한 테스트 자동화가 필요하다.
          • Setup 파트에서 테스트케이스에서 테스트의 예상되는 입출력을 정의해야한다.
          • Call 파트에서 객체나 메서드를 테스트한다.
          • Assertion 파트에서 테스트의 결과와 예상안을 비교해야한다.
        • 테스트 케이스
          • Validation : 시스템이 내 의도대로 동작하는지 확인.
          • Verification : 결함이 테스트 케이스를 통해 드러나는지 확인.
          • 비정상 입력에 대해 시스템이 적절한 예외 처리 등으로 대처하는지 확인.
        • 테스트 전략
          • 분할 테스트
            • 특정 집단의 공통된 특성을 가진 입력은 동일한 테스트로 본다.
            • 대표되는 테스트 케이스만 테스트한다.
          • 가이드라인 기반 테스트
            • 테스트 케이스를 선정하기 위한 테스트 가이드 라인을 사용한다.
            • 가이드 라인은 이전의 에러 경험을 반영한다.
        • 경계 테스트
          • 결함을 확인하기 위함
          • 데이터 범위의 경계 근처의 데이터로 테스트한다.
        • 테스트 절차 가이드라인
          • 하나의 값 만을 가지는 시퀀스로 테스트한다.
          • 테스트 마다 다른 크기로 테스트한다.
          • 시퀀스의 가장자리와 중간의 원소가 테스트되도록 유도한다. → 경계 테스트
          • 예시
            • 시스템의 모든 오류를 생성시키는 입력 선택
            • 버퍼 오버플로우를 유도
            • 같은 입력을 여러 번 반복
            • 유효하지 않는 출력 생성을 유도
            • 계산 결과의 데이터의 양, 크기를 극단적으로 줄이거나 늘린다.
      • 컴포넌트 테스트
        • 객체, 메서드 들의 집합인 컴포넌트가 제대로 동작하는지 테스트한다.
        • 연동- 상호작용 테스트이다.
        • 인터페이스를 통해 사용한다.
        • 유닛 테스트는 완료되었다고 가정한다.
        • 연동 시의 정상동작과 비정상 동작을 확인한다.
        • 인터페이스 테스팅
          • 매개 변수
          • 공유 메모리
          • 프로시저
          • 메시지 전달
        • 인터페이스 오류
          • 인터페이스 오용
            • 인터페이스를 잘못 사용하여 발생
          • 인터페이스 오해
            • 인터페이스에 대한 명세를 잘못 이해하고 호출하여 발생
              • 개발자 간 가정이 다를 수 있다.
              • 따라서, 설계 시점에서 정의해야 한다.
          • 타이밍 오류
            • 공유 메모리나 메시지 전달 인터페이스 사용 시 발생
            • produce → consump 테스트가 이루어져야함
        • 인터페이스 테스트 가이드라인
          • 시스템 규모에 따라 컴포넌트가 없을 수도 있다.
          • 데이터의 양 끝을 전달 → 경계 테스트
          • 널 포인터 전달
          • 고의적으로 컴포넌트가 실패하는 테스트 설계 및 전달
          • 스트레스 테스트 사용
      • 시스템 테스트
        • 컴포넌트를 통합하여 하나의 시스템으로 동작하는지 테스트한다.
        • 유닛테스트, 컴포넌트 테스트를 통과한 이후 테스트한다.
        • 시스템 돌발 상황도 테스트한다.
        • 외부 프레임워크도 통합하여 테스트한다.
        • 별개의 테스팅 팀을 두기도 한다.
      • 유즈케이스 테스트
        • 유즈케이스 기반으로 시스템을 테슽한다.
        • 별개의 테스팅 팀을 두기도 한다.

    테스트 전략

    • 과도한 테스트는 현실적으로 불가능
    • 따라서 현실적인 범위를 지정한다.
    • 상황에 맞거나 안맞는 입력을 모두 테스트한다.
    • 기능 간의 조합도 테스트한다.
    • 하향식 통합 테스트
      • Main 모듈을 테스트하기 위해 임시 서브 모듈과의 연동을 테스트한다.
      • 임시적 서브 모듈을 Stub 이라 한다.
      • 장점
        • Main의 문제를 조기 발견
        • 뼈대가 조기 완성
      • 단점
        • Stub 제작에 대해 추가 비용 발생
        • 서브 모듈에 대한 정확한 출력 판단이 불가
    • 상향식 통합 테스트
      • 서브 모듈을 테스트 하기 위해 임시 메인 모듈과의 연동을 테스트한다.
      • 임시 메인 모듈을 Drivers 라고 한다.
      • 장점
        • 서브 모듈의 문제 조기 파악
        • 기능이 완성되어 있어 테스트가 쉽다.
      • 단점
        • Drivers 모듈 제작에 추가 비용 발생
        • 메인이 구현될 때 까지 전체 서브 모듈이 독자적 기능 불가

    릴리즈 테스트

    • 개발팀이 외부에서 사용할 시스템의 특정 버전을 테스트한다.
    • 기능-성능-신뢰도-문제 발생에 대한 테스트를 수행한다.
    • 일반적으로 시스템 명세 기반의 블랙박스 테스트이다.
    • 시스템 테스트의 한 형태이다. → 대상 동일
    • 차이점
      • 별도의 팀이 테스트한다.
      • 시스템 테스트는 개발팀이 버그를 찾는 결함 테스트에 초점을 맞춘다. (Defect Test)
      • 릴리즈 테스트는 테스팅 팀이 외부 환경에서의 요구사항에 맞는지 확인한다. (Validation)
    • 요구사항 기반 테스트
      • 요구 사항 기반의 테스트 케이스를 작성한다.
        • 예시
          • 시스템 로깅에 의한 인증
          • 다운로드, 업로드
          • 스케줄링
          • 암호화-복호화
          • 조회 및 수정
          • 연결
          • 호출
    • 성능 테스트
      • 스트레스 테스트를 통해 테스트할 수 있다.

    유저 테스트

    • 사용자가 입력을 제공하고 시스템 테스트에 관한 의견을 전달한다.
    • 시스템-릴리즈 테스트 수행 이후에도 필수적으로 수행해야한다.
    • 사용자의 환경 변화가 시스템에 영향을 미칠 수 있다.
      • 안정성, 성능, 사용성, 견고성
    • 종류
      • 알파 테스트
        • 일부 사용자가 개발팀과 함께 테스트한다.
      • 베타 테스트
        • 소프트웨어의 특정 버전을 사용자에게 공개하여 테스트한다.
      • 인수 테스트
        • 맞춤형 제품에 대한 테스트이다.
        • 고객의 환경에 배치하여 테스트하고 인수를 결정한다.
    • 애자일 기법에서의 인수 테스트
      • 사용자가 개발팀의 한 부분이다.
      • 사용자에 의해 정의된 테스트를 통해 통합을 결정한다.
      • 자동화된 테스트를 수행한다.
      • 별도의 인수 테스트를 거치치 않는다.

    블랙박스 테스트, 화이트 박스 테스트

    • 블랙박스
      • 기능의 동작 확인
      • 제대로 동작하는지 확인한다.
      • 모든 테스트 단계에서 적용할 수 있다.
      • 높은 단계에서 적합하다.
    • 화이트박스
      • 소스코드나 설계을 확인
      • 어떻게 동작하는지 확인한다.
      • 코드 기반 테스트 이므로 낮은 단계나 작은 규모에 적합하다.
        • 유닛 테스트, 통합 테스트 등

    소프트웨어 유지보수

    소프트웨어 변화

    • 변화의 핵심은 기존 시스템의 변화를 적용하고 관리하는 것이다.
    • 필수적인 소프트웨어 변화
      • 새로운 요구사항
      • 비즈니스 환경의 변화
      • 오류 발견
      • 새로운 하드웨어 장비
      • 성능과 안정성의 개선
    • 변화의 중요성
      • 대부분의 조직에서 새 시스템 개발보다 유지 보수에 더 큰 투자를 한다.
      • 소프트웨어 예산의 대부분이 기존 시스템을 변화시키고 진화시키는것에 있다.

    변화와 서비스

    • 변화(진화) 단계
      • 시스템에 대해 새로운 요구사항이 제안되고 구현된다.
    • 서비스 단계
      • 기능적인 요소를 유지하면서 버그를 수정하고 소프트환경 변화를 적용한다.
      • 새로운 기능을 추가하지 않는다.
    • 폐기 단계
      • 소프트웨어 자체는 유지될 수 있으나 추가적인 변화가 이루어지지 않는다.

    진화 프로세스

    • 진화 단계에서 특별한 기준은 없다.
      • 대신, 소프트웨어 타입, 개발 프로세스, 개발자의 능력에 의존하여 결정한다.
    • 변화 제안
      • 시스템 진화의 핵심 절차이다.
      • 변화에 영향을 받는 컴포넌트
      • 비용
      • 변화에 대한 영향 측정
    • 시스템 생명 주기의 전반에 걸쳐 지속된다.
      1. 새 시스템
      2. 변화 식별 프로세스
      3. 변화 제안
      4. 소프트웨어 변화 프로세스 (변화 적용)
    • 변화 구현
      • 요구사항 명세와 설계 문서가 있다면 이 문서들 또한 진화 과정 중에 수정해야한다.
      • 설계, 구현, 테스트 같은 개발절차의 반복이다.
      • 개발과의 차이점
        • 기존의 프로그램에 대해 이해해야할 필요가 있다.
          • 시스템 구조
          • 시스템 기능
          • 시스템에 미치는 영향
      • 긴급한 변경
        • 심각한 오류
        • 시스템 환경의 변화
        • 비즈니스 환경의 급격한 변화
        • 절차
          1. 변화 요구
          2. 코드 분석
          3. 코드 수정
          4. 코드 적용
    • 애자일 기법에서는?
      • 애자일 기법은 점증적 개발에 기반하므로 서비스 → 진화의 단계가 매끄러워야 한다.
      • 문제점
        • 개발팀과 유지보수 팀의 프로세스가 다를 경우
          • 요구사항이나 설계 관련 자세한 문서가 없을 수 있다.
          • 자동화 테스트 개발을 선행해야 할 수 있다.
          • 코드 개선을 선행해야 할 수 있다.

    레거시

    • 오래된 언어, 기술로 구성된 오래된 시스템이다.
    • 구형 하드웨어, 프로세스에 의존적일 수 있다.
    • 사회기술적 요소와 엮여있을 수 있다.
    • 레거시 시스템의 교체는 위험하고 많은 비용이 든다.
      • 시스템 명세가 부족할 수 있다.
      • 시스템과 비즈니스 환경 및 절차가 매우 적합하게 맞아 떨어질 수 있다.
      • 문서화 되지 않은 비즈니스 정책 등이 시스템에 내장되어있을 수 있다.
      • 새 소프트웨어 개발에 시간-비용 적인 문제가 들 수 있다.
    • 레거시 시스템의 변경 또한 많은 비용이 든다.
      • 프로그래밍 스타일이 일관되지 않을 수 있다.
      • 구식 언어이므로 개발 인력이 많지 않을 수 있다.
      • 시스템 문서가 불충분 할 수 있다.
      • 시스템 구조 품질이 저하될 수 있다.
      • 프로그램이 특정 기계 등에 최적화 되어 이해하기 어려울 수 있다.
      • 데이터 처리에 오류가 있을 수 있다.
    • 레거시 시스템의 관리
      • 낮은 품질, 낮은 가치
        • 시스템을 폐기한다.
      • 낮은 품질, 높은 가치
        • 재공학 하거나 교체한다.
      • 높은 품질, 낮은 가치
        • 상용 프로그램으로 대체한다.
        • 변화 비용이 비싸질 경우 폐기한다.
        • 아니라면, 유지한다.
      • 높은 품질, 높은 가치
        • 기존의 시스템을 그대로 사용하고 유지보수한다.

    소프트웨어 유지보수

    • 유지보수 기준
      • 오류 수정
        • 버그나 취약점을 수정한다.
        • 요구사항을 만족시킨다.
      • 환경 변화 적응
        • 최초 환경으로부터 변화 시킨다.
      • 기능 추가 및 수정
      • 예방적 유지보수
        • 오류 발생을 방지하기 위해 코드를 변화시킨다.
    • 유지보수 비용
      • 유지보수 팀이 개발 팀과 다를 수 있다.
        • 이에 따라 이해 비용이 필요하다.
        • 개발 팀에 대한 혜택이 없어 개발 팀이 유지보수 품질을 신경쓰지 않을 수 있다.
        • 유지보수는 비선호된다.
          • 초심자에게 할당될 수 있다.
        • 프로그램이 오래될 수록 변경이 어려워진다.
          • 시스템 구조 품질이 저하되면 변경이 어렵다.
          • 이에 따라 유지보수 선호도가 낮아진다.
          • 해당 시스템의 유지보수에 대한 전문가 수가 감소한다.
          • 위 단계가 반복된다.
    • 유지보수 예측
      • 시스템의 어떤 부분이 문제를 일으키고 큰 비용을 소모하는지에 연관된다.
      • 시스템 유지보수성(복잡도)이나 유지보수 비용, 시스템 변화를 예측한다.
      • 시스템의 변화는 시스템의 구조 품질을 낮추어 다음 변화 난이도를 증가시킨다.
      • 변화량의 예측은 시스템과 외부 환경 간의 관계를 확인하고 이해해야한다.
        • 환경의 변화가 시스템의 동작에 영향을 미칠 수 있다.(딱 맞아떨어지는 시스템일 경우 영향이 크다.)
      • 환경과의 관계 판단 기준
        • 시스템 인터페이스의 개수와 복잡도
        • 특정 기관의 정책 절차에 의한 요구사항
          • 이 경우 휘발성이 강하다.
        • 비즈니스 프로세스
      • 복잡도 측정(코드 수준) 기준
        • 제어 구조 복잡도
        • 데이터 구조 복잡도
        • 메서드나 모듈, 객체의 크기
      • 프로세스 측정 기준
        • 버그나 요구사항 등의 수정 요구 횟수
        • 영향 분석에 필요한 평균 시간
        • 변경 요구 구현에 소요되는 평균 시간
        • 추가적으로 대기 중인 수정 요구
        • 위와 같은 기준에 적용된다면 유지보수성이 하락할 수 있다.
      • 소프트웨어 재공학
        • 레거시 시스템의 유지보수를 위해 시스템이나 컴포넌트를 재구조화 한다.
        • 재공학을 통해 유지보수 비용을 낮춘다.
        • 이점
          • 위험 감소
          • 비용 감소
        • 프로세스
          • 코드 변환
          • 역공학
          • 추상적인 구조 품질 향상
          • 프로그램 모듈화
          • 데이터 재공학
      • 리팩토링
        • 프로그램 구조를 향상시켜 품질 저하를 늦춘다.
        • 예방적인 성격을 띈다.
        • 기능 추가가 목적이 아니다.
      • 재공학과 리팩토링
        • 재공학
          • 유지보수 비용의 증가에 따라 실행한다.
          • 구조, 언어, 문서, 데이터구조가 바뀔 수 있다.
          • 개발자를 위한 리팩토링을 포함한다.
        • 리팩토링
          • 개발 및 진화 과정 전반에 걸쳐 구조 품질 저하 및 비용 증가를 방지하기 위해 실행한다.
      • Bad Smells
        • 중복 코드
        • 긴 메서드
        • 스위치 케이스 문
        • 데이터 집합
        • 추측 기반의 일반성
          • 실제 쓰이지 않는 것을 만든 것

    댓글

Designed by Tistory.