Automatic Hooks

No more manually connecting Players.PlayerAdded or CharacterAdded yourself. If a method with one of these exact names exists on your Service or Controller, Owl wires it up automatically during OwlStart you just define the method and it fires when it should.

Server hooks (Services)

Method Signature Fires when
OwlOnPlayerAdded (plr: Player) A player joins or is already in-game when the Service starts
OwlOnPlayerRemoving (plr: Player) A player leaves the game
OwlOnCharacterAdded (plr: Player, char: Model) A character spawns (initial spawn or respawn)
OwlOnCharacterRemoving (plr: Player, char: Model) A character is about to be removed
OwlOnSpawnReady (plr: Player, char: Model) ⚠️ CharacterAutoLoads = false mode only - see Owl vs Knit

Client hooks (Controllers)

Method Signature Fires when
OwlOnCharacterAdded (char: Model) The LocalPlayer's character spawns
OwlOnCharacterRemoving (char: Model) The LocalPlayer's character is about to be removed
OwlOnLocalPlayerReady (plr: Player) The LocalPlayer is ready and PlayerGui has loaded, the right place for UI setup
OwlOnPlayerCharacterReady (plr: Player, char: Model) A character has fully loaded (Humanoid + HumanoidRootPart both present)
OwlOnPlayerLeft (plr: Player) A player leaves (visible client-side, for other players leaving)

Using them

Just define the method with the exact name and signature from the tables above, no registration call, no Connect:

function DataService:OwlOnPlayerAdded(plr: Player)
    self._playerData[plr.UserId] = { Points = 0 }
end
 
function DataService:OwlOnPlayerRemoving(plr: Player)
    self._playerData[plr.UserId] = nil
end

OwlOnPlayerAdded firing "for players already present at startup" matters more than it looks: without it, a Service that starts after players have already joined (a redeploy scenario or a Service with heavy Dependencies) would silently skip initializing data for anyone already connected. Owl handles that edge case for you, you never need an extra for _, plr in Players:GetPlayers() loop alongside PlayerAdded.

Hooks run inside the module's OwlStart phase, so everything covered in Lifecycle still applies, by the time any hook fires, every Service and Controller has already finished OwlInit.

Where to go next

  • Lifecycle - how these hooks fit into OwlInit/OwlStart/OwlDestroy.
  • Owl vs Knit - more on OwlOnSpawnReady and manual-spawn mode.
  • Services and Controllers - where these hooks are typically defined alongside the rest of a module's logic.