SciPost Code Repository

Skip to content
Snippets Groups Projects
Commit 8824409f authored by George Katsikas's avatar George Katsikas :goat:
Browse files

add orcid, mail, and relevancy in profile dynsel

parent 7d2b1bad
No related branches found
No related tags found
No related merge requests found
...@@ -2,6 +2,8 @@ __copyright__ = "Copyright © Stichting SciPost (SciPost Foundation)" ...@@ -2,6 +2,8 @@ __copyright__ = "Copyright © Stichting SciPost (SciPost Foundation)"
__license__ = "AGPL v3" __license__ = "AGPL v3"
from functools import reduce
import re
from django import forms from django import forms
from django.db.models import Q from django.db.models import Q
...@@ -251,13 +253,58 @@ class ProfileDynSelForm(forms.Form): ...@@ -251,13 +253,58 @@ class ProfileDynSelForm(forms.Form):
def search_results(self): def search_results(self):
if self.cleaned_data["q"]: if self.cleaned_data["q"]:
splitwords = self.cleaned_data["q"].replace(",", "").split(" ") splitwords = self.cleaned_data["q"].replace(",", "").split(" ")
query = Q()
for word in splitwords: # Get ORCID term.
query = query & ( orcid_term = Q()
Q(last_name__icontains=word) | Q(first_name__icontains=word) for i, w in enumerate(splitwords):
) if re.match(r"[\d-]+", w):
profiles = Profile.objects.filter(query).distinct() splitwords.pop(i)
return profiles orcid_term |= Q(orcid_id__icontains=w)
# Get mail term.
mail_term = Q()
for i, w in enumerate(splitwords):
if "@" in w:
splitwords.pop(i) # Remove mail from further processing.
mail_term |= Q(emails__email__icontains=w)
base_query = mail_term & orcid_term
exact_query = base_query
exact_last_query = base_query
exact_first_query = base_query
contains_query = base_query
for w in splitwords:
# Find exact matches first where every word matches either first or last name.
exact_query &= Q(first_name__iexact=w) | Q(last_name__iexact=w)
# Find an exact match for the last name.
exact_last_query &= Q(first_name__icontains=w) | Q(last_name__iexact=w)
# Find an exact match for the first name.
exact_first_query &= Q(first_name__iexact=w) | Q(last_name__icontains=w)
# Find a contains match for the last name.
contains_query &= Q(first_name__icontains=w) | Q(last_name__icontains=w)
# If there are exact matches, do not include other matches.
exact_profiles = Profile.objects.filter(exact_query).distinct().distinct()
if exact_profiles.count() > 0:
return exact_profiles
# If there are partial exact matches, do not include other matches.
exact_first_profiles = Profile.objects.filter(exact_first_query)
exact_last_profiles = Profile.objects.filter(exact_last_query)
partial_exact_profiles = (
exact_first_profiles | exact_last_profiles
).distinct()
if partial_exact_profiles.count() > 0:
return partial_exact_profiles
# Include profiles matching all (partial) words in either first or last name.
contains_profiles = Profile.objects.filter(contains_query).distinct()
return contains_profiles
else: else:
return Profile.objects.none() return Profile.objects.none()
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment