Forking what is left of ZeroNet and hopefully adding an AT Proto Frontend/Proxy
1import re
2
3
4# Parse and modify sql queries
5class DbQuery:
6 def __init__(self, query):
7 self.setQuery(query.strip())
8
9 # Split main parts of query
10 def parseParts(self, query):
11 parts = re.split("(SELECT|FROM|WHERE|ORDER BY|LIMIT)", query)
12 parts = [_f for _f in parts if _f] # Remove empty parts
13 parts = [s.strip() for s in parts] # Remove whitespace
14 return dict(list(zip(parts[0::2], parts[1::2])))
15
16 # Parse selected fields SELECT ... FROM
17 def parseFields(self, query_select):
18 fields = re.findall("([^,]+) AS ([^,]+)", query_select)
19 return {key: val.strip() for val, key in fields}
20
21 # Parse query conditions WHERE ...
22 def parseWheres(self, query_where):
23 if " AND " in query_where:
24 return query_where.split(" AND ")
25 elif query_where:
26 return [query_where]
27 else:
28 return []
29
30 # Set the query
31 def setQuery(self, query):
32 self.parts = self.parseParts(query)
33 self.fields = self.parseFields(self.parts["SELECT"])
34 self.wheres = self.parseWheres(self.parts.get("WHERE", ""))
35
36 # Convert query back to string
37 def __str__(self):
38 query_parts = []
39 for part_name in ["SELECT", "FROM", "WHERE", "ORDER BY", "LIMIT"]:
40 if part_name == "WHERE" and self.wheres:
41 query_parts.append("WHERE")
42 query_parts.append(" AND ".join(self.wheres))
43 elif part_name in self.parts:
44 query_parts.append(part_name)
45 query_parts.append(self.parts[part_name])
46 return "\n".join(query_parts)