انتشار و بهروزرسانی Ajax نوشته و محصول
آموزش انتشار و بهروزرسانی Ajax نوشته و محصول در وردپرس بدون رفرش صفحه
در حالت عادی، زمانی که در پیشخوان وردپرس یک نوشته یا محصول جدید ایجاد میکنید و روی دکمه «انتشار» میزنید، صفحه دوباره بارگذاری میشود. این اتفاق شاید در نگاه اول ساده باشد، اما هنگام تولید محتوای زیاد، مدیریت محصولات ووکامرس یا ویرایشهای پشتسرهم، باعث کندشدن روند کار میشود.
در این آموزش میخواهیم دکمه انتشار در ویرایشگر کلاسیک وردپرس را به Ajax تبدیل کنیم. یعنی نوشته یا محصول بدون رفرش کامل صفحه منتشر یا بهروزرسانی شود. بعد از انتشار اول نیز دکمه «انتشار» به «بهروزرسانی» تبدیل خواهد شد و میتوانید تغییرات بعدی را هم بدون لود مجدد صفحه ذخیره کنید.
اگر در ابتدای مسیر طراحی سایت هستید، پیشنهاد میکنم ابتدا صفحه <a href=“https://miladalizadeh.ir/آموزش-رایگان-وردپرس/”>آموزش رایگان وردپرس</a> را مشاهده کنید تا با ساختار پیشخوان، نوشتهها، افزونهها و نحوه مدیریت محتوای وردپرس آشنا شوید.
این کد چه کاری انجام میدهد؟
کدی که در ادامه قرار میدهیم، چند قابلیت مهم را به ویرایشگر کلاسیک اضافه میکند:
- انتشار نوشته بدون رفرش صفحه
- بهروزرسانی نوشتههای منتشرشده با Ajax
- پشتیبانی از نوشتههای عادی وردپرس (
post) - پشتیبانی از محصولات ووکامرس (
product) - ذخیره عنوان، محتوای نوشته، خلاصه، دستهبندی و برچسبها
- ذخیره تصویر شاخص نوشته یا محصول
- نمایش پیام موفقیت پس از ذخیره
- تغییر آدرس مرورگر از صفحه افزودن نوشته به صفحه ویرایش همان نوشته، بدون رفرش
- جلوگیری از ایجاد نوشته جدید پس از رفرش صفحه
این قابلیت برای سایتهایی که تولید محتوا یا ثبت محصول زیادی دارند، تجربه کاربری پیشخوان را سریعتر و حرفهایتر میکند.
کد انتشار و ویرایش Ajax در وردپرس
بهترین روش، قرار دادن این کد در یک افزونه اختصاصی است تا با تغییر قالب سایت از بین نرود. برای مثال میتوانید یک افزونه ساده بسازید و کد زیر را داخل فایل اصلی آن قرار دهید:
add_action( 'wp_ajax_aep_save_post', 'aep_save_post_callback' );
function aep_save_post_callback() {
$post_id = isset( $_POST['post_id'] ) ? absint( $_POST['post_id'] ) : 0;
$form_data = isset( $_POST['form_data'] ) ? wp_unslash( $_POST['form_data'] ) : '';
$nonce = isset( $_POST['nonce'] ) ? sanitize_text_field( wp_unslash( $_POST['nonce'] ) ) : '';
if ( ! $post_id || empty( $form_data ) ) {
wp_send_json_error(
array(
'message' => 'اطلاعات نوشته کامل نیست.',
)
);
}
// اعتبارسنجی nonce وردپرس
$is_valid_nonce = wp_verify_nonce( $nonce, 'update-post_' . $post_id )
|| wp_verify_nonce( $nonce, 'add-post' );
if ( ! $is_valid_nonce ) {
wp_send_json_error(
array(
'message' => 'نشست شما منقضی شده است. لطفاً صفحه را یکبار رفرش کنید.',
),
403
);
}
$post = get_post( $post_id );
if ( ! $post ) {
wp_send_json_error(
array(
'message' => 'نوشته موردنظر پیدا نشد.',
),
404
);
}
if ( ! current_user_can( 'edit_post', $post_id ) ) {
wp_send_json_error(
array(
'message' => 'اجازه ویرایش این نوشته را ندارید.',
),
403
);
}
// تبدیل دادههای فرم به آرایه
parse_str( $form_data, $post_data );
// فقط برای نوشته و محصول
$allowed_post_types = array( 'post', 'product' );
if ( ! in_array( $post->post_type, $allowed_post_types, true ) ) {
wp_send_json_error(
array(
'message' => 'این نوع محتوا پشتیبانی نمیشود.',
)
);
}
/*
* قرار دادن دادههای واقعی فرم در $_POST
* بعضی افزونهها و متاباکسها هنگام ذخیره، اطلاعات را از $_POST میخوانند.
*/
$original_post_data = $_POST;
$_POST = wp_slash( $post_data );
// اطلاعات پایه نوشته
$update_data = array(
'ID' => $post_id,
'post_title' => isset( $post_data['post_title'] ) ? sanitize_text_field( $post_data['post_title'] ) : '',
'post_content' => isset( $post_data['content'] ) ? wp_kses_post( $post_data['content'] ) : '',
'post_excerpt' => isset( $post_data['excerpt'] ) ? wp_kses_post( $post_data['excerpt'] ) : '',
'post_status' => 'publish',
);
// برای محصول یا نوشته، نامک را نیز در صورت وجود ذخیره کن
if ( isset( $post_data['post_name'] ) ) {
$update_data['post_name'] = sanitize_title( $post_data['post_name'] );
}
// ذخیره دستهبندیها و برچسبها
if ( isset( $post_data['post_category'] ) ) {
$update_data['post_category'] = array_map( 'absint', (array) $post_data['post_category'] );
}
if ( isset( $post_data['tags_input'] ) ) {
$update_data['tags_input'] = sanitize_text_field( $post_data['tags_input'] );
}
// ذخیره نوشته
$result = wp_update_post( wp_slash( $update_data ), true );
// برگرداندن $_POST به حالت اصلی درخواست Ajax
$_POST = $original_post_data;
if ( is_wp_error( $result ) ) {
wp_send_json_error(
array(
'message' => $result->get_error_message(),
),
500
);
}
/*
* ذخیره تصویر شاخص
* در فرم کلاسیک، مقدار تصویر شاخص معمولاً در _thumbnail_id قرار دارد.
*/
if ( isset( $post_data['_thumbnail_id'] ) ) {
$thumbnail_id = absint( $post_data['_thumbnail_id'] );
if ( $thumbnail_id > 0 ) {
set_post_thumbnail( $post_id, $thumbnail_id );
} else {
delete_post_thumbnail( $post_id );
}
}
// اطلاعات تازهشده نوشته
$updated_post = get_post( $post_id );
wp_send_json_success(
array(
'message' => 'نوشته با موفقیت بهروزرسانی شد.',
'edit_link' => get_edit_post_link( $post_id, 'raw' ),
'view_link' => get_permalink( $post_id ),
'post_id' => $post_id,
'status' => $updated_post->post_status,
)
);
}
/**
* افزودن JavaScript در صفحه افزودن/ویرایش نوشته و محصول
*/
add_action( 'admin_enqueue_scripts', 'aep_enqueue_admin_script' );
function aep_enqueue_admin_script( $hook ) {
// فقط صفحه ویرایش یا افزودن نوشته
if ( ! in_array( $hook, array( 'post.php', 'post-new.php' ), true ) ) {
return;
}
$screen = get_current_screen();
if ( ! $screen || ! in_array( $screen->post_type, array( 'post', 'product' ), true ) ) {
return;
}
/*
* گوتنبرگ خودش بهصورت Ajax/REST کار میکند.
* این افزونه فقط برای Classic Editor طراحی شده است.
*/
if ( method_exists( $screen, 'is_block_editor' ) && $screen->is_block_editor() ) {
return;
}
wp_enqueue_script( 'jquery' );
$script = <<<'JS'
jQuery(function ($) {
/*
* تشخیص اینکه نوشته پیشتر منتشر شده یا نه
* اگر منتشر شده باشد، متن دکمه «بهروزرسانی» خواهد بود.
*/
function setButtonToUpdate($button) {
$button
.val('بهروزرسانی')
.prop('disabled', false)
.removeData('ajax-saving')
.css({
background: '',
borderColor: ''
});
}
/*
* گرفتن اطلاعات فرم و ارسال Ajax
*/
$(document).on('click', '#publish', function (e) {
e.preventDefault();
var $button = $(this);
var $form = $('#post');
var postId = $('#post_ID').val();
var nonce = $('[name="_wpnonce"]').val();
if (!postId) {
alert('شناسه نوشته پیدا نشد. لطفاً صفحه را یکبار رفرش کنید.');
return;
}
// جلوگیری از کلیک پشتسرهم
if ($button.data('ajax-saving')) {
return;
}
// انتقال محتوای TinyMCE به textarea اصلی وردپرس
if (typeof tinyMCE !== 'undefined') {
tinyMCE.triggerSave();
}
var isUpdate = $button.val().indexOf('بهروزرسانی') !== -1;
var loadingText = isUpdate ? 'در حال بهروزرسانی...' : 'در حال انتشار...';
var successText = isUpdate ? 'بهروزرسانی شد ✓' : 'منتشر شد ✓';
$button
.data('ajax-saving', true)
.val(loadingText)
.prop('disabled', true);
$.ajax({
url: ajaxurl,
type: 'POST',
data: {
action: 'aep_save_post',
post_id: postId,
nonce: nonce,
form_data: $form.serialize()
},
success: function (response) {
if (!response.success) {
var errorMessage = response.data && response.data.message
? response.data.message
: 'خطایی هنگام ذخیرهسازی رخ داد.';
alert(errorMessage);
setButtonToUpdate($button);
return;
}
// نمایش پیام سبز وردپرس
$('#message').remove();
$('#wpbody-content').prepend(
'<div id="message" class="notice notice-success is-dismissible">' +
'<p><strong>✓ ' + response.data.message + '</strong> ' +
'<a href="' + response.data.view_link + '" target="_blank">مشاهده نوشته</a>' +
'</p></div>'
);
// تغییر وضعیت بخش انتشار
$('#post-status-display').text('منتشرشده');
$('#visibility-display').text('عمومی');
/*
* بسیار مهم:
* تغییر آدرس مرورگر از post-new.php به صفحه ویرایش نوشته،
* بدون رفرش صفحه. بنابراین با F5 همان نوشته باز میشود.
*/
if (response.data.edit_link && window.history && window.history.replaceState) {
window.history.replaceState(
{ postId: response.data.post_id },
document.title,
response.data.edit_link
);
}
// فرم نیز روی همان نوشته تنظیم میشود
if (response.data.edit_link) {
$form.attr('action', response.data.edit_link);
}
// nonce صفحه برای دفعات بعد بهروزرسانی شود
// در اغلب سایتها nonce قبلی هم معتبر است، اما این مورد کمککننده است.
$button
.val(successText)
.css({
background: '#00a32a',
borderColor: '#00a32a'
});
// پس از کمی مکث، دکمه به «بهروزرسانی» تبدیل شود
setTimeout(function () {
setButtonToUpdate($button);
}, 1200);
},
error: function () {
alert('ارتباط با سرور برقرار نشد. لطفاً دوباره تلاش کنید.');
setButtonToUpdate($button);
}
});
});
});
JS;
wp_add_inline_script( 'jquery', $script );
}
راهنمای گامبهگام: چگونه این کد را به سایت وردپرسی خود اضافه کنیم؟
برای اضافه کردن این کد به وردپرس، چندین روش وجود دارد. در ادامه ایمنترین و استانداردترین روشها را با هم بررسی میکنیم:
روش اول: ویرایش از طریق مدیریت فایل هاست (روش حرفهای)
گاهی اوقات ممکن است دسترسی به ویرایشگر وردپرس (Theme File Editor) به دلایل امنیتی توسط توسعهدهنده قالب بسته شده باشد، یا شاید ترجیح میدهید به جای محیط وردپرس، مستقیماً با فایلهای سرور کار کنید. در این صورت، استفاده از File Manager هاست بهترین راهکار است.
گامهای اجرای کار در هاست (cPanel یا DirectAdmin):
- ورود به هاست: ابتدا وارد پنل مدیریت هاست خود (cPanel یا DirectAdmin) شوید.
- باز کردن فایل منیجر: روی گزینه File Manager کلیک کنید.
- مسیریابی: به پوشه ریشه سایت خود (معمولاً
public_html) بروید. سپس مسیر زیر را دنبال کنید:wp-content>themes>your-theme-name(نکته: بهجایyour-theme-nameنام پوسته فعال سایت خود را انتخاب کنید. اگر از Child Theme استفاده میکنید، حتماً وارد پوشه فرزند شوید). - ویرایش فایل: فایل
functions.phpرا پیدا کنید. روی آن راستکلیک کرده و گزینه Edit را انتخاب کنید. - جایگذاری کد: کد مورد نظر خود را به انتهای فایل اضافه کنید.
- ذخیره: دکمه Save Changes را در بالای صفحه ویرایشگر بزنید.
روش دوم : اضافه کردن کد به فایل functions.php (روش سریع)
فایل functions.php قلب تپنده قالب شماست و کدهای شخصیسازی در آن قرار میگیرند.
- وارد پیشخوان وردپرس شوید: از منوی سمت راست به مسیر نمایش > ویرایشگر پرونده پوسته (Theme File Editor) بروید.
- فایل مناسب را انتخاب کنید: از ستون سمت چپ (بخش پروندههای پوسته)، فایل توابع پوسته (functions.php) را پیدا کرده و روی آن کلیک کنید.
- قرار دادن کد: به انتهای فایل بروید، یک خط جدید ایجاد کنید و کدهای بالا را دقیقاً در انتهای فایل پیست (Paste) کنید.
- ذخیره تغییرات: روی دکمه بهروزرسانی پرونده کلیک کنید.
⚠️ یک هشدار امنیتی بسیار مهم:
پیش از ویرایش فایلهای قالب، حتماً یک نسخه پشتیبان (Backup) از فایل تهیه کنید. همچنین اگر قالب خود را آپدیت کنید، تغییراتی که در فایل
functions.phpقالب اصلی اعمال کردهاید پاک خواهند شد. برای جلوگیری از این مشکل، پیشنهاد میکنیم از پوسته فرزند (Child Theme) استفاده کنید یا به سراغ روش دوم بروید.
روش سوم: استفاده از افزونههای مدیریت کدهای سفارشی (روش ایمن و بدون خطر)
اگر نمیخواهید فایلهای قالب را به صورت دستی ویرایش کنید و نگران به هم ریختن سایت یا پاک شدن کدها در آپدیتهای بعدی قالب هستید، این روش بهترین گزینه است.
- افزونه رایگان WPcode (Insert Headers and Footers) یا Code Snippets را از مخزن وردپرس نصب و فعال کنید.
- از منوی جدیدی که در پیشخوان اضافه شده، روی Add Snippet (افزودن کد جدید) کلیک کنید.
- یک عنوان دلخواه برای آن انتخاب کنید (مثلاً: نوار اعلان بالای هدر).
- نوع کد (Code Type) را روی حالت PHP Snippet قرار دهید.
- کدهای بالا را در باکس مربوطه کپی کنید.
- وضعیت را روی Active (فعال) قرار داده و دکمه Save را بزنید.
درباره میلاد علیزاده وکیلی
میلاد علیزاده هستم مدرس دوره های آموزش برنامه نویسی در شهر تبریز که فعالیت خودم رو از سال 95 در زمینه ی طراحی و میزبانی وبسایت شروع کردم. هدف من از راه اندازی این وبسایت ارائه ی آموزشی متفاوت همچنین اشتغال محور و پروژه محور هستش که هنرجو بعد از آموزش بتواند با دانش و تجربه ای کافی مستقیما وارد بازار کار شده و در زمینه ی برنامه نویسی کسب درامد کند.
نوشتههای بیشتر از میلاد علیزاده وکیلی

دیدگاهتان را بنویسید