api_routes.py 8.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367
  1. from aiohttp import web
  2. from aiohttp_session import get_session
  3. from user import UserError
  4. from user import LoginError, log_in, log_out
  5. from user import SignupError, sign_up
  6. from user import find_user_by_id
  7. from user import get_user_videos, get_user_videos_count
  8. from user import is_video_liked
  9. from user import like_video, unlike_video
  10. from user import upload_avatar, upload_video
  11. from user import serialize_user
  12. from user import get_authorized_user
  13. from video import VideoError
  14. from video import serialize_video
  15. from video import find_video_by_id
  16. from video import get_random_video
  17. from video import get_likes, get_tags
  18. from comment import get_comments, get_comments_count, post_comment
  19. from common import search_videos, suggest_tag
  20. from tools import verify_captcha
  21. from config import config
  22. routes = web.RouteTableDef()
  23. def report_error(error):
  24. return web.json_response({
  25. 'error': str(error)
  26. })
  27. @routes.post('/api/random')
  28. async def api_random(request):
  29. video = await get_random_video()
  30. return web.json_response({
  31. 'video_id': video.id
  32. })
  33. @routes.post('/api/exists')
  34. async def api_exists(request):
  35. data = await request.post()
  36. video_id = data.get('video_id')
  37. is_exists = True
  38. try:
  39. video = await find_video_by_id(video_id)
  40. except VideoError:
  41. is_exists = False
  42. return web.json_response({
  43. 'video_id': video.id if is_exists else -1,
  44. 'is_exists': is_exists
  45. })
  46. @routes.post('/api/login')
  47. async def api_login(request):
  48. session = await get_session(request)
  49. data = await request.post()
  50. username = data.get('username')
  51. password = data.get('password')
  52. hcaptcha_token = data.get('h-captcha-response')
  53. if not await verify_captcha(hcaptcha_token):
  54. return report_error('captcha check failed')
  55. try:
  56. user = await log_in(session, username, password)
  57. except (UserError, LoginError) as error:
  58. return report_error(error)
  59. return web.json_response({
  60. 'user_id': user.id
  61. })
  62. @routes.post('/api/signup')
  63. async def api_signup(request):
  64. session = await get_session(request)
  65. data = await request.post()
  66. username = data.get('username')
  67. password = data.get('password')
  68. hcaptcha_token = data.get('h-captcha-response')
  69. if not await verify_captcha(hcaptcha_token):
  70. return report_error('captcha check failed')
  71. try:
  72. user = await sign_up(session, username, password, ip_address=request.remote)
  73. except (UserError, SignupError) as error:
  74. return report_error(error)
  75. return web.json_response({
  76. 'user_id': user.id
  77. })
  78. @routes.post('/api/logout')
  79. async def api_logout(request):
  80. session = await get_session(request)
  81. try:
  82. await log_out(session)
  83. except UserError as error:
  84. return report_error(error)
  85. return web.json_response({
  86. 'status': 'success'
  87. })
  88. @routes.post('/api/user')
  89. async def api_user(request):
  90. data = await request.post()
  91. user_id = data.get('user_id')
  92. try:
  93. user = await find_user_by_id(user_id)
  94. except UserError as error:
  95. return report_error(error)
  96. return web.json_response(await serialize_user(user))
  97. @routes.post('/api/videos')
  98. async def api_videos(request):
  99. data = await request.post()
  100. user_id = data.get('user_id')
  101. offset = data.get('offset')
  102. try:
  103. videos = await get_user_videos(user_id, offset=offset)
  104. videos_count = await get_user_videos_count(user_id)
  105. except (UserError, VideoError) as error:
  106. return report_error(error)
  107. return web.json_response({
  108. 'videos': videos,
  109. 'videos_count': videos_count
  110. })
  111. @routes.post('/api/comments')
  112. async def api_comments(request):
  113. data = await request.post()
  114. video_id = data.get('video_id')
  115. offset = data.get('offset')
  116. try:
  117. comments = await get_comments(video_id, offset=offset)
  118. comments_count = await get_comments_count(video_id)
  119. except VideoError as error:
  120. return report_error(error)
  121. return web.json_response({
  122. 'comments': comments,
  123. 'comments_count': comments_count
  124. })
  125. @routes.post('/api/search')
  126. async def api_search(request):
  127. data = await request.post()
  128. tags = data.get('tags')
  129. offset = data.get('offset')
  130. try:
  131. videos = await search_videos(tags, offset=offset)
  132. except SyntaxError as error: # SyntaxError is thrown by parse_tags.
  133. return report_error(error)
  134. return web.json_response({
  135. 'videos': videos
  136. })
  137. @routes.post('/api/suggest')
  138. async def api_tags(request):
  139. data = await request.post()
  140. tag = data.get('tag')
  141. try:
  142. tags_list = await suggest_tag(tag)
  143. except SyntaxError as error:
  144. return report_error(error)
  145. return web.json_response({
  146. 'tags_list': tags_list
  147. })
  148. @routes.post('/api/tags')
  149. async def api_tags(request):
  150. data = await request.post()
  151. video_id = data.get('video_id')
  152. try:
  153. tags_list = await get_tags(video_id)
  154. except VideoError as error:
  155. return report_error(error)
  156. return web.json_response({
  157. 'tags_list': tags_list
  158. })
  159. @routes.post('/api/liked')
  160. async def api_liked(request):
  161. session = await get_session(request)
  162. data = await request.post()
  163. video_id = data.get('video_id')
  164. try:
  165. is_liked = await is_video_liked(session, video_id)
  166. except (UserError, VideoError) as error:
  167. return report_error(error)
  168. return web.json_response({
  169. 'is_liked': is_liked
  170. })
  171. @routes.post('/api/likes')
  172. async def api_likes(request):
  173. data = await request.post()
  174. video_id = data.get('video_id')
  175. try:
  176. likes_count = await get_likes(video_id)
  177. except VideoError as error:
  178. return report_error(error)
  179. return web.json_response({
  180. 'likes_count': likes_count
  181. })
  182. @routes.post('/api/like')
  183. async def api_like(request):
  184. session = await get_session(request)
  185. data = await request.post()
  186. video_id = data.get('video_id')
  187. try:
  188. await like_video(session, video_id)
  189. likes_count = await get_likes(video_id)
  190. except (UserError, VideoError) as error:
  191. return report_error(error)
  192. return web.json_response({
  193. 'likes_count': likes_count
  194. })
  195. @routes.post('/api/unlike')
  196. async def api_unlike(request):
  197. session = await get_session(request)
  198. data = await request.post()
  199. video_id = data.get('video_id')
  200. try:
  201. await unlike_video(session, video_id)
  202. likes_count = await get_likes(video_id)
  203. except (UserError, VideoError) as error:
  204. return report_error(error)
  205. return web.json_response({
  206. 'likes_count': likes_count
  207. })
  208. @routes.post('/api/comment')
  209. async def api_comment(request):
  210. session = await get_session(request)
  211. data = await request.post()
  212. video_id = data.get('video_id')
  213. text = data.get('text')
  214. try:
  215. comment = await post_comment(session, video_id, text)
  216. except (UserError, VideoError, ValueError) as error:
  217. return report_error(error)
  218. return web.json_response({
  219. 'comment_id': comment.id
  220. })
  221. @routes.post('/api/upload/avatar')
  222. async def api_upload_avatar(request):
  223. session = await get_session(request)
  224. reader = await request.multipart()
  225. image = await reader.next()
  226. try:
  227. await upload_avatar(session, image)
  228. user = await get_authorized_user(session)
  229. except UserError as error:
  230. return report_error(error)
  231. return web.json_response(await serialize_user(user))
  232. @routes.post('/api/upload/video')
  233. async def api_upload_video(request):
  234. session = await get_session(request)
  235. if 'authorized' not in session:
  236. return web.json_response({
  237. 'error': 'not authorized.'
  238. })
  239. video = None
  240. tags = None
  241. hcaptcha_token = None
  242. reader = await request.multipart()
  243. while True:
  244. part = await reader.next()
  245. if not part:
  246. break
  247. if part.name == 'video':
  248. video = bytearray()
  249. size = 0
  250. while True:
  251. chunk = await part.read_chunk()
  252. if not chunk:
  253. break
  254. size += len(chunk)
  255. if size >= config.MAX_VIDEO_SIZE * 1024 * 1024:
  256. return report_error('illegal video')
  257. video += chunk
  258. elif part.name == 'tags':
  259. tags = await part.read_chunk()
  260. tags = tags.decode('ASCII')
  261. elif part.name == 'h-captcha-response':
  262. hcaptcha_token = await part.read_chunk()
  263. hcaptcha_token = hcaptcha_token.decode('ASCII')
  264. if not hcaptcha_token:
  265. return report_error('captcha check failed')
  266. if not await verify_captcha(hcaptcha_token):
  267. return report_error('captcha check failed')
  268. if not video:
  269. return report_error('illegal video')
  270. if not tags:
  271. return report_error('illegal tags')
  272. try:
  273. video = await upload_video(session, video, tags)
  274. except (UserError, VideoError, SyntaxError) as error:
  275. return report_error(error)
  276. return web.json_response({
  277. 'video_id': video.id
  278. })