AJAX комментарии в WordPress

Итак, комментарии на AJAX. Перед написанием этого поста я потратил добрую половину дня на их разработку — хорошо, что я уже был с ними знаком. В самый первый раз, когда я ещё начинал изучать jQuery, на создание асинхронных комментариев с нуля у меня ушли первые две недели января.

Кстати, я долго думал, имеет ли смысл поставить комментарии со стороннего сервиса, например disqus — но в итоге решил что свои комментарии на AJAX будут покруче.

Требования к AJAX-комментам

Допустим, мы только что решили поставить асинхронные комментарии у себя на сайте. Какую функциональность, на наш взгляд, они должны иметь?

  • самое главное — возможность работы со стандартными древовидными комментариями comment-reply.js,
  • вывод ошибок, в том числе вордпрессовских, особо с этим заморачиваться не буду, сделаю через alert() пока что,
  • проверка комментария на наличие запрещенных HTML-тегов. Читайте о том, как изменить список разрешенных тегов,
  • модерация комментария при необходимости,
  • запоминание в кукисах значений полей «Имя» и «Email»,
  • исключить возможность двойного нажатия на кнопку «Отправить»,
  • не используем никакие плагины WordPress;

Шаг 1. Подготовка. Структура HTML.

Будем отталкиваться от стандартных тем WordPress, это Twenty Ten и Twenty Eleven. Разумеется, то, что представлено в следующем куске кода — всего лишь HTML-шаблон, который должен сориентировать вас по атрибутам class и id, а также по расположению элементов, а вообще все эти штуки делаются через php!

<!-- можно <ul> или <ol> -->
<ol class="commentlist">
	<!-- класс depth-1 показывает уровень вложенности -->
	<li class="comment depth-1" id="li-comment-4">
		<div id="comment-4">
			<!-- тут содержимое комментария -->
			<div class="reply">
				<a class="comment-reply-link">Ответить</a>
			</div>
		</div>
		<!-- дальше идут ответы к предыдущему комментарию  -->
		<ul class="children">
			<!-- depth-2 - значит вложенность второго уровня -->
			<li class="comment depth-2" id="li-comment-5">
				<div id="comment-5">
					<!-- тут содержимое комментария -->
					<div class="reply">
						<a class="comment-reply-link">Ответить</a>
					</div>
				</div>
			</li>
		</ul>
	</li>
</ol>
<div id="respond">
	<!-- тут нужно обратить внимание также на атрибуты name -->
	<a id="cancel-comment-reply-link" style="display:none;">Отменить ответ</a>
	<form id="commentform">
		<input name="author" id="author" type="text" />
		<input name="email" id="email" type="text" /><!-- или type="email", как хотите -->
		<input name="url" id="url" type="text" />
		<textarea name="comment" id="comment"></textarea>
		<input name="submit" type="submit" id="submit" value="Отправить" />
		<!-- если у вас нет hidden-полей попробуйте вставить их через php-функцию comment_id_fields() -->
		<input type="hidden" name="comment_post_ID" />
		<input type="hidden" name="comment_parent" />
	</form>
</div>

Так что, если у вас что-то добавляется не туда, куда надо, сверяйтесь по этому листингу.

Примерно так это будет выглядеть:

список комментариев с указанием CSS-классов элементов

В код моего блога советую не залазить, у меня там структура немного другая, она может вас только запутать ещё больше. Если что-то не получается или есть вопрос — просто задайте его мне прямо в комментариях к этому посту.

Шаг 2. CSS

Если у вас со структурой всё окей, то стили по сути и не понадобятся, за исключением оформления ошибок, возникающих в результате валидации полей. То есть, если кто-то ввёл неверный адрес email, поле должно стать красного цвета (например).

input.error, textarea.error{
	background: #fe0000; /* или background:red или любой другой цвет, который больше вписывается в дизайн вашего блога */
}

Добавляем этот код в основной файл стилей вашей темы, обычно это — style.css.

Шаг 3. Подключение скриптов

Во-первых, давайте в папке с темой создадим какой-нибудь файл JavaScript, в который мы потом добавим весь наш код. У меня это будет файл comments.js.

Теперь наша задача — правильно подключить библиотеку jQuery и файл comments.js. Для этого воспользуемся функцией wp_enqueue_script().

Следующий код вставляем в файл functions.php вашей текущей темы:

function true_include_my_comment_script() {
	wp_enqueue_script( 'jquery' );
 	wp_enqueue_script( 'commentjs', get_stylesheet_directory_uri() . '/comments.js', array('jquery'), null );
}
 
add_action( 'wp_enqueue_scripts', 'true_include_my_comment_script' );

Зайдите в исходный код страницы (в Windows — Ctrl + U) и посмотрите, появился ли там comments.js, если да — переходим к следующему шагу, если нет — открываем файлы header.php и footer.php и убеждаемся, что там присутствуют функции wp_head() и wp_footer() соответственно.

Шаг 4. Скрипты jQuery

Открываем наш файл comments.js и вписываем туда:

jQuery.extend(jQuery.fn, {
	/*
	 * функция проверки, что длина поля не меньше 3х символов 
	 */
	checka: function () {
		if (jQuery(this).val().length < 3) {jQuery(this).addClass('error');return false} else {jQuery(this).removeClass('error');return true}
	},
	/*
	 * функция проверки правильности введенного email
	 */
	checke: function () {
		var emailReg = /^([\w-\.]+@([\w-]+\.)+[\w-]{2,4})?$/;
		var emailaddressVal = jQuery(this).val();
		if (!emailReg.test(emailaddressVal) || emailaddressVal == "") {
			jQuery(this).addClass('error');return false
		} else {
			jQuery(this).removeClass('error');return true
		}
	},
});
 
