Changeset 3354674
- Timestamp:
- 09/02/2025 12:09:57 PM (6 months ago)
- Location:
- wiser-review/trunk
- Files:
-
- 3 edited
-
readme.txt (modified) (2 diffs)
-
views/wiserw-plugin-settings.php (modified) (1 diff)
-
wiser-review.php (modified) (13 diffs)
Legend:
- Unmodified
- Added
- Removed
-
wiser-review/trunk/readme.txt
r3352566 r3354674 6 6 Tested up to: 6.8 7 7 Requires PHP: 7.4 8 Stable tag: 2. 18 Stable tag: 2.2 9 9 License: GPLv2 or later 10 10 License URI: https://www.gnu.org/licenses/gpl-2.0.html … … 124 124 = 2.1 = 125 125 Bulk Send - Past customer data - Feature improved 126 127 = 2.2 = 128 Rich snippt & SEO improvement with reviews. -
wiser-review/trunk/views/wiserw-plugin-settings.php
r3349699 r3354674 184 184 <p class="submit"> 185 185 <input type="submit" name="wiserrw_plugin_settings" id="submit" class="button button-primary" value="Save Changes"> 186 <a class="button button-primary" href="<?php echo admin_url( 'admin.php?page=wiser-review&wiser_clear_cache' ); ?>">Clear Cache</a> 187 <span style="margin-left:10px;"> 188 <?php 189 wiserrw_check_rest_api(); 190 ?> 191 </span> 186 192 </p> 187 193 </form> -
wiser-review/trunk/wiser-review.php
r3352566 r3354674 4 4 * Plugin URI: https://wiserreview.com 5 5 * Description: Wiser Review module helps you collect and display product reviews, star ratings, and nudges. It also automates review requests via email to boost custom engagement and conversions. 6 * Version: 2. 16 * Version: 2.2 7 7 * Author: Wiser Notify 8 8 * Requires Plugins: woocommerce … … 96 96 */ 97 97 function wiserrw_validate_api( $api_key ) { 98 $url = 'https://api.wiserreview.com/api/woocommerce/verify?key=' . $api_key ;98 $url = 'https://api.wiserreview.com/api/woocommerce/verify?key=' . $api_key.'&wiserrw_hook_url='.get_site_url().'/wp-json/wiserrw/v1/reviews'; 99 99 $args = array( 100 100 'method' => 'GET', … … 318 318 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 319 319 $api_data = wiserrw_validate_api( $api_key ); 320 if (!is_object($api_data) || !isset($api_data->data) || !isset($api_data->data->wsid)) { 321 return; 322 } 320 323 $date_from = strtotime( '-7 days' ); 321 324 $all_orders = wc_get_orders( … … 508 511 509 512 $fp = fopen( $filepath, $is_first_chunk ? 'w' : 'a' ); 510 511 if ( $is_first_chunk ) { 512 fputcsv( $fp, array('Order Id', 'First Name', 'Last Name', 'Phone', 'Email', 'Product Title', 'Product URL', 'Product Image URL', 'Product ID', 'Reviewer Image URL', 'Order Date' ) ); 513 } 514 515 foreach ( $chunk_ids as $order) { 516 $order_id = $order->get_id(); 513 if ( $fp ) { 514 if ( $is_first_chunk ) { 515 fputcsv( $fp, array('Order Id', 'First Name', 'Last Name', 'Phone', 'Email', 'Product Title', 'Product URL', 'Product Image URL', 'Product ID', 'Reviewer Image URL', 'Order Date' ) ); 516 } 517 518 foreach ( $chunk_ids as $order) { 519 $order_id = $order->get_id(); 520 521 $user_id = $order->get_user_id(); 522 /* Product Details */ 523 $items = $order->get_items(); 524 foreach ( $items as $item ) { 525 $product = $item->get_product(); 526 if (!$product) { 527 continue; 528 } 529 530 $product_id = $item->get_product_id(); 531 $product_price = $product->get_price(); 532 $url = get_permalink( $product_id ); 533 $product_name = $item->get_name(); 534 $image = wp_get_attachment_image_src( get_post_thumbnail_id( $product_id ), 'single-post-thumbnail' ); 535 $image_url = is_array($image) ? $image[0] : ''; 536 $reviewer_url = get_avatar_url( $user_id ); 537 $products_str[] = $product->get_name() . "|" . $image_url; 517 538 518 $user_id = $order->get_user_id(); 519 /* Product Details */ 520 $items = $order->get_items(); 521 foreach ( $items as $item ) { 522 $product = $item->get_product(); 523 if (!$product) { 524 continue; 525 } 526 527 $product_id = $item->get_product_id(); 528 $product_price = $product->get_price(); 529 $url = get_permalink( $product_id ); 530 $product_name = $item->get_name(); 531 $image = wp_get_attachment_image_src( get_post_thumbnail_id( $product_id ), 'single-post-thumbnail' ); 532 $image_url = $image[0]; 533 $reviewer_url = get_avatar_url( $user_id ); 534 $products_str[] = $product->get_name() . "|" . $image_url; 535 536 fputcsv( 537 $fp, 538 array( 539 $order_id, 540 $order->get_billing_first_name(), 541 $order->get_billing_last_name(), 542 $order->get_billing_phone(), 543 $order->get_billing_email(), 544 $product->get_name(), 545 $url, 546 $image_url, 547 $order->get_id(), 548 $reviewer_url, 549 $order->get_date_created()->date( 'Y-m-d H:i:s' ), 550 ) 551 ); 552 } 553 } 554 555 fclose( $fp ); 539 fputcsv( 540 $fp, 541 array( 542 $order_id, 543 $order->get_billing_first_name(), 544 $order->get_billing_last_name(), 545 $order->get_billing_phone(), 546 $order->get_billing_email(), 547 $product->get_name(), 548 $url, 549 $image_url, 550 $order->get_id(), 551 $reviewer_url, 552 $order->get_date_created()->date( 'Y-m-d H:i:s' ), 553 ) 554 ); 555 } 556 } 557 558 fclose( $fp ); 559 } 556 560 557 561 $processed = $offset + count( $chunk_ids ); … … 577 581 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 578 582 $api_data = wiserrw_validate_api( $api_key ); 583 if (!$api_data || !isset($api_data->data->wsid) || !isset($api_data->data->automation_id)) { 584 return; // Exit if invalid API data 585 } 579 586 $wiserrw_order_data = array(); 580 587 $wiserrw_line_items = array(); … … 649 656 $filepath = $upload_dir['basedir'] . '/' . $filename; 650 657 $is_first_chunk = 0 === $offset; 651 652 $fp = fopen( $filepath, $is_first_chunk ? 'w' : 'a' );653 654 if ( $is_first_chunk ) {655 fputcsv( $fp, array( 'First Name', 'Last Name', 'Phone', 'Email', 'Product Title', 'Product URL', 'Product Image URL', 'Product ID', 'Reviwer Image URL', 'Order Date' ) );656 }657 658 658 659 foreach ( $chunk_ids as $order ) { … … 816 817 global $wpdb; 817 818 818 return $wpdb->get_var("819 SELECT count(ID)820 FROM {$wpdb->posts}821 WHERE post_type = 'product'822 AND post_status = 'publish'");819 return $wpdb->get_var(" 820 SELECT count(ID) 821 FROM {$wpdb->posts} 822 WHERE post_type = 'product' 823 AND post_status IN ('publish', 'draft')"); 823 824 } 824 825 825 826 function wiserrw_get_products( $page, $per_page ) { 826 global $wpdb; 827 $offset = ( $page - 1 ) * $per_page; 828 829 return $wpdb->get_results( $wpdb->prepare( " 830 SELECT ID, 831 post_title as title, 832 post_name as slug, 833 comment_count 834 FROM {$wpdb->posts} 835 WHERE post_type = 'product' 836 AND post_status = 'publish' 837 LIMIT %d, %d 838 ", $offset, $per_page ), ARRAY_A ); 827 global $wpdb; 828 $offset = ( $page - 1 ) * $per_page; 829 830 return $wpdb->get_results( $wpdb->prepare( " 831 SELECT ID, 832 post_title as title, 833 post_name as slug, 834 post_status, 835 comment_count 836 FROM {$wpdb->posts} 837 WHERE post_type = 'product' 838 AND post_status IN ('publish', 'draft') 839 LIMIT %d, %d 840 ", $offset, $per_page ), ARRAY_A ); 839 841 } 840 842 function wiserrw_sync_products() { … … 845 847 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 846 848 $api_data = wiserrw_validate_api( $api_key ); 849 if (!is_object($api_data) || !isset($api_data->data) || !isset($api_data->data->wsid)) { 850 return; 851 } 847 852 $wsid = $api_data->data->wsid; 848 853 … … 965 970 } 966 971 972 // Get product URL with fallback for draft products 973 $product_url = get_permalink($p_id); 974 if (!$product_url || $prod['post_status'] === 'draft') { 975 if ($prod['post_status'] === 'draft') { 976 $product_url = home_url('/?post_type=product&p=' . $prod['ID']); 977 } else { 978 $shop_page_url = get_permalink(wc_get_page_id('shop')); 979 $product_url = $shop_page_url ? $shop_page_url : home_url('/product/'); 980 $product_url = trailingslashit($product_url) . sanitize_title($prod['title']); 981 } 982 } 983 984 // Get image URL with fallback 985 $image_url = wp_get_attachment_image_src(get_post_thumbnail_id($p_id), 'shop_single'); 986 if (!$image_url) { 987 $image_url = array(wc_placeholder_img_src('shop_single')); 988 } 989 967 990 $product_json = array( 968 991 'pid' => $prod['ID'], … … 971 994 'wsid' => $wsid, 972 995 'pn' => $title, 973 'piu' => isset($image_url[0]) ? $image_url[0] : '',974 'pu' => get_permalink($prod['ID']),996 'piu' => isset($image_url[0]) ? esc_url($image_url[0]) : wc_placeholder_img_src('shop_single'), 997 'pu' => esc_url($product_url), 975 998 'barcode'=> $gtin, 976 'variants' => $variants , // Include variants data999 'variants' => $variants 977 1000 ); 978 1001 … … 1059 1082 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 1060 1083 $api_data = wiserrw_validate_api( $api_key ); 1084 if (!is_object($api_data) || !isset($api_data->data) || !isset($api_data->data->wsid)) { 1085 return; 1086 } 1061 1087 $wsid = $api_data->data->wsid; 1062 1088 $url = $api_host . 'productWebhook/'.$p_id.'?wsid='.$wsid.'&key='.$api_key; … … 1081 1107 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 1082 1108 $api_data = wiserrw_validate_api( $api_key ); 1109 if ( !$api_data || !isset($api_data->data->wsid) ) { 1110 return; // Exit if invalid API data 1111 } 1083 1112 $wsid = $api_data->data->wsid; 1084 1113 $url = $api_host . 'productWebhook?wsid='.$wsid.'&key='.$api_key; … … 1170 1199 add_action( 'woocommerce_after_product_object_save', 'wiserrw_product_update_hook', 99, 1 ); 1171 1200 1201 function wiserrw_custom_endpoints() { 1202 register_rest_route( 1203 'wiserrw/v1', 1204 '/reviews', 1205 array( 1206 array( 1207 'methods' => 'POST', 1208 'permission_callback' => 'wiserrw_api_auth', 1209 'callback' => 'wiserrw_api_callback', 1210 'args' => array(), 1211 ) 1212 ) 1213 ); 1214 } 1215 add_action( 'rest_api_init', 'wiserrw_custom_endpoints' ); 1216 1217 1218 function wiserrw_api_auth( WP_REST_Request $request ) { 1219 $provided = $request->get_header( 'wiserrw-api-key' ); 1220 if ( ! $provided ) { 1221 $provided = $request->get_param( 'wiserrw_api_key' ); 1222 } 1223 1224 if ( ! is_string( $provided ) || $provided === '' ) { 1225 return new WP_Error( 1226 'wiserrw_auth_missing', 1227 'Missing API key. Send it in the API Key header or api_key.', 1228 array( 'status' => 401 ) 1229 ); 1230 } 1231 1232 $wiserrw_api_settings = get_option( 'wiserrw_api_settings', array() ); 1233 if (!is_array($wiserrw_api_settings) || empty($wiserrw_api_settings['wiserrw_api_key'])) { 1234 return new WP_Error( 1235 'wiserrw_auth_config', 1236 'API key not configured.', 1237 array( 'status' => 500 ) 1238 ); 1239 } 1240 1241 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 1242 $valid_keys = array($api_key); 1243 1244 foreach ( $valid_keys as $valid ) { 1245 if ( hash_equals( $valid, $provided ) ) { 1246 return true; 1247 } 1248 } return new WP_Error( 1249 'wiserrw_auth_missing', 1250 'Invalid API key.', 1251 array( 'status' => 401 ) 1252 ); 1253 } 1254 1255 1256 1257 function wiserrw_api_callback( WP_REST_Request $request ) { 1258 1259 $payload = array( 1260 'status' => 'ok', 1261 'method' => $request->get_method(), 1262 'time' => current_time( 'mysql', true ), 1263 'data' => $request->get_json_params() ?: $request->get_params(), 1264 ); 1265 do_action( 'wiserrw_endpoint_called', $request ); 1266 return new WP_REST_Response( $payload, 200 ); 1267 } 1268 1269 1270 function wiserrw_api_response_callback( $request ) { 1271 $data = $request->get_json_params() ?: $request->get_params(); 1272 if (empty($data) || !is_array($data)) { 1273 return; 1274 } 1275 1276 update_option( 'wiserrw_response', $data ); 1277 1278 if (!isset($data['arrPid']) || !is_array($data['arrPid'])) { 1279 return; 1280 } 1281 1282 foreach( $data['arrPid'] as $p_id ) { 1283 if (!empty($p_id) && is_numeric($p_id)) { 1284 wiserrw_generate_schema( $p_id ); 1285 } 1286 } 1287 } 1288 add_action( 'wiserrw_endpoint_called', 'wiserrw_api_response_callback' ); 1289 1290 function wiserrw_generate_schema( $p_id ) { 1291 if (empty($p_id) || !is_numeric($p_id)) { 1292 return; 1293 } 1294 1295 $wiserrw_api_settings = get_option( 'wiserrw_api_settings', array() ); 1296 if (!is_array($wiserrw_api_settings) || empty($wiserrw_api_settings['wiserrw_api_key'])) { 1297 return; 1298 } 1299 1300 $api_key = $wiserrw_api_settings['wiserrw_api_key']; 1301 $api_data = wiserrw_validate_api( $api_key ); 1302 1303 if (!is_object($api_data) || !isset($api_data->data) || !isset($api_data->data->wsid)) { 1304 return; 1305 } 1306 1307 $p_id_arr = array($p_id); // Initialize array properly 1308 $wsid = $api_data->data->wsid; 1309 $url = 'https://rs.wiserreview.com/api/getData'; 1310 1311 for( $i=0; $i<count($p_id_arr); $i++ ){ 1312 $product = get_post($p_id_arr[$i]); 1313 if( !$product ) { 1314 continue; 1315 } 1316 $schema_array = array(); 1317 $body = array( 1318 'arrType' => array('main'), 1319 'pid' => (string)$p_id_arr[$i], 1320 'wsid' => $wsid, 1321 ); 1322 $response = wp_remote_post( 1323 $url, 1324 array( 1325 'method' => 'POST', 1326 'headers' => array( 1327 'Content-Type' => 'application/json', 1328 ), 1329 'body' => wp_json_encode( $body ), 1330 'timeout' => 30, 1331 ) 1332 ); 1333 if ( !is_wp_error( $response ) ) { 1334 $json = wp_remote_retrieve_body( $response ); 1335 $data = json_decode( $json, true ); 1336 foreach( $data['data'] as $row ) { 1337 $schema_array['@context'] = "https://schema.org"; 1338 $schema_array['@type'] = "Product"; 1339 $schema_array['url'] = get_the_permalink($p_id_arr[$i]); 1340 $schema_array['name'] = get_the_title($p_id_arr[$i]); 1341 $schema_array['aggregateRating'] = array( 1342 '@type' => 'AggregateRating', 1343 'ratingValue' => $row['dataCount']['avgrtng'], 1344 'reviewCount' => $row['dataCount']['prtng'], 1345 'bestRating' => '5', 1346 'worstRating' => '1', 1347 ); 1348 foreach( $row['data'] as $review_row ) { 1349 $review = array( 1350 "@type" => "Review", 1351 'author' => array( 1352 '@type' => "Person", 1353 'name' => $review_row['un'] 1354 ), 1355 'reviewBody' => $review_row['orgnlrtxt'], 1356 'reviewRating' => array( 1357 '@type' => 'Rating', 1358 'ratingValue' => $review_row['rtng'], 1359 'bestRating' => '5', 1360 'worstRating' => '1', 1361 ), 1362 'publisher' => array( 1363 "@type" => "Organization", 1364 "name" => "WiserReview" 1365 ) 1366 ); 1367 $schema_array['review'][] = $review; 1368 } 1369 $json_schema = json_encode($schema_array,JSON_UNESCAPED_SLASHES); 1370 update_post_meta( $p_id_arr[$i], 'wiserrw_schema_json', $json_schema ); 1371 } 1372 } 1373 } 1374 } 1375 1376 // Add schema only on WooCommerce single product pages 1377 add_action( 'wp_head', 'wiserrw_product_schema' ); 1378 function wiserrw_product_schema() { 1379 if ( is_product() ) { 1380 global $product; 1381 $p_id = get_queried_object_id(); 1382 if( $p_id ) { 1383 $wiserrw_schema_json = get_post_meta( $p_id, 'wiserrw_schema_json', true ); 1384 if( $wiserrw_schema_json) { 1385 echo '<script id="WiserReviewSchemaJson" type="application/ld+json">'; 1386 echo $wiserrw_schema_json; 1387 echo '</script>'; 1388 } 1389 } 1390 1391 } 1392 } 1393 1394 1395 function wiserrw_check_rest_api() { 1396 $response = wp_remote_get( home_url( '/wp-json/' ) ); 1397 1398 if ( is_wp_error( $response ) ) { 1399 echo 'WooCommerce REST API is not enabled. Enable it in settings and click Save again here..'; 1400 return; 1401 } 1402 1403 $body = wp_remote_retrieve_body( $response ); 1404 $data = json_decode( $body, true ); 1405 1406 if ( !isset( $data['routes']['/wiserrw/v1/reviews'] ) ) { 1407 echo 'Please click Save again to apply the latest changes.'; 1408 } 1409 } 1410 1411 function wiserrw_clear_wp_cache() { 1412 if( isset( $_GET['wiser_clear_cache'] ) ) { 1413 global $wp_fastest_cache; 1414 1415 // WP Rocket 1416 if ( function_exists( 'rocket_clean_domain' ) ) { 1417 rocket_clean_domain(); 1418 } 1419 1420 if ( function_exists( 'wp_cache_flush' ) ) { 1421 wp_cache_flush(); 1422 } 1423 1424 // WP Super Cache 1425 if ( function_exists( 'wp_cache_clear_cache' ) ) { 1426 wp_cache_clear_cache(); 1427 } 1428 1429 // W3 Total Cache 1430 if ( function_exists( 'w3tc_flush_posts' ) ) { 1431 w3tc_flush_posts(); 1432 } 1433 1434 // Cache Enabler 1435 if ( has_action( 'ce_clear_cache' ) ) { 1436 do_action( 'ce_clear_cache' ); 1437 } 1438 1439 // Breeze 1440 if ( class_exists( 'Breeze_PurgeCache' ) ) { 1441 if ( method_exists( 'Breeze_PurgeCache', 'breeze_cache_flush' ) ) { 1442 Breeze_PurgeCache::breeze_cache_flush(); 1443 } 1444 } 1445 1446 if ( class_exists( 'Swift_Performance_Cache' ) ) { 1447 if ( method_exists( 'Swift_Performance_Cache', 'clear_all_cache' ) ) { 1448 Swift_Performance_Cache::clear_all_cache(); 1449 } 1450 } 1451 1452 // WP Fastest Cache 1453 if ( method_exists( 'WpFastestCache', 'deleteCache' ) && ! empty( $wp_fastest_cache ) ) { 1454 $wp_fastest_cache->deleteCache(); 1455 } 1456 1457 // Autoptimize 1458 if ( class_exists( 'WpeCommon' ) ) { 1459 if ( method_exists( 'WpeCommon', 'purge_memcached' ) ) { 1460 WpeCommon::purge_memcached(); 1461 } 1462 if ( method_exists( 'WpeCommon', 'clear_maxcdn_cache' ) ) { 1463 WpeCommon::clear_maxcdn_cache(); 1464 } 1465 if ( method_exists( 'WpeCommon', 'purge_varnish_cache' ) ) { 1466 WpeCommon::purge_varnish_cache(); 1467 } 1468 } 1469 1470 // SGOptimzer 1471 if ( function_exists('sg_cachepress_purge_cache') ) { 1472 sg_cachepress_purge_cache(); 1473 } 1474 } 1475 } 1476 add_action( 'admin_init', 'wiserrw_clear_wp_cache' );
Note: See TracChangeset
for help on using the changeset viewer.