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

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

ただいまの
回答率

90.23%

jQueryによるAjaxでのバリデーションを関数によって行う方法

解決済

回答 2

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 2,398

penginer

score 30

Ajaxにおける複数の関数での処理

 前提・実現したいこと

現在jQueryを用いたAjaxでアンケートフォームを作成しており、
各要素に変更が加わるか最後に送信する前にバリデーションチェックを行う方式をとろうとしています。
これは全部回答が終わってから戻ることを避け、かつ無回答で送信することを避けるためです。

この際各要素において、真偽値を返してエラーメッセージをechoする関数(Aとします)と
最終的な解答をechoする関数(Bとします)を用意し、
Aがtrueを返せばBが動くという方式で設計します。
尚、AとBにおいてechoする場所は異なります。

 発生している問題・エラーメッセージ

この場合どのように2つの関数に同じ値を引数に入れるかが分からないです。
また、関数が依存しあっているため可能な限り同じファイルに1つにしてまとめたいです。
(上に書いた前提はまだ変えても問題ないです)
またそもそも調べてもどのような仕様にすべきかわからない状況です。

  • 2018/4/7追記
    その後euledge様の解答を参考に修正した所、jsonは値を生成しましたが出力が全く成されず、
    バリデーションを行うPHPの関数はHTMLで値を入れているにもかかわらず値が入っていないと出力しております。
    また、json自体はpタグの閉じタグでないものは全て表示されず、いくつかの値はそもそも表示すらされませんでした(空文字のままです)

尚、Chromeの検証やNetBeansを見る限り文法上のエラーは無いようです。

 該当のソースコード

以下は全て仮のものです。また、

$(function (){
        var b=[];
        $("[name='b[]']:checked").each(function(){
            b.push(this.value);
        });
            var data={a:$("[name=a]").val(),b:b,c:$("[name=c]").val(),d:$("[name=d]").val(),e:$("[name=e]").val()};
            $(".a").change(function(){$.post("function-src.php",'json',data).done
                        (function(response){
                $("#a_valid").html(response.error_a);
                                $("#b_valid").html(response.error_b);
                                $("#c_valid").html(response.error_c);
                                $("#d_valid").html(response.error_d);
                                $("#e_valid").html(response.error_e);});
            }).
        });
    <span id="a_valid"></span>
<p>
  <input type="radio" name="a" value="a" id="a" class="a"><label for="a">A</label>
  <input type="radio" name="a" value="b" id="b" class="a"><label for="b">B</label>
  <input type="radio" name="a" value="c" id="c" class="a"><label for="c">C</label>

</p>
<!--この下にnameがbのチェックボックス(配列を用いるもの)、nameがcとdのプルダウンメニュー、nameがeのラジオボタンがあり
これら全てにaというクラス属性があります。
-->
function valid_a($a)
{

      $validation=false;
        if (!isset($a)) {
        $error_a = "<p style=\"color:#ff2800;\">入力されていません。</p>";
    } elseif (($a != "a") && ($a != "b") && ($a != "c")) {
        $error_a = "<p style=\"color:#ff2800;\">不正なPOSTです。</p>";
    }else {
    $validation=true;
    $error_a="";
      echo json_encode(compact('error_a'));;
    return $validation;
    }
}

function valid_a_echo($a)
{
  $a_echo ="";
$a_ans=array("a"=>"A","b"=>"B","c"=>"C");
  if (valid_a($a)) {
    $a_echo = $a_ans[$a];
  }
    echo json_encode(compact('a_echo'));
}
function valid_b($b){

  $b2 = array(/*配列の中身*/);
    $validation=false;
    if (!in_array($b)) {
        $error_b = "<p style=\"color:#ff2800;\">入力されていません。</p>";
      }else{
        for ($i = 0; $i <count($b) ; $i++) {
          if ((intval($b[$i])<0||intval($b[$i])>count($b2)-1)&&!ctype_digit($b[$i])) {
            $error_b = "<p style=\"color:#ff2800;\">不正なPOSTです。</p>";
            break;
          }
        }
        if ($i == count($b) - 1) {
          $validation=true;
          $error_b="";
        }
      }
      echo json_encode(compact('error_b'));
      return $validation;
}

function valid_b_echo($b)
{
  $b = array(/*配列の中身*/);
    $array=array();
  if (valid_b($b2)) {
      for ($j = 0; $j <count($b) ; $j++) {
      array_push($array,$b2[intval($b[$j])]);
      }
  }
  $b_echo=implode(",",$array);
      echo json_encode(compact('b_echo'));
}

