CakePHP2で存在しないコントローラ名・アクション名などがURLで指定された場合に、カスタマイズされたエラーを表示したい

[Sponsored Link]


当ブログでは「役に立った!」「写真使いました!」などご参考頂いた方からのAmazonギフト券の寄付をお待ち致しております。

Share on FacebookTweet about this on TwitterShare on Google+Share on TumblrPin on PinterestShare on LinkedInDigg this

以前、このブログでもCakePHPにおけるエラー処理にまつわる記事を書いたことがある。これはこれで当時は試行錯誤の中で調整したもので、あの記事を書きつつも「本当に、ただ単に存在しないコントローラ名やアクション名がURL中で指定された場合のエラー処理に、こんな複雑怪奇な設定を施さなければならないものか」などと疑わしく感じていたが、今こうして長く使っていると、あれは混乱の産物だったのだろうかなどと思うこともある。単なる存在しないルートの場合のエラー処理でいえば、ちょっとした処理だけで対応できる。

極論を言えば、1つファイルを修正するだけだ。core.phpなどの設定を変更する必要もないし、router.phpなどを修正したり追記したりすることも一切ない。あの日あの時あの場所で私が悩んでいたのは何だったのか……などと思わざるを得ないほどの単純さである。まったくもって涙がちょちょぎれる。己の頭が悪さというのは、まさにこういうときに感じるのであった。

実際に、app/View/Errors/error400.ctpファイルを修正するだけで事足りるのだ。本当にそれだけだ。
まあここでは念のため、オリジナルのerror400.ctpファイルは保存しておくことにして、そこからカスタマイズするべく編集をしてみたい。

# cd app/View/Errors
# mv error400.ctp error400.ctp.ORG
# vi error400.ctp (エディタで編集)

さて編集内容は以下のようになる。
ここでは単に「ページがありません」とでかでかと表示させるだけだ。

<?php
$this->layout = false;
echo '<h1>ページがありません</h1>';
?>

もしくはこう。

<?php
$this->layout = false;
?>
<h1>ページがありません</h1>

どんな表示になるかというと、こんな感じである。

Screenshot_1

[Sponsored Link]


いずれもポイントは「$this->layout = false;」で、これがないとデフォルトで指定されているなどのレイアウトを使用してしまう。レイアウトファイルが存在しないので、上記の画面も真っ白な背景に「ページがありません」がバーンと表示されているだけだ。
もしエラー画面で特別にしつらえたレイアウトがある場合には、falseではなくレイアウト名を指定すればいい。たとえばapp/View/Layouts/error.ctpというレイアウトファイルを用意しているのであれば、「$this->layout = ‘error’;」とすればいい。
たとえば、以下のように通常のレイアウトファイルへの変数指定などもできるわけだ。以下はapp/View/Errors/error404.ctpファイル。

<?php
$this->layout = 'error'; // app/View/Layouts/error.ctpファイルの指定
$this->set('title', 'ページがありません'); // レイアウト中で$titleという変数で参照可能
?>
<h1>ページがありません</h1>

2行目でレイアウトファイルを指定している。拡張子.ctpは付与しない。
3行目はViewファイルで使用可能なレイアウトファイル側への変数で、これはエラー処理であっても通常どおり使用可能である、ということを示すテストとして設定してみた。
そしてこのファイル全体の出力結果が、次に示すレイアウトファイルapp/View/Layouts/error.ctp中の「$this->fetch(‘content’);」という指定で取得できる。

<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title><?php echo $title; ?></title>
</head>
<body bgcolor="green">
<?php echo $this->fetch('content'); ?>
</body>
</html>

5行目では、さっそく$title変数を使ってViewからset()メソッドで渡された内容を表示している。
そして8行目では、fetch()メソッドでViewファイルの出力内容を取得して、ここに配置している。
7行目にちょっと視線を戻してもらい、背景色を緑(green)で指定している点だけ気に留めておきたい。
そしてこれを実行した場合の結果がこちら。

Screenshot_2

まあ別に大差ないんだけれど、要するに背景色が変わったのでレイアウトファイルが適切に使用されていることがわかるだろう。ページタイトルも変わっているので、自分でテストしている場合はブラウザのページタイトル表示にも注目されたい。

で、ちなみに私の場合はエラー表示をせずに、存在しないURLだったら特定のURL(たとえばトップページ)に飛ばしたいという希望があるため、app/View/Errors/error400.ctpファイルは以下のように設定している。

<?php
$this->layout = false;
echo '<meta http-equiv="Refresh" content="0;URL='.BASE_URL.'">';
?>

どうもViewファイルの実行時点ではすでにHTTPヘッダかコンテンツの一部は出力されてしまっているようで、PHPのheader()関数でのリダイレクトはできない。ということで、metaタグでの誘導を行っている。
3行目で指定している「BASE_URL」という定数は、app/Config/bootstrap.phpなどの設定ファイル中でdefine()で定義している定数であるが、もちろんこれらを使わずとも文字列でURLを指定するなどは可能である。

CakePHP2 実践入門 (WEB+DB PRESS plus)詳解CakePHP辞典―2.0/2.1/2.2/2.3対応Webアプリ開発を加速する CakePHP2定番レシピ119WebデザイナーのためのCakePHPビューコーディング入門オープンソース徹底活用 CakePHP 2.1によるWebアプリケーション開発

Share on FacebookTweet about this on TwitterShare on Google+Share on TumblrPin on PinterestShare on LinkedInDigg this

当ブログでは「役に立った!」「写真使いました!」などご参考頂いた方からのAmazonギフト券の寄付をお待ち致しております。


Atsushi Ezura について

ナチュラルな女性のしぐさや表情を撮りたいIT系エンジニア。女性モデル募集中プロフィール
カテゴリー: CakePHP, ウェブ, コンピュータ タグ: , パーマリンク

コメントを残す

メールアドレスが公開されることはありません。