新着情報

baserCMSで「簡単なブログ」プラグインを作ってみるチュートリアル

baserCMSのプラグインを作るための準備はできたけど、具体的にどうやって作ったらいいの?という人のためのチュートリアル記事です。
今回は、「簡単なブログ」プラグインを作成してみましょう。baserCMSの管理画面から「記事一覧を表示」、「記事を編集」、「新規記事を追加」、「記事を選んで削除」の機能と、閲覧側の「記事一覧表示」、「記事詳細を表示」の機能を実装します。

あらかじめ、baserCMSで初めてプラグインを作ってみる時の基本知識を参考に、プラグインの名前は bcforum で準備しておきます。

1. データベースを作成する

まずは、ブログ記事を保存しておくデータベースを作成します。

テーブル名 bc_pg_bcforum_posts

id int(8) primery_key auto_increment not_null
name int(255)
contents text
created datetime
modified datetime

id(プライマリーキー用), created(レコード作成日時), modified(レコード更新日時) の3項目は基本的には必須項目です。
created と modified は自動更新されます。ちなみに、プラグインテーブルの命名ルールは、bc_pg_プラグイン名_テーブル名で作成すること、となっているので、このルールに沿って作成くださいね。

2. ディレクトリ構成の確認

今回チャレンジする、「簡単なブログ」で作成するディレクトリやファイルの一覧です。

ディレクトリ構成

おおまかに分けると、

  • モデル → models
  • コントローラー → controllers
  • ビュー → views

の3つを作成することになります。

3. モデルを作成する

bcforum/models/bcforum_post.php

<?php
	class BcforumPost extends AppModel {
	// $name には、モデル名と同じ値をセットします
	var $name = BcforumPost;
	// plugin プロパティを設定します
	var $plugin = Bcforum;
	// データベースの接続設定をします。
	var $useDbConfig = plugin;
	}
?>

$name は、CakePHPでは、PHP4との互換用に書くもののようですが、baserCMSではPHP5を使っていても必須項目になっているみたいです。プラグインで利用するモデルでは、プラグイン名を設定する $plugin プロパティを設定します。app/config/database.php には、データベースへの接続設定が書かれてあります。そこでは、デフォルトの接続設定 baser と、プラグイン用の接続設定 plugin が用意されています。2つの違いはプレフィックスです。デフォルトであれば、プレフィックスは bc_ だけなのですが、プラグインの命名ルールでは、bc_pg_ までとなっているので、ここで設定しておきます。

4. コントローラとビューを作成する

bcforum/controllers/bcforum_posts_controller.php

