실패한 NGINX Plus 업그레이드 복구: '모듈 "M" 버전이 Y가 아닌 X임'

NGINX | 2017년 3월 14일

동적 모듈을 사용 중인 경우, NGINX 또는 NGINX Plus의 새 릴리스로 업그레이드하는 동안 다음과 같은 오류가 표시될 수 있습니다:

Setting up nginx-plus (1.11.10-1~xenial) ...
nginx: [emerg] module "/etc/nginx/modules/ngx_http_geoip_module.so" version 1011005 instead of 1011006 in /etc/nginx/nginx.conf:7

nginx: configuration file /etc/nginx/nginx.conf test failed

invoke-rc.d: initscript nginx, action "upgrade" failed.

가장 가능성이 높은 원인은 지정된 동적 모듈(.so 파일)을 업그레이드하지 않았기 때문입니다:

  • NGINX Open Source를 실행 중인 경우, 동적 모듈은 업그레이드하려는 버전에 맞게 컴파일해야 합니다.
  • NGINX Plus를 실행 중인 경우 동적 모듈은 업그레이드하려는 NGINX Plus 릴리스에 해당하는 NGINX Open Source 버전을 기준으로 컴파일해야 합니다.

이제부터는 간결하게 NGINX Plus로만 지칭하겠습니다.

당황하지 마세요!

이 오류 메시지가 NGINX Plus 서버의 중단을 의미하는 것은 아니므로 안심하셔도 됩니다. NGINX Plus는 서비스 중단 없이 업그레이드되므로 업그레이드에 실패해도 이전 버전이 계속 실행됩니다. 하지만 업그레이드가 완료되지 않아 시스템이 일관되지 않은 상태에 놓이게 됩니다:

  • 메모리에서 실행 중인 NGINX Plus 프로세스는 이전 버전을 사용하고 있습니다
  • 디스크에 있는 NGINX Plus 관련 파일은 모두 새 버전에 해당합니다
  • 오류 메시지에 언급된 동적 모듈은 이전 버전을 기준으로 컴파일되었습니다.

수동으로 nginx를 다시 시작하거나 시스템을 재부팅하지 마십시오. 새 NGINX Plus 릴리스와 호환되지 않는 동적 모듈이 있으면 새 NGINX Plus 프로세스를 시작할 수 없으므로, 이렇게 하면 서비스 중단이 발생합니다.

오류 메시지는 업그레이드 과정에서 발견된 첫 번째 비호환 모듈에만 해당하므로, 구성에서 모든 load_module 지시문을 찾아 각 모듈이 적절한 NGINX 버전에 맞게 컴파일되었는지 확인해야 합니다. 모든 NGINX에서 개발한 동적 모듈 및 인증된 타사 동적 모듈의 올바른 버전은 각 NGINX Plus 릴리스에 맞게 제공되므로<, 인증되지 않은 모듈만 다시 컴파일하면 됩니다.이 문서에서는 업그레이드 과정을 안전하게 완료하는 방법을 설명합니다.

무엇이 잘못되었나요?

NGINX 1.11.5와 NGINX Plus R11에서는 NGINX Open Source를 기반으로 동적 모듈을 컴파일하여 NGINX Plus에 로드할 수 있는 기능이 도입되었습니다. 이러한 바이너리 호환성을 유지하려면 모듈과 NGINX Plus가 동일한 기반 오픈 소스 버전을 사용해야 합니다. 해당 NGINX Open Source 버전을 기반으로 빌드된 동적 모듈을 먼저 설치하지 않고 NGINX Plus를 업그레이드하면 버전 불일치로 인해 업그레이드에 실패합니다.

동적 모듈을 타사 공급업체로부터 제공받은 경우, 업그레이드하려는 NGINX Plus 릴리스의 NGINX 버전에 맞는 새 버전을 공급업체에 요청해야 합니다. 동적 모듈을 소스에서 컴파일했고 해당 소스에 액세스할 수 있다면 계속 읽으십시오.

복구를 위한 여정

0단계: 빌드 환경 준비

