$value) { if (!$reflection->hasProperty($key)) continue; $property = $reflection->getProperty($key); $type = $property->getType(); $assignValue = $value; // 1. 빈 문자열('') 처리 로직 개선 if ($value === '') { // 프로퍼티가 null을 허용하는 경우에만 null 할당 if ($type instanceof ReflectionNamedType && $type->allowsNull()) { $assignValue = null; } else { // null을 허용하지 않는 경우, 타입별 기본값 지정 $typeName = ($type instanceof ReflectionNamedType) ? $type->getName() : ''; $assignValue = ($typeName === 'int' || $typeName === 'float') ? 0 : ''; } } // 2. 값이 존재할 때의 타입별 캐스팅 로직 elseif ($type instanceof ReflectionNamedType) { $typeName = $type->getName(); // 타입이 array이고 입력값이 문자열인 경우 (CSV -> Array) if ($typeName === 'array' && is_string($value)) { $assignValue = explode(DEFAULTS["DELIMITER_ROLE"], $value); } // 타입이 int이고 입력값이 숫자형인 경우 elseif ($typeName === 'int' && is_numeric($value)) { $assignValue = (int) $value; } // 타입이 float이고 입력값이 숫자형인 경우 elseif ($typeName === 'float' && is_numeric($value)) { $assignValue = (float) $value; } } // 최종 값 할당 $this->{$key} = $assignValue; } } // [중요] final 해제 또는 로직 변경 public function toArray(): array { // get_object_vars는 protected를 가져오지 못하므로 // Reflection을 사용하여 모든 프로퍼티를 가져오되, // 값을 가져올 때는 $this->{$name}을 통해 Getter나 매직메서드가 작동하게 합니다. $reflection = new ReflectionClass($this); $properties = $reflection->getProperties(); $result = []; foreach ($properties as $property) { $name = $property->getName(); // $this->$name 처리를 통해 자식의 __get()이 호출되도록 유도 $result[$name] = $this->{$name}; } return $result; } }