diff --git a/css/settings.css b/css/settings.css index 52f0b3e0..e5e71b9f 100644 --- a/css/settings.css +++ b/css/settings.css @@ -2559,6 +2559,29 @@ li.draggable-item .components-panel__body-toggle.components-button{ border-bottom: 0; padding: 24px 0 0; } +.validate-feeds-actions { + display: flex;; +} +.validate-feeds-actions .spinner:not(.is-active) { + display: none; +} +.validate-feeds-actions .spinner.is-active { + display: inline-block; +} +.feedzy-preview-list { + padding-left: 15px; +} +.feedzy-preview-list li { + list-style: disc; +} +.feedzy-preview-list li a { + text-decoration: none; +} +.feedzy-preview-list li time { + font-size: 11px; + font-weight: 500; + color: #757575; +} @-webkit-keyframes spin { 100% { -webkit-transform: rotate(360deg); } } diff --git a/includes/abstract/feedzy-rss-feeds-admin-abstract.php b/includes/abstract/feedzy-rss-feeds-admin-abstract.php index 54efcbf6..f63601f1 100644 --- a/includes/abstract/feedzy-rss-feeds-admin-abstract.php +++ b/includes/abstract/feedzy-rss-feeds-admin-abstract.php @@ -1598,7 +1598,7 @@ private function get_feed_item_filter( $sc, $sizes, $item, $feed_url, $index, $i 'item_url_follow' => isset( $sc['follow'] ) && 'yes' === $sc['follow'] ? 'nofollow' : '', 'item_url_title' => $item->get_title(), 'item_img' => $content_thumb, - 'item_img_path' => $this->feedzy_retrieve_image( $item, $sc ), + 'item_img_path' => isset( $sc['thumb'] ) && ( 'yes' === $sc['thumb'] || 'auto' === $sc['thumb'] ) ? $this->feedzy_retrieve_image( $item, $sc ) : '', 'item_title' => $content_title, 'item_content_class' => 'rss_content', 'item_content_style' => '', @@ -1866,9 +1866,9 @@ public function feedzy_image_encode( $img_url ) { // Check if img url is set as an URL parameter. $url_tab = wp_parse_url( $img_url ); if ( isset( $url_tab['query'] ) ) { - preg_match_all( '/(http|https):\/\/[^ ]+(\.gif|\.GIF|\.jpg|\.JPG|\.jpeg|\.JPEG|\.png|\.PNG)/', $url_tab['query'], $img_url ); - if ( isset( $img_url[0][0] ) ) { - $img_url = $img_url[0][0]; + preg_match_all( '/(http|https):\/\/[^ ]+(\.gif|\.GIF|\.jpg|\.JPG|\.jpeg|\.JPEG|\.png|\.PNG)/', $url_tab['query'], $matches ); + if ( isset( $matches[0][0] ) ) { + $img_url = $matches[0][0]; } } diff --git a/includes/admin/feedzy-rss-feeds-admin.php b/includes/admin/feedzy-rss-feeds-admin.php index c10cffdd..7fe31b25 100644 --- a/includes/admin/feedzy-rss-feeds-admin.php +++ b/includes/admin/feedzy-rss-feeds-admin.php @@ -708,6 +708,19 @@ public function add_feedzy_post_type_metaboxes() { 'low' ); } + + if ( 'publish' === get_post_status() ) { + add_meta_box( + 'feedzy_category_feeds_preview', + __( 'Feed Preview', 'feedzy-rss-feeds' ), + array( + $this, + 'render_feed_preview', + ), + 'feedzy_categories', + 'side' + ); + } } /** @@ -750,12 +763,106 @@ public function feedzy_category_feed() { ) . '

' . $invalid - . ' -

' . __( 'Learn how to organize feeds in Groups', 'feedzy-rss-feeds' ) . '

+ . ' +
+ + +
'; echo wp_kses( $output, apply_filters( 'feedzy_wp_kses_allowed_html', array() ) ); } + /** + * Render the feed preview metabox. + * + * @return void + */ + public function render_feed_preview() { + // phpcs:ignore WordPress.Security.NonceVerification.Recommended + if ( isset( $_GET['action'] ) && 'edit' !== $_GET['action'] ) { + return; + } + $feeds = get_post_meta( get_the_ID(), 'feedzy_category_feed', true ); + $feed_urls = $this->normalize_urls( $feeds ); + if ( empty( $feed_urls ) ) { + echo '

' . esc_html__( 'No feeds available for preview.', 'feedzy-rss-feeds' ) . '

'; + return; + } + $shortcode = array( + 'sort' => 'date_desc', + 'thumb' => 'no', + 'max' => 0, + ); + $atts = $this->get_short_code_attributes( $shortcode ); + $atts = $this->sanitize_attr( $atts, $feed_urls ); + $sizes = array( + 'width' => 0, + 'height' => 0, + ); + $feed = $this->fetch_feed( $feed_urls, $atts['refresh'], $atts ); + $feed_items = apply_filters( 'feedzy_get_feed_array', array(), $atts, $feed, $feed_urls, $sizes ); + $total_items = count( $feed_items ); + + $max_items_preview_count = 5; + $preview_feed_items = array_slice( $feed_items, 0, $max_items_preview_count ); + ?> + + + +
+ +
+ getTimestamp() + $array->getOffset(); + + return sprintf( + // translators: %s is the time difference. + __( '%s ago', 'feedzy-rss-feeds' ), + human_time_diff( $item_publish_time, $localtime ) + ); + } + /** * Utility method to save metabox data to * custom post type. @@ -841,6 +948,13 @@ public function feedzy_category_columns( $columns ) { $columns['actions'] = __( 'Actions', 'feedzy-rss-feeds' ); } + $new_columns = $this->array_insert_before( 'slug', $columns, 'source', __( 'Source', 'feedzy-rss-feeds' ) ); + if ( $new_columns ) { + $columns = $new_columns; + } else { + $columns['Source'] = __( 'source', 'feedzy-rss-feeds' ); + } + return $columns; } @@ -885,6 +999,33 @@ public function manage_feedzy_category_columns( $column, $post_id ) { case 'actions': echo wp_kses_post( sprintf( '', __( 'Click to remove invalid URLs from this category', 'feedzy-rss-feeds' ), $post_id, __( 'Validate & Clean', 'feedzy-rss-feeds' ) ) ); break; + case 'source': + $src = get_post_meta( $post_id, 'feedzy_category_feed', true ); + if ( empty( $src ) ) { + $src = __( 'No Source Configured', 'feedzy-rss-feeds' ); + } else { + $urls = $this->normalize_urls( $src ); + $src = ''; + if ( is_array( $urls ) ) { + + foreach ( $urls as $key => $url ) { + $too_long = 130; + if ( strlen( $src ) > $too_long ) { + $src .= '...'; + break; + } else { + $src .= '' . $url . ''; + if ( count( $urls ) > $key + 1 ) { + $src .= ', '; + } + } + } + } else { + $src .= '' . esc_html( $urls ) . ''; + } + } + echo wp_kses_post( $src ); + break; default: break; } @@ -1477,6 +1618,23 @@ public function ajax() { } wp_send_json_success( array( 'invalid' => count( $invalid ) ) ); break; + case 'validate_feeds_group': + $feeds = isset( $_POST['feeds'] ) ? sanitize_text_field( wp_unslash( $_POST['feeds'] ) ) : ''; + if ( empty( $feeds ) ) { + wp_send_json_error( __( 'No feeds provided for validation.', 'feedzy-rss-feeds' ) ); + } + $feeds = $this->normalize_urls( $feeds ); + if ( ! is_array( $feeds ) ) { + $feeds = array( $feeds ); + } + $valid = $this->get_valid_source_urls( $feeds, '1_mins', false ); + $invalid = array_diff( $feeds, $valid ); + wp_send_json_success( + array( + 'valid' => $valid, + 'invalid' => $invalid, + ) + ); } } diff --git a/includes/feedzy-rss-feeds-activator.php b/includes/feedzy-rss-feeds-activator.php index 495b04f5..dd1e2542 100644 --- a/includes/feedzy-rss-feeds-activator.php +++ b/includes/feedzy-rss-feeds-activator.php @@ -57,5 +57,35 @@ public static function activate() { ) ); } + self::add_feeds_group(); + } + + /** + * Adds a default feeds group with some popular WordPress-related feeds. + * + * This method checks if a feeds group already exists, and if not, creates one + * with a set of predefined feeds. + * + * @return void + */ + public static function add_feeds_group() { + if ( get_option( '_feedzy_news_group_id', false ) ) { + return; + } + + $group_args = array( + 'post_title' => __( 'News sites', 'feedzy-rss-feeds' ), + 'post_type' => 'feedzy_categories', + 'post_status' => 'publish', + 'post_content' => '', + ); + + $news_group = wp_insert_post( $group_args ); + + $feed_groups = 'https://themeisle.com/blog/feed/, https://wptavern.com/feed/, https://www.wpbeginner.com/feed/, https://wpshout.com/feed/, https://planet.wordpress.org/feed/'; + + add_post_meta( $news_group, 'feedzy_category_feed', $feed_groups ); + + update_option( '_feedzy_news_group_id', $news_group ); } } diff --git a/includes/feedzy-rss-feeds-feed-tweaks.php b/includes/feedzy-rss-feeds-feed-tweaks.php index afd20d87..48d8338e 100644 --- a/includes/feedzy-rss-feeds-feed-tweaks.php +++ b/includes/feedzy-rss-feeds-feed-tweaks.php @@ -466,10 +466,13 @@ function ( $allowed_html = array() ) { 'value' => array(), 'class' => array(), 'data-feedzy' => array(), + 'placeholder' => array(), + 'rows' => array(), ), 'button' => array( - 'class' => array(), - 'id' => array(), + 'class' => array(), + 'id' => array(), + 'disabled' => array(), ), 'p' => array( 'class' => array(), diff --git a/js/categories.js b/js/categories.js index 6c54f7d5..ff2e441a 100644 --- a/js/categories.js +++ b/js/categories.js @@ -4,6 +4,7 @@ $(document).ready(function(){ init(); + validateFeeds(); }); function init(){ @@ -33,4 +34,38 @@ }); } + // validate feeds group. + function validateFeeds() { + $('#feedzy_category_feeds textarea[name="feedzy_category_feed"]').on('input', function() { + if ($(this).val().length < 1) { + $('.validate-feeds').attr('disabled', true); + } else { + $('.validate-feeds').attr('disabled', false); + } + }); + + $('#feedzy_category_feeds .button.validate-feeds').on('click', function(e) { + e.preventDefault(); + var button = $(this); + button.attr('disabled', true); + $('#feedzy_category_feeds .spinner').addClass('is-active'); + $.ajax({ + url: ajaxurl, + method: 'POST', + data: { + action: 'feedzy_categories', + _action: 'validate_feeds_group', + security: feedzy.ajax.security, + feeds: $('textarea[name="feedzy_category_feed"]').val() + }, + success: function(data) { + if (data.success) { + $('textarea[name="feedzy_category_feed"]').val(data.data.valid.join(', ')); + $('#feedzy_category_feeds .spinner').removeClass('is-active'); + } + } + }) + }); + } + })(jQuery, feedzy);