jQuery(function($){
	$('#commentform').submit(function(){
		// может такое случиться, что пользователь залогинен - нужно это проверить, иначе валидация не пройдет
		if($("#author").length) var author = $("#author").checka();
		if($("#email").length) var email = $("#email").checke();
		var comment = $("#comment").checka();
		// небольшое условие для того, чтобы исключить двойные нажатия на кнопку отправки
		// в это условие также входит валидация полей
		if (!$('#submit').hasClass('loadingform') && !$("#author").hasClass('error') && !$("#email").hasClass('error') && !$("#comment").hasClass('error')){
			$.ajax({
				type : 'POST',
				url : 'http://' + location.host + '/wp-admin/admin-ajax.php',
				data: $(this).serialize() + '&action=ajaxcomments',
				beforeSend: function(xhr){
					// действие при отправке формы, сразу после нажатия на кнопку #submit 
					$('#submit').addClass('loadingform').val('Загрузка');
				},
				error: function (request, status, error) {
					if(status==500){
						alert('Ошибка при добавлении комментария');
					} else if(status=='timeout'){
						alert('Ошибка: Сервер не отвечает, попробуй ещё.');
					} else {
						// ворпдрессовские ошибочки, не уверен, что это самый оптимальный вариант
						// если знаете способ получше - поделитесь
						var errormsg = request.responseText;
						var string1 = errormsg.split("<p>");
						var string2 = string1[1].split("</p>");
						alert(string2[0]);
					}
				},
				success: function (newComment) {
					// Если уже есть какие-то комментарии
					if($('.commentlist').length > 0){
						// Если текущий комментарий является ответом
						if($('#respond').parent().hasClass('comment')){
							// Если уже есть какие-то ответы
							if($('#respond').parent().children('.children').length){	
								$('#respond').parent().children('.children').append(newComment);
							} else {
								// Если нет, то добавляем  <ul class="children">
								newComment = '<ul class="children">'+newComment+'</ul>';
								$('#respond').parent().append(newComment);
							}
							// закрываем форму ответа
							$("#cancel-comment-reply-link").trigger("click");
						} else {
							// обычный коммент
							$('.commentlist').append(newComment);
						}
					}else{
						// если комментов пока ещё нет, тогда
						newComment = '<ul class="commentlist">'+newComment+'</ol>';
						$('#respond').before($(newComment));
					}
					// очищаем поле textarea
					$('#comment').val('');
				},
				complete: function(){
					// действие, после того, как комментарий был добавлен
					$('#submit').removeClass('loadingform').val('Отправить');
				}
			});
		}
		return false;
	});
});

Последний шаг. PHP-обработчик

Читайте подробнее о том, как обрабатываются асинхронные запросы в WordPress. Код обработчика:

<?php
// если вы вставляете код не в новый файл, то <?php нужно удалить
function true_add_ajax_comment(){
	global $wpdb;
	$comment_post_ID = isset($_POST['comment_post_ID']) ? (int) $_POST['comment_post_ID'] : 0;
 
	$post = get_post($comment_post_ID);
 
	if ( empty($post->comment_status) ) {
		do_action('comment_id_not_found', $comment_post_ID);
		exit;
	}
 
	$status = get_post_status($post);
 
	$status_obj = get_post_status_object($status);
 
	/*
	 * различные проверки комментария
	 */
	if ( !comments_open($comment_post_ID) ) {
		do_action('comment_closed', $comment_post_ID);
		wp_die( __('Sorry, comments are closed for this item.') );
	} elseif ( 'trash' == $status ) {
		do_action('comment_on_trash', $comment_post_ID);
		exit;
	} elseif ( !$status_obj->public && !$status_obj->private ) {
		do_action('comment_on_draft', $comment_post_ID);
		exit;
	} elseif ( post_password_required($comment_post_ID) ) {
		do_action('comment_on_password_protected', $comment_post_ID);
		exit;
	} else {
		do_action('pre_comment_on_post', $comment_post_ID);
	}
 
	$comment_author       = ( isset($_POST['author']) )  ? trim(strip_tags($_POST['author'])) : null;
	$comment_author_email = ( isset($_POST['email']) )   ? trim($_POST['email']) : null;
	$comment_author_url   = ( isset($_POST['url']) )     ? trim($_POST['url']) : null;
	$comment_content      = ( isset($_POST['comment']) ) ? trim($_POST['comment']) : null;
 
	/* 
	 * проверяем, залогинен ли пользователь
	 */
	$user = wp_get_current_user();
	if ( $user->exists() ) {
		if ( empty( $user->display_name ) )
			$user->display_name=$user->user_login;
		$comment_author       = $wpdb->escape($user->display_name);
		$comment_author_email = $wpdb->escape($user->user_email);
		$comment_author_url   = $wpdb->escape($user->user_url);
		$user_ID = get_current_user_id();
		if ( current_user_can('unfiltered_html') ) {
			if ( wp_create_nonce('unfiltered-html-comment_' . $comment_post_ID) != $_POST['_wp_unfiltered_html_comment'] ) {
				kses_remove_filters(); // start with a clean slate
				kses_init_filters(); // set up the filters
			}
		}
	} else {
		if ( get_option('comment_registration') || 'private' == $status )
			wp_die( 'Вы должны зарегистрироваться или войти, чтобы оставлять комментарии.' );
	}
 
	$comment_type = '';
 
	/* 
	 * проверяем, заполнил ли пользователь все необходимые поля
 	 */
	if ( get_option('require_name_email') && !$user->exists() ) {
		if ( 6 > strlen($comment_author_email) || '' == $comment_author )
			wp_die( 'Ошибка: заполните необходимые поля (Имя, Email).' );
		elseif ( !is_email($comment_author_email))
			wp_die( 'Ошибка: введенный вами email некорректный.' );
	}
 
	if ( '' == trim($comment_content) ||  '<p><br></p>' == $comment_content )
		wp_die( 'Вы забыли про комментарий.' );
 
	/* 
	 * добавляем новый коммент и сразу же обращаемся к нему
	 */
	$comment_parent = isset($_POST['comment_parent']) ? absint($_POST['comment_parent']) : 0;
	$commentdata = compact('comment_post_ID', 'comment_author', 'comment_author_email', 'comment_author_url', 'comment_content', 'comment_type', 'comment_parent', 'user_ID');
	$comment_id = wp_new_comment( $commentdata );
	$comment = get_comment($comment_id);
 
	/*
	 * выставляем кукисы
	 */
	do_action('set_comment_cookies', $comment, $user);
 
	/*
	 * вложенность комментариев
	 */
	$comment_depth = 1;
	while($comment_parent){
		$comment_depth++;
		$parent_comment = get_comment($comment_parent);
		$comment_parent = $parent_comment->comment_parent;
	}
 
	$GLOBALS['comment'] = $comment;
	$GLOBALS['comment_depth'] = $comment_depth;
	/*
	 * ниже идет шаблон нового комментария, вы можете настроить его для себя,
	 * а можете воспользоваться функцией(которая скорее всего уже есть в теме) для его вывода
	 */
	?>
	<li <?php comment_class(); ?> id="li-comment-<?php comment_ID(); ?>">
		<div id="comment-<?php comment_ID(); ?>">
			<div class="comment-author vcard">
				<?php echo get_avatar( $comment, 40 ); ?>
				<cite class="fn"><?php echo get_comment_author_link(); ?></cite>
			</div>
			<?php if ( $comment->comment_approved == '0' ) : ?>
				<em class="comment-awaiting-moderation">Комментарий отправлен на проверку</em>
				<br />
			<?php endif; ?>
			<div class="comment-meta commentmetadata"><a href="<?php echo esc_url( get_comment_link( $comment->comment_ID ) ); ?>">
				<?php printf('%1$s в %2$s', get_comment_date(),  get_comment_time() ); ?></a><?php edit_comment_link('ред.', ' ' );	?>
			</div>
			<div class="comment-body"><?php comment_text(); ?></div>
		</div>
	</li>
	<?php
	die();
}
 
