mirror of
				https://github.com/janeczku/calibre-web
				synced 2025-10-30 23:03:02 +00:00 
			
		
		
		
	Books sort with non Books table column working #1938
This commit is contained in:
		
							
								
								
									
										15
									
								
								cps/db.py
									
									
									
									
									
								
							
							
						
						
									
										15
									
								
								cps/db.py
									
									
									
									
									
								
							| @@ -702,14 +702,21 @@ class CalibreDB(): | |||||||
|         return self.session.query(Books) \ |         return self.session.query(Books) \ | ||||||
|             .filter(and_(Books.authors.any(and_(*q)), func.lower(Books.title).ilike("%" + title + "%"))).first() |             .filter(and_(Books.authors.any(and_(*q)), func.lower(Books.title).ilike("%" + title + "%"))).first() | ||||||
|  |  | ||||||
|     def search_query(self, term): |     def search_query(self, term, *join): | ||||||
|         term.strip().lower() |         term.strip().lower() | ||||||
|         self.session.connection().connection.connection.create_function("lower", 1, lcase) |         self.session.connection().connection.connection.create_function("lower", 1, lcase) | ||||||
|         q = list() |         q = list() | ||||||
|         authorterms = re.split("[, ]+", term) |         authorterms = re.split("[, ]+", term) | ||||||
|         for authorterm in authorterms: |         for authorterm in authorterms: | ||||||
|             q.append(Books.authors.any(func.lower(Authors.name).ilike("%" + authorterm + "%"))) |             q.append(Books.authors.any(func.lower(Authors.name).ilike("%" + authorterm + "%"))) | ||||||
|         return self.session.query(Books).filter(self.common_filters(True)).filter( |         query = self.session.query(Books) | ||||||
|  |         if len(join) == 3: | ||||||
|  |             query = query.outerjoin(join[0], join[1]).outerjoin(join[2]) | ||||||
|  |         elif len(join) == 2: | ||||||
|  |             query = query.outerjoin(join[0], join[1]) | ||||||
|  |         elif len(join) == 1: | ||||||
|  |             query = query.outerjoin(join[0]) | ||||||
|  |         return query.filter(self.common_filters(True)).filter( | ||||||
|             or_(Books.tags.any(func.lower(Tags.name).ilike("%" + term + "%")), |             or_(Books.tags.any(func.lower(Tags.name).ilike("%" + term + "%")), | ||||||
|                 Books.series.any(func.lower(Series.name).ilike("%" + term + "%")), |                 Books.series.any(func.lower(Series.name).ilike("%" + term + "%")), | ||||||
|                 Books.authors.any(and_(*q)), |                 Books.authors.any(and_(*q)), | ||||||
| @@ -718,10 +725,10 @@ class CalibreDB(): | |||||||
|                 )) |                 )) | ||||||
|  |  | ||||||
|     # read search results from calibre-database and return it (function is used for feed and simple search |     # read search results from calibre-database and return it (function is used for feed and simple search | ||||||
|     def get_search_results(self, term, offset=None, order=None, limit=None): |     def get_search_results(self, term, offset=None, order=None, limit=None, *join): | ||||||
|         order = order or [Books.sort] |         order = order or [Books.sort] | ||||||
|         pagination = None |         pagination = None | ||||||
|         result = self.search_query(term).order_by(*order).all() |         result = self.search_query(term, *join).order_by(*order).all() | ||||||
|         result_count = len(result) |         result_count = len(result) | ||||||
|         if offset != None and limit != None: |         if offset != None and limit != None: | ||||||
|             offset = int(offset) |             offset = int(offset) | ||||||
|   | |||||||
| @@ -49,5 +49,5 @@ except ImportError as err: | |||||||
| try: | try: | ||||||
|     from . import gmail |     from . import gmail | ||||||
| except ImportError as err: | except ImportError as err: | ||||||
|     log.debug("Cannot import Gmail, sending books via G-Mail Accounts will not work: %s", err) |     log.debug("Cannot import gmail, sending books via Gmail Oauth2 Verification will not work: %s", err) | ||||||
|     gmail = None |     gmail = None | ||||||
|   | |||||||
| @@ -47,13 +47,13 @@ | |||||||
|             {{ text_table_row('title', _('Enter Title'),_('Title'), true, true) }} |             {{ text_table_row('title', _('Enter Title'),_('Title'), true, true) }} | ||||||
|             {{ text_table_row('sort', _('Enter Title Sort'),_('Title Sort'), false, true) }} |             {{ text_table_row('sort', _('Enter Title Sort'),_('Title Sort'), false, true) }} | ||||||
|             {{ text_table_row('author_sort', _('Enter Author Sort'),_('Author Sort'), false, true) }} |             {{ text_table_row('author_sort', _('Enter Author Sort'),_('Author Sort'), false, true) }} | ||||||
|             {{ text_table_row('authors', _('Enter Authors'),_('Authors'), true) }} |             {{ text_table_row('authors', _('Enter Authors'),_('Authors'), true, true) }} | ||||||
|             {{ text_table_row('tags', _('Enter Categories'),_('Categories'), false, false) }} |             {{ text_table_row('tags', _('Enter Categories'),_('Categories'), false, true) }} | ||||||
|             {{ text_table_row('series', _('Enter Series'),_('Series'), false, false) }} |             {{ text_table_row('series', _('Enter Series'),_('Series'), false, true) }} | ||||||
|             <th data-field="series_index" id="series_index" data-visible="{{visiblility.get('series_index')}}" data-edit-validate="{{ _('This Field is Required') }}" data-sortable="true" {% if g.user.role_edit() %} data-editable-type="number" data-editable-placeholder="1" data-editable-step="0.01" data-editable-min="0" data-editable-url="{{ url_for('editbook.edit_list_book', param='series_index')}}" data-edit="true" data-editable-title="{{_('Enter title')}}"{% endif %}>{{_('Series Index')}}</th> |             <th data-field="series_index" id="series_index" data-visible="{{visiblility.get('series_index')}}" data-edit-validate="{{ _('This Field is Required') }}" data-sortable="true" {% if g.user.role_edit() %} data-editable-type="number" data-editable-placeholder="1" data-editable-step="0.01" data-editable-min="0" data-editable-url="{{ url_for('editbook.edit_list_book', param='series_index')}}" data-edit="true" data-editable-title="{{_('Enter title')}}"{% endif %}>{{_('Series Index')}}</th> | ||||||
|             {{ text_table_row('languages', _('Enter Languages'),_('Languages'), false, false) }} |             {{ text_table_row('languages', _('Enter Languages'),_('Languages'), false, true) }} | ||||||
|             <!--th data-field="pubdate" data-type="date" data-visible="{{visiblility.get('pubdate')}}" data-viewformat="dd.mm.yyyy" id="pubdate" data-sortable="true">{{_('Publishing Date')}}</th--> |             <!--th data-field="pubdate" data-type="date" data-visible="{{visiblility.get('pubdate')}}" data-viewformat="dd.mm.yyyy" id="pubdate" data-sortable="true">{{_('Publishing Date')}}</th--> | ||||||
|             {{ text_table_row('publishers', _('Enter Publishers'),_('Publishers'), false, false) }} |             {{ text_table_row('publishers', _('Enter Publishers'),_('Publishers'), false, true) }} | ||||||
|           {% if g.user.role_delete_books() and g.user.role_edit()%} |           {% if g.user.role_delete_books() and g.user.role_edit()%} | ||||||
|             <th data-align="right" data-formatter="EbookActions" data-switchable="false">{{_('Delete')}}</th> |             <th data-align="right" data-formatter="EbookActions" data-switchable="false">{{_('Delete')}}</th> | ||||||
|           {% endif %} |           {% endif %} | ||||||
|   | |||||||
| @@ -12,7 +12,7 @@ | |||||||
|       <label for="mail_server_type">{{_('Choose Server Type')}}</label> |       <label for="mail_server_type">{{_('Choose Server Type')}}</label> | ||||||
|       <select name="mail_server_type" id="config_email_type" class="form-control" data-control="email-settings"> |       <select name="mail_server_type" id="config_email_type" class="form-control" data-control="email-settings"> | ||||||
|        <option value="0" {% if content.mail_server_type == 0 %}selected{% endif %}>{{_('Use Standard E-Mail Account')}}</option> |        <option value="0" {% if content.mail_server_type == 0 %}selected{% endif %}>{{_('Use Standard E-Mail Account')}}</option> | ||||||
|        <option value="1" {% if content.mail_server_type == 1 %}selected{% endif %}>{{_('G-Mail Account with OAuth2 Verfification')}}</option> |        <option value="1" {% if content.mail_server_type == 1 %}selected{% endif %}>{{_('Gmail Account with OAuth2 Verfification')}}</option> | ||||||
|       </select> |       </select> | ||||||
|     </div> |     </div> | ||||||
|     <div data-related="email-settings-1"> |     <div data-related="email-settings-1"> | ||||||
| @@ -20,7 +20,7 @@ | |||||||
|         {% if content.mail_gmail_token == {} %} |         {% if content.mail_gmail_token == {} %} | ||||||
|         <button type="submit" id="gmail_server" name="gmail" value="submit" class="btn btn-default">{{_('Setup Gmail Account as E-Mail Server')}}</button> |         <button type="submit" id="gmail_server" name="gmail" value="submit" class="btn btn-default">{{_('Setup Gmail Account as E-Mail Server')}}</button> | ||||||
|         {% else %} |         {% else %} | ||||||
|         <button type="submit" id="invalidate_server" name="invalidate" value="submit" class="btn btn-danger">{{_('Revoke G-Mail Access')}}</button> |         <button type="submit" id="invalidate_server" name="invalidate" value="submit" class="btn btn-danger">{{_('Revoke Gmail Access')}}</button> | ||||||
|         {% endif %} |         {% endif %} | ||||||
|       </div> |       </div> | ||||||
|     </div> |     </div> | ||||||
|   | |||||||
							
								
								
									
										22
									
								
								cps/web.py
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								cps/web.py
									
									
									
									
									
								
							| @@ -760,10 +760,26 @@ def list_books(): | |||||||
