This repository has been archived by the owner on Mar 11, 2022. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 1
/
figshare.py
167 lines (138 loc) · 5.68 KB
/
figshare.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
from typing import Union, Optional
import requests
from fastapi import APIRouter, HTTPException
router = APIRouter()
api_key: Optional[str] = None
stage_api_key: Optional[str] = None
def figshare_metadata_readme(figshare_dict: dict) -> dict:
"""
Function to provide shortened dict for README metadata
:param figshare_dict: Figshare API response
:return: README metadata based on Figshare response
"""
readme_dict = {}
if 'item' in figshare_dict:
print("figshare_metadata_readme: Using curation responses")
readme_dict['article_id'] = figshare_dict['item']['id']
readme_dict['curation_id'] = figshare_dict['id']
figshare_dict = figshare_dict['item']
else:
readme_dict['article_id'] = figshare_dict['id']
single_str_citation = figshare_dict['citation']
# Handle period in author list. Assume no period in dataset title
author_list = ([single_str_citation.split('):')[0] + ').'])
author_list += [str_row + '.' for str_row in
single_str_citation.split('): ')[1].split('. ')]
readme_dict.update({
'title': figshare_dict['title'],
'description': figshare_dict['description'],
'doi': f"https://doi.org/{figshare_dict['doi']}",
'preferred_citation': author_list,
'license': figshare_dict['license'],
'summary': figshare_dict['description'],
'references': figshare_dict['references'],
})
return readme_dict
@router.get('/figshare/{article_id}/')
def get_figshare(article_id: int, curation_id: Optional[int] = None,
stage: bool = False,
allow_approved: bool = False) -> Union[dict, HTTPException]:
"""
API call to retrieve Figshare metadata
\f
:param article_id: Figshare article ID
:param curation_id: Figshare curation ID
:param stage: Figshare stage or production API.
Stage is available for Figshare institutions
:param allow_approved: Return 200 responses even if curation is not pending
:return: Figshare API response
"""
if not stage:
base_url = "https://api.figshare.com"
else:
base_url = "https://api.figsh.com"
headers = {
'Content-Type': 'application/json',
'Authorization': f'token {api_key if not stage else stage_api_key}'
}
curation_url = f"{base_url}/v2/account/institution/review"
if curation_id is None:
url = f"{base_url}/v2/account/institution/reviews"
params = {
'offset': 0,
'limit': 1000,
'article_id': article_id
}
if not allow_approved:
params['status'] = 'pending'
curation_response = requests.get(url, headers=headers, params=params)
if curation_response.status_code != 200:
raise HTTPException(
status_code=curation_response.status_code,
detail=f"Figshare: {curation_response.json()['message']}",
)
else:
curation_json = curation_response.json()
if len(curation_json) != 0:
print(f"Retrieved curation_id for {article_id}: "
f"{curation_json[0]['id']} "
f"(status={curation_json[0]['status']})")
curation_id = curation_json[0]['id']
else:
art_response = requests.get(
f"{base_url}/v2/articles/{article_id}",
headers=headers)
if art_response.status_code != 200:
raise HTTPException(
status_code=art_response.status_code,
detail=f"Figshare: {art_response.json()['message']}"
)
else:
review_msg = "reviews" if allow_approved else "pending review"
raise HTTPException(
status_code=401,
detail=f"FastAPI: No valid {review_msg} for {article_id}"
)
if curation_id is not None:
url = f"{curation_url}/{curation_id}"
response = requests.get(url, headers=headers)
if response.status_code != 200:
raise HTTPException(
status_code=response.status_code,
detail=response.json(),
)
else:
r_json = response.json()
if not allow_approved:
if r_json['status'] == 'pending':
return r_json
else:
raise HTTPException(
status_code=401,
detail=f'FastAPI: No valid pending review for {article_id}'
)
else:
return r_json
@router.get('/metadata/{article_id}/')
async def get_readme_metadata(article_id: int,
curation_id: Optional[int] = None,
stage: bool = False,
allow_approved: bool = False) -> dict:
"""
API call for README metadata based on Figshare response
\f
:param article_id: Figshare article ID
:param curation_id: Figshare curation ID
:param stage: Figshare stage or production API.
Stage is available for Figshare institutions
:param allow_approved: Return 200 responses even if curation is not pending
:return: README metadata API response
"""
try:
figshare_dict = get_figshare(article_id, curation_id=curation_id,
stage=stage,
allow_approved=allow_approved)
readme_dict = figshare_metadata_readme(figshare_dict)
return readme_dict
except HTTPException as e:
raise e