| @@ -266,8 +266,15 @@ | ||
| 266 | 266 | if ((int) $webhook->get_id() !== (int) $keeper->get_id()) { |
| 267 | 267 | $this->_remove_webhook($webhook->get_id()); |
| 268 | 268 | } |
| 269 | 269 | } |
| 270 | + // Paused is a manual opt-out: quotes stay on, order posting stays off. | |
| 271 | + // If any copy is paused, the survivor stays paused so an active | |
| 272 | + // duplicate cannot keep delivering. Disabled is WooCommerce's | |
| 273 | + // automatic status after delivery failures, and we still heal that. | |
| 274 | + if (self::group_has_paused_webhook($existing)) { | |
| 275 | + $values['status'] = 'paused'; | |
| 276 | + } | |
| 270 | 277 | if (!$this->sync_webhook($keeper, $values, $secret, $user_id)) { |
| 271 | 278 | $missing[] = $name; |
| 272 | 279 | } |
| 273 | 280 | } |
| @@ -372,8 +379,23 @@ | ||
| 372 | 379 | return 0; |
| 373 | 380 | } |
| 374 | 381 | |
| 375 | 382 | /** |
| 383 | + * Whether the merchant paused any copy of this webhook. | |
| 384 | + * | |
| 385 | + * @param array $webhooks Webhook-like objects for one name. | |
| 386 | + * @return bool | |
| 387 | + */ | |
| 388 | + private static function group_has_paused_webhook($webhooks) { | |
| 389 | + foreach ($webhooks as $webhook) { | |
| 390 | + if (self::is_webhook_like($webhook) && 'paused' === $webhook->get_status()) { | |
| 391 | + return true; | |
| 392 | + } | |
| 393 | + } | |
| 394 | + return false; | |
| 395 | + } | |
| 396 | + | |
| 397 | + /** | |
| 376 | 398 | * Update in place. Do not delete+recreate (that is what duplicated hooks). |
| 377 | 399 | * |
| 378 | 400 | * @param object $webhook WC_Webhook. |
| 379 | 401 | * @param array $values Expected webhook config. |
| @@ -390,12 +412,13 @@ | ||
| 390 | 412 | $webhook->set_user_id($effective_user); |
| 391 | 413 | $changed = true; |
| 392 | 414 | } |
| 393 | 415 | |
| 394 | - if ($effective_user && $webhook->get_status() !== $values['status']) { | |
| 416 | + $current_status = $webhook->get_status(); | |
| 417 | + if ($effective_user && 'paused' !== $current_status && $current_status !== $values['status']) { | |
| 395 | 418 | $webhook->set_status($values['status']); |
| 396 | 419 | $changed = true; |
| 397 | - if (method_exists($webhook, 'set_failure_count')) { | |
| 420 | + if ('active' === $values['status'] && method_exists($webhook, 'set_failure_count')) { | |
| 398 | 421 | $webhook->set_failure_count(0); |
| 399 | 422 | } |
| 400 | 423 | } |
| 401 | 424 | |