upload_run_toa.py 6.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228
  1. #!/usr/bin/python3
  2. import sqlite3
  3. import json
  4. import sys
  5. import os
  6. import math
  7. """
  8. Reads the API KEY, that must be passed as first command line argument.
  9. :returns: Recovered API KEY.
  10. :raises Exception: Th KEY couldn't be red.
  11. """
  12. def readKey():
  13. try:
  14. key = sys.argv[1]
  15. return key
  16. except Exception as e:
  17. print("Error parsing API KEY: " + str(e))
  18. raise
  19. """
  20. Reads the JSON data, that must be passed as second command line argument.
  21. :param: index 2 for start data, 3 for result data
  22. :returns: Recovered data, in JSON format.
  23. :raises Exception: The data couldn't be red or converted to JSON.
  24. """
  25. def readData(index):
  26. try:
  27. data = json.loads(sys.argv[index])
  28. return data
  29. except Exception as e:
  30. print("Error parsing data: " + str(e))
  31. raise
  32. """
  33. Verifies that the API key matches the player data and that it exists in th DB.
  34. :param db: Connection to the database.
  35. :returns: Connection to the database.
  36. :param data: Data in json format.
  37. :param key: API KEY.
  38. :returns: True if key and player match, False otherwise.
  39. :raises IntegrityError: The queryes couldn't bre executed.
  40. """
  41. def verifyKey(db, data, key):
  42. print('Verifying KEY...')
  43. status = False
  44. try:
  45. uid = data["wizard_info"]["wizard_id"]
  46. cursor = db.cursor()
  47. cursor.execute('SELECT count(uid) AS c FROM player WHERE uid = ? AND api_key = ?;', (uid, key))
  48. if cursor.fetchone()[0] == 1:
  49. status = True
  50. cursor.close()
  51. except sqlite3.IntegrityError as e:
  52. print("Error executing statement: " + str(e))
  53. raise
  54. return status
  55. """
  56. Opens the database file and deletes from the user tables
  57. :param name: The path to the sqlite database.
  58. :returns: Connection to the database.
  59. :raises IntegrityError: The queryes couldn't bre executed.
  60. :raises IOError: The sqlite file couldn't be created.
  61. """
  62. def openDatabase():
  63. kdb = os.path.dirname(os.path.realpath(sys.argv[0])) + '/../../../sw.sqlite'
  64. udb = os.path.dirname(os.path.realpath(sys.argv[0])) + '/../../../../data/sw.sqlite'
  65. print('Configuring database...')
  66. try:
  67. db = sqlite3.connect(kdb)
  68. cursor = db.cursor()
  69. cursor.execute('attach "' + udb + '" as data;')
  70. cursor.close()
  71. return db
  72. except sqlite3.IntegrityError as e:
  73. print("Error executing statement: " + str(e))
  74. raise
  75. except IOError as e:
  76. print("I/O Error opening database " + name + ": " + str(e))
  77. raise
  78. """
  79. Inserts a row into the database.
  80. :param db: Connection to the database.
  81. :param table: Name of the table to insert into.
  82. :param values: List of values to insert.
  83. :raises IntegrityError: The insert query was unsuccesfull.
  84. """
  85. def insert(db, table, values):
  86. cursor = db.cursor()
  87. placeholders = ''
  88. for x in range(0, len(values)):
  89. placeholders = placeholders + '?, '
  90. placeholders = placeholders[:len(placeholders) - 2]
  91. query = 'INSERT INTO ' + table + ' VALUES (' + placeholders + ')'
  92. try:
  93. cursor.execute(query, values)
  94. except sqlite3.IntegrityError as e:
  95. print('Error Inserting into ' + table + ' with values (' + str(values) + '): ' + str(e))
  96. raise
  97. cursor.close;
  98. """
  99. Parses run data (tables run, run_party, run_drop_rune, run_drop_runecraft,
  100. run_drop_item, run_drop_unit, run_drop_sd, run_drop_unit_pieces,
  101. run_drop_shapeshifting).
  102. :param db: Sqlite database connection.
  103. :param data_start: JSON data of the run start.
  104. :param data_result: JSON data of the run result.
  105. """
  106. def parseRun(db, data_request, data_response):
  107. print("Parsing run...")
  108. cursor = db.cursor()
  109. # Read basic data
  110. uid = data_request["wizard_id"]
  111. dtime = data_response["tvaluelocal"]
  112. # Check if run has already been inserted.
  113. cursor.execute("SELECT count(id) AS c FROM run WHERE uid = ? AND dtime = ?;", (uid, dtime))
  114. if (cursor.fetchone()[0] > 0):
  115. print(" Run already in database. Stopping....")
  116. return 409;
  117. # We are inserting, get aditional info
  118. area_type = 10 # TOA
  119. area = 10 # TOA
  120. stage = data_request["floor_id"]
  121. difficulty = data_request["difficulty"]
  122. win = data_response["win_lose"]
  123. time = data_request["clear_time"]
  124. helper = 0
  125. # Get the new ID and insert
  126. cursor.execute("SELECT max(id) + 1 AS id FROM run;")
  127. id = cursor.fetchone()[0]
  128. if id == None:
  129. id = 1
  130. # Calculate rewards
  131. mana = 0
  132. energy = 0
  133. crystal = 0
  134. if stage == 10:
  135. energy = 50
  136. elif stage == 20:
  137. # Rainbowmon 3* MAX
  138. insert(db, "run_drop_item", (id, 143140325, 1))
  139. elif stage == 30:
  140. # Mystical Scroll
  141. insert(db, "run_drop_item", (id, 3, 1))
  142. elif stage == 40:
  143. crystal = 100
  144. elif stage == 50:
  145. # Mystical Scroll
  146. insert(db, "run_drop_item", (id, 3, 2))
  147. elif stage == 60:
  148. # Rainbowmon 4* MAX
  149. insert(db, "run_drop_item", (id, 143140430, 1))
  150. elif stage == 70:
  151. # Devilmon
  152. insert(db, "run_drop_item", (id, 151050101, 1))
  153. elif stage == 80:
  154. crystal = 300
  155. elif stage == 90:
  156. # Light and Dark Scroll
  157. insert(db, "run_drop_item", (id, 11, 1))
  158. elif stage == 100:
  159. # Legendary Scroll
  160. insert(db, "run_drop_item", (id, 10, 1))
  161. elif stage / 5 == 0:
  162. crystal = 10 * int(math.ceil((stage / 2) / 10) + 1)
  163. else:
  164. # Summon stone
  165. insert(db, "run_drop_item", (id, 8, 1))
  166. # Insert
  167. score = None
  168. rank = None
  169. insert(db, "run", (uid, id, dtime, area_type, area, stage, difficulty, win, time, mana, energy, crystal, helper, score, rank))
  170. # Parse units
  171. i = 0
  172. for unit in data_request["unit_id_list"]:
  173. unit_id = unit["unit_id"]
  174. cursor.execute("SELECT unit FROM unit WHERE uid = ? AND id = ?;", (uid, unit_id))
  175. unit_master_id = cursor.fetchone()[0]
  176. for k_unit in data_response["unit_list"]:
  177. if k_unit["unit_id"] == unit["unit_id"]:
  178. unit_master_id = k_unit["unit_master_id"];
  179. break;
  180. if i == 0:
  181. leader = 1 # TODO UNKNOWABLE? Check event start
  182. else:
  183. leader = 0
  184. front = 0
  185. insert(db, "run_party", (id, unit_master_id, unit_id, leader, front))
  186. i += 1
  187. db.commit()
  188. """
  189. Begin script
  190. """
  191. data_request = readData(2)
  192. data_response = readData(3)
  193. key = readKey()
  194. db = openDatabase()
  195. if verifyKey(db, data_response, key) == False:
  196. print("Invalid API KEY...")
  197. sys.exit(401)
  198. else:
  199. try:
  200. parseRun(db, data_request, data_response)
  201. except Exception as e:
  202. print("Error parsing TOA run: " + str(e))
  203. sys.exit(400)
  204. sys.exit(201)