หากคุณเคยได้รับอีเมลทำนองว่า "ฉันหาข้อมูลในเว็บไซต์ของคุณไม่เจอ คุณช่วยฉันได้ไหม" นั่นแหละคือตัวอย่างการใช้งานที่ดีสำหรับแชทขนาดเล็กด้วย AI เป้าหมายในที่นี้ไม่ใช่การ "แทนที่" ทีมสนับสนุนของคุณ แต่เป็นการให้คำตอบเบื้องต้นที่เป็นประโยชน์โดยอิงจากเนื้อหาในเว็บไซต์ของคุณ Sans ติดตั้ง เสียบเข้าไป.


ความต้องการ / กรณีการใช้งาน

แชทบอท AI แบบ "ง่ายๆ" บน WordPress จุดประสงค์หลักคือการตอบคำถามซ้ำๆ เช่น เวลาเปิดทำการ นโยบายการคืนเงิน "จะหาซื้อสินค้าชิ้นนั้นชิ้นนี้ได้จากที่ไหน" บทสรุป ไม่ใช่คำแนะนำแบบยาวๆ หรือความช่วยเหลือด้านการนำทาง ("ฉันกำลังมองหาบทช่วยสอนเกี่ยวกับเพอร์มาลิงก์") บนบล็อก ฉันมักเห็นว่า 80% ของคำขอที่เข้ามานั้นสรุปได้เป็นคำถาม 10 ข้อ

สิ่งที่ AI นำมาเสนอในที่นี้คือ อินเทอร์เฟซแชทแบบเรียบง่าย + เส้นทาง AJAX ที่ปลอดภัยของ WordPress ซึ่งส่งคำถามไปยัง API AI (เช่น OpenAI) และส่งคำตอบที่ใช้งานได้กลับมา เราตั้งใจทำให้ทุกอย่างเรียบง่าย: ไม่มีวิดเจ็ตของบุคคลที่สาม ไม่มี SDK ไม่มีส่วนประกอบของ Composer

สุดท้ายแล้ว คุณจะรู้ว่า:

  • แสดงภาพแมวตัวเล็ก (HTML/CSS/JS) ผ่านชอร์ตโค้ดของ WordPress
  • ส่งคำถามไปยังเซิร์ฟเวอร์ WordPress ของคุณ (AJAX) พร้อมกับค่า nonce (โทเค็นป้องกัน CSRF)
  • การเรียกใช้ API ของ AI ด้วย wp_remote_post()จัดการข้อผิดพลาด/หมดเวลา และแคชการตอบสนองด้วย Transients
  • ปกป้องคีย์ API ของคุณ (ที่จัดเก็บไว้ใน wp-config.php) และหลีกเลี่ยงการเปิดเผยข้อมูลดังกล่าวให้กับเบราว์เซอร์

สรุปด่วน

  • คุณเพิ่มค่าคงที่ API ใน wp-config.php (ไม่ตรงประเด็นเลย)
  • คุณสร้าง mu- ปลั๊กอิน (ปลั๊กอิน “ต้องใช้”) ซึ่งมีชอร์ตโค้ดให้ใช้งาน [ai_chatbot].
  • ส่วนหน้า (JS) เรียก admin-ajax.php โดยใช้ค่า nonce ไม่ใช่การใช้ AI API โดยตรง
  • เซิร์ฟเวอร์เรียกใช้ API ผ่านทาง wp_remote_post()หมดเวลาสั้น และระบบจัดการข้อผิดพลาดที่ดี
  • แคชของข้อมูลตอบสนอง (ข้อมูลชั่วคราว) เพื่อลดต้นทุน
  • ทำความสะอาดการตอบสนองก่อนแสดงผล (wp_kses()เพื่อจำกัดความเสี่ยงจาก XSS

ควรใช้ AI สำหรับเรื่องนั้นเมื่อใด

ใช้แชทบอทประเภทนี้หาก:

  • คุณได้รับคำถามซ้ำๆ และต้องการคำตอบแรกทันที
  • เนื้อหาของคุณมีครบถ้วนอยู่แล้ว (คำถามที่พบบ่อย หน้า "เกี่ยวกับเรา" คู่มือต่างๆ) และ AI สามารถช่วยแนะนำผู้ใช้ได้
  • คุณยอมรับว่าบางครั้งการตอบกลับอาจไม่สมบูรณ์แบบ และคุณได้เพิ่มข้อความที่ชัดเจน ("การตอบกลับอัตโนมัติ")
  • คุณต้องการแชทบอทที่มีน้ำหนักเบา ควบคุมได้ง่าย โดยไม่ต้องพึ่งพาปลั๊กอินที่ไม่โปร่งใสซึ่งแทรกสคริปต์ภายนอกไปทั่วทุกหนแห่ง

ฉันมักแนะนำให้ใช้กับบล็อกสอนวิธีการ เว็บไซต์แสดงผลงาน หรือกลุ่มเฉพาะที่คำถามค่อนข้างคงที่ (เช่น "วิธีการจอง", "กำหนดเวลา", "ราคา")

เมื่อใดที่ไม่ควรใช้ AI

หากโซลูชัน WordPress แบบดั้งเดิมทำงานได้ดีกว่า ง่ายกว่า และถูกกว่า ก็ควรหลีกเลี่ยงการใช้ AI:

  • Recherche ฝึกงาน เริ่มต้นด้วยการปรับปรุงฟังก์ชันการค้นหา (การดึงข้อมูล การจัดหมวดหมู่ หน้า "แผนผังเว็บไซต์") การใช้ AI อาจมีราคาแพงเพียงแค่เพื่อบอกคุณว่า "ให้ใช้ฟังก์ชันการค้นหา"
  • การสนับสนุนอย่างละเอียดอ่อน (สุขภาพ กฎหมาย การเงิน): ความเสี่ยงต่อการเกิดภาพหลอนมีอยู่จริง ในกรณีเหล่านี้ การใช้แบบฟอร์มติดต่อและฐานข้อมูลความรู้จะปลอดภัยกว่า
  • ปัญหาด้านธุรกรรม (คำสั่ง, บัญชี): หากการตอบสนองขึ้นอยู่กับข้อมูลส่วนตัว อย่าสร้างแชท AI แบบ "ง่ายๆ" คุณจำเป็นต้องมีระบบยืนยันตัวตนที่แท้จริง สิทธิ์การเข้าถึง และแบบจำลองภัยคุกคาม
  • งบประมาณจำกัด ถ้าปริมาณการเข้าชมเว็บไซต์ไม่มาก ก็ไม่มีปัญหา แต่ถ้ามีผู้เข้าชม 50,000 ครั้งต่อวัน ค่าใช้จ่ายอาจพุ่งสูงขึ้นอย่างมากหากคุณไม่มีแคช/การจำกัดอัตราการใช้งาน

ข้อกำหนดเบื้องต้น

เวอร์ชันเป้าหมาย : WordPress 6.9.4 (เมษายน 2026) และ PHP 8.1 ขึ้นไป

คีย์ API AI ผมใช้ OpenAI เป็นตัวอย่างเพราะ API มีความเสถียรและมีเอกสารประกอบอย่างดี แต่โครงสร้างพื้นฐานจะเหมือนกันกับ Anthropic/Mistral/Google

ความเข้าใจอย่างรวดเร็ว: การเรียกใช้ API และ HTTP

Une API คืออินเทอร์เฟซที่ช่วยให้คุณสามารถร้องขอสิ่งใดสิ่งหนึ่งจากบริการ (ในที่นี้คือ "ตอบคำถามนี้") ในทางเทคนิคแล้ว คุณจะส่งคำขอ HTTP (ส่วนใหญ่อยู่ในรูปแบบไฟล์ .txt) POST) โดยใช้ JSON และคุณจะได้รับ JSON กลับมา

