__init__.py 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257
  1. import json
  2. import random
  3. import re
  4. import sys
  5. from datetime import datetime
  6. from time import perf_counter
  7. from typing import Dict, Callable
  8. from uuid import uuid4
  9. import requests
  10. import connection
  11. import test.do_some_requests.current_websocket
  12. from game import random_ownable_name
  13. from test import failed_requests
  14. from util import round_to_n
  15. DEFAULT_PW = 'pw'
  16. PORT = connection.PORT
  17. HOST = 'http://127.0.0.1' + ':' + str(PORT)
  18. # HOST = 'http://koljastrohm-games.com' + ':' + str(PORT)
  19. JSON_HEADERS = {'Content-type': 'application/json'}
  20. EXIT_ON_FAILED_REQUEST = True
  21. response_collection: Dict[str, Dict] = {}
  22. default_request_method: Callable[[str, Dict], Dict]
  23. def receive_answer(token):
  24. """Waits until the server sends an answer that contains the desired request_token.
  25. All intermediate requests are also collected for later use, or, if they contain no token, they are just printed out.
  26. """
  27. if token in response_collection:
  28. json_content = response_collection[token]
  29. del response_collection[token]
  30. return json_content
  31. json_content = {}
  32. while 'request_token' not in json_content or json_content['request_token'] != token:
  33. if 'request_token' in json_content:
  34. response_collection[json_content['request_token']] = json_content
  35. received = test.do_some_requests.current_websocket.current_websocket.recv_data_frame()[1].data
  36. content = received.decode('utf-8')
  37. formatted_content = re.sub(r'{([^}]*?):(.*?)}', r'\n{\g<1>:\g<2>}', content)
  38. print('Received through websocket: ' + formatted_content)
  39. json_content = json.loads(content)
  40. return json_content
  41. def websocket_request(route: str, data: Dict) -> Dict:
  42. original_data = data
  43. if not test.do_some_requests.current_websocket.current_websocket.connected:
  44. ws_host = HOST.replace('http://', 'ws://')
  45. test.do_some_requests.current_websocket.current_websocket.connect(ws_host + '/websocket')
  46. token = str(uuid4())
  47. data = json.dumps({'route': route, 'body': data, 'request_token': token})
  48. print('Sending to websocket:', str(data).replace('{', '\n{')[1:])
  49. test.do_some_requests.current_websocket.current_websocket.send(data, opcode=2)
  50. json_content = receive_answer(token)
  51. print()
  52. status_code = json_content['http_status_code']
  53. if status_code == 200:
  54. pass
  55. elif status_code == 451: # Copyright problems, likely a bug in the upload filter
  56. # Try again
  57. return websocket_request(route, original_data)
  58. else:
  59. if EXIT_ON_FAILED_REQUEST:
  60. if not test.do_some_requests.current_websocket.current_websocket.connected:
  61. test.do_some_requests.current_websocket.current_websocket.close()
  62. sys.exit(status_code)
  63. failed_requests.append((route, status_code))
  64. return json_content['body']
  65. def http_request(route: str, data: Dict) -> Dict:
  66. original_data = data
  67. data = json.dumps(data)
  68. print('Sending to /' + route + ':', str(data).replace('{', '\n{')[1:])
  69. r = requests.post(HOST + '/json/' + route, data=data,
  70. headers=JSON_HEADERS)
  71. content = r.content.decode()
  72. print('Request returned: ' + content.replace('{', '\n{'))
  73. print()
  74. if r.status_code == 200:
  75. pass
  76. elif r.status_code == 451:
  77. return http_request(route, original_data)
  78. else:
  79. if EXIT_ON_FAILED_REQUEST:
  80. sys.exit(r.status_code)
  81. failed_requests.append((route, r.status_code))
  82. return json.loads(content)
  83. default_request_method: Callable[[str, Dict], Dict] = http_request
  84. # default_request_method = websocket_request
  85. def random_time():
  86. start = random.randrange(140)
  87. start = 1561960800 + start * 21600 # somewhere in july or at the beginning of august 2019
  88. return {
  89. 'dt_start': start,
  90. 'dt_end': start + random.choice([1800, 3600, 7200, 86400]),
  91. }
  92. def run_tests():
  93. print('You are currently in debug mode.')
  94. print('Host:', str(HOST))
  95. usernames = [f'user{datetime.now().timestamp()}',
  96. f'user{datetime.now().timestamp()}+1']
  97. banks = usernames[:1]
  98. session_ids = {}
  99. message = {}
  100. route = 'news'
  101. default_request_method(route, message)
  102. message = {}
  103. route = 'leaderboard'
  104. default_request_method(route, message)
  105. message = {}
  106. route = 'tradables'
  107. default_request_method(route, message)
  108. for username in usernames:
  109. message = {'username': username, 'password': DEFAULT_PW}
  110. route = 'register'
  111. default_request_method(route, message)
  112. message = {'username': username, 'password': DEFAULT_PW}
  113. route = 'login'
  114. session_ids[username] = default_request_method(route, message)['session_id']
  115. message = {'session_id': session_ids[username]}
  116. route = 'logout'
  117. default_request_method(route, message)
  118. message = {'username': username, 'password': DEFAULT_PW}
  119. route = 'login'
  120. session_ids[username] = default_request_method(route, message)['session_id']
  121. message = {'session_id': session_ids[username]}
  122. route = 'depot'
  123. default_request_method(route, message)
  124. message = {'session_id': session_ids[username]}
  125. route = 'orders'
  126. default_request_method(route, message)
  127. message = {'session_id': session_ids[username], "ownable": "\u20adollar"}
  128. route = 'orders_on'
  129. default_request_method(route, message)
  130. for password in ['pw2', DEFAULT_PW]:
  131. message = {'session_id': session_ids[username], 'password': password}
  132. route = 'change_password'
  133. default_request_method(route, message)
  134. message = {'username': username, 'password': password}
  135. route = 'login'
  136. session_ids[username] = default_request_method(route, message)['session_id']
  137. for limit in [0, 5, 10, 20, 50]:
  138. message = {'session_id': session_ids[username], 'limit': limit}
  139. route = 'trades'
  140. data = default_request_method(route, message)['data']
  141. assert len(data) <= limit
  142. for username in banks:
  143. message = {'session_id': session_ids[username], 'amount': 5.5e6}
  144. route = 'take_out_personal_loan'
  145. default_request_method(route, message)
  146. message = {'session_id': session_ids[username]}
  147. route = 'buy_banking_license'
  148. default_request_method(route, message)
  149. message = {'session_id': session_ids[username],
  150. 'coupon': 1.05,
  151. 'name': random_ownable_name(),
  152. 'run_time': 43200}
  153. route = 'issue_bond'
  154. default_request_method(route, message)
  155. message = {'issuer': username}
  156. route = 'bonds'
  157. default_request_method(route, message)
  158. message = {'issuer': username, 'only_next_mro_qualified': True}
  159. route = 'bonds'
  160. default_request_method(route, message)
  161. message = {'issuer': username, 'only_next_mro_qualified': False}
  162. route = 'bonds'
  163. default_request_method(route, message)
  164. message = {}
  165. route = 'bonds'
  166. default_request_method(route, message)
  167. message = {'only_next_mro_qualified': True}
  168. route = 'bonds'
  169. default_request_method(route, message)
  170. message = {'only_next_mro_qualified': False}
  171. route = 'bonds'
  172. default_request_method(route, message)
  173. for session_id in session_ids.values():
  174. message = {'session_id': session_id}
  175. route = 'logout'
  176. default_request_method(route, message)
  177. def main():
  178. global default_request_method
  179. for m in [
  180. test.do_some_requests.websocket_request,
  181. # test.do_some_requests.http_request
  182. ]:
  183. # print('Removing existing database (if exists)...', end='')
  184. # try:
  185. # os.remove(DB_NAME + '.db')
  186. # except PermissionError:
  187. # print('Could not recreate database')
  188. # sys.exit(-1)
  189. # except FileNotFoundError:
  190. # pass
  191. # print('done')
  192. default_request_method = m
  193. start = perf_counter()
  194. run_tests()
  195. print()
  196. print('Failed requests:', failed_requests)
  197. print('Total time:' + str(round_to_n(perf_counter() - start, 4)) + 's,')
  198. if test.do_some_requests.current_websocket.current_websocket.connected:
  199. test.do_some_requests.current_websocket.current_websocket.close()
  200. sys.exit(len(failed_requests))
  201. if __name__ == '__main__':
  202. main()