function valid_c($c)
{
      $validation=false;
        if (!isset($c)) {
        $error_c = "<p style=\"color:#ff2800;\">入力されていません。</p>";
    } elseif ((intval($c)<0||intval($c)>10)&&!ctype_digit($c)) {
        $error_c = "<p style=\"color:#ff2800;\">不正なPOSTです。</p>";
    }else {
    $validation=true;
    $error_c="";
    }
    echo json_encode(compact('error_c'));
    return $validation;
}

function valid_d($d)
{
      $validation=false;
        if (!isset($d)) {
        $error_d = "<p style=\"color:#ff2800;\">入力されていません。</p>";
    } elseif ((intval($d)<0||intval($d)>9)&&!ctype_digit($d)) {
        $error_d = "<p style=\"color:#ff2800;\">不正なPOSTです。</p>";
    }else {
    $validation=true;
    $error_d="";
    }
    echo json_encode(compact('error_d'));
    return $validation;
}

function valid_d_echo($c,$d)
{
  $d_echo ="";
  if (valid_c($c)&&valid_d($d)) {
    $d_echo = intval($c.$d);
  }
    echo json_encode(compact('d_echo'));
}

function valid_e($e)
{
      $validation=false;
        if (!isset($e)) {
        $error_e = "<p style=\"color:#ff2800;\">入力されていません。</p>";
    } elseif ((intval($e)<0||intval($e)>9)&&!ctype_digit($e)) {
        $error_e = "<p style=\"color:#ff2800;\">不正なPOSTです。</p>";
    }else {
    $validation=true;
    $error_e="";
    }
    echo json_encode(compact('error_e'));
    return $validation;
}

function valid_e_echo($e)
{
  $e_array = array(/*配列の中身*/);
  $e_echo ="";
  if (valid_e($e)) {
    $e_echo = $e_array[intval($e)];
  }
    echo json_encode(compact('e_echo'));
}
$a=filter_input(INPUT_POST,'a');
valid_a($a);
valid_b($b);
valid_c($c);
valid_d($d);
valid_e($e);
valid_a_echo($a);
valid_b_echo($b);
valid_c_echo($c);
valid_d_echo($d);
valid_e_echo($e);
/*valid_a_echo($a)が出力する値はvalid_a($a)の値が出力される場所ではないです。
今回はvalid_a~valid_eまでについて質問致します。*/
  • 気になる質問をクリップする

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

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

    クリップを取り消します

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

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

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

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

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

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

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

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

    質問の評価を下げる

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

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

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

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

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

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

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

    詳細な説明はこちら

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

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

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

質問への追記・修正、ベストアンサー選択の依頼

  • euledge

    2018/04/02 02:26

    PHPで何かフレームワーク使っているのであれば、追記してください

    キャンセル

  • penginer

    2018/04/02 13:50

    特に使っていないです

    キャンセル

回答 2

checkベストアンサー

0

コードが長くなるのでa,b,c のみでb,cについてはvalid_b(),valid_c()の呼び出しを省略した感じで
下に例示します。 

function valid_a($a)
{
  $error_a="";
  if (!isset($a)) {
    $error_a = "<p style=\"color:#ff2800;\">入力されていません。</p>";
  } elseif (($a != "a") && ($a != "b") && ($a != "c")) {
    $error_a = "<p style=\"color:#ff2800;\">不正なPOSTです。</p>";
  }
  return $error_a;
}

function valid_a_echo($a)
{
  $a_echo = "";
  $error_a = "";
  $a_ans=array("a"=>"A","b"=>"B","c"=>"C");
  $error_message = valid_a($a);
  if ($error_message == "") {
    $a_echo = $a_ans[$a];
  } else {
    $error_a = $error_message;
  }
  return compact('a_echo','error_a');
}

function valid_b_echo($b)
{
  // valid_b()を呼び出す箇所は省略

  $b_echo = "B";
  $error_b = "";
  return compact('b_echo','error_b');
}

function valid_c_echo($c)
{
  // valid_c()を呼び出す箇所は省略

  $c_echo = "";
  $error_c = "<p style=\"color:#ff2800;\">入力されていません。</p>";
  return compact('c_echo','error_c');
}

$a = "x";
$b = "b";
$c = null;

echo json_encode(
  array_merge(valid_a_echo($a),
              valid_b_echo($b),
              valid_c_echo($c)));