ใน WordPress การดำเนินการนี้ทำได้อย่างถูกต้องผ่านทาง HTTP API: wp_remote_post() (และ wp_remote_get()นี่คือวิธีการที่แนะนำ เนื่องจากสามารถจัดการการรับส่งข้อมูล (cURL, สตรีม) พร็อกซี และผสานรวมเข้ากับ WordPress ได้

แหล่งที่มาอย่างเป็นทางการ: WordPress HTTP API.

ตำแหน่งที่จะจัดเก็บคีย์ API (จำเป็น)

คุณจะเก็บกุญแจไว้ใน wp-config.phpไม่ควรใส่ไว้ในไฟล์ธีม และโดยเฉพาะอย่างยิ่งไม่ควรใส่ไว้ใน JavaScript หากคีย์ของคุณไปอยู่ในเบราว์เซอร์ มันจะถูกคัดลอกภายใน 30 วินาทีและนำไปใช้โดยที่คุณต้องเสียค่าใช้จ่าย

เพิ่มสิ่งนี้ลงใน wp-config.php (ควรอยู่ก่อนบรรทัด “แค่นี้แหละ หยุดตัดต่อได้แล้ว!”)

define('BPCAB_OPENAI_API_KEY', 'VOTRE_CLE_ICI');

ค่าใช้จ่าย การส่งข้อความแต่ละครั้งไปยัง API มีค่าใช้จ่าย (ต่อโทเค็น) แม้จะเป็นเพียง "ไม่กี่เซ็นต์" ก็อาจสะสมเพิ่มขึ้นได้ ดังนั้น เราจะใช้ระบบแคชและการจำกัดอัตราการใช้งานบนฝั่งเซิร์ฟเวอร์

ควรวางโค้ดไว้ที่ไหน

  • ตัวเลือกที่แนะนำ : mu- ปลั๊กอิน (ค่าใช้จ่าย อัตโนมัติ). เส้นทาง : wp-content/mu-plugins/.
  • ทางเลือก : ปลั๊กอินแบบกำหนดเองสุดคลาสสิกใน wp-content/plugins/.
  • หลีกเลี่ยง : functions.php ของธีม (โดยเฉพาะอย่างยิ่งหากคุณเปลี่ยนธีม หรือหากผู้สร้างอัปเดตไฟล์)

เอกสารอย่างเป็นทางการของ mu-plugins: ปลั๊กอินที่ต้องใช้.

สถาปัตยกรรมโซลูชัน

นี่คือข้อมูลทั้งหมดในรูปแบบภาษาที่เข้าใจง่าย:

  • ผู้เยี่ยมชมเปิดหน้าเว็บที่มีเนื้อหาดังนี้ [ai_chatbot].
  • ชอร์ตโค้ดนี้จะแสดง UI (หน้าต่างขนาดเล็ก) และโหลดไฟล์ JavaScript
  • เมื่อผู้ใช้ส่งข้อความ JavaScript จะส่งคำขอ POST ไปยังที่ใดที่หนึ่ง admin-ajax.php กับ:
    • ข้อความ
    • nonce ของ WordPress (คำสั่งค้นหาที่ป้องกันการปลอมแปลง)
  • WordPress รับคำขอผ่าน AJAX hook ตรวจสอบค่า nonce บังคับใช้ข้อจำกัดอัตราการใช้งาน จากนั้นจึงเรียกใช้ AI API ผ่านทาง wp_remote_post().
  • WordPress จะทำการตรวจสอบและกรองข้อมูลที่ได้รับ จัดเก็บไว้ชั่วคราวในแคช แล้วส่งข้อมูลในรูปแบบ JSON กลับไปยังเบราว์เซอร์
  • เบราว์เซอร์แสดงคำตอบ

เหตุใดจึงต้องใช้ WordPress AJAX (และไม่เรียกใช้ AI API ใน JavaScript)?

เนื่องจากคีย์ของคุณต้องอยู่บนฝั่งเซิร์ฟเวอร์ หากคุณเรียกใช้ OpenAI โดยตรงจากเบราว์เซอร์ คุณจะเปิดเผยคีย์...และคุณจะสูญเสียการควบคุม (ค่าใช้จ่าย การนำไปใช้ในทางที่ผิด การขโมยข้อมูล)

โค้ดฉบับสมบูรณ์ — ทีละขั้นตอน

เราจะสร้างปลั๊กอิน mu ที่มีคุณสมบัติดังนี้:

  • เพิ่มชอร์ตโค้ด [ai_chatbot]
  • การจัดคิว CSS/JS อย่างสะอาด
  • สร้างแอ็กชัน AJAX สำหรับผู้ใช้ที่เข้าสู่ระบบและผู้ใช้ที่ไม่ได้เข้าสู่ระบบ
  • เรียกใช้ API ของ OpenAI
  • แคชคำตอบ

ขั้นตอนที่ 1 — สร้างปลั๊กอิน mu

สร้างโฟลเดอร์ wp-content/mu-plugins/ ถ้าไฟล์นั้นไม่มีอยู่ ให้สร้างไฟล์ขึ้นมา:

wp-content/mu-plugins/bpcab-ai-chatbot.php

<?php
/**
 * Plugin Name: BPCAB — Chatbot IA simple (sans plugin)
 * Description: Ajoute un chatbot IA minimal via shortcode, avec appel serveur (wp_remote_post), cache transient, et sécurité de base.
 * Author: Vous
 * Version: 1.0.0
 */

if (!defined('ABSPATH')) {
	exit;
}

define('BPCAB_CHATBOT_VERSION', '1.0.0');

/**
 * Petit helper : récupère l'IP (approx) pour rate limiting.
 * Attention : derrière un proxy/CDN, l'IP peut être celle du proxy si mal configuré.
 */
function bpcab_get_client_ip(): string {
	$keys = array('HTTP_CF_CONNECTING_IP', 'HTTP_X_FORWARDED_FOR', 'REMOTE_ADDR');
	foreach ($keys as $key) {
		if (!empty($_SERVER[$key])) {
			$ip = sanitize_text_field(wp_unslash($_SERVER[$key]));
			// X-Forwarded-For peut contenir plusieurs IP : on prend la première.
			if (str_contains($ip, ',')) {
				$parts = explode(',', $ip);
				$ip = trim($parts[0]);
			}
			return $ip;
		}
	}
	return '0.0.0.0';
}

ขั้นตอนที่ 2 — การโหลดชอร์ตโค้ด + CSS/JS

Un รหัสผู้ใช้ เป็นแท็กที่อยู่ระหว่างวงเล็บ (เช่น [ai_chatbot]ซึ่ง WordPress จะแทนที่ด้วย HTML วิธีนี้สะดวกสำหรับ Divi 5, Elementor และ Avada เพราะทั้งหมดรู้วิธีแทรก shortcode (โมดูล "Code", วิดเจ็ต "Shortcode" เป็นต้น)

/**
 * Enqueue des assets uniquement si le shortcode est présent sur la page.
 */
function bpcab_maybe_enqueue_assets(): void {
	if (!is_singular()) {
		return;
	}

	global $post;
	if (!$post instanceof WP_Post) {
		return;
	}

	if (!has_shortcode($post->post_content, 'ai_chatbot')) {
		return;
	}

	$handle = 'bpcab-ai-chatbot';

	wp_register_style(
		$handle,
		plugins_url('bpcab-ai-chatbot.css', __FILE__),
		array(),
		BPCAB_CHATBOT_VERSION
	);

	wp_register_script(
		$handle,
		plugins_url('bpcab-ai-chatbot.js', __FILE__),
		array(),
		BPCAB_CHATBOT_VERSION,
		true
	);

	wp_enqueue_style($handle);
	wp_enqueue_script($handle);

	// Données côté JS (sans clé API !)
	wp_localize_script($handle, 'BPCAB_CHATBOT', array(
		'ajaxUrl' => admin_url('admin-ajax.php'),
		'nonce'   => wp_create_nonce('bpcab_chatbot_nonce'),
		'maxLen'  => 400,
	));
}
add_action('wp_enqueue_scripts', 'bpcab_maybe_enqueue_assets');

/**
 * Shortcode [ai_chatbot]
 */
function bpcab_ai_chatbot_shortcode(): string {
	// HTML volontairement simple, facile à styliser.
	ob_start();
	?>
	<div class="bpcab-chatbot" data-bpcab-chatbot="1">
		<div class="bpcab-chatbot__header">
			<strong>Assistant</strong>
			<span class="bpcab-chatbot__status" aria-live="polite">Prêt</span>
		</div>

		<div class="bpcab-chatbot__messages" role="log" aria-live="polite"></div>

		<form class="bpcab-chatbot__form">
			<input class="bpcab-chatbot__input" type="text" name="message" placeholder="Posez votre question…" autocomplete="off" />
			<button class="bpcab-chatbot__send" type="submit">Envoyer</button>
		</form>

		<p class="bpcab-chatbot__hint">
			<em>Réponse automatique. Ne partagez pas d’informations sensibles.</em>
		</p>
	</div>
	<?php
	return (string) ob_get_clean();
}
add_shortcode('ai_chatbot', 'bpcab_ai_chatbot_shortcode');

ข้อผิดพลาดที่พบบ่อยคือการวางโค้ดนี้ลงในไฟล์ที่ไม่ถูกต้อง (เช่น โค้ดตัวอย่างสำหรับสร้างโปรแกรม หรือปลั๊กอินตัวอย่างที่ทำงานช้าเกินไป) การใช้ปลั๊กอิน mu จะช่วยหลีกเลี่ยงปัญหาเหล่านี้ได้มาก

ขั้นตอนที่ 3 — สร้างไฟล์ CSS/JS

ในไฟล์เดียวกัน mu-plugins, สร้าง:

  • bpcab-ai-chatbot.css
  • bpcab-ai-chatbot.js

CSS ขั้นต่ำ (คุณสามารถปรับเปลี่ยนให้เข้ากับธีม/ตัวสร้างเว็บไซต์ได้):

.bpcab-chatbot{
	max-width: 520px;
	border: 1px solid rgba(0,0,0,.12);
	border-radius: 12px;
	overflow: hidden;
	background: #fff;
}

.bpcab-chatbot__header{
	display:flex;
	justify-content: space-between;
	align-items:center;
	padding: 12px 14px;
	background: #111827;
	color: #fff;
}

.bpcab-chatbot__messages{
	padding: 12px 14px;
	min-height: 220px;
	max-height: 360px;
	overflow:auto;
	background: #f9fafb;
}

.bpcab-chatbot__msg{
	margin: 0 0 10px 0;
	padding: 10px 12px;
	border-radius: 10px;
	line-height: 1.35;
}

.bpcab-chatbot__msg--user{
	background: #dbeafe;
}

.bpcab-chatbot__msg--bot{
	background: #fff;
	border: 1px solid rgba(0,0,0,.08);
}

.bpcab-chatbot__form{
	display:flex;
	gap: 8px;
	padding: 12px 14px;
	border-top: 1px solid rgba(0,0,0,.08);
	background: #fff;
}

.bpcab-chatbot__input{
	flex:1;
	padding: 10px 12px;
	border: 1px solid rgba(0,0,0,.18);
	border-radius: 10px;
}

.bpcab-chatbot__send{
	padding: 10px 14px;
	border-radius: 10px;
	border: 0;
	background: #111827;
	color: #fff;
	cursor: pointer;
}

.bpcab-chatbot__hint{
	padding: 0 14px 14px 14px;
	margin: 0;
	color: #6b7280;
	font-size: 13px;
}

JS ขั้นต่ำ : การส่งข้อมูลผ่าน AJAX ไปยัง WordPress เพื่อแสดงข้อความและจัดการสถานะ

(function () {
	function qs(root, sel) { return root.querySelector(sel); }

	function addMsg(messagesEl, text, who) {
		var p = document.createElement('p');
		p.className = 'bpcab-chatbot__msg bpcab-chatbot__msg--' + who;
		p.textContent = text;
		messagesEl.appendChild(p);
		messagesEl.scrollTop = messagesEl.scrollHeight;
	}

	function setStatus(root, text) {
		var s = qs(root, '.bpcab-chatbot__status');
		if (s) s.textContent = text;
	}

	function initChatbot(root) {
		var form = qs(root, '.bpcab-chatbot__form');
		var input = qs(root, '.bpcab-chatbot__input');
		var messages = qs(root, '.bpcab-chatbot__messages');

		if (!form || !input || !messages) return;

		addMsg(messages, "Bonjour ! Posez votre question, je vais essayer de vous orienter.", "bot");

		form.addEventListener('submit', function (e) {
			e.preventDefault();

			var msg = (input.value || '').trim();
			if (!msg) return;

			if (msg.length > (window.BPCAB_CHATBOT?.maxLen || 400)) {
				addMsg(messages, "Message trop long. Essayez de faire plus court.", "bot");
				return;
			}

			addMsg(messages, msg, "user");
			input.value = '';
			setStatus(root, 'Réflexion…');

			var data = new FormData();
			data.append('action', 'bpcab_chatbot_ask');
			data.append('nonce', window.BPCAB_CHATBOT?.nonce || '');
			data.append('message', msg);

			fetch(window.BPCAB_CHATBOT?.ajaxUrl || '', {
				method: 'POST',
				credentials: 'same-origin',
				body: data
			})
			.then(function (r) { return r.json(); })
			.then(function (payload) {
				if (!payload || !payload.success) {
					var err = payload?.data?.message || "Erreur côté serveur.";
					addMsg(messages, err, "bot");
					setStatus(root, 'Erreur');
					return;
				}
				addMsg(messages, payload.data.answer, "bot");
				setStatus(root, 'Prêt');
			})
			.catch(function () {
				addMsg(messages, "Impossible de contacter le serveur. Réessayez.", "bot");
				setStatus(root, 'Hors ligne');
			});
		});
	}

	document.addEventListener('DOMContentLoaded', function () {
		document.querySelectorAll('[data-bpcab-chatbot="1"]').forEach(initChatbot);
	});
})();

ข้อผิดพลาดที่พบบ่อย: “JS โหลดไม่ขึ้น” ใน 90% ของกรณี นี่คือแนวทางที่ผิด plugins_url()หรือแคช (ปลั๊กอิน/CDN) ที่ให้บริการเวอร์ชันเก่า เปลี่ยนเวอร์ชัน BPCAB_CHATBOT_VERSION เพื่อบังคับให้โหลดใหม่ หรือล้างแคช

ขั้นตอนที่ 4 — จุดเชื่อมต่อ AJAX + ค่า nonce + การจำกัดอัตราการใช้งาน

Un เบ็ด WordPress เป็นจุดเริ่มต้น มีสองประเภท:

  • การกระทำ : “ทำอะไรสักอย่างตรงนี้” (เช่น wp_enqueue_scripts).
  • ฟิลเตอร์ : “แก้ไขค่านี้” (เช่น the_content).

ในที่นี้ เราใช้การดำเนินการ AJAX: wp_ajax_* (เชื่อมต่อ) และ wp_ajax_nopriv_* (ไม่ได้เชื่อมต่อ)

/**
 * Rate limit très simple : X requêtes par minute par IP.
 * Ce n'est pas une protection parfaite, mais ça évite les abus basiques.
 */
function bpcab_rate_limit_or_die(string $ip, int $limit = 10, int $window_seconds = 60): void {
	$key = 'bpcab_rl_' . md5($ip);
	$hits = (int) get_transient($key);

	if ($hits >= $limit) {
		wp_send_json_error(array(
			'message' => 'Trop de requêtes. Attendez une minute et réessayez.'
		), 429);
	}

	set_transient($key, $hits + 1, $window_seconds);
}

/**
 * Handler AJAX : reçoit la question et renvoie une réponse IA.
 */
function bpcab_ajax_chatbot_ask(): void {
	// Vérification nonce (anti-CSRF)
	$nonce = isset($_POST['nonce']) ? sanitize_text_field(wp_unslash($_POST['nonce'])) : '';
	if (!wp_verify_nonce($nonce, 'bpcab_chatbot_nonce')) {
		wp_send_json_error(array('message' => 'Requête refusée (nonce invalide).'), 403);
	}

	$ip = bpcab_get_client_ip();
	bpcab_rate_limit_or_die($ip, 10, 60);

	$message = isset($_POST['message']) ? (string) wp_unslash($_POST['message']) : '';
	$message = trim($message);

	if ($message === '') {
		wp_send_json_error(array('message' => 'Message vide.'), 400);
	}

	if (mb_strlen($message) > 400) {
		wp_send_json_error(array('message' => 'Message trop long (max 400 caractères).'), 400);
	}

	$answer = bpcab_get_ai_answer($message);

	if (is_wp_error($answer)) {
		wp_send_json_error(array(
			'message' => $answer->get_error_message()
		), 500);
	}

	wp_send_json_success(array(
		'answer' => $answer,
	));
}
add_action('wp_ajax_bpcab_chatbot_ask', 'bpcab_ajax_chatbot_ask');
add_action('wp_ajax_nopriv_bpcab_chatbot_ask', 'bpcab_ajax_chatbot_ask');

ขั้นตอนที่ 5 — การเรียกใช้ OpenAI ผ่าน wp_remote_post() + แคชชั่วคราว

เราจะทำสิ่งต่อไปนี้:

  • สร้างคีย์แคชโดยอิงจากคำถาม (แฮช)
  • ตั้งค่า TTL (เช่น 24 ชั่วโมง) เพื่อหลีกเลี่ยงการจ่ายเงินสำหรับคำตอบเดียวกันซ้ำอีก
  • เพิ่มค่าหมดเวลาสั้นๆ (เช่น 20 วินาที) เพื่อป้องกันไม่ให้ PHP "ค้าง"
  • แก้ไขข้อมูลที่ได้รับ (อนุญาตให้ใช้ HTML เพียงบางส่วนเท่านั้น)
/**
 * Appelle l'API IA (OpenAI) et renvoie une réponse texte.
 * IMPORTANT : la clé API doit être définie dans wp-config.php via BPCAB_OPENAI_API_KEY
 */
function bpcab_get_ai_answer(string $user_message) {
	if (!defined('BPCAB_OPENAI_API_KEY') || BPCAB_OPENAI_API_KEY === '') {
		return new WP_Error('bpcab_missing_key', 'Clé API manquante. Ajoutez BPCAB_OPENAI_API_KEY dans wp-config.php.');
	}

	// Cache : même question => même réponse pendant 24h
	$cache_key = 'bpcab_ai_' . md5(mb_strtolower(trim($user_message)));
	$cached = get_transient($cache_key);
	if (is_string($cached) && $cached !== '') {
		return $cached;
	}

	/**
	 * Prompt système : court, orienté "site".
	 * Ici, on ne fait PAS encore de RAG (recherche dans vos contenus).
	 * On limite la responsabilité : pas de conseils médicaux/juridiques.
	 */
	$system = "Vous êtes un assistant pour un site WordPress. Répondez en français, de façon courte et pratique. "
		. "Si la question demande des infos sensibles (santé/juridique/finance), refusez et conseillez de contacter le propriétaire du site. "
		. "Si vous ne savez pas, dites-le et proposez une piste (ex: consulter la page FAQ).";

	/**
	 * API OpenAI (Chat Completions style Responses API selon évolution).
	 * En avril 2026, l'API a évolué plusieurs fois. Le principe reste :
	 * - endpoint HTTPS
	 * - JSON en entrée
	 * - JSON en sortie
	 *
	 * Si votre compte OpenAI recommande un endpoint différent, adaptez l'URL et le parsing.
	 * Référez-vous à la doc officielle.
	 */
	$endpoint = 'https://api.openai.com/v1/chat/completions';

	$body = array(
		'model' => 'gpt-4.1-mini',
		'temperature' => 0.2,
		'messages' => array(
			array('role' => 'system', 'content' => $system),
			array('role' => 'user', 'content' => $user_message),
		),
	);

	$args = array(
		'headers' => array(
			'Authorization' => 'Bearer ' . BPCAB_OPENAI_API_KEY,
			'Content-Type'  => 'application/json',
		),
		'timeout' => 20,
		'body' => wp_json_encode($body),
	);

	$response = wp_remote_post($endpoint, $args);

	if (is_wp_error($response)) {
		return new WP_Error('bpcab_http_error', 'Erreur HTTP : ' . $response->get_error_message());
	}

	$code = (int) wp_remote_retrieve_response_code($response);
	$raw  = (string) wp_remote_retrieve_body($response);

	if ($code < 200 || $code >= 300) {
		// On évite d'afficher tout le raw (peut contenir des détails techniques).
		return new WP_Error('bpcab_api_error', 'API IA indisponible (code ' . $code . '). Vérifiez votre clé/quota.');
	}

	$data = json_decode($raw, true);
	if (!is_array($data)) {
		return new WP_Error('bpcab_json_error', 'Réponse API illisible (JSON invalide).');
	}

	// Parsing "chat.completions"
	$text = $data['choices'][0]['message']['content'] ?? '';
	$text = is_string($text) ? trim($text) : '';

	if ($text === '') {
		return new WP_Error('bpcab_empty_answer', 'Réponse vide de l’API IA.');
	}

	/**
	 * Assainissement :
	 * - on autorise un peu de HTML basique (liens, strong, em, br)
	 * - on supprime le reste
	 */
	$allowed = array(
		'a' => array(
			'href' => true,
			'target' => true,
			'rel' => true,
		),
		'strong' => array(),
		'em' => array(),
		'br' => array(),
	);

	$safe = wp_kses($text, $allowed);

	// Cache 24h
	set_transient($cache_key, $safe, DAY_IN_SECONDS);

	return $safe;
}

สองข้อผิดพลาดที่ผมเห็นบ่อยๆ:

  • ลืมใส่เครื่องหมายเซมิโคลอน dans wp-config.php หรือในปลั๊กอิน mu: ผลลัพธ์คือหน้าจอสีขาว (ข้อผิดพลาดร้ายแรง) เปิดใช้งาน WP_DEBUG ในขั้นตอนการเตรียมงาน ไม่ใช่ในขั้นตอนการผลิตจริง
  • คัดลอกบทช่วยสอนเก่า ซึ่งใช้โครงสร้าง API เก่าหรือโมเดลที่ล้าสมัย ในกรณีนี้ คุณใช้ WordPress 6.9.4 + PHP 8.1 เป็นฐาน และคุณจะปรับเปลี่ยนเอนด์พอยต์ก็ต่อเมื่อ OpenAI เปลี่ยนคำแนะนำเท่านั้น

รหัสที่ประกอบเสร็จสมบูรณ์

ด้านล่างนี้คือไฟล์ฉบับสมบูรณ์ mu- ปลั๊กอินคุณจะต้องสร้างไฟล์ CSS/JS (ดังแสดงด้านบน) ด้วย อย่าใส่คีย์ในไฟล์นี้

<?php
/**
 * Plugin Name: BPCAB — Chatbot IA simple (sans plugin)
 * Description: Chatbot IA minimal via shortcode, AJAX WordPress, appel OpenAI avec wp_remote_post(), cache transient, sécurité de base.
 * Author: Vous
 * Version: 1.0.0
 */

if (!defined('ABSPATH')) {
	exit;
}

define('BPCAB_CHATBOT_VERSION', '1.0.0');

function bpcab_get_client_ip(): string {
	$keys = array('HTTP_CF_CONNECTING_IP', 'HTTP_X_FORWARDED_FOR', 'REMOTE_ADDR');
	foreach ($keys as $key) {
		if (!empty($_SERVER[$key])) {
			$ip = sanitize_text_field(wp_unslash($_SERVER[$key]));
			if (str_contains($ip, ',')) {
				$parts = explode(',', $ip);
				$ip = trim($parts[0]);
			}
			return $ip;
		}
	}
	return '0.0.0.0';
}

function bpcab_maybe_enqueue_assets(): void {
	if (!is_singular()) {
		return;
	}

	global $post;
	if (!$post instanceof WP_Post) {
		return;
	}

	if (!has_shortcode($post->post_content, 'ai_chatbot')) {
		return;
	}

	$handle = 'bpcab-ai-chatbot';

	wp_register_style(
		$handle,
		plugins_url('bpcab-ai-chatbot.css', __FILE__),
		array(),
		BPCAB_CHATBOT_VERSION
	);

	wp_register_script(
		$handle,
		plugins_url('bpcab-ai-chatbot.js', __FILE__),
		array(),
		BPCAB_CHATBOT_VERSION,
		true
	);

	wp_enqueue_style($handle);
	wp_enqueue_script($handle);

	wp_localize_script($handle, 'BPCAB_CHATBOT', array(
		'ajaxUrl' => admin_url('admin-ajax.php'),
		'nonce'   => wp_create_nonce('bpcab_chatbot_nonce'),
		'maxLen'  => 400,
	));
}
add_action('wp_enqueue_scripts', 'bpcab_maybe_enqueue_assets');

function bpcab_ai_chatbot_shortcode(): string {
	ob_start();
	?>
	<div class="bpcab-chatbot" data-bpcab-chatbot="1">
		<div class="bpcab-chatbot__header">
			<strong>Assistant</strong>
			<span class="bpcab-chatbot__status" aria-live="polite">Prêt</span>
		</div>

		<div class="bpcab-chatbot__messages" role="log" aria-live="polite"></div>

		<form class="bpcab-chatbot__form">
			<input class="bpcab-chatbot__input" type="text" name="message" placeholder="Posez votre question…" autocomplete="off" />
			<button class="bpcab-chatbot__send" type="submit">Envoyer</button>
		</form>

		<p class="bpcab-chatbot__hint">
			<em>Réponse automatique. Ne partagez pas d’informations sensibles.</em>
		</p>
	</div>
	<?php
	return (string) ob_get_clean();
}
add_shortcode('ai_chatbot', 'bpcab_ai_chatbot_shortcode');

function bpcab_rate_limit_or_die(string $ip, int $limit = 10, int $window_seconds = 60): void {
	$key = 'bpcab_rl_' . md5($ip);
	$hits = (int) get_transient($key);

	if ($hits >= $limit) {
		wp_send_json_error(array(
			'message' => 'Trop de requêtes. Attendez une minute et réessayez.'
		), 429);
	}

	set_transient($key, $hits + 1, $window_seconds);
}

function bpcab_get_ai_answer(string $user_message) {
	if (!defined('BPCAB_OPENAI_API_KEY') || BPCAB_OPENAI_API_KEY === '') {
		return new WP_Error('bpcab_missing_key', 'Clé API manquante. Ajoutez BPCAB_OPENAI_API_KEY dans wp-config.php.');
	}

	$cache_key = 'bpcab_ai_' . md5(mb_strtolower(trim($user_message)));
	$cached = get_transient($cache_key);
	if (is_string($cached) && $cached !== '') {
		return $cached;
	}

	$system = "Vous êtes un assistant pour un site WordPress. Répondez en français, de façon courte et pratique. "
		. "Si la question demande des infos sensibles (santé/juridique/finance), refusez et conseillez de contacter le propriétaire du site. "
		. "Si vous ne savez pas, dites-le et proposez une piste (ex: consulter la page FAQ).";

	$endpoint = 'https://api.openai.com/v1/chat/completions';

	$body = array(
		'model' => 'gpt-4.1-mini',
		'temperature' => 0.2,
		'messages' => array(
			array('role' => 'system', 'content' => $system),
			array('role' => 'user', 'content' => $user_message),
		),
	);

	$args = array(
		'headers' => array(
			'Authorization' => 'Bearer ' . BPCAB_OPENAI_API_KEY,
			'Content-Type'  => 'application/json',
		),
		'timeout' => 20,
		'body' => wp_json_encode($body),
	);

	$response = wp_remote_post($endpoint, $args);

	if (is_wp_error($response)) {
		return new WP_Error('bpcab_http_error', 'Erreur HTTP : ' . $response->get_error_message());
	}

	$code = (int) wp_remote_retrieve_response_code($response);
	$raw  = (string) wp_remote_retrieve_body($response);

	if ($code < 200 || $code >= 300) {
		return new WP_Error('bpcab_api_error', 'API IA indisponible (code ' . $code . '). Vérifiez votre clé/quota.');
	}

	$data = json_decode($raw, true);
	if (!is_array($data)) {
		return new WP_Error('bpcab_json_error', 'Réponse API illisible (JSON invalide).');
	}

	$text = $data['choices'][0]['message']['content'] ?? '';
	$text = is_string($text) ? trim($text) : '';

	if ($text === '') {
		return new WP_Error('bpcab_empty_answer', 'Réponse vide de l’API IA.');
	}

	$allowed = array(
		'a' => array('href' => true, 'target' => true, 'rel' => true),
		'strong' => array(),
		'em' => array(),
		'br' => array(),
	);

	$safe = wp_kses($text, $allowed);

	set_transient($cache_key, $safe, DAY_IN_SECONDS);

	return $safe;
}

function bpcab_ajax_chatbot_ask(): void {
	$nonce = isset($_POST['nonce']) ? sanitize_text_field(wp_unslash($_POST['nonce'])) : '';
	if (!wp_verify_nonce($nonce, 'bpcab_chatbot_nonce')) {
		wp_send_json_error(array('message' => 'Requête refusée (nonce invalide).'), 403);
	}

	$ip = bpcab_get_client_ip();
	bpcab_rate_limit_or_die($ip, 10, 60);

	$message = isset($_POST['message']) ? (string) wp_unslash($_POST['message']) : '';
	$message = trim($message);

	if ($message === '') {
		wp_send_json_error(array('message' => 'Message vide.'), 400);
	}

	if (mb_strlen($message) > 400) {
		wp_send_json_error(array('message' => 'Message trop long (max 400 caractères).'), 400);
	}

	$answer = bpcab_get_ai_answer($message);

	if (is_wp_error($answer)) {
		wp_send_json_error(array(
			'message' => $answer->get_error_message()
		), 500);
	}

	wp_send_json_success(array('answer' => $answer));
}
add_action('wp_ajax_bpcab_chatbot_ask', 'bpcab_ajax_chatbot_ask');
add_action('wp_ajax_nopriv_bpcab_chatbot_ask', 'bpcab_ajax_chatbot_ask');

คำอธิบายของโค้ด

ทำไมต้องใช้ปลั๊กอิน mu?

ปลั๊กอิน mu จะโหลดโดยอัตโนมัติโดยไม่ต้องเปิดใช้งาน และมีความ "เปราะบาง" น้อยกว่าโค้ดที่คัดลอกไปวางในธีม จากประสบการณ์ของผม เมื่อผู้เริ่มต้นใส่โค้ดเข้าไป functions.php จากนั้นเมื่อเปลี่ยนธีม (หรืออัปเดตธีมหลัก) แชทบอทก็จะหายไป

Pourquoi wp_localize_script()

เราใช้มันที่นี่เพื่อเปลี่ยนไปใช้ JS:

  • URL ของ AJAX (admin-ajax.php)
  • ทูตวาติกัน
  • ขีดจำกัดความยาว

วิธีนี้ช่วยหลีกเลี่ยงการ "กำหนด URL แบบตายตัว" และใช้งานได้แม้ว่า WordPress จะติดตั้งอยู่ในโฟลเดอร์ย่อยก็ตาม

เอกสาร: wp_localize_script ().

Nonce: สิ่งที่มันปกป้องอย่างแท้จริง

WordPress nonce ป้องกันไม่ให้เว็บไซต์อื่นส่งคำขอในนามของคุณผ่านเบราว์เซอร์ของผู้เข้าชม (การโจมตี CSRF) มันไม่ได้มาแทนที่ระบบการตรวจสอบสิทธิ์ แต่สำหรับแชทบอทสาธารณะแล้ว มันเป็นข้อกำหนดขั้นต่ำที่จำเป็น

เอกสาร: ประกาศจาก WordPress.

แคชข้อมูลชั่วคราว: เหตุใดจึงสำคัญ

les ชั่วคราว นี่คือแคชแบบคีย์/ค่าที่มีวันหมดอายุ หากผู้เยี่ยมชมถามว่า "เวลาทำการของคุณคือเมื่อไหร่?" 200 ครั้งในหนึ่งเดือน คุณคงไม่อยากจ่ายค่าบริการ AI 200 ครั้ง คุณจ่ายเพียงครั้งเดียว แล้วจึงแสดงคำตอบจากแคช

เอกสาร: API Transients.

การชำระล้างการตอบสนอง

API ของ AI อาจส่งข้อความ (หรือแม้แต่ HTML) ที่ไม่คาดคิดกลับมา หากคุณแทรกข้อความนี้เข้าไปใน DOM โดยตรง คุณอาจเปิดช่องโหว่ XSS ได้ ดูที่นี่:

  • เราอนุญาตเท่านั้น a, strong, em, br
  • อย่างอื่นถูกลบหมดแล้ว

ฟังก์ชันที่ใช้: wp_kses()เอกสาร: wp_kses().

ต้นทุนและการเพิ่มประสิทธิภาพ API

ราคาที่แน่นอนขึ้นอยู่กับรุ่นและสัญญาของคุณ ต่อไปนี้คือสิ่งที่สำคัญสำหรับการประมาณราคา:

  • จำนวนข้อความต่อเดือน
  • ความยาวเฉลี่ยของคำถามและคำตอบ (โทเค็น)
  • อัตราการเข้าถึงแคช (จำนวนคำถามที่เหมือนกันที่ถูกถามซ้ำ)

การประเมิน "หน้างาน" (ลำดับขนาด)

ในแชทบอท "แนะนำการใช้งาน" แบบง่ายๆ ผมมักสังเกตเห็นดังนี้:

  • คำถาม: 20 ถึง 60 โทเค็น
  • คำตอบ: 60 ถึง 200 โทเค็น
  • รวม: 100 ถึง 300 โทเค็นต่อการโต้ตอบ

หากคุณมีการโต้ตอบ 2,000 ครั้งต่อเดือน นั่นหมายถึง 200,000 ถึง 600,000 โทเค็นต่อเดือน ขึ้นอยู่กับโมเดล อาจจะสมเหตุสมผล... หรืออาจจะไม่ใช่ การแคชและโมเดล "ขนาดเล็ก" จะสร้างความแตกต่างอย่างมาก

การเพิ่มประสิทธิภาพทันที

  • แคช 24 ชั่วโมง (มีอยู่แล้ว) สำหรับคำถามที่พบบ่อย (FAQ) ที่เสถียร คุณสามารถเพิ่มช่วงเวลาเป็น 7 วันได้
  • คำตอบที่สั้นกว่า : เพิ่มข้อความ “ตอบไม่เกิน 5 ประโยค” ลงในคำถาม
  • อุณหภูมิต่ำ : จำนวนรูปแบบที่น้อยลง การเข้าถึงแคชก็จะมากขึ้น
  • จำกัดความยาว มีการส่งข้อความทั้งฝั่ง JavaScript และ PHP (ซึ่งมีอยู่แล้ว) เป็นการป้องกันสองชั้นเสมอ

รูปแบบขั้นสูงและกรณีการใช้งาน

ตัวเลือกที่ 1 — เพิ่ม "บริบทของไซต์" (โดยไม่ต้องใช้ RAG)

โดยไม่ต้องค้นหาผ่านบทความของคุณ คุณสามารถให้ข้อมูลบริบทแบบคงที่สั้นๆ (เช่น เวลาทำการ URL ของคำถามที่พบบ่อย) ซึ่งมีประโยชน์สำหรับเว็บไซต์ที่แสดงผลงาน

// Exemple : ajoutez ceci avant $body dans bpcab_get_ai_answer()
$site_context = "Contexte du site :n"
	. "- FAQ : https://example.com/faq/n"
	. "- Contact : https://example.com/contact/n"
	. "- Horaires : lun-ven 9h-18hn";

$body['messages'] = array(
	array('role' => 'system', 'content' => $system . "nn" . $site_context),
	array('role' => 'user', 'content' => $user_message),
);

ตัวเลือกที่ 2 — โหมด “สรุปบทความ” ผ่านแอตทริบิวต์ชอร์ตโค้ด

คุณสามารถอนุญาตได้ [ai_chatbot mode="resume"] และส่งข้อความที่ดึงมาจากหน้าปัจจุบันไปยัง AI หมายเหตุ: ยิ่งมีโทเค็นมากเท่าไร ค่าใช้จ่ายก็ยิ่งสูงขึ้นเท่านั้น

// Exemple (incomplet) : détecter un attribut et injecter le contenu
function bpcab_ai_chatbot_shortcode($atts = array()): string {
	$atts = shortcode_atts(array('mode' => 'chat'), $atts, 'ai_chatbot');

	// ... même HTML qu'avant, mais vous pourriez ajouter data-mode
	// <div data-mode="chat"> etc.
	// Ce snippet est volontairement partiel : il faut adapter le JS pour envoyer le mode.
	return '...';
}

ขอชี้แจงให้ชัดเจน: โค้ดส่วนนี้ยังไม่สมบูรณ์ เพื่อให้ใช้งานได้ โค้ด JavaScript ก็ต้องได้รับการแก้ไขด้วย (ส่ง) mode) และตัวจัดการ AJAX (เปลี่ยนข้อความแจ้งเตือนตามโหมด)

ตัวแปร 3 — การรวม Divi 5 / Elementor / Avada

  • Divi 5 เพิ่มโมดูล "โค้ด" หรือ "ชอร์ตโค้ด" แล้ววางลงไป [ai_chatbot]หาก Divi ทำการย่อ/รวมไฟล์ CSS/JS ให้ล้างแคชแบบคงที่ของ Divi หากไฟล์ CSS/JS ไม่ได้รับการอัปเดต
  • Elementor วิดเจ็ต “ชอร์ตโค้ด” → [ai_chatbot]หากคุณใช้การเพิ่มประสิทธิภาพไฟล์ภาพของ Elementor โปรดตรวจสอบว่าสคริปต์ไม่ได้ถูกเลื่อนการทำงานอย่างรุนแรง (มิฉะนั้น) DOMContentLoaded สามารถเกิดขึ้นได้ก่อนการฉีด: ในกรณีนี้ ให้เริ่มต้นการทำงานด้วยเช่นกัน elementor/frontend/init).
  • Avada : เพิ่มองค์ประกอบ “Shortcode” ใน Fusion Builder หากคุณใช้ Avada caching ให้ล้างแคชหลังจากเพิ่มไฟล์ CSS/JS แล้ว

