mirror of
https://github.com/simple-login/app.git
synced 2025-02-23 07:13:18 +08:00
Optimize Alias.get_contacts() to retrieve the latest reply for each contact in a single query
This commit is contained in:
parent
a0ed091b35
commit
f2fb599664
3 changed files with 27 additions and 9 deletions
|
@ -89,9 +89,8 @@
|
|||
<div class="mb-2 text-muted small-text">
|
||||
Created {{ contact.created_at | dt }} <br>
|
||||
|
||||
{% if contact.last_reply() %}
|
||||
{% set email_log = contact.last_reply() %}
|
||||
Last email sent {{ email_log.created_at | dt }}
|
||||
{% if contact.latest_reply %}
|
||||
Last email sent {{ contact.latest_reply | dt }}
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
|
|
|
@ -2,20 +2,19 @@ import enum
|
|||
import random
|
||||
import uuid
|
||||
from email.utils import formataddr
|
||||
from typing import List, Tuple
|
||||
from typing import List, Tuple, Optional
|
||||
|
||||
import arrow
|
||||
import bcrypt
|
||||
from arrow import Arrow
|
||||
from flask import url_for
|
||||
from flask_login import UserMixin
|
||||
from sqlalchemy import text, desc, CheckConstraint
|
||||
from sqlalchemy import text, desc, CheckConstraint, and_, func
|
||||
from sqlalchemy.exc import IntegrityError
|
||||
from sqlalchemy.orm import joinedload
|
||||
from sqlalchemy_utils import ArrowType
|
||||
|
||||
from app import s3
|
||||
from app.config import (
|
||||
EMAIL_DOMAIN,
|
||||
MAX_NB_EMAIL_FREE_PLAN,
|
||||
URL,
|
||||
AVATAR_URL_EXPIRATION,
|
||||
|
@ -914,13 +913,27 @@ class Alias(db.Model, ModelMixin):
|
|||
return self.user.email
|
||||
|
||||
def get_contacts(self, page=0):
|
||||
contacts = (
|
||||
Contact.filter_by(alias_id=self.id)
|
||||
latest_reply = func.max(EmailLog.created_at)
|
||||
q = (
|
||||
db.session.query(Contact, latest_reply)
|
||||
.join(
|
||||
EmailLog,
|
||||
and_(EmailLog.contact_id == Contact.id, EmailLog.is_reply),
|
||||
isouter=True,
|
||||
)
|
||||
.filter(Contact.alias_id == self.id)
|
||||
.group_by(Contact.id)
|
||||
.order_by(Contact.created_at.desc())
|
||||
.limit(PAGE_LIMIT)
|
||||
.offset(page * PAGE_LIMIT)
|
||||
.all()
|
||||
)
|
||||
|
||||
contacts = []
|
||||
for contact, l in q:
|
||||
contact.latest_reply = l
|
||||
contacts.append(contact)
|
||||
|
||||
return contacts
|
||||
|
||||
def __repr__(self):
|
||||
|
@ -1050,6 +1063,9 @@ class Contact(db.Model, ModelMixin):
|
|||
alias = db.relationship(Alias)
|
||||
user = db.relationship(User)
|
||||
|
||||
# the latest reply sent to this contact
|
||||
latest_reply: Optional[Arrow] = None
|
||||
|
||||
@property
|
||||
def email(self):
|
||||
return self.website_email
|
||||
|
|
3
shell.py
3
shell.py
|
@ -8,6 +8,9 @@ from app.models import *
|
|||
from server import create_app
|
||||
from time import sleep
|
||||
|
||||
from sqlalchemy import *
|
||||
from sqlalchemy.orm import *
|
||||
|
||||
|
||||
def create_db():
|
||||
if not database_exists(DB_URI):
|
||||
|
|
Loading…
Reference in a new issue