OnApartmentRoomBreakInCompleted
OnApartmentRoomBreakInCompleted is called after a player finishes breaking into an apartment room through its door, once the break-in is committed and the success toast has been shown. It fires at the end of ApartmentDoor.CompleteBreakIn.
void OnApartmentRoomBreakInCompleted(ApartmentRoom apartmentRoom, BasePlayer player, ApartmentDoor apartmentDoor)Parameters
| Parameter | Type | Description |
|---|---|---|
apartmentRoom | ApartmentRoom | The ApartmentRoom instance the player just broke into. Use it to identify the room, for example by its net ID or position, and to read or change room state. |
player | BasePlayer | The BasePlayer who completed the break-in. Use it to reward, message, notify the owner, or log the actor; check it for null before touching members. |
apartmentDoor | ApartmentDoor | The ApartmentDoor that was broken in. It is the entity whose CompleteBreakIn method ran, so you can read its position, owner ID and network ID. |
Return value
The return value is ignored. CompleteBreakIn returns void and the hook call is informational only, so returning a value or null changes nothing about the break-in, the toast, or the room state.
How it works
This hook runs at the tail of ApartmentDoor.CompleteBreakIn, after the held item has been used, StartBreakIn has been applied to the room, the player has received the blue success toast, and the break-in sound has been stopped. It is therefore a notification that the break-in already happened: nothing in the original method depends on your return value, so you cannot cancel or roll back the break-in from here.
apartmentRoom is the room that was entered, player is the actor who completed the break-in, and apartmentDoor is the door entity the break-in went through. The door is the most reliable handle for logging and proximity checks, because it is the object whose method fired. Declaring the parameters exactly as given is enough; since this hook only has one injection site with these types, there is no type-narrowing trick to apply here.
Use it for server-side consequences of a break-in: warning the room owner or their team, writing an audit line, starting a cooldown timer, or firing a custom event for other plugins. Keep the handler cheap, because it runs in the same frame as the break-in and any heavy work delays the player. Combine it with the checkout, purchase and upgrade hooks to build a full apartment audit trail.
Example plugin: Alert the room owner when someone breaks in
using System;
using System.Collections.Generic;
using Newtonsoft.Json;
using Oxide.Core;
using UnityEngine;
namespace Oxide.Plugins
{
[Info("Apartment BreakIn Alert", "RustPluginGenerator", "1.0.0")]
[Description("Notifies the apartment owner when another player completes a break-in through a door.")]
public class ApartmentBreakInAlert : RustPlugin
{
private const string PermAdmin = "apartmentbreakinalert.admin";
private class PluginConfig
{
[JsonProperty("Alert owner on break-in")]
public bool AlertOwner { get; set; } = true;
[JsonProperty("Seconds between alerts per owner")]
public float CooldownSeconds { get; set; } = 30f;
}
private PluginConfig config;
private readonly Dictionary<ulong, float> lastAlert = new Dictionary<ulong, float>();
protected override void LoadDefaultConfig() => config = new PluginConfig();
protected override void LoadConfig()
{
base.LoadConfig();
try
{
config = Config.ReadObject<PluginConfig>();
if (config == null) throw new Exception();
}
catch
{
PrintWarning("Configuration file is invalid, using defaults");
LoadDefaultConfig();
}
SaveConfig();
}
protected override void SaveConfig() => Config.WriteObject(config);
protected override void LoadDefaultMessages()
{
lang.RegisterMessages(new Dictionary<string, string>
{
["Alert"] = "{0} broke into your apartment at {1}.",
["NoOwner"] = "This apartment has no reachable owner to alert.",
["PermDenied"] = "You do not have permission to use this command."
}, this);
}
private string Msg(string key, string userId = null, params object[] args) => string.Format(lang.GetMessage(key, this, userId), args);
private void Init()
{
permission.RegisterPermission(PermAdmin, this);
}
private void OnApartmentRoomBreakInCompleted(ApartmentRoom apartmentRoom, BasePlayer player, ApartmentDoor apartmentDoor)
{
if (!config.AlertOwner || player == null || apartmentDoor == null) return;
ulong ownerId = apartmentDoor.OwnerID;
if (ownerId == 0 || ownerId == player.userID.Get()) return;
float now = UnityEngine.Time.realtimeSinceStartup;
float last;
if (lastAlert.TryGetValue(ownerId, out last) && now - last < config.CooldownSeconds) return;
lastAlert[ownerId] = now;
BasePlayer owner = BasePlayer.FindByID(ownerId);
if (owner == null || !owner.IsConnected) return;
Vector3 pos = apartmentDoor.transform.position;
owner.ChatMessage(Msg("Alert", owner.UserIDString, player.displayName, $"({pos.x:F0}, {pos.z:F0})"));
}
[ConsoleCommand("apartmentbreakin.test")]
private void CmdTest(ConsoleSystem.Arg arg)
{
BasePlayer admin = arg.Player();
if (admin != null && !permission.UserHasPermission(admin.UserIDString, PermAdmin))
{
arg.ReplyWith(Msg("PermDenied", admin.UserIDString));
return;
}
if (!admin.IsAdmin)
{
arg.ReplyWith(Msg("NoOwner", admin.UserIDString));
return;
}
arg.ReplyWith("OnApartmentRoomBreakInCompleted is passive; check the server console for alerts.");
}
private void Unload()
{
lastAlert.Clear();
}
}
}The plugin stores an optional Discord-style announcement toggle and a cooldown in its config. When OnApartmentRoomBreakInCompleted fires it skips inactive players, builds a readable message with the actor's display name and the door position, and alerts the owner of the door (by OwnerID) if that player is online and is not the actor. To avoid chat spam on repeated break-ins of the same door, a per-owner cooldown is tracked in a dictionary and reset on every alert. A console command lets admins replay the last alert for testing, and Unload clears the stored timers state.
Common use cases
Owner notifications
Message the apartment owner or their team when an intruder completes a break-in, including the intruder's name and the door coordinates, so defenders can respond.
Break-in audit log
Write a timestamped line with actor ID, door net ID and position to a data file for later review of contested apartment blocks.
Reward or event trigger
Grant a small item or run a custom server event only after a successful break-in, using the door entity to verify the location is inside an intended zone.
Pitfalls
Too late to cancel
The break-in is already committed when this hook fires and the return value is ignored. Use a door or damage hook if you need to prevent the action.
Owner may be offline
OwnerIDis a ulong and can refer to a sleeping or disconnected player. UseBasePlayer.FindByIDand null-check before sending anything.Frequent calls on busy servers
Do not call
PutsorPrintWarningin the handler. Send player-facing text through lang messages and rate-limit repeated alerts per owner.
Build a plugin with OnApartmentRoomBreakInCompleted
Describe what should happen and get a compiled plugin that uses this hook.
Edit the prompt on the next screen. 2 free plugins a month, no card.
Last updated Oct 26, 2026. Found a mistake? Email support@rustplugingenerator.com.
Build a plugin with OnApartmentRoomBreakInCompleted
Generate