ความปลอดภัยและแนวทางปฏิบัติที่ดีที่สุด

ห้ามเปิดเผยคีย์ API ทางฝั่งไคลเอ็นต์เด็ดขาด

กฎง่ายๆ: กุญแจต้องเสียบคาไว้ wp-config.phpเบราว์เซอร์ไม่ควรเห็นมันเลย แม้จะ "ซ่อน" อยู่ในชุดไฟล์ JavaScript ก็ยังสามารถกู้คืนได้อยู่ดี

ตรวจสอบและจำกัดจำนวนรายการ

  • ความยาวสูงสุดฝั่ง JavaScript (UX) + ฝั่ง PHP (ความปลอดภัย)
  • ปฏิเสธข้อความว่างเปล่า
  • มีการจำกัดอัตราการใช้งานตามที่อยู่ IP (มีการใช้งานอยู่แล้ว) หากต้องการจำกัดเพิ่มเติม คุณสามารถจำกัดตามเซสชัน/คุกกี้ได้ด้วย

ทำความสะอาดทางออก

แสดงผลลัพธ์เป็นข้อความ (เช่นเดียวกับใน JavaScript) textContentหรือกรองอย่างเข้มงวดหากอนุญาตให้ใช้ HTML ในกรณีนี้ เราทำทั้งสองอย่าง คือกรองข้อมูลฝั่งเซิร์ฟเวอร์และแสดงผลเป็นข้อความฝั่งไคลเอ็นต์ ซึ่งเป็นการกระทำที่ "ระมัดระวังเป็นพิเศษ" โดยเจตนา

