{"id":"cb0032d0e6e1e61d","repo":"pallets/flask","slug":"use-the-route-decorator-to-use-the-methods-arg","errorCode":null,"errorMessage":"Use the 'route' decorator to use the 'methods' argument.","messagePattern":"Use the 'route' decorator to use the 'methods' argument\\.","errorType":"validation","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"src/flask/sansio/scaffold.py","lineNumber":291,"sourceCode":"        \"\"\"The Jinja loader for this object's templates. By default this\n        is a class :class:`jinja2.loaders.FileSystemLoader` to\n        :attr:`template_folder` if it is set.\n\n        .. versionadded:: 0.5\n        \"\"\"\n        if self.template_folder is not None:\n            return FileSystemLoader(os.path.join(self.root_path, self.template_folder))\n        else:\n            return None\n\n    def _method_route(\n        self,\n        method: str,\n        rule: str,\n        options: dict[str, t.Any],\n    ) -> t.Callable[[T_route], T_route]:\n        if \"methods\" in options:\n            raise TypeError(\"Use the 'route' decorator to use the 'methods' argument.\")\n\n        return self.route(rule, methods=[method], **options)\n\n    @setupmethod\n    def get(self, rule: str, **options: t.Any) -> t.Callable[[T_route], T_route]:\n        \"\"\"Shortcut for :meth:`route` with ``methods=[\"GET\"]``.\n\n        .. versionadded:: 2.0\n        \"\"\"\n        return self._method_route(\"GET\", rule, options)\n\n    @setupmethod\n    def post(self, rule: str, **options: t.Any) -> t.Callable[[T_route], T_route]:\n        \"\"\"Shortcut for :meth:`route` with ``methods=[\"POST\"]``.\n\n        .. versionadded:: 2.0\n        \"\"\"\n        return self._method_route(\"POST\", rule, options)","sourceCodeStart":273,"sourceCodeEnd":309,"githubUrl":"https://github.com/pallets/flask/blob/6a2f545bfd8ed31e19066a299296917e034aca58/src/flask/sansio/scaffold.py#L273-L309","documentation":"The method shortcut decorators (@app.get, @app.post, @app.put, @app.delete, @app.patch) each hard-code a single HTTP method via _method_route. Passing methods= to them is contradictory — the shortcut already decides the method — so Flask raises TypeError instead of silently merging or overriding.","triggerScenarios":"@app.get('/x', methods=['GET','POST']) or any bp.post/put/delete/patch call that includes a methods= keyword in its options.","commonSituations":"Migrating from @app.route(..., methods=[...]) to the 2.0+ shortcut decorators and leaving the methods kwarg behind; copy-pasted route definitions; code generators emitting both forms.","solutions":["Remove the methods= argument from the shortcut decorator — @app.get already means methods=['GET'].","If the view must handle multiple methods, use @app.route('/x', methods=['GET','POST']) instead of a shortcut.","Alternatively stack shortcuts (@app.get and @app.post) on the same function with distinct endpoints only if the logic truly differs."],"exampleFix":"# before\n@app.get('/items', methods=['GET', 'POST'])\ndef items(): ...\n# after\n@app.route('/items', methods=['GET', 'POST'])\ndef items(): ...","handlingStrategy":"validation","validationCode":"# WRONG: @app.get('/x', methods=['POST'])\n# RIGHT: choose one form:\n@app.route('/x', methods=['GET', 'POST'])\ndef view(): ...","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never combine methods= with the shortcut decorators (@app.get/@app.post/etc.) — they hard-code the method","Use @app.route(...) whenever a view accepts multiple HTTP methods","Lint for the pattern r'@\\w+\\.(get|post|put|delete|patch)\\(.*methods=' in CI"],"tags":["flask","routing","decorator"],"analyzedSha":"6a2f545bfd8ed31e19066a299296917e034aca58","analyzedAt":"2026-07-31T19:13:49.921Z","schemaVersion":2}