PHP7에서 PHP8로 업그레이드할 때 발생하는 Fatal Error, Deprecated 경고, TypeError, Undefined Array Key 등 주요 마이그레이션 오류를 사례별로 정리했습니다. 실무 환경에서 바로 적용 가능한 해결 방법과 체크리스트를 함께 소개합니다.

PHP7 → PHP8 마이그레이션 과정에서는 예상보다 많은 호환성 문제가 발생할 수 있습니다. 특히 오래된 레거시 프로젝트나 CodeIgniter, Laravel, 자체 구축 CMS 환경에서는 PHP8의 강화된 타입 검사와 문법 변경으로 인해 기존 코드가 정상적으로 동작하지 않는 경우가 많습니다.
이번 글에서는 PHP7에서 PHP8로 업그레이드할 때 가장 많이 발생하는 오류와 실무 해결 방법을 정리합니다. 서버 이전, 리눅스 업그레이드, Apache 또는 Nginx 버전 변경과 함께 진행하는 경우가 많기 때문에 실제 운영 환경 기준으로 설명합니다.
PHP8 마이그레이션 전 반드시 확인해야 하는 이유
PHP8은 단순한 성능 개선 버전이 아닙니다.
다음과 같은 큰 변화가 포함되어 있습니다.
| 타입 검사 | 비교적 느슨함 | 엄격함 |
| Warning | 무시 가능 | Fatal Error 발생 가능 |
| 내부 함수 | NULL 허용 많음 | NULL 허용 제한 |
| 문자열 처리 | 암묵적 변환 | 명시적 처리 필요 |
| Array 접근 | Warning | Error 가능 |
즉, PHP7에서는 동작하던 코드가 PHP8에서는 중단될 수 있습니다.
1. Undefined Array Key 오류
오류 예시
$name = $_GET['name'];
PHP7
Notice: Undefined index: name
PHP8
Warning: Undefined array key "name"
원인
존재하지 않는 배열 키를 직접 호출했기 때문입니다.
해결 방법
$name = $_GET['name'] ?? '';
또는
if (isset($_GET['name'])) {
$name = $_GET['name'];
}
실무에서는 Null Coalescing Operator를 사용하는 것이 가장 일반적입니다.
$name = $_POST['name'] ?? '';
$email = $_POST['email'] ?? '';
2. Trying to Access Array Offset on Value of Type Null
오류 예시
$data = null;
echo $data['name'];
오류
Trying to access array offset on value of type null
원인
배열이라고 가정했지만 실제 값은 NULL입니다.
해결 방법
echo $data['name'] ?? '';
또는
if (is_array($data)) {
echo $data['name'];
}
API 응답 처리 시 자주 발생하는 오류입니다.
3. implode() Parameter Order 오류
PHP7에서는 동작하던 코드입니다.
implode($array, ',');
PHP8에서는 오류가 발생합니다.
TypeError
해결 방법
순서를 변경해야 합니다.
implode(',', $array);
공식 문법은 항상 구분자가 첫 번째 인자입니다.
4. count() Parameter Must Be an Array
오류 예시
$data = null;
$count = count($data);
PHP8 오류
count(): Argument #1 must be Countable|array
해결 방법
$count = count($data ?? []);
또는
$count = is_array($data)
? count($data)
: 0;
5. Required Parameter Follows Optional Parameter
오류 예시
function test($name = '', $age)
{
}
PHP8 Fatal Error
Required parameter $age follows optional parameter $name
해결 방법
function test($name, $age = 0)
{
}
또는
function test($age, $name = '')
{
}
6. Non-Static Method Cannot Be Called Statically
PHP7 코드
class User
{
public function getName()
{
return 'kim';
}
}
User::getName();
PHP8 오류
Non-static method cannot be called statically
해결 방법
$user = new User();
$user->getName();
또는
class User
{
public static function getName()
{
return 'kim';
}
}
7. Constructor 이름 방식 오류
PHP4 스타일 생성자는 제거되었습니다.
기존 코드
class Member
{
function Member()
{
echo 'start';
}
}
PHP8
Deprecated 또는 동작 안함
수정
class Member
{
public function __construct()
{
echo 'start';
}
}
8. each() 함수 제거
PHP7에서 Deprecated 되었던 함수입니다.
each($array);
PHP8에서는 제거되었습니다.
해결 방법
foreach ($array as $key => $value)
{
echo $key;
}
9. create_function() 제거
기존 코드
create_function('$a', 'return $a * 2;');
PHP8 제거
해결 방법
fn($a) => $a * 2;
또는
function($a) {
return $a * 2;
};
10. get_magic_quotes_gpc() 제거
PHP7 이하 레거시 프로젝트에서 자주 발견됩니다.
get_magic_quotes_gpc();
PHP8
Call to undefined function
해결 방법
관련 코드를 제거합니다.
Magic Quotes 기능 자체가 폐기되었습니다.
11. Call to Undefined Function mysql_connect()
매우 많이 발생하는 오류입니다.
기존 코드
mysql_connect();
PHP8
Call to undefined function mysql_connect()
원인
mysql 확장이 완전히 제거되었습니다.
해결 방법
mysqli 사용
$conn = mysqli_connect(
'localhost',
'root',
'password',
'dbname'
);
PDO 사용
$pdo = new PDO(
"mysql:host=localhost;dbname=test",
"user",
"password"
);
실무에서는 PDO 사용을 권장합니다.
12. TypeError 발생 증가
PHP8은 타입 검사가 매우 엄격합니다.
예시
strpos(null, 'abc');
오류
TypeError
해결
strpos($value ?? '', 'abc');
또는
if (!empty($value)) {
strpos($value, 'abc');
}
13. Fatal error: Uncaught ValueError
PHP8에서 새롭게 등장한 오류입니다.
예시
str_repeat('a', -1);
오류
ValueError
해결
$count = max(0, $count);
str_repeat('a', $count);
14. match 표현식 관련 오류
PHP8 신규 문법입니다.
$result = match($status) {
1 => 'success',
2 => 'fail'
};
일치하는 값이 없으면
UnhandledMatchError
발생할 수 있습니다.
수정
$result = match($status) {
1 => 'success',
2 => 'fail',
default => 'unknown'
};
15. String to Number 비교 방식 변경
PHP7
0 == "test"
결과
true
PHP8
false
비교 결과가 달라질 수 있습니다.
실무에서는 반드시
===
사용을 권장합니다.
if ($status === 1)
{
}
PHP8 마이그레이션 체크리스트
업그레이드 전 다음 항목을 점검하면 대부분의 장애를 예방할 수 있습니다.
| mysql_* 함수 사용 여부 | 필수 |
| each 함수 사용 여부 | 필수 |
| create_function 사용 여부 | 필수 |
| Magic Quotes 코드 존재 여부 | 필수 |
| 배열 키 존재 여부 검사 | 필수 |
| count() 사용 위치 확인 | 필수 |
| implode() 파라미터 순서 확인 | 필수 |
| 정적 호출 여부 확인 | 필수 |
| 타입 선언 검토 | 권장 |
| Composer 패키지 버전 확인 | 필수 |
실무에서 추천하는 PHP8 업그레이드 절차
1단계
현재 서버 버전 확인
php -v
2단계
Composer 패키지 점검
composer outdated
3단계
PHP Compatibility 검사
composer require --dev phpcompatibility/php-compatibility
PHP_CodeSniffer 실행
phpcs --standard=PHPCompatibility src/
4단계
스테이징 서버 테스트
운영 서버에서 바로 PHP8을 적용하지 말고 반드시 별도 테스트 서버에서 검증합니다.
5단계
에러 로그 모니터링
tail -f /var/log/php/error.log
또는
tail -f /var/log/apache2/error.log
FAQ
PHP7에서 PHP8로 업그레이드하면 성능이 얼마나 향상되나요?
일반적으로 PHP8의 JIT 컴파일러와 엔진 개선으로 PHP7 대비 성능 향상을 기대할 수 있습니다. 다만 웹 서비스에서는 코드 구조와 DB 성능의 영향이 더 크기 때문에 실제 체감은 환경마다 다릅니다.
PHP8 업그레이드 전에 가장 먼저 확인해야 할 것은 무엇인가요?
mysql_* 함수, each(), create_function() 같은 제거된 기능 사용 여부를 확인하는 것이 가장 중요합니다.
PHP8로 업그레이드하면 기존 CodeIgniter 프로젝트도 문제가 발생하나요?
구버전 CodeIgniter 3.x는 일부 수정이 필요할 수 있으며, 오래된 라이브러리나 커스텀 코드에서 PHP8 호환성 문제가 자주 발생합니다.
PHP8에서 가장 많이 발생하는 오류는 무엇인가요?
Undefined Array Key, TypeError, count() 관련 오류, mysql_connect 제거 오류가 가장 빈번하게 발생합니다.
마무리
PHP7 → PHP8 마이그레이션은 단순 버전 업그레이드가 아니라 코드 품질과 호환성을 개선하는 작업입니다. 특히 레거시 프로젝트에서는 Undefined Array Key, TypeError, mysql_connect 제거, each 함수 제거 등 다양한 오류가 발생할 수 있으므로 사전 점검이 중요합니다. 운영 서버에 적용하기 전 충분한 테스트 환경을 구축하고 로그를 분석하면서 단계적으로 PHP8 마이그레이션을 진행하는 것을 권장합니다.
'실무개발 > BackEnd' 카테고리의 다른 글
| Spring Boot WebSocket을 Shared Worker로 운영하는 방법: 여러 탭 연결 최적화 실무 정리 (0) | 2026.06.09 |
|---|---|
| Java 17 Maven 멀티 모듈 프로젝트 구성 방법: core, spring-boot, demo 구조 (0) | 2026.06.02 |
