diff --git a/overcooked_simulator/counter_factory.py b/overcooked_simulator/counter_factory.py
index 757cddfe27582ba50880a26f72fb8a624561e40c..9b1487c3706a70dde8b224283a1877c126c41b56 100644
--- a/overcooked_simulator/counter_factory.py
+++ b/overcooked_simulator/counter_factory.py
@@ -33,6 +33,7 @@ layout_chars:
 """
 import inspect
 import sys
+from random import Random
 from typing import Any, Type, TypeVar
 
 import numpy as np
@@ -121,6 +122,7 @@ class CounterFactory:
         order_and_score: OrderAndScoreManager,
         effect_manager_config: dict,
         hook: Hooks,
+        random: Random,
     ) -> None:
         """Constructor for the `CounterFactory` class. Set up the attributes necessary to instantiate the counters.
 
@@ -181,6 +183,9 @@ class CounterFactory:
         self.hook = hook
         """Reference to the hook manager."""
 
+        self.random = random
+        """Random instance."""
+
     def get_counter_object(self, c: str, pos: npt.NDArray[float]) -> Counter:
         """Create and returns a counter object based on the provided character and position."""
 
@@ -234,6 +239,7 @@ class CounterFactory:
                     ),
                     "plate_config": self.plate_config,
                     "dispensing": self.item_info[Plate.__name__],
+                    "random": self.random,
                 }
             )
         elif issubclass(counter_class, ServingWindow):
@@ -334,6 +340,7 @@ class CounterFactory:
             else:
                 manager = self.effect_manager_config[effect.manager]["class"](
                     hook=self.hook,
+                    random=self.random,
                     **self.effect_manager_config[effect.manager]["kwargs"],
                 )
                 manager.set_counters(counters)
diff --git a/overcooked_simulator/counters.py b/overcooked_simulator/counters.py
index 9bb481d3cc1d1444b9840cc42d8d5ac99b425d31..4626f50b354ce0bea3fae649c8c4d1282f6d4c4b 100644
--- a/overcooked_simulator/counters.py
+++ b/overcooked_simulator/counters.py
@@ -40,6 +40,7 @@ import uuid
 from collections import deque
 from collections.abc import Iterable
 from datetime import datetime, timedelta
+from random import Random
 from typing import TYPE_CHECKING, Optional, Callable, Set
 
 from overcooked_simulator.hooks import (
@@ -482,6 +483,7 @@ class PlateDispenser(Counter):
         dispensing: ItemInfo,
         plate_config: PlateConfig,
         plate_transitions: dict[str, ItemInfo],
+        random: Random,
         **kwargs,
     ) -> None:
         super().__init__(**kwargs)
@@ -499,6 +501,8 @@ class PlateDispenser(Counter):
         `out_of_kitchen_timer` list every frame."""
         self.plate_transitions: dict[str, ItemInfo] = plate_transitions
         """Transitions for the plates. Relevant for the sink, because a plate can become a clean one there."""
+        self.random = random
+        """Random instance."""
         self.setup_plates()
 
     def pick_up(self, on_hands: bool = True) -> Item | None:
@@ -523,9 +527,9 @@ class PlateDispenser(Counter):
         """Is called from the serving window to add a plate out of kitchen."""
         # not perfect identical to datetime.now but based on framerate enough.
         time_plate_to_add = env_time + timedelta(
-            seconds=np.random.uniform(
-                low=self.plate_config.plate_delay[0],
-                high=self.plate_config.plate_delay[1],
+            seconds=self.random.uniform(
+                a=self.plate_config.plate_delay[0],
+                b=self.plate_config.plate_delay[1],
             )
         )
         log.debug(f"New plate out of kitchen until {time_plate_to_add}")
diff --git a/overcooked_simulator/effect_manager.py b/overcooked_simulator/effect_manager.py
index 905fef957bf5f200b84ab84c141681838d0a9241..bb13ee977c25bcc715bf7867e0208671c1cd9748 100644
--- a/overcooked_simulator/effect_manager.py
+++ b/overcooked_simulator/effect_manager.py
@@ -1,8 +1,8 @@
 from __future__ import annotations
 
-import random
 from collections import deque
 from datetime import timedelta, datetime
+from random import Random
 from typing import TYPE_CHECKING, Tuple
 
 from overcooked_simulator.game_items import (
@@ -20,11 +20,12 @@ if TYPE_CHECKING:
 
 
 class EffectManager:
-    def __init__(self, hook: Hooks):
+    def __init__(self, hook: Hooks, random: Random) -> None:
         self.effects = []
         self.counters = []
         self.hook = hook
         self.new_effects: list[Tuple[Effect, Item | Counter]] = []
+        self.random = random
 
     def add_effect(self, effect: ItemInfo):
         self.effects.append(effect)
@@ -68,7 +69,7 @@ class FireEffectManager(EffectManager):
         if self.new_effects:
             for effect, target in self.new_effects:
                 self.effect_to_timer[effect.uuid] = now + timedelta(
-                    seconds=random.uniform(*self.spreading_duration)
+                    seconds=self.random.uniform(*self.spreading_duration)
                 )
                 self.next_finished_timer = min(
                     self.next_finished_timer, self.effect_to_timer[effect.uuid]
@@ -91,7 +92,7 @@ class FireEffectManager(EffectManager):
                             else:
                                 self.apply_effect(effect, counter)
                     self.effect_to_timer[effect.uuid] = now + timedelta(
-                        seconds=random.uniform(*self.spreading_duration)
+                        seconds=self.random.uniform(*self.spreading_duration)
                     )
             if self.effect_to_timer:
                 self.next_finished_timer = min(self.effect_to_timer.values())
diff --git a/overcooked_simulator/game_server.py b/overcooked_simulator/game_server.py
index d2735921fb0296276a8edbab50c79108672dc7c7..12088ce137d7e396e5b4c6babbbe4004472ef6ab 100644
--- a/overcooked_simulator/game_server.py
+++ b/overcooked_simulator/game_server.py
@@ -655,6 +655,7 @@ class CreateEnvironmentConfig(BaseModel):
     item_info_config: str  # file content
     environment_config: str  # file content
     layout_config: str  # file content
+    seed: int
 
 
 class AdditionalPlayer(BaseModel):
diff --git a/overcooked_simulator/gui_2d_vis/overcooked_gui.py b/overcooked_simulator/gui_2d_vis/overcooked_gui.py
index 7d544fe2cb95b1e8f9e2421d80981b2d68774fec..c9ee9a8f6d8e01afedbac52828b0c281887f0c01 100644
--- a/overcooked_simulator/gui_2d_vis/overcooked_gui.py
+++ b/overcooked_simulator/gui_2d_vis/overcooked_gui.py
@@ -460,6 +460,8 @@ class PyGameGUI:
             layout = file.read()
         with open(environment_config_path, "r") as file:
             environment_config = file.read()
+
+        seed = 161616161616
         creation_json = CreateEnvironmentConfig(
             manager_id=self.manager_id,
             number_players=2,
@@ -467,7 +469,9 @@ class PyGameGUI:
             item_info_config=item_info,
             environment_config=environment_config,
             layout_config=layout,
+            seed=seed,
         ).model_dump(mode="json")
+
         # print(CreateEnvironmentConfig.model_validate_json(json_data=creation_json))
         env_info = requests.post(
             f"{self.request_url}/manage/create_env/",
diff --git a/overcooked_simulator/order.py b/overcooked_simulator/order.py
index 299bcdd6e3c7afbfcd9b2a57c816a911606106f2..e5cc4fae636a713c02840681f92779e15faa7bb9 100644
--- a/overcooked_simulator/order.py
+++ b/overcooked_simulator/order.py
@@ -46,11 +46,11 @@ from __future__ import annotations
 
 import dataclasses
 import logging
-import random
 import uuid
 from abc import abstractmethod
 from collections import deque
 from datetime import datetime, timedelta
+from random import Random
 from typing import Callable, Tuple, Any, Deque, Protocol, TypedDict, Type
 
 from overcooked_simulator.game_items import Item, Plate, ItemInfo
@@ -137,9 +137,11 @@ class OrderGeneration:
         ```
     """
 
-    def __init__(self, available_meals: dict[str, ItemInfo], **kwargs):
+    def __init__(self, available_meals: dict[str, ItemInfo], random: Random, **kwargs):
         self.available_meals: list[ItemInfo] = list(available_meals.values())
         """Available meals restricted through the `environment_config.yml`."""
+        self.random = random
+        """Random instance."""
 
     @abstractmethod
     def init_orders(self, now) -> list[Order]:
@@ -161,11 +163,21 @@ class OrderGeneration:
 class OrderAndScoreManager:
     """The Order and Score Manager that is called from the serving window."""
 
