【CakePHP2】お問い合わせフォームをつくる(確認画面あり)
CakePHP2で簡単なコンタクトフォームをつくります。
- メール送信にCakeEmailを使用。
- バリデーション用にContactモデルを作成。
- 確認画面を挟む。
- PHP
- 5.6
- CakePHP
- 2.8.0
今回作成するファイル
app/
|-- Config/
| `-- email.php
|-- Controller/
| `-- ContactController.php
|-- Model/
| `-- Contact.php
|-- View/
| |-- Contact/
| | `-- ContactController.php
| |-- Emails/
| | `-- text/
| | `-- contact.ctp
| `-- Emails/
| `-- text/
| `-- contact.ctp
`-- Layouts/
`-- Emails/
`-- text/
`-- contact.ctp
メールの設定
/Config/email.php.defaultを/Config/email.phpとリネームし、基本設定を書いていきます。コントローラー側でも追記できますが、可能な限りここで定義しておきます。Gmailなど外部のメールサーバーも使用できます。
public $contact = array(
'transport' => 'Mail',
'from' => array('mail@example.com' => 'My Site'),
'to' => 'mail@example.com',
'subject' => 'お問い合わせ'
);
public $gmail = array(
'transport' => 'Smtp',
'host' => 'ssl://smtp.gmail.com',
'port' => 465,
'username' => 'my@gmail.com',
'password' => 'secret'
);
モデル
今回、データベースにcontactsテーブルは作っていませんが、バリデーションで使用するためにContactモデルを用意します。
- バリデーション名が変更
空文字のバリデーション名がCakePHP2.7からnotBlankとなっています。2.7未満ではnotEmptyに変更してください。
<?php
class Contact extends AppModel
{
public $useTable = false;
public $_schema = array(
'name' => array('type' => 'string', 'length' => 255),
'email' => array('type' => 'string', 'length' => 255),
'subject' => array('type' => 'string', 'length' => 255),
'body' => array('type' => 'text'),
);
public $validate = array(
'name' => array(
'notBlank' => array(
'rule' => array('notBlank'),
'message' => '未入力です。',
'required' => true,
),
'maxLength' => array(
'rule' => array('maxLength', 255),
'message' => '255文字以内で入力してくだい。',
'required' => true,
),
),
'email' => array(
'notBlank' => array(
'rule' => array('notBlank'),
'message' => '未入力です。',
'required' => true,
),
'email' => array(
'rule' => array('email'),
'message' => 'メールアドレス以外が入力されています。',
'required' => true,
),
'maxLength' => array(
'rule' => array('maxLength', 255),
'message' => '255文字以内で入力してくだい。',
'required' => true,
),
),
'subject' => array(
'notBlank' => array(
'rule' => array('notBlank'),
'message' => '未入力です。',
'required' => true,
),
'maxLength' => array(
'rule' => array('maxLength', 255),
'message' => '255文字以内で入力してくだい。',
'required' => true,
),
),
'body' => array(
'notBlank' => array(
'rule' => array('notBlank'),
'message' => '未入力です。',
'required' => true,
),
'maxLength' => array(
'rule' => array('maxLength', 3000),
'message' => '3000文字以内で入力してくだい。',
'required' => true,
),
),
);
}
ビュー
フォーム画面(入出力)のビューと、メールテンプレート用のビューを書いていきます。
フォーム入力画面
バリデーションのエラー表示をしたいので、容易にできるFormヘルパーを使用しています。
<?php
echo $this->Session->flash();
echo $this->Form->create('Contact');
echo $this->Form->input('name', array(
'type' => 'text',
'label' => 'お名前',
'maxlength' => 255,
)
);
echo $this->Form->input('email', array(
'type' => 'email',
'label' => 'メールアドレス',
'maxlength' => 255,
)
);
echo $this->Form->input('subject', array(
'type' => 'text',
'label' => '題名',
'maxlength' => 255,
)
);
echo $this->Form->input('body', array(
'type' => 'textarea',
'label' => 'お問い合わせ内容',
'maxlength' => 3000,
)
);
echo $this->Form->button('確認する', array(
'type' => 'submit',
'name' => 'confirm',
'value' => 'confirm'
));
echo $this->Form->end();
フォーム確認画面
送信データをhiddenへ。
<dl>
<?php foreach ($this->request->data['Contact'] as $name => $val): ?>
<dt><?php echo h($name); ?></dt>
<dd><?php echo h($val); ?></dd>
<?php endforeach; ?>
</dl>
<?php
echo $this->Form->create('Contact');
foreach ($this->request->data['Contact'] as $name => $val) {
echo $this->Form->hidden($name, array('value' => $val));
}
echo $this->Form->button('修正する', array(
'type' => 'submit',
'name' => 'confirm',
'value' => 'revise'
));
echo $this->Form->button('送信する', array(
'type' => 'submit',
'name' => 'confirm',
'value' => 'send'
));
echo $this->Form->end();
メール本文の表示
メール本文表示用のビューを書きます。コントローラー $email->viewVars($content)
でセットされます。
お問い合わせ:
<?php echo $subject; ?>
名前:
<?php echo $name; ?>
メールアドレス:
<?php echo $email; ?>
本文:
<?php echo $body;
メールレイアウト
<?php echo $this->fetch('content'); ?>
---------------------------------------
署名などの雛形
コントローラー
まずはフォームから受け取ったデータをバリデーション。エラーが無ければ確認ページを表示。その後、送信ボタンをクリックでメール送信処理をします。確認画面、送信処理前の両方でバリデーションしているのは改変対策のためです。
public function contact()
{
if (!$this->request->is('post') || !$this->request->data) {
return;
}
$this->Contact->set($this->request->data);
if (!$this->Contact->validates()) {
$this->Session->setFlash('入力内容に不備があります。');
return;
}
switch ($this->request->data['confirm']) {
case 'confirm':
$this->render('contact_confirm');
break;
case 'send':
if ($this->sendContact($this->request->data['Contact'])) {
$this->Session->setFlash('お問い合わせを受け付けました。');
$this->redirect('/');
} else {
$this->Session->setFlash('エラーが発生しました。');
}
break;
}
}
private function sendContact($content)
{
App::uses('CakeEmail', 'Network/Email');
$email = new CakeEmail('contact');
return $email
->from(array($content['email'] => $content['subject']))
->viewVars($content)
->template('contact', 'contact')
->send();
}
以上で簡単なコンタクトフォームができました。
おわりに
今回は使用しませんでしたが、セキュリティコンポーネントを使って改変対策やワンタイムトークンを追加したほうが安全です。また、IPやユーザーエージェントなども取得しておくとイタズラ対策にもなります。