Skip to content

Commit

Permalink
Merge pull request #557 from tienvx/add-comment
Browse files Browse the repository at this point in the history
chore: Use both pactffi_set_comment and pactffi_add_text_comment
  • Loading branch information
tienvx authored Apr 22, 2024
2 parents dbe5f87 + 6f32520 commit 3d38623
Show file tree
Hide file tree
Showing 13 changed files with 256 additions and 32 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ public function theHttpInteractionIsMarkedAsPending(): void
*/
public function aCommentIsAddedToTheHttpInteraction(string $value): void
{
$this->interaction->setComments(['text' => json_encode([$value])]);
$this->interaction->addTextComment($value);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ public function theMessageInteractionIsMarkedAsPending(): void
*/
public function aCommentIsAddedToTheMessageInteraction(string $value): void
{
$this->message->setComments(['text' => json_encode([$value])]);
$this->message->addTextComment($value);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ public function theSynchronousMessageInteractionIsMarkedAsPending(): void
*/
public function aCommentIsAddedToTheSynchronousMessageInteraction(string $value): void
{
$this->message->setComments(['text' => json_encode([$value])]);
$this->message->addTextComment($value);
}

/**
Expand Down
47 changes: 45 additions & 2 deletions src/PhpPact/Consumer/AbstractMessageBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -78,14 +78,57 @@ public function pending(?bool $pending): self
}

/**
* Add comments to the message interaction. This feature only work with specification v4. It doesn't affect pact file with specification <= v3.
* Set comments for the interaction.
*
* @param array<string, string> $comments
* This is used by V4 interactions to set comments for the interaction. A
* comment consists of a key-value pair, where the key is a string and the
* value is anything that can be encoded as JSON.
*
* Args:
* key:
* Key for the comment.
*
* value:
* Value for the comment. This must be encodable using
* `json_encode`, or an existing JSON string. The
* value of `null` will remove the comment with the given key.
*
* # Warning
*
* This function will overwrite any existing comment with the same key. In
* particular, the `text` key is used by {@see self::comment()}.
*
* @param array<string, mixed> $comments
*/
public function comments(array $comments): self
{
$this->message->setComments($comments);

return $this;
}

/**
* Add a text comment for the interaction.
*
* This is used by V4 interactions to set arbitrary text comments for the
* interaction.
*
* Args:
* comment:
* Text of the comment.
*
* # Warning
*
* Internally, the comments are appended to an array under the `text`
* comment key. Care should be taken to ensure that conflicts are not
* introduced by {@see self::comments()}.
*
* @param string $comment
*/
public function comment(string $comment): self
{
$this->message->addTextComment($comment);

return $this;
}
}
9 changes: 8 additions & 1 deletion src/PhpPact/Consumer/Driver/Interaction/AbstractDriver.php
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,16 @@ protected function setPending(Interaction|Message $interaction): void
protected function setComments(Interaction|Message $interaction): void
{
foreach ($interaction->getComments() as $key => $value) {
$value = (is_string($value) || is_null($value)) ? $value : json_encode($value);
$success = $this->client->call('pactffi_set_comment', $interaction->getHandle(), $key, $value);
if (!$success) {
throw new InteractionCommentNotSetException(sprintf("Can add comment '%s' to the interaction '%s'", $key, $interaction->getDescription()));
throw new InteractionCommentNotSetException(sprintf("Can not add comment '%s' to the interaction '%s'", $key, $interaction->getDescription()));
}
}
foreach ($interaction->getTextComments() as $value) {
$success = $this->client->call('pactffi_add_text_comment', $interaction->getHandle(), $value);
if (!$success) {
throw new InteractionCommentNotSetException(sprintf("Can not add text comment '%s' to the interaction '%s'", $value, $interaction->getDescription()));
}
}
}
Expand Down
47 changes: 45 additions & 2 deletions src/PhpPact/Consumer/InteractionBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -103,14 +103,57 @@ public function pending(?bool $pending): self
}

/**
* Add comments to the interaction. This feature only work with specification v4. It doesn't affect pact file with specification <= v3.
* Set comments for the interaction.
*
* @param array<string, string> $comments
* This is used by V4 interactions to set comments for the interaction. A
* comment consists of a key-value pair, where the key is a string and the
* value is anything that can be encoded as JSON.
*
* Args:
* key:
* Key for the comment.
*
* value:
* Value for the comment. This must be encodable using
* `json_encode`, or an existing JSON string. The
* value of `null` will remove the comment with the given key.
*
* # Warning
*
* This function will overwrite any existing comment with the same key. In
* particular, the `text` key is used by {@see self::comment()}.
*
* @param array<string, mixed> $comments
*/
public function comments(array $comments): self
{
$this->interaction->setComments($comments);

return $this;
}

