これからSilverlightを学ぶ人へのメール
オンラインでの友人(リアルで会ったことがない)が、今度仕事でSilverlightを触ることになった、という話を聞いたので以下のような内容のメールを送ってみました。
せっかくここまで書いたのでBlogにあげてみることにします(w
いろいろあるけど、まず書籍の話からしますか。
・「Silverlightで開発するデータ駆動アプリケーション 」
原書はVer.2のころに書かれたものなので、最新の部分については情報が足りないですがデータのバインディング(画面上のコントロールとデータを連携させる方法)についての説明はこの本がいまのところ一番詳しくてわかりやすいと思います。
基礎を理解する意味で、ぜひ読んでおくべきだと思います。
・「.NET開発テクノロジー入門 Visual Studio 2010対応版」
良い本なんですが、頭からひとつずつしっかり読もうとすると失敗するかも(w
こんな書評を書きましたが、どこが重要か、を考えたうえで読むと良い本だと思います。
Silverlightの開発、ということではWPF/Silverlightの章(3章)はまず読んでください。
WPFの部分はほとんどXAMLの説明なのでSilverlightでも基礎となる部分です。
Silverlightのところはほんとにそのまま基礎知識ですね。
あと重要なのがWCFの章の最後のほうにあるWCF Data ServicesとWCF RIA Servicesです。
Silverlightは直接データベースに接続できませんから、現状ですとこのどちらかの機能を使ってDB連携を実現するのが標準になります。
なので、4章を読むときはまずこの2つの技術の部分を先に読んだほうがいいでしょう。
サンプルとかみるとわかりますが、すごく簡単に(サンプルレベルでは)動かすことができます。
実際に動かすところまでが簡単すぎるのでその先に進もうとするとひっかかるんですよ。
業務アプリで使うなら認証は必須なはずですが、その認証をどうしたらいいか、とか(w で、4章の前のほうのWCFに関する基礎の知識が必要になってきたりします。
そんなつもりで読むといいと思います。
あと、Entity Frameworkの話ですね。
WCF Data ServicesとWCF RIA Servicesはウィザードでの動作等がサポートされているのは標準ではEntity Frameworkだけです。
なのでEntity Frameworkの知識が必須になります。
スループットの性能要件がものすごく厳しい、というようなアプリケーションでなければそんなに深いところまでの理解はなくても大丈夫かな。
この2冊と別にXAMLについての理解を深めるための本がなにか1冊あるといいかもしれません。
紹介できるような本を私は知らないんですが。。。
さて、Silverlightのアプリをつくりはじめるうえで、自分が気づいた注意点など。
上でも書いてますけど、データへのアクセスがWebサービス経由となるので、そのあたりで気を付けないといけないことがいろいろでてきますね。
SilverlightでのWebサービスの呼び出しは非同期アクセスが基本なので、というか非同期アクセスしか用意されていないのでそのやり方を知る必要があります。
で、データを取り出してきたらコントロールとバインドする必要があるのですが、ここで結構とまどいます。
バインディングの実装方法が何種類もあるので、ネットにころがってるサンプルがなかなか参考にならなかったりするんですよ。
よさそうなサンプルをいくつか拾ってきて、とりあえずそれぞれ単体では動きを確認できて、さあ必要な部分を一つにまとめよう、としたときにサンプルそれぞれで実装の仕方が違ってることが多く、「どうやったら一緒になるんだ?」と迷うことになったりします。
というかそういう状況に陥りました(w
これはいくつかサンプル動かして経験して自分としてはどういうやり方するか、をまとめていくしかないかと思います。
もしかしたら要件によって適切な実装方法が異なるといったことがあるかもしれません。
そこまでの経験はないのでこの考えが正しいかどうかわかりませんが。
あと、Silverlightでとまどうのは画面遷移かなぁ。
基本的にはHTML上のオブジェクトとしてSilverlightの表示域を確保して、という形になりますから、別ウィンドウを起動する、というWinFormだとよくやるパターンが使いにくいです。
画面の切替にしても、ベースになる領域を確保しておいて、そのなかをそっくり入れ替える、といった方法のほうが楽でしょうね。
このあたりは結構設計時に考慮が必要になるかと思います。
このあたりの注意点のいくつかは以下の記事をみていただいてやってみてもらうと経験できる部分があるかと思います。
https://blogonos.wordpress.com/category/wcf-ria-services/
SilverlightのUIは自由度が高いんですが、高いだけに考えないといけないことは多くなります。
このあたり注意しておくといいと思います。
ということで、いまできるアドバイスはこんなところかな。
慣れるのに苦労する部分はあると思いますけど、わかってくると楽しいとこも多いです。
頑張ってくださいませ。
#えと、せっかくこんなふうにまとめたので、具体的なスケジュール管理の個所はのぞいて
Blogにネタとしてアップさせてもらおうと思います(w
さて、私としてはこんなふうにまとめてみたのですが。
他の方の意見も聞いてみたいなぁ。
いろんな方にコメントに書きこんでいただけると、初学者がどういう点に気をつけて学習をすすめていけばよいかの指針ができるんじゃないかと思います。
ぜひ協力してくださいませ。
LightSwitchの裏側を探る:ユーザー認証とアクセス許可
前の記事で動作を確認したユーザー認証とアクセス許可の裏側をのぞいてみます。
まずユーザー認証に使われるデータベースですが、これはASP.NETに組み込まれているユーザー認証の仕組みをそっくり使っているようです。
テーブル/ビュー/ストアドプロシージャ等見慣れたものが並んでいます。
また、ServerGeneratedフォルダにあるWeb.configを見ると、メンバーシップ/ロール/プロファイルを利用するための設定が記述されており、これもASP.NETそのものです。
プロファイルとしてFullNameというプロパティが設定されていますが、これがユーザー登録画面で「氏名」として使われているようです。
パーミッションについては、ApplicationDefinition.lsmlに以下のように設定されています。
<Permission Name="一般">
<Permission.Attributes>
<DisplayName Value="一般" />
</Permission.Attributes>
</Permission>
<Permission Name="管理者">
<Permission.Attributes>
<DisplayName Value="管理者" />
</Permission.Attributes>
</Permission>
やはりLightSwitchのキモとなるのはApplicationDefinition.lsmlファイルのようですね。
それからログイン画面、ユーザー画面、役割画面ですが。。。
ログイン画面については情報が見つけられていません。
ユーザ画面、役割画面についてはMicrosoft.LightSwitch.Client.dll の中に
・Microsoft.LightSwitch.Security.Client.Implementation.UsersScreen
・Microsoft.LightSwitch.Security.Client.Implementation.RolesScreen
というクラスが存在しています。
多分このクラスがそれぞれの画面なのではないかと思われます。
なお、前の記事では言及していませんが、アプリケーションのプロパティでScreen NavigationをみるとUsers、Rolesという画面があらかじめ用意されていることがわかります。
Access ControlにはあらかじめSecurityAdministrationというパーミッションが用意されているので、このパーミッションを付加してデバッグを実行するとユーザー画面や役割画面を見ることができます。
ただし、ここでユーザーや役割を登録してみたところで開発中は必ず「testuser」になってしまうため、意味はなさそうです。
少し触ってみて不満に思うことは、この作り付けのユーザー画面に拡張性がなさそうな部分です。
例えばログインしているユーザのメールアドレスを保持しておいて、なにか処理したときに確認メールを送信したい、といった機能は容易に想像されるのですが、これを実装するためにログインユーザーとメールアドレスを簡単に関連づけするための方法が見つけられていません。
どうもログインユーザーを保持しているテーブルに直接アクセスする方法もなさそうですし。
ログイン画面に対しても何も手を入れることができないようなので、独自に用意したテーブルを使ってユーザー認証を行う、というのもできなさそうなんですよねぇ。。。
今のLightSwitchの実装だとユーザー認証のための情報は本当にログインするためだけにしか使えないようになっていると考えています。
もうちょっと柔軟にいろいろ使えるようになるといいんですけどねぇ。
まぁ、現在の実装ではユーザ情報を修正することさえできない(フォーラムで次のバージョンで実装予定という記述があったような)状態なので、今後良い方向に発展してくれることを期待したいと思います。
LightSwitch:ユーザ認証とアクセス許可
注)この記事の記述はベータ版の仕様に基づいています。今後機能に変更が加わる可能性があります。
LightSwitchにはユーザ認証の機能が組み込まれています。
データベースやWeb.Configの設定を見ると、ASP.NETと同じものをベースにユーザ認証を実装しているものと思われます。
ただし、このユーザ認証ですが、開発中に利用することができません。
作成したアプリケーションを配置してはじめてユーザ認証を利用することができるようになっています。
では、ログインするユーザによって画面の表示/非表示を切り替えるのにはどうするか。
この答えはパーミッション(アクセス許可)を利用する、ということになると思われます。
○動作確認用の画面を作成する
アクセス許可の動作を確認する準備として、まずは画面を作成します。
LightSwitchのアプリケーションを新規に作成し、アプリケーションのプロパティでCultureをJapaneseに設定、Application Typeが「Desktop client, 2-tier deployment」になっていることを確認します。
2-tierのタイプに設定しておくのは、とりあえず動作を確認するための配置の作業が簡単だからです。
次にScreenを追加します。
とりあえず Search Data Screenを選択し、Screen Dataの設定をせずに、Screen Nameを「一般表示用画面」として作成します。
同様に「管理者表示用画面」も作成します。
「一般表示用画面」で「Add Data Item…」をクリックしてUserNameというローカルプロパティを追加します。
画面エディタ内のAddボタンをクリックし、UserNameを表示するラベルを追加します。
Write Code ドロップダウンリストから「一般表示用画面_Loaded」を選択します。
コードエディタが表示されるので、以下のとおりに記述します。
このコードは認証されているユーザがいる場合、そのユーザ名を表示するためのコードになります。
とりあえずここで一度デバッグ実行してみます。
一般表示用画面と管理者表示用画面を持ったアプリケーションが表示されます。
○パーミッションを設定する
パーミッションの設定はアプリケーションのプロパティのAccess Controlタブから行ないます。
Form認証を有効にし、「一般」と「管理者」というパーミッションを作成します。
○アクセス権限の設定
「一般表示用画面」のWrite Code ドロップダウンリストから「CanRun一般表示用画面」を選択します。
コードエディタに以下のように記述します。
このコードは認証されているユーザが「一般」権限を持っているときに表示する、という意味になります。
同様にして、「管理者表示用画面」を「管理者」権限を持っているユーザだけが表示できるようにします。
アプリケーションのプロパティのパーミッションの作成画面に戻り、「一般」と「管理者」パーミッションのGranted for debugチェックボックスにチェックをつけてアプリケーションをデバッグ実行してみましょう。
ここでチェックをつけたパーミッションがデバッグの実行時ユーザに付加されるので、上記のように2つのパーミッションにチェックが入っていれば、画面は2つとも表示されます。
管理者のチェックをはずし、一般のみチェックした状態で実行すると、下記のように「一般表示用画面」のみが表示されることになります。
ここで画面の表示をよくみると、UserNameとして「TestUser」が表示されていることに気づきます。
開発中は必ずこの「TestUser」としてログインしているものとして実行されてしまうようです。
とりあえずここまでで動作確認用のアプリケーションの構築を終了し、アプリケーションを配置してみることにします。
○アプリケーションの配置
アプリケーションの配置はBuildメニューのPublishから実行します。
最初に配置パターンが2-tierでよいか確認がはいります。
そのままNextボタンをクリックします。
次に発行場所とデータベースをどう設定するかの確認がはいります。
とりあえずこのままNextボタンをクリックします。
データベースとの接続文字列の確認が行われます。
特に変更せずに続けていくと、開発マシンに直接データベースを発行して利用するような設定になります。
次にデフォルトの管理ユーザを作成する画面になります。
パーミッションの作成をした画面で説明していなかったのですが、あらかじめ全体を管理するためのパーミッションが一つ設定されています。
ここで作成するユーザはそのパーミッションを使ってアプリケーションの全体を管理するユーザになります。
次は配置に必要なモジュール等の設定になります。
とりあえずこのまま先にすすみます。
接続設定の確認、となりますが、このままPublishボタンをクリックします。
ここまでを実行すると、データベースが開発マシン内に構築されます。
SQL Server Management Studioで確認すると、アプリケーション名(ここではApplication4)と同名のデータベースが作成されていることがわかります。
また、アプリケーションのソースが含まれているフォルダ内に「Publish」フォルダが追加されています。
○アプリケーションのインストールと実行
Publishフォルダ内のsetup.exeを実行します。
セキュリティの警告がでますが、ここで「インストール」を実行します。
アプリケーションがインストールされ、ログイン画面が表示されます。
○ロールとユーザーの作成
配置作業のウィザードの中で作成した管理ユーザのユーザ名/パスワードを入力し、ログインします。
Administrationメニューとしてユーザーの管理画面と役割(ロール)の管理画面が表示されます。
ロールとして「一般ユーザーロール」を追加し、そのアクセス許可に「一般」を追加します。
また、「管理ユーザーロール」を追加し、そのアクセス許可として「一般」と「管理者」を追加します。
ユーザーを作成します。
「user1」には「一般ユーザーロール」を、「user2」には「管理ユーザーロール」を追加します。
LightSwitchにはログアウトの機能はないようです。
ユーザーを変更するには一度アプリケーションを終了させる必要があります。
インストールしたアプリケーションは[スタート]-[すべてのプログラム]から実行することができます。
○ユーザー(ロール)に付加したアクセス許可の動作の確認
user1でログインすると、一般表示用画面だけが利用できます。
user2でログインすると、管理者表示用画面も利用できることが確認できます。
○まとめ
いろいろ調べていてわかりにくかったのが、ユーザー認証の仕組みはしっかり組み込まれているのに、開発時にはその仕組を利用できない、という部分でした。
普通に考えると、例えば画面の表示/非表示は役割(ロール)によって制御するものだと思い込んでいましたから。
アクセス許可の仕組みがユーザー認証とは別に存在し、開発時にはアクセス許可の状態を自由に設定して動作の確認ができることが理解できてみると、アクセス許可として細かい設定を多く作成しておきロールはそのアクセス許可を組み合わせたものとすることでより柔軟な制御が可能になるな、と納得しているところです。
アクセス許可が利用できるのは画面の表示/非表示だけではないようなので、そのあたりもう少しつっこんで調べていきたいと思います。
LightSwitchの裏側を探る 3:ビルドの実行と選択リスト、計算項目の追加
前の記事でデータベース内にテーブルがどのタイミングで追加されるのかがわからない、と書きましたが、実はビルドすれば追加される、ということがわかりました。
前の記事の直後にビルドを実行すると、下記のように「会員テーブルSet」という名前のテーブルが追加されます。
そしてこのとき、Bin\Dataフォルダに存在していたSchemaChange.xmlファイルが消えます。
どうも、IDE上で行ったスキーマ変更の情報が一旦SchemaChange.xmlに書き込まれ、ビルド時に実際のデータベースを変更するとこのSchemaChange.xmlファイルが消える、という動きになっているようです。
こんなことがわかったのはあるいみケガの功名かも。
さて、次に作成したテーブルのなかで、「性別」項目を男性/女性が選べるように設定してみます。
「性別」の項目を選び、プロパティからChoice Listリンクをクリックします。
選択リストを設定するダイアログが表示されるので、ここで以下のように登録します。
これだけでOKなんですが、この「男性/女性」といった情報はどこに保存されるか、というと、、、
Dataフォルダの ApplicationDefinition.lsml 内に格納されます。
「性別」に関する情報部分が以下のようになっていました。
———————————————————————————————————-
<EntityProperty Name="性別" PropertyType="Microsoft.LightSwitch:Int32">
<EntityProperty.Attributes>
<Required />
<NotSearchable />
<SupportedValue DisplayName="男性" Value="1" />
<SupportedValue DisplayName="女性" Value="2" />
</EntityProperty.Attributes>
</EntityProperty>
———————————————————————————————————-
テキストエディタでフォルダ内のファイルに対して全検索かけてみましたけど、このフォルダにしか「男性/女性」の文字はありません。
結構、このApplicationDefinition.lsmlファイル、重要っぽいです。
さて、次に行ったのは、計算によって値を表示するデータ項目の追加。
誕生日から計算して年齢を表示する項目を追加してみます。
テーブルに「年齢」項目を追加し、プロパティで Is Computed にチェックを入れて Edit Method リンクをクリックします。
IDE内にソースコードを記述する画面が表示されるので、以下のようにプログラムを追記しました。
会員テーブルクラスの Partial なソースとしてプログラムを記述することになります。
こうなってくると、「会員テーブル」という名前をつけたのが間違いだったかなぁ。
「会員」としておくとテーブル名も「会員Set」となり、またクラスも「会員クラス」だったわけで。。。
どうもレコード1つにたいしての名前をつけたほうが良かったようですね。
まぁ、いまさらしょうがないので、このまま続けます。
さて、このプログラムを保存すると、Commonフォルダ内に UserCode という名前のフォルダが作成され、そこに上記の「会員テーブル.cs」ファイルが追加されました。
どうもこの「UserCode」フォルダが開発者が追記したプログラムの置き場所になりそうです。
さて、データ構造を触るのはここまでにして、次回は画面を追加してみようと思います。
そのまえにここまでで他に追加されてるプログラムがありました。
Common\GeneratedArtifacts の下のDataRuntime.csとServer\GeneratedArtifacts の下のDataService.cs の内容が生成されています。
データを取り出す部分のコードや取得/設定時のパーシャルメソッドの定義が行われているようです。
LightSwitch用のdll内の定義クラスが使われているため、どうにもソースが読みにくかったりするのですが。。。
LightSwitchの裏側を探る 4:スクリーンの追加
さて、とうとうデータ側の準備がととのったので、とうとう画面を追加してみます。
といっても、Add Screenから Editable Grid Screen を選択してScreen Dataとして会員テーブルSetを設定するだけ。
まぁ、これだけだとちょっとさびしいので、Screenの操作画面から画面名を「会員一覧」に変更します。
しかし、この画面がUIの設定画面なんですよねぇ。
部品の単位で操作していくので、慣れれば操作はできますが、、、これでUIイメージしろっていっても。。。
ま、でもとりあえずこれだけで動きます。
実行させるとこんな感じ。
操作用の「追加、編集、削除」とかが日本語になってますね。「Excelにエクスポート」とかも。
このままでデータの追加とかも可能です。
あとはデータ溜め込んで、検索かけて、と利用していけばいい、ということになります。
Screenを追加して、ソースのほうはどう変わったか、というとServerGenerated\GeneratedArtifactsフォルダにサーバ上のエンティティのクラスやドメインサービスのソースが生成されます。
また、ClientGenerated\GeneratedArtifactsフォルダにはクライアント側のデータコンテキスト、そしてClient\GeneratedArtifactsフォルダにはスクリーンの呼び出しコードとしてScreen.csが作成されています。
いままでの操作全体を含めて、とにかくGeneratedArtifacts、という名前のフォルダにソースがどんどん生成されていきますね。
ただ、Screen.csみてもXAMLやXAMLに相当する画面を生成するコードが書いてあるわけじゃありません。
ここではやっぱりLightSwitch用のクラスを使って画面を生成する枠を作っているだけみたいで、どうもその中の設定、つまりUIの設定画面で操作している部分も全部 ApplicationDefinition.lsml に含まれているみたいです。
この状態だと、直接ソースをいじって画面の表示を修正する、なんてことは簡単にはできなさそうです。
独自のUIコントロールを追加して利用するための方法はドキュメントやツールキットでも紹介されていますから、その基本通りに用意されている口を通して拡張するしかない、というのが現時点での認識だったりします。