Skip to content

Commit

Permalink
JMeter로 부하/스트레스 테스트하기 (#10)
Browse files Browse the repository at this point in the history
  • Loading branch information
tinajeong authored Jan 17, 2024
1 parent 2aaf68a commit 2e9af2c
Show file tree
Hide file tree
Showing 3 changed files with 391 additions and 27 deletions.
173 changes: 146 additions & 27 deletions ch03/정찬미.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,19 +15,26 @@ _class: lead
## 3.2 메모리

- 시간이 갈수록 프로세스 코어의 데이터 수요를 메인 메모리가 맞추기 어려워짐.
- CPU idle time이 증가하는 문제점.
- CPU idle time이 증가하는 문제점 발생.
- 무어의 법칙 : 반도체칩 기술의 발전속도에 관한 것으로, 반도체칩에 집적할 수 있는 트랜지스터의 숫자가 ***18개월마다 두배씩 증가한다는 법칙***
- 한계점은 있다.무어의 법칙이 둔화되고 있기는 하나 여전히 유효한 법칙
![](https://img.etnews.com/photonews/1509/720847_20150903143404_559_0001.jpg)

---

<!-- footer : 65p -->
## 3.2.1 메모리 캐시

- 메모리 접근 시간을 최적화하기 위한 캐시 메모리의 역할의 중요성.
- 캐시 메모리 종류별 액세스 시간
![캐시 메모리 종류별 액세스 시간](https://oopy.lazyrockets.com/api/v2/notion/image?src=https%3A%2F%2Fs3-us-west-2.amazonaws.com%2Fsecure.notion-static.com%2F931f02f9-db8d-43df-8095-39d59f5fa14f%2FScreen_Shot_2021-08-09_at_9.17.54_PM.png&blockId=889d8c66-4854-404c-8382-c864eb98e46e)

---
----

<!-- header : '메모리 종류별 액세스 시간' -->
<!-- footer : 65p -->
![메모리 종류별 액세스 시간](https://oopy.lazyrockets.com/api/v2/notion/image?src=https%3A%2F%2Fs3-us-west-2.amazonaws.com%2Fsecure.notion-static.com%2F931f02f9-db8d-43df-8095-39d59f5fa14f%2FScreen_Shot_2021-08-09_at_9.17.54_PM.png&blockId=889d8c66-4854-404c-8382-c864eb98e46e)

---
<!-- header : '' -->
<!-- footer : 68p -->
## 3.2.1 메모리 캐시

Expand All @@ -37,54 +44,166 @@ _class: lead
- Shared(공유) 상태 : 데이터가 두 개 이상의 프로세서 캐시에 적재되어 있는 상태
- Invalid(무효) 상태 : 데이터가 다른 프로세스에 의해 수정되어 무효화된 상태

> 멀티 프로세서는 동시에 공유 상태에 있을 수 없다.
>
> 멀티 프로세서는 동시에 공유 상태에 있을 수 없다.

<!-- header : '' -->
<!-- footer : 68p ~ 72p -->
## 3.2.1 메모리 캐시

- 하나의 프로세서가 배타 또는 수정 상태라면 다른 프로세서는 모두 무효상태가 된다.

----

<!-- footer : 68p ~ 72p -->
<!-- header : MESI 상태 변이 다이어그램 -->

![bg 50%](https://oopy.lazyrockets.com/api/v2/notion/image?src=https%3A%2F%2Fs3-us-west-2.amazonaws.com%2Fsecure.notion-static.com%2F76da7896-4e61-4091-87e2-c65463e12c81%2FScreen_Shot_2021-08-09_at_9.25.54_PM.png&blockId=ab2442bc-c309-455f-8720-01a5ecef53be)

----

<!-- header : '' -->
<!-- footer : 68p ~ 72p -->
## 3.2.1 메모리 캐시


- 동시기록 _write-through_ (캐시 연산 결과 바로 메모리에 기록) vs 후기록 _write-back_ (변경된 블록만 메모리에 기록)
- 캐시 기술 덕분에 메모리 대역폭 측면에서 큰 효과
- 최대 전송률 _burst rate_ 요소 : 메모리 클록 주파수 , 메모리 버스 폭(보통 64비트), 인터페이스 개수(요즘 대부분 2개)
- ex) DDR RAM (Double Date Rate RAM) : 최대 전송률 2배
- 상용 하드웨어에서 이론적인 최대 속도는 8 ~12GB/s
- `70p` 캐시 하드웨어의 작동원리를 나타낸 간단한 코드 -> 자바 성능을 논할 때는 객체 할당률에 대한 애플리케이션 민감도가 굉장히 중요하다.

> 섣부른 직감만 가지고 JVM 성능 문제를 잘못 판단하기 쉽다.
---

<!-- footer : 66p -->
<!-- header : '' -->
<!-- footer : 72p ~75p-->
## 3.3 최신 프로세서의 특성

- 변환색인버퍼 (TLB) : 가상메모리 주소를 물리 메모리 주소로 매핑
- 변환색인버퍼 (TLB) : 가상메모리 주소를 물리 메모리 주소로 매핑. 페이지 테이블의 캐시 역할
- TLB가 없으면 L1 캐시에 페이지 테이블이 있어도 가상 주소 룩업에 16 사이클이 걸리므로 성능이 제대로 나오지 않음.
- 분기예측과 추측 실행 : 프로세서가 조건 분기하는 기준값을 평가하느라 대기하는 현상을 방지
- `가장 발생 가능성이 큰 브랜치를 미리 결정하는 휴리스틱` -> 맞다면 진행, 틀리면 명령 모두 폐기, 파이프라인 refresh 하는 risk
- 하드웨어 메모리 모델 : 어떻게 하면 서로 다른 여러 CPU가 일관되게 동일한 메모리 주소를 액세스할 수 있을까?
- JMM은 프로세서 타입별로 상이한 메모리 액세스 일관성을 고려하여 명시적으로 약한 메모리 모델(메모리정렬의 측면에서)을 정의함. 멀티스레드코드가 제대로 작동하게 하려면 락과 volatile을 정확히 사용해야 함.
- 기계 공감 _mechanial sympathy_ : 더 나은 성능을 얻기 위해 하드웨어 작동 원리를 깊이 이해하기

---

<!-- footer : 67p -->
<!-- header : '' -->
<!-- footer : 75p ~ -->
## 3.4 운영체제

- 스레딩, 메모리 관리, I/O 처리 등 운영체제의 핵심 기능과 JVM과의 상호작용.
- OS의 주 임무 : 여러 실행 프로세스가 공유하는 리소스 액세스를 관장
- 스케줄러 : 프로세스 스케줄러는 CPU 액세스를 통제하고, 실행 큐를 통해 프로세스를 관리함.

> 실제 측정 플로세스에서 나온 통계치는 시스템에 있는 다른 프로세스의 동작에도 영향을 받는다. -> 지터 _jitter_ 와 스케줄링 오버헤드는 측정 결과에 노이즈를 끼게 만드는 주요인.

---

<!-- footer : 68p -->
## 3.5 단순 시스템 모델
<!-- header : '' -->
<!-- footer : 75p ~ 80p-->

- 자바 애플리케이션 성능 최적화를 위한 기본적인 시스템 모델 이해.
- JVM 성능 최적화를 위한 기본적인 시스템 이해의 중요성.
### OS마다 다르게 작동하는 부분들
- 시간 문제 : POSIX(portable operating system interface, 포직스) 같은 업계 표준이 있어도 발생한다.
- 컨텍스트 교환 : 커널 모드로 컨텍스트가 교환되면 TLB를 비롯한 다른 캐시까지도 무효화됨(시스템 콜 반환 시 다시 채워야함)
![시스템 콜이 유저모드 IPC에 미치는 영향](https://resize-v3.pubpub.org/eyJidWNrZXQiOiJhc3NldHMucHVicHViLm9yZyIsImtleSI6InpiYTI3ZW13LzIxNjAyNTk0Mjk5OTkzLnBuZyIsImVkaXRzIjp7InJlc2l6ZSI6eyJ3aWR0aCI6ODAwLCJmaXQiOiJpbnNpZGUiLCJ3aXRob3V0RW5sYXJnZW1lbnQiOnRydWV9fX0=)

---

<!-- footer : 69p -->
## 3.6 기본 감지 전략
<!-- header : '' -->
<!-- footer : 75p ~ 80p-->

- 리눅스 : 가상 동적 공유 객체 (virtual dynamically shared object, vDSO) 장치 제공 -> 시스템 콜의 속도를 높이려고 쓰는 유저 공간의 메모리 영역 -> 커널모드로 컨텍스트 교환이 일어나지 않기 때문에 속도 향상

- 하드웨어 및 OS 수준에서 발생하는 성능 문제를 감지하는 전략.
- 자바 애플리케이션에서 일반적으로 발생하는 성능 병목 현상의 식별 및 해결 방법.
- JVM과 운영체제 간의 상호작용에서 발생할 수 있는 성능 이슈를 식별하는 방법.
----

<!-- footer : 81p -->
## 3.5 단순 시스템 모델에서 성능 이슈 분석

### 기본 감지 전략

> 성능 진단의 첫 단추는 어느 리소스가 한계에 다다랐는지 밝히는 일이다.
----

<!-- footer : 82p -->

### 기본 감지 전략 : 1. CPU 사용률
- 핵심 지표, 사용률이 가능하면 100%에 가까워야 함.

```zsh
$ vm_stat 1
Mach Virtual Memory Statistics: (page size of 16384 bytes)
free active specul inactive throttle wired prgable faults copy 0fill reactive purged file-backed anonymous cmprssed cmprssor dcomprs comprs pageins pageout swapins swapouts
7924 430962 1996 429043 0 94700 5326 22842329 825402 8359485 310160 82192 326827 535174 121760 47980 24021 157746 707752 9639 0 0
7602 431344 2007 429023 0 94684 5326 4205 204 1526 0 0 326844 535530 121760 47980 0 0 6 0 0 0
7573 431326 2032 428994 0 94660 5326 2874 71 1131 0 0 326868 535484 121760 47980 0 0 0 0 0 0
7575 431218 2036 429123 0 94668 5333 3617 71 1592 0 0 326872 535505 121760 47980 0 0 0 0 0 0
7259 431273 2042 429140 0 94742 5323 5355 198 2161 0 0 326879 535576 121760 47980 0 0 1 0 0 0
```

----

<!-- footer : 83p -->
### 기본 감지 전략 : 1. CPU 사용률

- `free`: 사용되지 않은 페이지 수. 이 값이 너무 낮으면 시스템이 메모리 부족 상태에 있을 수 있다.
- `active`: 현재 사용 중인 페이지 수. 이 값이 높으면 많은 양의 메모리가 현재 사용 중임을 나타.
- `wired`: 커널에 의해 사용되는 페이지 수. 이 값이 높으면 커널이 많은 양의 메모리를 사용하고 있다는 뜻.
- `faults`: 페이지 폴트 수. 페이지 폴트는 시스템이 디스크에서 데이터를 메모리로 가져와야 할 때 발생. 이 값이 높으면 시스템이 많은 양의 I/O를 수행하고 있음을 나타냄.

----

<!-- footer : 83p -->
### 기본 감지 전략 : 1. CPU 사용률

- `pageins`: 페이지 인 수. 이 값이 높으면 시스템이 많은 양의 데이터를 디스크에서 메모리로 이동하고 있음을 나타냄.
- `pageout`: 페이지 아웃 수. 이 값이 높으면 시스템이 메모리 부족 상태에 있을 수 있으며, 메모리에서 디스크로 데이터를 이동하고 있음을 나타냄.
- `swapins``swapouts`: 스왑 인과 스왑 아웃 수. 이 값들이 높으면 시스템이 스왑 공간을 많이 사용하고 있음을 나타냄. 이는 메모리 부족 상태를 나타낼 수 있다.

----

<!-- footer : 84p -->
### 기본 감지 전략 : 1. CPU 사용률

- CPU 사용률이 100%에 근접하지 않다면
- 락 때문에 본의 아니게 발생한 **컨텍스트 교환** 때문인가?
- I/O 경합이 일어나 블로킹이 발생했나? 등을 따져 보아야 함

----

<!-- footer : 84p ~ 88p -->
## 3.6 기본 감지 전략

- 가비지 수집 : 어떤 시스템에서 CPU 사용률이 아주 높게 나타난다면, GC는 주범은 아니다. GC 자체는 유저 공간의 CPU 사이클을 소모하되 커널 공간의 사용률에는 영향을 미치지 않는 활동이다.
- 반면 JVM 프로세스가 유저 공간에서 CPU를 100%에 가깝게 사용하고 있다면 GC가 원인일 확률이 높다.
- 입출력 : 자바 프로그램은 대부분 I/O 서브시스템을 심하게 가동하는 애플리케이션 클래스도 비교적 적은 편이다.
- 커널 바이패스 I/O : 커널을 거치지 않고 직접 하드웨어에 접근하는 방식 (매우 유용한 패턴이지만 자바에서는 커스텀라이브러리를 사용해 구현해야 함)
- Netty, DPDK(Data Plane Development Kit), Java NIO 등
- 기계공감 : 자바가 추상화를 해준다고 기계의 동작을 몰라도 된다는 말은 아니다.
- 두 스레드가 동일한 캐시 라인을 수정하려고 시도하면 경합이 발생한다. 이 과정에서 `잘못된 공유``성능 저하 이슈`가 발생할 수 있다. 그리고 변수 주변에 패딩을 넣어 강제로 다른 캐시 라인으로 보내 해결하기도한다.
---

<!-- footer : 70p -->
<!-- footer : 88p ~89p -->
## 3.7 가상화

- 가상화 기술이 자바 애플리케이션 성능에 미치는 영향.
- 클라우드 컴퓨팅 및 가상화된 환경에서의 자바 성능 최적화 전략.
- JVM이 가상화된 환경에서 어떻게 동작하는지에 대한 심층 분석.
- 일반적인 가상화의 형태 : 이미 실행 중인 호스트 OS 위에서 OS사본 (게스트 OS)을 하나의 프로세스로 실행하는 방식
- 가상화의 특징
1. 가상화 OS에서 실행하는 프로그램은 베어 메탈(비가상화 OS)에서 실행할 떄와 동일하게 작동해야 한다.
2. 하이퍼바이저는 모든 하드웨어 리소스 액세스를 조정해야한다.
3. 가상화 오버헤드는 가급적 작아야 하며 실행 시간의 상당 부분을 차지해선 안 된다.

> 가상화 시스템에서는 게스트 OS가 하드웨어가 직접 액세스 할 수 없어서 프리빌리지드 명령어를 언프리빌리지드 _unprivileged_ 명렁어로 수정해 사용
> 가상화 환경에서의 성능 분석은 한층 더 어렵다.
---

<!-- footer : 71p -->
## 3.8 JVM과 운영체제

- JVM이 운영체제와 어떻게 상호작용하는지에 대한 상세한 분석.
- JVM의 가비지 컬렉션, 스레드 관리, I/O 처리 등이 OS와 어떻게 상호작용하는지.

---
- 자바 네이티브 인터페이스 (JNI) : 자바와 OS 간의 통신을 위한 인터페이스
---
104 changes: 104 additions & 0 deletions ch04/정찬미.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
---
marp: true
_class: lead
---

<!-- footer : 93p -->
# Ch 4. 성능 테스트 패턴 및 안티패턴

> 1. 유형별 베스트 프랙티스 안내
> 2. 성능 테스트에 좋지 않은 영향을 끼치는 일반적인 안티패턴과 리팩터링하는 방법
---
<!-- header : 4.1 성능 테스트 유형-->
<!-- footer : 93p -->

> "그래도 뭐라도 하는 게 아무것도 안 하는 것 보단 낫지" 않냐는 그릇된 믿음은
> 위험한 반쪽자리 진실이다.
- 가장 흔히 저지르는 실수 : 구체적인 내용을 정하지 않고 **뭉뚱그려** 성능 테스트를 수행하는 것.
- 성능 테스트 기획 Tip : 테스트로 확인하고 싶은 *정량적 질문 리스트*와 그 테스트가 대상 *애플리케이션 입장에서 중요한 이유*를 적어보자!

---

<!-- footer : 98p -->
### 질문 예시

1. **응답시간 테스트 (Latency Test)**: 종단 트랜잭션에 걸리는 **시간**은?
2. **처리율 테스트 (Throughput Test)**: 현재 시스템이 처리 가능한 동시 트랜잭션 **개수**는?
3. **부하 테스트 (Load Test)**: **특정 부하**를 시스템이 감당할 수 있는가?
4. **스트레스 테스트 (Stress Test)**: 이 시스템의 **한계점** *breaking point* 은 어디까지인가?
5. **내구성 테스트 (Endurance Test)**: 시스템을 **장시간 실행**할 경우 성능 이상 증상이 나타나는가?
6. **용량 계획 테스트 (Capacity Planning Test)**: **리소스를 추가한 만큼** 시스템이 확장되는가?
7. **저하 테스트 (Degradation Test)**: 시스템이 **부분적으로 실패할 경우** 어떤 일이 벌어지나?

----

1. **응답시간 테스트 (Latency Test)**
- UX상에서 직관적이고 중요한 지표
- 평균값의 함정에 빠질 수 있다.
2. **처리율 테스트 (Throughput Test)**
- 지연시간 테스트와 함께 수행 -> 일반적인 상황애서 어느정도의 처리율을 유지하고 있는가?
3. **부하 테스트 (Load Test)**
- 부하가 걸릴 가능성이 높은 서비스의 특정 부분에 집중 ex> 광고 캠페인
4. **스트레스 테스트 (Stress Test)**
- 일반적이지 않은 상황에서 시스템이 어느정도까지 견딜 수 있는지 점진적으로 검증
- Maximum TPS를 시스템의 한계로 본다.

----
<!-- header : ''-->
<!-- footer : ''-->
## 궁금증 : 부하 테스트 vs 스트레스 테스트?

- **부하 테스트**: 시스템이 예상 사용량(**임계치**)을 처리할 수 있는지 확인
- 부하 상태에서 시스템의 성능을 측정하고, 이를 통해 성능 임계치를 결정하는 것
- **스트레스 테스트**: 시스템이 **극한의 부하나 조건**에서 어떻게 작동하는지 확인
- CPU, 에러 발생, 응답시간 등이 어떻게 작동하는지 검증

![이해에 좋은 그래프](https://blog.imqa.io/content/images/2020/04/image-11.png)

----

<!-- header : 4.2 기본 베스트 프랙티스-->
<!-- footer : 100p-->
## 성능테스트 시 필요한 태도!

- 검증할 부분이 무엇인지, 어떻게 측정할지 생각하기
- 쉬운 부분보다 중요한 부분에 집중하기
- 중요한 부분을 먼저 하기

> it is sometimes tempting to report on an easy measure, rather than the right measure.
----

## 기본 베스트 프랙티스

- 운영 환경과 되도록 비슷하게 구축되어야 한다. (현실에선 자주 무시되는 부분...!)
- 인프라, 데이터셋 등
- 성능 비기능 요건 NFR을 구성원들과 잘 협의해야 한다.
- 소프트웨어개발주기 *SDLC* 의 일부에 포함 시켜 상시로 성능회귀테스트를 진행한다. _performance regression testing_
- 자바에서 특정해 발생하는 이슈에 주의한다.
- 메서드가 호출되지 않거나, 너무 복잡하고 커서 컴파일 분석을 할 수 없는 경우

----

<!-- header : 4.3 성능 테스트 안티패턴-->
<!-- footer : 102p-->
## 성능 테스트 안티패턴

- 지루해서 필요이상으로 복잡한 코드를 개발
- 이력서 부풀리려고 불필요한 기술 덧대기
- 또래 압박으로 충분한 논의 없이 진행
- 이해가 부족한데 무조건 새로운 툴로 진행하려는 것
- 성능 지표 측정이나 팀 내 공유를 하지 않고 개선하려는 것

> 문제가 터지고 나서야 : "그동안 UAT에 만족하며 안일하게 살았구나, 운영 환경에서 큰 문제가 생겼을 때 신속하게 대응할 준비를 전혀 안했구나.."
---
<!-- header : ''-->
<!-- footer : ''-->
## References

- 자바 최적화 Ch. 4
- [Optimizing Java Ch 4.](https://www.oreilly.com/library/view/optimizing-java/9781492039259/ch04.html)
- https://blog.imqa.io
Loading

0 comments on commit 2e9af2c

Please sign in to comment.