GDPR: ข้อมูลที่ส่งไปยังบุคคลที่สาม

หากผู้เยี่ยมชมป้อนข้อมูลส่วนบุคคล คุณอาจส่งข้อมูลนั้นไปยังผู้ให้บริการ (OpenAI) ดังนั้น โปรดวางแผนให้เหมาะสม:

  • ข้อความที่ชัดเจน (“อย่าเปิดเผยข้อมูลที่ละเอียดอ่อน”)
  • การกล่าวถึงในนโยบายความเป็นส่วนตัวของคุณ
  • การตั้งค่าผู้ให้บริการ (การเก็บรักษาข้อมูล การยกเลิกการรับข้อมูล ฯลฯ) ตามสัญญาของคุณ

ห้ามทดสอบในสภาพแวดล้อมการใช้งานจริงโดยไม่มีข้อมูลสำรอง

ปลั๊กอิน mu ที่มีข้อผิดพลาด PHP จะทำให้เว็บไซต์ทั้งหมดใช้งานไม่ได้ (เพราะมันโหลดโดยอัตโนมัติ) ควรทดลองทำในเวอร์ชันทดสอบก่อน หากจำเป็นต้องใช้งานในเวอร์ชันใช้งานจริง ควรคงสิทธิ์การเข้าถึง FTP/SSH ไว้เพื่อลบไฟล์ในกรณีที่หน้าจอว่างเปล่า

