티스토리 뷰
발생일: 2016.07.14
키워드: nginx, ssi, 중첩 if 문, multiple condition, server side include
문제:
nginx 의 SSI에서 중첩으로 if 구문을 넣으려고 한다.
아래처럼 넣어봤는데 잘 되지 않는다.
<!--# if expr="$name = foo" -->
<!--# if expr="$address = bar" -->
...
<!--# endif -->
<!-- # endif -->
이상하다. 아래처럼 && 연산자로 추가해봤는데도 잘 되지 않는다.
<!--#if expr="$name = foo && $address = bar" -->
...
<!-- #endif -->
여러 방법으로 테스트해봤는데,
어떤 경우엔 [an error occurred while processing the directive] 와 같이 구문 오류라고 나오고,
어떤 경우엔 바깐 if 문을 타는 등 의도치 않게 동작한다.
왜 그럴까?
해결책:
nginx SSI 모듈 API에 따르면 if 구문은 1뎁스만 가능하다고 한다.
> Only one level of nesting is currently supported. The command has the following parameter:
좀 지저분하긴 하지만, 변수에 두 조건의 값을 할당해 비교하는 방식으로 우회할 수 있다.
<!--# set var="name_and_address" value="${name}_${address}" -->
<!--# if expr="$name_and_address = foo_bar" -->
...
<!--# endif -->
논의:
- 어떤 튜토리얼에서는 SSI에 중첩 if 문이나 &&, || 연산자를 사용할 수 있다고 하지만, 이 튜토리얼은 Apache 의 SSI 설명이다.
nginx 에서는 제공하지 않는 것에 주의한다.
- 필요한 경우, 아래와 같이 정규식을 사용하면 좀 더 유연하게 처리할 수 있다.
<!--# if expr="$name_and_address = /.+_.+/" -->
- 테스트했던 버전은 nginx 1.4 버전이었는데, 중첩으로 정의하는 경우 구문 오류 대신 암묵적으로 다음 조건으로 넘어가는 이슈가 있었다.
아래 테스트에서 (A)에 매칭되지 않은 경우 종료되어야 하지만 (B)가 실행됨
<!--# if expr="$name = foo" -->
<!--# if expr="$address = bar" --> (A)
...
<!--# endif -->
<!--# else -->
... (B)
<!-- # endif -->
- 어이없이 시간을 까먹었던 건, var 디렉티브에서 선언한 변수를 $ 없이 사용한 것 때문이었다.
<!-- set var="name_and_address" value="${name}_${address}" -->
<!--# if expr="name_and_address = foo_bar" --> // $name_and_adress 로 작성했어야 함
- nginx 의 location 블럭 내 if 디렉티브도 동작 방식은 동일하다.
조건에 따라 변수를 할당하고 최종적으로 만들어진 변수의 값을 비교하는 방법으로 우회할 수 있다.
참고:
반응형
댓글
공지사항