1前書き

Expression Language(EL)は、Spring with

SpEL

やJBoss with JBoss ELなど、多くのJavaフレームワークで採用されているスクリプト言語です。

この記事では、JSFによるこのスクリプト言語の実装 – Unified ELに焦点を当てます。

ELは現在バージョン3.0になっています。これは、処理エンジンをスタンドアロンモード(Java SEプラットフォームなど)で使用できるようにするためのメジャーアップグレードです。以前のバージョンは、JavaEE準拠のアプリケーションサーバーまたはWebコンテナに依存していました。この記事ではELバージョン2.2について説明します。


2即時評価および延期評価

JSFにおけるELの主な機能は、JSFビュー(通常はXHTMLマークアップ)とJavaベースのバックエンドを接続することです。バックエンドは、ユーザー作成のマネージドBean、またはHTTPセッションのようなコンテナ管理のオブジェクトにすることができます。

EL 2.2を見ます。 JSFのELには、直接構文ELと遅延構文ELの2つの一般形式があります。


2.1. 即時構文EL

JSP ELとも呼ばれるこのスクリプト形式は、Java Webアプリケーション開発のJSP時代からの影響を受けません。

JSP EL式はドル記号(

$

)で始まり、その後に左中括弧(

\ {

)が続き、次に実際の式が続き、最後に右中括弧(

}

)で閉じます。

${ELBean.value > 0}

この構文は

  1. ページのライフサイクルの中で(最初に)一度だけ評価されます.

これが何を意味するのかということです。上記の例の式で読み取られることは、ページがロードされる前に設定されなければなりません。

  1. Bean値への読み取り専用アクセスを提供します.

  2. その結果、JavaBeanの命名規則に準拠する必要があります.

ほとんどの用途では、この形式のELはあまり用途が広くありません。


2.2. 遅延実行EL

延期実行ELは、JSF固有に設計されたELです。 JSP ELとの大きな構文上の違いは、「

$

」ではなく「

#」

でマークされていることです。

#{ELBean.value > 0}

延期EL:

  1. JSFのライフサイクルと同期しています. これは、EL式が

遅延ELは、JSFページのレンダリングの異なる時点(最初と最後)で評価されます。

  1. Bean値への読み書きアクセスを提供します. これは設定することを可能にします

ELを使用したJSFバッキングBean(または他の場所)の値。

  1. プログラマがオブジェクトに対して任意のメソッドを呼び出せるようにします.

ELのバージョンに応じて、そのようなメソッドに引数を渡します。

Unified ELは、遅延ELとJSP ELの両方を統合し、同じページ内で両方の構文を使用できるようにする仕様です。


3統一されたEL

Unified ELでは、値表現とメソッド表現の2種類の表現が可能です。

そして、ちょっとしたメモ – 次のセクションでは、いくつかの例を示します。これらの例はすべて、アプリ内で利用可能です(最後のGithubリンクを参照)。

http://localhost:8080/jsf/el__intro.jsf


3.1. 値の式

値式を使用すると、配置場所に応じてマネージドBeanのプロパティを読み取るか設定することができます。

次の式は、マネージドBeanのプロパティをページに読み込みます。

Hello, #{ELBean.firstName}

ただし、次の式を使用すると、ユーザーオブジェクトに値を設定できます。

<h:inputText id="firstName" value="#{ELBean.firstName}" required="true"/>

この種の処理に適格であるためには、変数はJavaBean命名規則に従う必要があります。 Beanの値を確定するためには、それを囲むフォームを保存するだけです。


3.2. メソッド式

Unified ELは、JSFページ内からパブリックな非静的メソッドを実行するためのメソッド式を提供します。メソッドは戻り値を持っていてもいなくてもかまいません。

これが簡単な例です。

<h:commandButton value="Save" action="#{ELBean.save}"/>

参照されている

save()

メソッドは、

ELBean.

という名前のバッキングBeanで定義されています。

EL 2.2からは、ELを使用してアクセスしたメソッドに引数を渡すこともできます。これにより、例を次のように書き換えることができます。

<h:inputText id="firstName" binding="#{firstName}" required="true"/>
<h:commandButton value="Save"
  action="#{ELBean.saveFirstName(firstName.value.toString().concat('(passed)'))}"/>

ここでは、

inputText

コンポーネント用のページスコープのバインディング式を作成し、

value

属性をメソッド式に直接渡します。

変数は特別な表記法、中括弧、またはエスケープ文字なしでメソッドに渡されることに注意してください。


3.3. 暗黙のELオブジェクト

JSF ELエンジンは、いくつかのコンテナ管理オブジェクトへのアクセスを提供します。

それらのいくつかは以下のとおりです。


  • #\ {Application}

    :

    #\ {servletContext}

    としても利用可能、これは

Webアプリケーションインスタンスを表すオブジェクト
**

#\ {applicationScope}

:Webにアクセス可能な変数のマップ

アプリケーション全体
**

#\ {Cookie}

