BT

最新技術を追い求めるデベロッパのための情報コミュニティ

寄稿

Topics

地域を選ぶ

InfoQ ホームページ アーティクル FlexおよびJavaアプリケーションのアーキテクチャ(page4)

FlexおよびJavaアプリケーションのアーキテクチャ(page4)

ブックマーク

Flexアプリケーションアーキテクチャ

サーバーサイドでFlash Remotingを設定し、FlexでRemoteObjectインスタンスを定義する方法がわかったところで、今度はこのオブジェクトを使用するアプリケーションの作成方法を見てみましょう。

イベントの使用

典型的なFlexアプリケーションは、ユーザーインターフェイスを定義するMXMLコードと、ロジックのActionScriptコードから構成されます。JavaScriptとブラウザーDOMオブジェクトの場合と同様、この2つはイベントとイベントハンドラーによって結び付けられます。RemoteObjectをアプリケーションで使用するには、インスタンスを定義し、サーバーサイドのリモーティング宛先のメソッドを呼び出し、resultおよびfaultイベントに対するコールバック関数を指定し、それらの関数の中で、サーバーから返されたデータを使用して必要な処理を行います。

ここに示す単純なアプリケーションは、従業員データをデータベースから取得して、FlexのDataGridコンポーネントに表示します。アプリケーションが初期化された後、サーバー上のremoting-config.xmlファイルに定義されたemployeeService宛先のgetEmployees()メソッドが呼び出され、サーバーからデータが正常に返されると変数employeesにデータが格納され、何らかの理由で要求が失敗した場合、Alertボックスにメッセージが表示されます。データバインディングを使用して、employees変数がDataGridのdataProviderプロパティにバインドされます。

<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
   xmlns:s="library://ns.adobe.com/flex/spark"
   xmlns:mx="library://ns.adobe.com/flex/mx"            
   initialize="employeeSvc.getEmployees()">
   <fx:Script>
      <![CDATA[
         import mx.collections.ArrayCollection;
         import mx.controls.Alert;
         import mx.rpc.events.FaultEvent;
         import mx.rpc.events.ResultEvent;
         [Bindable]private var employees:ArrayCollection;
         private function onResult(e:ResultEvent):void{
            employees=e.result as ArrayCollection;               
         }
         private function onFault(e:FaultEvent):void{
            Alert.show("Error retrieving data.","Error");
         }
      ]]>
   </fx:Script>
   <fx:Declarations>
      <s:RemoteObject id="employeeSvc" destination="employeeService"
         result="onResult(event)" fault="onFault(event)" />
   </fx:Declarations>
   <mx:DataGrid dataProvider="{employees}"/>
</s:Application> 

RemoteObjectを使用する場合、resultおよびfaultハンドラーをサービスレベルで定義できます。

<s:RemoteObject id="employeeSvc" destination="employeeService" result="onResult(event)"
fault="onFault(event)"/>

メソッドレベル:

<s:RemoteObject id="employeeSvc" destination="employeeService">
   <s:method name="getEmployees" result="onResult(event)" fault="onFault(event)"/>
   <s:method name="getDepartments" result="onResult2(event)" fault="onFault2(event)"/>
</RemoteObject> 

または呼び出しごと:

<s:Application xmlns:fx=http://ns.adobe.com/mxml/2009"
   xmlns:s="library://ns.adobe.com/flex/spark"               
   xmlns:mx="library://ns.adobe.com/flex/mx"
   initialize="getEmployeesResult.token=employeeSvc.getEmployees()">
   <fx:Declarations>
      <s:RemoteObject id="employeeSvc" destination="employeeService"/>
      <s:CallResponder id="getEmployeesResult" result="onResult(event)"
         fault="onFault(event)"/>
   </fx:Declarations>
        

データバインディングの使用

データバインディングはFlexフレームワークの強力な機能であり、データが変更されたときにユーザーインターフェイスを更新する作業を、イベントリスナーを明示的に登録して作成しなくても実現できます。上記のアプリケーションコードで、employees変数定義の前にある[Bindable]タグは、コンパイラーディレクティブです。ファイルのコンパイル時に、employees変数が変更されたときにイベントをブロードキャストするActionScriptコードが自動的に生成されます。

[Bindable]private var employees:ArrayCollection;

DataGridのdataProviderプロパティの代入文にある中括弧は、実際にはコードを生成します。このコードは、employees変数の変更をリッスンし、変更された場合はそれに応じてDataGridビューを更新します。

<mx:DataGrid dataProvider="{employees}"/>

このアプリケーションでは、employeesの初期値はnullであり、DataGridにデータは表示されていません。サーバーからデータが正常に取得されてemployeesに格納されると、DataGridが更新されて従業員データが表示されます。

ビューステートの使用

ユーザーインターフェイスのもっと大きな変更、例えばコンポーネントの追加、削除、移動、変更などを実行時に動的に行いたい場合には、Flexのビューステートを使用します。Flexのすべてのビューまたはコンポーネントに対して、複数のステートを定義し、そのビュー内のすべてのオブジェクトに関して、そのオブジェクトがどのステートに含まれ、そのステートでどのように表示され、動作するかを定義できます。ステートを切り替えるには、コンポーネントのcurrentStateプロパティを、定義されたステートの1つの名前に設定します。

<s:states>
 <s:State name="employees"/>
 <s:State name="departments"/> 
</s:states>
<mx:DataGrid dataProvider="{employees}" includeIn="employees"/>
<s:Button label.employees="Switch to departments"
   label.departments="Switch to employees"
   click.employees="currentState='departments'"
   click.departments="currentState='employees'"/>