上記の実行結果は以下のJsonになります。

{
 "a_echo":"",
 "error_a":"<p style=\"color:#ff2800;\">不正なPOSTです。</p>",
 "b_echo":"B",
 "error_b":"",
 "c_echo":"",
 "error_c":"<p style=\"color:#ff2800;\">入力されていません。</p>"
} 


このJsonを受け取ればエラーメッセージと、解凍を両方受け取れるので空白じゃないほうを使ってHTML上に表示できるのではないでしょうか?

投稿

  • 回答の評価を上げる

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

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

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

  • 回答の評価を下げる

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

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

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

  • 2018/04/07 17:44

    遅くなってしまい申し訳ありませんでした。
    結局表示はされませんでした。
    echoを用いて調べた所、jsonやPHPは問題ないようなので
    問題はJavascriptにあるようです。
    もし何かお気づきの点がございましたらご教授いただいてもよろしいでしょうか?
    (尚spanをdivにしました。)

    キャンセル

  • 2018/04/08 14:01

    確認する項目としては、javascriptで返ってきたレスポンスをconsole.logで書き出してみることでしょうか

    キャンセル

0

まずは、valid_a($a)とvalid_a_echo($a) に同じ引数を入れるにはという点について回答します。

valid_a_echo($a)では内部で呼んでいるvalid_a($a)でバリデーションエラーがなかったら$a_ans、エラーがあったら空文字を返すようにしていると思います。
valid_aでエラーがあった場合には空文字ではなくそのエラーの出力をvalid_a_echo($a)から返してあげればよいのではないでしょうか?
そのためにはvalid_a($a)の返り値が今はbooleanになっていますが、文字列を返すようにしてあげるとよいと思います。

下記に動作のイメージのコードを記します。しばらくPHPやっていないので構文ミスなどはご容赦を、

function valid_a($a)
{
  if (エラーがあったら) {
    return エラーメッセージ;
  } else {
    return "";
  }
}

function valid_a_echo($a)
{
  $a_ans=array("a"=>"A","b"=>"B","c"=>"C");
  $error_message = valid_a($a);
  if (error_message が 空文字だったら) {
    $a_echo = $a_ans[$a];
  } else {
    $a_echo = $error_message;
  }
  echo json_encode(compact('a_echo'));
}

これでvalid_aとvalid_a_echoは valid_a_echo を呼んであげることで解決できると思いますが
次にa,b,c,d,eそれぞれのバリデーションを function-src.phpを呼ぶことで一度に対応することとしたいですね?

これも結局は上で行ったことの延長で、今度は、valid_a_echo($a)でechoしているものを returnにしてあげて、valid_a_echo,valid_b_echo,valid_c_echo,valid_d_echo,valid_e_echoを呼ぶ親が最後にechoしてあげればよいのではないでしょうか?

下記にイメージのコードを示します。こちらも構文ミスなどはご容赦を

<?php
$a_echo = valid_a_echo($_POST["a"]);
$b_echo = valid_b_echo($_POST["b"]);
$c_echo = valid_c_echo($_POST["c"]);
$d_echo = valid_d_echo($_POST["d"]);
$e_echo = valid_a_echo($_POST["e"]);


ここで $a_echo,$b_echo,$c_echo,$d_echo,$e_echo をひとつのjsonにまとめて echoする。


function valid_a($a)
{
  省略
}

function valid_a_echo($a)
{
  省略
  return json_encode(compact('a_echo'));
}
function valid_b($a)
{
  省略
}

function valid_b_echo($a)
{
  省略
  return json_encode(compact('a_echo'));
}
function valid_c($a)
{
  省略
}

function valid_c_echo($a)
{
  省略
  return json_encode(compact('a_echo'));
}
function valid_d($a)
{
  省略
}

function valid_d_echo($a)
{
  省略
  return json_encode(compact('a_echo'));
}
function valid_e($a)
{
  省略
}

function valid_e_echo($a)
{
  省略
  return json_encode(compact('a_echo'));
}

?>

投稿

  • 回答の評価を上げる

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

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

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

  • 回答の評価を下げる

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

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

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

  • 2018/04/03 15:13

    御解答感謝します。
    ただ、上にも書いたとおり解答とエラーメッセージの出力箇所を分けたいので
    そこのアドバイスを頂いてもよろしいでしょうか?

    キャンセル

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

  • ただいまの回答率 90.23%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる