Skip to content

Commit 6c1c849

Browse files
committed
Release version 1.8.2
- Added SEO columns for WooCommerce categories (Title Tag + Meta Description) - Enhanced sitemap error handling with 404 responses - Added post type and taxonomy validation in sitemap generation - Improved XSS protection with esc_url() and esc_html() - Removed problematic remove_all_filters() calls - Updated documentation links and changelog
1 parent d831b0a commit 6c1c849

File tree

4 files changed

+527
-45
lines changed

4 files changed

+527
-45
lines changed

BasicSEO.php

Lines changed: 166 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,17 @@
33
*
44
* @package BasicSEO
55
* @author https://github.com/Torwald45
6-
* @version 1.8.1
6+
* @version 1.8.2
77
* @pluginURI https://github.com/Torwald45/basic-seo
8-
* @changelog @pluginURI https://github.com/Torwald45/basic-seo/CHANGELOG.md
9-
* Features:
8+
* @changelog https://github.com/Torwald45/basic-seo/blob/main/CHANGELOG.md
9+
* @roadmap https://github.com/Torwald45/basic-seo/blob/main/ROADMAP.md
10+
* Features:
1011
* - Custom Title Tag for pages, posts and WooCommerce (shop page & categories)
1112
* - Meta Description for pages, posts and WooCommerce (shop page & categories)
13+
* - SEO columns in admin view for posts, pages, products and WooCommerce categories
1214
* - Open Graph support (title, description, image)
1315
* - XML Sitemap with HTML display (pages, posts, products, categories)
16+
* - Error handling for XML Sitemap
1417
* - Quick Edit support in admin panel
1518
* - Breadcrumbs support via [basicseo-breadcrumb] shortcode
1619
* - Media attachments redirect (prevents duplicate content)
@@ -143,18 +146,16 @@ function basicseotorvald_v1_add_columns($columns) {
143146
return $columns;
144147
}
145148

146-
remove_all_filters('manage_posts_columns');
147-
remove_all_filters('manage_pages_columns');
148-
remove_all_filters('manage_product_posts_columns');
149-
150-
add_filter('manage_posts_columns', 'basicseotorvald_v1_add_columns');
151-
add_filter('manage_pages_columns', 'basicseotorvald_v1_add_columns');
152-
add_filter('manage_product_posts_columns', 'basicseotorvald_v1_add_columns');
149+
add_filter('manage_posts_columns', 'basicseotorvald_v1_add_columns', 20);
150+
add_filter('manage_pages_columns', 'basicseotorvald_v1_add_columns', 20);
151+
add_filter('manage_product_posts_columns', 'basicseotorvald_v1_add_columns', 20);
153152

154153
foreach(basicseotorvald_v1_get_supported_post_types() as $post_type) {
155-
add_filter("manage_{$post_type}_posts_columns", 'basicseotorvald_v1_add_columns');
154+
add_filter("manage_{$post_type}_posts_columns", 'basicseotorvald_v1_add_columns', 20);
156155
}
157156

157+
158+
158159
// Display content in columns
159160
function basicseotorvald_v1_column_content($column_name, $post_id) {
160161
static $displayed = array();
@@ -310,6 +311,68 @@ function basicseotorvald_v1_save_product_cat_fields($term_id) {
310311
add_action('created_product_cat', 'basicseotorvald_v1_save_product_cat_fields');
311312
add_action('edited_product_cat', 'basicseotorvald_v1_save_product_cat_fields');
312313

314+
/**
315+
* ==============================================
316+
* WOOCOMMERCE CATEGORY COLUMNS
317+
* ==============================================
318+
*/
319+
320+
// Add new columns to the product category list
321+
function basicseotorvald_v1_add_product_cat_columns($columns) {
322+
$new_columns = array();
323+
324+
// Preserve checkbox column if exists
325+
if (isset($columns['cb'])) {
326+
$new_columns['cb'] = $columns['cb'];
327+
}
328+
329+
// Preserve thumbnail column if exists
330+
if (isset($columns['thumb'])) {
331+
$new_columns['thumb'] = $columns['thumb'];
332+
}
333+
334+
// Add name column (required)
335+
$new_columns['name'] = $columns['name'];
336+
337+
// Add our new SEO columns
338+
$new_columns['seo_title'] = 'Title Tag';
339+
$new_columns['seo_desc'] = 'Meta Description';
340+
341+
// Preserve remaining standard columns
342+
if (isset($columns['description'])) {
343+
$new_columns['description'] = $columns['description'];
344+
}
345+
if (isset($columns['slug'])) {
346+
$new_columns['slug'] = $columns['slug'];
347+
}
348+
if (isset($columns['count'])) {
349+
$new_columns['count'] = $columns['count'];
350+
}
351+
352+
return $new_columns;
353+
}
354+
add_filter('manage_edit-product_cat_columns', 'basicseotorvald_v1_add_product_cat_columns');
355+
356+
// Display content in the new columns
357+
function basicseotorvald_v1_product_cat_column_content($content, $column_name, $term_id) {
358+
switch ($column_name) {
359+
case 'seo_title':
360+
$title = get_term_meta($term_id, BSTV1_TERM_TITLE, true);
361+
return $title ? esc_html($title) : '';
362+
363+
case 'seo_desc':
364+
$desc = get_term_meta($term_id, BSTV1_TERM_DESC, true);
365+
return $desc ? esc_html(wp_trim_words($desc, 10, '...')) : '';
366+
}
367+
return $content;
368+
}
369+
add_filter('manage_product_cat_custom_column', 'basicseotorvald_v1_product_cat_column_content', 10, 3);
370+
371+
/**
372+
* END OF WOOCOMMERCE CATEGORY COLUMNS
373+
* ==============================================
374+
*/
375+
313376
/**
314377
* ==============================================
315378
* META TAGS OUTPUT IN HEAD
@@ -445,23 +508,32 @@ function basicseotorvald_v1_generate_sitemap_index() {
445508
$post_types = get_post_types(['public' => true]);
446509
unset($post_types['attachment']);
447510

448-
foreach ($post_types as $post_type) {
449-
// Check if post type has any posts
450-
$count = wp_count_posts($post_type);
451-
if ($count->publish > 0) {
452-
$url = home_url("/sitemap-post-type-{$post_type}.xml");
453-
$output .= "<a href='{$url}'>{$url}</a><br>\n";
511+
if (empty($post_types)) {
512+
$output .= '<p>No public post types found.</p>';
513+
} else {
514+
foreach ($post_types as $post_type) {
515+
// Check if post type has any posts
516+
$count = wp_count_posts($post_type);
517+
if ($count && $count->publish > 0) {
518+
$url = home_url("/sitemap-post-type-{$post_type}.xml");
519+
$output .= "<a href='" . esc_url($url) . "'>" . esc_html($url) . "</a><br>\n";
520+
}
454521
}
455522
}
456523

457524
// Get all public taxonomies
458525
$taxonomies = get_taxonomies(['public' => true]);
459-
foreach ($taxonomies as $taxonomy) {
460-
// Check if taxonomy has any terms
461-
$terms = get_terms(['taxonomy' => $taxonomy, 'hide_empty' => true]);
462-
if (!empty($terms) && !is_wp_error($terms)) {
463-
$url = home_url("/sitemap-taxonomy-{$taxonomy}.xml");
464-
$output .= "<a href='{$url}'>{$url}</a><br>\n";
526+
527+
if (empty($taxonomies)) {
528+
$output .= '<p>No public taxonomies found.</p>';
529+
} else {
530+
foreach ($taxonomies as $taxonomy) {
531+
// Check if taxonomy has any terms
532+
$terms = get_terms(['taxonomy' => $taxonomy, 'hide_empty' => true, 'number' => 1]);
533+
if (!empty($terms) && !is_wp_error($terms)) {
534+
$url = home_url("/sitemap-taxonomy-{$taxonomy}.xml");
535+
$output .= "<a href='" . esc_url($url) . "'>" . esc_html($url) . "</a><br>\n";
536+
}
465537
}
466538
}
467539

@@ -471,25 +543,39 @@ function basicseotorvald_v1_generate_sitemap_index() {
471543
// Generate sitemap for specific post type
472544
function basicseotorvald_v1_generate_post_type_sitemap($post_type) {
473545
$output = '<h1>XML Sitemap</h1>';
546+
547+
// Verify post type exists
548+
if (!post_type_exists($post_type)) {
549+
return '<div class="error">Error: Post type does not exist.</div>';
550+
}
551+
474552
$output .= '<table>
475553
<tr>
476554
<th>URL</th>
477555
<th>Last Modified</th>
478556
</tr>';
479557

480-
$posts = get_posts([
481-
'post_type' => $post_type,
482-
'post_status' => 'publish',
483-
'posts_per_page' => -1,
484-
'orderby' => 'modified',
485-
'order' => 'DESC'
486-
]);
487-
488-
foreach ($posts as $post) {
489-
$output .= '<tr>
490-
<td><a href="' . get_permalink($post->ID) . '">' . get_permalink($post->ID) . '</a></td>
491-
<td>' . get_the_modified_date('Y-m-d\TH:i:sP', $post->ID) . '</td>
492-
</tr>';
558+
// no limit posts to 500 to prevent server overload
559+
$posts = get_posts([
560+
'post_type' => $post_type,
561+
'post_status' => 'publish',
562+
'posts_per_page' => -1,
563+
'orderby' => 'modified',
564+
'order' => 'DESC'
565+
]);
566+
567+
if (empty($posts)) {
568+
$output .= '<tr><td colspan="2">No published content found.</td></tr>';
569+
} else {
570+
foreach ($posts as $post) {
571+
$permalink = get_permalink($post->ID);
572+
if ($permalink) {
573+
$output .= '<tr>
574+
<td><a href="' . esc_url($permalink) . '">' . esc_html($permalink) . '</a></td>
575+
<td>' . get_the_modified_date('Y-m-d\TH:i:sP', $post->ID) . '</td>
576+
</tr>';
577+
}
578+
}
493579
}
494580

495581
$output .= '</table>';
@@ -503,22 +589,35 @@ function basicseotorvald_v1_generate_post_type_sitemap($post_type) {
503589
// Generate sitemap for taxonomy
504590
function basicseotorvald_v1_generate_taxonomy_sitemap($taxonomy) {
505591
$output = '<h1>XML Sitemap</h1>';
592+
593+
// Verify taxonomy exists
594+
if (!taxonomy_exists($taxonomy)) {
595+
return '<div class="error">Error: Taxonomy does not exist.</div>';
596+
}
597+
506598
$output .= '<table>
507599
<tr>
508600
<th>URL</th>
509601
<th>Last Modified</th>
510602
</tr>';
511603

512-
$terms = get_terms([
513-
'taxonomy' => $taxonomy,
514-
'hide_empty' => true
515-
]);
604+
$terms = get_terms([
605+
'taxonomy' => $taxonomy,
606+
'hide_empty' => true
607+
]);
516608

517-
foreach ($terms as $term) {
518-
$output .= '<tr>
519-
<td><a href="' . get_term_link($term) . '">' . get_term_link($term) . '</a></td>
520-
<td>' . date('Y-m-d\TH:i:sP') . '</td>
521-
</tr>';
609+
if (empty($terms) || is_wp_error($terms)) {
610+
$output .= '<tr><td colspan="2">No terms found or an error occurred.</td></tr>';
611+
} else {
612+
foreach ($terms as $term) {
613+
$term_link = get_term_link($term);
614+
if (!is_wp_error($term_link)) {
615+
$output .= '<tr>
616+
<td><a href="' . esc_url($term_link) . '">' . esc_html($term_link) . '</a></td>
617+
<td>' . date('Y-m-d\TH:i:sP') . '</td>
618+
</tr>';
619+
}
620+
}
522621
}
523622

524623
$output .= '</table>';
@@ -556,6 +655,12 @@ function basicseotorvald_v1_handle_sitemap_request() {
556655
if (post_type_exists($post_type)) {
557656
echo basicseotorvald_v1_generate_post_type_sitemap($post_type);
558657
exit;
658+
} else {
659+
status_header(404);
660+
echo '<h1>Error 404: Sitemap not found</h1>';
661+
echo '<p>The requested post type does not exist.</p>';
662+
echo '<p><a href="' . home_url('/sitemap.xml') . '">Back to main sitemap</a></p>';
663+
exit;
559664
}
560665
}
561666

@@ -565,9 +670,25 @@ function basicseotorvald_v1_handle_sitemap_request() {
565670
if (taxonomy_exists($taxonomy)) {
566671
echo basicseotorvald_v1_generate_taxonomy_sitemap($taxonomy);
567672
exit;
673+
} else {
674+
status_header(404);
675+
echo '<h1>Error 404: Sitemap not found</h1>';
676+
echo '<p>The requested taxonomy does not exist.</p>';
677+
echo '<p><a href="' . home_url('/sitemap.xml') . '">Back to main sitemap</a></p>';
678+
exit;
568679
}
569680
}
681+
682+
// If we got here, the sitemap URL pattern was invalid
683+
if (strpos($current_url, 'sitemap') !== false && strpos($current_url, '.xml') !== false) {
684+
status_header(404);
685+
echo '<h1>Error 404: Sitemap not found</h1>';
686+
echo '<p>Invalid sitemap URL format.</p>';
687+
echo '<p><a href="' . home_url('/sitemap.xml') . '">Back to main sitemap</a></p>';
688+
exit;
689+
}
570690
}
691+
571692
add_action('init', 'basicseotorvald_v1_handle_sitemap_request');
572693

573694
/**

CHANGELOG.md

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,20 @@
11
# Changelog for Basic SEO
22

3+
## Version 1.8.2 - December 4, 2024
4+
**Tested up to**:
5+
- WordPress: 6.7
6+
- WooCommerce: 9.4.1
7+
8+
### Improvements
9+
- Enhanced sitemap generation with better error handling
10+
- Added post type and taxonomy validation in sitemap
11+
- Improved 404 error responses for invalid sitemap requests
12+
13+
### Technical
14+
- Added post_type_exists() and taxonomy_exists() validation
15+
- Improved empty data handling in sitemap generation
16+
- Added proper HTTP status codes for error responses
17+
318
## Version 1.8.1 - November 17, 2024
419
**Tested up to**:
520
- WordPress: 6.7

0 commit comments

Comments
 (0)