:HTTP Cookie変数のマップ


  • #\ {facesContext}

    :

    FacesContext

    の現在のインスタンス


  • #\ {flash}

    :JSF Flashスコープオブジェクト


  • #\ {header}

    :現在のリクエストのHTTPヘッダのマップ


  • #\ {initParam}

    :のコンテキスト初期化変数のマップ

ウェブアプリケーション
**

#\ {param}

:HTTPリクエストクエリパラメータのマップ


  • #\ {request}

    :

    HTTPServletRequest

    オブジェクト


  • #\ {requestScope}

    :リクエストスコープの変数のマップ


  • #\ {sessionScope}

    :セッションスコープの変数マップ


  • #\ {session}

    :

    HTTPSession

    オブジェクト


  • #\ {viewScope}

    :ビュー(ページ)スコープの変数マップ

次の簡単な例は、

headers

暗黙オブジェクトにアクセスすることによって、すべての要求ヘッダーと値をリストします。

<c:forEach items="#{header}" var="header">
   <tr>
       <td>#{header.key}</td>
       <td>#{header.value}</td>
   </tr>
</c:forEach>


4 EL

でできること

その汎用性の点で、ELはJavaコード、XHTMLマークアップ、Javascript、さらには

faces-config.xml

ファイルのようなJSF設定ファイルでも使用できます。具体的なユースケースを調べてみましょう。


4.1. ページマークアップでELを使う

ELは標準のHTMLタグで紹介できます。

<meta name="description" content="#{ELBean.pageDescription}"/>


4.2. JavaScriptでELを使う

Javascriptまたは<script>タグで見つかった場合、ELは解釈されます。

<script type="text/javascript"> var theVar = #{ELBean.firstName};</script>

バッキングBean変数は、ここではJavaScript変数として設定されます。


4.3. 演算子を使用してELでブール論理を評価する

ELはかなり高度な比較演算子をサポートします。


  • eq

    等価演算子。“ __ ==”と同じです。


  • lt

    演算子より小さい。「<」と同じです。


  • le

    演算子以下、「⇐」と同等


  • gt

    演算子より大きい。「>」と同じ。


  • ge

    以上、「

    > = .

    」と同等


4.4. バッキングBeanのELを評価する

バッキングBeanコード内から、JSFアプリケーションを使用してEL式を評価できます。これにより、JSFページとバッキングBeanを関連付けることで、可能性の世界が開かれます。暗黙のELオブジェクトを取得することも、実際のHTMLページコンポーネントまたはその値をバッキングBeanから簡単に取得することもできます。

FacesContext ctx = FacesContext.getCurrentInstance();
Application app = ctx.getApplication();
String firstName = app.evaluateExpressionGet(ctx, "#{firstName.value}", String.class);
HtmlInputText firstNameTextBox = app.evaluateExpressionGet(ctx, "#{firstName}", HtmlInputText.class);

これにより、開発者はJSFページと対話する際の柔軟性が大幅に向上します。


5 EL

でできないこと

EL <3.0にはいくつかの制限があります。次のセクションではそれらのいくつかについて説明します。


5.1. 過負荷なし

ELはオーバーロードの使用をサポートしていません。そのため、以下のメソッドを使用してバッキングBeanで:

public void save(User theUser);
public void save(String username);
public void save(Integer uid);

JSF ELは次の式を正しく評価できません

<h:commandButton value="Save" action="#{ELBean.save(firstName.value)}"/>

JSFの

ELResolver

は、

bean

のクラス定義をイントロスペクトし、

java.lang.Class#getMethods

によって返される最初のメソッド(クラスで使用可能なメソッドを返すメソッド)を選びます。返されるメソッドの順序は保証されていないため、必然的に未定義の動作になります。


5.2. 列挙型または定数値なし

JSF EL <3.0では、スクリプト内での定数値またはEnumの使用はサポートされていません。だから、次のいずれかを持っている

public static final String USER__ERROR__MESS = "No, you can’t do that";
enum Days { Sat, Sun, Mon, Tue, Wed, Thu, Fri };

次のことができないことを意味します。

<h:outputText id="message" value="#{ELBean.USER__ERROR__MESS}"/>
<h:commandButton id="saveButton" value="save" rendered="bean.offDay==Days.Sun"/>


5.3. ヌルセーフティ機能なし

JSF EL <v3.0は暗黙のnullセーフアクセスを提供していません。現代のスクリプティングエンジンについては奇妙に感じるかもしれません。

したがって、以下の式の

person

がnullの場合、式全体が見苦しいNPEで失敗します。

Hello Mr, #{ELBean.person.surname}"


6. 結論

JSF ELの基本、長所、および制限のいくつかを調べました。

これは主に用途が広いスクリプト言語で、改善の余地があります。それはまた、JSFビューをJSFモデルとコントローラーに結び付ける糊です。

この記事に付随するソースコードはhttps://github.com/eugenp/tutorials/tree/master/jsf[GitHub]にあります。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です