[symfony]Webデバッグツールバーにピークメモリを表示する

Posted under php,symfony by uechoco on 火曜日 8 12月 2009 at 23 : 41 : 46

知りませんでした。symfonyのWebデバッグツールバーに表示されているメモリ使用量は、メモリの最大使用量ではなかったのです現在の確保されたメモリ量というのが正しいです。これってsymfony使いの常識ですか?

当然、メモリの最大使用量を表示したいですよね。symfony 1.2以上であれば、簡単に実装できます。(symfony 1.0をお使いの方は、sfWebDebugで、より正確なメモリ使用量を見るには - Sooeyをご覧ください。)

symfonyのWebデバッグツールバーのカスタマイズ方法は、Cookbookにしっかりと載っているのです。今回参考にするのは、The symfony Cookbook | Webデバッグツールバーをカスタマイズする方法 | symfony | Web PHP Frameworkです。実際にやってみましょう。

まずはメモリの最大使用量を表示するためのsfWebDebugPanelクラスの派生クラスを作成します。sfWebDebugPanelMemoryクラスをほんの少しだけ変えただけのクラスです。libフォルダなどに作りましょう。

PHP:
  1. <?php
  2.  
  3. /**
  4.  * sfWebDebugPanelPeakMemory adds a panel to the web debug toolbar with the peak memory used by the script.
  5.  *
  6.  * @package    symfony
  7.  * @subpackage debug
  8.  */
  9. class sfWebDebugPanelPeakMemory extends sfWebDebugPanel
  10. {
  11.   public function getTitle()
  12.   {
  13.     if (function_exists('memory_get_peak_usage'))
  14.     {
  15.       $totalMemory = sprintf('%.1f', (memory_get_peak_usage() / 1024));
  16.  
  17.       return '<img src="'.$this->webDebug->getOption('image_root_path').'/memory.png" alt="Peak Memory" /> peak:'.$totalMemory.' KB';
  18.     }
  19.   }
  20.  
  21.   public function getPanelTitle()
  22.   {
  23.   }
  24.  
  25.   public function getPanelContent()
  26.   {
  27.   }
  28. }

お気づきかと思いますが、Webデバッグツールバーの1つ1つの項目はsfWebDebugPanelクラスの派生クラスです。構造化がうまくなされているので、追加も簡単という訳です。

次に、Webデバッグツールバーに登録します。今回はプロジェクト全体で適用したいので、ProjectConfiguration.class.phpを変更します。frontendConfiguration.class.phpでも同じコードで動きます。

PHP:
  1. class ProjectConfiguration extends sfProjectConfiguration
  2. {
  3.   public function setup()
  4.   {
  5.     // ...
  6.     $this->dispatcher->connect('debug.web.load_panels', array($this, 'configureWebDebugToolbar'));
  7.   }
  8.  
  9.   public function configureWebDebugToolbar(sfEvent $event)
  10.   {
  11.     $webDebugToolbar = $event->getSubject();
  12.     $webDebugToolbar->setPanel('peak_memory', new sfWebDebugPanelPeakMemory($webDebugToolbar));
  13.     $webDebugToolbar->removePanel('memory');
  14.   }
  15.  
  16. }

字面でなんとなくわかるかもしれませんが、Webデバッグツールバーのロード時にconfigureWebDebugToolbar()メソッドを呼び出すように登録しています。メソッド内では、さきほど作成した最大使用量を表示するパネルを追加し、代わりに元々あったメモリ表示のパネルを削除しています。

実際に使用したときのWebデバッグツールバーがこのようになります。
sfWebDebugPanelPeakMemory
上記sfWebDebugPanelPeakMemoryクラスの中で、わかりやすく「peak:」を表示するようにしています。

今一度、symfonyを見直してみるのもいいかもしれませんね。


[OpenPNE3]opFreepagePluginをgithubに移行しました。

Posted under OpenPNE3,php,symfony by uechoco on 火曜日 1 12月 2009 at 00 : 22 : 59

