async def _booking(request): valid = await validate_request(request) if valid["errmsg"]: return rest_result(request, {"status": 400, "errmsg": valid["errmsg"]}) cms_ids = valid["hotels"] db = databases("hub") start_time = valid["start_time"] end_time = valid["end_time"] days = valid["days"] # 避免传入的开始时间早于当前日期导致无效查询 # TODO: 抽象成单独校验日期的方法 for index, hid in enumerate(cms_ids): booking_url = await db["poi_items"].find_one( { "_id": ObjectId(hid), "crawl_info.crawl_website": "bk_url" }, {"crawl_info.$": "1"}, ) if not booking_url: continue await get_booking_prices(booking_url["crawl_info"][0]["crawl_url"], hid, start_time, days) calendar_one.delay(hid, start_time, end_time) if index % 10 == 0: _check_prices.apply_async( kwargs={ "base_url": booking_url["crawl_info"][0]["crawl_url"], "cms_id": hid, "start_time": start_time, "days": days, }, countdown=settings.CHECK_PRICE_DELAY_TIME, ) return rest_result(request, {"status": 200, "data": "ok"})
async def availability(request): """ 查价任务统一发布接口\n compare中为需要比价的第三方网站\n 目前支持ctrip 和 booking """ request.headers["Accept"] = "application/json" valid = await validate_request(request) logger.info(f"valid: {valid}") if valid["errmsg"]: return rest_result(request, {"status": 400, "errmsg": valid["errmsg"]}) compare = valid["compare"] hotels = valid["hotels"] start_time = valid["start_time"] days = valid["days"] only_compare = valid["only_compare"] """ 获取第三方价格放在scrapy中执行,celery仅发布任务 优先放入celery中执行 """ if "ctrip" in compare: await ctrip(hotels, start_time, days) if "booking" in compare: await booking(hotels, start_time, days) if not only_compare: for uid, _hotels in hotels.items(): for hotel in uid.split(";"): quoter_id, hotel_id = hotel.split("::") if quoter_id == "cms": calendar_one.delay(hotel_id, start_time=start_time, end_time=None, days=days) else: get_provider_prices.delay( hotel_id=hotel_id, quoter_id=quoter_id, start_time=start_time, hotels=None, days=days, ) return rest_result(request, {"status": 200, "data": list(hotels.keys())})
async def booking_provider(request): valid = await validate_request(request) provider_compair_booking.delay(valid["start_time"], valid["days"], valid["hotels"]) return rest_result( request, { "status": 200, "data": valid.get("errmsg") or valid["hotels"] }, )
async def _weego(request): valid = await validate_request(request) logger.info(f"weego params : {valid}") for hotel_id in valid.get("hotels", []): calendar_one.delay(hotel_id, valid["start_time"], valid["end_time"]) return rest_result( request, { "status": 200, "data": valid.get("errmsg") or valid["hotels"] }, )
async def _provider(request): """ hotel from statics providers data """ body = request.json if not body: return rest_result(request, { "status": 400, "errmsg": "request without params!" }) start_time = body.get("start_time") end_time = body.get("end_time") days = body.get("days") hotel_ids = body.get("hotel_ids", []) quoter = body.get("quoter") quoters = body.get("quoters", []) or body.get("hotels", []) if quoter in settings.SUPPLIER_NAME_2_ID: quoter = settings.SUPPLIER_NAME_2_ID[quoter] if days and not end_time: end_time = (datetime.strptime(start_time, "%Y-%m-%d") + timedelta(days=days)).strftime("%Y-%m-%d") for hotel_id in hotel_ids: get_provider_prices.delay( hotel_id=hotel_id, quoter_id=quoter, start_time=start_time, end_time=end_time, ) for hotel in quoters: hotel_id = hotel["hotel_id"] quoter_id = (hotel.get("quoter") or settings.SUPPLIER_NAME_2_ID[hotel.get("provider")]) get_provider_prices.delay( hotel_id=hotel_id, quoter_id=quoter_id, start_time=start_time, end_time=end_time, ) return rest_result(request, {"status": 200, "data": "ok"})
async def skyscanner(request): valid = await validate_request(request) if valid["errmsg"] and not request.json.get("provider"): return rest_result(request, {"status": 400, "errmsg": valid["errmsg"]}) start_time = valid["start_time"] days = valid["days"] for hotel in valid["hotels"]: get_skyscanner.delay(start_time, days, hotel_id=hotel) db = databases("scripture") for hotel_id, hotel_name in request.json.get("provider", {}).items(): sid = await db["statics.hotels.skyscanner"].find_one( {"name": { "$regex": hotel_name.lower(), "$options": "i" }}, {"sid": "1"}, ) if sid: get_skyscanner.delay(start_time, days, sid=sid["sid"], hotel_id=hotel_id) return rest_result(request, {"status": 200, "data": "ok"})
async def ctrip_provider(request): valid = await validate_request(request) if valid["provider"]: hotels = [] for _hotel in valid["hotels"]: if isinstance(_hotel, str): _hotel = {"hotel_id": _hotel, "provider": valid["provider"]} elif isinstance(_hotel, dict): _hotel["provider"] = valid["provider"] hotels.append(_hotel) valid["hotels"] = hotels provider_compair_ctrip.delay(valid["start_time"], valid["days"], valid["hotels"]) return rest_result( request, { "status": 200, "data": valid.get("errmsg") or list(valid["hotels"]) }, )
async def _crawl_upload(request): ori_hotel_info = {} opt = request.form.get('opt') if not opt: logger.warning(f'{request}无opt,非法请求') return rest_result(request, {"status": 400, "errmsg": "非法请求"}) match_prob = request.form.get('prob') if opt == 'form': ori_hotel_name = request.form.get('name') if not ori_hotel_name: return rest_result(request, {"status": 400, "errmsg": "酒店名为必填项"}) ori_hotel_provider = request.form.get('provider') if ori_hotel_provider and ori_hotel_provider not in settings.SUPPLIER_NAME_2_ID: return rest_result(request, {"status": 400, "errmsg": "供应商有误"}) ori_hotel_code = request.form.get('code') ori_hotel_address = request.form.get('address') ori_hotel_country = request.form.get('country') ori_hotel_info = { "ori_hotel": [{ "ori_hotel_name": ori_hotel_name, "ori_hotel_provider": ori_hotel_provider, "ori_hotel_code": ori_hotel_code, "ori_hotel_address": ori_hotel_address, "ori_hotel_country": ori_hotel_country, }] } logger.debug(f'ori_hotel_info:{ori_hotel_info}') elif opt == 'excel': excel = request.files.get('excel') if not excel: logger.info(f'{request}包含文件为空') return rest_result(request, {"status": 400, "errmsg": "文件为空"}) excel_info = f'文件名: {excel.name},mime: {excel.type}' logger.info(f'上传了一份文件:文件信息:{excel_info}') if XLSXMIME != excel.type: logger.info(f'{request}{excel_info} 上传了错误的文件类型') return rest_result(request, {"status": 400, "errmsg": "错误的文件类型"}) book = xlrd.open_workbook(file_contents=excel.body) _page = book.sheet_by_index(0) ori_hotel_info["ori_hotel"] = [] for row_index in range(_page.nrows): one_hotel_info = {} for col_index, cel_value in enumerate(_page.row_values(row_index)): if col_index == 0 and not cel_value: break if col_index == 1 and cel_value and cel_value not in settings.SUPPLIER_NAME_2_ID: one_hotel_info = {} break if cel_value and col_index < 5: one_hotel_info[hotel_info_key[col_index]] = cel_value if one_hotel_info: ori_hotel_info["ori_hotel"].append(one_hotel_info) logger.debug(f'{request}上传了一份excel文件,response_dict:{ori_hotel_info}') ori_hotel_info['match_prob'] = match_prob logger.info(f'{request}开始了一次酒店匹配,原始酒店信息为:{ori_hotel_info}') try: result = requests.post(f'{settings.EXAMINER_API}/api/v1/match/', json=ori_hotel_info) if result.status_code == 200: logger.debug(f'result.json(){result.json()}') tr = '' if not result.json(): return rest_result(request, {"status": 200, "结果": "匹配结束无相似酒店"}) for hotel in result.json(): _similar_hotel = hotel["similar_hotel"] tr += f'<tr>' \ f'<td>原酒店名称:{hotel["ori_hotel_name"]}</td>' \ f'<td>' \ f'相似酒店名称:{_similar_hotel["hotel_name"]},' \ f'供应商:{_similar_hotel["hotel_provider"]},' \ f'酒店ID:{_similar_hotel["hotel_code"]},' \ f'地址:{_similar_hotel["hotel_addr"]},' \ f'国家:{_similar_hotel["hotel_country"]},' \ f'相似率:{_similar_hotel["hotel_prob"]}' \ f'</td>' \ f'</tr>' table = f'<table border="1">{tr}</table>' return html(table) else: logger.warning(f'酒店信息:{ori_hotel_info}对应查询异常') return rest_result(request, {"status": 500, "errmsg": "查询异常"}) except Exception as exc: logger.warning(f"examiner api 异常", exc_info=exc) return rest_result(request, { "status": 500, "errmsg": "examiner lose effectiveness" })
async def preparation_check(request): body = request.json check_preparation.delay(body["hotels"]) return rest_result(request, {"status": 200, "data": "ok"})
async def availability(request): """ 查价任务统一查询数据接口\n compare中为需要比价的第三方网站\n 目前支持ctrip 和 booking return { 'status': 200, 'data': { quoter_id1::hotel_id1;quoter_id2::hotel_id2: [ {'checkin': { 'price': '', 'booking': '', 'ctrip', '', 'msg': '', 'type': -1/0/1 } } ], cms::cms_id [ {'checkin': { 'price': '', 'booking': '', 'ctrip', '', 'msg': '', 'type': -1/0/1 } } ], } } """ request.headers["Accept"] = "application/json" valid = await validate_request(request) if valid["errmsg"]: return rest_result(request, {"status": 400, "errmsg": valid["errmsg"]}) results = [] if valid['is_ori_price']: price_type = 3 elif valid['is_without_tax']: price_type = 2 else: price_type = 1 to_text = valid['to_text'] only_supplier = valid["only_supplier"] start_time = datetime.strptime(valid["start_time"], "%Y-%m-%d") end_time = datetime.strptime(valid["end_time"], "%Y-%m-%d") logger.info(f"valid: {valid}") _hotel_prices = { datetime.strftime(start_time + timedelta(days=i), "%Y-%m-%d"): { "type": -1, "price": "", "room": "", "supplier": "", "each_supplier": {}, "updated_at": "", } for i in range((end_time - start_time).days + 1) } for uid in valid["hotels"]: hotel_prices = copy.deepcopy(_hotel_prices) hotel_prices = await get_weego_prices(uid, hotel_prices, price_type) for compare in valid["compare"]: hotel_prices = await add_compare_prices( compare, uid, hotel_prices, start_time, end_time ) results.append({uid: hotel_prices}) results = add_msg(results, to_text, only_supplier) return rest_result(request, {"status": 200, "data": results})