我在这里遇到了一个复杂的小问题。
我正在构建一个WordPress插件,我选择了一个"父母" post(我调用的自定义类型' step')然后AJAX函数显示一个新的选择栏,其中包含该父项的所有子项。我这样做是通过输出在AJAX函数中调用的PHP文件中的new和元素来实现的。这有效,但现在我想重复这个过程,当这个新的输出元素添加到页面时,从同一个JQuery文件运行一个函数。 (参见Javascript代码)
主要php插件文件(在插件目录下的文件夹中):
<?php
/*
Plugin Name: n8jadams Step by Step Plugin (WIP)
Plugin URI:
Description:
Author: Nathan James Adams
Author URI: http://nathanjamesadams.com
Version: 0.0.1a
*/
//Exit if accessed directly
if(!defined('ABSPATH')) {
exit;
}
//My custom post type, it works fine
require_once(plugin_dir_path(__FILE__).'n8jadams-step-funnel-cpt.php');
require_once(plugin_dir_path(__FILE__).'n8jadams-ajax.php');
//Add my javascript
function n8jadams_init_javascript() {
wp_register_script('n8jadams_javascript', plugin_dir_url(__FILE__).'n8jadams-scripts.js', array('jquery'),'1.1', false);
wp_enqueue_script('n8jadams_javascript');
}
add_action('wp_enqueue_scripts', 'n8jadams_init_javascript');
//Adds a plugin menu to the wordpress sidebar
function n8jadams_add_plugin_menu() {
add_menu_page('', 'Steps Settings', 4, 'steps-settings', 'n8jadams_steps_settings', '');
}
add_action('admin_menu', 'n8jadams_add_plugin_menu');
//The actual function for the menu page
function n8jadams_steps_settings() {
//Access the database and the tables we want
global $wpdb;
$posts = $wpdb->prefix.'posts';
//Get the user id
$user = wp_get_current_user();
$userid = $user->ID;
//Initialize javascript (it works here!)
n8jadams_init_javascript();
/* Get all the parents */
$parentsquery = "
SELECT `ID`, `post_title`
FROM $posts
WHERE `post_author` = $userid
AND `post_parent` = 0
AND `post_status` = 'publish'
AND `post_type` = 'step'
";
$parentsarray = $wpdb->get_results($parentsquery);
?>
<h4>My Forms:</h4>
<select id="parentselect">
<option id="-1"> - Select Your Step Form - </option>
<?php
//output the parents
for($i=0;$i<sizeof($parentsarray);$i++) {
echo '<option id="'.$parentsarray[$i]->ID.'">'.$parentsarray[$i]->post_title.'</option>';
}
?>
</select>
<div id="displayChildren"></div>
<?php
}
?>
Javascript(n8jadams-scripts.js):
(function($){
$('#parentselect').change(function(s) {
var thisID = s.target[s.target.selectedIndex].id;
var outputDisplay = document.getElementById('displayChildren');
if(thisID != '-1') {
$.ajax({
type: 'POST',
url: 'admin-ajax.php',
data: {
action: 'n8jadams_get_children',
id: thisID
},
success: function(response){
if(response == "") {
outputDisplay.textContent = "This form has no children. Add them in the sidebar menu of this step form.";
} else {
outputDisplay.innerHTML = response;
}
},
error: function(errorThrown) {
alert(errorThrown);
}
});
} else {
outputDisplay.textContent = '';
}
});
// I want this function to work
/*
$('#childselect').change(function(t) {
console.log("test");
});
*/
})(jQuery);
AJAX调用的PHP文件(n8jadams-ajax.php):
<?php
function n8jadams_get_children() {
//Get the id of the parent
$parent_post_id = $_POST['id'];
//Sanitize the input (Added after question was answered)
$parent_post_id = preg_replace("/[^0-9]/","",$parent_post_id);
//Access database
global $wpdb;
$posts = $wpdb->prefix.'posts';
$user = wp_get_current_user();
$userid = $user->ID;
$childrenquery = "
SELECT `ID`, `post_title`,`post_content`
FROM $posts
WHERE `post_parent` = $parent_post_id
AND `post_status` = 'publish'
AND `post_type` = 'step'
AND `post_author` = $userid
";
//Retrieve the children associated with this parent
$childrenarray = $wpdb->get_results($childrenquery);
//Initialize Javascript (it doesn't work here!)
n8jadams_init_javascript();
if(!empty($childrenarray)) { ?>
<h4>My Steps:</h4>
<select id="childselect">
<option id="-1"> - Select Your Step - </option>
<?php
//output the children of the parent
for($i=0;$i<sizeof($childrenarray);$i++) {
echo '<option id="'.$childrenarray[$i]->ID.'">'.$childrenarray[$i]->post_title.'</option>';
} ?>
</select>
<?php wp_die();
}
}
add_action('wp_ajax_n8jadams_get_children', 'n8jadams_get_children');
add_action('wp_ajax_nopriv_n8jadams_get_children', 'n8jadams_get_children');
?>
我无法弄清楚为什么我的javascript文件不能在AJAX调用的PHP文件中工作。也许StackOverflow的巨大智慧可以帮助我。我在这里先向您的帮助表示感谢。 :)
答案 0 :(得分:0)
你正在挂钩 wp_enqueue_scripts
,这只是为Wordpress的前端(普通访客看到的部分)运行的。如果要将脚本加载到WordPress的后端wp-admin中,请使用admin_enqueue_scripts
操作。
由于此代码在/ wp-admin /中不起作用,因此您无需使用admin_enqueue_scripts。我想整个问题是你将一个处理程序附加到$('#childselect')
,而当时页面上不存在这样的元素。使用延迟$(..).on(..)
:
$(document).on('change', '#childselect', function(e) {
//Black magic
});
附注:正如评论中已经提到的,以下部分包含一个未经过消毒的变量,允许攻击者执行sql注入。
$childrenquery = "
SELECT `ID`, `post_title`,`post_content`
FROM $posts
WHERE `post_parent` = $parent_post_id
AND `post_status` = 'publish'
AND `post_type` = 'step'
AND `post_author` = $userid
";
尽可能使用WP_Query。如果仅在Wordpress的后端使用此功能,请不要使用wp_ajax_nopriv_*
,因为未登录到您网站的用户无权使用该功能。