Associateは入門レベルの試験で、この試験の合格が他の試験の受験資格にもなっています。
Reactiveとついている通り、Reactive Web App開発の基礎的な知識を問われる試験。
試験問題は、
https://www.outsystems.com/learn/certifications/
の、「Associate Reactive Developer (OutSystems 11)」項目のリンク「Exam Details」でダウンロードできる資料から。解凍したら、Japaneseフォルダにあるファイル「Associate Reactive Developer Sample Exam - JP.pdf」を開いてください。
Associate Reactive Developerのサンプル問題について解説 1/4(#1-#5)
Associate Reactive Developerのサンプル問題について解説 2/4(#6-#10)
Associate Reactive Developerのサンプル問題について解説 3/4(#11-#15)
Associate Reactive Developerのサンプル問題について解説 4/4(#16-#20)
#6 ブロックとイベント(OnInitialize)
Reactive Web Appとモバイルアプリでは、画面で自動発生し、Service Studioでハンドラをかけるイベントがいくつかあり、Initializeはその1つです。
画面遷移を行うときに最初に発生するイベントがInitializeで、そのハンドラでは変数の初期化などを行います。Initializeが終了してから画面に定義されたAggregateとData Actionが開始されます(FetchプロパティがAt Startの場合)。
DOMが完全に準備されると、Readyイベントが発生します。つまり、Initializeの時点ではDOMは準備できていません。
というわけで、選択肢A(On Initializeイベントは、画面やブロックの描画前、かつデータの取得開始前にトリガーされる。)が正解。
他の選択肢を見ておきます。
B:「画面やブロックの描画後にトリガーされる」のはRender。画面のDOMが準備された後、最初の1回の描画時のみにトリガーされるのはReady。いずれにせよInitializeとは違います
C:「Aggregateによるデータの取得後にトリガーされ」るのは、After Fetch。AggregateのOn After Fetchプロパティでハンドラを設定できます
D:「ブロックの入力パラメータの変更後にトリガーされる」のはParameter Changed。Blockを配置した画面側から、Blockの入力パラメータを変更すると発生します
イベントのライフサイクルについて詳しくは、画面とブロックのライフサイクルイベントを参照。
#7 Aggregate/画面でのデータ取得(FetchプロパティとOn After Fetch)
まず、前提知識を整理しておきます。
Fetchプロパティ
画面に定義したAggregateのFetchプロパティは、以下の2つの値のいずれかをとります。
At start:Initializeイベント終了後、自動的にデータ取得が開始される
Only on demand:Action FlowでRefresh Dataしたときのみデータの取得が開始される
On After Fetch
Aggregateのデータ取得が終了すると発生するイベントがAfter Fetch。
AggregateのプロパティOn After Fetchでそのハンドラを定義できます。
よくある使い方は、複数のAggregateの実行に順序を付けたいときに、1つ目のAggreagteのOn After Fetchでフィルタ条件を変更した上で、2つ目のAggregateに対しRefresh Dataするというもの。
問題の検討
問題の設定から
- CountryというEntityから国の一覧をDropdown Widgetに表示する
- CityというEntityから都市の一覧をDropdown Widgetに表示する
- ただし、CityのDropdownに表示するのは、選択した国内の都市のみにする
というのが実現したいこと。
これを実現するためには、Countryで国を選択したときに、Cityを検索するAggregateを新しい条件で再検索し、その結果を2番めのDropdownに表示する必要があります。
各選択肢を検討してみましょう。設問は「正しくないもの」です。
A:○。これは必須ではないと思いますが、×ではないですね。初期表示のやり方として、①Local変数Cityにデフォルト値を設定しておいて、GetCitiesのFetchはAt startにする②FetchはOnly on demandにして、CountryのDropdownは未選択で初期表示する、の2通り考えられます。この選択肢は②の方針かと思われます
B:○。CountryのDropdownの選択が変わるとOnChange Screen Actionが動きます。国が変わったので、都市を検索する条件が変わってます。よってGetCities Aggregateを更新してデータを再取得する
C:○。選択された国内の都市を検索したいわけなので、都市を検索するAggregateのFilterに条件を設定します。
D:×。都市の再取得(GetCities Aggregate)は、対象の国が変わったときです。国のAggregateを取得したときではありません。
というわけで正解はD。
#8 ブロックとイベント(ブロック)
ブロックは一塊のUI要素と、そのためのデータ取得及びロジックを部品としてラッピングし、各画面に配置して利用できるようにするもの。
正解は選択肢B(画面や他のブロックでインスタンス化できる)。
ブロックは独立して配置することはできません。必ず画面か他のブロックに配置して利用します。
A:×。ブロックにも配置できる。
C:×。画面かブロックに配置する必要があり、クライアントアクションだけで表示させることはできません。
D:×。「外部HTMLでもインスタンス化」というのはOutSystemsの仕組みを通さずに表示できるという意味でしょうが、そういうことはできません。
#9 ブロックとイベント(Trigger Event)
ブロックにはEventという要素を追加できます。
画面と配置したブロックの間には、仕組み上の壁があり、画面は自由にブロック内を操作することができません。
ブロックで特定のタイミング(通信の終了や、UIの準備完了など)に名前をつけ、配置した画面側でこのタイミングに反応するActionを書くことができます。
この仕組がブロックのEventです。Eventのハンドラを作れば、画面はブロック内で発生したデータを受け取って操作することもできます(画面から直接ブロック内のローカル変数を操作することはできない)。
詳しくはイベントを使用してブロックの変更を親に反映するを参照。
この問題で聞かれているTrigger Eventというのは、定義したEventを発生させる要素で、ブロックのAction Flowに記述します。各選択肢では、イベントが発生したかをどこからどこへ通知するか、というのがポイント。
イベントは、「イベントを定義したブロック」から「ブロックを配置した親の画面・ブロック」へ通知するものです。
この説明に合致する選択肢は、A(Trigger Eventを使用すると、ブロックからその親(画面またはブロック)に、ブロックのスコープ内で関連イベントが発生したことを通知できる。)です。
#10 フォームの検証(Built-in Validation)
詳細な情報はフォームのフィールドを検証する参照。
ButtonのBuilt-in Validations(Eventsカテゴリにある)をYesに設定しておくと、Clickイベント時に、Form内のInputの入力をチェックしてくれます。
対象は、
- 必須なのに入力がない項目がないか(Mandatoryプロパティで指定:入力必須であることを示す)
- 型が一致しない入力がされた項目がないか(ドキュメントでは、Input Typeプロパティを見ているようなことが書いてあるが、動かしてみるとむしろFormのSourceに紐付けているEntity属性の型をチェックしているように見える)
Built-in Validationsの結果は、以下のように設定される。
- 各入力WidgetのValidプロパティにValidationの結果(Falseだとエラーあり)
- 各入力WidgetのValidationMessageにエラーメッセージ(エラーがなければ空)
- Form WidgetのValueプロパティにはForm全体での検証結果(1つでも入力項目にエラーがあればFalseになる)
デバッガを使って、わざとBuilt-in Validationに引っかかる入力を渡したときのWidgetの値。
以上を踏まえて、各選択肢を見ていきます。
A:×。型もチェックされる
B:×。「ロジックで使用される」という限定はない。Form内の全項目がチェックされる
C、D:保留。どちらの選択肢も、前半は必須フィールドが入力されているか、ということを言っていて正しい。後半のチェック対象が、Cは入力フィールドの想定データ型(Input TYpeプロパティのことであろう)であり、DはFormのソースのデータ型となっているところに違いがある。サンプル問題に示された正解はCであり、ドキュメントでもCのほうが正しい。ただし、実際に動作させてみると疑問はある。Input Typeでは数値項目に「Number」を指定するのだが、上に示したデバッガのSS(Input_Int WidgetはデータソースがInteger型で、Input TypeはNumberとしている)のようにエラーメッセージは「Enter a valid integer.」となっており、むしろデータソースの型の方を見ていることを示唆している。
というわけで、A/Bは確実に落とせるのですが、CかDかは悩む。試験時に回答するならドキュメントに記載のあるCの方でしょうか……。
ここは後で修正するかもしれません。