Skip to content

Commit 6aec22c

Browse files
committed
feat: improves fromArray conversion
1 parent 1f7b7bd commit 6aec22c

File tree

1 file changed

+58
-5
lines changed

1 file changed

+58
-5
lines changed

src/Providers/Http/DTO/Request.php

Lines changed: 58 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -327,11 +327,10 @@ public function toArray(): array
327327
{
328328
$array = [
329329
self::KEY_METHOD => $this->method->value,
330-
self::KEY_URI => $this->getUri(), // Include query params if GET with data
330+
self::KEY_URI => $this->getUri(),
331331
self::KEY_HEADERS => $this->headers->getAll(),
332332
];
333333

334-
// Include body if present (getBody() handles the conversion)
335334
$body = $this->getBody();
336335
if ($body !== null) {
337336
$array[self::KEY_BODY] = $body;
@@ -349,11 +348,65 @@ public static function fromArray(array $array): self
349348
{
350349
static::validateFromArrayData($array, [self::KEY_METHOD, self::KEY_URI, self::KEY_HEADERS]);
351350

351+
$method = HttpMethodEnum::from($array[self::KEY_METHOD]);
352+
$uri = $array[self::KEY_URI];
353+
$data = null;
354+
355+
// For GET requests, extract query parameters from URI
356+
if ($method->isGet()) {
357+
$parsedData = self::parseDataFromUri($uri);
358+
if ($parsedData !== null) {
359+
$uri = $parsedData['uri'];
360+
$data = $parsedData['data'];
361+
}
362+
} else {
363+
// Handle body which can be string, array, or object from JSON deserialization
364+
$bodyData = $array[self::KEY_BODY] ?? null;
365+
if (is_object($bodyData)) {
366+
/** @var array<string, mixed> $bodyData */
367+
$bodyData = (array) $bodyData;
368+
}
369+
$data = $bodyData;
370+
}
371+
352372
return new self(
353-
HttpMethodEnum::from($array[self::KEY_METHOD]),
354-
$array[self::KEY_URI],
373+
$method,
374+
$uri,
355375
$array[self::KEY_HEADERS] ?? [],
356-
$array[self::KEY_BODY] ?? null
376+
$data
357377
);
358378
}
379+
380+
/**
381+
* Parses query parameters from a URI string.
382+
*
383+
* @since n.e.x.t
384+
*
385+
* @param string $uri The URI to parse.
386+
* @return array{uri: string, data: array<string, mixed>}|null Returns parsed data or null if no query string.
387+
*/
388+
private static function parseDataFromUri(string $uri): ?array
389+
{
390+
$queryString = parse_url($uri, PHP_URL_QUERY);
391+
if ($queryString === null || $queryString === false || $queryString === '') {
392+
return null;
393+
}
394+
395+
$queryParams = [];
396+
parse_str($queryString, $queryParams);
397+
398+
if (empty($queryParams)) {
399+
return null;
400+
}
401+
402+
// Remove query string from URI since it will be reconstructed from data
403+
$questionPos = strpos($uri, '?');
404+
$cleanUri = $questionPos !== false ? substr($uri, 0, $questionPos) : $uri;
405+
406+
// PHPStan doesn't understand that parse_str always creates string keys
407+
return [ // @phpstan-ignore-line
408+
'uri' => $cleanUri,
409+
'data' => $queryParams,
410+
];
411+
}
359412
}

0 commit comments

Comments
 (0)