<reasoning_content>
*   Goal: Implement priority-based job scheduling.
    *   Requirements:
        1.  `add_job` needs an optional `priority` parameter (default=0).
        2.  Higher priority (higher number) comes first.
        3.  Same priority = FIFO (First In, First Out).
        4.  `get_next_job()` returns the highest priority job.
    *   Priority levels: 0 (Normal), 1 (High), 2 (Critical).
    *   Implementation Detail: Since higher numbers mean higher priority and same priority must be FIFO, a priority queue is ideal. Python's `heapq` is a min-priority queue. To make it a max-priority queue with FIFO, I should store entries as `(-priority, entry_count, data)`.

    *   `JobQueue` class.
    *   `self.jobs`: A list to act as the heap.
    *   `self.counter`: To ensure FIFO for same priority.
    *   `add_job(name, data, priority=0)`: Push to heap.
    *   `get_next_job()`: Pop from heap.

    *   `import heapq`
    *   `count = 0`
    *   `heapq.heappush(self.jobs, (-priority, count, name, data))`
    *   `return heapq.heappop(self.jobs)`

    *   `get_next_job` should return `tuple[str, dict] | None`.
    *   The `name` is a string, `data` is a dict.

    ```python
    import heapq

    class JobQueue:
        def __init__(self):
            self.jobs = []
            self.counter = 0

        def add_job(self, name: str, data: dict, priority: int = 0):
            # heapq is a min-heap. To treat higher priority numbers
            # as higher priority, we use negative priority.
            # We use a counter to maintain FIFO for equal priorities.
            heapq.heappush(self.jobs, (-priority, self.counter, name, data))
            self.counter += 1

        def get_next_job(self) -> tuple[str, dict] | None:
            if not self.jobs:
                return None
            _, _, name, data = heapq.heappop(self.jobs)
            return (name, data)
    ```

    *   Requirement 1: `add_job` accepts optional priority (default=0). Yes.
    *   Requirement 2: Higher priority before lower. Yes (negative priority in min-heap makes highest number smallest).
    *   Requirement 3: Same priority FIFO. Yes (counter).
    *   Requirement 4: `get_next_job()` signature and behavior. Yes.

    Wait, the example shows `queue.get_next_job()` returns `(name, data)`.
    Wait, looking at the example: `queue.get_next_job() # Returns critical job first`.
    The return type is `tuple[str, dict] | None`.

    Let's double check the priority logic:
    Priority 2 (Critical) -> `-2`
    Priority 1 (High) -> `-1`
    Priority 0 (Normal) -> `0`
    Min-heap will pick `-2` first. Correct.
</reasoning_content>

<content>
```python
import heapq

class JobQueue:
    def __init__(self):
        self.jobs = []
        self.counter = 0

    def add_job(self, name: str, data: dict, priority: int = 0):
        # Using negative priority because heapq is a min-heap, 
        # but we want higher numbers to have higher priority.
        # The counter ensures FIFO order for jobs with the same priority.
        heapq.heappush(self.jobs, (-priority, self.counter, name, data))
        self.counter += 1

    def get_next_job(self) -> tuple[str, dict] | None:
        if not self.jobs:
            return None
        
        _, _, name, data = heapq.heappop(self.jobs)
        return (name, data)
```
</content>