aws

Jenkins 빌드 최적화를 위한 멀티프로세스 개선

하리하링웹 2024. 8. 5. 12:59

 현재 사용하고 있는 빌더에서 번들링 작업 시 멀티프로세스를 사용하고 있지만, Jenkins 빌드 머신의 24개 코어를 충분히 활용하지 못해 빌드 시간이 오래 걸리는 문제가 발생하고 있다는 사실을 찾아냈다. 기존 빌더에서는 워커 개수를 4개로 하드코딩하여 사용하고 있었기 때문에 발생한 문제이며 이를 개선하기 위해 다음과 같은 작업을 진행했다.

CPU 코어 수에 맞춘 워커 개수 증가

 먼저 os.cpus().length;를 사용하여 CPU 코어 개수를 얻고, 해당 개수만큼 worker-pool의 개수를 증가시켜 효율을 높였다.

const numWorkers = os.cpus().length;

 

청크 분배 방식 개선

 위의 CPU 코어에 맞게 워커 개수를 늘리는 작업 자체는 쉬운 작업이지만 이 때 문제가 발생한 부분이 하나 더 있었다.

 

 기존에는 워커의 인덱스에 따른 slice로 작업을 분배하여, 특정 워커에 작업이 몰리면 다른 워커들은 놀게 되어 결과적으로 번들링 시간은 큰 개선이 되지 않는 현상이 발생했다.

 이를 개선하기 위해 청크를 slice가 아니라 mod를 사용하여 전체 workerData에서 한 개씩 나눠주는 방식으로 테스트를 진행했다. 이 방식으로 번들링 시간이 약 15% 감소하는 것을 확인할 수 있었다.

 

 하지만 이러한 방식으로 작업을 나눠주는 것은 좀 불편하다고 느껴 큐 방식을 적용한 추가적인 작업을 진행하였다.

 

 먼저 작업 데이터를 초기화 과정에서 큐 안에 모두 넣어준 뒤 메인프로세스에서는 이 큐를 바라보면서 큐 안의 메시지를 모두 소모할 때 까지 루프를 돌며 각 워커에 뿌려주는 방식으로 동작하게 만들어 주었다.

 

 이후 테스트를 진행해 보았는데 예상과는 달리 오히려 번들링 시간이 늘어난 것을 확인하였다.

 

 이는 Node.js에서 새 워커를 만들고 제거하는 시간이 큐에 있는 한 개의 메시지를 처리하는 시간보다 더 오래 걸리기 때문에 발생한 문제였다. 따라서 약 100개 단위로 작업을 배치 처리하도록 코드를 변경해보았다.

 

 결과적으로는 mod 연산으로 각 워커에 균등하게 작업을 나눠준 뒤 실행시키는 것보다는 좀 더 느린 결과 값을 받을 수 있었다. 

 

 시간을 좀 들여 테스트를 해보면 batch 처리 해야하는 작업의 적절한 값을 찾을 수 있었겠지만 빌더의 번들링 과정 내부적으로 초반부분에 번들링이 시간이 오래 걸리는 파일이 모여있어 mod 연산으로 균등하게 나눠주는 것 만으로도 이미 충분히 최적화가 완료되었다고 판단하였으며 어느정도 유의미한 결과 값을 얻었기에 젠킨스 빌드 머신에서 아래 두 개의 항목을 개선한 내용으로 테스트를 진행해보았다.

  • 멀티프로세스 작업 개수 cpu 최대코어수(24개) 만큼 증가
  • 작업 분산을 단순 slice가 아니라 mod 연산으로 나눠줌
11:13:10  memory allocation of 223232 bytes failed
11:13:10  memory allocation of 44 bytes failed

 

 하지만 잘 동작할 것이라는 예상과는 달리 젠킨스에서는 위 에러 메시지를 받을 수 있었다.

 원인 파악을 위해 로깅도 해보고 로컬에서 테스트도 진행해 본 결과 원인은 워커의 개수를 24개로 늘렸을 때, 각 워커에서 절대적으로 차지하는 메모리 때문에 메모리 초과 문제가 발생한것이였다.

 워커 개수를 24개까지 늘리는 것은 너무 지나치다고 판단하여 최대 8개까지 사용하도록 변경하였으며 변경후 테스트해 보았을 때 정상적으로 동작하는 것을 확인할 수 있었다.

 번들링 시간 또한 유의미한 성능 개선을 이룰 수 있었기에 이 수정 내용을 적용하여 배포하기로 결정했다.

추가 개선 사항

 번들링 과정 앞의 TSC(타입스크립트 컴파일) 작업도 최대 8개 워커로 분산하도록 개선할 예정이다. 현재 워커의 개수는 8개로 동작하는 반면 TSC 과정의 작업 개수는 최대 6개까지만 분할되어 있기에 이 작업을 좀 더 쪼개 자원을 100% 사용할 수 있도록 개선해야한다.

 단순하게 작업을 쪼개기만 하면 되는 문제이기에 아마 간단하게 해결 될 것이라고 예상하고있다.

결론

 이번 작업을 통해 Jenkins 빌드 머신에서 워커 개수를 증가시키고 작업 분산 방식을 최적화하여 빌드 시간을 유의미하게 줄일 수 있었다. 최종적으로 워커개수를 4개에서 8개로 늘렸고, 작업 분산 방식을 개선하여 안정적인 성능 향상을 이루었다. 앞으로도 빌더 관련하여 이런 느낌의 작업들을 통해 더욱 최적화를 진행할 예정이다.

'aws' 카테고리의 다른 글

[AWS] 고성능 아키텍처  (0) 2024.08.10
[AWS]복원성 아키텍쳐  (0) 2024.08.06
[AWS]데이터 유입, 변환, 분석  (0) 2024.08.04
[AWS] DNS와 CDN: Route 53과 CloudFront  (0) 2024.08.04
[AWS]데이터 유입, 변환, 분석  (0) 2024.08.01