🍃 Spring

Spring AOT(Ahead-Of-Time) 경험 이야기

loose 2023. 3. 11. 04:00
반응형

Spring 6.0 AOT 지원

Spring 6.0.0, Spring Boot 3.0을 맞아 Spring AOT에 대한 전폭적인 지지를 할 것으로 보입니다.

AOT에 대한 내용은 그리 어렵지 않습니다.

그냥 어플리케이션 시작 시간을 빠르게 하는 기술이라고 합니다.

기존의 JVM 방식에서는 프로그램이 올라갈 때 바이트 코드를 컴파일하지만 AOT는 '네이티브 이미지'라는 것을 미리 만들어서 미리 컴파일 할 수 있도록 해주는 기능을 제공합니다.

더불어 메모리 사용량도 줄여 경량화 애플리케이션을 구축하는 데 도움을 준다고 합니다.

 

사용 방법

일단 Spring AOT를 이용하려면 JVM이 아닌 GraalVM을 사용해야합니다.

 

Release GraalVM Community Edition 22.3.1 · graalvm/graalvm-ce-builds

GraalVM is a high-performance Java Development Kit based on OpenJDK and provides the Native Image feature for ahead-of-time compilation. It also supports the execution of JavaScript, LLVM bitcode, ...

github.com

그리고 기존에 JVM 경로로부터 다운받은 GraalVM으로 전부 바꿔줘야합니다.

인텔리제이 내에 JDK 설정도 전부 바꿔줘야합니다.

그리고 gradle 설정에

graalvm에 관한 Plugin을 하나 추가해주면 끝인 듯 합니다.(아마도?)

 

실행 시간 테스트

이제 실행 시간을 테스트 해볼 시간입니다.

기존에 프로젝트 실행 시간이 오래 걸리는 애플리케이션이 없어서 올바른 예시가 될지는 모르겠으나 클래스 객체를 1억개 만드는 방식의 코드를 구현했습니다.

그리고 실행해봤습니다.

약 3.353초가 걸렸네요.

비교를 위해 기존의 JVM과 비교를 해봤습니다.

JVM GraalVM
2.958 3.356
2.991 3.389
2.977 3.375
3.045 3.317
3.031 3.302
3.223 3.429
2.994 3.401

결과는 GraalVM이 더 느렸습니다.

감사하게도 아래 댓글 달린 분의 말씀에 의해 원인을 찾아보니 제가 GraalVM의 Native Image 기능을 이용하지 않았기 때문인데요.

Native Image 기능을 이용하려면 아래 nativeCompile을 하여 생성된 Native Image를 실행해야 합니다.

그렇다면 왜 Native Image 기능을 이용하지 않았을 때 GraalVM이 더 느린걸까 찾아본 결과 추측된 원인으로는 GraalVM은 Execution Engine에서 JVM과 다르게 Interpreter를 사용하지 않는다고 합니다. JIT Compiler와 GraalVM에서 만든 컴파일러를 사용하여 컴파일 및 캐시, 최적화 작업에 들어갑니다. Execution Engine에 Compiler와 Interpreter에 관한 내용은 JVM Warmup 글에 좀 자세하게 적어놨습니다.

요약하자면 JIT Compiler는 최적화 기능이 존재해 초기에는 느리지만 추후에는 빠른 속도를 보장한다는 특징이 존재하고 Interpreter는 최적화 같은 기능은 없지만 초기 속도가 가장 빠르다는 특징이 존재합니다. 그렇기에 Interpreter가 존재하지 않는 GraalVM의 특징으로 인해 느린게 아닐까 생각해봅니다.

 

Windows에서 Native Image 이용하기 실패

 

우선은 Native Compile을 하기 위한 조건이 굉장히 많았습니다. 

기존에 JVM은 JAVA_HOME 환경 변수만 추가하면 되었지만 GraalVM은 PATH 환경 변수를 추가해서 VM의 bin폴더를 잡아줘야 합니다.

Insufficient privileges for administration of the GraalVM installation. You need to become "BUILTIN\Administrators" user to perform administrative tasks on GraalVM.

그리고 해당 vm 폴더 접근 권한을 설정해줘야하구요.

 

Default native-compiler executable 'cl.exe' not found via environment variable PATH

위 에러가 뜬다면 리눅스라면 SDKMAN를 설치하거나 윈도우라면 Visual Studio나 Windows SDK가 필수적으로 필요합니다.

제가 테스트 해본 환경은 Windows 여서 Windows SDK를 설치했습니다.

그리고 설치가 완료되면 대개 아래와 같은 경로에 cl.exe 파일이 생기는데 

C:\Program Files (x86)\Microsoft Visual Studio\2019\Community\VC\Tools\MSVC\14.27.29110\bin\Hostx64\x64

위의 경로도 PATH 환경 변수에 추가해서 사용해야합니다.

 

그리고 아래와 같은 에러를 마주쳤는데,

Error: Native-image building on Windows currently only supports target architecture: AMD64 ((x64) unsupported)

대개 윈도우 환경에서 영어가 아닌 언어의 컴퓨터에서 종종 발생하는 것 같습니다.

 

Error: Native-image building on Windows currently only supports target architecture: AMD64 (?? unsupported) · Issue #3122 · or

Describe the issue [INFO] [io.quarkus.deployment.pkg.steps.NativeImageBuildStep] Running Quarkus native-image plugin on GraalVM Version 20.3.0 (Java Version 11.0.9+10-jvmci-20.3-b06) [INFO] [io.qua...

github.com

-H:-CheckToolchain 옵션을 주면 해결이 된다고 하는데, 해당 정보가 아직은 모자란 것 같아서 여기서 꽉 막히더군요. 역시 좀 레퍼런스가 있고 영어 환경인 리눅스 환경에서 추후에 다시 해봐야겠습니다. 아니면 Windows 환경에서도 충분한 가이드라인이나 관련 자료가 존재한다면 다시 해봐야겠습니다.

728x90