วิธีการทดสอบและแก้ไขข้อผิดพลาด

เปิดใช้งานการบันทึกข้อมูลอย่างถูกต้อง

ในสภาพแวดล้อมการทดสอบ ให้เปิดใช้งาน:

define('WP_DEBUG', true);
define('WP_DEBUG_LOG', true);
define('WP_DEBUG_DISPLAY', false);

เอกสาร: การดีบักใน WordPress.

ตรวจสอบคำขอ AJAX

  • เปิดเครื่องมือสำหรับนักพัฒนา (DevTools) ของเบราว์เซอร์ → แท็บเครือข่าย → กรองตาม admin-ajax.php.
  • ตรวจสอบสถานะ HTTP (200/403/429/500) และการตอบสนอง JSON
  • หากคุณเห็นหน้า HTML แทนที่จะเป็น JSON นั่นมักเป็นข้อผิดพลาดร้ายแรงของ PHP (หรือปลั๊กอินรักษาความปลอดภัยที่ดักจับข้อมูลอยู่)

ทดสอบ AI API “ในการทดลองใช้งานจริง”

ก่อนที่จะผสานรวม JavaScript คุณสามารถโทรติดต่อได้ bpcab_get_ai_answer() ในบริบทของผู้ดูแลระบบ (ชั่วคราว) และบันทึกการตอบกลับ อย่าปล่อยโค้ดนี้ไว้ถาวร

ถ้าวิธีนั้นไม่ได้ผล

อาการ สาเหตุที่เป็นไปได้ การตรวจสอบ Solution
ไม่มีอะไรแสดงบนหน้าเว็บ รหัสย่อหายไปหรือไม่ได้รับการตีความ ตรวจสอบว่าหน้าเว็บนั้นมีเนื้อหาดังต่อไปนี้ [ai_chatbot] (ไม่อยู่ในบล็อก "โค้ด" ที่มีการหลีกเลี่ยงวงเล็บ) ใช้บล็อก "Shortcode" (Elementor) / โมดูล Shortcode (Divi/Avada)
หน้าต่างแชทปรากฏขึ้น แต่ปุ่มไม่ตอบสนอง JavaScript โหลดไม่สำเร็จ (แคช, เส้นทาง, ข้อขัดแย้ง) เครื่องมือสำหรับนักพัฒนา → คอนโซล (ข้อผิดพลาด) + เครือข่าย (ไฟล์ JS 404?) ตรวจสอบ plugins_url()ล้างแคช เพิ่มค่า BPCAB_CHATBOT_VERSION
ตอบกลับ “ไม่ถูกต้อง ไม่มี” nonce หมดอายุ, การแคชหน้าเว็บแบบเข้มข้น หรือ JavaScript กำลังรับค่า nonce เก่า ดูที่มูลค่า BPCAB_CHATBOT.nonce ในคอนโซล ลดขนาดแคชในหน้าเว็บที่มีฟังก์ชันแชท หรือสร้างค่า nonce ใหม่เมื่อโหลดหน้าเว็บ (วิธีขั้นสูงกว่า)
ข้อผิดพลาด 429 “มีการร้องขอมากเกินไป” ข้อจำกัดอัตราที่เข้มงวดเกินไป หรือการทดสอบซ้ำซ้อน ลองทำแบบเดียวกันในโหมดการเรียกดูแบบส่วนตัว / ใช้ IP ที่แตกต่างกัน เพิ่มช่วงเวลา/ขีดจำกัด หรือจำกัดเฉพาะผู้ใช้ที่เข้าสู่ระบบแล้ว
ข้อผิดพลาด “AI API ไม่พร้อมใช้งาน (รหัส 401/403)” คีย์ไม่ถูกต้อง, ไม่ได้โหลดคีย์, สิทธิ์การเข้าถึง ตรวจสอบ BPCAB_OPENAI_API_KEY dans wp-config.php (ไม่มีช่องว่าง) สร้างรหัสใหม่ ตรวจสอบการเรียกเก็บเงิน/โควต้าทางฝั่งผู้จำหน่าย
ข้อผิดพลาด “JSON ไม่ถูกต้อง” การตอบสนอง API ถูกตัดทอน (พร็อกซี, WAF) หรือปลายทางเปลี่ยนแปลงไป เข้าสู่ระบบ $raw ในขั้นตอนการเตรียมการ (โปรดสังเกตข้อมูล) ปรับปลายทาง/รูปแบบตามเอกสารทางการ และเพิ่มระยะเวลาหมดเวลาหากจำเป็น
หน้าจอสีขาวหลังจากเพิ่มปลั๊กอิน mu ข้อผิดพลาด PHP (วงเล็บ, เครื่องหมายเซมิโคลอน) เวอร์ชัน PHP เก่าเกินไป ปรึกษา wp-content/debug.log หรือบันทึกเซิร์ฟเวอร์ แก้ไขไวยากรณ์ ตรวจสอบว่าเป็น PHP เวอร์ชัน 8.1 ขึ้นไป และลบไฟล์ผ่าน FTP หากจำเป็น