-    def __init__(self, order_config, available_meals: dict[str, ItemInfo], hook: Hooks):
+    def __init__(
+        self,
+        order_config,
+        available_meals: dict[str, ItemInfo],
+        hook: Hooks,
+        random: Random,
+    ):
+        self.random = random
+        """Random instance."""
         self.score: float = 0.0
         """The current score of the environment."""
         self.order_gen: OrderGeneration = order_config["order_gen_class"](
-            available_meals=available_meals, kwargs=order_config["order_gen_kwargs"]
+            available_meals=available_meals,
+            random=random,
+            kwargs=order_config["order_gen_kwargs"],
         )
         """The order generation."""
         self.serving_not_ordered_meals: Callable[
@@ -511,8 +523,8 @@ class RandomOrderGeneration(OrderGeneration):
     ```
     """
 
-    def __init__(self, available_meals: dict[str, ItemInfo], **kwargs):
-        super().__init__(available_meals, **kwargs)
+    def __init__(self, available_meals: dict[str, ItemInfo], random: Random, **kwargs):
+        super().__init__(available_meals, random, **kwargs)
         self.kwargs: RandomOrderKwarg = RandomOrderKwarg(**kwargs["kwargs"])
         self.next_order_time: datetime | None = datetime.max
         self.number_cur_orders: int = 0
@@ -524,7 +536,7 @@ class RandomOrderGeneration(OrderGeneration):
         if not self.kwargs.sample_on_serving:
             self.create_random_next_time_delta(now)
         return self.create_orders_for_meals(
-            random.choices(self.available_meals, k=self.kwargs.num_start_meals),
+            self.random.choices(self.available_meals, k=self.kwargs.num_start_meals),
             now,
             self.kwargs.sample_on_serving,
         )
@@ -547,7 +559,7 @@ class RandomOrderGeneration(OrderGeneration):
             self.needed_orders = max(self.needed_orders, 0)
             self.number_cur_orders += len(new_finished_orders)
             return self.create_orders_for_meals(
-                random.choices(self.available_meals, k=len(new_finished_orders)),
+                self.random.choices(self.available_meals, k=len(new_finished_orders)),
                 now,
             )
         if self.next_order_time <= now:
@@ -560,7 +572,7 @@ class RandomOrderGeneration(OrderGeneration):
                     self.next_order_time = datetime.max
                 self.number_cur_orders += 1
                 return self.create_orders_for_meals(
-                    [random.choice(self.available_meals)],
+                    [self.random.choice(self.available_meals)],
                     now,
                 )
         return []
@@ -575,7 +587,7 @@ class RandomOrderGeneration(OrderGeneration):
             else:
                 duration = timedelta(
                     seconds=getattr(
-                        random, self.kwargs.order_duration_random_func["func"]
+                        self.random, self.kwargs.order_duration_random_func["func"]
                     )(**self.kwargs.order_duration_random_func["kwargs"])
                 )
             log.info(f"Create order for meal {meal} with duration {duration}")
@@ -601,7 +613,7 @@ class RandomOrderGeneration(OrderGeneration):
 
     def create_random_next_time_delta(self, now: datetime):
         self.next_order_time = now + timedelta(
-            seconds=getattr(random, self.kwargs.sample_on_dur_random_func["func"])(
+            seconds=getattr(self.random, self.kwargs.sample_on_dur_random_func["func"])(
                 **self.kwargs.sample_on_dur_random_func["kwargs"]
             )
         )
diff --git a/overcooked_simulator/overcooked_environment.py b/overcooked_simulator/overcooked_environment.py
index 96b4949fc322887526d927564cc1543176fc35b0..0f2115bceb024960aa0b955a569fe1425577fa55 100644
--- a/overcooked_simulator/overcooked_environment.py
+++ b/overcooked_simulator/overcooked_environment.py
@@ -4,11 +4,11 @@ import dataclasses
 import inspect
 import json
 import logging
-import random
 import sys
 from datetime import timedelta, datetime
 from enum import Enum
 from pathlib import Path
+from random import Random
 from typing import Literal, TypedDict, Callable, Tuple
 
 import numpy as np
@@ -125,7 +125,10 @@ class Environment:
         layout_config: Path | str,
         item_info: Path | str,
         as_files: bool = True,
+        seed: int = 56789223842348,
     ):
+        self.random: Random = Random(seed)
+        """Random instance."""
         self.hook: Hooks = Hooks(self)
         """Hook manager. Register callbacks and create hook points with additional kwargs."""
 
@@ -176,6 +179,7 @@ class Environment:
                 if info.type == ItemType.Meal and item in self.allowed_meal_names
             },
             hook=self.hook,
+            random=self.random,
         )
         """The manager for the orders and score update."""
 
@@ -201,6 +205,7 @@ class Environment:
             order_and_score=self.order_and_score,
             effect_manager_config=self.environment_config["effect_manager"],
             hook=self.hook,
+            random=self.random,
         )
 
         (
@@ -675,11 +680,13 @@ class Environment:
         self.players[player.name] = player
         if player.pos is None:
             if len(self.designated_player_positions) > 0:
-                free_idx = random.randint(0, len(self.designated_player_positions) - 1)
+                free_idx = self.random.randint(
+                    0, len(self.designated_player_positions) - 1
+                )
                 player.move_abs(self.designated_player_positions[free_idx])
                 del self.designated_player_positions[free_idx]
             elif len(self.free_positions) > 0:
-                free_idx = random.randint(0, len(self.free_positions) - 1)
+                free_idx = self.random.randint(0, len(self.free_positions) - 1)
                 player.move_abs(self.free_positions[free_idx])
                 del self.free_positions[free_idx]
             else: