iPhone/iPadのホーム画面コンテスト開催中!賞品は iTunes カード!

CakePHP & PHP 2008/01/06 03:48

CakePHP 管理者サイトでBasic認証を簡単に行うコンポーネント

CakePHPの管理者向けサイトにBasic認証を簡単に追加するコンポーネントです。

1.2系で動作しますが、ちょこちょこっといじれば1.1でも動くかと。

1. Routing.adminを有効にする

そもそもこれをやらないと意味がありません。[app/config/core.php]でRouting.adminを有効にします。

これにより[http://example.com/admin/~]のURLで管理者用アクションにアクセスできます。

PHP:
  1. Configure::write('Routing.admin', 'admin');

2. 認証コンポーネントを設置

認証コンポーネントを[app/controllers/components/admin_auth.php]に設置します。

[2008/05/29] 継承元をComponentからObjectへ変更しました。(janさんありがとうございます!)

PHP:
  1. <?php
  2. class AdminAuthComponent extends Object {
  3.   /**
  4.    * before filter
  5.    */
  6.   public function startup(&$controller) {
  7.     if (!preg_match("/^" . Configure::read('Routing.admin')  . "_/i", $controller->action)) {
  8.       return;
  9.     }
  10.  
  11.     $user = env('PHP_AUTH_USER');
  12.     $pass = env('PHP_AUTH_PW');
  13.  
  14.     if (empty($user) || empty($pass)) {
  15.       $this->unauthorized($controller);
  16.     } else {
  17.       if (!$this->auth($user, $pass)) {
  18.         $this->forbidden($controller);
  19.       }
  20.     }
  21.   }
  22.  
  23.   /**
  24.    * unauthorized
  25.    *
  26.    * @param  object Controller $controller
  27.    */
  28.   protected function unauthorized($controller) {
  29.     header("WWW-Authenticate: Basic realm=\"Please Enter Your Password\"");
  30.     $controller->redirect(null, 401, false);
  31.     echo "Authorization Required";
  32.     exit;
  33.   }
  34.  
  35.   /**
  36.    * forbidden
  37.    *
  38.    * @param  object Controller $controller
  39.    */
  40.   protected function forbidden($controller) {
  41.     $controller->redirect(null, 403, false);
  42.     echo "Authorization Required";
  43.     exit;
  44.   }
  45.  
  46.   /**
  47.    * auth
  48.    *
  49.    * @param  string $user
  50.    * @param  string $pass
  51.    * @return boolean
  52.    */
  53.   protected function auth($user, $pass) {
  54.     $hash = sha1($user . $pass . Configure::read('Security.salt'));
  55. //debug: var_dump($hash);
  56.     return $hash === ADMIN_AUTH_HASH;
  57.   }
  58. }
  59. ?>

3. AppControllerで読み込む

AppControllerの$componentsでAdminAuthComponentを読み込むだけでokです。これで[/admin/]なURLにアクセスされるとBasic認証を行い、認証が通った場合のみアクションを実行します。

PHP:
  1. <?php
  2. class AppController extends Controller {
  3.   public $components = array('AdminAuth');
  4. }
  5. ?>

認証情報

上記ソースでは簡易的にユーザ名+パスワード+Security.saltでsha1ハッシュを生成して、それを定数ADMIN_AUTH_HASHと比較して認証を行っています。

ADMIN_AUTH_HASHは[app/config/core.php]等で定義しておけばokです。

ちなみにハッシュ値を簡単に作成するには、AdminAuthComponent#auth()でコメントアウトしているvar_dump()を有効にします。これでブラウザからアクセスしてユーザID・パスワードを認証ダイアログで入力すればハッシュ値が出力されます。

ハッシュ生成後はvar_dump()の行は削除する or コメントアウトするようにしましょう。

拡張とか

ここでは単純な実装になっていますが、AdminAuthComponentを変更すれば以下のような拡張が考えられます。

  • ハッシュ値では無くDBの値で認証
  • HTTPからのアクセスはHTTPSへリダイレクト
  • Basic認証を他の認証に変更

ちなみにRouting.adminのURLは単純にapache側で認証をかけるとすり抜けられる可能性があります。(@see:CakePHP URLマッピング修正パッチ)

このコンポーネントを使えばいかなるURLでアクセスされても、管理者用アクションを(初回)実行する際は認証を通過させることができます。



■Related Posts

10 Responses to “CakePHP 管理者サイトでBasic認証を簡単に行うコンポーネント”

  1. on 28 5月 2008 at 04:45 1.jan said …

    コンポーネントの継承の部分なのですが、Componentからの継承であっているのでしょうか?
    入力ダイアログがなかなか表示されないので試行錯誤していたのですが、マニュアルに書いてある通りにObjectから継承させると動いたもので。

  2. on 28 5月 2008 at 13:12 2.shinbara said …

    情報ありがとうございます!
    1.2beta環境では、Componentからの継承で問題無いですよ。
    1.1では試してませんが、若干修正が必要かもしれません;-)

  3. on 28 5月 2008 at 14:22 3.jan said …

    環境は1.2.0.6311です。
    「cakephp "extends component"」でググってみたら、日本語のサイトではこちらのブログしかヒットしなかったので、アレ?と思ったり(苦笑)

  4. on 29 5月 2008 at 22:24 4.shinbara said …

    janさん:
    同じ1.2betaですか。うーん、なんで動かないんでしょうね。

    Componentを継承しているコンポーネントは他にも例があるので問題無いとは思いますが、book.cakephp.org見るとObjectを継承しているようなので、変更しますね。
    # フレームワークのコンポーネントも
    # Objectを継承してますね。

    ご指摘ありがとうございます!

    # 1.2ではComponentを継承するという話を見たような
    # ソースを見たような記憶があったのですが
    # 出典が思い出せません。。。

  5. on 29 6月 2008 at 14:51 5.halt said …

    そもそもComponentクラスがObjectクラスを継承してるからComponentで問題ないと思いますけどねえ。

  6. on 09 10月 2008 at 18:10 6.custar said …

    私もメソッド群を component に纏 (まと) めるため、component.php を眺めて
    みました。

    Component Class はソースの記述にある通り、Controller に読み込まれている
    コンポーネントを纏めて扱う、単なるハンドラーでしかありません。

    | /**
    | * Handler for Controller::$components
    | */
    | class Component extends Object

    ソース内に、Component に備わっているようなメソッドが幾つも見受けられま
    すが、それらは単に個々のコンポーネントのメソッドを順に実行しているだけ
    です。

    よって、独自 Component を作成する場合、Component Class から呼び出される
    それらのメソッドを実装すると、適当なタイミングで実行されるようになりま
    す (callback)。

    (1) init()
    (2) initialize()
    (3) startup()
    (4) beforeRender()
    (5) beforeRedirect()
    (6) shutdown()

    私も Component Class がコンポーネントの基底クラスかな、と予想していたの
    ですが、そうではありませんでした。

    沢山のコンポーネントを作成されるような場合、Object Class を継承した基底
    クラスを独自に作り、そこから派生させていく、という手も考えられます。

    対象 : cakephp v1.2 rc3

  7. on 29 10月 2008 at 02:11 7.[cakephp]1.2で管理者用アクションの設定をする | blog.hereticsintheworld said …

    [...] 参考、関連サイト ・CakePHP URLマッピング修正パッチ ・CakePHP 管理者サイトでBasic認証を簡単に行うコンポーネント [...]

  8. on 25 5月 2009 at 00:09 8.今週の管理人Bookmark (5/18-5/25) - ElectronicBrain is eating BreakFast said …

    [...] CakePHP 管理者サイトでBasic認証を簡単に行うコンポーネント | Shin x blog [...]

  9. on 31 5月 2009 at 19:33 9.[CakePHP] 管理者画面でIP制限をかけてみる - ElectronicBrain is eating BreakFast said …

    [...] CakePHP 管理者サイトでBasic認証を簡単に行うコンポーネント | Shin x blog [...]

  10. on 22 2月 2010 at 20:34 10.[CakePHP] CakePHP(PHP)でのBasic認証はPHPがCGI版で動いている場合は使えないようです « [ま]技術雑記 said …

    [...] CakePHP 管理者サイトでBasic認証を簡単に行うコンポーネント | Shin x blog http://www.1×1.jp/blog/2008/01/cakephp_adminauthcomponent.html [...]

Trackback This Post | Subscribe to the comments through RSS Feed

Leave a Reply