MXMLコンポーネントの使用

アプリケーションが大規模になるとともに、ロジックをActionScriptクラスのいくつかのパッケージに分割し、ビューを別々のMXMLファイル(MXMLコンポーネントと呼ぶ)に分割する必要が出てきます。各MXMLコンポーネントは、既存のコンポーネントを拡張しており、アプリケーションに含めることはできますが、単独で実行することはできません。MXMLのコンポーネントを使用するには、そのコンポーネントのインスタンスを作成し(クラス名はファイル名と同じ)、コンパイラーがコンポーネントを見つけられるように適切な名前空間をインクルードします。

次に示すのは、MasterViewというMXMLコンポーネントのコードで、com.adobe.samples.viewsパッケージのMasterView.mxmlに保存されています。

<s:Group xmlns:fx="http://ns.adobe.com/mxml/2009"         
   xmlns:s="library://ns.adobe.com/flex/spark" >
   <fx:Metadata>
      [Event(name="masterDataChange",type="flash.events.Event")]
   </fx:Metadata>
   <fx:Script>
      <![CDATA[
         import mx.collections.ArrayList;
        [Bindable]private var masterData:ArrayList=new ArrayList(["data1", "data2", "data3"]);
         public var selectedData:String;
         private function onChange(e:Event):void{
           selectedData=dataList.selectedItem;
           this.dispatchEvent(new Event("masterDataChange"));
         }
      ]]>
   </fx:Script>
   <s:DropDownList id="dataList" dataProvider="{masterData}" change="onChange(event)"/>
</s:Group>

次に示すのは、このカスタムMasterViewコンポーネントをインスタンス化して使用するアプリケーションのコードです。

<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
   xmlns:s="library://ns.adobe.com/flex/spark" 
   xmlns:views="com.adobe.samples.views.*">
   <fx:Script>
      <![CDATA[
        import mx.controls.Alert;
        private function onMasterDataChange(e:Event):void{
          Alert.show(e.currentTarget.selectedData,"Master data changed");
        }
      ]]>
   </fx:Script>
   <views:MasterView masterDataChange="onMasterDataChange(event)"/>
</s:Application>

イベントのブロードキャスト

緩く結合したコンポーネントを作成するには、そのコンポーネントに対するパブリックAPI(コンポーネントのパブリックメンバー)を定義するか、上記のMasterViewコードの例に示すように、カスタムイベントを定義してブロードキャストする必要があります。[Event]メタデータタグを使用して、イベントをコンポーネントのAPIの一部として定義し、どのタイプのイベントオブジェクトをブロードキャストするかを指定しています。

<fx:Metadata>
  [Event(name="masterDataChange",type="flash.events.Event")]
</fx:Metadata>

コンポーネントで何らかのイベントが発生した場合(この例ではDropDownListのchangeイベント)、コンポーネントはメタデータに指定されたタイプのイベントオブジェクトのインスタンスを作成してブロードキャストします。

this.dispatchEvent(new Event("masterDataChange"));

このカスタムコンポーネントをインスタンス化するコードは、このカスタムイベントのリスナーを登録し、イベントハンドラーを登録することができます。

<views:MasterView masterDataChange="onMasterDataChange(event)"/>

このように、カスタムイベントを定義してブロードキャストする緩く結合したコンポーネントは、Flexアプリケーションの中心的な構成要素です。実は、Flexフレームワーク自体のコンポーネントもこの方式で作成されています。カスタムイベントのブロードキャストについて詳しくは、ビデオFlash Builder 4でのFlex 4のイベントの定義*を参照してください。

モジュールの作成

デフォルトでは、コードはすべて1つのSWFファイルにコンパイルされます。SWFファイルが大きくなりすぎる場合や、特定のユーザーだけが使用する機能が含まれている場合は、モジュールを使用して、アプリケーションを複数のSWFファイルに分割し、実行時にメインアプリケーションから動的にロードしたりアンロードしたりできます。モジュールを作成するには、Moduleクラスを拡張したクラス(MXMLのActionScript)を作成してコンパイルします。実行時にモジュールを動的にアプリケーションにロードするには、<mx:ModuleLoader>タグまたはModuleLoaderクラスのメソッドを使用します。

マイクロアーキテクチャの使用

アプリケーションの基本的な作成方法は以上ですが、アプリケーションが大規模になるにつれて、何らかの方法でそのファイルを整理し、アプリケーションのデータおよびデータサービスを集中化し、すべてのコンポーネントの間の通信を処理する必要が出てきます。このために、Flexアプリケーションの構築にあたって、エンタープライズアプリケーション開発で長年にわたって有用性が証明されてきたデザインパターンを使用することができます。実際、Flex専用のマイクロアーキテクチャが多数開発されており、これからも開発されるでしょう。最も歴史が古く、最も確立されているのは、Cairngorm*です。これはオープンソースのマイクロアーキテクチャで、コマンドと委譲、フロントコントローラ、シングルトンデータモデル、シングルトンサービスストア、イベントディスパッチャーを使用します。その他の一般的なフレームワークとしては、Pure MVC*Mate*Parsley*Swiz*Spring ActionScript*があります。これらをはじめとするフレームワークについて詳しくは、AdobeデベロッパーセンターのFlexアーキテクチャを参照してください。

次のステップ

この記事では、FlexおよびJavaアプリケーションのアーキテクチャについて説明しました。詳しくは、記事内のリンクと以下のリソースを参照してください。

 

ページ4/4

 

この記事に星をつける

おすすめ度
スタイル

BT