언어
Python
StackOverflow 질문 수: 2213927
사용 기업
클라썸
슈퍼브에이아이
엔라이튼
토스랩
큐피스트
핀다
드라마앤컴퍼니
딜리셔스
파운트
뤼이드
직방
에이블리
플렉스
식스샵
드림어스컴퍼니
숨고
스푼
바로고
더 보기
SK텔레콤
[Python] C Library 이용해서 성능 높이기(SIMD + 병렬처리, 3편)
이번 포스팅은 [Python] C Library 이용해서 성능 높이기(Ctypes+Numpy, 2편) 의 후속 포스팅으로 찾아왔습니다!지난번 포스팅에서 Ctypes와 Numpy + SIMD, openMP를 다 써봅시다! 라고 했었는데요해당 내용을 이번 포스팅에서 다뤄볼 예정입니다!이번 포스팅에서는.를 다뤄볼 생각 입니다.C에서 Thread를 사용할 경우pthread 혹은 C++의 Thread모듈을 사용하게 됩니다.다행히도 Python에서 사용하는 Thread와 유사한 사용 패턴을 제공합니다.Thread를 만들면서 해당 Thread에서 실행할 함수를 제공하고다시 Thread를 Join시켜서 분리된 작업을 마무리 시킵니다.이때 malloc을 이용해서 memory를 확보하고, 이 메모리 주소 기반으로 Thread마다 나눠서 데이터를 처리하는것이 가능합니다.openmp는 예전에도 잠깐 나왔었지만C++에서 컴파일러 한태 자동으로 해당 구문을 병렬처리하라 라고 알려주는 기능 입니다.를 통해서 활용이 가능하며최신 gcc나 msvc컴파일러에서 바로 활용이 가능합니다.여러가지 활용 방법이 있지만이번 포스팅에서는 단순하게 embrassingly parallel을 위한 만 적용할 예정입니다.아래는 그 예시코드입니다.하나의 명령어로 2개 이상의 Data를 한번에 처리할 수 있는 처리 방법을 의미합니다.단순하게 함수로 묶어서 코드한줄에 두개의 Data를 처리하는것이 아니라CPU명령어 Level에서 한번에 256, 512bit의 Data를 한번에 계산할 수가 있습니다.기본적으로 와 를 이용해서 256bit SIMD연산이 가능합니다.저는 이번에 SIMD Array Add연산을 통해서 성능비교를 해볼 예정입니다.256bit SIMD Add를 통해서 Data를 계산하는 방법은 아래를 참고해주세요!이제 위 기술들을 조합해봐야겠죠?위에서 각자 적용하는 것은 해 보았으니SIMD와 병렬처리를 조합한 코드를 간단히 보고 넘어가겠습니다.Thread한태 malloc을 통해서 할당받은 pointer를 넘겨주고해당 pointer를 thread job내부에서 typecasting을 통해서 계산하는 구조를 가지고 있습니다.그럼 이번에 OpenMP를 사용한 경우를 보실까요?OpenMP를 사용할 경우, 위처럼 편리하게 반복문을 병렬화 시켜서 계산 할 수가 있습니다.최종 벤치마킹을 위해 사용된 C함수들의 소스코드 입니다.먼저 Data를 증가시켜 가면서 테스트 했을 때 C Thread를 사용하면서 발생하는 오버헤드는 크지 않은것 같습니다.덕분에 Python내부에서 multi-core를 활용하여 빠른 연산이 가능했습니다.그리고, SIMD를 사용한 효과를 생각보다 크지 않았습니다.결국 numpy c-api를 이용할 경우 GIL을 벗어난 multi-core활용이 가장 큰 이점이라고 할 수 있습니다.• None numpy에서 넘겨받은 Array를 바로 쓸 수 있는 장점을 극대화할 수 있다.• None OMP의 경우 element를 partition없이 반복문 처리하는것은 비효율적이다.• None SI
python
스푼
로컬 환경에서 Molecule + Docker 활용한 Ansible Role 단위 테스트하기
안녕하세요, 스푼라디오 SRE 팀에서 DevOps 업무를 맡고 있는 백영진(Paul)입니다. 지난 5년 간, 저희 팀은 AWS의 Multi-Account Multi-Region 환경에서 서비스의 안정성과 확장성을 보장하기 위해 Ansible을 활용한 인프라 자동화 및 CI/CD 배포 시스템을 구축하였습니다. 또한 다양한 운영 체제(AmazonLinux, Ubuntu) 환경에서 Ansible Role을 검증하기 위해 Vagrant & VirtualBox를 사용하여 로컬 환경에서 테스트를 수행해왔습니다. 그러나 Mac M1 기기에서는 Vagrant & VirtualBox 실행에 문제가 있었습니다. 이 문제를 해결하기 위해 Molecule이라는 도구와 Docker 활용해서 Ansible Roles를 테스트 방법에 대해 설명을 하겠습니다.1.Molecule 란 무엇인가?Ansible Molecule은 다양한 시나리오를 기반으로 Ansible Role을 테스트할 수 있는 프레임워크로, 현재 Ansible/Red Hat에 의해 유지 관리되고 있습니다. Molecule은 Docker, Vagrant, EC2, Azure, OpenStack, Podman 등 다양한 드라이버를 제공하여 테스트 환경을 구성할 수 있게 해줍니다. 또한 Ansible Molecule는 지속적 통합(Continuous Integration)를 통해 Ansible Role에 변경이 생길 때마다 테스트 프로세스를 자동화하여 지속적인 테스트를 수행할 수 있습니다.2. Molecule 테스트 환경 구성하기Molecule 테스트를 위해 Docker 컨테이너 환경을 구성하였습니다. 또한, Docker-In-Docker (DinD) 기술을 활용하여, 다양한 운영 체제 환경에서 Ansible Role을 테스트할 수 있도록 환경을 구성 하였습니다. 아래의 Dockerfile을 참고해 주시기 바랍니다.# Python 3.10을 기본 이미지로 설정FROM python:3.10# 필수 패키지 업데이트 및 설치RUN apt-get update && \ apt-get install -y git sudo curl && \ apt-get clean && \ rm -rf /var/lib/apt/lists/*# Docker 설치(DinD)RUN curl -fsSL https://get.docker.com -o get-docker.sh && \ sh get-docker.sh && \ rm get-docker.sh# Ansible 및 Molecule 설치RUN pip install --no-cache-dir ansible molecule docker pytest testinfraRUN python3.10 -m pip install -U "molecule-plugins[docker]"Molecule 실행하기 위해서는 Python 3.10 버전 이상이 필요합니다. Docker-In-Docker를 위해서 Docker 설치 하였고, Molecule 드라이버를 Docker 로 설정하기 위해서 플러그인을 설치 및 검증을 위해 pytest, testinfra 패키지를 설치 하였습니다. Molecule 컨테이너 실행하기 위해서 Docker Compose로 구성하였고, Yaml 파일은 아래와 같습니다.version: '3'services: moleclue: container_name: moleclue build: context: . dockerfile: ./Dockerfile volumes: - "./:/workspace" - "/var/run/docker.sock:/var/run/docker.sock" # (DinD) tty: true로컬 PC에서 Docker Desktop을 이미 설치했다고 가정하고 진행하겠습니다. GitHub에서 데모 프로젝트를 클론 합니다. 데모 프로젝트에는 테스트를 위한 간단한 Ansible Role과 Molecule 환경을 구성 및 실행하기 위한 파일로 구성되어 있습니다.# github clonevagrant@molecule:~$ git clone https://github.com/baiyongzhen/molecule-demoCloning into 'molecule-demo'...remote: Enumerating objects: 30, done.remote: Counting objects: 100% (30/30), done.remote: Compressing objects: 100% (23/23), done.remote: Total 30 (delta 0), reused 27 (delta 0), pack-reused 0Unpacking objects: 100% (30/30), 7.58 KiB | 369.00 KiB/s, done.vagrant@molecule:~$ lsmolecule-demovagrant@molecule:~$ cd molecule-demo/# Molecule 환경 실행vagrant@molecule:~/molecule-demo$ docker-compose up -d[+] Building 4.7s (3/8) => [internal] load .dockerignore 0.2s => => transferring context: 2B# docker ps 명령어를 통해서 컨테이너 실행 상태 확인vagrant@molecule:~/molecule-demo$ docker ps -aCONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES60180282c58d molecule-demo-moleclue "python3" 26 seconds ago Up 25 seconds moleclue# docker exec 명령어를 통해서 컨테이너 접속vagrant@molecule:~/molecule-demo$ docker exec -it 60180282c58d /bin/bash# workspace 폴더로 이동root@60180282c58d:/# cd workspace/root@60180282c58d:/workspace# lsDockerfile Vagrantfile bitbucket-runner docker-te
ansible
bitbucket
docker
github
python
SK텔레콤
AWS Lambda와 EventBridge로 누구보다 빠르게 멘사 테스트 신청하기
예전부터 문제적남자 같은 프로그램을 보면서 퀴즈 푸는 것을 아주 좋아했는데요.한번 멘사 시험에 도전해볼까? 라는 생각을 최근에 가지게 되었습니다. ㅎㅎ신청을 하려고 멘사코리아 홈페이지에 등록된 테스트 일정들을 확인해 봤는데,위처럼 테스트 일정이 굉장히 무작위로 열리는 것을 알 수 있습니다.때문에 몇 번의 신청 기간을 놓쳐버린 저는, AWS 서비스들을 사용해서 멘사 테스트 알람 스케줄러를 만들기로 결심합니다..ㅋㅋ먼저 알람 메일 발송을 위해 Amazon SES(Simple Email Service)를 구성합니다.SES는 이름 그대로 별도의 메일 서버 없이 간단하게 메일 발송을 도와주는 AWS 서비스 입니다.• None 'Amazon SES - 자격 증명' 에서 '자격 증명 생성' 을 클릭해줍니다.• None '이메일 주소'에 개인 이메일 주소를 입력하고 생성을 눌러줍니다.• None 처음 생성하면 상태가 '보류중'으로 뜨는데요, 입력한 메일 수신함에서 승인 링크를 클릭하면 '확인됨'으로 바뀌어 발신/수신 용도로 사용이 가능하게 됩니다.이어서 멘사테스트 페이지를 크롤링하고 메일 발송을 수행하는 코드를 실행할 Lambda를 구성합니다.Lambda는 간단한 코드를 서버리스로 실행할 수 있는 AWS 서비스 입니다.• None 'AWS Lambda - 함수' 에서 '함수 생성' 을 클릭해줍니다.• None 함수 이름을 작성하고 런타임을 선택한 뒤 '함수 생성' 을 클릭해줍니다. 저는 파이썬으로 크롤링 코드를 작성하였으므로, 런타임은 Python 3.12를 선택하였습니다.• None 아래와 같이 파이썬으로 멘사 테스트 크롤링 코드를 작성하였습니다. 1) 게시물 번호에 해당하는 태그(td.c.f_ver11)를 확인한 후, 가장 최신 게시물 번호를 추출 2) 해당 번호가 지정한 번호보다 클 경우, send_email() 실행• None 이대로 함수를 실행하면 'no module named' 에러가 발생합니다. Lambda 기본 패키지 라이브러리에 requests 등의 모듈이 없기 때문입니다. 로컬에서 관련 패키지를 다운로드&압축 한 뒤, Lambda Layer를 통해 패키지 압축 파일을 업로드 해주어야 합니다. pip -t 로 패키지를 다운로드한 후, 다운로드한 폴더를 python_lib.zip으로 압축해줍니다.• None 'Lambda - 계층 - 계층 생성' 으로 들어가서 방금 압축해준 python_lib.zip을 업로드해 줍니다.• None 이제 다시 'Labmda - 함수' 로 들어와서 이전에 만든 mensa-alarm 함수에 레이어를 추가해줍니다.• None 마지막으로 Lambda에서 send_email을 호출할 수 있도록 Lambda의 IAM Role에 AmazonSESFullAccess Policy를 추가해줍니다.• None 이제 Lambda 코드를 Deploy하고 테스트를 수행해보면, 아래와 같이 함수 실행에 성공함을 확인할 수 있습니다.• None 메일도 잘 발송되는지 테스트하기 위해 Lambda 코드의 마지막 게시물 번호를 210으로
python
SK텔레콤
[Python] Uvicorn에 대해서
이번 포스팅은 FastAPI에서 기본적으로 사용하는 WebServer인 Uvicorn의 workers가 어떤 의미를 갖는지 알아봅니다.그리고 일반적으로 알기 어려운 WebServer의 역할을 Python코드를 통해서 알아봅니다.일반적으로 Web서버의 구성은 아래처럼 구성 됩니다.Springboot같은 경우 Webserver의 역할을 Tomcat이나 Apache 서버가 해줍니다.하지만 Python같은 경우 Gunicorn이라는 패키지를 통해서 Client의 Requests를 받고, 이를 WAS(=Django, FastAPI Application)로 넘겨줍니다.그래서 이 Gunicorn의 위치는 WebServer와 WAS사이에서 위치하게 됩니다.WebServer, Middleware는 왜 쓰는건가요🤔?(Python기준) client가 보내는 reques message는 NIC를 거쳐서 윈도우 socket으로 넘어오게 됩니다. 이때 도착한 메세지를 python이 이해할 수 있는 형태로 바꿔주는 것을 WSGI(혹은 ASGI)가 담당해 줍니다. 이때 의문이 드는데, Flask와 같은 WAS친구들도 자체적으로 WSGI가 구현 되어 있어서 python run.py 형태로 서버를 실행할 수가 있습니다. 문제는 python run.py로 실행할 경우 Python은 GIL의 때문에 Thread를 사용해서 한순간에 여러 요청을 처리할 수 없습니다. 그러기 때문에 Multiprocessing을 사용 해야합니다. 이때 WAS마다 알아서 Multiprocessing을 적용하는 것이 아니라 middleware에서 해당 기능을 구현하여 WAS의 개발을 쉽게 해 준다 정도로 생각하면 되겠습니다. webServer의 경우 NIC로 전달된 사용자의 요청을 보다 효율적으로 처리하기 위해서 사용된다고 보시면 됩니다.Gunicorn같은 경우 Gevent는 비동기 라이브러리를 사용해서 해당 기능을 구현합니다.대신 Gunicorn의 경우 WSGI기반의 Application을 호스팅하기 때문에 Worker(=Process) 내에서 Concurrency를 구현하기 위해서 greenlet Thread를 사용합니다.덕분에 Gunicorn을 사용할 경우 비동기 함수 없이 Worker개수 이상의 Requests를 Concurrency로 처리할 수가 있습니다Uvicorn의 경우 FastAPI를 실행할때 필수적으로 사용됩니다.Gunicorn과는 다르게 Uvicorn은 ASGI 기반으로 동작합니다.이말즉 Uvicorn 내부에서는 Aysncio 기반으로 Concurrency를 구현합니다.실제 Uvicorn 내부에서는 asyncio.run을 통해서 비동기함수를 실행시킵니다.그렇기 때문에 Uvicorn같은 경우 Gunicorn과 다르게 thread를 설정하는 항목이 없죠.Gunicorn과 Uvicorn을 그림으로 비교해보면 아래처럼 이해하면 좋습니다.때문에 Gunicorn의 경우 Concurrency에 한계가 있지만, Uvicorn의 경우 비동기함수를 사용해서 별도의 Thread생성 없이 Concur
python