--- /dev/null
+using Robust.Shared.Prototypes;
+
+namespace Content.Server.Antag.Mimic;
+
+/// <summary>
+/// Replaces the relevant entities with mobs when the game rule is started.
+/// </summary>
+[RegisterComponent]
+public sealed partial class MobReplacementRuleComponent : Component
+{
+ // If you want more components use generics, using a whitelist would probably kill the server iterating every single entity.
+
+ [DataField]
+ public EntProtoId Proto = "MobMimic";
+
+ /// <summary>
+ /// Chance per-entity.
+ /// </summary>
+ [DataField]
+ public float Chance = 0.001f;
+}
--- /dev/null
+using Content.Server.Antag.Mimic;
+using Content.Server.GameTicking.Rules;
+using Content.Server.GameTicking.Rules.Components;
+using Content.Shared.VendingMachines;
+using Robust.Shared.Map;
+using Robust.Shared.Random;
+
+namespace Content.Server.Antag;
+
+public sealed class MobReplacementRuleSystem : GameRuleSystem<MobReplacementRuleComponent>
+{
+ [Dependency] private readonly IRobustRandom _random = default!;
+
+ protected override void Started(EntityUid uid, MobReplacementRuleComponent component, GameRuleComponent gameRule, GameRuleStartedEvent args)
+ {
+ base.Started(uid, component, gameRule, args);
+
+ var query = AllEntityQuery<VendingMachineComponent, TransformComponent>();
+ var spawns = new List<(EntityUid Entity, EntityCoordinates Coordinates)>();
+
+ while (query.MoveNext(out var vendingUid, out _, out var xform))
+ {
+ if (!_random.Prob(component.Chance))
+ continue;
+
+ spawns.Add((vendingUid, xform.Coordinates));
+ }
+
+ foreach (var entity in spawns)
+ {
+ var coordinates = entity.Coordinates;
+ Del(entity.Entity);
+
+ Spawn(component.Proto, coordinates);
+ }
+ }
+}