<?php /** * Theme Functions */ // Theme setup require_once get_template_directory() . '/inc/theme-setup.php'; require_once get_template_directory() . '/inc/custom-post-types.php'; require_once get_template_directory() . '/inc/schema-markup.php'; require_once get_template_directory() . '/inc/wholesale-functions.php'; require_once get_template_directory() . '/inc/admin-customizations.php'; require_once get_template_directory() . '/inc/admin-dashboard.php'; // Enqueue assets add_action('wp_enqueue_scripts', 'boya_enqueue_assets'); function boya_enqueue_assets() { wp_enqueue_style('boya-main', get_template_directory_uri() . '/assets/css/main.css', [], '1.0.0'); wp_enqueue_style('boya-fonts', 'https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&family=Merriweather:wght@300;400;700&display=swap', [], null); wp_enqueue_script('boya-main', get_template_directory_uri() . '/assets/js/main.js', [], '1.0.0', true); wp_enqueue_script('boya-carousel', get_template_directory_uri() . '/assets/js/carousel.js', [], '1.0.0', true); wp_enqueue_script('boya-inquiry', get_template_directory_uri() . '/assets/js/inquiry-fix.js', [], '1.0.0', true); } // ===== SEO: Meta Description + Open Graph + Twitter Cards ===== add_action('wp_head', 'boya_seo_head', 1); function boya_seo_head() { $title = wp_get_document_title(); $url = home_url(add_query_arg([])); $site_name = 'Boya Textile'; $description = ''; $image = wp_upload_dir()['baseurl'] . '/2026/06/alibaba/product_1.jpg'; $type = 'website'; if (is_front_page()) { $description = 'Professional sofa cover manufacturer in China. OEM/ODM custom stretch sofa covers, sofa throws, cushion covers, and upholstery fabrics. Factory direct wholesale, OEKO-TEX certified, 15+ years experience.'; $image = wp_upload_dir()['baseurl'] . '/2026/06/alibaba/product_1.jpg'; } elseif (is_singular('boya_product')) { $type = 'product'; $product = get_queried_object(); $description = wp_trim_words(get_the_excerpt($product) ?: get_the_content($product), 25); $thumb = get_the_post_thumbnail_url($product->ID, 'large'); if ($thumb) $image = $thumb; } elseif (is_singular('post')) { $type = 'article'; $post = get_queried_object(); $description = wp_trim_words(get_the_excerpt($post) ?: get_the_content($post), 25); $thumb = get_the_post_thumbnail_url($post->ID, 'large'); if ($thumb) $image = $thumb; } elseif (is_page()) { $page = get_queried_object(); $description = wp_trim_words(get_the_excerpt($page) ?: get_the_content($page), 25); } elseif (is_post_type_archive('boya_product')) { $description = 'Browse our full catalog of sofa covers, sofa throws, cushion covers, and upholstery fabrics. Factory direct wholesale pricing. MOQ from 50 PCS.'; } elseif (is_tax('boya_product_cat')) { $term = get_queried_object(); $description = "Shop wholesale $term->name from Boya Textile. Factory direct pricing, custom sizes, OEM/ODM available. MOQ from 50 PCS."; } $description = esc_attr($description); $title_esc = esc_attr($title); $url_esc = esc_url($url); $image_esc = esc_url($image); ?> <meta name="description" content="<?= $description ?>"> <meta property="og:title" content="<?= $title_esc ?>"> <meta property="og:description" content="<?= $description ?>"> <meta property="og:url" content="<?= $url_esc ?>"> <meta property="og:type" content="<?= $type ?>"> <meta property="og:site_name" content="<?= $site_name ?>"> <meta property="og:image" content="<?= $image_esc ?>"> <meta name="twitter:card" content="summary_large_image"> <meta name="twitter:title" content="<?= $title_esc ?>"> <meta name="twitter:description" content="<?= $description ?>"> <meta name="twitter:image" content="<?= $image_esc ?>"> <?php } /** * REST API: Expose meta fields for boya_product */ add_action('rest_api_init', function() { register_rest_route('boya/v1', '/report', [ 'methods' => 'GET', 'callback' => 'boya_report_callback', 'permission_callback' => function() { return current_user_can('manage_options'); }, ]); register_rest_route('boya/v1', '/mark-featured', [ 'methods' => 'POST', 'callback' => 'boya_mark_featured_callback', 'permission_callback' => function() { return current_user_can('manage_options'); }, ]); register_rest_route('boya/v1', '/deduplicate', [ 'methods' => 'POST', 'callback' => 'boya_deduplicate_callback', 'permission_callback' => function() { return current_user_can('manage_options'); }, ]); register_rest_route('boya/v1', '/bulk-set-data', [ 'methods' => 'POST', 'callback' => 'boya_bulk_set_data_callback', 'permission_callback' => function() { return current_user_can('manage_options'); }, ]); register_rest_route('boya/v1', '/unfeature-all', [ 'methods' => 'POST', 'callback' => function() { $products = get_posts(['post_type'=>'boya_product','posts_per_page'=>-1,'post_status'=>'any']); foreach ($products as $p) delete_post_meta($p->ID, '_boya_featured'); return ['success'=>true]; }, 'permission_callback' => function() { return current_user_can('manage_options'); }, ]); register_rest_route('boya/v1', '/create-1688', [ 'methods' => 'GET', 'callback' => 'boya_create_1688_auto', 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/upload-english-imgs', [ 'methods' => 'GET', 'callback' => 'boya_upload_english_images', 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/replace-main-imgs', [ 'methods' => 'GET', 'callback' => 'boya_replace_main_images', 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/restore-imgs', [ 'methods' => 'GET', 'callback' => function() { $pid = 1113; $original_ids = [1108, 1109, 1110, 1111, 1112]; $spec_ids = [1114, 1115, 1116, 1117]; $gallery = array_merge($original_ids, $spec_ids); update_post_meta($pid, '_boya_gallery_ids', json_encode($gallery)); set_post_thumbnail($pid, $original_ids[0]); return ['success'=>true, 'gallery'=>$gallery]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/upload-translated', [ 'methods' => 'GET', 'callback' => 'boya_upload_translated_images', 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/set-domain', [ 'methods' => 'GET', 'callback' => function() { $domain = 'boyasofababric.com'; update_option('siteurl', 'http://' . $domain); update_option('home', 'http://' . $domain); return [ 'success' => true, 'siteurl' => get_option('siteurl'), 'home' => get_option('home'), ]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/replace-urls', [ 'methods' => 'GET', 'callback' => function() { global $wpdb; $old = 'http://localhost:8080'; $new = 'http://boyasofababric.com'; $count = 0; // Post content $count += (int)$wpdb->query("UPDATE {$wpdb->posts} SET post_content = REPLACE(post_content, '$old', '$new')"); // Post excerpt $count += (int)$wpdb->query("UPDATE {$wpdb->posts} SET post_excerpt = REPLACE(post_excerpt, '$old', '$new')"); // Post meta $count += (int)$wpdb->query("UPDATE {$wpdb->postmeta} SET meta_value = REPLACE(meta_value, '$old', '$new') WHERE meta_value LIKE '%localhost:8080%'"); // Options $count += (int)$wpdb->query("UPDATE {$wpdb->options} SET option_value = REPLACE(option_value, '$old', '$new') WHERE option_value LIKE '%localhost:8080%'"); // WooCommerce/Guid $count += (int)$wpdb->query("UPDATE {$wpdb->posts} SET guid = REPLACE(guid, '$old', '$new')"); return ['success'=>true, 'replaced_fields'=>$count]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/enable-https', [ 'methods' => 'GET', 'callback' => function() { global $wpdb; $old = 'http://boyasofababric.com'; $new = 'https://boyasofababric.com'; $count = 0; $count += (int)$wpdb->query("UPDATE {$wpdb->posts} SET post_content = REPLACE(post_content, '$old', '$new')"); $count += (int)$wpdb->query("UPDATE {$wpdb->posts} SET post_excerpt = REPLACE(post_excerpt, '$old', '$new')"); $count += (int)$wpdb->query("UPDATE {$wpdb->postmeta} SET meta_value = REPLACE(meta_value, '$old', '$new') WHERE meta_value LIKE '%http://boyasofababric.com%'"); $count += (int)$wpdb->query("UPDATE {$wpdb->options} SET option_value = REPLACE(option_value, '$old', '$new') WHERE option_value LIKE '%http://boyasofababric.com%'"); $count += (int)$wpdb->query("UPDATE {$wpdb->posts} SET guid = REPLACE(guid, '$old', '$new')"); return ['success'=>true, 'replaced_fields'=>$count]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/set-email', [ 'methods' => 'POST', 'callback' => function(WP_REST_Request $r) { $email = sanitize_email($r->get_param('email')); if (!$email) return new WP_Error('invalid', 'Valid email required'); update_option('admin_email', $email); // Update user email too $user = get_user_by('email', $email); if (!$user) { $admin = get_users(['role'=>'administrator', 'number'=>1]); if (!empty($admin)) { wp_update_user(['ID'=>$admin[0]->ID, 'user_email'=>$email]); } } return ['success'=>true, 'admin_email'=>get_option('admin_email')]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/set-smtp', [ 'methods' => 'POST', 'callback' => function(WP_REST_Request $r) { $host = sanitize_text_field($r->get_param('host')); $port = intval($r->get_param('port')); $user = sanitize_text_field($r->get_param('user')); $pass = sanitize_text_field($r->get_param('pass')); $from = sanitize_email($r->get_param('from')); $from_name = sanitize_text_field($r->get_param('from_name')); update_option('boya_smtp_host', $host); update_option('boya_smtp_port', $port); update_option('boya_smtp_user', $user); update_option('boya_smtp_pass', $pass ? base64_encode($pass) : ''); update_option('boya_smtp_from', $from); update_option('boya_smtp_from_name', $from_name); return ['success'=>true]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/test-email', [ 'methods' => 'POST', 'callback' => function(WP_REST_Request $r) { $to = sanitize_email($r->get_param('to')); if (!$to) $to = get_option('admin_email'); $subject = 'Boya Textile - Test Email'; $message = 'This is a test email from Boya Textile website. If you received this, email sending is working correctly.'; $sent = wp_mail($to, $subject, $message); return ['success'=>$sent, 'sent_to'=>$to]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/activate-plugin', [ 'methods' => 'POST', 'callback' => function(WP_REST_Request $r) { $slug = sanitize_text_field($r->get_param('slug')); if (!$slug) return new WP_Error('invalid', 'slug required'); require_once ABSPATH . 'wp-admin/includes/plugin.php'; require_once ABSPATH . 'wp-admin/includes/plugin-install.php'; $plugins = get_plugins(); foreach ($plugins as $path => $data) { if (strpos($path, $slug) === 0) { $result = activate_plugin($path); if (is_wp_error($result)) { return ['success'=>false, 'error'=>$result->get_error_message(), 'path'=>$path]; } return ['success'=>true, 'activated'=>$path]; } } return ['success'=>false, 'error'=>'Plugin not found', 'checked_slug'=>$slug]; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/config-smtp', [ 'methods' => 'POST', 'callback' => function(WP_REST_Request $r) { $pass = $r->get_param('pass'); if (!$pass) return new WP_Error('invalid', 'App password required'); $config = [ 'mail' => [ 'mailer' => 'smtp', 'from_email' => 'mosomimark@gmail.com', 'from_name' => 'Boya Textile', 'from_name_force' => true, 'from_email_force' => true, ], 'smtp' => [ 'host' => 'smtp.gmail.com', 'port' => 587, 'encryption' => 'tls', 'autoload' => true, 'user' => 'mosomimark@gmail.com', 'pass' => $pass, 'auto_tls' => true, ], ]; update_option('wp_mail_smtp', $config); return ['success'=>true, 'message' => 'WP Mail SMTP configured with Gmail']; }, 'permission_callback' => '__return_true', ]); register_rest_route('boya/v1', '/debug-smtp', [ 'methods' => 'GET', 'callback' => function() { require_once ABSPATH . WPINC . '/PHPMailer/PHPMailer.php'; require_once ABSPATH . WPINC . '/PHPMailer/SMTP.php'; require_once ABSPATH . WPINC . '/PHPMailer/Exception.php'; $mail = new PHPMailer\PHPMailer\PHPMailer(true); try { $mail->isSMTP(); $mail->Host = '74.125.137.108'; $mail->SMTPAuth = true; $mail->Username = 'mosomimark@gmail.com'; $mail->Password = 'Zjh580870'; $mail->SMTPSecure = 'tls'; $mail->Port = 587; $mail->Helo = 'smtp.gmail.com'; $mail->setFrom('mosomimark@gmail.com', 'Test'); $mail->addAddress('mosomimark@gmail.com'); $mail->Subject = 'SMTP Test'; $mail->Body = 'Test from Boya Textile'; $mail->send(); return ['success'=>true]; } catch (Exception $e) { return ['success'=>false, 'error'=>$mail->ErrorInfo, 'exception'=>$e->getMessage()]; } }, 'permission_callback' => '__return_true', ]); }); function boya_deduplicate_callback(WP_REST_Request $request) { $products = get_posts([ 'post_type' => 'boya_product', 'posts_per_page' => -1, 'post_status' => 'publish', 'orderby' => 'date', 'order' => 'ASC', ]); $seen = []; $deleted = 0; $errors = 0; $details = []; foreach ($products as $p) { $key = strtolower(trim($p->post_title)); if (isset($seen[$key])) { $del = wp_delete_post($p->ID, true); if ($del) { $deleted++; $details[] = "Deleted #{$p->ID}: {$p->post_title}"; } else { $errors++; } } else { $seen[$key] = true; } } return [ 'success' => true, 'deleted' => $deleted, 'errors' => $errors, 'details' => $details, ]; } function boya_bulk_set_data_callback(WP_REST_Request $request) { $products = get_posts([ 'post_type' => 'boya_product', 'posts_per_page' => -1, 'post_status' => 'publish', ]); $updated = 0; foreach ($products as $p) { $title = strtolower($p->post_title); $price = get_post_meta($p->ID, '_boya_wholesale_price', true); $color = get_post_meta($p->ID, '_boya_color_count', true); $size = get_post_meta($p->ID, '_boya_size', true); // Set price based on product type if (!$price || $price <= 0) { if (strpos($title, 'throw') !== false || strpos($title, 'blanket') !== false) { $new_price = 4.50; } elseif (strpos($title, 'cushion') !== false) { $new_price = 3.50; } elseif (strpos($title, 'fabric') !== false || strpos($title, 'polyester') !== false || strpos($title, 'chenille') !== false) { $new_price = 5.00; } else { $new_price = 6.80; } update_post_meta($p->ID, '_boya_wholesale_price', $new_price); $updated++; } // Set default color count if (!$color || $color <= 0) { update_post_meta($p->ID, '_boya_color_count', 12); $updated++; } // Set default SKU if missing $sku = get_post_meta($p->ID, '_sku', true); if (!$sku) { update_post_meta($p->ID, '_sku', 'BTX-' . $p->ID); $updated++; } } return ['success' => true, 'updated' => $updated, 'total' => count($products)]; } function boya_mark_featured_callback(WP_REST_Request $request) { $ids = $request->get_param('ids'); if (!$ids || !is_array($ids)) return new WP_Error('invalid', 'ids array required'); $count = 0; foreach ($ids as $id) { if (update_post_meta((int)$id, '_boya_featured', '1')) $count++; } return ['success' => true, 'updated' => $count]; } function boya_report_callback() { $products = get_posts([ 'post_type' => 'boya_product', 'posts_per_page' => -1, 'post_status' => 'publish', ]); $total = count($products); $with_price = $with_color = $with_size = $featured = 0; $no_price = $no_color = $no_size = []; $titles = []; foreach ($products as $p) { $price = get_post_meta($p->ID, '_boya_wholesale_price', true); $color = get_post_meta($p->ID, '_boya_color_count', true); $size = get_post_meta($p->ID, '_boya_size', true); $feat = get_post_meta($p->ID, '_boya_featured', true); if ($price && $price > 0) $with_price++; else $no_price[] = ['id' => $p->ID, 'title' => $p->post_title]; if ($color && $color > 0) $with_color++; else $no_color[] = ['id' => $p->ID, 'title' => $p->post_title]; if ($size) $with_size++; else $no_size[] = ['id' => $p->ID, 'title' => $p->post_title]; if ($feat === '1') $featured++; $titles[] = $p->post_title; } $dupe_counts = array_count_values($titles); $dupes = array_filter($dupe_counts, function($c) { return $c > 1; }); return [ 'total' => $total, 'with_price' => $with_price, 'with_color' => $with_color, 'with_size' => $with_size, 'featured' => $featured, 'no_price' => array_slice($no_price, 0, 50), 'no_color' => array_slice($no_color, 0, 50), 'no_size' => array_slice($no_size, 0, 50), 'duplicates' => $dupes, ]; } /** * Upload English spec images for 1688 product */ function boya_upload_english_images() { $pid = 1113; require_once ABSPATH . 'wp-admin/includes/media.php'; require_once ABSPATH . 'wp-admin/includes/file.php'; require_once ABSPATH . 'wp-admin/includes/image.php'; $dir = ABSPATH . 'wp-content/uploads/2026/06/double-elephant/'; $files = ['spec1_product_overview.jpg', 'spec2_size_chart.jpg', 'spec3_features.jpg', 'spec4_company_info.jpg']; $new_ids = []; foreach ($files as $f) { $filepath = $dir . $f; if (!file_exists($filepath)) continue; $name = 'Double Elephant - ' . pathinfo($f, PATHINFO_FILENAME); $filename = basename($filepath); // Copy to uploads with correct year/month subdir $upload = wp_upload_bits($filename, null, file_get_contents($filepath)); if ($upload['error']) continue; $attachment = [ 'post_title' => $name, 'post_content' => '', 'post_status' => 'inherit', 'post_mime_type' => mime_content_type($filepath), 'guid' => $upload['url'], ]; $attach_id = wp_insert_attachment($attachment, $upload['file'], $pid); if (is_wp_error($attach_id)) continue; wp_update_attachment_metadata($attach_id, wp_generate_attachment_metadata($attach_id, $upload['file'])); $new_ids[] = $attach_id; } $existing = get_post_meta($pid, '_boya_gallery_ids', true); $gallery = $existing ? json_decode($existing, true) : []; if (!is_array($gallery)) $gallery = []; $gallery = array_merge($gallery, $new_ids); update_post_meta($pid, '_boya_gallery_ids', json_encode($gallery)); return [ 'success' => true, 'product_id' => $pid, 'uploaded' => count($new_ids), 'ids' => $new_ids, 'total_gallery' => count($gallery), ]; } /** * Replace original Chinese 1688 images with English versions for product #1113 */ function boya_replace_main_images() { $pid = 1113; require_once ABSPATH . 'wp-admin/includes/media.php'; require_once ABSPATH . 'wp-admin/includes/file.php'; require_once ABSPATH . 'wp-admin/includes/image.php'; $dir = ABSPATH . 'wp-content/uploads/2026/06/double-elephant/'; $files = ['en_main_hero.jpg', 'en_features.jpg', 'en_size_chart.jpg', 'en_usage.jpg', 'en_company_info.jpg']; $new_ids = []; foreach ($files as $f) { $filepath = $dir . $f; if (!file_exists($filepath)) continue; $name = 'Double Elephant - ' . pathinfo($f, PATHINFO_FILENAME); $upload = wp_upload_bits(basename($filepath), null, file_get_contents($filepath)); if ($upload['error']) continue; $attachment = [ 'post_title' => $name, 'post_content' => '', 'post_status' => 'inherit', 'post_mime_type' => mime_content_type($filepath), 'guid' => $upload['url'], ]; $attach_id = wp_insert_attachment($attachment, $upload['file'], $pid); if (is_wp_error($attach_id)) continue; wp_update_attachment_metadata($attach_id, wp_generate_attachment_metadata($attach_id, $upload['file'])); $new_ids[] = $attach_id; } // Replace first 5 gallery slots with English images, keep remaining $existing = get_post_meta($pid, '_boya_gallery_ids', true); $gallery = $existing ? json_decode($existing, true) : []; if (!is_array($gallery)) $gallery = []; $gallery = array_merge($new_ids, array_slice($gallery, 5)); update_post_meta($pid, '_boya_gallery_ids', json_encode($gallery)); // Set first English image as featured if (!empty($new_ids)) { set_post_thumbnail($pid, $new_ids[0]); } return [ 'success' => true, 'product_id' => $pid, 'uploaded' => count($new_ids), 'ids' => $new_ids, 'gallery_order' => '5 English main images + ' . max(0, count($gallery) - 5) . ' spec images', 'total_gallery' => count($gallery), ]; } /** * Upload translated (English text overlaid on original) images for product #1113 */ function boya_upload_translated_images() { $pid = 1113; require_once ABSPATH . 'wp-admin/includes/media.php'; require_once ABSPATH . 'wp-admin/includes/file.php'; require_once ABSPATH . 'wp-admin/includes/image.php'; $dir = ABSPATH . 'wp-content/uploads/2026/06/double-elephant/'; $files = ['en_product_1.jpg', 'en_product_2.jpg', 'en_product_3.jpg', 'en_product_4.jpg', 'en_product_5.jpg']; $new_ids = []; foreach ($files as $f) { $filepath = $dir . $f; if (!file_exists($filepath)) continue; $name = 'Double Elephant - ' . pathinfo($f, PATHINFO_FILENAME); $upload = wp_upload_bits(basename($filepath), null, file_get_contents($filepath)); if ($upload['error']) continue; $attachment = [ 'post_title' => $name, 'post_content' => '', 'post_status' => 'inherit', 'post_mime_type' => mime_content_type($filepath), 'guid' => $upload['url'], ]; $attach_id = wp_insert_attachment($attachment, $upload['file'], $pid); if (is_wp_error($attach_id)) continue; wp_update_attachment_metadata($attach_id, wp_generate_attachment_metadata($attach_id, $upload['file'])); $new_ids[] = $attach_id; } // Replace first 5 gallery slots, keep spec images $existing = get_post_meta($pid, '_boya_gallery_ids', true); $gallery = $existing ? json_decode($existing, true) : []; if (!is_array($gallery)) $gallery = []; $gallery = array_merge($new_ids, array_slice($gallery, 5)); update_post_meta($pid, '_boya_gallery_ids', json_encode($gallery)); if (!empty($new_ids)) set_post_thumbnail($pid, $new_ids[0]); return [ 'success' => true, 'product_id' => $pid, 'uploaded' => count($new_ids), 'ids' => $new_ids, 'gallery' => '5 translated main images + ' . max(0, count($gallery) - 5) . ' spec images', 'total_gallery' => count($gallery), ]; } /** * Standard sofa throw sizes: fixed width 180cm, lengths 130-480cm */ function boya_standard_sizes() { return [ '180×130 cm (4.3 ft)', '180×180 cm (6 ft)', '180×230 cm (7.5 ft)', '180×260 cm (8.5 ft)', '180×300 cm (10 ft)', '180×340 cm (11 ft)', '180×380 cm (12.5 ft)', '180×420 cm (14 ft)', '180×460 cm (15 ft)', '180×480 cm (16 ft)', ]; } /** * Standard cushion cover sizes */ function boya_cushion_sizes() { return [ '70×70 cm', '70×90 cm', '70×120 cm', '70×150 cm', '70×180 cm', '70×210 cm', '90×70 cm', '90×90 cm', '90×120 cm', '90×160 cm', '90×180 cm', '90×210 cm', '90×240 cm', '90×260 cm', '90×280 cm', '110×110 cm', '110×160 cm', '110×180 cm', '110×210 cm', '110×240 cm', '110×260 cm', '110×280 cm', '120×160 cm (Chaise)', '120×180 cm (Chaise)', '45×45 cm (Pillow)', '30×50 cm (Pillow)', ]; } /** * Create 1688 product — Double Elephant Faux Leather Cushion Cover */ function boya_create_1688_auto() { // ── Download + upload images from 1688 ── $image_urls = [ 'https://cbu01.alicdn.com/img/ibank/O1CN018ZST3z1l0Il7I5y2x_!!2215790904756-0-cib.jpg_.webp', 'https://cbu01.alicdn.com/img/ibank/O1CN0164CtTL1l0Il6Pub4T_!!2215790904756-0-cib.jpg_.webp', 'https://cbu01.alicdn.com/img/ibank/O1CN01PR3RZ91l0Il6hgM7E_!!2215790904756-0-cib.jpg_.webp', 'https://cbu01.alicdn.com/img/ibank/O1CN01Qbtf1i1l0Il7Hw1az_!!2215790904756-0-cib.jpg_.webp', 'https://cbu01.alicdn.com/img/ibank/O1CN01DUpZdS1l0Il6hhYyL_!!2215790904756-0-cib.jpg_.webp', ]; require_once ABSPATH . 'wp-admin/includes/media.php'; require_once ABSPATH . 'wp-admin/includes/file.php'; require_once ABSPATH . 'wp-admin/includes/image.php'; $gallery_ids = []; foreach ($image_urls as $i => $url) { $name = 'Double-Elephant-Faux-Leather-Cushion-Cover-' . ($i + 1); $id = media_sideload_image($url, 0, $name, 'id'); if (!is_wp_error($id) && $id) { $gallery_ids[] = $id; } } // ── Build sizes string ── $size_list = boya_cushion_sizes(); $size_str = implode(', ', array_slice($size_list, 0, 10)) . ' and more (26 sizes total)'; // ── Create product ── $pid = wp_insert_post([ 'post_type' => 'boya_product', 'post_title' => 'Double Elephant Faux Leather Cushion Cover — Solid & Cute Animal Pattern', 'post_status' => 'publish', 'post_content' => '<h3>Product Overview</h3> <p>Premium faux leather (PU leather) cushion cover from Double Elephant collection. Features a light luxury style with solid color and cute animal pattern options. Suitable for all sofa types — living room, bedroom, and office seating.</p> <h3>Key Features</h3> <ul> <li><strong>Material:</strong> High-quality faux leather (PU) — soft touch, durable, easy to clean</li> <li><strong>Pattern:</strong> Solid colors + cute animal patterns</li> <li><strong>Style:</strong> Light luxury — modern and elegant design</li> <li><strong>Non-Slip:</strong> Non-slip backing keeps cushion cover in place</li> <li><strong>Easy Care:</strong> Wipe clean with damp cloth — low maintenance</li> <li><strong>Customizable:</strong> OEM sizes, colors, and patterns available</li> </ul> <h3>Available Options</h3> <ul> <li><strong>Sizes:</strong> ' . $size_str . '</li> <li><strong>Colors:</strong> Brown, Green, Black, Cream White (Double Elephant series)</li> <li><strong>Custom:</strong> Custom sizes at 50 RMB/sqm — contact for details</li> <li><strong>Pillow Covers:</strong> 45×45cm and 30×50cm available</li> </ul> <h3>Specifications</h3> <table> <tr><td>Product No.</td><td>Double Elephant</td></tr> <tr><td>Material</td><td>Faux Leather (PU)</td></tr> <tr><td>Pattern</td><td>Solid, Cute Animal</td></tr> <tr><td>Style</td><td>Light Luxury</td></tr> <tr><td>Customizable</td><td>Yes — Sizes, Color, Fabric, Logo</td></tr> <tr><td>Sofa Type</td><td>Universal — fits all sofa types</td></tr> <tr><td>Chaise Options</td><td>120×160cm, 120×180cm with slit</td></tr> </table>', 'meta_input' => [ '_boya_wholesale_price' => '5.20', '_boya_color_count' => '4', '_boya_size' => $size_str, '_boya_featured' => '1', '_sku' => 'BTX-DE001', '_boya_gallery_ids' => json_encode($gallery_ids), ], ]); if (is_wp_error($pid)) { return ['error' => $pid->get_error_message()]; } // Set featured image + category if (!empty($gallery_ids)) { set_post_thumbnail($pid, $gallery_ids[0]); } // Assign to Cushion Covers category if it exists $cushion_cat = get_term_by('slug', 'cushion-covers', 'boya_product_cat'); if ($cushion_cat) { wp_set_object_terms($pid, [$cushion_cat->term_id], 'boya_product_cat'); } return [ 'success' => true, 'product_id' => $pid, 'title' => 'Double Elephant Faux Leather Cushion Cover', 'gallery_ids' => $gallery_ids, 'edit_url' => admin_url('post.php?post=' . $pid . '&action=edit'), 'size_count' => count($size_list), ]; } /** * SMTP Email Configuration */ add_action('phpmailer_init', 'boya_smtp_config'); function boya_smtp_config($phpmailer) { $host = get_option('boya_smtp_host'); if (!$host) return; $phpmailer->isSMTP(); $phpmailer->Host = $host; $phpmailer->Port = get_option('boya_smtp_port', 587); $phpmailer->SMTPAuth = true; $phpmailer->Username = get_option('boya_smtp_user'); $pass = get_option('boya_smtp_pass'); if ($pass) $phpmailer->Password = base64_decode($pass); $phpmailer->SMTPSecure = 'tls'; $phpmailer->From = get_option('boya_smtp_from', get_option('admin_email')); $phpmailer->FromName = get_option('boya_smtp_from_name', 'Boya Textile'); } // ===== P1: Exit-Intent Popup ===== add_action('wp_footer', 'boya_exit_popup'); function boya_exit_popup() { if (is_admin()) return; ?> <style> #boya-exit-popup{position:fixed;top:0;left:0;right:0;bottom:0;background:rgba(0,0,0,0.6);z-index:99998;display:none;align-items:center;justify-content:center} #boya-exit-popup.show{display:flex} #boya-exit-popup .popup-inner{background:#fff;border-radius:12px;padding:2rem;max-width:480px;width:90%;position:relative;text-align:center;box-shadow:0 20px 60px rgba(0,0,0,0.2)} #boya-exit-popup .popup-close{position:absolute;top:10px;right:14px;font-size:24px;cursor:pointer;color:#999;border:none;background:none} #boya-exit-popup h3{font-size:1.3rem;color:#2c3e50;margin:0 0 0.5rem} #boya-exit-popup p{color:#666;font-size:0.9rem;margin:0 0 1.25rem} #boya-exit-popup input,#boya-exit-popup textarea{width:100%;padding:10px 14px;border:1px solid #ddd;border-radius:6px;margin-bottom:10px;font-size:0.9rem;box-sizing:border-box;font-family:inherit} #boya-exit-popup textarea{height:80px;resize:none} #boya-exit-popup button{background:#c4956a;color:#fff;border:none;padding:12px 24px;border-radius:6px;font-size:0.95rem;font-weight:600;cursor:pointer;width:100%} #boya-exit-popup button:hover{background:#b07d50} #boya-exit-popup .trust-line{font-size:0.75rem;color:#999;margin-top:10px} </style> <div id="boya-exit-popup"> <div class="popup-inner"> <button class="popup-close" onclick="document.getElementById('boya-exit-popup').classList.remove('show')">&times;</button> <h3>👋 Wait! Don't Leave Yet</h3> <p>Get a <strong>free sample</strong> and <strong>factory price quote</strong> — we reply within 2 hours!</p> <form id="boya-exit-form"> <input type="text" name="name" placeholder="Your Name" required> <input type="email" name="email" placeholder="Your Email" required> <input type="text" name="product" placeholder="Product You're Interested In"> <textarea name="message" placeholder="Tell us what you need..."></textarea> <button type="submit">📩 Get Quote</button> </form> <div class="trust-line">🛡️ Trade Assurance | ⏱ Reply within 2 hours | 📦 Free sample available</div> </div> </div> <script> document.addEventListener('mouseleave', function(e){ if(e.clientY < 5 && !sessionStorage.getItem('boya_exit_shown')){ document.getElementById('boya-exit-popup').classList.add('show'); sessionStorage.setItem('boya_exit_shown','1'); } }); document.getElementById('boya-exit-form')?.addEventListener('submit', function(e){ e.preventDefault(); var btn = this.querySelector('button'); btn.textContent = 'Sending...'; btn.disabled = true; var data = new FormData(this); data.append('action', 'boya_exit_inquiry'); fetch('/wp-admin/admin-ajax.php', { method:'POST', body:data }) .then(r=>r.json()).then(d=>{ if(d.success){ btn.textContent='✅ Sent! We\'ll contact you soon'; setTimeout(function(){ document.getElementById('boya-exit-popup').classList.remove('show'); },2000); } else { btn.textContent='📩 Try Again'; btn.disabled=false; } }).catch(function(){ btn.textContent='📩 Try Again'; btn.disabled=false; }); }); </script> <?php } add_action('wp_ajax_nopriv_boya_exit_inquiry', 'boya_handle_exit_inquiry'); add_action('wp_ajax_boya_exit_inquiry', 'boya_handle_exit_inquiry'); function boya_handle_exit_inquiry() { $name = sanitize_text_field($_POST['name'] ?? ''); $email = sanitize_email($_POST['email'] ?? ''); $product = sanitize_text_field($_POST['product'] ?? ''); $message = sanitize_textarea_field($_POST['message'] ?? ''); $body = "Name: $name\nEmail: $email\nProduct: $product\nMessage: $message"; wp_mail('mosomimark@gmail.com', 'Exit Popup Inquiry - Boya Textile', $body); wp_send_json_success(); } // ===== P2: Customer Cases Post Type ===== add_action('init', 'boya_cases_cpt'); function boya_cases_cpt() { register_post_type('boya_case', [ 'labels' => ['name'=>'Customer Cases','singular_name'=>'Case','add_new'=>'Add Case','add_new_item'=>'Add New Case','edit_item'=>'Edit Case'], 'public' => true, 'has_archive' => true, 'rewrite' => ['slug'=>'customer-cases'], 'supports' => ['title','editor','thumbnail','excerpt'], 'menu_icon' => 'dashicons-testimonial', 'show_in_rest' => true, ]); } // ===== P2: Product Video Support ===== add_action('add_meta_boxes', 'boya_video_metabox'); function boya_video_metabox() { add_meta_box('boya_video', 'Product Video URL (YouTube)', function($post) { $val = get_post_meta($post->ID, '_boya_video_url', true); echo '<input type="url" name="_boya_video_url" value="'.esc_attr($val).'" style="width:100%;padding:8px" placeholder="https://www.youtube.com/watch?v=...">'; }, 'boya_product', 'side'); } add_action('save_post', function($id) { if (isset($_POST['_boya_video_url'])) update_post_meta($id, '_boya_video_url', esc_url_raw($_POST['_boya_video_url'])); }); // AJAX inquiry handler add_action('wp_ajax_boya_ajax_inquiry', 'boya_handle_ajax_inquiry'); add_action('wp_ajax_nopriv_boya_ajax_inquiry', 'boya_handle_ajax_inquiry'); function boya_handle_ajax_inquiry() { $name = sanitize_text_field($_POST['name'] ?? ''); $company = sanitize_text_field($_POST['company'] ?? ''); $email = sanitize_email($_POST['email'] ?? ''); $phone = sanitize_text_field($_POST['phone'] ?? ''); $product = sanitize_text_field($_POST['product'] ?? ''); $message = sanitize_textarea_field($_POST['message'] ?? ''); $body = "Name: $name\nCompany: $company\nEmail: $email\nPhone: $phone\nProduct: $product\n\nMessage:\n$message"; $sent = mail('mosomimark@gmail.com', '[Boya Inquiry] '.($name ?: 'New Inquiry'), $body, "From: Boya Textile <noreply@boyasofafabric.com>\r\n"); if ($sent) wp_send_json_success(); else wp_send_json_error('Mail server error. Please email us directly.'); } // BOYA v2.0 — Safe optimizations add_filter('wp_get_attachment_url', function($u,$i){$u=str_replace('tablecloth2.jpg/factory/','factory/',$u);$u=str_replace('tablecloth2.jpg/wechat-qr.jpg','wechat-qr.jpg',$u);return $u;},10,2); add_action('template_redirect', function(){ if (is_admin()) return; ob_start(function($b){ $b = str_replace('tel:+8618167140260', 'tel:+8618167140260', $b); $b = str_replace('+861****0260', '+86 18167140260', $b); $b = str_replace('/wp-content/uploads/2026/06/tablecloth2.jpg/factory/', '/wp-content/uploads/2026/06/factory/', $b); $b = str_replace('/wp-content/uploads/2026/06/tablecloth2.jpg/wechat-qr.jpg', '/wp-content/uploads/2026/06/wechat-qr.jpg', $b); return $b; }); }); add_action('init',function(){remove_action('wp_head','print_emoji_detection_script',7);remove_action('wp_print_styles','print_emoji_styles');}); add_action('wp_default_scripts',function($s){if(!is_admin()&&isset($s->registered['jquery'])){$s->registered['jquery']->deps=array_diff($s->registered['jquery']->deps,['jquery-migrate']);}}); add_action('wp_enqueue_scripts',function(){wp_dequeue_style('wp-block-library');wp_dequeue_style('global-styles');},100); add_action('wp_head',function(){if(is_front_page()){echo '<meta name="description" content="Professional sofa cover manufacturer in China since 2010. OEM/ODM custom sofa covers, throws, cushion covers. Factory direct, OEKO-TEX certified, MOQ from 50 PCS.">';}},0); add_filter('document_title_parts',function($t){if(is_front_page()){$t['title']='Professional Sofa Cover Manufacturer China | Boya Textile';}if(is_page('about-us')){$t['title']='About Boya Textile — China Sofa Cover Manufacturer Since 2010';}return $t;}); add_action('send_headers',function(){if(!is_admin()){header('X-Content-Type-Options:nosniff');header('X-Frame-Options:SAMEORIGIN');}}); remove_action('wp_head','wp_generator');add_filter('the_generator','__return_empty_string'); add_filter('wp_get_attachment_image_attributes',function($a){if(!isset($a['loading'])){$a['loading']='lazy';}return $a;},10,3); // BOYA v3.0 B2B SEO + conversion enhancements add_action('wp_head', 'boya_v3_structured_data', 20); function boya_v3_structured_data() { if (is_admin()) return; $logo = 'https://boyasofafabric.com/wp-content/uploads/2026/06/boya-logo.jpg'; $schema = []; $schema[] = [ '@context' => 'https://schema.org', '@type' => 'Organization', '@id' => home_url('/#organization'), 'name' => 'Boya Textile', 'legalName' => 'Haining Xucun Town Boya Textile Business Department', 'url' => home_url('/'), 'logo' => $logo, 'description' => 'China manufacturer of custom sofa covers, sofa throws, cushion covers, tablecloths and home textile products for B2B wholesale buyers.', 'foundingDate' => '2010', 'email' => 'mosomimark@gmail.com', 'telephone' => '+86 18167140260', 'contactPoint' => [[ '@type' => 'ContactPoint', 'telephone' => '+86 18167140260', 'contactType' => 'sales', 'email' => 'mosomimark@gmail.com', 'availableLanguage' => ['English','Chinese'] ]], 'address' => ['@type'=>'PostalAddress','addressLocality'=>'Haining','addressRegion'=>'Zhejiang','addressCountry'=>'CN'], 'sameAs' => ['https://hnbyfz.en.alibaba.com/','https://www.youtube.com/@Jinghuizheng-r1j'] ]; $schema[] = ['@context'=>'https://schema.org','@type'=>'WebSite','@id'=>home_url('/#website'),'url'=>home_url('/'),'name'=>'Boya Textile','publisher'=>['@id'=>home_url('/#organization')],'potentialAction'=>['@type'=>'SearchAction','target'=>home_url('/?s={search_term_string}'),'query-input'=>'required name=search_term_string']]; if (is_front_page()) { $schema[] = ['@context'=>'https://schema.org','@type'=>'FAQPage','@id'=>home_url('/#faq'),'mainEntity'=>[ ['@type'=>'Question','name'=>'What is the MOQ for custom sofa covers?','acceptedAnswer'=>['@type'=>'Answer','text'=>'Our MOQ starts from 50 PCS for many sofa cover, cushion cover and home textile products. Exact MOQ depends on material, size, color and packaging requirements.']], ['@type'=>'Question','name'=>'Do you support OEM and ODM orders?','acceptedAnswer'=>['@type'=>'Answer','text'=>'Yes. We support OEM/ODM customization including fabric, size, color, pattern, logo label, washing label and retail packaging.']], ['@type'=>'Question','name'=>'Can you provide samples before bulk production?','acceptedAnswer'=>['@type'=>'Answer','text'=>'Yes. We can provide samples for quality checking and size confirmation before bulk production.']], ['@type'=>'Question','name'=>'Which products do you manufacture?','acceptedAnswer'=>['@type'=>'Answer','text'=>'We manufacture sofa covers, sofa throws, cushion covers, tablecloths, throw pillows, upholstery fabrics and related home textile products.']], ['@type'=>'Question','name'=>'How fast can you reply to a quotation request?','acceptedAnswer'=>['@type'=>'Answer','text'=>'For clear product requirements, we usually reply within 24 hours. You can contact us by email or WhatsApp for faster communication.']] ]]; } if (is_singular('boya_product')) { global $post; $img = get_the_post_thumbnail_url($post->ID, 'large'); $schema[] = ['@context'=>'https://schema.org','@type'=>'Product','name'=>get_the_title($post),'description'=>wp_strip_all_tags(get_the_excerpt($post) ?: wp_trim_words($post->post_content, 40)),'image'=>$img ?: $logo,'brand'=>['@type'=>'Brand','name'=>'Boya Textile'],'manufacturer'=>['@id'=>home_url('/#organization')],'sku'=>get_post_meta($post->ID, '_sku', true) ?: ('BTX-' . $post->ID),'offers'=>['@type'=>'Offer','priceCurrency'=>'USD','availability'=>'https://schema.org/InStock','url'=>get_permalink($post)]]; } foreach ($schema as $item) echo "\n<script type=\"application/ld+json\">" . wp_json_encode($item, JSON_UNESCAPED_SLASHES|JSON_UNESCAPED_UNICODE) . "</script>\n"; } add_action('wp_footer', 'boya_v3_home_conversion_sections', 5); function boya_v3_home_conversion_sections() { if (!is_front_page() || is_admin()) return; ?> <style>.boya-v3-seo{background:#f8f5f0;padding:48px 20px;font-family:inherit}.boya-v3-wrap{max-width:1180px;margin:0 auto}.boya-v3-grid{display:grid;grid-template-columns:repeat(4,minmax(0,1fr));gap:16px;margin:24px 0}.boya-v3-card{background:#fff;border:1px solid #eadfce;border-radius:14px;padding:20px;box-shadow:0 8px 24px rgba(0,0,0,.04)}.boya-v3-card strong{display:block;color:#2c3e50;margin-bottom:6px}.boya-v3-cta{background:#2c3e50;color:#fff;border-radius:18px;padding:28px;margin-top:26px;display:flex;gap:18px;align-items:center;justify-content:space-between;flex-wrap:wrap}.boya-v3-cta a{background:#c4956a;color:#fff;padding:13px 22px;border-radius:8px;text-decoration:none;font-weight:700}.boya-v3-faq{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:14px;margin-top:20px}.boya-v3-faq details{background:#fff;border:1px solid #eadfce;border-radius:12px;padding:16px}.boya-v3-faq summary{font-weight:700;cursor:pointer;color:#2c3e50}@media(max-width:800px){.boya-v3-grid,.boya-v3-faq{grid-template-columns:1fr}.boya-v3-cta{display:block}.boya-v3-cta a{display:inline-block;margin-top:14px}}</style> <section class="boya-v3-seo" aria-label="Boya Textile manufacturing advantages and FAQ"><div class="boya-v3-wrap"><h2>Custom Sofa Covers & Home Textiles from China Factory</h2><p>Boya Textile supports wholesale buyers, furniture brands, Amazon sellers and importers with OEM/ODM sofa covers, cushion covers, sofa throws, tablecloths and upholstery fabrics. Send your size, fabric, color and packaging requirements to get a factory quotation.</p><div class="boya-v3-grid"><div class="boya-v3-card"><strong>MOQ from 50 PCS</strong><span>Flexible trial orders for new designs and market testing.</span></div><div class="boya-v3-card"><strong>OEM/ODM Support</strong><span>Custom size, color, fabric, logo label and packaging.</span></div><div class="boya-v3-card"><strong>Factory Direct</strong><span>Direct communication with manufacturing and export team.</span></div><div class="boya-v3-card"><strong>OEKO-TEX Available</strong><span>Material and quality options for international buyers.</span></div></div><h2>Frequently Asked Questions</h2><div class="boya-v3-faq"><details open><summary>What is your MOQ?</summary><p>MOQ starts from 50 PCS for many items. Custom fabric, logo and packaging may require a higher MOQ.</p></details><details><summary>Can you make OEM sofa covers?</summary><p>Yes. We can customize size, fabric, color, pattern, brand label, washing label and packaging.</p></details><details><summary>Can I get samples first?</summary><p>Yes. Samples can be arranged before bulk production to confirm material, size and workmanship.</p></details><details><summary>How do I get a quote?</summary><p>Send product photos, size, fabric requirement, quantity and destination country by email or WhatsApp.</p></details></div><div class="boya-v3-cta"><div><strong>Need a custom sofa cover quotation?</strong><br>Send your design or product requirements. We usually reply within 24 hours.</div><a href="https://wa.me/8618167140260" target="_blank" rel="noopener">Get Factory Quote</a></div></div></section> <?php } // BOYA v4.0 SEO consolidation + category archive landing pages // Added by Hermes Agent: fixes B2B SEO titles/meta/canonical/schema and product-category 404 pages. add_action('after_setup_theme', function () { if (function_exists('boya_seo_head')) { remove_action('wp_head', 'boya_seo_head', 1); } if (function_exists('boya_v3_structured_data')) { remove_action('wp_head', 'boya_v3_structured_data', 20); } }, 20); function boya_v4_request_category_term() { $path = trim(parse_url($_SERVER['REQUEST_URI'] ?? '', PHP_URL_PATH), '/'); if (!preg_match('#^product-category/([^/]+)/?$#', $path, $m)) return null; $term = get_term_by('slug', sanitize_title($m[1]), 'boya_product_cat'); return ($term && !is_wp_error($term)) ? $term : null; } function boya_v4_meta_context() { $site = 'Boya Textile'; $path = trim(parse_url($_SERVER['REQUEST_URI'] ?? '', PHP_URL_PATH), '/'); $title = 'Professional Sofa Cover Manufacturer China | Boya Textile'; $desc = 'Boya Textile is a China home textile manufacturer supplying custom sofa covers, cushion covers, tablecloths and upholstery fabrics for B2B wholesale buyers. OEM/ODM, factory direct, MOQ from 50 PCS.'; $canonical = home_url('/'); $type = 'website'; $image = 'https://boyasofafabric.com/wp-content/uploads/2026/06/alibaba/product_1.jpg'; $term = boya_v4_request_category_term(); if (is_front_page()) { $title = 'Custom Sofa Cover Manufacturer China | OEM Sofa Covers Wholesale'; $desc = 'Custom sofa cover manufacturer in China since 2010. OEM/ODM stretch sofa covers, cushion covers, tablecloths and upholstery fabrics. Factory direct wholesale, OEKO-TEX, MOQ from 50 PCS.'; $canonical = home_url('/'); } elseif (is_post_type_archive('boya_product') || $path === 'products') { $title = 'Wholesale Sofa Covers, Cushion Covers & Upholstery Fabrics | Boya Textile'; $desc = 'Browse Boya Textile products including sofa covers, cushion covers, tablecloths, throw pillows and upholstery fabrics. Factory direct wholesale pricing, custom sizes and OEM/ODM support.'; $canonical = home_url('/products/'); } elseif ($term || is_tax('boya_product_cat')) { if (!$term && is_tax('boya_product_cat')) $term = get_queried_object(); $name = $term ? $term->name : 'Home Textile Products'; $slug = $term ? $term->slug : ''; $title = 'Wholesale ' . $name . ' Manufacturer China | Boya Textile'; $desc = 'Source wholesale ' . $name . ' from Boya Textile, China home textile factory. Custom materials, sizes, colors and packaging for importers, retailers and e-commerce brands. MOQ from 50 PCS.'; $canonical = home_url('/product-category/' . $slug . '/'); } elseif (is_singular('boya_product')) { global $post; $product_title = get_the_title($post); $terms = wp_get_post_terms($post->ID, 'boya_product_cat', ['fields' => 'names']); $family = (!is_wp_error($terms) && !empty($terms)) ? $terms[0] : 'Sofa Cover'; $short_title = mb_strlen($product_title) > 68 ? mb_substr($product_title, 0, 65) . '…' : $product_title; $title = $short_title . ' | Boya Textile'; $raw = wp_strip_all_tags(get_the_excerpt($post) ?: get_post_field('post_content', $post->ID)); $raw = preg_replace('/\s+/', ' ', $raw); $desc = $family . ' from Boya Textile factory for B2B buyers. Confirm size, fabric, color, logo, packaging and MOQ before wholesale or OEM production.'; $canonical = get_permalink($post); $type = 'product'; $thumb = get_the_post_thumbnail_url($post->ID, 'large'); if ($thumb) $image = $thumb; } elseif (is_singular('post')) { global $post; $post_title = get_the_title($post); $short_title = mb_strlen($post_title) > 68 ? mb_substr($post_title, 0, 65) . '...' : $post_title; $title = $short_title . ' | Boya Textile'; $raw = wp_strip_all_tags(get_the_excerpt($post) ?: get_post_field('post_content', $post->ID)); $desc = wp_trim_words(preg_replace('/\s+/', ' ', $raw), 28, ''); $canonical = get_permalink($post); $type = 'article'; $thumb = get_the_post_thumbnail_url($post->ID, 'large'); if ($thumb) $image = $thumb; } elseif (is_page('blog') { { $title = 'B2B Home Textile Blog Directory | Fabric Sourcing Guides | Boya Textile'; $desc = 'Browse Boya Textile B2B blog guides by topic: fabric sourcing, upholstery performance, OEM sofa cover manufacturing, cleaning, care, commercial projects and market trends.'; $canonical = home_url('/blog/'); } elseif (is_page('contact')) { $title = 'Contact Boya Textile | Get Wholesale Sofa Cover Quote'; $desc = 'Contact Boya Textile for custom sofa covers, cushion covers, tablecloths and upholstery fabric wholesale quotes. Fast response for OEM/ODM orders, samples and factory pricing.'; $canonical = home_url('/contact/'); } elseif (is_page('about-us')) { $title = 'About Boya Textile | China Sofa Cover & Home Textile Factory'; $desc = 'Learn about Boya Textile, a China manufacturer focused on sofa covers, cushion covers, tablecloths and upholstery fabrics for global wholesale and OEM/ODM buyers.'; $canonical = home_url('/about-us/'); } elseif (is_page('factory-tour')) { $title = 'Factory Tour | Boya Textile Sofa Cover Manufacturing China'; $desc = 'See Boya Textile factory production, fabric inspection, cutting, sewing and packaging processes for custom sofa covers and B2B home textile orders.'; $canonical = home_url('/factory-tour/'); } elseif (is_page('oem-custom-services')) { $title = 'OEM Custom Sofa Cover Services | Private Label Home Textiles'; $desc = 'OEM/ODM custom sofa cover and home textile service from Boya Textile. Custom fabrics, sizes, colors, labels and packaging for wholesale buyers.'; $canonical = home_url('/oem-custom-services/'); } elseif (is_page('faq')) { $title = 'B2B Sofa Cover FAQ | 200 Wholesale & OEM Questions | Boya Textile'; $desc = 'Answers to 200 B2B questions about sofa cover wholesale, MOQ, OEM customization, fabrics, samples, production, packaging, shipping, quality control and reorders from Boya Textile.'; $canonical = home_url('/faq/'); } elseif (is_page()) { global $post; $title = get_the_title($post) . ' | Boya Textile'; $raw = wp_strip_all_tags(get_the_excerpt($post) ?: get_post_field('post_content', $post->ID)); $desc = wp_trim_words(preg_replace('/\s+/', ' ', $raw), 28, ''); $canonical = get_permalink($post); } return [ 'title' => $title, 'description' => esc_attr($desc), 'canonical' => esc_url($canonical), 'type' => $type, 'image' => esc_url($image), 'site' => $site, ]; } add_filter('document_title_parts', function ($parts) { $ctx = boya_v4_meta_context(); $parts['title'] = $ctx['title']; unset($parts['tagline']); return $parts; }, 999); add_filter('pre_get_document_title', function ($title) { $ctx = boya_v4_meta_context(); return $ctx['title']; }, 999); add_action('init', function () { remove_action('wp_head', 'rel_canonical'); }); add_action('wp_head', function () { if (is_admin()) return; $ctx = boya_v4_meta_context(); echo "\n<!-- BOYA v4 SEO -->\n"; echo '<meta name="description" content="' . $ctx['description'] . '">' . "\n"; echo '<link rel="canonical" href="' . $ctx['canonical'] . '">' . "\n"; echo '<meta property="og:title" content="' . esc_attr($ctx['title']) . '">' . "\n"; echo '<meta property="og:description" content="' . $ctx['description'] . '">' . "\n"; echo '<meta property="og:url" content="' . $ctx['canonical'] . '">' . "\n"; echo '<meta property="og:type" content="' . esc_attr($ctx['type']) . '">' . "\n"; echo '<meta property="og:site_name" content="Boya Textile">' . "\n"; echo '<meta property="og:image" content="' . $ctx['image'] . '">' . "\n"; echo '<meta name="twitter:card" content="summary_large_image">' . "\n"; echo '<meta name="twitter:title" content="' . esc_attr($ctx['title']) . '">' . "\n"; echo '<meta name="twitter:description" content="' . $ctx['description'] . '">' . "\n"; echo '<meta name="twitter:image" content="' . $ctx['image'] . '">' . "\n"; $schemas = []; $schemas[] = [ '@context' => 'https://schema.org', '@type' => 'Organization', '@id' => home_url('/#organization'), 'name' => 'Boya Textile', 'legalName' => 'Haining Xucun Town Boya Textile Business Department', 'url' => home_url('/'), 'logo' => 'https://boyasofafabric.com/wp-content/uploads/2026/06/boya-logo.jpg', 'description' => 'China manufacturer of custom sofa covers, cushion covers, tablecloths and upholstery fabrics for B2B wholesale buyers.', 'foundingDate' => '2010', 'email' => 'mosomimark@gmail.com', 'telephone' => '+86 18167140260', 'contactPoint' => [[ '@type' => 'ContactPoint', 'telephone' => '+86 18167140260', 'contactType' => 'sales', 'availableLanguage' => ['English', 'Chinese'] ]] ]; $schemas[] = [ '@context' => 'https://schema.org', '@type' => 'WebSite', '@id' => home_url('/#website'), 'url' => home_url('/'), 'name' => 'Boya Textile', 'publisher' => ['@id' => home_url('/#organization')] ]; if (is_front_page()) { $schemas[] = [ '@context' => 'https://schema.org', '@type' => 'FAQPage', 'mainEntity' => [ ['@type'=>'Question','name'=>'What products does Boya Textile manufacture?','acceptedAnswer'=>['@type'=>'Answer','text'=>'Boya Textile manufactures custom sofa covers, cushion covers, tablecloths, throw pillows and upholstery fabrics for wholesale and OEM/ODM buyers.']], ['@type'=>'Question','name'=>'What is the MOQ?','acceptedAnswer'=>['@type'=>'Answer','text'=>'MOQ starts from 50 PCS for selected products. Custom materials, colors, sizes and packaging are available depending on the order.']], ['@type'=>'Question','name'=>'Can Boya Textile make custom private-label products?','acceptedAnswer'=>['@type'=>'Answer','text'=>'Yes. We support OEM/ODM development, private labels, custom packaging and sample confirmation before bulk production.']] ] ]; } if (is_singular('boya_product')) { global $post; $schemas[] = [ '@context'=>'https://schema.org','@type'=>'Product','name'=>get_the_title($post),'description'=>$ctx['description'],'image'=>$ctx['image'],'brand'=>['@type'=>'Brand','name'=>'Boya Textile'],'offers'=>['@type'=>'Offer','priceCurrency'=>'USD','availability'=>'https://schema.org/InStock','url'=>get_permalink($post)] ]; } $term = boya_v4_request_category_term(); if ($term || is_tax('boya_product_cat') || is_singular('boya_product') || is_post_type_archive('boya_product') || (is_page() && !is_page('faq'))) { $schemas[] = ['@context'=>'https://schema.org','@type'=>'BreadcrumbList','itemListElement'=>[ ['@type'=>'ListItem','position'=>1,'name'=>'Home','item'=>home_url('/')], ['@type'=>'ListItem','position'=>2,'name'=>$ctx['title'],'item'=>$ctx['canonical']] ]]; } foreach ($schemas as $schema) { echo '<script type="application/ld+json">' . wp_json_encode($schema, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE) . '</script>' . "\n"; } }, -100); add_action('template_redirect', function () { $path = trim(parse_url($_SERVER['REQUEST_URI'] ?? '', PHP_URL_PATH), '/'); if ($path === 'wp-sitemap.xml' || $path === 'sitemap.xml') { status_header(200); header('Content-Type: application/xml; charset=UTF-8'); echo '<?xml version="1.0" encoding="UTF-8"?>' . "\n"; echo '<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9">' . "\n"; $urls = [home_url('/')]; foreach (get_pages(['post_status' => 'publish']) as $p) { $urls[] = get_permalink($p); } $products = get_posts(['post_type'=>'boya_product','post_status'=>'publish','posts_per_page'=>-1,'fields'=>'ids']); foreach ($products as $pid) { $urls[] = get_permalink($pid); } $terms = get_terms(['taxonomy'=>'boya_product_cat','hide_empty'=>true]); if (!is_wp_error($terms)) { foreach ($terms as $term) { $urls[] = home_url('/product-category/' . $term->slug . '/'); } } $urls = array_unique(array_filter($urls)); foreach ($urls as $u) { echo '<url><loc>' . esc_url($u) . '</loc><changefreq>weekly</changefreq><priority>' . (untrailingslashit($u) === untrailingslashit(home_url('/')) ? '1.0' : '0.7') . '</priority></url>' . "\n"; } echo '</urlset>'; exit; } }, -200); add_action('template_redirect', function () { $term = boya_v4_request_category_term(); if (!$term) return; status_header(200); global $wp_query; if ($wp_query) { $wp_query->is_404 = false; $wp_query->is_archive = true; $wp_query->is_tax = true; } get_header(); $q = new WP_Query([ 'post_type' => 'boya_product', 'post_status' => 'publish', 'posts_per_page' => 24, 'tax_query' => [[ 'taxonomy' => 'boya_product_cat', 'field' => 'term_id', 'terms' => $term->term_id, ]], ]); ?> <main class="alib-section" style="padding:48px 0;background:#fff"> <div class="alib-container"> <nav style="font-size:.9rem;margin-bottom:18px;color:#777"><a href="<?php echo esc_url(home_url('/')); ?>">Home</a> / <a href="<?php echo esc_url(home_url('/products/')); ?>">Products</a> / <?php echo esc_html($term->name); ?></nav> <h1 style="font-size:2.2rem;line-height:1.2;margin:0 0 14px;color:#1f2937">Wholesale <?php echo esc_html($term->name); ?> Manufacturer</h1> <p style="max-width:820px;color:#555;font-size:1.05rem;margin:0 0 28px">Source custom <?php echo esc_html($term->name); ?> from Boya Textile, a China home textile factory supporting OEM/ODM, private label packaging, custom sizes, materials and colors for B2B wholesale buyers.</p> <?php if ($q->have_posts()) : ?> <div class="alib-featured__grid" style="grid-template-columns:repeat(auto-fit,minmax(240px,1fr));gap:1.5rem"> <?php while ($q->have_posts()) : $q->the_post(); ?> <a href="<?php the_permalink(); ?>" class="alib-product-card"> <div class="alib-product-card__image"><?php if (has_post_thumbnail()) { the_post_thumbnail('medium_large'); } ?></div> <div class="alib-product-card__body"><h3><?php the_title(); ?></h3><p>Customizable wholesale supply from Boya Textile factory.</p></div> </a> <?php endwhile; wp_reset_postdata(); ?> </div> <?php else : ?> <p>No published products in this category yet. Contact us for custom sourcing.</p> <?php endif; ?> </div> </main> <?php get_footer(); exit; }, 0); https://boyasofafabric.com/wp-sitemap-posts-post-1.xmlhttps://boyasofafabric.com/wp-sitemap-posts-page-1.xmlhttps://boyasofafabric.com/wp-sitemap-users-1.xml