2025-01-31 21:36:31 +08:00

143 lines
5.9 KiB
Python

from flask import Blueprint, render_template, session, request
from extensions import db
from models import Movie, Genre, CategorySearch, Search
recommendations_bp = Blueprint('recommendations', __name__)
@recommendations_bp.route('/recommendations', methods=['GET'])
def recommendations():
if 'user_id' not in session:
return render_template('recommendations.html', common_search_movies=[], liked_genres_movies=[])
user_id = session['user_id']
per_page = 12 # 每页展示的电影数量
page = request.args.get('page', 1, type=int) # 当前页码
# 获取“你常搜的”电影推荐
common_search_movies = []
common_searches = Search.query.filter_by(user_id=user_id).order_by(Search.search_times.desc()).all()
if common_searches:
common_keywords = [search.keyword for search in common_searches]
common_search_query = Movie.query.filter(
db.or_(*[Movie.title.contains(keyword) | Movie.actor.contains(keyword) for keyword in common_keywords])
).order_by(Movie.average_rating.desc()).paginate(page=page, per_page=per_page)
common_search_movies = common_search_query.items
else:
common_search_query = None # 如果没有条目,则用于模板中的判断
# 获取“你喜欢的类型”电影推荐
liked_genres_movies = []
liked_genres_searches = CategorySearch.query.filter_by(user_id=user_id).order_by(CategorySearch.search_times.desc()).all()
if liked_genres_searches:
liked_genre_ids = [search.category_id for search in liked_genres_searches]
liked_genres_query = Movie.query.filter(
db.or_(*[Movie.genres.contains(str(genre_id)) for genre_id in liked_genre_ids])
).order_by(Movie.average_rating.desc()).paginate(page=page, per_page=per_page)
liked_genres_movies = liked_genres_query.items
else:
liked_genres_query = None # 如果没有条目,则用于模板中的判断
return render_template(
'recommendations.html',
common_search_movies=common_search_movies,
common_search_query=common_search_query,
liked_genres_movies=liked_genres_movies,
liked_genres_query=liked_genres_query
)
from flask import jsonify, request
@recommendations_bp.route('/load_more_common_search', methods=['GET'])
def load_more_common_search():
user_id = session.get('user_id')
if not user_id:
return jsonify({"error": "User not logged in"}), 401
# 获取请求中的 offset 参数,默认为 0
offset = int(request.args.get('offset', 0))
limit = 12 # 每次加载12条
# 获取用户的“你常搜的”关键词,按频率从高到低排序
common_searches = Search.query.filter_by(user_id=user_id).order_by(Search.search_times.desc()).all()
# 用于存储所有符合条件的电影
all_movies_query = []
for search in common_searches:
keyword = search.keyword
movies_for_keyword = Movie.query.filter(
(Movie.title.contains(keyword)) | (Movie.actor.contains(keyword))
).order_by(Movie.average_rating.desc())
all_movies_query.extend(movies_for_keyword) # 累积所有关键词的电影
# 应用 offset 和 limit
all_movies_query = all_movies_query[offset:offset + limit]
# 将电影数据转化为字典列表
movies_data = []
for movie in all_movies_query:
genre_ids = movie.genres.split(",") if movie.genres else []
genre_names = Genre.query.filter(Genre.id.in_(genre_ids)).all()
movie.genre_names = ", ".join([genre.name for genre in genre_names])
movies_data.append({
"id": movie.id,
"title": movie.title,
"release_date": movie.release_date,
"genres": movie.genre_names,
"rating_count": movie.rating_count,
"average_rating": movie.average_rating,
"actor": movie.actor
})
return jsonify(movies_data=movies_data, has_more=len(movies_data) == limit)
@recommendations_bp.route('/load_more_liked_genres', methods=['GET'])
def load_more_liked_genres():
user_id = session.get('user_id')
if not user_id:
return jsonify({"error": "User not logged in"}), 401
# 获取请求中的 offset 参数,默认为 0
offset = int(request.args.get('offset', 0))
limit = 12 # 每次加载12条
# “你喜欢的类型”推荐,按频率从高到低排序
liked_genres_searches = CategorySearch.query.filter_by(user_id=user_id).order_by(CategorySearch.search_times.desc()).all()
liked_genres_movies = []
for search in liked_genres_searches:
genre_id = str(search.category_id)
# 生成匹配 genre_id 的 LIKE 查询条件,并按评分排序
conditions = [
Movie.genres.like(f"%,{genre_id},%") |
Movie.genres.like(f"{genre_id},%") |
Movie.genres.like(f"%,{genre_id}") |
(Movie.genres == genre_id)
]
movies_for_genre = Movie.query.filter(db.or_(*conditions)).order_by(Movie.average_rating.desc()).offset(offset).limit(limit).all()
liked_genres_movies.extend(movies_for_genre)
if len(liked_genres_movies) >= limit:
break # 每次最多加载12条
# 转换每部电影的 genres ID 列表为名称列表
for movie in liked_genres_movies:
genre_ids = movie.genres.split(",") if movie.genres else []
genre_names = Genre.query.filter(Genre.id.in_(genre_ids)).all()
movie.genre_names = ", ".join([genre.name for genre in genre_names])
# 将电影数据转化为字典列表
movies_data = [{
"id": movie.id,
"title": movie.title,
"release_date": movie.release_date,
"genres": movie.genre_names,
"rating_count": movie.rating_count,
"average_rating": movie.average_rating,
"actor": movie.actor
} for movie in liked_genres_movies]
return jsonify(movies_data=movies_data, has_more=len(movies_data) == limit)