동적 모듈은 별도의 시스템에서 컴파일할 것을 강력히 권장합니다. 여기서는 이 시스템을 “빌드 환경”이라고 합니다. 이렇게 하면 동적 모듈과 함께 NGINX Plus를 실행하는 시스템(여기서는 “프로덕션 환경”이라고 함)의 위험과 복잡성을 최소화할 수 있습니다. 빌드 환경의 운영 체제 및 버전은 프로덕션 환경과 동일해야 합니다. 또한 다음 구성 요소가 설치되어 있어야 합니다.

  • UnZip 유틸리티
  • 컴파일러 및 make 유틸리티
  • Perl 호환 정규식 라이브러리(개발 파일)
  • Zlib 압축 라이브러리(개발 파일)

빌드 환경에 이러한 필수 구성 요소가 설치되어 있는지 확인하려면 다음 명령을 실행하세요.

  • Ubuntu/Debian의 경우:
buildenv$ sudo apt-get install unzip gcc make libpcre3-dev zlib1g-dev
  • CentOS/RHEL/Oracle Linux의 경우:
buildenv$ sudo yum install unzip gcc make pcre-devel zlib-devel

1단계: NGINX Open Source 다운로드

  1. 프로덕션 환경에서 다음 명령을 실행하여 현재 실행 중인 NGINX Plus 릴리스에 해당하는 NGINX Open Source 버전을 확인합니다. 이 출력에서는 주황색으로 강조되어 있습니다. NGINX 1.11.10은 NGINX Plus R12에 해당합니다.
production$ nginx -vnginx version: nginx/1.11.10 (nginx-plus-r12)
  1. 빌드 환경에서 작업하면서 적절한 NGINX Open Source 버전의 소스 코드를 다운로드합니다.
build-env$ wget -qO - http://nginx.org/download/nginx-1.11.10.tar.gz | tar zxfv -

2단계: 동적 모듈 소스 코드 가져오기

동적 모듈의 소스 코드를 원하는 빌드 디렉터리에 복사합니다. 여기서는 GitHub 리포지토리에서 NGINX “hello world” 샘플 모듈을 복사합니다.

buildenv$ git clone https://github.com/perusio/nginx-hello-world-module.git
Cloning into 'nginx-hello-world-module'...

3단계: 동적 모듈 컴파일

  1. 동적 모듈을 컴파일하려면 먼저 NGINX configure 스크립트를 --with-compat 인수와 함께 실행하여 동적 모듈이 NGINX Plus와 바이너리 호환되도록 합니다. 그런 다음 make modules를 실행하여 해당 모듈만 컴파일합니다.
buildenv$ cd nginx-1.11.10/buildenv$ ./configure --with-compat --add-dynamic-module=../nginx-hello-world-module
buildenv$ make modules
  1. 빌드 프로세스에서 동적 모듈이 .so 파일로 objs 하위 디렉터리에 생성되었는지 확인합니다.