OpenPNE 3.0.0がリリースされて間もない頃、[OpenPNE3]管理画面付きプラグイン(opFreepagePlugin)#1 開発準備、DBスキーマの設定の全6回のシリーズで、フリーページ機能を作るという目的で、OpenPNE3のプラグインの作成方法を公開していました。

OpenPNE3の開発環境もだいぶ変化してきており、メインコードはgithubに、BTSはredmineにそれぞれ移行しています。それに合わせて、プラグインも登録できるようになっていることを、手嶋屋の方から教えていただきました。

OpenPNE3自体は3.1系に突入し、symfony 1.4化&ORMのDoctrine化が進行していますので、opFreepagePluginはレガシーコードになっています。そして、サンプルで作っているので、日本語パラダイスで、国際化に対応しておらず、表示もしょぼいです(笑

それでも、せっかくプラグインの登録ができるとのことでしたので、redmineに登録してみました。そして、opFreepagePluginのソースコードをgithub.comで公開しました。

gitやredmineなどの慣れない操作、そしてsymfony 1.4やDoctrineなどの慣れないコードがいろいろありますが、せっかくの機会ですので、ちょっとずつ改善していこうかと思います。


[SQL]都道府県コードに沿ったSQL

Posted under CakePHP,php,symfony by uechoco on 月曜日 21 9月 2009 at 11 : 27 : 46

適当なアプリを作ると、都道府県テーブルってよく作るよなってことで、SQLを備忘録で貼っときます。HTMLのセレクトボックスで公開していたり、同じようなSQLを公開している人はもちろん居るのですが、symfonyやCakePHPのようなCoCフレームワークのカラム名のものがなかったので、自分のために貼っときます。一応MySQLばっか使うので、MySQLの出力結果になっています。適当にENGINEとか変えれば他でも使えます。もちろん、JIS X 0401に準拠した都道府県コードを使っています。

CREATE文(utf8を想定)

SQL:
  1. DROP TABLE IF EXISTS `prefs`;
  2. CREATE TABLE IF NOT EXISTS `prefs` (
  3.   `id` int(10) UNSIGNED NOT NULL,
  4.   `name` varchar(5) NOT NULL,
  5.   PRIMARY KEY  (`id`)
  6. ) ENGINE=MyISAM  DEFAULT CHARSET=utf8;

INSERT文

SQL:
  1. INSERT INTO `prefs` (`id`, `name`) VALUES
  2. (1, '北海道'),
  3. (2, '青森県'),
  4. (3, '岩手県'),
  5. (4, '宮城県'),
  6. (5, '秋田県'),
  7. (6, '山形県'),
  8. (7, '福島県'),
  9. (8, '茨城県'),
  10. (9, '栃木県'),
  11. (10, '群馬県'),
  12. (11, '埼玉県'),
  13. (12, '千葉県'),
  14. (13, '東京都'),
  15. (14, '神奈川県'),
  16. (15, '新潟県'),
  17. (16, '富山県'),
  18. (17, '石川県'),
  19. (18, '福井県'),
  20. (19, '山梨県'),
  21. (20, '長野県'),
  22. (21, '岐阜県'),
  23. (22, '静岡県'),
  24. (23, '愛知県'),
  25. (24, '三重県'),
  26. (25, '滋賀県'),
  27. (26, '京都府'),
  28. (27, '大阪府'),
  29. (28, '兵庫県'),
  30. (29, '奈良県'),
  31. (30, '和歌山県'),
  32. (31, '鳥取県'),
  33. (32, '島根県'),
  34. (33, '岡山県'),
  35. (34, '広島県'),
  36. (35, '山口県'),
  37. (36, '徳島県'),
  38. (37, '香川県'),
  39. (38, '愛媛県'),
  40. (39, '高知県'),
  41. (40, '福岡県'),
  42. (41, '佐賀県'),
  43. (42, '長崎県'),
  44. (43, '熊本県'),
  45. (44, '大分県'),
  46. (45, '宮崎県'),
  47. (46, '鹿児島県'),
  48. (47, '沖縄県');

一応HTMLの<select>タグ形式

HTML:
  1. <select name="pref_id">
  2.   <option value="1">北海道</option>
  3.   <option value="2">青森県</option>
  4.   <option value="3">岩手県</option>
  5.   <option value="4">宮城県</option>
  6.   <option value="5">秋田県</option>
  7.   <option value="6">山形県</option>
  8.   <option value="7">福島県</option>
  9.   <option value="8">茨城県</option>
  10.   <option value="9">栃木県</option>
  11.   <option value="10">群馬県</option>
  12.   <option value="11">埼玉県</option>
  13.   <option value="12">千葉県</option>
  14.   <option value="13">東京都</option>
  15.   <option value="14">神奈川県</option>
  16.   <option value="15">新潟県</option>
  17.   <option value="16">富山県</option>
  18.   <option value="17">石川県</option>
  19.   <option value="18">福井県</option>
  20.   <option value="19">山梨県</option>
  21.   <option value="20">長野県</option>
  22.   <option value="21">岐阜県</option>
  23.   <option value="22">静岡県</option>
  24.   <option value="23">愛知県</option>
  25.   <option value="24">三重県</option>
  26.   <option value="25">滋賀県</option>
  27.   <option value="26">京都府</option>
  28.   <option value="27">大阪府</option>
  29.   <option value="28">兵庫県</option>
  30.   <option value="29">奈良県</option>
  31.   <option value="30">和歌山県</option>
  32.   <option value="31">鳥取県</option>
  33.   <option value="32">島根県</option>
  34.   <option value="33">岡山県</option>
  35.   <option value="34">広島県</option>
  36.   <option value="35">山口県</option>
  37.   <option value="36">徳島県</option>
  38.   <option value="37">香川県</option>
  39.   <option value="38">愛媛県</option>
  40.   <option value="39">高知県</option>
  41.   <option value="40">福岡県</option>
  42.   <option value="41">佐賀県</option>
  43.   <option value="42">長崎県</option>
  44.   <option value="43">熊本県</option>
  45.   <option value="44">大分県</option>
  46.   <option value="45">宮崎県</option>
  47.   <option value="46">鹿児島県</option>
  48.   <option value="47">沖縄県</option>

symfony系のYAML定義(symfony的にはテーブル名の最後のsはつけない方が一般的かな?)

TEXT:
  1. propel:
  2.   prefs:
  3.     _attributes: { phpName: Prefs }
  4.     id:
  5.     name: { type: VARCHAR, size: '5', required: true, defaultValue: '' }

そのうちフレームワーク毎のモデルクラスとかも貼っておこうかな。


[Mac]netatalkの.AppleDoubleでsymfonyコマンドがつまずく時がある

Posted under Linux,mac入門記,php,symfony by uechoco on 日曜日 13 9月 2009 at 02 : 03 : 07

タイトルでもわかるとおり、非常に限定的な環境でsymfonyを使ったときにハマってしまったので、今後、私と同じようなマニアックな環境でハマってしまった人がググってくれることを期待して備忘録を残します。

さて、私はMac OS X上にVMware Fusion 2を導入していて、会社での開発をVM上のCentOS 5で行っています。開発ではMacのCocoaに対応したEclipse 3.5を主にしようしています。EclipseでVM上のファイルを直接読み書きするため、netatalkというMac版sambaとも言えるソフトウェアをCentOSに導入して、MacとLinux間の共有を行っています。ここら辺のお話は、以前3回に渡って書いたnetatalk導入のブログの記事を参照してもらえればと思います。

Mac OS Xでで外部ストレージ(NFS)などを用いるとき、ファイルのメタ情報を保存するために、netatalkでは.AppleDoubleというフォルダを各フォルダごとに生成し、そのフォルダの中に元ファイル名と同名のファイル名でメタ情報を格納します。※WikipediaのAppleSingleにAppleDoubleについて記載があります。netatalkではnoadoubleというオプションがあり、「必要なければ.AppleDoubleを作らない」という設定にすることができるのですが、必要ある場合は当然作成されてしまいます。例えば、Eclipseからアクセスして保存とかをすると、.AppleDoubleが作られてしまうような気がします。

CentOS上にsymfonyを展開してMacからターミナルで操ろうとしたとき、基本的にはsymfonyのあの深いフォルダ階層のすべてに.AppleDoubleが生成されてしまうということです。そこでこまったのがsymfonyコマンド。propel:build-xxxとかやろうとすると、どうも.AppleDoubleのせいでうまくいかないことがあります。

例えばpropel:build-model

Bash:
  1. [ueno@localhost project]$ ./symfony propel:build-model
  2.   Unable to parse file "/path/to/project/config/.AppleDouble/schema.yml": Unable to parse line 1 (

なぜか.AppleDoubleフォルダ内のshema.ymlがパースできないと言われてしまいます。前述の通り、.AppleDoubleフォルダの中に元ファイル名と同名のメタファイルを生成しますので、もしかしたらschema.ymlという名前に反応してしまったのかもしれません。一応propel:build-modelのヘルプを見てみましょう。

Bash:
  1. [ueno@localhost project]$ ./symfony help propel:build-model
  2. Usage:
  3.  symfony propel:build-model [--phing-arg="..."]
  4.  
  5. Aliases: propel-build-model
  6.  
  7. Options:
  8.  --phing-arg  Arbitrary phing argument (multiple values allowed)
  9.  
  10. Description:
  11.  The propel:build-model task creates model classes from the schema:
  12.  
  13.    ./symfony propel:build-model
  14.  
  15.  The task read the schema information in config/*schema.xml and/or
  16.  config/*schema.yml from the project and all installed plugins.
  17.  
  18.  You mix and match YML and XML schema files. The task will convert
  19.  YML ones to XML before calling the Propel task.
  20.  
  21.  The model classes files are created in lib/model.
  22.  
  23.  This task never overrides custom classes in lib/model.
  24.  It only replaces files in lib/model/om and lib/model/map.

検索条件はconfig/*schema.ymlと書いてありますので、フォルダも引っかかってしまうようです。

で解決策はどうするのか?propel:build-xxx系のコマンドなどでは、symfonyライブラリの中に含まれるsfFinder.class.phpというユーティリティを利用しています。この中に、指定されたルールに基づいて、ファイルやディレクトリを検索するというin()メソッドがあるのですが、この中で、バージョン管理ソフトのディレクトリを無視するようなプログラムの掛かれば部分があります。symfony 1.2.8のlib/symfony/util/sfFinder.class.phpの341行目付近です。

php:
  1. /**
  2.    * Searches files and directories which match defined rules.
  3.    *
  4.    * @return array list of files and directories
  5.    */
  6.   public function in()
  7.   {
  8.     $files    = array();
  9.     $here_dir = getcwd();
  10.  
  11.     $finder = clone $this;
  12.  
  13.     if ($this->ignore_version_control)
  14.     {
  15.       $ignores = array('.svn', '_svn', 'CVS', '_darcs', '.arch-params', '.monotone', '.bzr', '.git', '.hg');
  16.  
  17.       $finder->discard($ignores)->prune($ignores);
  18.     }

svnやらcvsやらgitやらのメタ情報を保存するフォルダの除外指定が列挙されています。ならばここにAppleDoubleをいれればいいんでないか?ということで、修正多野がこちら

php:
  1. if ($this->ignore_version_control)
  2.     {
  3.       $ignores = array('.svn', '_svn', 'CVS', '_darcs', '.arch-params', '.monotone', '.bzr', '.git', '.hg', '.AppleDouble');
  4.  
  5.       $finder->discard($ignores)->prune($ignores);
  6.     }

symfonyのコアを書き換えるのはどうかと思ったのですが、この設定を付け加えるだけでnetatalk環境でのsymfonyコマンドが問題なく使えるようになったので開発が進みそうです。

まぁ、こんな環境でsymfony使う人はなかなか居ないと思いますが。。。


[OpenPNE3]管理画面付きプラグイン(opFreepagePlugin)#6 プラグインのパッケージング

Posted under OpenPNE3,php,symfony by uechoco on 土曜日 7 3月 2009 at 01 : 05 : 26

前回まででopFreepagePluginの開発部分は完了しました。今回はプラグインのバージョン情報を定義し、アーカイブ化することで、外部に公開できるファイルにしたいと思います。なお、このプラグインのパッケージング方法はOpenPNE 3.0.0で確認しているものです。近いうちにプラグインリリース用symfony拡張コマンドを充実させる予定もあるようですので、その点は加味してご覧ください。

プラグインのパッケージングは非常に簡単です。まずはプラグイン情報が書かれたpackage.xmlを作成します。これもコマンド1つで作成できます。今回はopFreepagePluginをバージョン0.9.0、ステータスをbeta、リリース文を"First release"とします。以下のようなコマンドになります。

BASH:
  1. ./symfony opPlugin:define opFreepagePlugin 0.9.0 beta "First release"

以下のような出力がなされます。

BASH:
  1. [uechooc@localhost pneroot]$ ./symfony opPlugin:define opFreepagePlugin 0.9.0 beta "First release"
  2. &gt;&gt; sfPearFrontendPlugin Attempting to discover channel "plugins.openpne.jp"...
  3. &gt;&gt; sfPearFrontendPlugin downloading channel.xml ...
  4. &gt;&gt; sfPearFrontendPlugin Starting to download channel.xml (598 bytes)
  5. &gt;&gt; sfPearFrontendPlugin .
  6. &gt;&gt; sfPearFrontendPlugin ...done: 598 bytes
  7. &gt;&gt; sfPearFrontendPlugin Auto-discovered channel "plugins.openpne.jp", alias
  8. &gt;&gt; sfPearFrontendPlugin "plugins.openpne.jp", adding to registry
  9. &gt;&gt; sfPearFrontendPlugin Attempting to discover channel "pear.symfony-project.com"...
  10. &gt;&gt; sfPearFrontendPlugin downloading channel.xml ...
  11. &gt;&gt; sfPearFrontendPlugin Starting to download channel.xml (663 bytes)
  12. &gt;&gt; sfPearFrontendPlugin ...done: 663 bytes
  13. &gt;&gt; sfPearFrontendPlugin Auto-discovered channel "pear.symfony-project.com", alias
  14. &gt;&gt; sfPearFrontendPlugin "symfony", adding to registry
  15. &gt;&gt; sfPearFrontendPlugin Attempting to discover channel
  16. &gt;&gt; sfPearFrontendPlugin "plugins.symfony-project.org"...
  17. &gt;&gt; sfPearFrontendPlugin downloading channel.xml ...
  18. &gt;&gt; sfPearFrontendPlugin Starting to download channel.xml (639 bytes)
  19. &gt;&gt; sfPearFrontendPlugin ...done: 639 bytes
  20. &gt;&gt; sfPearFrontendPlugin Auto-discovered channel "plugins.symfony-project.org", alias
  21. &gt;&gt; sfPearFrontendPlugin "symfony-plugins", adding to registry
  22. &gt;&gt; sfPearFrontendPlugin Analyzing
  23. &gt;&gt; sfPearFrontendPlugin apps/mobile_frontend/modules/freepage/actions/actions.class.php
  24. &gt;&gt; sfPearFrontendPlugin Analyzing
  25. &gt;&gt; sfPearFrontendPlugin apps/mobile_frontend/modules/freepage/templates/indexSuccess.php
  26. &gt;&gt; sfPearFrontendPlugin Analyzing
  27. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/actions/actions.class.php
  28. &gt;&gt; sfPearFrontendPlugin Analyzing
  29. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/templates/editSuccess.php
  30. &gt;&gt; sfPearFrontendPlugin Analyzing
  31. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/templates/indexSuccess.php
  32. &gt;&gt; sfPearFrontendPlugin Analyzing
  33. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/templates/listSuccess.php
  34. &gt;&gt; sfPearFrontendPlugin Analyzing
  35. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/templates/newSuccess.php
  36. &gt;&gt; sfPearFrontendPlugin Analyzing
  37. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/templates/_form.php
  38. &gt;&gt; sfPearFrontendPlugin Analyzing
  39. &gt;&gt; sfPearFrontendPlugin apps/pc_backend/modules/opFreepagePlugin/templates/_submenu.php
  40. &gt;&gt; sfPearFrontendPlugin Analyzing
  41. &gt;&gt; sfPearFrontendPlugin apps/pc_frontend/modules/freepage/actions/actions.class.php
  42. &gt;&gt; sfPearFrontendPlugin Analyzing
  43. &gt;&gt; sfPearFrontendPlugin apps/pc_frontend/modules/freepage/templates/indexSuccess.php
  44. &gt;&gt; sfPearFrontendPlugin Analyzing config/config.php
  45. &gt;&gt; sfPearFrontendPlugin Analyzing lib/opFreepagePluginRouting.class.php
  46. &gt;&gt; sfPearFrontendPlugin Analyzing lib/filter/FreepageFormFilter.class.php
  47. &gt;&gt; sfPearFrontendPlugin Analyzing lib/filter/base/BaseFreepageFormFilter.class.php
  48. &gt;&gt; sfPearFrontendPlugin Analyzing lib/form/FreepageForm.class.php
  49. &gt;&gt; sfPearFrontendPlugin Analyzing lib/form/base/BaseFreepageForm.class.php
  50. &gt;&gt; sfPearFrontendPlugin Analyzing lib/model/Freepage.php
  51. &gt;&gt; sfPearFrontendPlugin Analyzing lib/model/FreepagePeer.php
  52. &gt;&gt; sfPearFrontendPlugin Analyzing lib/model/map/FreepageMapBuilder.php
  53. &gt;&gt; sfPearFrontendPlugin Analyzing lib/model/om/BaseFreepage.php
  54. &gt;&gt; sfPearFrontendPlugin Analyzing lib/model/om/BaseFreepagePeer.php

いろいろなファイルを解析していますが、これらはパッケージ内に含まれるファイル一覧を作成し、それぞれのファイルのチェックサムを取得している処理です。package.xmlには様々な設定項目があるのですが、コマンドラインで指定できる項目以外は固定で挿入されてしまいます。例えば、ライセンスはApache Licenseで固定されています。

パッケージ情報が生成できたので、アーカイブを作成します。これもコマンド一発です。以下のコマンドはopFreepagePluginのアーカイブををカレントディレクトリに作成します。

BASH:
  1. ./symfony opPlugin:archive opFreepagePlugin ./

このコマンドを実行後、カレントディレクトリにはopFreepagePlugin-0.9.0.tgzというファイルが作成されています。バージョン名が付加されたtgzファイルですね。あとはこのファイルを公開すれば完成です。PEARのチャンネルサーバがあればコマンドラインからのインストールにも対応できると思うのでいいですね。plugins.openpne.jpなんかが一般開放されるとうれしいのですが。

以上でこの連載シリーズは終了です。OpnePNE3のプラグインが増えるといいですね!技術的な知識がある運営者ならばプラグインで独自の機能を作って自分のSNSを盛り上げることも可能でしょう。OpenSocialとsymfonyプラグインの双方で拡張できるOpenPNE3の可能性は無限大です!


« 前ページへ次ページへ »

Copyright © 2012 うえちょこ@ぼろぐ. WP Theme created by Web Top.