|
14 | 14 | use Saloon\Contracts\FakeResponse; |
15 | 15 | use Saloon\Http\Faking\MockClient; |
16 | 16 | use Saloon\Contracts\Authenticator; |
| 17 | +use Saloon\Helpers\OAuth2\OAuthConfig; |
| 18 | +use Saloon\Http\OAuth2\GetUserRequest; |
17 | 19 | use Saloon\Contracts\Body\BodyRepository; |
18 | 20 | use Saloon\Http\PendingRequest\MergeBody; |
19 | 21 | use Saloon\Http\PendingRequest\MergeDelay; |
20 | 22 | use Saloon\Http\Middleware\DelayMiddleware; |
21 | 23 | use Saloon\Http\PendingRequest\BootPlugins; |
| 24 | +use Saloon\Http\OAuth2\GetAccessTokenRequest; |
22 | 25 | use Saloon\Traits\Auth\AuthenticatesRequests; |
23 | 26 | use Saloon\Http\Middleware\ValidateProperties; |
| 27 | +use Saloon\Http\OAuth2\GetRefreshTokenRequest; |
24 | 28 | use Saloon\Http\Middleware\DetermineMockResponse; |
25 | 29 | use Saloon\Exceptions\InvalidResponseClassException; |
26 | 30 | use Saloon\Exceptions\Request\FatalRequestException; |
27 | 31 | use Saloon\Traits\PendingRequest\ManagesPsrRequests; |
28 | 32 | use Saloon\Http\PendingRequest\MergeRequestProperties; |
29 | 33 | use Saloon\Http\PendingRequest\BootConnectorAndRequest; |
| 34 | +use Saloon\Http\OAuth2\GetClientCredentialsTokenRequest; |
30 | 35 | use Saloon\Traits\RequestProperties\HasRequestProperties; |
31 | 36 | use Saloon\Http\PendingRequest\AuthenticatePendingRequest; |
| 37 | +use Saloon\Http\OAuth2\GetClientCredentialsTokenBasicAuthRequest; |
32 | 38 |
|
33 | 39 | class PendingRequest |
34 | 40 | { |
@@ -89,7 +95,11 @@ public function __construct(Connector $connector, Request $request, ?MockClient |
89 | 95 | $this->connector = $connector; |
90 | 96 | $this->request = $request; |
91 | 97 | $this->method = $request->getMethod(); |
92 | | - $this->url = URLHelper::join($this->connector->resolveBaseUrl(), $this->request->resolveEndpoint()); |
| 98 | + $this->url = URLHelper::join( |
| 99 | + $this->connector->resolveBaseUrl(), |
| 100 | + $this->request->resolveEndpoint(), |
| 101 | + $this->resolveAllowBaseUrlOverrideForUrl(), |
| 102 | + ); |
93 | 103 | $this->authenticator = $request->getAuthenticator() ?? $connector->getAuthenticator(); |
94 | 104 | $this->mockClient = $mockClient ?? $request->getMockClient() ?? $connector->getMockClient() ?? MockClient::getGlobal(); |
95 | 105 |
|
@@ -316,4 +326,35 @@ protected function tap(callable $callable): static |
316 | 326 |
|
317 | 327 | return $this; |
318 | 328 | } |
| 329 | + |
| 330 | + /** |
| 331 | + * Resolve whether an absolute URL may be used when joining the connector base with the request endpoint. |
| 332 | + * Uses the request flag when set, else OAuth config for token/user internal requests, else the connector flag. |
| 333 | + */ |
| 334 | + protected function resolveAllowBaseUrlOverrideForUrl(): bool |
| 335 | + { |
| 336 | + if ($this->request->allowBaseUrlOverride !== null) { |
| 337 | + return $this->request->allowBaseUrlOverride; |
| 338 | + } |
| 339 | + |
| 340 | + if ($this->usesOAuthConfigTokenOrUserEndpoint() && method_exists($this->connector, 'oauthConfig') && $this->connector->oauthConfig() instanceof OAuthConfig) { |
| 341 | + return $this->connector->oauthConfig()->getAllowBaseUrlOverride(); |
| 342 | + } |
| 343 | + |
| 344 | + return $this->connector->allowBaseUrlOverride; |
| 345 | + } |
| 346 | + |
| 347 | + /** |
| 348 | + * True for internal OAuth2 requests (token exchange, refresh, client credentials, or user info). |
| 349 | + */ |
| 350 | + protected function usesOAuthConfigTokenOrUserEndpoint(): bool |
| 351 | + { |
| 352 | + $request = $this->request; |
| 353 | + |
| 354 | + return $request instanceof GetAccessTokenRequest |
| 355 | + || $request instanceof GetRefreshTokenRequest |
| 356 | + || $request instanceof GetUserRequest |
| 357 | + || $request instanceof GetClientCredentialsTokenRequest |
| 358 | + || $request instanceof GetClientCredentialsTokenBasicAuthRequest; |
| 359 | + } |
319 | 360 | } |
0 commit comments