[AIR] SimpleLogger

Tags:

SimpleLogger

FlashやFlexのクラスオブジェクトArray, ArrayCollection, Objectの中身を最深層までモニターに表示するAdobe AIRアプリケーションです。中身を確認したいオブジェクトを送信専用クラス(SimpleLogger.as)の引数に渡すだけでモニターに中身が表示されます。一応既存のloggingツールと差別化されているはず。詳細は[AIR] SimpleLoggerよりどうぞ。

追記 2008/09/01

ログの消去ボタンの追加、スクロールバーの動作修正、ウィンドウの外観をOSデフォルトのものに変更。ThunderBoltもObject深層まで走査できるっぽいので差別化されてないかも。でもThunderBoltはでかくてダサい。

追記 2008/09/02

XMLオブジェクトの解析が可能になった。XMLだけ特別にツリー状に表示される。

追記 2008/09/04

英語ページ作成。日本語ページより見やすい気がする。

[Flex][Flash]Debug Loggingツール比較

Tags: , ,

サーバーから受信したxmlデータをActionScript Objectで受信したとき、格納したArrayCollection (Array)の構造を簡単に調べたいというのがそもそもの目的。いくつかあたってみたのでその簡単な使い方と個人的な感想を書き留める。Flex 3でしか確認していないので、Flashの場合は少し勝手が違うかもしれません。結論を先に言うと、Xray, ThunderBolt, Arthropodの中で目的を達成できたのはXrayのみ。個人的に気に入ったのはArthropod。

調べたこと

以下のようなxmlデータをHTTPServiceのレスポンスとして受け取りArrayCollectionに格納したとき、ネストした内容(id, name)がLoggingツールで見れるかどうか確認。

<?xml version="1.0" encoding="utf-8"?>

<users>
    <user>
        <id>1</id>
        <name>Chris Allen</name>
    </user>
    <user>
        <id>2</id>
        <name>Wade Arnold</name>
    </user>
    <user>
        <id>3</id>
        <name>Aral Balkan</name>
    </user>
    <user>
        <id>4</id>
        <name>Nicolas Cannasse</name>
    </user>
</users>

1. Xray

生のArrayCollectionの中身は見えなかったが、ArrayUtil.toArray()を用いて受信データをArrayCollection -> Arrayに変換すれば確認可能。ツール自体の機能で、ステージ上のオブジェクト全てのプロパティを丸見えにすることができ、さらにプロパティをXrayコンソールから動的にいじることができるのが便利。フレームレートがリアルタイムに確認できるので、例えば予定以下のパフォーマンスだった場合に、ボトルネックになる箇所を探せる可能性がある(アルファをいじったら改善された etc.)。難点は超不安定なところ。専用コンソール(.swf)がやたらと落ちる(起動中に止まる)。Macを再起動しないと再生できないような状態になることもしばしばで、使うのがためらわれる。現在開発進行中ではないことも理由かもしれない。

使い方

  1. osflash-xray - Google Code > Downloads > Xray_Flex2_Library_v0.5.swc をダウンロード(コネクター)。Flex3と名のつくものはなくてこれが最新バージョンになっている。
  2. Xray ( The AdminTool ) Open Source Flash > Downloads > Interfaceよりコンソールをダウンロード(SWF Onlyと書かれたもの)。これを使ってモニターすることになる。
  3. Flexプロジェクトにswcファイルにパスを通す。
    import com.blitzagency.xray.inspector.flex2.Flex2Xray;
    import com.blitzagency.xray.logger.XrayLog;

    をインポートし、それぞれのインスタンスを作成して、swfファイルを起動(例えばmyFlexと命名)。

    var xray:Flex2Xray = new Flex2Xray();
    var log:XrayLog = new XrayLog();
  4. Xrayコンソール(Xray.swf)を起動して左側のGoボタンを押すと調べたいswfファイルのモニタリングを開始する。
  5. myFlex内の調べたいオブジェクトに例えば以下のような処理を(myFlex内で)施すことでXray.swfコンソールで中身を確認できる。
    //ac is ArrayCollection receiving the xml data
    var ary:Array = ArrayUtil.toArray(ac);
    log.debug("Nested arrays:", ary);

Xray

2. Arthropod

シンプルでコンパクトで見た目もこぎれいなAIR製Logger。利用方法も簡単なので非常に良いと思うけど、目的は達成できず。ArrayColection、ArrayCollectionをArray変換したもの、ネストしたArrayともに視覚化できなかった。今回は結局何にもできなかったけど、個人的にはオススメ。

使い方

  1. Arthropod > DownloadよりASソース(1ファイル)とコンソール本体(.air)をダウンロード
  2. Flexプロジェクト(myFlex)にソースをインポート。
    import com.carlcalderon.arthropod.Debug;
  3. myFlex内の調べたいオブジェクトに以下のような処理を施し、myFlex.swfを起動するとArthropod.airで中身をモニターすることができる。Logging用のインスタンスを作らなくてよいところが便利。
    //ac is ArrayCollection receiving the xml data
    var ary:Array = ArrayUtil.toArray(ac);
    Debug.array(ary);
  4. 他にもいくつかユーティリティがあるがそれほど多くなく、長ったらしいドキュメンテーションもない。

Arthropod

3. ThunderBolt

Arthropodと同じくモニターはair製で、Flash Playerが吐くFlashlog.txtをモニターする作りになっている。ArrayCollection、ArrayCollectionをArray化したものの視覚化はできなかったが、例えば以下のようにネストしたArrayの中身は確認できた。

var ary:Array = [{id:"1",name:"Chris Allen"},
                {id:"2",name:"Wade Arnold"},
                {id:"3",name:"Aral Balkan"},
                {id:"4",name:"Nicolas Cannasse"}];

ただ、僕の目的は達成できておらず、さらに起動までの設定が少し面倒、モニターが無駄にでかい、なんか見た目がダサイというところが使う気を起こさせない。

使い方

設定についてはFlashのログ閲覧アプリThunderBoltをいれてみた|_level0.CUPPYが詳しいのでそちらを参照ください。少し補足しておくと、Flash PlayerにFlashlog.txt (Macの場合、/Users/USERNAME/Library/Preferences/Macromedia/Flash Player/Logs/flashlog.txt)というログファイルを吐き出させる設定が必要で、そのためには”/Users/USERNAME/mm.cfg”に以下の記述をする必要がある。

TraceOutputFileEnable=1

ThunderBolt

[Flash]パイチャート

Tags:

twitter円グラフ | ra66it.netがキレイだったんで真似てみた。円弧の描画はAS3CB Libraryを使った。画面クリックで描画再スタートします。

[Flash]パイチャート

E4Xで取得する方がAMFで取得するより5倍早い

Tags: , ,

Railsからの応答をE4Xで受信した場合とAMFで受信した場合を比較した。使ったのはidとnameからなる1000行のMySQLデータ。Flexからリクエストしてから応答までの時間を測定したところ、AMFの方が5倍も遅くなって困惑した。環境はFlex SDK 3.0, Ruby 1.8.6, Rails 2.1, MySQL 5.0.45で全て同じローカルマシン内。

Rails側

RubyAMFをインストールしたRailsプロジェクト内にUserモデルとUsersControllerを作成。UserモデルはMySQLのusersテーブル(id, name)とシンクロ済み(テストデータはgeneratedata.comで作成)。UsersControllerに以下のようにindexを記述。

class UsersController < ApplicationController

  def index
    @users = User.find(:all)
    respond_to do |format|
      format.xml {render :xml => @users} # For HTTPService
      format.amf {render :amf => @users} # For RemoteObject
    end
  end
end

AMFの結果をArrayCollectionで簡単に受け取れるようrubyamf_config.rbを一部修正。ただしこの設定はRemoteObjectに対して有効で、NetConnectionではArrayCollectionが使えないため無効。

require ‘app/configuration’
module RubyAMF
  module Configuration
    ClassMappings.assume_types = true
    ClassMappings.use_array_collection = true
  end
end

Flex側 (HTTPService - E4X)

load()とonResult()までの時間を10回測った。測定時間はTextAreaに、受信内容はDataGridにそれぞれ表示。

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml">

    <mx:HBox width="100%" height="100%">
        <mx:DataGrid id="dg" width="50%" height="100%">
            <mx:columns>
                <mx:DataGridColumn dataField="id"/>
                <mx:DataGridColumn dataField="name"/>
            </mx:columns>
        </mx:DataGrid>
        <mx:TextArea id="loadText" width="50%" height="100%"/>
    </mx:HBox>
    <mx:Button label="Load" width="100" height="30" click="load(event)" />

    <mx:Script>
        <![CDATA[
            import mx.rpc.http.HTTPService;
            import mx.rpc.events.ResultEvent;
            import mx.rpc.events.FaultEvent;
            import flash.utils.getTimer;

            private var _start:uint;
            private var _str:String = "";

            private function load(e:Event):void{
                var req:HTTPService = new HTTPService();
                req.url = "http://127.0.0.1:3000/users.xml";
                req.resultFormat = HTTPService.RESULT_FORMAT_E4X;
                req.send();
                req.addEventListener(ResultEvent.RESULT,onResult);
                req.addEventListener(FaultEvent.FAULT,onFault);
                _start = getTimer();
            }

            private function onResult(e:ResultEvent):void{
                dg.dataProvider = e.target.lastResult.user;
                _str += (getTimer() - _start).toString() + " msec\n";
                loadText.text = _str;
            }

            private function onFault(e:FaultEvent):void{
                loadText.text = e.fault.faultDetail;
            }
        ]]>
    </mx:Script>
</mx:Application>

Flex側 (RemoteObject - AMF)

MXMLの骨格はHTTPServiceを使う場合と同じ。スクリプト部分とservices-config.xmlの設定は以下の通り。

スクリプト部分

<mx:Script>
    <![CDATA[
        import mx.rpc.remoting.RemoteObject;
        import mx.rpc.events.ResultEvent;
        import mx.rpc.events.FaultEvent;
        import flash.utils.getTimer;

        private var _start:uint;
        private var _str:String = "";

        private function load(e:Event):void{
            var ro:RemoteObject = new RemoteObject();
            ro.source = "UsersController";
            ro.destination = "rubyamf";
            ro.index();
            ro.addEventListener(ResultEvent.RESULT,onResult);
            ro.addEventListener(FaultEvent.FAULT,onFault);
            _start = getTimer();
        }

        private function onResult(e:ResultEvent):void{
            dg.dataProvider = e.result;
            _str += (getTimer() - _start).toString() + " msec\n";
            loadText.text = _str;
        }

        private function onFault(e:FaultEvent):void{
            loadText.text = e.fault.faultString;
        }
    ]]>
</mx:Script>

services-config.xml (コンパイラオプションに追加)

<?xml version="1.0" encoding="UTF-8"?>
<services-config>
    <services>
        <service id="remoting-service"
            class="flex.messaging.services.RemotingService"
            messageTypes="flex.messaging.messages.RemotingMessage">
            <destination id="rubyamf">
                <channels>
                    <channel ref="ch-rubyamf" />
                </channels>
                <properties>
                    <source>*</source>
                </properties>
            </destination>
        </service>
    </services>

    <channels>
        <channel-definition id="ch-rubyamf"
            class="mx.messaging.channels.AMFChannel">
            <endpoint uri="http://127.0.0.1:3000/rubyamf/gateway"
                class="flex.messaging.endpoints.AMFEndpoint" />
        </channel-definition>
    </channels>
</services-config>

結果

HTTPService - E4X

load()からonResult()までの時間測定は右テキストエリア内(msec)。10回測定でだいたい0.5-0.6秒。ちなみにRESULT_FORMAT_OBJECT(ActionScript Object)で受信すると0.7-0.8秒ぐらいだった。

RemoteObject - AMF

HTTPServiceの場合と同じ測定で一回あたり約3秒。

AMF、通信設定が面倒なくせにすげー遅い。Ajax and Flex Data Loading Benchmarks | James Ward - RIA Cowboyの結果と違いすぎる。どっか間違ってる?

WordpressやFlickrのファイルアップロードがFlash Player 10で機能しない理由

Tags:

Flash Player 10だとWordpressのアップローダー(.swf)のダイアログがポップアップせず、だからファイルアップロードしようにもできなかった。何が悪いのかわからないままFlash Player 10をアンインストールしていたのだけどセキュリティの問題らしい。

The latest one that’s bugging me is a Flash 10 Player change that only allows you to open a file browse dialog via a direct user interaction such as a button push/mouse click. The idea here is to prevent malicious code from opening a file dialog and perhaps making you think it is for something else, and you wind up uploading some sensitive data to someone else’s server. I can see the point, but it’s creating some havoc.

Flash Player 10 Beta breaking WordPress, Flickr, other uploaders | BIT-101 Blog

つまりローカルファイルにアクセスできるようになった分セキュリティが厳しくなり、マウスクリック等の直接的なユーザーインタラクションのみFileReference.browse()が発動するようになっているのが原因らしい。WordpressやFlickrなどJavaScriptなどでアップローダーを遠隔発動させているところは軒並みアウトということになる。

Thanks Keith Peters, I have been suffered from the problem without any ideas.

関連リンク:

The Flash Blog » Flash Player 10 FileReference Changes
[FlashPlayer10]Flash Player 10自体のバグ・10が原因の不具合

追記 2008/08/20

修正じゃなくて仕様になるっぽい。

FileReference.browse() と FileReference.download() の呼び出しが、ユーザ操作により発生したイベント内に制限されるようになります。Flsh Player 10 以降、これらのメソッドを使用するには、マウスのクリックやキーの押下等によるイベントから呼び出すよう記述する必要があります。

akihiro kamijo: Flash Player 10 におけるセキュリティ変更

追記 2008/09/15

Wordpress 2.6ではFlashアップローダーを使わないように設定できるので問題ない。2.5以前はプラグインでFlashアップローダーをdisableにできる。詳しくはデバッグ機能付きFlash Player 10のブラウザプラグイン - blog Boreal Kissを参照。

Next Page →