File size: 2,404 Bytes
1d12e97
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
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
from fastapi import FastAPI, Query, Request, HTTPException
from fastapi.responses import JSONResponse, HTMLResponse
from rdflib import Graph
import os
import uvicorn

app = FastAPI(title="Cars Knowledge Graph SPARQL Endpoint")

# Load the Knowledge Graph
g = Graph()
GRAPH_FILE = "cars_knowledge_graph.ttl"

if os.path.exists(GRAPH_FILE):
    print(f"Loading Knowledge Graph from {GRAPH_FILE}...")
    g.parse(GRAPH_FILE, format="turtle")
    print(f"Graph loaded with {len(g)} triples.")
else:
    print(f"WARNING: {GRAPH_FILE} not found. Please run convert_data.py first.")

@app.get("/", response_class=HTMLResponse)
async def home():
    return """
    <h1>Cars Knowledge Graph SPARQL Endpoint (FastAPI)</h1>
    <p>The Knowledge Graph is published and accessible.</p>
    <p>Send SPARQL queries to: <code>/sparql</code></p>
    <h3>Example Query:</h3>
    <pre>
    SELECT ?s ?p ?o WHERE { ?s ?p ?o } LIMIT 10
    </pre>
    <p>View API Docs at: <a href="/docs">/docs</a></p>
    """

async def run_query(query: str):
    if not query:
        raise HTTPException(status_code=400, detail="No query provided")
    
    try:
        results = g.query(query)
        
        # Format results as JSON
        res_list = []
        for row in results:
            res_dict = {}
            if getattr(results, "vars", None):
                for i, var in enumerate(results.vars):
                    if row[i] is not None:
                        res_dict[str(var)] = str(row[i])
            res_list.append(res_dict)
            
        return {"results": res_list}
        
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))

@app.get("/sparql")
async def sparql_get(query: str = Query(..., description="SPARQL Query")):
    return await run_query(query)

@app.post("/sparql")
async def sparql_post(request: Request):
    # Handle both form data and raw body
    content_type = request.headers.get("content-type", "")
    if "application/x-www-form-urlencoded" in content_type:
        form = await request.form()
        query = form.get("query")
    else:
        # data = await request.json() # Optional depending on client
        query = (await request.body()).decode("utf-8")
        
    return await run_query(query)

if __name__ == "__main__":
    print("Starting SPARQL Endpoint on http://localhost:8000")
    uvicorn.run(app, host="0.0.0.0", port=8000)