質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.23%

cakephp2 同一ページに同名のinput textが2つ以上ある(別のForm)場合のバリデーションについて

解決済

回答 4

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 1,485
退会済みユーザー

退会済みユーザー

タイトルの通りですが、一つのFormでSubmitした際、まったく別のFormでもバリデーションが反応してしまって困っています。例えば記事投稿ページのPost.titleというフィールドと、全ページ共通部分のタイトル検索フィールドPost.titleなどは同一ページ上に存在します。
これを回避する手段はあるでしょうか?お手数ですがご教授頂ければ幸いです。

<追記>
ありがとうございます。
addページでtitleがnullの状態で、Submitするとaddページ、検索フォームともに”このフィールドは入力必須です”のメッセージが出力されてしまう状態です。
actionが異なっているのにバリデーションが反応してしまうこと自体がおかしいのでしょうか?
searchはsearch pluginを使用しています。
お二人に教えていただいた内容も試してみましたが、うまく設定できていないのか機能してくれません。。

posts/add (新規記事投稿)
posts/search (記事タイトル検索)

Post.php <Model>

public $actsAs = array('Search.Searchable');

public $validate = array(
    'title' => array(
        'rule' => 'notBlank',
        'message' => 'このフィールドは入力必須です。'
    )
);

public $filterArgs = array(
    array('name' => 'title', 'type' => 'like')
}

PostsController.php

public function add() {

        $this->loadModel('Category', 'Tag');

        // add to categories table
        $this->set('posts', $this->Category->find('list', array('fields' => 'Category.name')));

        // tag
        $this->set('tag', $this->Tag->find('list'));

        if ($this->request->is('post')) {
            $this->request->data['Post']['user_id'] = $this->Auth->user('id');
            #$this->Post->create();
            if ($this->Post->saveAll($this->request->data)) {
                $this->Session->setFlash(__('Your post has been saved.'), 'alert', array(
                    'plugin' => 'BoostCake',
                    'class' => 'alert-success'
                ));
                return $this->redirect(array('action' => 'index'));
            }

            // tagが2つ以上選択されていない場合のエラーメッセージを取得
            $errors = $this->Post->validationErrors;
            if (!empty($errors)) $this->set('tag_error', $errors['Tag']);

            $this->Session->setFlash(__('Unable to add your post.'), 'alert', array(
                'plugin' => 'BoostCake',
                'class' => 'alert-danger'
            ));
        }
    }

    public function search() {
        #$this->Post->recursive = 2;
        $this->Prg->commonProcess();

        $conditions = $this->Post->parseCriteria($this->Prg->parsedParams());
        if (!empty($conditions)) {
            $this->set('posts', $this->paginate(array(
                $conditions
                ))
            );
        }
    }

sidebar.ctp(search)

<?php
    echo $this->Form->create('Post', array(
        'novalidate' => true,
        'url' => array_merge(array('action' => 'search'), $this->params['pass'])
        ));
    echo $this->Form->input('Post.title', array('div' => 'form-group', 'class' => 'form-control'));
    echo $this->Form->end();
    ?>

add.ctp(create)

<?php
echo $this->Form->create('Post', array('type' => 'file', 'novalidate' => true));
echo $this->Form->input('title', array('class' => 'form-control', 'div' => 'form-group'));
echo $this->Form->input('body', array('rows' => '3', 'class' => 'form-control', 'div' => 'form-group'));
echo $this->Form->input('category_id', array(
    'type' => 'select',
    'div' => 'form-group',
    'class' => 'form-control',
    'options' => $posts));

echo $this->Form->input('Tag', array(
    'div' => 'checkbox_wrap',
    'type' => 'select',
    'multiple' => 'checkbox',
    'options' => $tag
    ));

if (!empty($tag_error)) {
    echo '<div class="error-message tagerr">';
    echo $tag_error[0];
    echo '</div>';
}
?>
  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 4

+2

CakePHPのvalidationは、それが検索ボックスとして機能しているのか投稿用として機能しているのか等は判断出来ません。
が、その要素が「update」なのか「create」なのかという事に置いては、validationを区別する事が出来ます。
http://book.cakephp.org/2.0/ja/models/data-validation.html#on

validation ruleに

'on' => 'update'


と記述すれば、データの更新時のみそのルールが適用されます。
(同様に、createを指定すれば新規登録時のみのルールとなります)
今回は、投稿時にはcreate, 検索時にはselect(find) となりますので、検索時には動作しないルールが作成できるはずです。

ただ、検索用のFormと投稿用のFormは、そもそも飛び先(action)が異なるはずだと思います。
であれば、検索時にはvalidationしなければいいとも思いますが、なぜに検索時にvalidationが動くのでしょうか。

$conditions = ['title' => $this->request->data('Post.title')];
$this->Post->find('all', $conditions);


のように、単純にfindしているだけであればvalidationは動かないはずですが。。

もし何等か$this->Post->save() する必要があるのであれば、検索のときにはvalidationをしない指定をする事も可能です。

$this->Post->saveAll($this->request->data, ['validate' => false]);


http://book.cakephp.org/2.0/ja/models/data-validation/validating-data-from-the-controller.html

この内容で対応出来ないようであれば、FormのHTMLと、Controller, Modelのソースコードを提示して改めて状況説明下さい。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

check解決した方法

0

filterArgsにfieldを設定することで解決です。ありがとうございました。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

0

検索フォームと更新フォームを別々にするか検索用項目の接頭辞に sarch_ など付与してください

追記

# 検索用モデル(Prefix:Search)
class SearchPost extends Post {
      public $useTable = false; 
      public $validate = array(
            # 独自のvalidate 
      );}
# コントローラーへの指定は割愛しています。
echo $this->Form->input('SearchPost.title');

とするか

if ($mode=='SEARCH' && $this->Post->validates(array(
            # 独自のvalidate 
))) {
    // バリデーションOK (検索)
} else if ($this->Post->validates()) {
    // バリデーションOK (登録)
} else {
    // バリデーションNG
}

とするくらいでしょうか

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/08/16 08:25

    ありがとうございます。
    検索フォームと投稿フォームは別のフォームですが、同一ページ上に存在します。(検索フォームは全ページ共通のため)

    接頭辞に_search付与とは以下のようなことでしょうか?
    テーブルのカラム名と一致させる必要があるのではないでしょうか?
    echo $this->Form->input('Post.search_title');

    よろしくお願いいたします。

    キャンセル

0

アクションごとにモデルを作成してみてはいかがでしょうか?
コントローラーから使用するモデルを指定できます。
$this->loadModel(‘ModelName’);

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 90.23%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる
  • トップ
  • PHPに関する質問
  • cakephp2 同一ページに同名のinput textが2つ以上ある(別のForm)場合のバリデーションについて