|     sort = request.args.get("sort", "id") |     sort = request.args.get("sort", "id") | ||||||
|     order = request.args.get("order", "").lower() |     order = request.args.get("order", "").lower() | ||||||
|     state = None |     state = None | ||||||
|  |     join = tuple() | ||||||
|  |  | ||||||
|     if sort == "state": |     if sort == "state": | ||||||
|         state = json.loads(request.args.get("state", "[]")) |         state = json.loads(request.args.get("state", "[]")) | ||||||
|     if sort != "state" and order: |     elif sort == "tags": | ||||||
|  |         order = [db.Tags.name.asc()] if order == "asc" else [db.Tags.name.desc()] | ||||||
|  |         join = db.books_tags_link,db.Books.id == db.books_tags_link.c.book, db.Tags | ||||||
|  |     elif sort == "series": | ||||||
|  |         order = [db.Series.name.asc()] if order == "asc" else [db.Series.name.desc()] | ||||||
|  |         join = db.books_series_link,db.Books.id == db.books_series_link.c.book, db.Series | ||||||
|  |     elif sort == "publishers": | ||||||
|  |         order = [db.Publishers.name.asc()] if order == "asc" else [db.Publishers.name.desc()] | ||||||
|  |         join = db.books_publishers_link,db.Books.id == db.books_publishers_link.c.book, db.Publishers | ||||||
|  |     elif sort == "authors": | ||||||
|  |         order = [db.Authors.name.asc()] if order == "asc" else [db.Authors.name.desc()] | ||||||
|  |         join = db.books_authors_link,db.Books.id == db.books_authors_link.c.book, db.Authors | ||||||
|  |     elif sort == "languages": | ||||||
|  |         order = [db.Languages.lang_code.asc()] if order == "asc" else [db.Languages.lang_code.desc()] | ||||||
|  |         join = db.books_languages_link,db.Books.id == db.books_languages_link.c.book, db.Languages | ||||||
|  |     elif order and sort in ["sort", "title", "authors_sort", "series_index"]: | ||||||
|         order = [text(sort + " " + order)] |         order = [text(sort + " " + order)] | ||||||
|     elif not state: |     elif not state: | ||||||
|         order = [db.Books.timestamp.desc()] |         order = [db.Books.timestamp.desc()] | ||||||
| @@ -778,9 +794,9 @@ def list_books(): | |||||||
|             books = calibre_db.session.query(db.Books).filter(calibre_db.common_filters()).all() |             books = calibre_db.session.query(db.Books).filter(calibre_db.common_filters()).all() | ||||||
|         entries = calibre_db.get_checkbox_sorted(books, state, off, limit,order) |         entries = calibre_db.get_checkbox_sorted(books, state, off, limit,order) | ||||||
|     elif search: |     elif search: | ||||||
|         entries, filtered_count, __ = calibre_db.get_search_results(search, off, order, limit) |         entries, filtered_count, __ = calibre_db.get_search_results(search, off, order, limit, *join) | ||||||
|     else: |     else: | ||||||
|         entries, __, __ = calibre_db.fill_indexpage((int(off) / (int(limit)) + 1), limit, db.Books, True, order) |         entries, __, __ = calibre_db.fill_indexpage((int(off) / (int(limit)) + 1), limit, db.Books, True, order, *join) | ||||||
|  |  | ||||||
|     for entry in entries: |     for entry in entries: | ||||||
|         for index in range(0, len(entry.languages)): |         for index in range(0, len(entry.languages)): | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 Ozzie Isaacs
					Ozzie Isaacs