개념: MVEL 기초
구문
MVEL은 Java 기반 어플리케이션을 위한 표현식 언어입니다. 구문은 Java와 유사하지만 더 효율적인 콘텐츠 매칭을 위한 몇 가지 추가 기능이 있습니다.
참고:
- MVEL은 Java 네임스페이스 및 클래스를 사용하지만 둘 다 자체적으로 선언할 수는 없습니다.
- Java와 달리 MVEL은 동적으로 입력되며 옵션 입력이 지원됩니다.
- MVEL 표현식은 단일 문 또는 여러 줄의 스크립트일 수 있습니다. 여러 줄 스크립트의 경우 세미콜론을 사용하여 각 문을 구분합니다.
- MVEL은 최종 값 출력의 원칙에 따라 작동합니다. 다음을 지원합니다.return키워드이지만 일반적으로 필요하지 않습니다.
- MVEL은 연산자 우선순위 규칙을 지원하며 괄호를 사용하여 실행 순서를 제어합니다.
- MVEL 문자열 리터럴을 작은따옴표 또는 큰따옴표로 묶을 수 있습니다.
- 세미콜론은 MVEL의 예약된 문자입니다. 표현식에서는 사용할 수 없습니다. 사용(char) 59대신 예:props['string']='a;b'오류가 발생합니다. 이 코드는 다음을 수행하지 않습니다.props['string']= (char) 59 props['string_new']='a'props['string']'b'
MVEL 표현식에는 다음이 포함될 수 있습니다.
- 부울 표현식
- 메서드 호출
- 속성 표현식
- 변수 지정내역
간단한 MVEL 속성 표현식의 예는 다음과 같습니다.
context.errorMessage
속성을 추출합니다.
errorMessage
변수 또는 컨텍스트 오브젝트에서 context
.MVEL은 일반적인 Java 비교, 수학 및 논리 연산자를 모두 지원합니다. 다음 표에는 기타 주요 MVEL 연산자가 요약되어 있습니다.
연산자 | 설명 | 예 |
|---|---|---|
new
| 오브젝트를 인스턴스화합니다. | new String("foo")
|
with
| 단일 오브젝트 인스턴스에서 여러 작업을 수행합니다. | with (value) { name = 'Foo', age = 50, sex = Sex.MALE }
|
assert
| 값이 true이거나 실패하면 AssertionError를 표시합니다. | assert foo != null
|
contains
| 왼쪽 값이 오른쪽 값을 포함하는지 여부를 결정합니다. | var contains "Foo"
|
is 또는 instance of
| 왼쪽에 있는 값이 오른쪽에 있는 클래스의 구성원인지 여부를 확인합니다. | var instanceof String
|
strsim
| 문자열을 비교하여 유사도를 백분율로 반환합니다. | "foobol" strsim "foobar"
|
soundslike
| 두 문자열 간에 SOUNDEX 비교를 수행합니다. | "foobar" soundslike "fubar"
|
&
| 비트 AND 연산을 수행합니다. | foo & 5
|
|
| 비트 OR 연산을 수행합니다. | foo | 5
|
^
| 비트 단위 XOR 연산을 수행합니다. | foo ^ 5
|
+
| 2개의 문자열을 연결하기 위한 오버로드된 연산자입니다. | "foo" + "bar"
|
#
| 2개의 리터럴을 문자열로 연결합니다. | 8 # 9
|
in
| 컬렉션 내의 오브젝트를 검사합니다. | (foo in list)
|
=
| 변수에 값을 지정합니다. | var = "foobar"
|
가치 테스트
Java에서 연산자는
==
참조가 동일한 오브젝트를 가리키는지 확인합니다. 그러나 MVEL에서 비교 연산자는 ==
값이 같은지 확인합니다. MVEL 표현식 foo == 'bar'
은 Java의 foo.equals("bar")
.MVEL 부울 표현식의 예는 다음과 같습니다.
user.name == 'John Smith'
다음을 반환합니다.
true
다음과 같은 경우 name
변수 또는 컨텍스트 오브젝트의 속성 user
John Smith입니다.MVEL은 유형 강제변환을 사용합니다. 서로 다른 유형의 값 2개를 비교하는 경우 오른쪽의 값이 왼쪽의 유형으로 강제 변환됩니다. 그렇게 할 수 없는 경우 왼쪽의 값이 오른쪽의 유형으로 강제 변환됩니다. 예를 들어 다음과 같습니다.
"123" == 123;
이 표현식은 다음을 반환합니다.
true
MVEL은 비교를 수행하기 전에 오른쪽의 값을 문자열로 강제 변환하기 때문입니다.목록, 맵 및 배열
MVEL 목록을 대괄호로 묶습니다. 항목을 쉼표로 구분합니다. 예를 들어 다음과 같습니다.
["Paris", "London", "Berlin"]
MVEL 맵을 대괄호로 묶습니다. 키와 값을 콜론으로 구분합니다. 예를 들어 다음과 같습니다.
["Foo" : "Bar", "Bar" : "Foo"]
MVEL 배열은 중괄호로 묶습니다. 항목을 쉼표로 구분합니다. 예를 들어 다음과 같습니다.
{"Bill", "Bob", "Ben"}
속성 탐색
MVEL은 속성, 정적 필드, 목록, 맵 및 배열에 액세스하는 데 사용되는 단일 통합 구문을 제공합니다.
Java에서는 다음 문을 사용하여 오브젝트의 속성에 액세스할 수 있습니다.
context.getException().getCause()
MVEL에서는 다음 표현식을 사용하여 동일한 속성에 액세스할 수 있습니다.
context.exception.cause
동일한 방식으로 목록과 배열에 액세스합니다. 예를 들어 다음과 같습니다.
parts[2]
배열과 동일한 방식으로 맵에 액세스하지만 모든 오브젝트를 인덱스 값으로 전달할 수 있습니다. 예를 들어 다음과 같습니다.
props["foobar"]
맵에서 문자열을 키로 사용하는 경우 맵 자체를 가상 오브젝트로 처리할 수 있습니다. 예를 들어 다음과 같습니다.
props.foobar
MVEL은 인덱싱을 위해 문자열을 배열로 처리합니다.
이 예에서는 다음을 반환합니다.
B
:foo = "Berlin"; foo[0];
지정내역
표현식 내에서 사용하거나 런타임 시 추출하기 위해 MVEL 표현식에 변수를 지정할 수 있습니다.
MVEL은 동적으로 입력되는 언어이므로 새 변수를 선언할 때 유형을 지정할 필요가 없습니다. 하지만 지정할 수도 있습니다.
다음 두 예는 모두 MVEL에서 유효합니다.
str = "Some string"; String str = "Some string";
유형이 지정된 변수에 값을 지정할 때 MVEL은 자동 유형 변환을 수행하려고 시도합니다. 예를 들어 다음과 같습니다.
String num = 1;
동적으로 입력된 변수의 값을 다른 유형으로 캐스트할 수 있습니다. 예를 들어 다음과 같습니다.
String num = 1;
섹션: 입력 및 강제 변환
MVEL은 옵션 정적 입력과 함께 동적 입력을 사용합니다. 네이티브 Java 오브젝트는 정적으로 입력됩니다. 이와 상호 작용하기 위해 MVEL이 유형 강제 변환을 수행해야 하는 경우가 있으며, 이는 성능에 영향을 미칠 수 있습니다.
MVEL은 현재 값에 가장 적합한 유형으로 자동 강제 변환을 수행합니다. 즉, 숫자로 작업할 때는 주의해야 합니다. MVEL이 무한 정밀도에서 자동으로 캐스트되기 때문에 부동 소수점 산술에서 오류가 발생할 수 있습니다.
java.math.BigDecimal
대상 java.lang.Double
및 java.lang.Long
. 이로 인해 저장된 값의 유형이 예상과 다른 경우 문제가 발생할 수 있습니다. 일반적으로 MVEL에서는 재무 값으로 정수가 아닌 산술을 수행하지 않아야 합니다.MVEL의 유형 강제 변환으로 인해 입력을 조정하지 않고도 Java 메서드를 호출할 수 있습니다. 인터프리터 또는 컴파일러는 메서드에 전달되는 유형을 분석하고 필요한 강제 변환을 결정합니다.
배열 유형이 충돌하는 경우 전체 배열이 필요한 입력 유형으로 강제 변환됩니다.
지정된 값을 강제 변환할 수 있는 경우, 정적으로 입력된 변수에 대해 필요한 모든 강제 변환이 수행됩니다. 그렇지 않은 경우 예외가 발생합니다.