a b/api.py
1
from fastapi import FastAPI, HTTPException
2
from fastapi.responses import JSONResponse
3
from pydantic import BaseModel
4
from aitrika.engine.online_aitrika import OnlineAItrika
5
from aitrika.llm.openai import OpenAILLM
6
from aitrika.utils.text_parser import generate_documents
7
from dotenv import load_dotenv
8
from fastapi.openapi.utils import get_openapi
9
import json
10
import os
11
import uvicorn
12
13
app = FastAPI(title="AItrika API", description="AItrika API", version="0.1.0")
14
load_dotenv()
15
16
17
class PubMedRequest(BaseModel):
18
    pubmed_id: int
19
20
21
class QueryRequest(BaseModel):
22
    pubmed_id: int
23
    query: str
24
25
26
@app.post(
27
    "/associations",
28
    summary="Get associations from a PubMed article",
29
    responses={
30
        200: {"description": "Associations retrieved successfully"},
31
        422: {"description": "Invalid PubMed ID provided"},
32
    },
33
)
34
def get_associations(request: PubMedRequest):
35
    """
36
    Extracts associations from a PubMed article based on its ID.
37
38
    Args:
39
        request (PubMedRequest): An object containing the PubMed ID.
40
41
    Returns:
42
        dict: A dictionary containing the extracted associations.
43
44
    Raises:
45
        HTTPException: If the PubMed ID is invalid or the article is not found.
46
    """
47
    try:
48
        engine = OnlineAItrika(pubmed_id=request.pubmed_id)
49
        associations = engine.extract_associations()
50
        return JSONResponse(content={"associations": associations}, status_code=200)
51
    except ValueError as e:
52
        raise HTTPException(status_code=422, detail=str(e))
53
    except Exception:
54
        raise HTTPException(status_code=500, detail="An unexpected error occurred")
55
56
57
@app.post(
58
    "/abstract",
59
    summary="Get abstract of a PubMed article",
60
    responses={
61
        200: {"description": "Abstract retrieved successfully"},
62
        422: {"description": "Invalid PubMed ID provided"},
63
    },
64
)
65
def get_abstract(request: PubMedRequest):
66
    """
67
    Retrieves the abstract of a PubMed article based on its ID.
68
69
    Args:
70
        request (PubMedRequest): An object containing the PubMed ID.
71
72
    Returns:
73
        dict: A dictionary containing the abstract of the article.
74
75
    Raises:
76
        HTTPException: If the PubMed ID is invalid or the article is not found.
77
    """
78
    try:
79
        engine = OnlineAItrika(pubmed_id=request.pubmed_id)
80
        abstract = engine.extract_abstract()
81
        return JSONResponse(content={"abstract": abstract}, status_code=200)
82
    except ValueError as e:
83
        raise HTTPException(status_code=422, detail=str(e))
84
    except Exception:
85
        raise HTTPException(status_code=500, detail="An unexpected error occurred")
86
87
88
@app.post(
89
    "/query",
90
    summary="Query a PubMed article",
91
    responses={
92
        200: {"description": "Query result retrieved successfully"},
93
        422: {"description": "Invalid PubMed ID or query provided"},
94
    },
95
)
96
def query_document(request: QueryRequest):
97
    """
98
    Queries a PubMed article with a user-provided question.
99
100
    Args:
101
        request (QueryRequest): An object containing the PubMed ID and the query.
102
103
    Returns:
104
        dict: A dictionary containing the result of the query.
105
106
    Raises:
107
        HTTPException: If the PubMed ID is invalid, the article is not found, or the query fails.
108
    """
109
    try:
110
        engine = OnlineAItrika(pubmed_id=request.pubmed_id)
111
        abstract = engine.extract_abstract()
112
        documents = generate_documents(content=abstract)
113
        llm = OpenAILLM(
114
            documents=documents,
115
            api_key=os.getenv("OPENAI_API_KEY"),
116
        )
117
        result = llm.query(query=request.query)
118
        return JSONResponse(content={"result": result}, status_code=200)
119
    except ValueError as e:
120
        raise HTTPException(status_code=422, detail=str(e))
121
    except Exception:
122
        raise HTTPException(status_code=500, detail="An unexpected error occurred")
