Skip to content

Latest commit

 

History

History
143 lines (105 loc) · 4.22 KB

provider.md

File metadata and controls

143 lines (105 loc) · 4.22 KB

Basic Provider Usage

All of the following code will be used exclusively for Providers. This will run the Pacts against the real Provider and either verify or fail validation on the Pact Broker.

Create Unit Test

Create a single unit test function. This will test all defined consumers of the service.

protected function setUp(): void
{
    // Start API
}

protected function tearDown(): void
{
    // Stop API
}

public function testPactVerifyConsumers(): void
{
    $config = new VerifierConfig();
    $config->getProviderInfo()
        ->setName('someProvider')
        ->setHost('localhost')
        ->setPort(8000);
    $config->getProviderState()
        ->setStateChangeUrl(new Uri('http://localhost:8000/pact-change-state'))
        ->setStateChangeTeardown(true)
        ->setStateChangeAsBody(true);

    // If your provider dispatch messages
    $config->addProviderTransport(
        (new ProviderTransport())
            ->setProtocol(ProviderTransport::MESSAGE_PROTOCOL)
            ->setPort(8000)
            ->setPath('/pact-messages')
            ->setScheme('http')
    );

    // If you want to publish verification results to Pact Broker.
    if ($isCi = getenv('CI')) {
        $publishOptions = new PublishOptions();
        $publishOptions
            ->setProviderVersion(exec('git rev-parse --short HEAD'))
            ->setProviderBranch(exec('git rev-parse --abbrev-ref HEAD'));
        $config->setPublishOptions($publishOptions);
    }

    // If you want to display more/less verification logs.
    if ($logLevel = \getenv('PACT_LOGLEVEL')) {
        $config->setLogLevel($logLevel);
    }

    // Add sources ...

    $verifyResult = $verifier->verify();

    $this->assertTrue($verifyResult);
}

Verification Sources

There are four ways to verify Pact files. See the examples below.

Verify From Pact Broker

This will grab the Pact files from a Pact Broker.

$selectors = (new ConsumerVersionSelectors())
    ->addSelector(new Selector(mainBranch: true))
    ->addSelector(new Selector(deployedOrReleased: true));

$broker = new Broker();
$broker
    ->setUrl(new Uri('http://localhost'))
    ->setUsername('user')
    ->setPassword('pass')
    ->setToken('token')
    ->setEnablePending(true)
    ->setIncludeWipPactSince('2020-01-30')
    ->setProviderTags(['prod'])
    ->setProviderBranch('main')
    ->setConsumerVersionSelectors($selectors)
    ->setConsumerVersionTags(['dev']);

$verifier->addBroker($broker);

Verify From Url

This will grab the Pact file from a url.

$url = new Url();
$url
    ->setUrl(new Uri('http://localhost:9292/pacts/provider/personProvider/consumer/personConsumer/latest'))
    ->setUsername('user')
    ->setPassword('pass')
    ->setToken('token');

$verifier->addUrl($url);

Verify Files in Directory

This will grab local Pact files in directory. Results will not be published.

$verifier->addDirectory('C:\SomePath');

Verify Files by Path

This will grab local Pact file. Results will not be published.

$verifier->addFile('C:\SomePath\consumer-provider.json');

Start API

Starting API Asynchronously

You can use the built in PHP server to accomplish this during your tests setUp function. The Symfony Process library can be used to run the process asynchronous.

PHP Server

Symfony Process

Set Up Provider State

The PACT verifier is a wrapper of the Ruby Standalone Verifier. See API with Provider States for more information on how this works. Since most PHP rest APIs are stateless, this required some thought.

Here are some options:

  1. Write the posted state to a file and use a factory to decide which mock repository class to use based on the state.
  2. Set up your database to meet the expectations of the request. At the start of each request, you should first reset the database to its original state.

No matter which direction you go, you will have to modify something outside of the PHP process because each request to your server will be stateless and independent.