fix: game.player → game.players[1] for RCON compatibility

RCON에서 game.player는 nil이므로 game.players[1] 사용.
- PLAYER_HELPER 상수 추가 (nil 체크 포함)
- check_player() 메서드 추가
- lua_with_player() 메서드 추가
This commit is contained in:
2026-03-25 15:08:04 +09:00
parent 149e66e9c9
commit 4756ef9624

View File

@@ -7,6 +7,15 @@ import struct
import time
# 모든 Lua 코드 앞에 붙일 플레이어 참조 헬퍼
# RCON에서는 game.player가 nil이므로 game.players[1]을 사용
PLAYER_HELPER = """
local p = game.players[1]
if not p then rcon.print("NO_PLAYER") return end
if not p.character then rcon.print("NO_CHARACTER") return end
"""
class FactorioRCON:
"""팩토리오 RCON 클라이언트"""
@@ -35,7 +44,6 @@ class FactorioRCON:
def run(self, lua_command: str) -> str:
"""Lua 명령 실행 후 결과 반환"""
# /c 없이 순수 Lua로 전송 (RCON은 자동으로 콘솔 명령으로 처리)
cmd = f"/c {lua_command}"
req_id = self._send_packet(2, cmd) # type 2 = EXECCOMMAND
result = self._recv_packet()
@@ -45,6 +53,29 @@ class FactorioRCON:
"""여러 줄 Lua 코드 실행"""
return self.run(code)
def lua_with_player(self, code: str) -> str:
"""플레이어 참조(p)를 자동으로 주입한 Lua 코드 실행.
code 안에서 'p'로 플레이어를 참조할 수 있음."""
return self.run(PLAYER_HELPER + code)
def check_player(self) -> bool:
"""접속한 플레이어가 있는지 확인"""
result = self.run("""
local count = 0
for _ in pairs(game.players) do count = count + 1 end
if count == 0 then
rcon.print("NO_PLAYER")
else
local p = game.players[1]
if p.character then
rcon.print("OK:" .. p.name .. ":" .. string.format("%.0f,%.0f", p.position.x, p.position.y))
else
rcon.print("NO_CHARACTER:" .. p.name)
end
end
""")
return result.startswith("OK")
def _send_packet(self, ptype: int, body: str) -> int:
req_id = self._req_id
self._req_id += 1
@@ -55,7 +86,6 @@ class FactorioRCON:
return req_id
def _recv_packet(self) -> dict:
# 패킷 크기 읽기
raw = self._recv_bytes(4)
size = struct.unpack("<i", raw)[0]
data = self._recv_bytes(size)