[a-zA-Z0-9-]+)', [ 'methods' => 'GET', 'callback' => function($request) { $slug = $request['slug']; if (!function_exists('get_coauthors')) { return new WP_Error('no_plugin', 'Co-Authors Plus not active', ['status' => 404]); } global $coauthors_plus; if (isset($coauthors_plus) && method_exists($coauthors_plus, 'get_coauthor_by')) { $coauthor = $coauthors_plus->get_coauthor_by('user_nicename', $slug); if ($coauthor) { // Получаем ID записи гостевого автора $author_post_id = $coauthor->ID; // ПОЛУЧАЕМ ФОТО ИЗ МИНИАТЮРЫ ЗАПИСИ (post thumbnail) $photo = null; $photo_sizes = []; if (has_post_thumbnail($author_post_id)) { $photo_id = get_post_thumbnail_id($author_post_id); // Основные размеры $photo_sizes = [ 'thumbnail' => wp_get_attachment_image_url($photo_id, 'thumbnail'), 'medium' => wp_get_attachment_image_url($photo_id, 'medium'), 'large' => wp_get_attachment_image_url($photo_id, 'large'), 'full' => wp_get_attachment_image_url($photo_id, 'full'), ]; $photo = $photo_sizes['medium']; } return [ 'id' => $coauthor->user_nicename, 'name' => $coauthor->display_name, 'firstName' => $coauthor->first_name ?? '', 'lastName' => $coauthor->last_name ?? '', 'description' => $coauthor->description ?? '', // Фото из миниатюры поста (это то, что вам нужно) 'photo' => $photo, 'photo_sizes' => $photo_sizes, // Для обратной совместимости 'avatar' => $photo ?: '', 'url' => get_author_posts_url($coauthor->ID, $coauthor->user_nicename), 'type' => $coauthor->type ?? 'guest-author' ]; } } return new WP_Error('not_found', 'Author not found', ['status' => 404]); }, 'permission_callback' => '__return_true' ]); }); add_action('rest_api_init', function() { register_rest_route('my/v1', '/author/(?P[a-zA-Z0-9-]+)/posts', [ 'methods' => 'GET', 'callback' => function($request) { $slug = $request['slug']; $per_page = $request->get_param('per_page') ?: 10; $cursor = $request->get_param('cursor'); $before = $request->get_param('before'); $after = $request->get_param('after'); // Устанавливаем нужные типы постов $post_type = ['profile_article', 'anew', 'yellow']; if (!function_exists('get_coauthors')) { return new WP_Error('no_plugin', 'Co-Authors Plus not active', ['status' => 404]); } global $coauthors_plus; // Получаем автора по slug $coauthor = null; if (isset($coauthors_plus) && method_exists($coauthors_plus, 'get_coauthor_by')) { $coauthor = $coauthors_plus->get_coauthor_by('user_nicename', $slug); } if (!$coauthor) { return new WP_Error('not_found', 'Author not found', ['status' => 404]); } // Определяем тип автора и получаем термин таксономии author $author_term = null; if ($coauthor->type === 'guest-author') { $author_term = get_term_by('slug', 'cap-' . $coauthor->user_nicename, 'author'); } else { $author_term = get_term_by('slug', $coauthor->user_nicename, 'author'); } if (!$author_term) { return new WP_Error('not_found', 'Author term not found', ['status' => 404]); } // Базовые аргументы запроса $args = [ 'post_type' => $post_type, 'posts_per_page' => $per_page, 'post_status' => 'publish', 'tax_query' => [ [ 'taxonomy' => 'author', 'field' => 'term_id', 'terms' => $author_term->term_id, ] ], 'orderby' => 'date', 'order' => 'DESC', ]; // Применяем курсорную пагинацию if ($after) { $args['date_query'] = [ [ 'column' => 'post_date', 'before' => $after, 'inclusive' => false, ] ]; } elseif ($before) { $args['date_query'] = [ [ 'column' => 'post_date', 'after' => $before, 'inclusive' => false, ] ]; $args['order'] = 'ASC'; } elseif ($cursor) { $cursor_post = get_post($cursor); if ($cursor_post) { $args['date_query'] = [ [ 'column' => 'post_date', 'before' => $cursor_post->post_date, 'inclusive' => false, ] ]; } } $query = new WP_Query($args); $posts = $query->posts; if ($before) { $posts = array_reverse($posts); } // Форматируем посты - ТОЛЬКО нужные поля $formatted_posts = []; foreach ($posts as $post) { setup_postdata($post); // Получаем соавторов $coauthors = []; if (function_exists('get_coauthors')) { $post_coauthors = get_coauthors($post->ID); foreach ($post_coauthors as $post_coauthor) { $coauthors[] = [ 'id' => $post_coauthor->user_nicename, 'name' => $post_coauthor->display_name, ]; } } // Получаем рубрики/категории $categories = []; $taxonomies = ['category', 'rubric']; foreach ($taxonomies as $taxonomy) { $terms = get_the_terms($post->ID, $taxonomy); if ($terms && !is_wp_error($terms)) { foreach ($terms as $term) { $categories[] = [ 'id' => $term->term_id, 'name' => $term->name, 'slug' => $term->slug, 'taxonomy' => $taxonomy, ]; } } } $formatted_posts[] = [ 'id' => $post->ID, 'title' => $post->post_title, 'slug' => $post->post_name, 'type' => $post->post_type, 'date' => $post->post_date, 'link' => get_permalink($post->ID), // Только картинка (разные размеры) 'featured_image' => [ 'full' => get_the_post_thumbnail_url($post->ID, 'full'), 'large' => get_the_post_thumbnail_url($post->ID, 'large'), 'medium' => get_the_post_thumbnail_url($post->ID, 'medium'), 'thumbnail' => get_the_post_thumbnail_url($post->ID, 'thumbnail'), ], // Рубрики 'categories' => $categories, // Соавторы 'coauthors' => $coauthors, // Курсор для пагинации 'cursor' => $post->post_date, ]; } wp_reset_postdata(); // ИСПРАВЛЕННАЯ ПАГИНАЦИЯ $has_next = false; $next_cursor = null; $has_previous = false; $previous_cursor = null; $first_cursor = null; $last_cursor = null; if (!empty($posts)) { $first_post = reset($posts); $last_post = end($posts); $first_cursor = $first_post->post_date; $last_cursor = $last_post->post_date; // Простая проверка: если количество найденных постов больше, чем количество на странице // ИЛИ если есть больше страниц $has_next = $query->max_num_pages > 1; // Если есть следующая страница, курсор - дата последнего поста if ($has_next) { $next_cursor = $last_post->post_date; } // Проверяем предыдущие посты (если это не первая страница) if ($cursor || $after || $before) { // Если есть курсор, значит это не первая страница $has_previous = true; $previous_cursor = $first_post->post_date; } } // Добавим отладку (можно убрать после тестирования) error_log('=== AUTHOR POSTS DEBUG ==='); error_log('Slug: ' . $slug); error_log('Posts found: ' . count($posts)); error_log('Total posts: ' . $query->found_posts); error_log('Max num pages: ' . $query->max_num_pages); error_log('Has next: ' . ($has_next ? 'true' : 'false')); error_log('Next cursor: ' . ($next_cursor ?? 'null')); error_log('========================'); return [ 'data' => $formatted_posts, 'pagination' => [ 'total' => $query->found_posts, 'per_page' => (int)$per_page, 'has_next' => $has_next, 'has_previous' => $has_previous, 'next_cursor' => $next_cursor, 'previous_cursor' => $previous_cursor, 'first_cursor' => $first_cursor, 'last_cursor' => $last_cursor, ], 'author' => [ 'id' => $coauthor->user_nicename, 'name' => $coauthor->display_name, ] ]; }, 'args' => [ 'per_page' => [ 'type' => 'integer', 'default' => 10, 'minimum' => 1, 'maximum' => 100, ], 'cursor' => [ 'type' => 'string', 'description' => 'Cursor for pagination', ], 'after' => [ 'type' => 'string', 'description' => 'Get posts after this date', ], 'before' => [ 'type' => 'string', 'description' => 'Get posts before this date', ], ], 'permission_callback' => '__return_true' ]); });