123
124
125
@app.post(
126
    "/results",
127
    summary="Get results from a PubMed article",
128
    responses={
129
        200: {"description": "Results retrieved successfully"},
130
        422: {"description": "Invalid PubMed ID provided"},
131
    },
132
)
133
def get_results(request: PubMedRequest):
134
    """
135
    Extracts results from a PubMed article based on its ID.
136
137
    Args:
138
        request (PubMedRequest): An object containing the PubMed ID.
139
140
    Returns:
141
        dict: A dictionary containing the extracted results.
142
143
    Raises:
144
        HTTPException: If the PubMed ID is invalid or the article is not found.
145
    """
146
    try:
147
        engine = OnlineAItrika(pubmed_id=request.pubmed_id)
148
        llm = OpenAILLM(
149
            documents=generate_documents(content=engine.extract_abstract()),
150
            api_key=os.getenv("OPENAI_API_KEY"),
151
        )
152
        results = engine.extract_results(llm=llm)
153
        return JSONResponse(content={"results": results}, status_code=200)
154
    except ValueError as e:
155
        raise HTTPException(status_code=422, detail=str(e))
156
    except Exception:
157
        raise HTTPException(status_code=500, detail="An unexpected error occurred")
158
159
160
@app.post(
161
    "/participants",
162
    summary="Get number of participants from a PubMed article",
163
    responses={
164
        200: {"description": "Number of participants retrieved successfully"},
165
        422: {"description": "Invalid PubMed ID provided"},
166
    },
167
)
168
def get_number_of_participants(request: PubMedRequest):
169
    """
170
    Extracts the number of participants from a PubMed article based on its ID.
171
172
    Args:
173
        request (PubMedRequest): An object containing the PubMed ID.
174
175
    Returns:
176
        dict: A dictionary containing the number of participants.
177
178
    Raises:
179
        HTTPException: If the PubMed ID is invalid or the article is not found.
180
    """
181
    try:
182
        engine = OnlineAItrika(pubmed_id=request.pubmed_id)
183
        llm = OpenAILLM(
184
            documents=generate_documents(content=engine.extract_abstract()),
185
            api_key=os.getenv("OPENAI_API_KEY"),
186
        )
187
        number_of_participants = engine.extract_number_of_participants(llm=llm)
188
        return JSONResponse(
189
            content={"number_of_participants": number_of_participants}, status_code=200
190
        )
191
    except ValueError as e:
192
        raise HTTPException(status_code=422, detail=str(e))
193
    except Exception:
194
        raise HTTPException(status_code=500, detail="An unexpected error occurred")
195
196
197
@app.post(
198
    "/outcomes",
199
    summary="Get outcomes from a PubMed article",
200
    responses={
201
        200: {"description": "Outcomes retrieved successfully"},
202
        422: {"description": "Invalid PubMed ID provided"},
203
    },
204
)
205
def get_outcomes(request: PubMedRequest):
206
    """
207
    Extracts outcomes from a PubMed article based on its ID.
208
209
    Args:
210
        request (PubMedRequest): An object containing the PubMed ID.
211
212
    Returns:
213
        dict: A dictionary containing the extracted outcomes.
214
215
    Raises:
216
        HTTPException: If the PubMed ID is invalid or the article is not found.
217
    """
218
    try:
219
        engine = OnlineAItrika(pubmed_id=request.pubmed_id)
220
        llm = OpenAILLM(
221
            documents=generate_documents(content=engine.extract_abstract()),
222
            api_key=os.getenv("OPENAI_API_KEY"),
223
        )
224
        outcomes = engine.extract_outcomes(llm=llm)
225
        return JSONResponse(content={"outcomes": outcomes}, status_code=200)
226
    except ValueError as e:
227
        raise HTTPException(status_code=422, detail=str(e))
228
    except Exception:
229
        raise HTTPException(status_code=500, detail="An unexpected error occurred")
230
231
232
if __name__ == "__main__":
233
    with open("docs/api-reference/openapi.json", "w") as f:
234
        json.dump(
235
            get_openapi(
236
                title=app.title,
237
                version=app.version,
238
                openapi_version=app.openapi_version,
239
                description=app.description,
240
                routes=app.routes,
241
            ),
242
            f,
243
        )
244
    uvicorn.run(app, host="0.0.0.0", port=8000)