本記事では、別ページに設置したPHPを活用して、非同期通信を用いたシンプルなデータ検証システムを実装する方法をご紹介します。
この仕組みでは、ユーザが入力したテキストを別ページのPHPで検証し、その結果をフロントエンドで即時にフィードバックすることが可能です。
今回のサンプルでは、固定値との一致確認を例にしていますが、実際にはデータベース照合や外部APIとの連携など、より複雑な検証ロジックを組み込むこともできます。
以下、各パートごとにコード例とその解説を掲載していますので、ぜひご参考ください。
全体像
このサンプルは、以下の2つの主要なパートで構成されています:
※ 入力値をinputTextとして送信し、valueが「hoge」であるかを判定するシンプルな検証をしています。
・ フロントエンド(HTML/JavaScript/CSS)(PHP) ユーザの入力値を取得し、非同期通信を通じて検証用PHPに送信します。
※ 検証結果に応じ、入力エラーの場合は登録ボタンを無効化するなど、ユーザに分かりやすいフィードバックを提供します。
注意点
・ ページのURLも、実際の環境に合わせて正しく設定してください。
・ エラーハンドリングや通信エラー時の処理を充実させることで、ユーザにとって分かりやすいフィードバックを提供できます。
DB連携の可能性
本サンプルでは固定値との照合を行っていますが、実際の運用ではデータベースに保存された値との突合や、複数条件での検証も可能です。
ユーザ情報や検証結果の履歴をデータベースに保存することで、後日の分析や不正アクセスの監視など、より高度なシステム運用が実現します。
検証用ページのコード例
ページのPHPタブに、以下のPHPコードを記述することで、入力値の検証用APIを構築できます。
必要に応じて、認証処理やDB連携などの機能を追加して、セキュアかつ柔軟なシステムに仕上げてください。
<?php
// 入力値は「inputText」というキーで送信される前提です
$inputText = $SPIRAL->getParam("inputText");
if (!isset($inputText)) {
$response = [
'status' => 'failed',
'errorMessage' => 'inputTextパラメータが存在しないか形式が不正です'
];
$SPIRAL->setTHValue("response",$response);
return;
}
// 検証対象の値(例として "hoge" を使用)
$checkValue = "hoge";
// ここでは、入力値と定義値の一致を検証します。
// 実際には、データベース照合や外部APIとの連携も可能です。
if ($inputText === $checkValue) {
$response = [
'status' => 'success'
];
$SPIRAL->setTHValue("response",$response);
} else {
$response = [
'status' => 'failed',
'errorMessage' => '照合エラー'
];
$SPIRAL->setTHValue("response",$response);
}
?>
// 検証対象の値(例として "hoge" を使用)
$checkValue = "hoge";
<p th:text="${cp.result.value['response']}"></p>
検証用フロントエンドコード例
下記のコードは、ユーザの入力値を取得し、別ページのPHPに送信して検証結果をUIに反映する仕組みを示しています。
【フロント:Javascript】
document.addEventListener("DOMContentLoaded", function () {
const checkFieldName = "inputText"; // チェック対象のinput要素のname属性
const API_URL = 'https://spiral-site.com/testBackend'; // PHPを設置したページのURLに変更してください
// 入力フィールド、送信ボタン、結果表示領域の取得
const inputField = document.querySelector("[name='" + checkFieldName + "']");
const submitButton = document.querySelector(".sp-form-next-button");
const resultMessage = document.getElementById("result");
if (!inputField) {
console.error("要素 [name='" + checkFieldName + "'] が見つかりません");
return;
}
/*
* PHPを呼び出して検証を実施する処理
*/
async function performValidation(value) {
try {
const response = await fetch(API_URL, {
method: "POST",
headers: {
"Content-Type": "application/x-www-form-urlencoded; charset=UTF-8",
"Accept": "text/html"
},
body: new URLSearchParams({ inputText: value }).toString(),
credentials: "include"
});
const text = await response.text();
console.log("status:", response.status, "body:", text);
// HTMLから<p>タグの中身を抽出
const match = text.match(/<p[^>]*>\s*(\{[^}]+\})\s*<\/p>/i);
if (!match) {
return { status: "error", errorMessage: "HTML内に結果<p>が見つかりません" };
}
const content = match[1]; // {status=success, errorMessage=hoge}
// 中身をパース(=区切りを:に変換してJSON風に整形)
const obj = {};
content
.replace(/[{}]/g, "")
.split(",")
.forEach(pair => {
const [key, val] = pair.split("=").map(s => s.trim());
if (key) obj[key] = val || "";
});
// 想定フォーマットに変換して返す
return {
status: obj.status || "error",
data: { status: obj.status || "" },
errorMessage: obj.errorMessage || ""
};
} catch (error) {
throw new Error("通信エラー");
}
}
/**
* UIの更新を担当する処理
* @param {Object} options
* @param {string} options.message - 表示するメッセージ
* @param {string} options.color - メッセージの色
* @param {boolean} options.isValid - 登録ボタンの有効状態(true:有効、false:無効)
*/
function updateUI({ message, color, isValid }) {
resultMessage.textContent = message;
resultMessage.style.color = color;
if (submitButton) {
submitButton.disabled = !isValid;
}
}
/**
* 全体の検証処理(入力チェック → ページ呼び出し → UI更新)を実施する関数
*/
window.validate = async function () {
const checkValue = inputField.value;
if (!checkValue) {
updateUI({ message: "値を入力してください", color: "red", isValid: false });
return;
}
try {
const data = await performValidation(checkValue);
if (data.status === "success" && data.data && data.data.status === "success") {
updateUI({ message: "success", color: "green", isValid: true });
} else {
const errorMsg = (data.data && data.data.errorMessage) || data.errorMessage || "不明なエラー";
updateUI({ message: "エラー: " + errorMsg, color: "red", isValid: false });
}
} catch (error) {
updateUI({ message: error.message, color: "red", isValid: false });
}
};
});
const checkFieldName = "inputText"; // チェック対象のinput要素のname属性
const API_URL = 'https://spiral-site.com/testBackend'; // PHPを設置したページのURLに変更してください
<input type="text" name="inputText">
<p id="result"></p>
<button type="button" onclick="validate()">検証</button>
/* 必要に応じてスタイルを追加してください */
#result {
font-size: 1.2em;
margin-top: 10px;
}
.sp-form-next-button:disabled {
opacity: 0.5;
cursor: not-allowed;
}
最後に
実運用では、セキュリティ対策やエラーハンドリング、データベース連携などの機能を追加することで、より堅牢なシステムへと発展させることが可能です。
本記事が、非同期通信の理解に役立つことを願っています。
不具合やご質問がある場合は、下記の「コンテンツに関しての要望はこちら」からご連絡ください。