def post(self, request, *args, **kwargs): doc = request.data.xpath('/routesRequest') if len(doc) < 1: return error_response('Не найден объект routesRequest', code='routesRequest_not_found') doc = doc[0] doc_id = doc.get('idDoc', '') if not doc_id: return error_response('Не указан параметр idDoc', code='idDoc_not_found') try: org_id = int(doc.get('idOrg', '')) except ValueError: org_id = 0 sess_id = get_wialon_session_key(request.user) try: routes = get_routes(sess_id) except APIProcessError as e: return error_response(str(e), code=e.code) finally: logout_session(request.user, sess_id) context = self.get_context_data(**kwargs) context.update({ 'doc_id': doc_id, 'create_date': utcnow(), 'routes': routes, 'org_id': org_id }) return XMLResponse('ura/routes.xml', context)
def post(self, request, *args, **kwargs): doc = request.data.xpath('/echoRequest') if len(doc) < 1: return error_response('Не найден объект echoRequest', code='echoRequest_not_found') doc = doc[0] doc_id = doc.get('idDoc', '') if not doc_id: return error_response('Не указан параметр idDoc', code='idDoc_not_found') context = self.get_context_data(**kwargs) context.update({ 'doc_id': doc_id, 'create_date': utcnow() }) return XMLResponse('ura/echo.xml', context)
def post(self, request, *args, **kwargs): jobs = [] jobs_els = request.data.xpath('/breakJobs/job') if jobs_els: for j in jobs_els: data = parse_xml_input_data(request, self.model_mapping, j) job_id = data.pop('job_id') if not job_id: return error_response('Не указан параметр idJob', code='idJob_not_found') if data.get('new_date_end' ) and data['new_date_end'] <= data['date_begin']: self.model.objects.filter(pk=job_id).delete() else: try: self.job = self.model.objects.get(pk=job_id) except self.model.DoesNotExist: return error_response('Задание с ID=%s не найдено' % job_id, code='job_not_found') for k, v in data.iems(): if k == 'new_date_end': k = 'date_end' elif k == 'date_end' and 'new_date_end' in data and data[ 'new_date_end']: continue setattr(self.job, k, v) self.job.save() jobs.append(self.job) context = self.get_context_data(**kwargs) context.update({'now': utcnow(), 'breakJobs': jobs}) return XMLResponse('ura/ackBreakJobs.xml', context)
def post(self, request, *args, **kwargs): doc = request.data.xpath('/orgRequest') if len(doc) < 1: return error_response('Не найден объект orgRequest', code='orgRequest_not_found') doc = doc[0] doc_id = doc.get('idDoc', '') if not doc_id: return error_response('Не указан параметр idDoc', code='idDoc_not_found') orgs = User.objects.filter(supervisor=request.user, is_active=True) context = self.get_context_data(**kwargs) context.update({ 'doc_id': doc_id, 'orgs': orgs, 'create_date': utcnow() }) return XMLResponse('ura/orgs.xml', context)
def post(self, request, **kwargs): units = [] context = self.get_context_data(**kwargs) context.update({'now': utcnow(), 'units': units}) units_els = request.data.xpath('/getMoving/unit') if not units_els: logout_session(request.user, self.sess_id) return error_response('Не указаны объекты типа unit', code='units_not_found') self.get_geozones_report_template_id() for unit_el in units_els: self.get_input_data(unit_el) self.unit_id = int(self.input_data.get('unit_id')) self.get_job() self.get_route() self.get_report_data() self.get_object_messages() self.ride_points = [] unit_info = { 'id': self.unit_id, 'date_begin': utc_to_local_time(self.input_data['date_begin'], request.user.timezone), 'date_end': utc_to_local_time(self.input_data['date_end'], request.user.timezone), 'points': self.ride_points } self.prepare_geozones_visits() self.process_messages() self.report_post_processing(unit_info) self.update_job_points_cache() self.prepare_output_data() units.append(unit_info) logout_session(request.user, self.sess_id) return XMLResponse('ura/moving.xml', context)
def post(self, request, **kwargs): jobs = [] print('Start getRaces:\n' + str(request.body)) context = self.get_context_data(**kwargs) context.update({ 'now': utcnow(), 'jobs': jobs }) jobs_els = request.data.xpath('/getRaces/job') if not jobs_els: logout_session(request.user, self.sess_id) return error_response('Не указаны объекты типа job', code='jobs_not_found') self.get_geozones_report_template_id() for job_el in jobs_els: self.get_input_data(job_el) self.unit_id = int(self.input_data.get('unit_id')) self.get_job() self.get_route() self.points_dict_by_name = {x['name']: x['id'] for x in self.route['points']} self.get_report_data() self.get_object_messages() self.prepare_geozones_visits() self.ride_points = [] self.process_messages() races = [] job_info = { 'obj': self.job, 'races': races } self.make_races(races) self.report_post_processing(job_info) self.prepare_output_data(job_info) jobs.append(job_info) logout_session(request.user, self.sess_id) return XMLResponse('ura/races.xml', context)
def dispatch_method(self, request, *args, **kwargs): method = request.method.lower() if method in self.http_method_names: handler = getattr(self, method, self.http_method_not_allowed) else: handler = self.http_method_not_allowed # для изменяющих методов подставим json данные в request.data if method in ('post', 'put', 'patch', 'delete'): if request.body: try: request.data = self.parse_raw_data(request) except APIParseError as e: return error_response(str(e), code=getattr(e, 'code', None)) else: request.data = None request.user = AnonymousUser() # если метод не 405 и не публичный, проверяем авторизацию # публичные эндпоинты вообще не проверяем, это может пойти им во вред if handler != self.http_method_not_allowed \ and not getattr(handler, 'is_public_http_method', False): try: request.user = self.authenticate(request) except AuthenticationFailed as e: # обновлять токен не имеет смысла, он неправильный. Просим войти заново. return error_response(str(e), status=403, code=getattr(e, 'code', None)) try: self.pre_view_trigger(request, **kwargs) except APIProcessError as e: return error_response( str(e), status=e.http_status if e.http_status else None, code=e.code) except (ValueError, IndexError, KeyError, AttributeError, TypeError) as e: send_trigger_email('Ошибка в работе интеграции Wialon', extra_data={ 'POST': request.body, 'Exception': str(e), 'Traceback': traceback.format_exc(), 'user': request.user }) return error_response( 'Ошибка входящих данных из источника данных. ' 'Попробуйте повторить запрос позже.', status=400, code='source_data_invalid') except Exception as e: send_trigger_email('Ошибка в работе интеграции Wialon', extra_data={ 'POST': request.body, 'Exception': str(e), 'Traceback': traceback.format_exc(), 'user': request.user }) return error_response('Внутренняя ошибка сервера', status=500, code='internal_server_error') attempts = 0 attempts_limit = 20 last_error = '' while attempts < attempts_limit: try: return handler(request, *args, **kwargs) except APIValidationError as e: return validation_error_response(e.messages) except APIProcessError as e: return error_response( str(e), status=e.http_status if e.http_status else None, code=e.code) except WialonException as e: last_error = str(e) attempts += 1 print( 'Инициирую новую попытку доступа к Wialon. Последняя ошибка: %s' % last_error) # после каждого падения Виалона ждет 5 секунд и повторяем попытку sleep(5) except (ValueError, IndexError, KeyError, AttributeError, TypeError) as e: send_trigger_email('Ошибка в работе интеграции Wialon', extra_data={ 'POST': request.body, 'Exception': str(e), 'Traceback': traceback.format_exc(), 'user': request.user }) return error_response( 'Ошибка входящих данных из источника данных. ' 'Попробуйте повторить запрос позже', status=400, code='source_data_invalid') except Exception as e: send_trigger_email('Ошибка в работе интеграции Wialon', extra_data={ 'POST': request.body, 'Exception': str(e), 'Traceback': traceback.format_exc(), 'user': request.user }) return error_response('Внутренняя ошибка сервера', status=500, code='internal_server_error') send_trigger_email('Лимит попыток обращения в Wialon (%s) закончился' % attempts_limit, extra_data={ 'Последняя ошибка': last_error, 'user': request.user }) return error_response( 'Лимит попыток обращения в Wialon (%s) закончился. %s' % (attempts_limit, last_error), status=400, code='attempts_limit')
def http_method_not_allowed(self, request, *args, **kwargs): return error_response(_('Метод не разрешен (%s): %s') % (request.method, request.path), status=405, code='method_not_allowed')
def post(self, request, *args, **kwargs): jobs = [] jobs_els = request.data.xpath('/setJobs/job') sess_id = get_wialon_session_key(request.user) if jobs_els: for j in jobs_els: data = parse_xml_input_data(request, self.model_mapping, j) name = data.get('name') if not name: logout_session(request.user, sess_id) return error_response('Не указан параметр jobName', code='jobName_not_found') routes = get_routes(sess_id, with_points=True) units = get_units(sess_id) routes_ids = [x['id'] for x in routes] if data['route_id'] not in routes_ids: return error_response( 'Шаблон задания idRoute неверный или не принадлежит текущей организации', code='route_permission') units_cache = { u['id']: '%s (%s) [%s]' % (u['name'], u['number'], u['vin']) for u in units } try: data['unit_title'] = units_cache.get(int(data['unit_id'])) except (ValueError, TypeError, AttributeError): pass if not data['unit_title']: return error_response( 'Объект ID=%s не найден в текущем ресурсе организации' % data['unit_id'], code='unit_not_found_permission') routes_cache = {r['id']: r for r in routes} try: data['route_title'] = routes_cache.get( int(data['route_id']), {}).get('name') except (ValueError, TypeError, AttributeError): pass data['user'] = request.user self.job = self.model.objects.create(**data) register_job_notifications(self.job, sess_id, routes_cache=routes_cache) logout_session(request.user, sess_id) jobs.append(self.job) context = self.get_context_data(**kwargs) context.update({'now': utcnow(), 'acceptedJobs': jobs}) return XMLResponse('ura/ackjobs.xml', context)