В первом посте из этой серии мы определили, что такое API, чем он отличается от API настроек, а также некоторые общие вызовы, которые мы можем сделать для API. В этом посте мы рассмотрим практическую реализацию API и то, как справляться с некоторыми особенностями, связанными с обработкой данных с истекшим сроком действия.
WordPress Transients API — это мощный (но очень простой в использовании) аспект WordPress API. Вообще говоря, это действительно облегчает хранение данных с истекшим сроком действия, и позволяет действительно легко использовать различные плагины для кэширования, чтобы в конечном итоге увеличить скорость вашего сайта.
Настройте плагин
Для целей этого плагина мы собираемся создать простой виджет, который будет перечислять топ-комментаторы блогов всех времен. Цель плагина — сохранить его стройность, чтобы мы могли выделить функциональные возможности плагина.
Обратите внимание, что все файлы плагина могут быть получены из GitHub в любое время. Тем временем, создайте каталог с именем top-commenters-cached и убедитесь, что он имеет следующую структуру каталогов:
Если вы не заинтересованы в локализации плагина, не стесняйтесь оставлять каталог ‘lang’ вне плагина. На данный момент, мы готовы начать писать виджет.
Основная функциональность
Плагин прост. Должно…
- Разрешить пользователю дать виджет
- Получить топ-10 самых популярных комментаторов жизни блога
Достаточно просто. Вот код для основного плагина. Обратите внимание, что он прокомментирован повсюду, поэтому потратьте некоторое время на чтение, чтобы понять, что мы делаем. Если вы не знакомы с API виджетов, не забудьте проверить наш пост WordPress Widget Boilerplate .
001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
027
028
029
030
031
032
033
034
035
036
037
038
039
040
041
042
043
044
045
046
047
048
049
050
051
052
053
054
055
056
057
058
059
060
061
062
063
064
065
066
067
068
069
070
071
072
073
074
075
076
077
078
079
080
081
082
083
084
085
086
087
088
089
090
091
092
093
094
095
096
097
098
099
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
|
class Top_Commenters_Cached extends WP_Widget {
const name = ‘Top Commenters (Cached!)’;
const locale = ‘top-commenters-cached-locale’;
const slug = ‘top-commenters-cached’;
/*—————————————————*/
/* Constructor
/*—————————————————*/
/**
* The widget constructor.
* the widget, loads localization files, and includes necessary scripts and
* styles.
*/
function Top_Commenters_Cached() {
$widget_opts = array (
‘classname’ => self::name,
‘description’ => __(‘A plugin used to demonstrate the WordPress Transients API for an Envato blog series.’, self::locale)
);
$this->WP_Widget(self::slug, __(self::name, self::locale), $widget_opts);
load_plugin_textdomain(self::locale, false, dirname(plugin_basename( __FILE__ ) ) . ‘/lang/’ );
} // end constructor
/*—————————————————*/
/* API Functions
/*—————————————————*/
/**
* Outputs the content of the widget.
*
* @args The array of form elements
* @instance
*/
function widget($args, $instance) {
extract($args, EXTR_SKIP);
echo $before_widget;
$widget_title = empty($instance[‘widget_title’]) ?
$commenters = $this->query_for_commenters();
// Display the widget
include(WP_PLUGIN_DIR . ‘/’ . self::slug . ‘/views/widget.php’);
echo $after_widget;
} // end widget
/**
* Processes the widget’s options to be saved.
*
* @new_instance The previous instance of values before the update.
* @old_instance The new instance of values to be generated via the update.
*/
function update($new_instance, $old_instance) {
$instance = $old_instance;
$instance[‘widget_title’] = $this->strip($new_instance, ‘widget_title’);
return $instance;
} // end widget
/**
* Generates the administration form for the widget.
*
* @instance The array of keys and values for the widget.
*/
function form($instance) {
$instance = wp_parse_args(
(array)$instance,
array(
‘widget_title’ => »
)
);
$widget_title = $this->strip($instance, ‘widget_title’);
// Display the admin form
include(WP_PLUGIN_DIR . ‘/’ . self::slug . ‘/views/admin.php’);
} // end form
/*—————————————————*/
/* Private Functions
/*—————————————————*/
/**
* Retrieves the weekly top commenters for the past week and stores the values in the cache.
* If the cache is empty, then the function will request information from the database and
* store it in the cache.
*/
private function query_for_commenters() {
$commenters = null;
// query the database for the top commenters
global $wpdb;
$commenters = $wpdb->get_results(«
select count(comment_author) as comments_count, comment_author, comment_type
from $wpdb->comments
where comment_type != ‘pingback’
and comment_author != »
and comment_approved = ‘1’
group by comment_author
order by comment_author desc
LIMIT 10
«);
return $commenters
} // end query_for_commenters
/*—————————————————*/
/* Helper Functions
/*—————————————————*/
/**
* Convenience method for stripping tags and slashes from the content
* of a form input.
*
* @obj The instance of the argument array
* @title The title of the element from which we’re stripping tags and slashes.
*/
private function strip($obj, $title) {
return strip_tags(stripslashes($obj[$title]));
} // end strip
} // end class
add_action(‘widgets_init’, create_function(», ‘register_widget(«Top_Commenters_Cached»);’));
?>
|
Далее, давайте взглянем на вид виджета. Это та часть плагина, которая отвечает за отображение списка комментариев. Он работает, отображая заголовок виджета (если он определен), а затем просматривает результаты, создавая новый элемент списка.
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
<?php if(strlen(trim($widget_title)) > 0) { ?>
<h3 class=»widget-title»>
<?php echo $widget_title;
</h3>
<?php
} // end if
global $wpdb;
$comment_list = ‘<ol>’;
foreach($commenters as $commenter) {
$comment_list .= ‘<li>’;
// actually print the commenter’s name and the number of comments
$comment_list .= $commenter->comment_author;
$comment_list .= ‘ (‘ . $commenter->comments_count . ‘)’;
$comment_list .= ‘</li>’;
} // end foreach
$comment_list .= ‘</ol>’;
echo $comment_list;
?>
|
Очевидно, мы оставили часть кода. А именно, панель администратора. Это должно просто позволить пользователям вводить заголовок для их виджета:
01
02
03
04
05
06
07
08
09
10
11
|
<div>
<fieldset>
<legend>
<?php _e(‘Widget Options’, self::locale);
</legend>
<label for=»<?php echo $this->get_field_id(‘widget_title’); ?>» class=»block»>
<?php _e(‘Title:’, self::locale);
</label>
<input type=»text» name=»<?php echo $this->get_field_name(‘widget_title’); ?>» id=»<?php echo $this->get_field_id(‘widget_title’); ?>» value=»<?php echo $instance[‘widget_title’]; ?>» class=»» />
</fieldset>
</div>
|
Помните, что вы можете просмотреть полный исходный код и загрузить плагин из его репозитория GitHub .
Кэшировать данные
На данный момент у нас есть функциональный плагин; тем не менее, мы пока не кешируем какие-либо данные. Самая интенсивная часть этого плагина — когда мы запрашиваем базу данных, а результаты запроса — это то, что мы на самом деле хотим кэшировать, поэтому давайте сделаем это.
Найдите запрос в коде:
01
02
03
04
05
06
07
08
09
10
11
|
global $wpdb;
$commenters = $wpdb->get_results(«
select count(comment_author) as comments_count, comment_author, comment_type
from $wpdb->comments
where comment_type != ‘pingback’
and comment_author != »
and comment_approved = ‘1’
group by comment_author
order by comment_author desc
LIMIT 10
«);
|
И давайте сохраним результаты в течение 12 часов, используя API для переходных процессов:
1
|
set_transient(‘top_commenters_cached’, $commenters, 60 * 60 * 12);
|
Довольно легко, правда? Конечно, мы еще не закончили.
Получить данные
Как только переходный процесс установлен, мы должны быть в состоянии получить переходный процесс. Давайте настроим это сейчас:
1
2
3
|
private function query_for_commenters() {
return get_transient(‘top_commenters_cached’);
} // end query_for_commenters
|
Это все, что нужно сделать!
Но подождите — если вы помните из первого поста в серии, переходные процессы фактически истекают, поэтому мы не можем получить переходные процессы.
Нахождение недостающих данных
Независимо от того, что вы делаете, извлечение данных, срок действия которых истек, обычно выполняется одинаково:
- Проверить наличие переходного процесса
- Если он существует, используйте его
- Если он не существует, установите его, затем получите его
Итак, давайте сделаем это в контексте нашего плагина:
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
private function query_for_commenters() {
$commenters = null;
// check to see if the transient exists.
if(!get_transient(‘top_commenters_cached’)) {
// query the database for the top commenters
global $wpdb;
$commenters = $wpdb->get_results(«
select count(comment_author) as comments_count, comment_author, comment_type
from $wpdb->comments
where comment_type != ‘pingback’
and comment_author != »
and comment_approved = ‘1’
group by comment_author
order by comment_author desc
LIMIT 10
«);
// store the result
set_transient(‘top_commenters_cached’, $commenters, 60 * 60 * 12);
} // end if
// transient is guaranteed to exist now, so return it
return get_transient(‘top_commenters_cached’);
} // end query_for_commenters
|
Вывод
Не так уж плохо, правда?
Как вы можете видеть, работа с Transient API требует немного больше, чем знание того, когда его использовать и какие функции доступны. На мой взгляд, это один из самых мощных аспектов WordPress API.
Если вы обнаруживаете, что извлекаете большие объемы данных, ищете способ истечения срока действия данных для обновления или просто хотите воспользоваться плагинами кэширования, не забудьте воспользоваться API-интерфейсом Transients.