/**
* Add a text comment for the interaction.
*
* This is used by V4 interactions to set arbitrary text comments for the
* interaction.
*
* Args:
* comment:
* Text of the comment.
*
* # Warning
*
* Internally, the comments are appended to an array under the `text`
* comment key. Care should be taken to ensure that conflicts are not
* introduced by {@see self::comments()}.
*
* @param string $comment
*/
public function comment(string $comment): self
{
$this->interaction->addTextComment($comment);

return $this;
}
}
34 changes: 25 additions & 9 deletions src/PhpPact/Consumer/Model/Interaction/CommentsTrait.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,28 +5,44 @@
trait CommentsTrait
{
/**
* @var array<string, string>
* @var array<string, mixed>
*/
private array $comments = [];

/**
* @return array<string, string>
* @var string[]
*/
private array $textComments = [];

/**
* @return array<string, mixed>
*/
public function getComments(): array
{
return $this->comments;
}

/**
* @param array<string, string> $comments
* @param array<string, mixed> $comments
*/
public function setComments(array $comments): void
{
$this->comments = $comments;
}

/**
* @return string[]
*/
public function setComments(array $comments): self
public function getTextComments(): array
{
$this->comments = [];
foreach ($comments as $key => $value) {
$this->comments[$key] = $value;
}
return $this->textComments;
}

return $this;
/**
* @param string $comment
*/
public function addTextComment(string $comment): void
{
$this->textComments[] = $comment;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -168,8 +168,12 @@ public function testSetPending(?bool $pending, $success): void
}

#[TestWith([[], true])]
#[TestWith([['key1' => 'value1'], false])]
#[TestWith([['key2' => 'value2', 'key3' => 'value3'], true])]
#[TestWith([['key1' => null], true])]
#[TestWith([['key1' => null], false])]
#[TestWith([['key2' => 'string value'], true])]
#[TestWith([['key2' => 'string value'], false])]
#[TestWith([['key3' => ['value 1', 'value 2']], true])]
#[TestWith([['key3' => ['value 1', 'value 2']], false])]
public function testSetComments(array $comments, $success): void
{
$this->interaction->setComments($comments);
Expand All @@ -185,11 +189,36 @@ public function testSetComments(array $comments, $success): void
['pactffi_upon_receiving', $this->interactionHandle, $this->description, null],
];
foreach ($comments as $key => $value) {
$calls[] = ['pactffi_set_comment', $this->interactionHandle, $key, $value, $success];
$calls[] = ['pactffi_set_comment', $this->interactionHandle, $key, (is_string($value) || is_null($value)) ? $value : json_encode($value), $success];
}
if (!$success) {
$this->expectException(InteractionCommentNotSetException::class);
$this->expectExceptionMessage("Can add comment '$key' to the interaction '{$this->description}'");
$this->expectExceptionMessage("Can not add comment '$key' to the interaction '{$this->description}'");
}
$this->assertClientCalls($calls);
$this->driver->registerInteraction($this->interaction, false);
}

#[TestWith(['comment 1', false])]
#[TestWith(['comment 2', true])]
public function testAddTextComment(string $comment, $success): void
{
$this->interaction->addTextComment($comment);
$this->pactDriver
->expects($this->once())
->method('getPact')
->willReturn(new Pact($this->pactHandle));
$calls = [
['pactffi_new_interaction', $this->pactHandle, $this->description, $this->interactionHandle],
['pactffi_given', $this->interactionHandle, 'item exist', null],
['pactffi_given_with_param', $this->interactionHandle, 'item exist', 'id', '12', null],
['pactffi_given_with_param', $this->interactionHandle, 'item exist', 'name', 'abc', null],
['pactffi_upon_receiving', $this->interactionHandle, $this->description, null],
['pactffi_add_text_comment', $this->interactionHandle, $comment, $success],
];
if (!$success) {
$this->expectException(InteractionCommentNotSetException::class);
$this->expectExceptionMessage("Can not add text comment '$comment' to the interaction '{$this->description}'");
}
$this->assertClientCalls($calls);
$this->driver->registerInteraction($this->interaction, false);
Expand Down
39 changes: 35 additions & 4 deletions tests/PhpPact/Consumer/Driver/Interaction/MessageDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -165,8 +165,12 @@ public function testSetPending(?bool $pending, $success): void
}

#[TestWith([[], true])]
#[TestWith([['key1' => 'value1'], false])]
#[TestWith([['key2' => 'value2', 'key3' => 'value3'], true])]
#[TestWith([['key1' => null], true])]
#[TestWith([['key1' => null], false])]
#[TestWith([['key2' => 'string value'], true])]
#[TestWith([['key2' => 'string value'], false])]
#[TestWith([['key3' => ['value 1', 'value 2']], true])]
#[TestWith([['key3' => ['value 1', 'value 2']], false])]
public function testSetComments(array $comments, $success): void
{
$this->message->setComments($comments);
Expand All @@ -184,11 +188,38 @@ public function testSetComments(array $comments, $success): void
['pactffi_message_with_metadata_v2', $this->messageHandle, 'key2', 'value2', null],
];
foreach ($comments as $key => $value) {
$calls[] = ['pactffi_set_comment', $this->messageHandle, $key, $value, $success];
$calls[] = ['pactffi_set_comment', $this->messageHandle, $key, (is_string($value) || is_null($value)) ? $value : json_encode($value), $success];
}
if (!$success) {
$this->expectException(InteractionCommentNotSetException::class);
$this->expectExceptionMessage("Can add comment '$key' to the interaction '{$this->description}'");
$this->expectExceptionMessage("Can not add comment '$key' to the interaction '{$this->description}'");
}
$this->assertClientCalls($calls);
$this->driver->registerMessage($this->message);
}

#[TestWith(['comment 1', false])]
#[TestWith(['comment 2', true])]
public function testAddTextComment(string $comment, $success): void
{
$this->message->addTextComment($comment);
$this->pactDriver
->expects($this->once())
->method('getPact')
->willReturn(new Pact($this->pactHandle));
$calls = [
['pactffi_new_message_interaction', $this->pactHandle, $this->description, $this->messageHandle],
['pactffi_message_given', $this->messageHandle, 'item exist', null],
['pactffi_message_given_with_param', $this->messageHandle, 'item exist', 'id', '12', null],
['pactffi_message_given_with_param', $this->messageHandle, 'item exist', 'name', 'abc', null],
['pactffi_message_expects_to_receive', $this->messageHandle, $this->description, null],
['pactffi_message_with_metadata_v2', $this->messageHandle, 'key1', 'value1', null],
['pactffi_message_with_metadata_v2', $this->messageHandle, 'key2', 'value2', null],
['pactffi_add_text_comment', $this->messageHandle, $comment, $success],
];
if (!$success) {
$this->expectException(InteractionCommentNotSetException::class);
$this->expectExceptionMessage("Can not add text comment '$comment' to the interaction '{$this->description}'");
}
$this->assertClientCalls($calls);
$this->driver->registerMessage($this->message);
Expand Down
10 changes: 9 additions & 1 deletion tests/PhpPact/Consumer/InteractionBuilderTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -120,14 +120,22 @@ public function testSetPending(?bool $pending): void
}

#[TestWith([[]])]
#[TestWith([['key' => 'value']])]
#[TestWith([['key1' => null, 'key2' => 'value', 'key3' => ['value']]])]
public function testSetComments(array $comments): void
{
$this->assertSame($this->builder, $this->builder->comments($comments));
$interaction = $this->getInteraction();
$this->assertSame($comments, $interaction->getComments());
}

public function testAddTextComment(): void
{
$this->assertSame($this->builder, $this->builder->comment('comment 1'));
$this->assertSame($this->builder, $this->builder->comment('comment 2'));
$interaction = $this->getInteraction();
$this->assertSame(['comment 1', 'comment 2'], $interaction->getTextComments());
}

private function getInteraction(): Interaction
{
$reflection = new ReflectionProperty($this->builder, 'interaction');
Expand Down
10 changes: 9 additions & 1 deletion tests/PhpPact/Consumer/MessageBuilderTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -102,14 +102,22 @@ public function testSetPending(?bool $pending): void
}

#[TestWith([[]])]
#[TestWith([['key' => 'value']])]
#[TestWith([['key1' => null, 'key2' => 'value', 'key3' => ['value']]])]
public function testSetComments(array $comments): void
{
$this->assertSame($this->builder, $this->builder->comments($comments));
$message = $this->getMessage();
$this->assertSame($comments, $message->getComments());
}

public function testAddTextComment(): void
{
$this->assertSame($this->builder, $this->builder->comment('comment 1'));
$this->assertSame($this->builder, $this->builder->comment('comment 2'));
$message = $this->getMessage();
$this->assertSame(['comment 1', 'comment 2'], $message->getTextComments());
}

public function testSetSingleCallback(): void
{
$callbacks = [
Expand Down
Loading

0 comments on commit 3d38623

Please sign in to comment.