ホーム > Silverlight > ログインしているユーザー情報をもとに返却するXAPファイルを変更する。

ログインしているユーザー情報をもとに返却するXAPファイルを変更する。


ユーザーによって違うバージョンを提供したいという場合があります。

例えば一般ユーザーには安定しているVersion 1.0を使わせたいけれど、あるユーザーにはお試し版のVer1.1のSilverlightアプリケーションを使わせたいといった場合です。場合によっては古いアプリケーションをしばらく使わせたいといった場合も有るでしょう。

ASP.NETでどうにかしたい場合は例えば次の方法が思いつきます。

  1. SilverlightをホストするHTMLのobjectタグを動的に書き換える。
  2. ジェネリックハンドラーで動的に切り替える。
  3. IHttpHandlerで動的に切り替える。 2のジェネリックハンドラーで動的に切り替える方法を考えてみます。

概要

Silverlightをロードする場合、通常であればsourceパラメーターにSilverlightの配置先を指定します。

HTML側にはすべてのユーザーで同じURLを指定させ、ユーザーのセッション情報をもとにデータベースで管理しているユーザーごとのバージョンテーブルを検索し、ユーザー別に指定されたXAPファイルをダウンロードさせます。

image

ジェネリックハンドラーの記述

通常ASP.NETのページはASPXの拡張子で作成しますが、画像やXAPファイルなどのコンテンツファイルを動的に返したいときはASHXを利用することで余計な処理が少ない分パフォーマンスよくクライアントに折り返すことができます。

Visual Studioでジェネリックハンドラーを追加したい場合には、Visual StudioでGeneric Handlerを追加します。

image

ジェネリックハンドラーではどのようなコンテンツを返却するかをProcessRequestメソッドに記述します。

実際に返却するコンテンツは、ProcessRequestメソッドの引数であるHttpContextクラスのResponseプロパティーやRequestプロパティー、Sessionプロパティーをもとに値を返却します。ただし、Sessionプロパティーを利用するためには、IRequiresSessionStateインターフェイスを実装する必要があります。

using System;
using System.Web;
using System.IO;
using System.Web.SessionState;

namespace WebApplication1
{
    public class SilverlightVersionSelector : IHttpHandler, IRequiresSessionState
    {
        public void ProcessRequest(HttpContext context)
        {
            context.Response.ContentType = "application/xaml+xml";

            // 1.QueryStringからアプリケーション名を取得する。              //
            var app = context.Request["xap"];
            if (string.IsNullOrEmpty(app))
            {
                context.Response.BinaryWrite(XapManager.GetDefaultXap());
            }

            // 2.セッション情報からユーザーの情報を取得する。
            if (context.Session == null || context.Session["_userContext"] == null)
            {
                context.Response.BinaryWrite(XapManager.GetBeforeAuthenticationXap(app));
                return;
            }
            var userContext = context.Session["_userContext"] as UserContext;

            // 3.アプリケーション名とユーザー情報からユーザーに返却するXAPを決定する。
            var path = context.Server.MapPath(((Func<UserContext, string, string>)((u,appName)=>
            {
                if (appName == "app1" && u.UserId == "karua")
                    return @"\ClientBin\SilverlightApplication1.xap";
                else
                    return @"\ClientBin\SilverlightApplication2.xap";

            }))(userContext, app));

            // 4.XAPファイルが存在したら、XAPファイルを返却する。
            if (!File.Exists(path))
            { 
                context.Response.StatusCode = 404;
                context.Response.End();
                return;
            }
            context.Response.BinaryWrite(File.ReadAllBytes(path));
        }

        public bool IsReusable
        {
            get
            {
                return true;
            }
        }

    }
}

順番に見ていきましょう。

1.QueryStringからアプリケーション名を取得する。

通常であれば、Silverlightをロードする場合は次のようなHTMLでXAPファイルを指定します。

<object data="data:application/x-silverlight-2," 
        type="application/x-silverlight-2" width="100%" height="100%">
  <param name="source" value="/ClientBin/SilverlightApplication1.xap"/>
  <param name="onError" value="onSilverlightError" />
  <param name="background" value="white" />
  <param name="minRuntimeVersion" value="4.0.50401.0" />
  <param name="autoUpgrade" value="true" />
</object>

今回は作成したジェネリックハンドラーを指定し、xapパラメータをもとにロードするXAPファイルを切り替えます。もしXAPパラメーターが指定されなかった場合は、既定のXAPファイルがロードされるようにしておきましょう。

<object data="data:application/x-silverlight-2," 
        type="application/x-silverlight-2" width="100%" height="100%">
  <param name="source" value="/SilverlightVersionSelector.ashx?xap=app1"/>
  <param name="onError" value="onSilverlightError" />
  <param name="background" value="white" />
  <param name="minRuntimeVersion" value="4.0.50401.0" />
  <param name="autoUpgrade" value="true" />
</object>

2.セッション情報からユーザーの情報を取得する。

セッション情報から現在ログインしているユーザーの情報を取得します。ジェネリックハンドラーでセッション変数を利用する場合はIRequiresSessionStateインターフェイスを実装しないと、Session変数が取得できないので注意しましょう。ここでも取得できない場合にはログイン前のXAPファイルを返すようにしておきましょう。

3.アプリケーション名とユーザー情報からユーザーに返却するXAPを決定する。

今回のサンプルでは、単純にxapパラメーターがapp1で、セッション変数に格納されているユーザー名がkaruaだったらSilverlightApplication1.xapを、それ以外だったらSilverlightApplication2.xapを返すようにしていますが、本来でしたら、データベースなどのユーザー別の台帳のようなものを用意して検索するようにします。

4.XAPファイルが存在したら、XAPファイルを返却する。

3で取得したファイルが存在したら、ファイルの情報をバイナリーで読み出しHttpContextクラスのResponseプロパティーのBinaryWriteメソッドを使って書き出します。

広告
カテゴリー:Silverlight タグ: ,
  1. まだコメントはありません。
  1. No trackbacks yet.

コメントを残す

以下に詳細を記入するか、アイコンをクリックしてログインしてください。

WordPress.com ロゴ

WordPress.com アカウントを使ってコメントしています。 ログアウト / 変更 )

Twitter 画像

Twitter アカウントを使ってコメントしています。 ログアウト / 変更 )

Facebook の写真

Facebook アカウントを使ってコメントしています。 ログアウト / 変更 )

Google+ フォト

Google+ アカウントを使ってコメントしています。 ログアウト / 変更 )

%s と連携中

%d人のブロガーが「いいね」をつけました。