add_action('wp_ajax_ajaxcomments', 'true_add_ajax_comment'); // wp_ajax_{значение параметра action}
add_action('wp_ajax_nopriv_ajaxcomments', 'true_add_ajax_comment'); // wp_ajax_nopriv_{значение параметра action}

Комменты можете протестировать прямо на моем блоге, там совсем незначительные изменения в коде, также я протестировал весь код из статьи ничего не меняя, как есть, на теме Twenty Ten.

Со временем пост будет обновляться по мере совершенствования кода в нем, после появления каких-либо доработок.

Также есть доработки, которые я не буду добавлять, дабы не усложнять пост, но вам стоит попробовать сделать их самим:

  • При добавлении нового комментария неплохо также обновлять цифру с количеством комментариев, которую обычно можно найти рядом с датой публикацией поста и в заголовке непосредственно перед самими комментами,
  • Вы можете оформить ошибки в виде красивых всплывающих окон или в виде подсказок,
  • Очень здорово, если при нажатии на кнопку отправки, на ней будет появляться анимация-прелоадер, как у меня на блоге.
Подпишитесь, чтобы раз в неделю получать свежие статьи с блога по email.

Смотрите также

Комментарии 217

  • Ольга29 октября 2012 в 14:10 #

    ДОЖДАЛАСЬ!!!! Сегодня же буду пробовать встроить это в свой сайт. О результатах отпишусь ниже. А это, так сказать, тестовый коммент, ну и конечно с благодарностью!

  • Александр29 октября 2012 в 16:10 #

    Интересная статья... Надо будет попробовать это "внедрить" на свой блог. Спасибо за советы!

  • Dan15 ноября 2012 в 12:11 #

    Протестируем, спасибо!

  • Алекс19 ноября 2012 в 23:11 #

    Вау! Круто!

  • Алекс19 ноября 2012 в 23:11 #

    100 комментов можно?

  • Макс24 декабря 2012 в 13:12 #

    Прикольно!

  • velina26 декабря 2012 в 08:12 #

    Попробуем

  • Сергий4 января 2013 в 17:01 #

    Всю голову сломал уже с этим. Плагин WP Ajax Edit Comments так и не получилось заставить работать! Попробую с этим. Спасибо за твой труд! =)

  • Радик5 января 2013 в 05:01 #

    круто

  • test9 января 2013 в 10:01 #

    спасибо за код.
    в целях оптимизации js кода советую кэшировать получаемые jquery элементы.

    • test9 января 2013 в 10:01 #

      и с прошедшим :)(

      • Lector7 июня 2013 в 13:06 #

        Довольно-таки интересный подход! Надо будет попробовать!) У меня может не по теме вопрос, вот стандартные комменты, когда добавляю коммент, у меня почему-то не перенаправляет на этот самый коммент, то есть нет в конце строки "/#comments-34", а просто редиректит на новость. Не подскажите как сделать чтоб на последний добавленный коммент редиректило? Спасибо

        • Миша9 июня 2013 в 08:06 #

          а что стоит в параметре action формы?

          <form action="?">

          а вообще советую глянуть например стандартную тему Twenty Ten и сравнить со своей темой, посмотреть, что именно не так

  • Dmitry17 января 2013 в 23:01 #

    Давно хотел разобраться что есть ajax а этот код прекрасная возможность ознакомится с технологией на практике. Спасибо!

  • Евгений10 февраля 2013 в 03:02 #

    Хаос) новичку ничерта не понять...

    • Миша10 февраля 2013 в 07:02 #

      а я старался поподробнее описывать)

      • Виталий Охрименко23 сентября 2015 в 07:09 #

        Вот сейчас пытаюсь установить, однако нифига не понятно с последним шагом: Последний шаг. PHP-обработчик

        В коде комментарий: "// если вы вставляете код не в новый файл, то <?php нужно удалить" о каком файле речь? Куда вообще это вставлять.
        Я вроде не новичек, уже хоть как-то в кодах разбираюсь, но куда эту штуку девать пока не понятно. Советую на последнем и первом шаге чуток подробней остановится. Первый я так понимаю чисто наглядный, для сравнения со своей темой? или опять неправильно понял?

  • Мерген17 февраля 2013 в 13:02 #

    Как в вордпресс создать еще одну форму комментариев во вкладке рядом с основной, 2 дня потратил на это и не смог сделать, подскажите пожалуйста

    • Миша17 февраля 2013 в 18:02 #

      а чем будут отличаться эти формы комментариев?

      • Мерген17 февраля 2013 в 19:02 #

        1ая форма обычная,а вторая для анонимного комментирования. Подсунул их в две вкладки. Сделал, но один баг существует, если отвечаешь на чей то коммент анонимным, то комментарий публикуется как новый

      • Миша18 февраля 2013 в 22:02 #

        в общем вот мой скайп misha_10000, разберемся на месте.

      • Мерген19 февраля 2013 в 18:02 #

        что то тебя в скайпе нету

  • Евгений18 февраля 2013 в 22:02 #

    отписался от комментариев, уведомления все-равно приходят) глюк? или....?

    • Миша19 февраля 2013 в 05:02 #

      странно, я вот тут смотрю, ещё один тоже отписался - всё норм, а у тебя активная подписка отображается) попробуй ещё раз)

  • Владимир18 февраля 2013 в 23:02 #

    Подскажи пожалуйста что за плагин который после отправки комментария сразу показывает его в дереве комментов. в ссылке я указал сайт, где довел до середины этой отправки. Не могу только отобразить его без перезагрузки

  • Евгений19 февраля 2013 в 18:02 #

    http://prntscr.com/tchox вот скрин) я это делаю каждый раз когда приходит уведомление о новом комменте)

  • ollejah24 февраля 2013 в 15:02 #
    // ворпдрессовские ошибочки
    var errormsg = $(request.responseText).filter('p').text();
    console.log(errormsg);
  • Otshelnik-fm11 марта 2013 в 21:03 #

    Вопрос по существу - комментарии не будут разбиваться на страницы? У меня стоит в настройках блога разбитие комментариев на страницы

  • Otshelnik-fm11 марта 2013 в 21:03 #

    В добавок к вопросу.
    Этот вариант комментариев встроенный на ваш сайт видоизменялся с октября? я имею ввиду не по стилям, а по соответствию той части что в примере?

  • Мурад23 марта 2013 в 22:03 #

    Привет! Возникла проблема, следующего характера, если авторизован то всё работает, а вот если я не авторизован выдается ошибка
    Fatal error: Call to a member function exists() on a non-object in Z:\home\love-trip\www\wp-includes\comment.php on line 615

    • Александр16 апреля 2013 в 08:04 #

      Круть. Заделай видео, или по подробней опиши, что и куда втыкать, чтобы работало.. Я сам разобраться долго буду. Если сделаешь, напиши в личку,- договоримся.

  • Otshelnik-fm28 марта 2013 в 09:03 #

    Беда этих древовидных комментариев в том что не найдешь последние сообщения если комментариев много. У себя отказался от них. Использую линейный стиль, и активно использую цитирование. На хабре тоже с этим беда. Считаю что маразм эти древовидные. Да и не зря на всех форумах используют линейные комментарии

  • Виктор10 апреля 2013 в 17:04 #

    Как прикрутить редактор WysiBB. офф сайт http://www.wysibb.com/?

    • Миша10 апреля 2013 в 20:04 #

      ну там на офф сайте описано же,
      1. подключить скрипт редактора
      2. подключить CSS стили редактора
      3. задействовать его для какой-либо textarea

  • Максим15 апреля 2013 в 22:04 #

    Привет, Александр!

  • Александр15 апреля 2013 в 22:04 #

    Слушай, а ты знаешь, как весь этот процесс прикрутить к шаблону вордпресс?

  • Максим16 апреля 2013 в 08:04 #

    Здравствуйте Михаил наткнулся на ваш блог в нете очень интересно познавательно у меня к вам вопрос не могли бы вы более подробно описать прикручивание скрипта коментов AJAX для WordPress? А то местами понятно местами нет например не понятно куда встовлять код для
    Подготовка. Структура HTML.
    понятно что это листинг для удобства сверки и у вас написано что это пример стандартных тем ну я что то не пойму толе я не там смотрю толе версия wordpress не совпадает у меня 3.5 в результате чего я так понимаю выскакивает ошибка как писал человек выше
    Fatal error: Call to a member function exists() on a non-object in Z:\home\wordp.ru\www\wp-includes\comment.php on line 615 это после того когда пытаешься не залогеный комент отправить и почему то вроде написал в поле текст а он запрашивает "вы забыли про комментарий"
    правда со второго раза отправляет очень хотелось бы получить ответы на эти вопросы заранее спасибо

    • Миша16 апреля 2013 в 19:04 #

      Добрый день)
      в первом шаге прост дан пример чтобы не косячились результаты из ajax, то есть это - просто пример расположения элементов относительно друг друга и их идентификаторы\классы.
      с версией WordPress проблем быть не должно

      когда пытаешься не залогеный комент отправить и почему то вроде написал в поле текст а он запрашивает “вы забыли про комментарий”

      это значит что следует перепровить HTML атрибуты name у текстового поля, если все ок, то отследить его дальше по скриптам и в php

      Скажу честно, пост написан полгода назад и не обновлялся - есть более безопасные методы использования ajax-обработчика. Но тем не менее тут всё рабочее, у меня на сайте оно используется)

      почему со второго раза только отправляется - хз вообще если честно

      в общем постараюсь ответить на любые конкретные вопросы в комментах.

      • Максим17 апреля 2013 в 08:04 #

        Спасибо вам Михаил за ответ. Тогда подскажите пожалуйста вот этот листинг HTML с каким файлом PHP сверять надо? С файлом в шаблоне "contact.php" или в папке wp-includes файл comment-template.php?
        А то я то как делал сначала подключил через шаблон файле functions.php
        jQuery и за ним указал путь к JS файлу, Файл ajax_comment.php закинул в корень сайта все вроде заработало но как то корявенько я думаю что потому что я не совсем понял с каким PHP файлом сверять классы и ID
        Заранее спасибо за ответ ?

        • Миша18 апреля 2013 в 06:04 #

          листинг HTML с каким файлом PHP сверять надо?

          ну для начала можно сверить со страницей на которой находится форма через Ctrl + U
          а там уже, если в форме косяки, то - для комментариев обычно comments.php. В файлы движка не лезем! все делаем через тему.

          Файл ajax_comment.php закинул в корень сайта все вроде заработало но как то корявенько я думаю что потому что я не совсем понял с каким PHP файлом сверять

          да, всё верно
          но реально самое трудное позади, главное что асинхронный запрос отсылается

          • Виталий Охрименко23 сентября 2015 в 07:09 #

            Что-то частично получилось (частично ключевое слово)
            Пока имею только то, что к адресу подтянулось окончание: #comment-3184
            Форма комментариев не подтягивается к кнопке ответить в случае ее нажатия, а страница полностью вообще не загружается, уже 10 минут в браузере крутится загрузка страницы после добавления нового комментария...буду дальше пробовать

            • Миша23 сентября 2015 в 19:09 #

              С PHP-обработчиком можете пока что не колдовать, ваша первая цель, чтобы отсылался запрос - если он успешно отошлется без обработчика, то вам будет возвращен "0".

              У вас именно проблема с HTML / JS сейчас.

      • Александр17 апреля 2013 в 11:04 #

        Миша, мои знания по ajax и jquery на низком уровне, поэтому мне не совсем ясно, в какие именно файлы втыкать данные скрипты своего шаблона. Я могу только предполагать.

        Есть шаблон с файлами
        http://www.fotolink.su/v.php?id=45bff0f0867e15b9d68dc52e494fc1fa

        Куда ставить

        HTML структуру
        CSS
        Счетчик Комментариев
        Скрипты
        PHP обработчик ??

        Признателен тебе за ответ.

        • Миша18 апреля 2013 в 06:04 #

          HTML структуру

          вероятнее всего comments.php

          CSS

          style.css

          Счетчик Комментариев

          пока что не трогаем

          Скрипты

          тут уже нужно смотреть самому, в принципе создай и подключи новый файл

          PHP обработчик

          это отдельный файл в корне сайта, его тоже нужно создать самому

          • Александр18 апреля 2013 в 10:04 #

            Спасибо, Миша.

            Буду разбираться.

            • Виталий Охрименко23 сентября 2015 в 07:09 #

              Вот непонятно...php разработчик как я понимаю это последний шаг. Ну создаю я файл в корне сайта и что? Куда и к чему его нужно подключать чтобы к комментариям пристал? Как его именовать? Что нужно сравнивать с чем из первого шага. Миш, очень бы хотелось чтобы статья была расчитана не на опытных программистов, а на средней руки блогеров

  • Againagain5 августа 2013 в 20:08 #

    большое спасибо. опробуем

  • Евгеша22 августа 2013 в 17:08 #

    Тестовый =)

  • Роман24 августа 2013 в 22:08 #

    А мне в блог можете такой аякс коммент сделать?

    • Миша30 августа 2013 в 11:08 #

      да, могу конечно, свяжитесь со мной по email или по скайпу
      P.S. сорри за долгий ответ, был в отъезде

  • Ольга27 августа 2013 в 15:08 #

    тест аякса )

  • Денис29 сентября 2013 в 02:09 #

    Что насчет supercache ? отключил в браузере яваскрипт, ваша форма комментов загрузилась, значит закеширует сие дело супер каче так? как сделать чтобы не закешировал и чтобы была премодерация

    • Миша29 сентября 2013 в 20:09 #

      отключил в браузере яваскрипт, ваша форма комментов загрузилась

      при чем тут кэш?)

  • Денис29 сентября 2013 в 20:09 #

    да, я тупанул чот совсем, эта форма на аяксе защищает от спам ботов?

  • Денис1 октября 2013 в 09:10 #

    Миша!, форма защищает от спама через спамилки или нет?

    • Миша3 октября 2013 в 08:10 #

      сорри за долгий ответ
      если отключить стандартную форму, то защищает

      • Денис3 октября 2013 в 08:10 #

        Спасибо,

        если отключить стандартную форму

        Всмысле отключить? тоесть просто использовать ваш метод?

        Может быть знаете еще способ как сделать так чтобы сделать проверку на ссылку, если ссылка вставлена в коммент, то его попросту нельзя было бы отправить?

        • Миша4 октября 2013 в 10:10 #

          Может быть знаете еще способ как сделать так чтобы сделать проверку на ссылку, если ссылка вставлена в коммент, то его попросту нельзя было бы отправить?

          в настройках админки

  • Денис4 октября 2013 в 10:10 #

    Я имел ввиду что его физически нельзя будет отправить, не будет работать кнопка опубликовать, или не будет работать параметр post или что там как называется не знаю.

  • Денис4 октября 2013 в 10:10 #

    Чот судя по ответам вам не интересно отвечать как я понял, если так, скажите прямо, я просто перестану спрашивать

    • Otshelnik-fm4 октября 2013 в 18:10 #

      Всё можно сделать. Но вы же хотите халявы? Сделайте то, сделайте это... А благодарности нет. Зато обида в вашем сообщении так и прёт. Этож какой Миша плохой! Сделал людям добро, а вам мало

      • Денис4 октября 2013 в 19:10 #

        я просто спросил вопрос у программиста, я жен спрашивал его уверстальщика, за 10 лет вордпресса или сколь он там существует я не нашел такого плагина почемуто...

        • Миша6 октября 2013 в 21:10 #

          Денис, вырубить стандартную вордпрессовскую форму нетрудно, достаточно удалить в форме параметр action, но я не считаю, что это хорошая идея, про защиту от спама я уже писал тут.

      • Миша6 октября 2013 в 21:10 #

        Чот судя по ответам вам не интересно отвечать как я понял

        сорри, у меня порой не хватает времени на развернутый ответ в несколько абзацев,

        Всё можно сделать. Но вы же хотите халявы? Сделайте то, сделайте это… А благодарности нет. Зато обида в вашем сообщении так и прёт. Этож какой Миша плохой! Сделал людям добро, а вам мало

        Otshelnik-fm, спасибо за поддержку)

        • Денис6 октября 2013 в 23:10 #

          понятно, спасибо, успехов вам! я использую тот метод тоже, но и для ручных постеров хотел бы сделать неповадным :)

  • Сергей18 октября 2013 в 04:10 #

    Спасибо. Сейчас себе тоже сделаю.

  • hohlhohl23 октября 2013 в 19:10 #

    пвапвапва

  • Генри4 ноября 2013 в 12:11 #

    Спасибо за вашу работу

  • Алексей16 ноября 2013 в 23:11 #

    пишу больше для теста) ... у себя тоже надо бы подобное сделать

  • Евгений1 декабря 2013 в 07:12 #

    у меня не работает когда пользователь не зарегистрирован, вернее отправляет но с ошибкой
    Fatal error: Call to a member function exists() on a non-object in Z:\home\perchatki.ru\www\wp-includes\comment.php on line 629
    Подскажите пожалуйста как исправить.

  • Мурад21 декабря 2013 в 22:12 #

    у меня не работает когда пользователь не зарегистрирован, вернее отправляет но с ошибкой
    Fatal error: Call to a member function exists() on a non-object in Z:\home\perchatki.ru\www\wp-includes\comment.php on line 629
    Подскажите пожалуйста как исправить.

  • иван26 декабря 2013 в 14:12 #

    Спасибо хорошая статья

  • Анатолий6 января 2014 в 14:01 #

    Спасибо за статью! Давно думал такое сделать...

  • Vitimus24 января 2014 в 12:01 #

    А на joomla сможете повторить? Очень надо!

  • Сергей14 февраля 2014 в 17:02 #

    Здравствуйте Миша.
    Прежде всего, хочу поблагодарить вас за полезную статью.
    Спасибо.
    Сделал все как у вас, но столкнулся с проблемой такого рода:
    Fatal error: Call to a member function exists() on a non-object in Z:\home\wordp.ru\www\wp-includes\comment.php on line 668
    как я понял, почитав комментарии к статье, я не первый.
    Ну, то есть, как и у других комментаторов, все отлично работает для зарегистрированных пользователей, а для остальных вылазит ошибка.
    Полез в код, долго мучился, но решил проблему закомментировав вот эти строки в вашем скрипте:

    /*
     * выставляем кукисы
     */
    do_action('set_comment_cookies', $comment, $user);

    все заработало как часы, проверял в разных браузерах, ни каких проблем.
    Отсюда вопрос: правильно ли я сделал, вообще можно ли так делать и не повлияет ли такое вот решение на работу моего блога? Если можно поясните мне пожалуйста, что я отключил своим действием?

    • Миша15 февраля 2014 в 01:02 #

      Добрый день, Сергей,
      Спасибо за содержательный комментарий.
      Думаю это не скажется отрицательно на работе блога, разве что после публикации коммента сайт не будет сохранять имя и email автора.

      • Сергей24 февраля 2014 в 22:02 #

        Здравствуйте Миша. Наверно уже сейчас можно сделать выводы, хотя прошло не так много времени и комментариев было оставлено на блоге не так много.
        Скажу сразу, все работает отлично, грех жаловаться. Специально экспериментировал с настройками в админке на блоге, я имею ввиду "Обсуждение", ставил разные параметры, все отлично.
        Вы писали:

        Думаю это не скажется отрицательно на работе блога, разве что после публикации коммента сайт не будет сохранять имя и email автора

        все сохраняется, могу только еще раз вас поблагодарить за отличную работу. Спасибо!
        Ели вы не против, позже напишу еще отчет, пусть подольше поработает ваш хук(если можно его так назвать).

  • Сергей15 февраля 2014 в 01:02 #

    Ну так это же плохо, я правильно понимаю? Мыло же должно сохраняться, на будущее. Блин, вот как сделать чтобы все работало. :) Все равно, большое спасибо вам. Пока оставлю, посмотрю как будет работать, а потом видно будет.

  • Mac15 марта 2014 в 22:03 #

    Спасибо!

  • Alex20 марта 2014 в 02:03 #

    Спасибо

  • Konst30 марта 2014 в 00:03 #

    Крутяк!!!

    • Денис21 мая 2014 в 09:05 #

      Ув. Администратор сия блога если тема еще актуальна и этот хук будет работать на версии 3.9.1 ?
      Подскажите пожалуйста куда пихать HTML и JS.
      заранее огромное спасибо)

      • Миша21 мая 2014 в 15:05 #

        У меня же работает на блоге)
        HTML - никуда - в посту дан просто пример (возможно надо будет поправить стандартный код).
        JS - после подключения jQuery.

        • Денис21 мая 2014 в 20:05 #

          Понятно спасибо большое за подсказку
          А что именно нужно подправить не подскажите?

  • Шурик10 апреля 2014 в 00:04 #

    Класс

  • Andrew11 апреля 2014 в 10:04 #

    супер

  • Антон12 апреля 2014 в 21:04 #

    Список радио http://newsrbk.ru/radios.html

  • Алекс25 мая 2014 в 22:05 #

    А можно ли узнать, как сделать так, чтобы поля "Имя" и "Электронная почта" появлялись после клика на поле "Оставить комментарий"?
    Спасибо за статью.

    • Миша26 мая 2014 в 07:05 #

      это делается на jQuery, код будет выглядеть примерно следующим образом:

      $('#form').submit(function(){
      	if( $('#fields').is(':hidden') {
      		$('#fields').slideDown(200);
      		return false;
      	}
      });
      // #form - форма, которая будет отправляться
      // #fields - это div блок, который будет появляться при клике на кнопку
      • Денис4 июля 2014 в 15:07 #

        Бро, надо чтобы комменты подгружались по клику на кнопку load_more_comments

        • Миша4 июля 2014 в 15:07 #

          А мне нравится когда сразу все комменты на странице — можно сделать поиск Ctrl (Cmd) + F :)

          А вообще ответ на твой комментарий — это материал для нового поста, который будет опубликован 18-го июля.

  • Саша25 мая 2014 в 23:05 #

    Спасибо. Использую.

  • Стасик27 мая 2014 в 12:05 #

    спасибо

  • user27 мая 2014 в 15:05 #

    Здорово!

  • alex5 июня 2014 в 12:06 #

    Попробую разобраться

  • Саша8 июня 2014 в 13:06 #

    Спасибо за статью, все получилось

  • Виктор13 июня 2014 в 10:06 #

    Cпасибо за статью

  • Skreep14 июня 2014 в 15:06 #

    Спасибо)

  • Эльдар8 июля 2014 в 21:07 #

    Спасибо! Статья класс!

  • slikNET10 июля 2014 в 19:07 #

    Подскажите, с помощью какого плагина вы делаете цитаты в комментах http://take.ms/30QSV

  • slikNET10 июля 2014 в 21:07 #

    У меня, если коммент оставляет админ, то коммент должен быть одобрен, хотя по сути такого быть не должно, от админа все комменты сразу должны высвечиваться....
    Подскажите в чем причина если знаете!

  • slikNET10 июля 2014 в 22:07 #

    все решил)
    может кому то понадобится
    в файле function.php после строки
    $comment_author_url = $wpdb->escape($user->user_url);
    добавить
    $user_ID = get_current_user_id();

  • Эльдар18 июля 2014 в 11:07 #

    Миша, а ты можешь поделится темой, хотя бы просто с кодом работы комментариев, просто ни на одной теме не получается его запустить(

    • Эльдар18 июля 2014 в 14:07 #

      Сделал теперь начал отправлять, но вместо комментария просто цифра '0', что может быть?

      • Миша18 июля 2014 в 19:07 #

        Значит дело не доходит до обработчика PHP :) нужно проверить параметр action в ajax запросе и в хуке.

  • Владимир16 августа 2014 в 04:08 #

    Спасибо за статью, очень помогла

  • Александр20 августа 2014 в 11:08 #

    Спасибо!

    • Александр20 августа 2014 в 11:08 #

      Один нюанс - на кнопке отправки, после нажатия, должно быть написано "Отправка", а не "Загрузка".

  • семеныч29 августа 2014 в 01:08 #

    коментарий

  • семеныч29 августа 2014 в 01:08 #

    что то долго

  • Илья26 сентября 2014 в 20:09 #

    Я делал комменты со встроенным редактором (wp_editor), так что мне не подошёл скрипт comment-reply.js, хотя у меня и не ajax. Но всё-таки завести полноценный редактор тоже была задача не из простых. Вам, Миша, видна моя почта, если интересно, киньте туда письмо, я вам ответным постараюсь описать, как у меня это вышло. В комментах, увы, этого не сделать и на треть.
    А за статью спасибо, ajax + редактор будет вообще кибершедевр :)

    • Миша27 сентября 2014 в 09:09 #

      Да, wp_editor в комментариях эт круто)) мне кажется что comment-reply.js у вас не работает из-за какой-то неучтенной мелочи.

      С ajax-комментариями несколько сложнее — вам нужно будет поискать функции для работы с TinyMCE.

      • Илья27 сентября 2014 в 17:09 #

        Вот об этом я и хотел написать. Нет, comment-reply.js в этом случае работать не будет, потому что перед переносом редактор нужно отключать, у него есть такая команда. Потом - включать обратно. То есть нужен переделанный скрипт, который будет содержать соответствующие команды для редактора. Но у него есть определённые проблемы с адаптивностью, которыми обычное текстовое поле не страдает.
        В общем, сначала делаете так (отключает функциональность tinymce):
        tinymce.EditorManager.execCommand('mceRemoveEditor', false, 'comment');
        - потом переносите форму в другое место.
        Далее включаете обратно и даёте ему фокус:
        tinymce.EditorManager.execCommand('mceAddEditor', false, 'comment');
        tinymce.EditorManager.execCommand('mceFocus', false, 'comment');
        Ну фокус давать это как бонус, чтобы не надо было в него курсор руками ставить опять. Первый параметр это команда объекта EditorManager, второй не помню, третий - атрибут name у textarea, куда подключается редактор. В общем-то всё.

        Про ajax+tinymce согласен, но не думаю что это очень уж тяжело, просто данные нужно брать из какого-то свойства этого объекта, а не из textarea, вот и всё.

  • Роман19 ноября 2014 в 14:11 #

    Тестирую))

  • nik2 декабря 2014 в 20:12 #

    спасибо, полезный пост.

  • nikolas2 декабря 2014 в 20:12 #

    спасибоу!

  • Игорь7 декабря 2014 в 10:12 #

    Спасибо за статью.
    Подскажите как прикрутить проверку "на лету", т.е. конструкцию .blur.
    Пробовал.. как-то не особо получилось.
    Заранее Спасибо.

  • Magzhan23 декабря 2014 в 15:12 #

    Миша помогите плиз, не получается у меня!

  • evol16 января 2015 в 06:01 #

    Давно искал эту тему

  • Дима21 января 2015 в 22:01 #

    Оставляю комментарий дабы опробовать сие чудо)

  • Дима21 января 2015 в 22:01 #

    Спасибо Миша! все работает как часы)

  • Максим29 января 2015 в 19:01 #

    Спасибо!!!

  • Radnk28 февраля 2015 в 02:02 #
    Notice: Функция wpdb::escape с версии 3.6 считается устаревшей! Используйте wpdb::prepare() or esc_sql().

    Как можно переписать?

  • Игорь Фёдоров14 марта 2015 в 15:03 #

    Тестовый комментарий :-)

  • Марат23 апреля 2015 в 19:04 #

    тест :-)

  • Bлад9 мая 2015 в 01:05 #

    Спасибо большое Миша - заработало сразу без проблем. Только вот возник вопрос - как сделать чтобы комментарий добавлялся (встраивался) в уже готовый commentlist, а не создавал свою новую обертку. А то у меня идет сначала свой стандартный comentlist (с комментариями), потом навигация комментариев, потом comentlist который добавляется через ajax, получается 2 comentlist (причем через навигацию), и еще почему-то в таком случае не появляется кнопка "ответить" через функцию:

    <?php $args = array('add_below' => 'comment','reply_text' => "Ответить",'depth' => 10);
    						comment_reply_link($args)?>

    . Правда после обновления страницы - все становиться на свои места.

    • Миша9 мая 2015 в 07:05 #

      Если он добавляет второй .commentlist, то значит не выполняется условие:

      if($('.commentlist').length > 0){

      Это значит, что элемента класса .commentlist у вас нет :) Какие CSS классы у вашего блока с комментариями?

  • Bлад9 мая 2015 в 13:05 #

    Всё! Спасибо за подсказку. Сразу вчера и не заметил, что у меня не class="commentlist", а id="commentlist, заменил в .js все на id - теперь работает. Теперь понятно почему создавался новый листинг. Еще раз спасибо! А вот кнопка "ответить" появляется только после обновления почему-то. А вы какой код используете для кнопки - такой же как я привел выше или может другой?

  • александр31 мая 2015 в 10:05 #

    класс

  • Артур19 июня 2015 в 18:06 #

    Спасибо вам большое за статью.
    У вас нас на сайте прекрасно реализованы комментарии. Хочется и себе и такой и благодаря вам немного приблизился к желаемому. )

  • Александр29 июня 2015 в 17:06 #

    Миша, не подскажете, использую ваш скрипт и мечатю усовершенствовать его, чтобы можно было прикреплять фотографии к комментарию, но не один плагин не работает с ним.. Можете помочь?

    • Миша29 июня 2015 в 23:06 #

      А вы как хотите, чтоб вставлялись фотографии? Через img тег?

      • Александр30 июня 2015 в 00:06 #

        Чтобы была кнопка обзор, прямо под формой комментирования - через которую можно было выбрать фото и прикрепить его к комментарию, а еще замечательнее, если не будет ограничений и можно будет сразу несколько фото прикрепить.. Кликая по ссылке прикрепить еще.. И после отправки коммента.. Вложения отображались прямо под текстом комментария... Это будет очень полезно и удобно..

        • Миша30 июня 2015 в 07:06 #

          Идея хорошая, только не знаю, найду ли я пока что время на её реализацию.

          • Александр30 июня 2015 в 08:06 #

            Если вдруг появится время, то в мире станет точно на 1 человека счастливее. Остальные я думаю будут только рады) постоянно читаю ваш блог и все рассылки! Спасибо за ваши труды, очень надеюсь что получится это сделать)

  • Александр1 августа 2015 в 12:08 #

    Интересно будет попробовать. Станет ли это работать с плагином мемберлюкс?

  • Саня5 августа 2015 в 11:08 #

    Круто)

  • Владимир14 августа 2015 в 11:08 #

    Спасибо за статью. Отсылаю комментарий для тестирования ajax

  • Сергей25 августа 2015 в 09:08 #

    Добрый день!
    Сделал все как написано получаю такую ошибку

    Notice: Undefined index: _wp_unfiltered_html_comment in Z:\home\smeshariki\www\wp-content\themes\smeshariki\functions.php on line 243

    • Миша31 августа 2015 в 13:08 #

      Добрый день!
      Сорри за задержку с ответом — был в отъезде.

      Данное notice можно убрать, использовав условие с isset():

      if( isset( $_POST['_wp_unfiltered_html_comment'] ) ) {
       
      }
      • Сергей31 августа 2015 в 20:08 #

        спасибо за ответ) после трех часовых танцев с бубном у меня все заработало)

  • Вячеслав30 августа 2015 в 22:08 #

    Тестовый комент)) Спасибо автору.

  • Виталий Охрименко23 сентября 2015 в 08:09 #

    Миш, я правильно понимаю:
    последний шаг - Последний шаг. PHP-обработчик это подключение нового файла php с любым названием который по сути заменяет стандартный comment.php?

    • Миша23 сентября 2015 в 19:09 #

      Прошу прощения, не указал в статье — PHP вставлять в файл functions.php в текущей теме.

  • Thank You15 октября 2015 в 17:10 #

    Спасибо огромное

  • Kenny19 октября 2015 в 22:10 #

    Спасибо, все работает)

  • Алексей6 ноября 2015 в 05:11 #

    Михаил, а как ты реализовал форму заказа? Может, напишешь статью, как это делается?

  • Вадим17 ноября 2015 в 15:11 #

    Что не пошло у меня, комментарии добавляются, как и раньше
    файл comments.js создал, в function.php добавил подключение и обработчик, но увы(

  • Вадим17 ноября 2015 в 16:11 #

    Все работает, недоглядел просто(
    Спасибо!))

  • Игорь17 ноября 2015 в 18:11 #

    Спасибо

  • Анна10 декабря 2015 в 23:12 #

    Прошу вашей помощи! Сил нет уже искать причину неработоспособности кода.
    Все сделала, как в статье. По отдельности все работает, но комментарии не добавляются и не показываются.
    1) в js файле нет ошибок, выводит и код в success, и в complete
    2) в коде php тоже нет ошибок, проверяла на отдельной странице, все работает, комментарии добавляются и выводятся
    Но если я добавляю функцию через хук add_action, она не срабатывает вообще, ни одна строка. Соответственно комментарии не добавляются и не показываются. Проверяла тысячу раз соответствие названий (их не меняла, все скопировано с сайта).
    Помогите, где искать проблему???

  • Анна11 декабря 2015 в 08:12 #

    на локалхосте(

    • Миша11 декабря 2015 в 11:12 #

      Очень жаль, потому что так очень трудно что-то сказать.

      Опишите как можно подробнее, что происходит, после того, как вы нажимаете кнопку добавления комментария.

      • Анна12 декабря 2015 в 00:12 #

        Ура! Ура! Несколько часов поисков, и я нашла ошибку!
        Проблема была в названиях полей формы. Дело в том, что давным-давно я делала антиспам защиту на комментарии функцией, которая подменяет названия полей. И об этой функции совершенно забыла(( Блин, столько времени потратить...
        Но я рада, что все-таки я это сделала! Спасибо вам большое за статью, за то, что не остались равнодушны)) Статья супер! Именно по этой теме ничего больше не нашла в интернете, так что вам респект!
        Так, а где копилка сайта? За такую ценную информацию с удовольствием заплатила бы)

        • Миша12 декабря 2015 в 09:12 #

          Благодарю :) копилки нет к сожалению, но в качестве благодарности можете любой из моих плагинов купить)

          • Анна12 декабря 2015 в 15:12 #

            Хорошо) Купила плагин Topbutton. У меня, правда, есть такая кнопка, но раз сказала - значит сделала, может пригодится)) Без вашей статьи я бы не разобралась! Так что очень благодарна! Еще раз спасибо)

  • Александр11 декабря 2015 в 13:12 #

    Михаил, сделайте пожалуйста возможность прикреплять неограниченное кол-во фото к комментариям!

  • Виталий18 декабря 2015 в 15:12 #

    Очень полезная функция

  • Valeriy3 января 2016 в 02:01 #

    Подскажите, как вывести уведомление о том что комментарий слишком маленький?
    В js я выставляю например length < 200, того что фон поля становиться красным недостаточно ...

Оставить комментарий / вопрос

phpjsHTMLCSSSQLПросто код
  Для того, чтобы оставить комментарий, пожалуйста, зарегистрируйтесь или авторизуйтесь на сайте.
Получайте новости блога по email или следите за мной в социальных сетях.
  • Иван: Спасибо за ответ. Что тогда не так делаю? Создаю новый метабокс: function register_metabox() { add_meta_box( 'exam...

  • Миша: Добый день, Иван! А для радио-кнопок всё работает так же, как и для текстовых полей, просто значения value полей фикс...

  • Иван: Михаил, создал метабокс и вывел там два радиобаттона. $html1 .= ''; $html1 .= ''; Я должен выбрать, добавлять ста...

  • Леонид: Понимаю) У меня она тоже вызывает взрыв мозга, но по сути она незатейливая - первым параметром просто пишется имя скрипт...

  • Миша: Леонид, спасибо большое за полезное дополнение к статье! Я в первую очередь делал упор на то, чтобы сделать код в ста...