If you want to receive both an absolute or a relative URI and replace one query string parameter (or even more), preserving whatever other parameter in the query string, like this:
// Get https://example.com?page=asdlol
echo uri_with_extra_params('https://example.com', [
'page' => 'asdlol',
]);
// Get https://example.com?page=asdlol
echo uri_with_extra_params('https://example.com?page=old', [
'page' => 'asdlol',
]);
// Get https://example.com?test=toast&page=asdlol
echo uri_with_extra_params('https://example.com?test=toast', [
'page' => 'asdlol',
]);
// Get /homepage/?page=asdlol
echo uri_with_extra_params('/homepage/', [
'page' => 'asdlol',
]);
To reach the above results, where the original URI is kept as-is (relative or absolute), just replacing the very specific query string parameters, you can use this function:
/**
* Get an URI as-is, forcing one query string parameter or more.
*
* @param $uri string URI relative or absolute, with or without query string
* @param $extra array Associative query string parameters to be added or replaced.
* @return URI relative or absolute, with the desired query string parameters
*/
function uri_with_extra_params(string $uri, array $extra): string
{
// Get the URI and the query string.
$url_parts = explode('?', $uri, 2);
$url_without_query_string = $url_parts[0];
$query_string_raw = $url_parts[1] ?? '';
// Get the query string array data.
$query_string_data = [];
parse_str($query_string_raw, $query_string_data);
// Force your new parameter(s).
$query_string_data_new = array_replace($query_string_data, $extra);
// Return the final URI in the desired language.
return $url_without_query_string . '?' . http_build_query($query_string_data_new);
}
Example to rewrite the current request URI and forcing a specific page "p":
// If the page was http://localhost/?something=1&page=1,
// get the page http://localhost/?something=1&page=2
$new_page = uri_with_extra_params($_SERVER['REQUEST_URI'], [
'page' => '2',
] );
I like this solution because it keeps the rest of the query string as-is, and it works for both relative and absolute URIs.