115호. 라라벨 6.10.0 새 기능 free

2020-01-15



안녕하세요. 오늘은 라라벨 6.10.0에 새로 추가된 기능을 정리했습니다. 마이너 업데이트인데도 추가된 기능이 꽤 많네요.


withoutMix, withMix 테스트 헬퍼 추가


테스트를 할 때 예외가 발생하면 애플리케이션 내에서 예외가 처리되어서 어떤 예외가 나면서 테스트를 실패했는지 알 수 없을 때 withoutExceptionHandling을 사용합니다. withoutExceptionHandlingwithExceptionHandling과 같은 개념을 Laravel Mix에 적용한 헬퍼가 추가되었습니다.


이렇게 하던 것을


$this->swap(\Illuminate\Foundation\Mix::class, function () {
return '';
});

이제 이렇게 할 수 있습니다.


$this->withoutMix();

에러백을 지정할 수 있게 됨


validateWithBag으로 유효성 검사 실패시 에러를 담을 에러백을 지정할 수 있게 되었습니다.


$request->validateWithBag('contact_form', [
'email' => 'required|email',
'message' => 'required',
]);

PHPUnit 9 지원


PHPUnit은 현재 8.5.2가 최신 안정 버전입니다. 그런데 PHPUnit 9를 지원한다니 이상하죠? 기능을 추가한 그래엄 캠벨은 라라벨 6.0이 LTS이지만 최신 PHP를 사용할 수 있게 지원하고 싶어 기능을 추가했다고 합니다. PHP 8이 아마도 PHPUnit 8 버전을 지원하지 않을 것이라 예상해서 말이죠. 이게 뭔 말인고 하니 라라벨이 PHPUnit 8까지만 지원하는데, PHP 8이 PHPUnit 8을 지원하지 않으면, 라라벨도 PHP 8을 쓸 수 없기 때문에 의존성을 미리 PHPUnit 9로 올려놓겠단 얘기입니다. 굉장히 먼 미래까지(그래봤자 2~3년이지만) 대비하는 느낌이네요.


exclude_if 유효성 검사 규칙 추가


다른 속성의 값을 기반으로 특정 속성을 유효성 검사에서 손쉽게 제외할 수 있게 되었습니다.


이와 반대 개념인 required_if 는 이미 존재했는데, 이것 만으로는 불충분했습니다. PR에서는 다음과 같은 예를 들었어요.


has_appointment를 체크하면 doctor_name과 appointment_date를 입력하는 인풋이 나타나고 체크를 해제하면 사라지는데, 사라질 때 보여지지만 않을 뿐 입력 값은 남아있는 상황입니다.


그래서 아래와 같이 데이터가 전송되는데


// Post data
{"has_appointment": false, "appointment_date": "2019-12-13"}

required_if 로 아래와 같이 유효성 검사를 하면


public function post(Request $request)
{
$data = $request->validate([
'has_appointment' => 'required|bool',
'appointment_date' => 'required_if:has_appointment,true|date',
'doctor_name' => 'required_if:has_appointment,true|string'
]);

// $data === ['has_appointment' => false, 'appointment_date' => '2019-12-13']

SomeModel::create($data);
}

has_appointment 가 false 임에도 불구하고 appointment_date 값을 갖는 모델이 생성됩니다. 원래 의도대로라면 appointment_date 값이 없이 생성되었어야 하죠.


따라서 부득이하게 컨트롤러에 다음과 같은 코드가 추가적으로 필요해집니다.


if (! $data['has_doctor_appointment') {
$data['appointment_date'] = null;
$data['doctor_name'] = null;
}

새로 추가된 exclude_if를 사용하면 이런 상황을 조금 더 편하게 처리할 수 있습니다.


public function post(Request $request)
{
$data = $request->validate([
'has_doctor_appointment' => 'required|bool',
'appointment_date' => 'exclude_if:has_appointment,false|required|date',
'doctor_name' => 'exclude_if:has_appointment,false|required|string',
]);

// $data === ['has_appointment' => false]

SomeModel::create($data);
}

최근에 저도 이 기능이 아쉬웠는데 잘 됐네요.


PostgreSQL에 generated column 지원 추가


PostgreSQL 12에 generated column 이라는 기능이 추가되었는데, 이를 지원하기 위한 기능이 추가되었습니다.


Eloquent Builder에 mixin 지원 추가


Eloquent Builder는 Macroable 트레이트를 쓰지 않고도 매크로를 추가할 수 있는데, 여러 매크로를 한 번에 등록할 수 있는 mixin()도 추가되었습니다.


Redis Connection에 매크로를 추가할 수 있게 됨


Macroable 트레이트를 추가하면 런타임에 기능을 확장할 수 있습니다. Redis Connection 클래스에 Macroable 트레이트를 추가했다고 하네요.


관련 글



패키지의 composer.json에서 추가적인 정보를 추출할 수 있게 됨


기존에는 providersaliases 섹션의 정보만 추출했는데 이외의 섹션 정보도 사용할 수 있게 되었다고 합니다.


컨테이너에 redis.connection 별칭 추가



  • \Illuminate\Redis\Connections\Connection::class

  • \Illuminate\Contracts\Redis\Connection::class


위 두 클래스가 redis.connection 으로 컨테이너에 등록되었습니다. 레디스 Connection 클래스나 Contract를 타입힌트 할 수 있고, 컨테이너로 적절한 구현을 받아 쓸 수 있습니다. RedisManager를 직접 타입 힌트 하지 않아도 되서 프레임워크 내부에 덜 커플링 될 수 있는 장점도 있다고 하네요.


CallOtherCommands를 Illuminate\Console\Command에서 트레이트로 분리


냉무


Storage::putFile()에 절대 경로 사용 가능


Storage::putFile()의 시그니처는 다음과 같습니다. 내용과 주석 일부는 편의상 제거했습니다.


/*
* @param \Illuminate\Http\File|\Illuminate\Http\UploadedFile|string $file
*/
public function putFile($path, $file, $options = []){}

소스 코드에 아래의 코드가 한 줄 추가 되었습니다.


$file = is_string($file) ? new File($file) : $file;

두 번째 인자인 $file이 문자열이면 파일 객체를 만들고 그렇지 않으면 \Illuminate\Http\File|\Illuminate\Http\UploadedFile 객체를 그대로 사용하네요.


이상입니다! 참 많은 기능들이 추가되었는데 이 중 메뉴얼에 추가된 녀석은 한 가지 밖에 없네요. 신기합니다. ㅎㅎ


1일 1식 라라벨 115호

2020년 1월 15일


이현석

메쉬 코리아 개발자. 바쁜 팀장님 대신 알려주는 신입 PHP 개발자 안내서를 쓰고, 클린 아키텍처 인 PHP를 번역했습니다. 2020년에 출간될 Laravel Up & Running 2nd Edition을 번역하고 있습니다.