{"record":{"id":"b1f9c9dc1d5af70d","repo":"symfony/symfony","slug":"the-request-was-not-redirected","errorCode":null,"errorMessage":"The request was not redirected.","messagePattern":"The request was not redirected\\.","errorType":"exception","errorClass":"LogicException","httpStatus":null,"severity":"error","filePath":"src/Symfony/Component/BrowserKit/AbstractBrowser.php","lineNumber":551,"sourceCode":"    }\n\n    /**\n     * Reloads the current browser.\n     */\n    public function reload(): Crawler\n    {\n        return $this->requestFromRequest($this->history->current(), false);\n    }\n\n    /**\n     * Follow redirects?\n     *\n     * @throws LogicException If request was not a redirect\n     */\n    public function followRedirect(): Crawler\n    {\n        if (!isset($this->redirect)) {\n            throw new LogicException('The request was not redirected.');\n        }\n\n        if (-1 !== $this->maxRedirects) {\n            if ($this->redirectCount > $this->maxRedirects) {\n                $this->redirectCount = 0;\n                throw new LogicException(\\sprintf('The maximum number (%d) of redirections was reached.', $this->maxRedirects));\n            }\n        }\n\n        $request = $this->internalRequest;\n\n        if (\\in_array($this->internalResponse->getStatusCode(), [301, 302, 303], true)) {\n            $method = 'GET';\n            $files = [];\n            $content = null;\n        } else {\n            $method = $request->getMethod();\n            $files = $request->getFiles();","sourceCodeStart":533,"sourceCodeEnd":569,"githubUrl":"https://github.com/symfony/symfony/blob/698e28026c22cf35d032cdb6e800db48b1535790/src/Symfony/Component/BrowserKit/AbstractBrowser.php#L533-L569","documentation":"Thrown by AbstractBrowser::followRedirect() (line 551) when called but the most recent request did not produce a redirect - i.e. $this->redirect was never set (the response status was not 3xx without a Location header, or followRedirects was off and the property stayed null). The contract is: you can only followRedirect() after a request that actually redirected.","triggerScenarios":"Calling `$client->followRedirect()` manually after a request that returned a 2xx response; calling it twice (the second time the redirect has already been consumed); calling it when followRedirects was off and the previous response had no Location header.","commonSituations":"Tests that assume a route redirects but it returns 200; calling followRedirect() after the client already auto-followed; misordered assertions where followRedirect runs against a non-redirect response; redirects disabled via `$client->followRedirects(false)` then forgetting to check the status.","solutions":["Check the response status before following: `if ($client->getInternalResponse()->getStatusCode() >= 300 && < 400) { $client->followRedirect(); }`.","Inspect `$client->getInternalResponse()->getHeader('Location')` to confirm a redirect exists.","If using `followRedirects(false)`, only call followRedirect() after verifying a 3xx response.","Avoid calling followRedirect() after auto-following has already consumed the redirect."],"exampleFix":"// before\n$client->followRedirects(false);\n$client->request('GET', '/maybe-redirect');\n$client->followRedirect(); // may throw if not a redirect\n\n// after\n$client->followRedirects(false);\n$client->request('GET', '/maybe-redirect');\nif (in_array($client->getInternalResponse()->getStatusCode(), [301,302,303,307,308], true)) {\n    $client->followRedirect();\n}","handlingStrategy":"validation","validationCode":"$client->followRedirects(false);\n$client->request('GET', '/maybe-redirect');\n$status = $client->getInternalResponse()->getStatusCode();\nif ($status >= 300 && $status < 400 && null !== $client->getInternalResponse()->getHeader('Location')) {\n    $client->followRedirect();\n}","typeGuard":"function clientHasPendingRedirect(\\Symfony\\Component\\BrowserKit\\AbstractBrowser $c): bool {\n    $r = new \\ReflectionObject($c);\n    $prop = $r->getProperty('redirect');\n    if (!$prop->isInitialized($c)) {\n        return false;\n    }\n    return null !== $prop->getValue($c);\n}","tryCatchPattern":"try {\n    $client->followRedirect();\n} catch (\\Symfony\\Component\\BrowserKit\\Exception\\LogicException $e) {\n    if (str_contains($e->getMessage(), 'was not redirected')) {\n        // not a redirect; assert on the actual response\n    } else {\n        throw $e;\n    }\n}","preventionTips":["Before followRedirect(), assert the response status is 3xx.","When using followRedirects(false), always check status before following.","Avoid calling followRedirect() after the client has already auto-followed."],"tags":["browser-kit","testing","redirect","lifecycle","api-misuse"],"analyzedSha":"698e28026c22cf35d032cdb6e800db48b1535790","analyzedAt":"2026-08-06T23:40:49.025Z","schemaVersion":2},"datasetVersion":"2026-08-07T03:17:09.362Z"}