ปัญหาที่สมจริงและวิธีแก้ไขที่รวดเร็ว

  • วางโค้ดผิดที่ หากคุณใส่โค้ดไว้ในส่วน "โค้ดที่กำหนดเอง" ของตัวสร้างเว็บไซต์ โค้ดนั้นอาจถูกกรอง/แปลงเป็นอักขระพิเศษ ควรใช้ mu-plugin แทน
  • ตะขอที่ไม่เหมาะสม หากคุณสอบถาม JS บน initคุณเสี่ยงที่จะโหลดเร็วเกินไป/ไม่ถูกต้อง ในที่นี้เราใช้ wp_enqueue_scripts.
  • ความขัดแย้งของแคช แคชบางตัวจะแคช HTML ที่มีค่า nonce อยู่ด้วย ผลที่ได้คือ ค่า nonce จะล้าสมัยสำหรับทุกคน วิธีแก้ปัญหา: ไม่รวมหน้านั้นไว้ในแคช หรือสร้างเส้นทางที่ส่งคืนค่า nonce ที่ "ใหม่กว่า" (วิธีขั้นสูง)
  • Permalinks ไม่เกี่ยวข้องโดยตรง แต่ฉันเคยเห็นเว็บไซต์ที่... admin_url() กำลังถูกกรองโดยปลั๊กอินรักษาความปลอดภัยที่ตั้งค่าไม่ถูกต้อง หาก AJAX ไม่ตอบสนอง ให้ทดสอบ URL /wp-admin/admin-ajax.php โดยตรงในเบราว์เซอร์

