14日目: フィード
昨日、あなたは自身の symfony アプリケーションの開発を始めました。今やめないでください。symfony をさらに学ぶにしたがい、アプリケーションに新しい機能を追加しようとし、どこかでそれをホストしようとし、コミュニティと共有しようとしてください。
今日から全く違うことをします。求人情報を探している場合、新しいものが投稿されるとすぐに知らせてくれることが望ましいでしょう。1時間ごとに Web サイトを確認するのはあまり便利ではないので、Jobeet のユーザーに最新情報を提供するために求人情報のフィードを追加します。
フォーマット
symfony フレームワークはフォーマットと mime-yype を標準サポートします。これは同じ Model と Controller がリクエストされたフォーマットに基づいて異なるテンプレートを持てることを意味します。デフォルトのフォーマットは HTML ですが、txt
、js
、css
、json
、xml
、rdf
もしくは atom
のように、symfony は~くつかのフォーマットをそのまま使えます。
フォーマットは request オブジェクトの setRequestFormat()
メソッドを使って設定できます:
$request->setRequestFormat('xml');
しかし、たいていの場合、フォーマットは URL に埋め込まれます。このケースでは、特別な変数の sf_format
が対応するルートで使われる場合、symfony が設定します。求人リストでは、リストの URL は次の通りです:
http://www.jobeet.com.localhost/frontend_dev.php/job
この URL は次の内容と同等です:
http://www.jobeet.com.localhost/frontend_dev.php/job.html
両方の URL は同等です。sfPropelRouteCollection
sfDoctrineRouteCollection
クラスによって生成されたルートは拡張子として sf_format
を持ち、html
はデフォルトのフォーマットだからです。app:routes
タスクを実行すれば自身で確認できます:
フィード
最新の求人フィード
異なるフォーマットをサポートすることは異なるテンプレートを作ることと同じくらい簡単です。最新の求人用に Atom フィードを作るには、indexSuccess.atom.php
テンプレートを作ります:
<!-- apps/frontend/modules/job/templates/indexSuccess.atom.php --> <?xml version="1.0" encoding="utf-8"?> <feed xmlns="http://www.w3.org/2005/Atom"> <title>Jobeet</title> <subtitle>Latest Jobs</subtitle> <link href="" rel="self"/> <link href=""/> <updated></updated> <author><name>Jobeet</name></author> <id>Unique Id</id> <entry> <title>Job title</title> <link href="" /> <id>Unique id</id> <updated></updated> <summary>Job description</summary> <author><name>Company</name></author> </entry> </feed>
テンプレートの名前
html
は Web アプリケーションでもっとも使われる共通のフォーマットなので、テンプレートの名前から省略できます。indexSuccess.php
とindexSuccess.html.php
テンプレートは同等で symfony は最初に見つけた方を使います。なぜデフォルトでテンプレートのサフィックスは
Success
なのでしょうか?アクションはレンダリングするテンプレートを指定して返すことができます。アクションが何も返さない場合、次のコードと同等です:return sfView::SUCCESS; // == 'Success'サフィックスを変更したい場合、次のように何かを返せば良いだけです:
return sfView::ERROR; // == 'Error' return 'Foo';昨日見たように、テンプレートの名前は
setTemplate()
メソッドを利用して変更することもできます:$this->setTemplate('foo');
デフォルトでは、symfony はフォーマットに従って Content-Type
レスポンスを変更します。なお、HTML ではないすべてのフォーマットにはレイアウトは無効です。Atom フィードに関して、symfony は Content-Type
を application/atom+xml; charset=utf-8
に変更します。
Jobeet のフッターにおいて、フィードへのリンクを追加します:
<!-- apps/frontend/templates/layout.php --> <li class="feed"> <a href="<?php echo url_for('job', array('sf_format' => 'atom')) ?>">Full feed</a> </li>
内部 URI は変数として sf_format
を使用した求人リストと同じです。
ブラウザがフィードを自動的に検出できるように <link>
タグをレイアウトの head セクションに追加します:
<!-- apps/frontend/templates/layout.php --> <link rel="alternate" type="application/atom+xml" title="Latest Jobs" href="<?php echo url_for('job', array('sf_format' => 'atom'), true) ?>" />
href
リンク属性に関して、url_for()
ヘルパーの第2引数により絶対 URL が使われます。
Atom テンプレートのヘッダーを次のコードで置き換えます:
<!-- apps/frontend/modules/job/templates/indexSuccess.atom.php --> <title>Jobeet</title> <subtitle>Latest Jobs</subtitle> <link href="<?php echo url_for('job', array('sf_format' => 'atom'), true) ?>" rel="self"/> <link href="<?php echo url_for('homepage', true) ?>"/>
getCreatedAt('U')) ?> getLatestPost()->getDateTimeObject('created_at')->format('U')) ?> Jobeet 'atom'), true)) ?>
タイムスタンプを日付として得るための getCreatedAt()
format()
の引数として使う U
の使い方に気が付いてください。最新の投稿に日付を得るために、getLatestPost()
を作ります:
[php] // lib/model/JobeetJobPeer.php class JobeetJobPeer extends BaseJobeetJobPeer { static public function getLatestPost() { $criteria = new Criteria(); self::addActiveJobsCriteria($criteria);
return JobeetJobPeer::doSelectOne($criteria);
}
// ...
}
[php] // lib/model/doctrine/JobeetJobTable.class.php class JobeetJobTable extends Doctrine_Table { public function getLatestPost() { $q = Doctrine_Query::create()->from('JobeetJob j');
$this->addActiveJobsQuery($q);
return $q->fetchOne();
}
// ...
}
フィードエントリーは次のコードで生成されます:
<!-- apps/frontend/modules/job/templates/indexSuccess.atom.php --> <?php use_helper('Text') ?> <?php foreach ($categories as $category): ?> <?php foreach ($category->getActiveJobs(sfConfig::get('app_max_jobs_on_homepage')) as $job): ?> <entry> <title> <?php echo $job->getPosition() ?> (<?php echo $job->getLocation() ?>) </title> <link href="<?php echo url_for('job_show_user', $job, true) ?>" /> <id><?php echo sha1($job->getId()) ?></id>
</summary>
<author>
<name><?php echo $job->getCompany() ?></name>
</author>
</entry>
<?php endforeach ?>
<?php endforeach ?>
リクエストオブジェクト ($sf_request
) の getHost()
メソッドは現在のホストを返します。企業ロゴの絶対パスを作る際に役立ちます。
フィードを作成する際に、
curl
もしくはwget
のようなコマンドラインツールを使えばフィードの実際の内容を見れるのでデバッグが楽になります。
カテゴリの最新求人フィード
Jobeet のゴールの1つはよりターゲットを絞った求人を見つけるための手助けになることです。ですので、それぞれのカテゴリ用のフィードを提供する必要があります。
最初に、異なるフォーマットのサポートを追加するために category
ルートを更新しましょう:
これで、category
ルートは html
と atom
フォーマットの両方を理解します。テンプレートのカテゴリフィードへのリンクを更新します:
<!-- apps/frontend/modules/job/templates/indexSuccess.php --> <div class="feed"> <a href="<?php echo url_for('category', array('sf_subject' => $category, 'sf_format' => 'atom')) ?>">Feed</a> </div> <!-- apps/frontend/modules/category/templates/showSuccess.php --> <div class="feed"> <a href="<?php echo url_for('category', array('sf_subject' => $category, 'sf_format' => 'atom')) ?>">Feed</a> </div>
最後のステップは showSuccess.atom.php
テンプレートを作ることです。しかしこのフィードは求人の一覧も表示するので、_list.atom.php
パーシャルを作ることでフィードエントリを生成するコードをリファクタリングできます。html
フォーマットのように、パーシャルはフォーマット固有です:
<!-- apps/frontend/modules/job/templates/_list.atom.php --> <?php use_helper('Text') ?> <?php foreach ($jobs as $job): ?> <entry> <title><?php echo $job->getPosition() ?> (<?php echo $job->getLocation() ?>)</title> <link href="<?php echo url_for('job_show_user', $job, true) ?>" /> <id><?php echo sha1($job->getId()) ?></id>
</summary>
<author>
<name><?php echo $job->getCompany() ?></name>
</author>
</entry>
<?php endforeach ?>
求人フィードのテンプレートを単純にするために _list.atom.php
パーシャルを使うことができます:
<!-- apps/frontend/modules/job/templates/indexSuccess.atom.php --> <?xml version="1.0" encoding="utf-8"?> <feed xmlns="http://www.w3.org/2005/Atom"> <title>Jobeet</title> <subtitle>Latest Jobs</subtitle> <link href="<?php echo url_for('job', array('sf_format' => 'atom'), true) ?>" rel="self"/> <link href="<?php echo url_for('homepage', true) ?>"/>
getCreatedAt('U')) ?> getLatestPost()->getDateTimeObject('created_at')->format('U')) ?> Jobeet 'atom'), true)) ?>
<?php foreach ($categories as $category): ?>
<?php include_partial('job/list', array('jobs' => $category->getActiveJobs(sfConfig::get('app_max_jobs_on_homepage')))) ?>
<?php endforeach ?>
</feed>
最後に、showSuccess.atom.php
テンプレートを作ります:
<!-- apps/frontend/modules/category/templates/showSuccess.atom.php --> <?xml version="1.0" encoding="utf-8"?> <feed xmlns="http://www.w3.org/2005/Atom"> <title>Jobeet (<?php echo $category ?>)</title> <subtitle>Latest Jobs</subtitle> <link href="<?php echo url_for('category', array('sf_subject' => $category, 'sf_format' => 'atom'), true) ?>" rel="self" /> <link href="<?php echo url_for('category', array('sf_subject' => $category), true) ?>" />
getLatestPost()->getCreatedAt('U')) ?> getLatestPost()->getDateTimeObject('created_at')->format('U')) ?> Jobeet $category), true)) ?>
<?php include_partial('job/list', array('jobs' => $pager->getResults())) ?>
</feed>
メインの求人情報フィードと同じように、カテゴリ用の最新の求人の投稿日付が必要です:
// lib/model/JobeetCategory.php // lib/model/doctrine/JobeetCategory.class.php class JobeetCategory extends BaseJobeetCategory { public function getLatestPost() { return $this->getActiveJobs(1)->getFirst(); }
// ...
}
また明日
symfony の多くの機能と同じように、ネイティブのフォーマットサポートによって難なくフィードを Web サイトに追加できます。今日は、求職者のユーザーエクスペリエンスを強化しました。明日は、Web サービスを提供することで求人の投稿者に優れた公開機能を提供する方法を経験することになります。
ORM
インデックス
Document Index
関連ページリスト
Related Pages
- 1日目: プロジェクトを始める
- 2日目: プロジェクト
- 3日目: ~データモデル~
- 4日目: Controller と View
- 5日目: ルーティング
- 6日目: モデルの詳細
- 7日目: カテゴリページで遊ぶ
- 8日目: ユニットテスト
- 9日: 機能テスト
- 10日目: フォーム
- 11日目: フォームをテストする
- 12日目: アドミンジェネレータ
- 13日目: ユーザー
- 14日目: フィード
- 15日目: Web サービス
- 16日目: ~メーラー~
- 17日目: 検索
- 18日目: ~AJAX~
- 19日目: 国際化とローカライゼーション
- 20日目: プラグイン
- 21日目: キャッシュ
- 22日目: デプロイ
- 23日目: 別の視点から symfony を見る
- Appendix A - License
- 謝辞
日本語ドキュメント
Japanese Documents
- 2011/01/18 Chapter 17 - Extending Symfony
- 2011/01/18 The generator.yml Configuration File
- 2011/01/18 Les tâches
- 2011/01/18 Emails
- 2010/11/26 blogチュートリアル(8) ビューの作成
リリース情報
Release Information
- 2.0 : 2.0.15(2011/05/30)
Symfony2日本語ドキュメント - 1.4 : 1.4.18(2012/05/30)
Changelog