2026-06-18 TIL (79μΌμ°¨)
π μΈλ¦¬μΌ μμ§ λ©ν°νλ μ΄μ΄ λ€νΈμν¬ ν΅μ¬ κ°λ μ΄μ 리
μΈλ¦¬μΌ μμ§μ λ©ν°νλ μ΄μ΄ νκ²½μ μ² μ ν ν΄λΌμ΄μΈνΈ-μλ²(Client-Server) μν€ν μ²λ₯Ό κΈ°λ°μΌλ‘ μλν©λλ€. μ±κ³΅μ μΈ λ©ν°νλ μ΄ κ²μμ κ°λ°νκΈ° μν΄ λ°λμ μμμΌ ν λ€νΈμν¬μ ν΅μ¬ κ°λ κ³Ό μ£Όμ ν΄λμ€λ€μ μν μ μ 리νμ΅λλ€.
1. μλ²μ μ λμ κΆν (Server Authority)κ³Ό ν€λ리μ€(Headless)
βοΈ μλ²λ κ²μμ βμ λμ μΈ μ¬νβ
μλ²λ κ²μ λ΄μμ μΌμ΄λλ λͺ¨λ μΌμ μ΅μ’ κ²°μ κΆμ(Authority)μ λλ€. ν΄λΌμ΄μΈνΈ(νλ μ΄μ΄μ μ»΄ν¨ν°)κ° βλ΄κ° μ μ λ§μ·λ€!βλΌκ³ 보λ΄λ ν¨ν·μ 무쑰건 μ λ’°νμ§ μμ΅λλ€. ν΄λΌμ΄μΈνΈμ λ°μ΄ν°λ₯Ό κ·Έλλ‘ λ―ΏμΌλ©΄ ν¨ν· λ³μ‘°λ₯Ό ν΅ν ν΄νΉ(μ: 무쑰건 ν€λμ· μ μ€)μ 무방λΉλ‘ λ ΈμΆλκΈ° λλ¬Έμ λλ€. λ°λΌμ μλ²λ μ§μ 보μ΄μ§ μλ λ§΅μ μ΄μμ λ°μ¬ν΄ λ³΄κ³ , μ₯μ λ¬Όμ λ§νμ§ μκ³ μ μ€νλμ§λ₯Ό 물리μ μΌλ‘ κ³μ°νμ¬ νμ ν©λλ€.
π βλμ κ°λ¦° 보λκ²μ λ§μ€ν°β (Headless Server)
λ°λμΌμ΄ν°λ μλ²(Dedicated Server)λ κ·Έλν½(λ λλ§)κ³Ό μ리(μ€λμ€) κΈ°λ₯μ μμ ν κΊΌλ²λ¦° ν€λ리μ€(Headless) μνλ‘ κ΅¬λλ©λλ€.
- ν΄λΌμ΄μΈνΈμ λ§΅: λΉ, κ·Έλ¦Όμ, μΊλ¦ν° μΈν, νκ²½μ λ± λμ 보μ΄κ³ λ€λ¦¬λ λͺ¨λ κ²μ λ λλ§ν©λλ€.
- μλ²μ λ§΅: νλ €ν κ·Έλν½μ μμ§λ§, ν¬λͺ ν 물리 μΆ©λ체(Collision), AI μ΄λ κ²½λ‘(NavMesh), 보μ΄μ§ μλ νΈλ¦¬κ±° λ± κ²μ νμ μ νμν λΌλλ§μ λ©λͺ¨λ¦¬μ λμ ν΅μ ν©λλ€.
2. λ°μ΄ν° λκΈ°νμ 리ν리μΌμ΄μ (Replication)
π‘ μλ² μ€νκ³Ό λκΈ° (Listen)
μλ²κ° Open {Levelμ΄λ¦}?Listen λͺ
λ Ήμ΄λ₯Ό μ€ννλ©΄, μλ² μ»΄ν¨ν°κ° λ§΅μ μ΄κ³ μμΌ(Socket, ν΅μ ꡬλ©)μ κ°λ°©νμ¬ λ€λ₯Έ νλ μ΄μ΄λ€μ μ μμ κΈ°λ€λ¦½λλ€. μ΄λ μλ²κ° ν΄λΌμ΄μΈνΈμκ² 3D λ§΅ μμ
μ΄λ κ·Έλν½ νμΌμ λ€μ΄λ‘λν΄ μ£Όλ κ²μ΄ μλλλ€(μμ
μ μ΄λ―Έ κ°μμ νλλμ€ν¬μ μ€μΉλμ΄ μμ). μλ²κ° λΏμ΄λ΄λ κ²μ βμ’ν, 체λ ₯, μν λ³ν λ±μ μμ λ°μ΄ν°βμ
λλ€.
π― μλ³Έκ³Ό 볡μ¬λ³Έμ κ΄κ³
- μλ³Έ (Authority): κ²μ μΈκ³μ βμ§μ§β λͺ¬μ€ν°, μμ΄ν , μΊλ¦ν°λ μ€μ§ μλ²μλ§ μ‘΄μ¬ν©λλ€.
- 볡μ¬λ³Έ (Proxy): ν΄λΌμ΄μΈνΈ νλ©΄μ 보μ΄λ λͺ¨λ κ²λ€μ μλ²κ° 보λ΄μ€ μ 보λ₯Ό λ°νμΌλ‘ νλ΄ λ΄κ³ μλ βκ»λ°κΈ°(볡μ¬λ³Έ)βμ λλ€. μ΄λ κ² μλ²μ μνλ₯Ό ν΄λΌμ΄μΈνΈμ λκΈ°ννλ κ³Όμ μ 리ν리μΌμ΄μ (Replication)μ΄λΌκ³ ν©λλ€.
3. πΊοΈ μ£Όμ ν΄λμ€μ μμ‘΄ ꡬμ (μ΄λμ μ‘΄μ¬νλκ°?)
μΈλ¦¬μΌ μμ§ λ©ν°νλ μ΄μ ν΅μ¬μ βμ΄ ν΄λμ€κ° λꡬμ μ»΄ν¨ν°μ μ‘΄μ¬νλκ°?βλ₯Ό νμ νλ κ²μ λλ€.
| ν΄λμ€ (Class) | μλ² (Server) | λ΄ μ»΄ν¨ν° (λ) | λ¨μ μ»΄ν¨ν° (νμΈ) | μν λ° λΉμ |
|---|---|---|---|---|
| GameMode | π΅ (μλ³Έ) | β | β | μ¬νλ§ μλ λΉλ° λ£°λΆ. μ μ κ³μ°, μΉλ¦¬ 쑰건 λ±μ κ΄λ¦¬. (ν΄λΌμ΄μΈνΈμ μμΌλ©΄ ν΄νΉ μν) |
| PlayerController | π΅ (μλ³Έ) | π΅ (볡μ¬λ³Έ) | β | λλ§ μ₯κ³ μλ 리λͺ¨μ»¨. λμ ν€λ³΄λ/λ§μ°μ€ μ λ ₯μ μ²λ¦¬. λ¨μ 컨νΈλ‘€λ¬λ λ΄ μ»΄ν¨ν°μ μ‘΄μ¬νμ§ μμ (Null). |
| Character / Pawn | π΅ (μλ³Έ) | π΅ (볡μ¬λ³Έ) | π΅ (볡μ¬λ³Έ) | κ²½κΈ°μ₯μ λ°λ μ‘체. λ΄κ° μμ§μ΄λ©΄ λ¨λ€ νλ©΄μμλ μμ§μ¬μΌ νλ―λ‘ λͺ¨λμκ² λκΈ°νλ¨. |
| PlayerState | π΅ (μλ³Έ) | π΅ (볡μ¬λ³Έ) | π΅ (볡μ¬λ³Έ) | μ μ λ±λ²νΈμ μ μν. λ¨μ 컨νΈλ‘€λ¬λ₯Ό λ³Ό μ μμΌλ―λ‘, λλ€μ, ν(Ping), K/D μ μ λ± κ³΅κ° μ 보λ₯Ό λ΄μ λͺ¨λμκ² λΏλ €μ£Όλ κ°λ°©. |
(π‘ μ°Έκ³ : ν΄λΌμ΄μΈνΈμμ GetGameMode()λ₯Ό νΈμΆνλ©΄ νμ nullptrμ λ°νν©λλ€. κ²μλͺ¨λλ μλ²μλ§ μκΈ° λλ¬Έμ
λλ€. κ²μλͺ¨λμ μ κ·Όνλ €λ©΄ HasAuthority()λ₯Ό ν΅ν΄ νμ¬ μ½λκ° μλ²μμ μ€ν μ€μΈμ§ νμΈν΄μΌ ν©λλ€.)
4. λ€νΈμν¬ νλΆ κ΅¬μ‘° (NetDriver, NetConnection, NetMode)
μΈλ¦¬μΌ μμ§μ΄ μ΄ λ³΅μ‘ν ν΅μ μ μ΄λ»κ² κ΄λ¦¬νλμ§ λ‘μ°λ 벨(Low-level) ꡬ쑰λ₯Ό μ΄ν΄νλ κ²λ μ€μν©λλ€.
π NetDriver μ NetConnection (μΈν°λ· 곡μ κΈ°μ λμ )
- NetDriver (μΈν°λ· 곡μ κΈ°): μ»΄ν¨ν°μ λ€νΈμν¬ ν¬νΈ(Socket)λ₯Ό μ§μ μ΄κ³ λ«μΌλ©°, μΈλΆμμ λ€μ΄μ€λ λͺ¨λ λ°μ΄ν°λ₯Ό κ°μ₯ λ¨Όμ λ°μλ΄λ λ€νΈμν¬ μ΄κ΄ κ΄λ¦¬μ(Hub)μ λλ€. μ±κΈνλ μ΄μμλ μ‘΄μ¬νμ§ μμΌλ©° λ©ν°νλ μ΄ μμλ§ μμ±λ©λλ€.
- NetConnection (κ°λ³ λμ ): 곡μ κΈ°μ 1λ², 2λ² μ»΄ν¨ν°λ‘ κ°λ λμ μ΄ κ½ν μλ―μ΄, νΉμ μ»΄ν¨ν° 1λμ ν΅μ νκΈ° μν΄ λ§λ€μ΄μ§ μ μ© ν΅μ νμ΄ν(κ°μ²΄)μ λλ€.
μ΄ κ΅¬μ‘°λ₯Ό μ€μ μΈλ¦¬μΌ μμ§μ C++ μ½λ λλμΌλ‘ λ¨μνν΄μ 보면 μ΄λ μ΅λλ€.
1
2
3
4
5
6
7
8
9
10
class UNetDriver
{
// [μλ²μ©] λμκ² μ μν μ¬λ¬ νλ μ΄μ΄λ€μ λμ λ€λ° (λ°°μ΄)
TArray<UNetConnection*> ClientConnections;
// [ν΄λΌμ΄μΈνΈμ©] λ΄κ° μλ²μ μ°κ²°νκΈ° μν΄ κ½μ λ¨ νλμ λμ
UNetConnection* ServerConnection;
// ... κΈ°ν λ€νΈμν¬ μ²λ¦¬ ν¨μλ€ ...
}
β κΆκΈμ¦ ν΄κ²°: UNetDriverλ λλ체 μ΄λμ μλ κ±ΈκΉ?
UNetDriverλ μΈλ¦¬μΌ μμ§ μμ€ μ½λμ λ΄μ₯λ ν΅μ¬ C++ ν΄λμ€μ
λλ€. μΈλΆμ μ 3μ μλ² νλ‘κ·Έλ¨μ΄ μλλΌ, μλ² μ»΄ν¨ν°μ ν΄λΌμ΄μΈνΈ μ»΄ν¨ν°κ° κ°κ° μμ μ λ©λͺ¨λ¦¬(RAM)μ μ§μ μμ±ν΄μ λ€κ³ μλ κ°μ²΄μ
λλ€.
- μλ² μ»΄ν¨ν°: λ©ν°νλ μ΄ λ°©μ μ΄λ©΄ μμ§ λ΄λΆμμ μκΈ°λ§μ
UNetDriverλ₯Ό νλ μΌλλ€. (κ±°λν μ°μ²΄κ΅ λ³Έμ ) - ν΄λΌμ΄μΈνΈ μ»΄ν¨ν°: μλ²μ μ μνλ €κ³ νλ©΄ μμ§ λ΄λΆμμ μκΈ°λ§μ
UNetDriverλ₯Ό νλ μΌλλ€. (λλ€ μ°μ²΄κ΅ μ§μ )
μ¦, λ©ν°νλ μ΄κ° μΌμ§λ μκ° κ°μμ μ»΄ν¨ν° μμμ μΈλ¦¬μΌ μμ§μ΄ μ€μ€λ‘ UNetDriverλ₯Ό κΉ¨μ μλ‘ ν΅μ μ μμνλ ꡬ쑰μ
λλ€.
π‘ μ¬ν 1: μν λΆλ΄ (μ°μ²΄κ΅κ³Ό μ°μ²΄λΆ)
κ° μ»΄ν¨ν°κ° λ€κ³ μλ λ·λλΌμ΄λ²λ μ΄ μ»€λ₯μ κ°μ²΄λ€μ κ΄λ¦¬νλ©° λ€μκ³Ό κ°μ΄ μν μ λΆλ΄ν©λλ€.
- UNetDriver (μ°μ²΄κ΅ μ§μ€κ΅): μΈν°λ· λ§μμ λ μμ€λ λͺ¨λ λ°μ΄ν°(ν¨ν·)λ₯Ό 무μμ λ°μ κ²λ©΄μ λ³΄κ³ βμ, μ΄κ±΄ 1λ² λμ μμ μ¨ λ°μ΄ν°λ€?β νκ³ λΆλ₯νμ¬ ν΄λΉ
UNetConnectionμκ² ν μ€ν©λλ€. - UNetConnection (κ°μΈ μ λ΄ μ°μ²΄λΆ): μκΈ°κ° λ΄λΉνλ νλ μ΄μ΄μ λ°μ΄ν°λ§ μ λ¬Έμ μΌλ‘ μ²λ¦¬ν©λλ€. μλλ°©μ ν(Ping) κ³μ°, ν¨ν· μ μ€ μ μ¬μ μ‘ μμ²μ μννλ©°, κ°μ₯ μ€μνκ²λ μ΄ λμ μ λμ μ΄λ€
PlayerControllerκ° μ°κ²°λμ΄ μλμ§ κΈ°μ΅νκ³ κ΄λ¦¬ν©λλ€.
π‘ μ¬ν 2: NetConnectionμ μ 체μ μμ± μμ
μ΄λ³΄μλ€μ΄ κ°μ₯ λ§μ΄ νλ μ€ν΄ μ€ νλλ βClientConnection, ServerConnection, UNetConnectionμ΄ λͺ¨λ λ€λ₯Έ κ°μ²΄μΈκ°?β νλ κ²μ λλ€.
κ²°λ‘ λΆν° λ§νμλ©΄, ClientConnectionκ³Ό ServerConnectionμ μ 체(λ°μ΄ν° νμ
)κ° λ°λ‘ UNetConnectionμ
λλ€. μ¦, UNetConnectionμ βν΅μ μΌμ΄λΈ(λμ )β κ·Έ μ체λ₯Ό μλ―Ένλ μ€κ³λ(ν΄λμ€)μ
λλ€. μλ² μ
μ₯μμλ λ΄κ² κ½ν λμ μ βν΄λΌμ΄μΈνΈ 컀λ₯μ
βμ΄λΌ λΆλ₯΄κ³ , ν΄λΌμ΄μΈνΈ μ
μ₯μμλ λ΄ μ»΄ν¨ν°μ κ½ν λμ μ βμλ² μ»€λ₯μ
βμ΄λΌκ³ λΆλ₯Ό λΏ, μ€μ λ‘λ λμΌν νμ
μ μλ°©ν₯ νμ΄νμ
λλ€.
μ΄ λμ (UNetConnection)μ μΈμ μμ±λ κΉμ? ν΅μ μ΄ λ°μν λλ§λ€ μκΈ°λ κ²μ΄ μλλΌ, βνλ μ΄μ΄κ° μλ²μ μ²μ μ μμ μλνλ λ°λ‘ κ·Έ μκ°(Handshake)βμ λ± ν λ² μμ±λ©λλ€.
- ν΄λΌμ΄μΈνΈμ μ μ μλ: ν΄λΌμ΄μΈνΈκ° μλ²μ μ μμ μλνλ©΄, ν΄λΌμ΄μΈνΈ μ»΄ν¨ν°μ
UNetDriverκ° μ¦μUNetConnectionκ°μ²΄λ₯Ό μμ±(ServerConnectionμ μ μ₯)νκ³ μλ²μ λ Έν¬(μμ²)ν©λλ€. - μλ²μ μλ½: μλ²κ° μμ²μ λ°μΌλ©΄, μλ²μ
UNetDriverμμ μλ‘μ΄UNetConnectionκ°μ²΄λ₯Ό μμ±νμ¬ μμ μClientConnectionsλ°°μ΄μ μΆκ°ν©λλ€. - μ°κ²° μλ£: μμͺ½ μ»΄ν¨ν°μ κ°κ°
UNetConnectionμ΄ μμ±λμ΄ λ Όλ¦¬μ μΌλ‘ μ°κ²°μ΄ μλ£λλ©΄, μμ λ°°μ΄PlayerControllerκ° μ΄ λμ μ νκ³ ν΄λΌμ΄μΈνΈμκ² λ°κΈλ©λλ€.
π μμ κΆ (Ownership)
λ©ν°νλ μ΄μμλ βλκ° μ΄ μ‘ν°μ μ§μ§ μ£ΌμΈμΈκ°?βλ₯Ό λ°μ§λ μμ κΆ(Ownership)μ΄ λ§€μ° μ€μν©λλ€. RPC(μ격 νλ‘μμ νΈμΆ)μ μ€ν κΆνμ κ²°μ νκΈ° λλ¬Έμ λλ€.
- μμ κΆ νΈλ¦¬:
ClientConnectionβ‘οΈPlayerControllerβ‘οΈPawn(Character)β‘οΈWeapon(무기 μ‘ν°) - μ΄ μμ κ΄κ³(Family)μ μν΄ μλ€λ©΄, μ‘ν°μμ
GetNetConnection()μ νΈμΆνμ λ λ³ΈμΈμ μ‘°μ’ νλ ν΅μ κ°μ²΄λ₯Ό μ μμ μΌλ‘ λ°μμ¬ μ μμ΅λλ€.
π₯οΈ λ· λͺ¨λ (NetMode)
νμ¬ μ½λκ° μ€νλκ³ μλ μ»΄ν¨ν°μ μ 체(μν )λ₯Ό λνλ
λλ€. (GetNetMode() ν¨μλ‘ νμΈ κ°λ₯)
- NM_Standalone: μ±κΈνλ μ΄ λͺ¨λ. (λ€νΈμν¬ μ°κ²° μμ)
- NM_DedicatedServer: νλ μ΄μ΄(κ·Έλν½/μ¬μ΄λ) μμ΄ μ€μ§ κ²μ λ‘μ§λ§ λμκ°λ μμ μλ².
- NM_ListenServer: λκ΅°κ°κ° λ°©μ₯(νΈμ€νΈ)μ΄ λμ΄ μλ² μν κ³Ό ν΄λΌμ΄μΈνΈ(νλ μ΄) μν μ λμμ μννλ μλ².
- NM_Client: μλ²μ μ μνμ¬ νλ©΄μ λ λλ§νκ³ μ λ ₯μ 보λ΄λ μΌλ° μ μμ.
5. ν΅μ¬ μμ½: λ‘μ§ μ²λ¦¬μ 보μ
λ°λ―Έμ§ κ³μ°, μμ΄ν νλ, μ€ν― λ³ν λ± κ²μμ μ€λν μν₯μ λ―ΈμΉλ λͺ¨λ ν΅μ¬ λ‘μ§μ λ°λμ μλ²(Authority)μμλ§ μ²λ¦¬ν΄μΌ ν©λλ€.
ν΄λΌμ΄μΈνΈμμ λ°λ―Έμ§λ₯Ό κΉλλ‘ κ΅¬ννλ©΄, ν΄μ»€κ° ν¨ν· μ€λν/λ³μ‘°λ₯Ό ν΅ν΄ μ‘°μλ λ°μ΄ν°λ₯Ό μλ²λ‘ λ³΄λ΄ κ²μ μνκ³λ₯Ό νκ΄΄ν μ μμ΅λλ€. ν΄λΌμ΄μΈνΈλ μ€μ§ βλ§μ°μ€λ₯Ό ν΄λ¦νλ€(곡격 μλ)βλΌλ μ λ ₯(Input)λ§μ μλ²μ μ λ¬νκ³ , κΉμΈ 체λ ₯μ κ²°κ³Όκ°(Replication)μ λ°μ νλ©΄μ UIλ₯Ό κ°±μ νλ μν λ§ μνν΄μΌ ν©λλ€.