65호. 라라벨 6.1.0 에 추가된 기능 소개 free

2019-10-02

라라벨 6.1.0이 배포됐습니다. 추가된 기능이 많네요!



  • LazyCollection에 eager() 매서드 추가 (#29832)

  • 개별 로그 드라이버/채널 제거 기능 추가 (#30132, a52a0dd)

  • TestResponse에 assertNoContent() 매서드 추가 (#30125)

  • 노티피케이션 큐용 잡 미들웨어 추가 (#30070)

  • SendQueueNotifications에 InteractsWithQueue 추가 (#30140)

  • 노티피케이션 큐 재전송 허용 시간 설정 기능 추가 (#30141)

  • 테스트 리퀘스트에 쿠키 첨부 매서드 추가 (#30101)


LazyCollection에 eager() 매서드 추가


공식적인 기능 설명은 "모든 아이템을 eager 로드해서 배열로 만들고 이를 새 레이지 컬렉션을 만든다. (Eager load all items into a new lazy collection backed by an array.)" 입니다.


코드로 보면 전체 아이템을 호출해서 새로운 레이지 컬렉션을 만들어 반환합니다.


public function eager()
{
return new static($this->all());
}

원래 레이지 컬렉션의 용도는 대량의 데이터를 적은 메모리로 처리하기 위한 것입니다(자세한 사항은 1일 1식 라라벨 51호 - 라라벨 6, 레이지 컬렉션을 참고하세요). 그런데 전체 데이터를 한 번에 불러들인다고 하니 다소 의아하네요. 이 코드를 추가한 사람은 아래의 코드를 예로 들었는데, 아래의 코드는 쿼리를 한 번만 날리는 반면, eager()를 하지 않으면 두 번을 날린다고 합니다.


$users = User::cursor();

$users = $users->eager();

$count = $users->count();

$users->each(function ($user) {
//
});

얼핏 N+1 문제를 해결하기 위해 쓰는 eager 로드와 비슷해보이지만 개념이나 용도가 좀 다르게 느껴져서 저는 아직 어느 상황에 써야할지 정확하게 느낌이 오진 않네요.


원래는 eager()가 아니라 cache()라는 매서드명으로 만들어졌다가 논의를 통해 바뀐건데, 저는 오히려 cache()가 좀 더 적절한 것 같아요. 테스트 코드를 보면 더 그런 느낌을 받습니다. 아래는 이 기능과 함께 추가된 테스트 코드인데, 일부러 아직 eager()로 바꾸기 전의 코드를 가져와봤습니다.


public function testCache() // 나중에 testEager()로 바뀜
{
$source = [1, 2, 3, 4, 5];

$data = LazyCollection::make(function () use (&$source) {
yield from $source;
})->cache(); // 나중에 ->eager()로 바뀜

$source[] = 6;

$this->assertSame([1, 2, 3, 4, 5], $data->all());
}

혹시 용도가 뽝 떠오르시는 분들은 제게 힌트 좀 주세요.


개별 로그 드라이버/채널 제거 기능 추가


DatabaseManagerpurge() 매서드가 있는 것에 영감을 받아서 LogManager에도 purge() 매서드를 추가했다고 합니다. 사용방법은 테스트 코드를 참고하면 될 것 같아요.


public function testLogMnagerPurgeResolvedChannels()
{
$manager = new LogManager($this->app);
$this->assertEmpty($manager->getChannels());

$manager->channel('single')->getLogger();
$this->assertCount(1, $manager->getChannels());

$manager->purge('single');
$this->assertEmpty($manager->getChannels());
}

TestResponse에 assertNoContent() 매서드 추가


컨텐트가 없는 상황을 기존엔 두 개의 매서드로 확인하던 걸 하나의 매서드로 확인 할 수 있습니다.


Before


$response = $this->get('api/endpoint');

$response->assertStatus(409);
$this->assertEmpty($response->content());

After


$response = $this->get('api/endpoint');

$response->assertNoContent(409);

assertNoContent()에 상태코드를 넘겨주지 않아도 되며, 기본 상태값은 204입니다.


노티피케이션 큐용 잡 미들웨어 추가


잡 큐 미들웨어는 있었지만 노티피케이션 큐는 지원이 안됐었습니다. (#30057) 이제 큐를 사용하는 노티피케이션에도 잡 미들웨어를 적용할 수 있다고 하네요.


잡 미들웨어와 마찬가지로 through() 매서드로 적용합니다.


class Notification extends BaseNotification implements ShouldQueue
{
use Queueable;
}

$user = User::find(2);
$notification = (new Notification())->through(new RateLimited);
$user->notify($notification);

혹은 노티피케이션 클래스에 middleware() 매서드로 추가할 수도 있습니다.


public function middleware()
{
return [new SomeMiddleware];
}

노티피케이션 큐 재전송 허용 시간 설정 기능 추가


SendQueueNotificationsretryUntil() 혹은 timeoutAt 프로퍼티를 정의해서 재전송을 언제까지 허용할건지 설정할 수 있게 되었습니다.


테스트 리퀘스트에 쿠키 첨부 매서드 추가


기존에는 테스트 리퀘스트에 쿠키를 넣어서 보내려면 call() 매서드를 써야했는데, withCookies()로 더 편하게 쿠키를 첨부할 수 있게 되었습니다.


Before


$cookies = [
'name1' => encrypt('value1'),
'name2' => encrypt('value2')
];
$response = $this->call('get', 'test', [], $cookies);

After


$response = $this->withCookies([
'name1' => 'value1',
'name2' => 'value2'
])->get('test');

withCookie()disableCookieEncryption()도 추가되었습니다.



  • withCookie: 첨부할 쿠키 항목이 하나일 때 사용

  • disableCookieEncryption: 암호화를 비활성화하고 싶을 때 사용


1일 1식 라라벨 65호

2019년 10월 2일

유료 구독자 전용 레터입니다.

한 달 1만원으로 매일 라라벨 관련 메일 받아보시고 과거 메일도 열람하세요. 일반 구독으로 공개글만 받아보실 수도 있습니다.

구독하기 버튼을 눌러주시면 구독과 동시에 xly에도 가입됩니다.

이현석

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