from app import app, db from app.forms.search import AdvancedSearchForm, SearchForm from app.models.post import Post from app.models.comment import Comment from app.models.topic import Topic from app.models.forum import Forum from app.models.program import Program from app.utils.render import render from sqlalchemy import text, func, Date from flask import request from flask_sqlalchemy import Pagination SEARCH_RESULTS_PER_PAGE = 20 def paginate(data, page, per_page): # Based on page and per_page info, calculate start and end index of items to keep start_index = (page - 1) * per_page end_index = start_index + per_page # Get the paginated list of items items = data[start_index:end_index] # Create Pagination object return Pagination(None, page, per_page, len(data), items) def websearch_to_tsquery_multilang(search): return func.websearch_to_tsquery('french', search).op('||')(func.websearch_to_tsquery('english', search)) def to_tsvector_multilang(text): return func.to_tsvector('french', text).op('||')(func.to_tsvector('english', text)) @app.route('/rechercher/') @app.route('/rechercher//') def search(page=1): form = AdvancedSearchForm(request.args) results = list() if form.validate(): tsquery = websearch_to_tsquery_multilang(form.q.data) # Topics are sorted first in results topic_query = db.session.query(Topic).where( to_tsvector_multilang(Topic.title).bool_op('@@')(tsquery) ).group_by( Topic.id, Post.id ) # Programms follow directly in the results program_query = db.session.query(Program).where( to_tsvector_multilang(Program.name).bool_op('@@')(tsquery) ).group_by( Program.id, Post.id ) # Comments are less important than topics and programs comment_query = db.session.query(Comment).where( to_tsvector_multilang(Comment.text).bool_op('@@')(tsquery) ).group_by( Comment.id, Post.id ) if (form.date.data): topic_query = topic_query.where( Topic.date_created.cast(Date) == form.date.data ) program_query = program_query.where( Program.date_created.cast(Date) == form.date.data ) comment_query = comment_query.where( Comment.date_created.cast(Date) == form.date.data ) if (form.sortBy.data == "Date croissante"): topic_query = topic_query.order_by( Topic.date_created.asc() ) program_query = program_query.order_by( Program.date_created.asc() ) comment_query = comment_query.order_by( Post.date_created.asc() ) elif (form.sortBy.data == "Date décroissante"): topic_query = topic_query.order_by( Topic.date_created.desc() ) program_query = program_query.order_by( Program.date_created.desc() ) comment_query = comment_query.order_by( Post.date_created.desc() ) elif (form.sortBy.data == "Alphabétique croissant"): topic_query = topic_query.order_by( Topic.title.asc() ) program_query = program_query.order_by( Program.name.asc() ) comment_query = comment_query.order_by( Comment.text.asc() ) elif (form.sortBy.data == "Alphabétique décroissant"): topic_query = topic_query.order_by( Topic.title.desc() ) program_query = program_query.order_by( Program.name.desc() ) comment_query = comment_query.order_by( Comment.text.desc() ) results = list(topic_query) + list(program_query) + list(comment_query) results = paginate(results, page, SEARCH_RESULTS_PER_PAGE) return render('search.html', form=form, results=results)