# RulePreventsExecutionException

## Overview

`RulePreventsExecutionException` is a custom exception class in the Midnite81\Guardian package. This exception is thrown when a rate limiting rule prevents the execution of a request in the Guardian system.

## Class Details

* **Namespace**: `Midnite81\Guardian\Exceptions`
* **Extends**: `Exception`

## Purpose

The primary purpose of this exception is to provide detailed information when a request is blocked due to rate limiting rules. It encapsulates the specific rule that caused the prevention, allowing for more informative error handling and logging.

## Properties

* `protected ?RateLimitRule $preventingRule`: Stores the rule that prevented the execution. It can be null if no specific rule is identified.

## Constructor

```php
public function __construct(?RateLimitRule $preventingRule = null)
```

The constructor takes an optional `RateLimitRule` object, which represents the rule that prevented the execution.

## Methods

### getPreventingRule

```php
public function getPreventingRule(): ?RateLimitRule
```

Returns the `RateLimitRule` object that prevented the execution, or `null` if no specific rule was identified.

### getErrorMessageFromRule (protected)

```php
protected function getErrorMessageFromRule(): string
```

Generates a human-readable error message based on the preventing rule. This method is used internally to create the exception message.

## Usage

This exception is typically thrown by the Guardian system when a rate limit is exceeded. You can catch this exception to handle rate limiting scenarios in your application.

Example:

```php
use Midnite81\Guardian\Exceptions\RulePreventsExecutionException;

try {
    // Your Guardian-protected code here
} catch (RulePreventsExecutionException $e) {
    $rule = $e->getPreventingRule();
    if ($rule) {
        echo "Request blocked. Rate limit: {$rule->getLimit()} requests per {$rule->getDuration()} {$rule->getInterval()->value}.";
    } else {
        echo "Request blocked by an unspecified rule.";
    }
}
```

## Error Messages

The exception provides detailed error messages:

* If a specific rule prevented execution:

  ```
  Cannot execute the request. Rate limit exceeded: X requests per Y [interval].
  ```

  Where X is the limit, Y is the duration, and \[interval] is the time unit (e.g., second, minute, hour).
* If no specific rule is identified:

  ```
  Cannot execute the request because a rule prevents it.
  ```

## Integration with Guardian

This exception is thrown by the `Guardian::send()` method when `$throwIfRulePrevents` is set to `true` (which is the default behavior). It allows developers to handle rate limiting scenarios gracefully in their applications.

## Best Practices

1. Always catch this exception when working with Guardian-protected code sections.
2. Use the information provided by the exception to inform users about the rate limit and when they can retry.
3. Consider implementing a backoff strategy or queue system for requests that hit rate limits frequently.

By utilizing `RulePreventsExecutionException`, you can create more robust and user-friendly applications that gracefully handle rate limiting scenarios.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://guardian.midnite.uk/exceptions/rule-prevents-execution-exception.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