ทรัพยากร

คำถามที่พบบ่อย

ถ้าผมเพิ่มปลั๊กอิน mu เข้าไป มันจะ "ไม่ต้องใช้ปลั๊กอิน" จริงๆ หรือเปล่า?

คุณไม่ได้ติดตั้งปลั๊กอินจากภายนอก wordpress.org แต่ในทางเทคนิคแล้ว คุณกำลังเพิ่มโค้ดในรูปแบบของปลั๊กอิน ซึ่งเป็นเจตนา เพราะเป็นวิธีที่สะอาดที่สุดในการทำให้โค้ดเป็นอิสระจากธีม

ฉันสามารถใส่โค้ดลงไปได้ไหม functions.php ?

ใช่ แต่ฉันไม่แนะนำ คุณเสี่ยงที่จะสูญเสียแชทบอทเมื่อคุณเปลี่ยนธีม และโปรแกรมสร้างธีมอาจทำให้การแก้ไขข้อผิดพลาดซับซ้อนขึ้น หากคุณจะทำจริงๆ ให้ใช้ธีมลูก (child theme)

ทำไมต้องใช้ admin-ajax.php แทนที่จะใช้ REST API?

ทั้งสองวิธีใช้ได้ผล สำหรับผู้เริ่มต้น WordPress ที่ใช้ AJAX นั้นติดตั้งง่ายและรวดเร็ว หากต้องการวิธีการที่ทันสมัยกว่า ให้เปลี่ยนไปใช้ REST register_rest_route() และสิทธิ์การเรียกกลับ แกนหลัก (เรียก) wp_remote_post()(แคช, ความปลอดภัย) ยังคงเหมือนเดิม

ค่า nonce มีปัญหาเมื่อใช้งานร่วมกับปลั๊กอินแคชของฉัน ฉันควรทำอย่างไรดี?

การไม่รวมหน้าเว็บนั้นไว้ในแคช (วิธีแก้ปัญหาแบบง่าย) หรือการสร้างเอนด์พอยต์ที่ส่งค่า nonce กลับมาเมื่อมีการร้องขอ จากนั้นอัปเดต JavaScript เพื่อเรียกใช้ค่าดังกล่าว วิธีนี้เป็นวิธีคลาสสิกสำหรับเว็บไซต์ที่มีการแคชข้อมูลจำนวนมาก (CDN ที่มีประสิทธิภาพสูง)

ฉันจะจำกัดการใช้งานแชทบอทให้แสดงเฉพาะบางหน้าได้อย่างไร?

ชอร์ตโค้ดช่วยให้คุณควบคุมสิ่งนี้ได้อยู่แล้ว: คุณเพียงแค่เพิ่มมันในตำแหน่งที่คุณต้องการ และโค้ดจะเรียกใช้ JavaScript/CSS ก็ต่อเมื่อมีชอร์ตโค้ดอยู่เท่านั้น

เราจะป้องกันไม่ให้ AI พูดจาไร้สาระได้อย่างไร?

คุณไม่สามารถรับประกันได้ 100% ลดความเสี่ยง:

  • คำตอบสั้นๆ
  • อุณหภูมิต่ำ
  • ข้อความนั้นชัดเจน: “ถ้าคุณไม่รู้ ก็บอกมาตรงๆ”
  • ไปยังหน้าคำถามที่พบบ่อย/ติดต่อเรา

ฉันสามารถแสดงลิงก์ที่คลิกได้ในคำตอบหรือไม่?

ใช่ แต่ต้องทำอย่างระมัดระวัง ในบทช่วยสอนนี้ เราจะทำความสะอาดด้วย wp_kses() โดยการอนุญาต aในส่วนของ JavaScript เราจะแสดงผลด้วย textContent (ดังนั้นจึงไม่มี HTML) หากคุณต้องการลิงก์ที่คลิกได้ คุณต้องแสดงลิงก์เหล่านั้นในรูปแบบ HTML (innerHTML) และเพื่อใช้ความระมัดระวังเป็นพิเศษ (สุขอนามัยที่เข้มงวด การเติมอัตโนมัติของ rel="noopener nofollow").

ใช้งานร่วมกับ Divi 5 / Elementor / Avada ได้หรือไม่?

ใช่: ใช้โมดูล/วิดเจ็ต "Shortcode" แล้ววางลงไป [ai_chatbot]โค้ดนี้ไม่ขึ้นอยู่กับธีม ปัญหาที่มักเกิดขึ้นมักมาจากเรื่องการแคช/การย่อขนาดไฟล์: การล้างแคชหลังจากเพิ่มไฟล์ใหม่

ทำไมถึงจำกัดไว้แค่ 400 ตัวอักษรล่ะ?

เพื่อหลีกเลี่ยงข้อความแจ้งเตือนจำนวนมาก ลดต้นทุน และจำกัดการใช้ในทางที่ผิด คุณสามารถเพิ่มจำนวนข้อความแจ้งเตือนได้ แต่โปรดตระหนักถึงผลที่ตามมาอย่างเต็มที่ (โทเค็น ความล่าช้า การเรียกเก็บเงิน)

จะเปลี่ยนโมเดล AI ได้อย่างไร?

เปลี่ยนค่า model dans $bodyควรใช้โมเดล "ขนาดเล็ก" สำหรับแชทบอทให้คำแนะนำ หากต้องการขยายขนาด ควรตรวจสอบต้นทุนและเวลาแฝงอยู่เสมอ

ฉันได้รับข้อความแสดงข้อผิดพลาด “HTTP Error: cURL error 28”

หมดเวลาแล้ว โปรดตรวจสอบ:

  • อนุญาตให้เข้าถึงเครือข่ายจากเซิร์ฟเวอร์โฮสติ้ง (ไฟร์วอลล์)
  • DNS
  • ออกเมนเตซ timeout (เช่น 30) หากเซิร์ฟเวอร์ของคุณทำงานช้า

หากคุณใช้แพ็กเกจโฮสติ้งแบบแชร์ที่ล็อกไว้ นี่เป็นเรื่องปกติ