diff --git a/README.md b/README.md index 8958f0a..fd3ccfd 100644 --- a/README.md +++ b/README.md @@ -52,11 +52,12 @@ When as user :user When user :user exists When sending :verb to :url When the response should be a JSON array with the following mandatory values -When the response should contain the initial state :name with the following values: When /^set the display name of user "([^"]*)" to "([^"]*)"$/ When /^set the email of user "([^"]*)" to "([^"]*)"$/ When sending :verb to ocs :url When the response should have a status code :code +When fetch field :path from prevous JSON response +When the response should contain the initial state :name with the following values: When the following :appId app config is set ``` @@ -105,8 +106,13 @@ Then the response should be a JSON array with the following mandatory values | (jq).Foo.Bar | 33 | ``` -## Parse initial state -If you need to parse the initial state to use placeholder or get any value from current initial state, implement a method `parseText` like this: +## Parse text + +If you need to: +- Get values from a request, store and use in other request +- Parse the response of a request + +Implement a method `parseText` like the follow code and remember to call parent method: ```php protected function parseText(string $text): string { $patterns = [ @@ -118,6 +124,8 @@ protected function parseText(string $text): string { $this->file['uuid'] ?? $this->getFileUuidFromText($text), ]; $text = preg_replace($patterns, $replacements, $text); + $text = parent::parseText($text); return $text; } ``` +For more information about parseText, check the scenario `Test get field from json response` diff --git a/features/bootstrap/FeatureContext.php b/features/bootstrap/FeatureContext.php index c782772..e7f1f59 100644 --- a/features/bootstrap/FeatureContext.php +++ b/features/bootstrap/FeatureContext.php @@ -63,6 +63,7 @@ public function sendRequest(string $verb, string $url, $body = null, array $head // Url $actual = preg_replace('/^\/index.php/', '', $lastRequest->getRequestUri()); + $url = $this->parseText($url); Assert::assertEquals($url, $actual); // Headers diff --git a/features/test.feature b/features/test.feature index e152172..9632b9a 100644 --- a/features/test.feature +++ b/features/test.feature @@ -64,6 +64,23 @@ Feature: Test this extension | (jq).Foo | (jq).Bar == "33" | | (jq).Foo.Bar | 33 | + Scenario: Test get field from json response + When set the response to: + """ + { + "data": [ + { + "foo":"bar" + } + ] + } + """ + And sending "POST" to "/" + And fetch field "data.0.foo" from prevous JSON response + # After fetch the field, you can use the value of field like this: + And sending "POST" to "/?foo=" + | field | | + Scenario: Test initial state with string When set the response to: """ diff --git a/src/NextcloudApiContext.php b/src/NextcloudApiContext.php index bad2b37..564379e 100644 --- a/src/NextcloudApiContext.php +++ b/src/NextcloudApiContext.php @@ -23,6 +23,7 @@ class NextcloudApiContext implements Context { protected string $baseUrl; protected RunServerListener $server; protected string $currentUser = ''; + protected array $fields = []; /** * @var string[] */ @@ -180,8 +181,8 @@ public function sendRequest(string $verb, string $url, $body = null, array $head } try { - $this->requestOptions = $options; list($fullUrl, $options) = $this->beforeRequest($fullUrl, $options); + $this->requestOptions = $options; $this->response = $client->{$verb}($fullUrl, $options); } catch (ClientException $ex) { $this->response = $ex->getResponse(); @@ -191,6 +192,8 @@ public function sendRequest(string $verb, string $url, $body = null, array $head } protected function beforeRequest(string $fullUrl, array $options): array { + $options = $this->parseFormParams($options); + $fullUrl = $this->parseText($fullUrl); return [$fullUrl, $options]; } @@ -307,6 +310,21 @@ private function validateAsJsonQuery(string $expected, string $actual): void { Assert::assertTrue($result, 'The jq "' . $expected . '" do not match with: ' . $actual); } + /** + * @When fetch field :path from prevous JSON response + */ + public function fetchFieldFromPreviousJsonResponse(string $path): void { + $this->response->getBody()->seek(0); + $responseArray = json_decode($this->response->getBody()->getContents(), true); + $keys = explode('.', $path); + $value = $responseArray; + foreach ($keys as $key) { + Assert::assertArrayHasKey($key, $value, 'Key [' . $key . '] of path [' . $path . '] not found.'); + $value = $value[$key]; + } + $this->fields[$path] = $value; + } + /** * @When the response should contain the initial state :name with the following values: */ @@ -354,7 +372,33 @@ public function setAppConfig(string $appId, TableNode $formData): void { $this->setCurrentUser($currentUser); } + protected function parseFormParams(array $options): array { + if (!empty($options['form_params'])) { + $this->parseTextRcursive($options['form_params']); + } + return $options; + } + + private function parseTextRcursive(array &$array): array { + array_walk_recursive($array, function (mixed &$value) { + if (is_string($value)) { + $value = $this->parseText($value); + } elseif ($value instanceof \stdClass) { + $value = (array) $value; + $value = json_decode(json_encode($this->parseTextRcursive($value))); + } + }); + return $array; + } + protected function parseText(string $text): string { + $patterns = []; + $replacements = []; + foreach ($this->fields as $key => $value) { + $patterns[] = '/<' . $key . '>/'; + $replacements[] = $value; + } + $text = preg_replace($patterns, $replacements, $text); return $text; } diff --git a/vendor-bin/psalm/composer.lock b/vendor-bin/psalm/composer.lock index 1be7a43..a8f52c0 100644 --- a/vendor-bin/psalm/composer.lock +++ b/vendor-bin/psalm/composer.lock @@ -8,16 +8,16 @@ "packages": [ { "name": "amphp/amp", - "version": "v2.6.2", + "version": "v2.6.4", "source": { "type": "git", "url": "https://github.com/amphp/amp.git", - "reference": "9d5100cebffa729aaffecd3ad25dc5aeea4f13bb" + "reference": "ded3d9be08f526089eb7ee8d9f16a9768f9dec2d" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/amphp/amp/zipball/9d5100cebffa729aaffecd3ad25dc5aeea4f13bb", - "reference": "9d5100cebffa729aaffecd3ad25dc5aeea4f13bb", + "url": "https://api.github.com/repos/amphp/amp/zipball/ded3d9be08f526089eb7ee8d9f16a9768f9dec2d", + "reference": "ded3d9be08f526089eb7ee8d9f16a9768f9dec2d", "shasum": "" }, "require": { @@ -29,8 +29,8 @@ "ext-json": "*", "jetbrains/phpstorm-stubs": "^2019.3", "phpunit/phpunit": "^7 | ^8 | ^9", - "psalm/phar": "^3.11@dev", - "react/promise": "^2" + "react/promise": "^2", + "vimeo/psalm": "^3.12" }, "type": "library", "extra": { @@ -85,7 +85,7 @@ "support": { "irc": "irc://irc.freenode.org/amphp", "issues": "https://github.com/amphp/amp/issues", - "source": "https://github.com/amphp/amp/tree/v2.6.2" + "source": "https://github.com/amphp/amp/tree/v2.6.4" }, "funding": [ { @@ -93,7 +93,7 @@ "type": "github" } ], - "time": "2022-02-20T17:52:18+00:00" + "time": "2024-03-21T18:52:26+00:00" }, { "name": "amphp/byte-stream", @@ -913,16 +913,16 @@ }, { "name": "phpstan/phpdoc-parser", - "version": "1.26.0", + "version": "1.27.0", "source": { "type": "git", "url": "https://github.com/phpstan/phpdoc-parser.git", - "reference": "231e3186624c03d7e7c890ec662b81e6b0405227" + "reference": "86e4d5a4b036f8f0be1464522f4c6b584c452757" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/231e3186624c03d7e7c890ec662b81e6b0405227", - "reference": "231e3186624c03d7e7c890ec662b81e6b0405227", + "url": "https://api.github.com/repos/phpstan/phpdoc-parser/zipball/86e4d5a4b036f8f0be1464522f4c6b584c452757", + "reference": "86e4d5a4b036f8f0be1464522f4c6b584c452757", "shasum": "" }, "require": { @@ -954,9 +954,9 @@ "description": "PHPDoc parser with support for nullable, intersection and generic types", "support": { "issues": "https://github.com/phpstan/phpdoc-parser/issues", - "source": "https://github.com/phpstan/phpdoc-parser/tree/1.26.0" + "source": "https://github.com/phpstan/phpdoc-parser/tree/1.27.0" }, - "time": "2024-02-23T16:05:55+00:00" + "time": "2024-03-21T13:14:53+00:00" }, { "name": "psr/container",