buildenv$ ls objs/*.soobjs/ngx_http_hello_world.so
  1. 파일 이름에 NGINX Open Source 버전을 포함하여 모듈 파일의 복사본을 만듭니다. 이렇게 하면 프로덕션 환경에서 여러 버전의 동적 모듈을 더 쉽게 관리할 수 있습니다.
buildenv$ cp objs/ngx_http_hello_world.so ./ngx_http_hello_world_1.11.10.so

4단계: 동적 모듈을 프로덕션 환경에 복사

동적 모듈의 파일 이름에 NGINX Open Source 버전을 포함했으므로, 운영에 영향을 주지 않고 프로덕션 환경에 안전하게 복사할 수 있습니다.

buildenv$ scp ./ngx_http_hello_world_1.11.10.so production:/etc/nginx/modules

5단계: 동적 모듈 교체

프로덕션 환경에서 작업하면서 새 .so 파일로 현재 파일을 교체합니다. 동적 모듈은 nginx가 다시 시작되거나 구성이 다시 로드될 때만 메모리에 로드되므로, 이 시점에 교체해도 안전합니다.

production$ cd /etc/nginx/modulesproduction$ cp ngx_http_hello_world.so ngx_http_hello_world_ROLLBACK.so
production$ ln -fs ngx_http_hello_world_1.11.10.so ngx_http_hello_world.so
production$ ls -gG
-rw-r--r-- 1 243576 Jan 31 16:18 ngx_http_hello_world_1.11.10.so
-rw-r--r-- 1 243576 Oct 20 10:40 ngx_http_hello_world_ROLLBACK.so
lrwxrwxrwx 1     24 Jan 31 16:26 ngx_http_hello_world.so -> ngx_http_hello_world_1.11.10.so

6단계: NGINX Plus 업그레이드 완료

  1. 다음 명령을 실행하여 모듈 버전이 올바른지, NGINX Plus가 업그레이드 프로세스를 완료할 준비가 되었는지 확인합니다.
production$ nginx -tnginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful
  1. 업그레이드 프로세스를 완료하여 NGINX Plus가 새 릴리스와 동적 모듈을 사용하도록 합니다.
production$ service nginx upgradeStarting new master nginx:                                 [  OK  ]
Graceful shutdown of old nginx:                            [  OK  ]

업그레이드 실패 방지

다음에 NGINX Plus를 업그레이드할 때는 업그레이드 전에 이 지침을 따르면 업그레이드 프로세스를 시작할 때 업데이트된 동적 모듈을 바로 사용할 수 있으므로 시간을 절약하고 오류를 방지할 수 있습니다.


공유

작성자 소개

관련 블로그 게시물

시청하기: KubeCon North America 2023에서의 NGINX Gateway Fabric
NGINX | 2023. 11. 30.

시청하기: KubeCon North America 2023에서의 NGINX Gateway Fabric

이 영상에서는 KubeCon의 NGINX 부스를 찾아가, 저희가 공개한 Kubernetes Gateway API 구현을 살펴봅니다.

F5 NGINX로 대규모 WAF 플릿을 확인하고 관리하는 2가지 방법
NGINX | 2023. 03. 23.

F5 NGINX로 대규모 WAF 플릿을 확인하고 관리하는 2가지 방법

앱 보안을 강화하는 두 가지 방법을 소개합니다. NGINX Management Suite를 통해 WAF 운영에 대한 가시성을 높이고, NGINX App Protect WAF를 활용해 코드형 보안을 구현하는 것입니다.

Ingress 컨트롤러 선택 가이드, 4부: NGINX Ingress Controller 옵션
NGINX | 2021. 09. 27.

Ingress 컨트롤러 선택 가이드, 4부: NGINX Ingress Controller 옵션

개발 주체, 개발 철학, 프로덕션 환경 준비도, 보안 및 지원을 기준으로 어떤 NGINX Ingress 컨트롤러가 가장 적합한지 알아보세요.

진화하는 공격 환경에 NGINX App Protect Denial of Service가 적응하는 방법
NGINX | 2021. 07. 06.

진화하는 공격 환경에 NGINX App Protect Denial of Service가 적응하는 방법

NGINX App Protect Denial of Service(DoS)가 계층 7 DoS 공격을 방어하기 위해 완화 방법을 실시간으로 조정하는 방식을 설명합니다. 정상적인 사용자 행동과 서버 상태에 대한 모델을 생성하여 공격을 나타내는 이상 징후를 감지하고 맞춤형 완화 시그니처를 적용할 수 있습니다.

NGINX Instance Manager를 활용한 대규모 구성 업데이트 및 인증서 관리
NGINX | 2021. 06. 30.

NGINX Instance Manager를 활용한 대규모 구성 업데이트 및 인증서 관리

NGINX Instance Manager 버전 1.0에는 두 가지 새로운 기능이 도입되었습니다. NGINX 인스턴스에 태그와 사용자 역할을 지정하면 전체 그룹에 구성을 한 번에 적용할 수 있습니다. 인증서 검사는 만료 예정인 인증서를 감지하여 서비스 중단을 방지할 수 있도록 인증서를 교체할 수 있게 해줍니다.

Netflix가 자사 CDN의 핵심으로 NGINX를 선택한 이유
NGINX | 2015. 03. 25.

Netflix가 자사 CDN의 핵심으로 NGINX를 선택한 이유

Netflix가 글로벌 콘텐츠 전송 네트워크인 Open Connect의 스트리밍 미디어 기술로 NGINX를 선택한 이유를 NGINX 개발자 Gleb Smirnoff에게서 알아보세요.