diff --git a/submissions/models.py b/submissions/models.py index 7152bbec356f59dc5205e5ec592027ca642857aa..56a4b9d6789457653789014ed59bc3842b727fac 100644 --- a/submissions/models.py +++ b/submissions/models.py @@ -3,6 +3,7 @@ __license__ = "AGPL v3" import datetime +import feedparser from django.contrib.postgres.fields import JSONField from django.contrib.contenttypes.fields import GenericRelation @@ -273,6 +274,32 @@ class Submission(models.Model): ) event.save() + """ + Identify coauthorships from arXiv, using author surname matching. + """ + def flag_coauthorships_arxiv(self, fellows): + coauthorships = {} + if self.metadata and 'entries' in self.metadata: + author_last_names = [] + for author in self.metadata['entries'][0]['authors']: + # Gather author data to do conflict-of-interest queries with + author_last_names.append(author['name'].split()[-1]) + authors_last_names_str = '+OR+'.join(author_last_names) + + for fellow in fellows: + # For each fellow found, so a query with the authors to check for conflicts + search_query = 'au:({fellow}+AND+({authors}))'.format( + fellow=fellow.contributor.user.last_name, + authors=authors_last_names_str) + queryurl = 'https://export.arxiv.org/api/query?search_query={sq}'.format( + sq=search_query) + queryurl += '&sortBy=submittedDate&sortOrder=descending&max_results=5' + queryurl = queryurl.replace(' ', '+') # Fallback for some last names with spaces + queryresults = feedparser.parse(queryurl) + if queryresults.entries: + coauthorships[fellow.contributor.user.last_name] = queryresults.entries + return coauthorships + class SubmissionEvent(SubmissionRelatedObjectMixin, TimeStampedModel): """Private message directly related to a Submission. diff --git a/submissions/templates/submissions/admin/editorial_assignment_form.html b/submissions/templates/submissions/admin/editorial_assignment_form.html index df473a80d47ac289a9f7303c1965dff8c4344d05..0761db76ba37f126cea40b4f53ae96df497623da 100644 --- a/submissions/templates/submissions/admin/editorial_assignment_form.html +++ b/submissions/templates/submissions/admin/editorial_assignment_form.html @@ -62,4 +62,38 @@ </div> </div> + +<div class="row"> + <div class="col-12"> + {% if coauthorships %} + <div class="card card-outline-danger"> + <div class="card-body"> + <h3 class="card-title text-danger">The system identified the following potential coauthorships (from arXiv database)</h3> + <p class="card-text text-danger">(only up to 5 most recent shown; if within the last 3 years, referee is disqualified):</p> + </div> + <div class="card-body"> + <ul class="list-group list-group-flush"> + {% for author, entries in coauthorships.items %} + <li class="list-group-item pt-3"> + <div class="card-content"> + <h3>For Fellow: {{ author }}</h3> + </div>{{ value}} + </li> + {% for entry in entries %} + <li class="list-group-item"> + {% include 'partials/submissions/arxiv_queryresult.html' with item=entry id=forloop.counter %} + </li> + {% endfor %} + {% endfor %} + </ul> + </div> + </div> + {% else %} + <h3 class="text-success">The system has not identified any coauthorships (from arXiv database)</h3> + {% endif %} + </div> +</div> + + + {% endblock %} diff --git a/submissions/views.py b/submissions/views.py index ad09959d78e7f6c24a8e8dcbeb54dcedf36ba180..8e6375aed27c13db5c50d7cdd25f590fd16e11c7 100644 --- a/submissions/views.py +++ b/submissions/views.py @@ -445,14 +445,21 @@ def assign_submission(request, arxiv_identifier_w_vn_nr): arxiv_identifier_w_vn_nr=arxiv_identifier_w_vn_nr) form = EditorialAssignmentForm(request.POST or None, submission=submission) + fellows_with_expertise = submission.fellows.filter( + contributor__expertises__contains=[submission.subject_area]) + coauthorships = submission.flag_coauthorships_arxiv(fellows_with_expertise) + if form.is_valid(): ed_assignment = form.save() SubmissionUtils.load({'assignment': ed_assignment}) SubmissionUtils.send_assignment_request_email() messages.success(request, 'Your assignment request has been sent successfully.') return redirect('submissions:pool') + context = { 'submission_to_assign': submission, + 'fellows_with_expertise': fellows_with_expertise, + 'coauthorships': coauthorships, 'form': form } return render(request, 'submissions/admin/editorial_assignment_form.html', context) @@ -1405,26 +1412,7 @@ def prepare_for_voting(request, rec_id): return redirect(reverse('submissions:editorial_page', args=[recommendation.submission.arxiv_identifier_w_vn_nr])) else: - # Identify possible co-authorships in last 3 years, disqualifying Fellow from voting: - if recommendation.submission.metadata and 'entries' in recommendation.submission.metadata: - author_last_names = [] - for author in recommendation.submission.metadata['entries'][0]['authors']: - # Gather author data to do conflict-of-interest queries with - author_last_names.append(author['name'].split()[-1]) - authors_last_names_str = '+OR+'.join(author_last_names) - - for fellow in fellows_with_expertise: - # For each fellow found, so a query with the authors to check for conflicts - search_query = 'au:({fellow}+AND+({authors}))'.format( - fellow=fellow.contributor.user.last_name, - authors=authors_last_names_str) - queryurl = 'https://export.arxiv.org/api/query?search_query={sq}'.format( - sq=search_query) - queryurl += '&sortBy=submittedDate&sortOrder=descending&max_results=5' - queryurl = queryurl.replace(' ', '+') # Fallback for some last names with spaces - queryresults = feedparser.parse(queryurl) - if queryresults.entries: - coauthorships[fellow.contributor.user.last_name] = queryresults.entries + coauthorships = recommendation.submission.flag_coauthorships_arxiv(fellows_with_expertise) context = { 'recommendation': recommendation,