如何测试外部API?

How to test external APIs?

我很难开始测试与外部 API (Vimeo API) 的集成,例如(删除视频 - 上传视频 - 等等) .

这样做是不是一个坏主意:


use Tests\TestCase;
use Vimeo\Laravel\VimeoManager;

class VimeoApiTest extends TestCase
{
    protected function setUp() : void
    {
        parent::setUp();
        $this->vimeo = new VimeoManager();
    }

    /** @test */
    public function a_video_can_be_deleted()
    {
        $video = $this->vimeo->upload($fakeVideo);

        // make http request to delete the video
        $result = $this->vimeo->delete($video['id']);

        $this->assertEquals('success', $result['status']);
    }
}

在我看来,测试包不应该是你的责任。测试包的实现是。您的示例直接测试包的 VimeoManager 。我认为这不是你应该做的。

向上传视频的 API 路由发出请求是您应该测试的。在此测试期间,您不想将它上传到真实的 Vimeo API,但您想模拟它。

Laravel 包含一个可以做到这一点的包,它被称为 Mockery。您可以模拟 类 到 return 值的方法,而无需执行初始逻辑。在这种情况下,您将模拟 VimeoManager.

delete 方法

Laravel也提供所谓的Facades which can easily be mocked. I can see this package makes use of such facade。在这种情况下,您可以执行以下操作来测试假设您的删除请求的实现。

/** @test */
use Vimeo\Laravel\Facades\Vimeo;

public function your_test()
{
    Vimeo::shouldReceive('delete')
        ->once()
        ->with(...) // The parameters is should receive.
        ->andReturn(...); // The value it should return.

    // Make the delete request to your API.
}

我通常反对我的测试应该连接到的模拟服务器。 模拟服务器和使用模拟器的主要缺点是 API 的实现可能会改变(例如抛出 exception/new 状态代码或超时可能更短)或者 [=16= 之间可能不兼容] 介于 2 个版本的服务器之间。

Should I hit the real Vimeo's server while testing?

如果有可能,请使用 docker 创建本地 Vimeo 的服务器 :) 您的测试将发现 API 将来

是否有变化

好吧,您可以根据自己的喜好进行测试。我发现进行两种类型的测试很有用。

与 "something" 其他(服务、系统等)交互的测试称为集成测试。这些很好,让您放心,但与您在线互动的系统相关联,情况并非总是如此。

第二种类型的测试可以有几个不同的名称,但这不是重点。第二种测试的要点是,您可以 "mock" 排除 external/internal 依赖关系,确保您的代码所依赖的 "thing" 是您想要的 online/behaves。模拟是当您操纵 "thing" 以某种方式响应时。通常,这是通过某些框架或语言功能完成的。这些类型的测试给您的代码带来了更大的负担,在我看来更重要。