pythonsqliteflasksqlalchemyflask-login

Flask-login is making Flask return 404 error


I have a script which is basically a blog post website, it has multiple routes and uses many libraries. Here is a MRE of my code.

from flask import Flask, render_template, request
from flask_login import UserMixin, LoginManager, current_user
from flask_sqlalchemy import SQLAlchemy
from sqlalchemy.orm import relationship, DeclarativeBase, Mapped, mapped_column
from sqlalchemy import Integer, String, Text, ForeignKey
from typing import List

app = Flask(__name__)

app.config['SECRET_KEY'] = '8BYkEfBA6O6donzWlSihBXox7C0sKR6b'
login_manager = LoginManager()
login_manager.init_app(app)


@login_manager.user_loader
def load_user(user_id):
    return db.get_or_404(User, user_id)

class Base(DeclarativeBase):
    pass

app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///posts.db'
db = SQLAlchemy(model_class=Base)
db.init_app(app)

class BlogPost(db.Model):
    __tablename__ = "blog_posts"
    id: Mapped[int] = mapped_column(Integer, primary_key=True)
    title: Mapped[str] = mapped_column(String(250), unique=True, nullable=False)
    subtitle: Mapped[str] = mapped_column(String(250), nullable=False)
    date: Mapped[str] = mapped_column(String(250), nullable=False)
    body: Mapped[str] = mapped_column(Text, nullable=False)
    author = relationship("User", back_populates='posts')
    img_url: Mapped[str] = mapped_column(String(250), nullable=False)
    author_id = db.Column(Integer, ForeignKey('users.id'))

class User(UserMixin, db.Model):
    __tablename__ = "users"
    id: Mapped[int] = mapped_column(Integer, primary_key=True)
    email: Mapped[str] = mapped_column(String, unique=True, nullable=False)
    password: Mapped[str] = mapped_column(String, nullable=False)
    name: Mapped[str] = mapped_column(String, nullable=False)
    posts: Mapped[List["BlogPost"]] = relationship(back_populates="author")

with app.app_context():
    db.create_all()


@app.route("/")
def home():
    return render_template('test.html')

While I was playing around to see what was causing the problem, I realized that as soon as I added the flask_login (which requires SQLAlchemy), flask returned a 404 not found error. In my real code, I use flask_login very often to control many things. This has bamboozled me since it stopped working all of a sudden.


Solution

  • One possible explanation for the 404 return value is your implementation of the callback for the LoginManager. Actually, a 404 error message isn't needed here when the user ID isn't found.

    Try the following variation.

    @login_manager.user_loader
    def load_user(user_id):
        return db.session.get(User, int(user_id))
    

    If the user doesn't stay logged in, there's another problem.