<?php
	// 継承するコントローラのpluginsをインポートする
	app::import(Controller, Plugins);
	// baserCMS にパッケージされている PluginsController を継承させます
	class BcforumPostsController extends PluginsController {
	// nameプロパティをちゃんと定義しておきます【重要】
	var $name = "BcforumPosts";
	// モデル宣言 (Plugin,プラグイン名.モデル名)
	var $uses = array(Plugin, Bcforum.BcforumPost);
	// このコンポーネントを読み込むと、このコントローラーに認証がかかります
	var $components = array(BcAuth,Cookie,BcAuthConfigure);

	function beforeFilter() {
	}

	function index() {
		// ブログ一覧を表示させる
	}

	function view($id) {
		// ブログ詳細を表示させる
	}
	
	function admin_index() {
		// 管理画面からブログ一覧を表示させる
	}

	function admin_edit($id) {
		// ブログを編集する
	}

	function admin_add() {
		// ブログを新規登録する
	}

	function admin_delete($id) {
		// ブログを削除する
	}

?>

ディレクトリ構成の一覧と比較してみると、view ファイルとだいたい一致してますよね。

http://{baserCMS設置URL}/bcforum/bcforum_posts/index

上記のアドレスをリクエストすると、 function index() が実行されます。

http://{baserCMS設置URL}/admin/bcforum/bcforum_posts/index

上記のアドレスをリクエストすると、 function admin_index() が実行されます。

つまり、アクション名の先頭に、プレフィックス admin_ がある場合は、アドレスのルート直下に admin ディレクトリが必要になります。

index() と view() の認証を許可する

コンポーネントで定義したことで、コントローラー全体に認証がかかってしまっています。ログインしていなくても、ブログの閲覧だけはできるようにしたいですよね。そこで、beforFilter() に、下記を記述しましょう。

function beforeFilter() {
	$this->BcAuth->allow(index, view);
}

これで、2つのアクションは、ログインしてなくても実行できるようになりました。
でも、今は2つでも、プラグイン開発を進めていくと、認証外したいアクションが増えるかも・・・ 管理画面の admin_ がつくやつだけ認証かけれないの?という時は、下記のように書き換えちゃいましょう。

function beforeFilter() {
	if (!preg_match(/^admin_/, $this->action)) {
		$this->BcAuth->allow($this->action);
	}
}

admin_ で始まるアクション以外の認証を解除してくれるようになりました。これだけだと、継承元の記述が全部上書きされてしまうので、お約束の

parent::beforeFilter();

も忘れずに記述しておいてくださいね。

アクション admin_index() を作成する

管理画面のトップページ処理を作成します。ブログ一覧を表示させて、それぞれの記事への編集ボタンを作成しましょう。

function admin_index() {
	// タイトルをセットします
	$this->pageTitle = 記事一覧;
	// 管理画面のサブメニュー
	$this->subMenuElements = array(bcforum_posts_index); 
	// モデルから今回のブログデータのテーブル情報を全て取得します
	$datas = $this->BcforumPost->find(all);
	// 取得したデータを view へセットします
	$this->set(datas, $datas);
}

$this->pageTitle は、タイトルをセットします。タイトルタグや、ぱんくずリスト、h1タグなどに使われます。$this->subMenuElements は、ナビゲーターリンクに使用できます。 bcforum/views/elements/admin/submenus/bcforum_posts_index.php を作成して、「新規ブログ登録」や「ブログ一覧表示」などのナビゲーションメニューを作成することで、呼び出すことができます。詳しくは、ナビゲーションメニューを作成する を参照ください。

admin_index() を表示するビューを作成する

bcforum/views/bcforum_posts/admin/index.php

<table class="list-table">
	<tr>
		<th></th>
		<th></th>
		<th>ID</th>
		<th>タイトル</th>
	</tr>
	<?php foreach ($datas as $data): ?>
	<tr>
		<td><?php $bcBaser->link(編集する, array(plugin => bcforum, plugin => bcforum, controller => bcforum_posts, action => edit, $data[BcforumPost][id])) ?></td>
		<td><?php $bcBaser->link(削除する, array(plugin => bcforum, plugin => bcforum, controller => bcforum_posts, action => delete, $data[BcforumPost][id])) ?></td>
		<td><?php echo $data[BcforumPost][id] ?></td>
		<td><?php echo $data[BcforumPost][name] ?></td>
	</tr>
	<?php endforeach ?>
</table>

$datas を var_dump してみると分かりますが、bc_pg_bcforum_posts の情報が配列で格納されています。これを、foreach 文で回して一覧を表示させましょう。
編集ボタンも追加して、アクション edit へリンクを作成し、 id を引数として渡します。環境によって左右されないURLを作成してくれるので、HTMLヘルパーを使いましょう。

アクション admin_edit() を作成する

記事の編集画面の表示と、編集登録処理を行います。データが存在する項目は、フォームに初期値として表示させます。

function admin_edit($id) {
	// タイトルをセットします
	$this->pageTitle = 記事編集;
	//管理画面のサブメニュー
	$this->subMenuElements = array(bcforum_posts_index);
	if (!$this->data) {
		// フォームにDBデータを表示
		$this->data = $this->BcforumPost->read(null, $id);
	} else {
		// 送信データをDBに保存
		$this->BcforumPost->set($this->data);
		if ($this->BcforumPost->save()) {
			$this->Session->setFlash(保存しました);
			$this->redirect(index);
		} else {
			$this->Session->setFlash(失敗!);
		}
	}
}

$this->data は、送信されてきたフォームデータが格納されます。
!$this->data ということは、フォームからデータが送信されていないということですから、ビュー画面のフォームに初期値を表示するため、データベースの情報を取得してくる必要があります。$this->data が存在する場合は、フォームからデータが送信されている=編集しましたよ、ということなので、そのデータをデータベースへ格納します。

admin_edit() を表示するビューを作成する

bcforum/views/bcforum_posts/admin/edit.php

<?php echo $bcForm->create(BcforumPost); ?>
<?php echo $bcForm->hidden(BcforumPost.id) ?>
<table class="form-table">
	<tr>
		<th>ID</th>
		<td><?php echo $bcForm->value(BcforumPost.id) ?></td>
	</tr>
	<tr>
		<th>タイトル</th>
		<td><?php echo $bcForm->text(BcforumPost.name) ?></td>
	</tr>
	<tr>
		<th>内容</th>
		<td><?php echo $bcForm->textarea(BcforumPost.contents) ?></td>
	</tr>
</table>
<div class="submit">
	<?php echo $bcForm->submit(保存, array(class => button)) ?>
</div>
<?php echo $bcForm->end() ?>

フォームヘルパーで、編集フォームを作成します。データベースから取得した情報を初期値として表示させます。 id は編集できないように、hidden 属性で出力しておきましょう。

アクション admin_add() を作成する

function admin_add() {
	// タイトルをセットします
	$this->pageTitle = 記事追加;
	// 管理画面のサブメニュー
	$this->subMenuElements = array(bcforum_posts_index);
	if ($this->data) {
		// 送信データをDBに保存
		$this->BcforumPost->set($this->data);
		if ($this->BcforumPost->save()) {
			$this->Session->setFlash(保存しました);
			$this->redirect(index);
		} else {
			$this->Session->setFlash(失敗!);
		}
	}
}

admin_add() を表示するビューを作成する

bcforum/views/bcforum_posts/admin/add.php

<?php echo $bcForm->create(BcforumPost); ?>
<table class="form-table">
	<tr>
		<th>タイトル</th>
		<td><?php echo $bcForm->text(BcforumPost.name) ?></td>
	</tr>
	<tr>
		<th>内容</th>
		<td><?php echo $bcForm->textarea(BcforumPost.contents) ?></td>
	</tr>
	</table>
<div class="submit">
	<?php echo $bcForm->submit(保存, array(class => button)) ?>
</div>
<?php echo $bcForm->end() ?>

edit.php とほぼ同じですね。編集フォームの時に記述した、hidden 属性の id 、これが存在しないだけで、新規レコードに追加してくれます。簡単ですね!

アクション index() を作成する

一般の閲覧者が見ることのできるページを作成します。ログインしなくてもみることができるページですね。 この動きって、実は admin_index() とほぼ同じで大丈夫ですよね。そんな時は、 admin_index() のアクションを再利用しちゃいましょう。

function index() {
	$this->setAction(admin_index); //admin_indexのアクションをそのまま呼び出せる
	$this->pageTitle = トピックス一覧; //上書きすることもできる
}

今回は、admin_index() を呼び出したあと、タイトル部分だけは上書きして変えてみました。

index() を表示するビューを作成する

bcforum/views/bcforum_posts/index.php

<table class="row-table-01">
	<tr>
		<th></th>
		<th>ID</th>
		<th>タイトル</th>
	</tr>
	<?php foreach ($datas as $data): ?>
	<tr>
		<td><?php $bcBaser->link(詳細, array(plugin => bcforum, controller => bcforum_posts, action => view, $data[BcforumPost][id])) ?></td>
		<td><?php echo $data[BcforumPost][id] ?></td>
		<td><?php echo $data[BcforumPost][name] ?></td>
	</tr>
	<?php endforeach ?>
</table>

admin_index() のビューとほとんど同じです。違うのは、編集ボタンが詳細表示ボタンになったところくらいですね。それから、閲覧側のアクションには、プレフィックスである admin がつきませんでした。なので、ビューを作成する場合も、今まで作った管理画面用の admin ディレクトリ内ではないのでご注意ください。

アクション view() を作成する

詳細ボタンがクリックされた時に呼び出されるアクションです。引数である id をもとにして、レコードを呼び出し、データをビューに渡します。

function view($id) {
	if ($id) {
		$data = $this->BcforumPost->read(null, $id);
		$this->set(data, $data);
	}
}

view() を表示するビューを作成する

<table class="row-table-01">
	<tr>
		<th>ID</th>
		<td><?php echo $data[BcforumPost][id] ?></td>
	</tr>
	<tr>
		<th>タイトル</th>
		<td><?php echo $data[BcforumPost][name] ?></td>
	</tr>
	<tr>
		<th>内容</th>
		<td><?php echo $data[BcforumPost][contents] ?></td>
	</tr>
</table>

$data に渡したデータを、表示させます。

アクション admin_delete() を作成する

削除処理を作成します。

function admin_delete($id) {
	if($this->BcforumPost->delete($id)) {
		$this->Session->setFlash(削除しました);
		$this->redirect(index);
	} else {
		$this->Session->setFlash(失敗!);
		$this->redirect(’index’);
	}
}

削除処理ができたあとは、一覧表示にリダイレクトするので、ここではビュー画面は作成しません。

ナビゲーションメニューを作成する

bcforum/views/elements/admin/submenus/bcforum_posts_index.php

<tr>
	<th>ダッシュボードメニュー</th>
	<td>
		<ul class="cleafix">
			<li>
				<?php $bcBaser->link(一覧を表示する, array(plugin => bcforum, controller => bcforum_posts, action => index)) ?>
			</li>
			<li>
				<?php $bcBaser->link(新規に登録する, array(plugin => bcforum, controller => bcforum_posts, action => add)) ?>
			</li>
		</ul>
	</td>
</tr>

baser の管理画面とデザインを揃えたいなというときは、baser/views/elements/admin/submenus/ の中のファイルを参考に作成するといいですよ。

以上でチュートリアルは終了です。
baserCMSは、CakePHPでできているので、この処理どうやって書くんだっけ?って時なんか、ちょっと検索するとたくさんのtipsが見つかるので、とってもカスタマイズしやすいですね!実は私、そんなにCakePHP詳しくないのですが、CakePHPについての記事を書いて下さっている方々のおかげでいつも助かってます。お世話になってます。ありがとうございます!

baserCMS   2012/07/09   admin

この記事へのコメント

コメントを送る

  ※ メールは公開されません
Loading...
 画像の文字を入力してください
このページの先頭へ戻る