| @@ -439,8 +439,22 @@ | ||
| 439 | 439 | update_option('mxchat_video_embed_enabled', $vce_value); |
| 440 | 440 | wp_send_json_success(['message' => esc_html__('Setting saved', 'mxchat')]); |
| 441 | 441 | return; |
| 442 | 442 | |
| 443 | + // Page-cache purge on settings save (plan b76ed6, Support Ticket 468). | |
| 444 | + // STANDALONE option, same pattern. Default ON — the purge already ships | |
| 445 | + // (3.2.9), so this is an opt-OUT for large sites. Switching it off also | |
| 446 | + // drops a deferred purge the debounce may have scheduled seconds ago, | |
| 447 | + // so "off" takes effect at once rather than after one more purge. | |
| 448 | + case 'mxchat_cache_purge_enabled': | |
| 449 | + $cpe_value = ($value === 'on' || $value === '1') ? 'on' : 'off'; | |
| 450 | + update_option('mxchat_cache_purge_enabled', $cpe_value); | |
| 451 | + if ($cpe_value === 'off' && class_exists('MxChat_Cache_Purge')) { | |
| 452 | + wp_clear_scheduled_hook(MxChat_Cache_Purge::DEFERRED_EVENT); | |
| 453 | + } | |
| 454 | + wp_send_json_success(['message' => esc_html__('Setting saved', 'mxchat')]); | |
| 455 | + return; | |
| 456 | + | |
| 443 | 457 | // Clamped to the same 20-95 the field advertises. An out-of-range or |
| 444 | 458 | // non-numeric POST is corrected rather than refused, and the corrected |
| 445 | 459 | // value is echoed back so the field can reconcile — a silently stored |
| 446 | 460 | // 0 here would put a video on every answer, which is the bug. |
| @@ -1057,8 +1071,36 @@ | ||
| 1057 | 1071 | if ($field_name === 'mxchat_pinecone_host') { |
| 1058 | 1072 | $new_value = str_replace(['https://', 'http://'], '', $new_value); |
| 1059 | 1073 | } |
| 1060 | 1074 | break; |
| 1075 | + case 'mxchat_pinecone_index_type': | |
| 1076 | + // 362c31: document only once the host has been checked (see sanitize_pinecone_settings). | |
| 1077 | + $new_value = ($value === 'document') ? 'document' : 'vector'; | |
| 1078 | + if ($new_value === 'document' && strtolower(trim((string) ($current_options['mxchat_pinecone_host'] ?? ''), '/')) !== strtolower((string) ($current_options['mxchat_pinecone_docs_verified_host'] ?? ''))) { | |
| 1079 | + wp_send_json_error(['message' => esc_html__('Check the document index host first (Check index or Create index for me).', 'mxchat')]); | |
| 1080 | + } | |
| 1081 | + // 3e83e4: same gate as the form save — no switch onto a half-copied index. | |
| 1082 | + if ($new_value === 'document' && (($current_options['mxchat_pinecone_index_type'] ?? 'vector') !== 'document') && class_exists('MxChat_Pinecone_Documents')) { | |
| 1083 | + $running = MxChat_Pinecone_Documents::migration_blocks_switch((string) ($current_options['mxchat_pinecone_host'] ?? '')); | |
| 1084 | + if ($running !== null) { | |
| 1085 | + wp_send_json_error(['message' => MxChat_Pinecone_Documents::switch_blocked_message($running)]); | |
| 1086 | + } | |
| 1087 | + } | |
| 1088 | + break; | |
| 1089 | + case 'mxchat_pinecone_vector_host': | |
| 1090 | + $new_value = trim(str_replace(['https://', 'http://'], '', sanitize_text_field($value)), '/'); | |
| 1091 | + break; | |
| 1092 | + case 'mxchat_pinecone_vector_index': | |
| 1093 | + case 'mxchat_pinecone_docs_region': | |
| 1094 | + $new_value = sanitize_text_field($value); | |
| 1095 | + break; | |
| 1096 | + case 'mxchat_pinecone_docs_cloud': | |
| 1097 | + $new_value = in_array($value, array('aws', 'gcp', 'azure'), true) ? $value : 'aws'; | |
| 1098 | + break; | |
| 1099 | + case 'mxchat_pinecone_docs_language': | |
| 1100 | + $lang_value = sanitize_key($value); | |
| 1101 | + $new_value = (class_exists('MxChat_Pinecone_Documents') && array_key_exists($lang_value, MxChat_Pinecone_Documents::languages())) ? $lang_value : 'en'; | |
| 1102 | + break; | |
| 1061 | 1103 | case 'mxchat_pinecone_top_k': |
| 1062 | 1104 | // d0cae1: out-of-range and junk normalize to the default 50 — |
| 1063 | 1105 | // same clamp the read site applies. |
| 1064 | 1106 | $top_k = absint($value); |
| @@ -1499,9 +1541,10 @@ | ||
| 1499 | 1541 | } |
| 1500 | 1542 | |
| 1501 | 1543 | $product_id = 'MxChatPRO'; |
| 1502 | 1544 | $domain = parse_url(home_url(), PHP_URL_HOST); // Get the current domain |
| 1503 | - | |
| 1545 | + $was_active = (get_option('mxchat_license_status', 'inactive') === 'active'); | |
| 1546 | + | |
| 1504 | 1547 | // Call WooCommerce Software API for activation (not just validation) |
| 1505 | 1548 | $response = wp_remote_get( |
| 1506 | 1549 | add_query_arg( |
| 1507 | 1550 | array( |
| @@ -1547,9 +1590,16 @@ | ||
| 1547 | 1590 | update_option('mxchat_license_status', 'active'); |
| 1548 | 1591 | update_option('mxchat_pro_email', $customer_email); |
| 1549 | 1592 | update_option('mxchat_activation_key', $license_key); |
| 1550 | 1593 | delete_option('mxchat_license_error'); |
| 1551 | - | |
| 1594 | + | |
| 1595 | + // A fresh activation starts the licence domain check (c93ede) from a | |
| 1596 | + // clean slate: no grace streak carried over, first daily check at a | |
| 1597 | + // random time within the day. | |
| 1598 | + if (class_exists('MxChat_License_Check')) { | |
| 1599 | + MxChat_License_Check::reset(true); | |
| 1600 | + } | |
| 1601 | + | |
| 1552 | 1602 | // Also track on your website (this is your existing domain tracking) |
| 1553 | 1603 | $this->track_domain_on_website($license_key, $customer_email, $domain); |
| 1554 | 1604 | |
| 1555 | 1605 | wp_send_json_success(array('message' => esc_html__('License activated successfully', 'mxchat'))); |
| @@ -1556,9 +1606,17 @@ | ||
| 1556 | 1606 | } else { |
| 1557 | 1607 | $error_message = isset($data->error) ? $data->error : esc_html__('Activation failed', 'mxchat'); |
| 1558 | 1608 | update_option('mxchat_license_status', 'inactive'); |
| 1559 | 1609 | update_option('mxchat_license_error', $error_message); |
| 1560 | - | |
| 1610 | + | |
| 1611 | + // c93ede: a refusal by the licence owner (domain switched off, new sites | |
| 1612 | + // blocked) or a revoked key is an explicit "off" from mxchat.ai. Remember | |
| 1613 | + // who controls it so Pro & Extensions says so, and keep checking so the | |
| 1614 | + // owner's switch-on restores Pro without another click here. | |
| 1615 | + if (class_exists('MxChat_License_Check')) { | |
| 1616 | + MxChat_License_Check::note_activation_refusal(isset($data->code) ? (string) $data->code : '', (string) $error_message, $was_active); | |
| 1617 | + } | |
| 1618 | + | |
| 1561 | 1619 | //error_log('MxChat Activation failed: ' . $error_message); |
| 1562 | 1620 | wp_send_json_error($error_message); |
| 1563 | 1621 | } |
| 1564 | 1622 | } |
| @@ -1643,9 +1701,15 @@ | ||
| 1643 | 1701 | delete_option('mxchat_license_status'); |
| 1644 | 1702 | delete_option('mxchat_pro_email'); |
| 1645 | 1703 | delete_option('mxchat_activation_key'); |
| 1646 | 1704 | delete_option('mxchat_license_error'); |
| 1647 | - | |
| 1705 | + | |
| 1706 | + // Nothing left to check: drop the licence domain check's state and its | |
| 1707 | + // scheduled event (c93ede). | |
| 1708 | + if (class_exists('MxChat_License_Check')) { | |
| 1709 | + MxChat_License_Check::reset(false); | |
| 1710 | + } | |
| 1711 | + | |
| 1648 | 1712 | //error_log('MxChat deactivate: Local data cleared'); |
| 1649 | 1713 | |
| 1650 | 1714 | // Notify your website's API to properly deactivate |
| 1651 | 1715 | $response = wp_remote_post('https://mxchat.ai/mxchat-api/deactivate-license', array( |