<reasoning_content>
The user wants a Python implementation of a priority-based job scheduling queue.
Key requirements:
1. `add_job` method accepts a job name, job data, and an optional priority (default 0).
2. Higher priority values are processed first.
3. FIFO order for same priority.
4. `get_next_job` method returns the highest priority job as a tuple `(name, data)` or `None` if empty.
5. Priority levels: 0 (Normal), 1 (High), 2 (Critical).

I'll use a list to store jobs, where each job is stored as a tuple or object containing priority, insertion order (to maintain FIFO for same priority), name, and data.
Alternatively, I can use `heapq` module for efficient priority queue operations. Since we need FIFO for same priority, I'll include a sequence counter in the heap tuple.

Heap tuple structure: `(-priority, sequence, name, data)`
- Negative priority because `heapq` is a min-heap, but we want higher priority first.
- Sequence ensures FIFO for equal priorities.

Let's implement a `JobQueue` class.

```python
import heapq

class JobQueue:
    def __init__(self):
        self._queue = []
        self._counter = 0

    def add_job(self, name: str, data: dict, priority: int = 0) -> None:
        # Negate priority because heapq is a min-heap
        heapq.heappush(self._queue, (-priority, self._counter, name, data))
        self._counter += 1

    def get_next_job(self) -> tuple[str, dict] | None:
        if not self._queue:
            return None
        # Pop the smallest item (highest priority due to negation)
        _, _, name, data = heapq.heappop(self._queue)
        return (name, data)
```

Wait, the prompt says "Write only the Python code, no explanations."
I should make sure the types match the requirement: `get_next_job() -> tuple[str, dict] | None`
The implementation looks solid.

Let's double check requirements:
1. `add_job` accepts optional priority parameter (default=0) -> Yes.
2. Higher priority jobs processed before lower -> Yes (negated priority in min-heap).
3. Same priority maintains FIFO -> Yes (using counter).
4. `get_next_job() -> tuple[str, dict] | None` -> Yes.
5. Priority levels example matches logic.

One minor point: `tuple[str, dict] | None` syntax requires Python 3.10+. I'll assume modern Python. If not, `Optional[Tuple[str, dict]]` could be used, but the prompt uses `|`. I'll stick to `|`.

I will write out the class definition.

```python
import heapq
from typing import Optional, Tuple

class JobQueue:
    def __init__(self):
        self._queue = []
        self._counter = 0

    def add_job(self, name: str, data: dict, priority: int = 0) -> None:
        heapq.heappush(self._queue, (-priority, self._counter, name, data))
        self._counter += 1

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

Wait, `Tuple[str, dict] | None` might cause syntax error in older Python versions, but the prompt uses it, so it's fine. I'll just use the exact signature requested.

Let's verify the example:
```python
queue = JobQueue()
queue.add_job("normal", {"type": "normal"}, priority=0)
queue.add_job("critical", {"type": "critical"}, priority=2)
queue.add_job("high", {"type": "high"}, priority=1)

job = queue.get_next_job()  # Returns critical job first
```
Heap state after adds:
1. `(0, 0, "normal", {...})`
2. `(-2, 1, "critical", {...})`
3. `(-1, 2, "high", {...})`

Heap order (min-heap on first element):
`(-2, 1, "critical", ...)` is smallest. Popped first. Correct.
Next: `(-1, 2, "high", ...)`
Next: `(0, 0, "normal", ...)`

FIFO for same priority:
If we add two priority 0 jobs:
`(0, 0, "A", ...)`
`(0, 1, "B", ...)`
Heap order keeps 0 before 1. Popped A then B. Correct.

The implementation is correct and efficient.
I will output only the code.
One thing: `typing` imports might not be strictly necessary if using built-in `tuple` and `|`, but it's safer to include them or just rely on Python 3.10+ syntax as requested. I'll stick to the prompt's type hint style.

Final code:
```python
import heapq

class JobQueue:
    def __init__(self):
        self._queue = []
        self._counter = 0

    def add_job(self, name: str, data: dict, priority: int = 0) -> None:
        heapq.heappush(self._queue, (-priority, self._counter, name, data))
        self._counter += 1

    def get_next_job(self) -> tuple[str, dict] | None:
        if not self._queue:
            return None
        _, _, name, data = heapq.heappop(self._queue)
        return (name, data)
```
This matches all requirements. I'll output it.
Wait, should I include `from typing import Optional, Tuple`? The prompt uses `tuple[str, dict] | None`, which is valid in 3.10+. I'll just use it as is.
All good.
Output matches request.✅
Proceed. 
Self-Correction/Verification during thought:
Is there any edge case? Empty queue returns None. Correct.
Priority levels are just integers, handled correctly.
FIFO is handled by `_counter`.
Higher priority first is handled by `-priority`.
Code is concise.
Ready. 
Output matches the final code block.✅
I will produce exactly that. 
One minor point: `tuple[str, dict] | None` might need `from __future__ import annotations` for older versions, but I'll assume modern Python as per prompt syntax. I'll just write it as requested.
All set. 
Output generation. 
```python
import heapq

class JobQueue:
    def __init__(self):
        self._queue = []
        self._counter = 0

    def add_job(self, name: str, data: dict, priority: int = 0) -> None:
        heapq.heappush(self._queue, (-priority, self._counter, name, data))
        self._counter += 1

    def get_next_job(self) -> tuple[str, dict] | None:
        if not self._queue:
            return None
        _, _, name, data = heapq.heappop(self._queue)
        return (name, data)
```
Matches perfectly. No extra text. Done. 
Proceeds. 
[Output Generation] -> *Proceeds*

</reasoning_content>

<content>
```python
import heapq

class JobQueue:
    def __init__(self):
        self._queue = []
        self._counter = 0

    def add_job(self, name: str, data: dict, priority: int = 0) -> None:
        heapq.heappush(self._queue, (-priority, self._counter, name, data))
        self._counter += 1

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