国产av日韩一区二区三区精品,成人性爱视频在线观看,国产,欧美,日韩,一区,www.成色av久久成人,2222eeee成人天堂

重寫后的標題為:How can I simulate the Symfony mailer for testing purposes?
P粉739706089
P粉739706089 2023-12-13 09:42:22
0
2
702

我正在 Symfony 6 項目的自定義類中使用 Symfony 郵件程序。我通過類的構造函數(shù)中的類型提示使用自動裝配,如下所示:

class MyClass {
        public function __construct(private readonly MailerInterface $mailer) {}


        public function sendEmail(): array
        {
            // Email is sent down here
            try {
                $this->mailer->send($email);
            
                return [
                    'success' => true,
                    'message' => 'Email sent',
                ];
            } catch (TransportExceptionInterface $e) {
                return [
                    'success' => false,
                    'message' => 'Error sending email: ' . $e,
                ];
            }
        }
    }

在控制器中調用 sendEmail() 方法,一切正常。

現(xiàn)在我想測試 TransportExceptions 是否被正確處理。為此,我需要郵件程序在我的測試中拋出 TransportExceptions 。然而,這并沒有像我希望的那樣起作用。

注意:我無法通過傳遞無效的電子郵件地址來引發(fā)異常,因為 sendMail 方法只允許有效的電子郵件地址。

我嘗試過的事情:

1) 使用模擬郵件程序

// boot kernel and get Class from container
$container = self::getContainer();
$myClass = $container->get('AppModelMyClass');

// create mock mailer service
$mailer = $this->createMock(Mailer::class);
$mailer->method('send')
        ->willThrowException(new TransportException());
$container->set('SymfonyComponentMailerMailer', $mailer);

結果我無法模擬 Mailer 類,因為它是 final。

2)使用模擬(或存根)MailerInterface

// create mock mailer service
$mailer = $this->createStub(MailerInterface::class);
$mailer->method('send')
        ->willThrowException(new TransportException());
$container->set('SymfonyComponentMailerMailer', $mailer);

沒有錯誤,但不拋出異常。郵件服務似乎沒有被取代。

3) 使用自定義 MailerExceptionTester 類

// MailerExceptionTester.php
<?php

namespace AppTests;

use SymfonyComponentMailerEnvelope;
use SymfonyComponentMailerExceptionTransportException;
use SymfonyComponentMailerMailerInterface;
use SymfonyComponentMimeRawMessage;

/**
 * Always throws a TransportException
 */
final class MailerExceptionTester implements MailerInterface
{
    public function send(RawMessage $message, Envelope $envelope = null): void
    {
        throw new TransportException();
    }
}

在測試中:

// create mock mailer service
$mailer = new MailerExceptionTester();
$container->set('SymfonyComponentMailerMailer', $mailer);

與 2) 中的結果相同

4)嘗試更換MailerInterface服務而不是Mailer

// create mock mailer service
$mailer = $this->createMock(MailerInterface::class);
$mailer->method('send')
        ->willThrowException(new TransportException());
$container->set('SymfonyComponentMailerMailerInterface', $mailer);

錯誤消息:SymfonyComponentDependencyInjectionExceptionInvalidArgumentException:“SymfonyComponentMailerMailerInterface”服務是私有的,您無法替換它。

5) 將 MailerInterface 設置為公開

// services.yaml
services:
    SymfonyComponentMailerMailerInterface:
        public: true

錯誤:無法實例化接口 SymfonyComponentMailerMailerInterface

6) 為 MailerInterface 添加別名

// services.yaml
services:
    app.mailer:
        alias: SymfonyComponentMailerMailerInterface
        public: true

錯誤消息:SymfonyComponentDependencyInjectionExceptionInvalidArgumentException:“SymfonyComponentMailerMailerInterface”服務是私有的,您無法替換它。

如何在測試中替換自動連接的 MailerInterface 服務?

P粉739706089
P粉739706089

全部回復(2)
P粉704066087

您第一次嘗試的順序應該是正確的。

// boot kernel and get Class from container
$container = self::getContainer();
$container->set('Symfony\Component\Mailer\Mailer', $mailer);

// create mock mailer service
$mailer = $this->createMock(Mailer::class);
$mailer->method('send')
        ->willThrowException(new TransportException());

$myClass = $container->get('App\Model\MyClass');

未經(jīng)測試,但您將類作為對象獲取,因此在模擬之前已經(jīng)解決了對服務的依賴關系。這應該首先替換容器中的服務,然后從容器中獲取MyClass

但是,您也可以完全跳過容器的構建。只需使用 PhpUnit。

$mock = $this->createMock(Mailer::class);
// ... 

$myClass = new MyClass($mock);
$myClass->sendEmail();
P粉226667290

我正在嘗試這樣做,并且我相信我已經(jīng)根據(jù)您已經(jīng)嘗試過的方法找到了解決方案。

在我的 services.yaml 中,我重新聲明 mailer.mailer 服務,并在測試環(huán)境中將其設置為公共:

when@test:
    services:
        mailer.mailer:
            class: Symfony\Component\Mailer\Mailer
            public: true
            arguments:
                - '@mailer.default_transport'

此設置應該使 Symfony Mailer 服務的行為方式與以前完全相同,但是因為它現(xiàn)在是公共的,所以如果需要,我們可以覆蓋它在容器中使用的類。

我復制了您編寫的自定義 Mailer 類...

// MailerExceptionTester.php

...在我的測試代碼中,我獲取了測試容器并將 mailer.mailer 服務替換為異常拋出類的實例:

$mailer = new MailerExceptionTester();
static::getContainer()->set('mailer.mailer', $mailer);

現(xiàn)在,無論注入 Mailer 服務,所使用的類都將是自定義異常拋出類!

最新下載
更多>
網(wǎng)站特效
網(wǎng)站源碼
網(wǎng)站素材
前端模板