import datetime
import time
import json
import self as self
import MessageToSlack
import os
import pymysql.cursors
import random
import sys
import undetected_chromedriver.v2 as uc
from decouple import config
from functools import reduce
from selenium.webdriver.common.by import By
from selenium.webdriver.common.action_chains import ActionChains
from selenium.webdriver.common.desired_capabilities import DesiredCapabilities
from dateutil.relativedelta import relativedelta
# 用来驱动浏览器的
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
# from decouple import config
class Cainiao_Scrape:
need_customer_data = []
discount_rate_data = []
parameter_setting_data = []
page_count = 0
# 初始设置函数
def __init__(self, web_url, pro_db_host, pro_db_user, pro_db_pwd, pro_db_name, u02_db_host, u02_db_user, u02_db_pwd,
u02_db_name, u01_db_host, u01_db_user, u01_db_pwd, u01_db_name, cainiao_ac, cainiao_pwd):
self.vars = None
self.driver = None
self.web_url = web_url
# production
self.pro_db_host = pro_db_host
self.pro_db_user = pro_db_user
self.pro_db_pwd = pro_db_pwd
self.pro_db_name = pro_db_name
# u02
self.u02_db_host = u02_db_host
self.u02_db_user = u02_db_user
self.u02_db_pwd = u02_db_pwd
self.u02_db_name = u02_db_name
# u01
self.u01_db_host = u01_db_host
self.u01_db_user = u01_db_user
self.u01_db_pwd = u01_db_pwd
self.u01_db_name = u01_db_name
self.cainiao_ac = cainiao_ac
self.cainiao_pwd = cainiao_pwd
# 浏览器配置
def setup_method(self, method):
port_number = "127.0.0.1:9222"
# port_number = "192.168.20.24:2223"
try:
check_folder = os.path.isdir("ScreenCap")
if not check_folder:
os.makedirs("ScreenCap")
chrome_options = webdriver.ChromeOptions()
chrome_options.add_experimental_option(
"debuggerAddress", port_number)
capabilities = DesiredCapabilities.CHROME
capabilities["goog:loggingPrefs"] = {
'browser': 'ALL', "performance": "ALL"}
capabilities["goog:perfLoggingPrefs"] = {'enableNetwork': True}
chrome_options.add_argument("--disable-extensions")
chrome_options.add_argument("--disable-popup-blocking")
chrome_options.add_argument("--ignore-certificate-errors")
chrome_options.add_argument("--disable-plugins-discovery")
chrome_options.add_argument('--no-first-run')
chrome_options.add_argument('--no-service-autorun')
chrome_options.add_argument('--no-default-browser-check')
chrome_options.add_argument('no-startup-window')
chrome_options.add_argument('--disable-dev-shm-usage')
# chrome_options.add_argument('--no-sandbox') # highest right to operate
# chrome_options.add_argument('--headless') #--headless是不显示浏览器启动及执行过程
# chrome_options.add_argument('--disable-gpu') # 不加载gpu,规避bug
self.driver = webdriver.Chrome(
options=chrome_options, desired_capabilities=capabilities)
self.vars = {}
# 清除浏览器cookie
# self.driver.delete_all_cookies()
MessageToSlack.post_message_to_slack("Start Chrome Driver")
except Exception as r:
self.teardown_method
MessageToSlack.post_message_to_slack(
"浏览器配置setup_method抛出异常:%s" % str(r))
sys.exit()
# 菜鸟登录的函数
def login_cainiao(self):
try:
MessageToSlack.post_message_to_slack("Go to cainiao website")
try:
self.driver.get(self.web_url)
except Exception as get2:
MessageToSlack.post_message_to_slack(str(get2))
MessageToSlack.post_message_to_slack('get that page again')
self.driver.get(self.web_url)
link = self.web_url
time.sleep(random.randint(4, 6))
# # 打开本地的浏览器的时候,先跳过登录这一块然后再测试
# self.driver.switch_to.frame(0)
# time.sleep(random.randint(4, 6))
# # 点击输入账户
# self.driver.find_element(By.XPATH, "//input[@id='fm-login-id']").click()
# time.sleep(2)
# self.driver.find_element(By.XPATH, "//input[@id='fm-login-id']").send_keys(self.cainiao_ac)
# # 点击输入密码
# self.driver.find_element(By.XPATH, "//input[@id='fm-login-password']").click()
# time.sleep(2)
# self.driver.find_element(By.XPATH, "//input[@id='fm-login-password']").send_keys(self.cainiao_pwd)
# # 调取滑块验证部分
# self.slide_auth()
# # 点击登陆按钮
# self.driver.find_element(By.XPATH, "//button[@type='submit']").click()
# MessageToSlack.post_message_to_slack('pressed login button')
# # 如果有快速进入的验证框,点击快速验证
# try:
# self.driver.switch_to.frame(0)
# self.driver.find_element(By.XPATH, "//button[@type='submit']").click()
# MessageToSlack.post_message_to_slack('pressed quick entry button')
# except Exception as gin1:
# MessageToSlack.post_message_to_slack(str(gin1))
# MessageToSlack.post_message_to_slack('pressed quick entry button Unable to locate element')
# pass
# time.sleep(random.randint(4, 6))
# self.driver.get_log("performance") # get_log方法用于获取给定日志类型的日 get log first time, after get once log will be deleted
try:
self.driver.get(self.web_url)
except Exception as get1:
MessageToSlack.post_message_to_slack(str(get1))
MessageToSlack.post_message_to_slack('get that page again')
self.driver.get(self.web_url)
time.sleep(random.randint(4, 6))
MessageToSlack.post_message_to_slack("Get Data Page")
MessageToSlack.post_message_to_slack(
"此时浏览器打开的页面的标题:%s" % self.driver.title)
# 获取cai_niao_watermark_dailylogs表中stock_central_amt>0并且日期範圍由2年前的今天到今天的customer_name数据
self.get_db_customer_data()
# time.sleep(2)
# 遍历客户列表
db_customer_data = self.need_customer_data
MessageToSlack.post_message_to_slack('今日要更新的db_customer_data的客户数量为:%d' % len(db_customer_data))
MessageToSlack.post_message_to_slack(db_customer_data)
for item in db_customer_data:
customer_name = item['customer_name']
customer_id = item['customer_id']
# 调用客户查询函数
self.customer_query(customer_id, customer_name)
continue
self.goto_parameter_setting()
time.sleep(2)
MessageToSlack.post_message_to_slack("Data Scrape finished")
# # to press button to log out
# self.driver.switch_to.default_content()
# self.driver.find_element(By.CSS_SELECTOR, ".cct-nickname").click()
# time.sleep(1)
# self.driver.find_element(By.LINK_TEXT, "退出").click()
# MessageToSlack.post_message_to_slack("logged out")
except Exception as tc:
self.driver.get_screenshot_as_file(
"./ScreenCap/" + datetime.datetime.now().strftime("%Y%m%d_%H%M%p") + ".png") # 异常时捕获页面截图
MessageToSlack.post_message_to_slack(
"菜鸟登录的函数login_cainiao抛出异常:%s" % str(tc))
# self.teardown_method # 调用关闭浏览器函数
sys.exit() # 退出程序机制 通过引发SystemExit异常来退出Python程序
# 获取拖动按钮位置并拖动
def slide_auth(self):
try:
time.sleep(random.randint(4, 6))
# check have slide verify elements or not
if (self.driver.find_element(By.ID, "baxia-password")).is_displayed():
self.driver.switch_to.frame('baxia-dialog-content')
element = self.driver.find_element(By.ID, "nc_1_n1z")
slide_bar = self.driver.find_element(By.ID, "nc_1__scale_text")
action = ActionChains(self.driver)
action.move_to_element(element).pause(1).click_and_hold(element).pause(1).move_by_offset(
slide_bar.size['width'] - element.size['width'], 0).pause(1).release() # mobile slider
action.perform()
MessageToSlack.post_message_to_slack(
"Slide the verification bar")
self.driver.switch_to.parent_frame()
time.sleep(2)
if (self.driv2er.find_element(By.ID, "baxia-password")).is_displayed():
counter1 = 0
while (self.driver.find_element(By.ID, "baxia-password")).is_displayed() and counter1 < 6:
self.driver.switch_to.frame('baxia-dialog-content')
wrapper = self.driver.find_element(By.ID, "nocaptcha")
wrapper.click()
time.sleep(random.randint(2, 3))
element = self.driver.find_element(By.ID, "nc_1_n1z")
slide_bar = self.driver.find_element(
By.ID, "nc_1__scale_text")
action = ActionChains(self.driver)
action.move_to_element(element).pause(1).click_and_hold(element).pause(1).move_by_offset(
slide_bar.size['width'] - element.size['width'], 0).release() # mobile slider
action.perform()
MessageToSlack.post_message_to_slack(
"Slide the verification bar")
self.driver.switch_to.parent_frame()
time.sleep(random.randint(2, 3))
counter1 += 1
counter1 = 0
if (self.driver.find_element(By.ID, "baxia-password")).is_displayed():
raise Exception(
"Still cannot pass the slide certification after 5 attempt")
except Exception as s:
self.driver.get_screenshot_as_file(
"./ScreenCap/" + datetime.datetime.now().strftime("%Y%m%d_%H%M%p") + ".png")
MessageToSlack.post_message_to_slack(
"获取拖动按钮位置并拖动slide_auth抛出异常:%s" % str(s))
self.teardown_method
sys.exit()
# 点击查询客户
def customer_query(self, customer_id, customer_name):
# 点击客户列表中的客户名称输入框,并赋值对应的时间段,点击查询按钮
if (self.driver.find_element(By.XPATH, '//form[@id="J_Form"]')).is_displayed():
MessageToSlack.post_message_to_slack(
'customer name search form exists')
# 点击输入企业名称
self.driver.find_element(
By.XPATH, "//input[@id='c-text-51']").click()
time.sleep(2)
self.driver.execute_script(
'document.querySelector("#c-text-51").value="";')
self.driver.find_element(
By.XPATH, "//input[@id='c-text-51']").send_keys(customer_name)
# 日期选择范围
two_yrs_ago = datetime.datetime.now() - relativedelta(years=2)
start_year = int(two_yrs_ago.strftime('%Y'))
start_month = int(two_yrs_ago.strftime('%m'))
start_day = int(two_yrs_ago.strftime('%d'))
# 年月日的XPATH
current_selection_year_start = '.c-cal-year[data-year="%s"]' % start_year
current_selection_month_start = '.c-cal-month[data-month="%s"]' % start_month
current_selection_day_start = '.c-cal-day[data-day="%s"]' % start_day
# 点击日期选择器的DIV
self.driver.find_element(
By.XPATH, "//div[@id='c-calendar-select-66']").click()
time.sleep(1)
# 点击日期选择器的年份
self.driver.find_element(
By.XPATH, '//*[@id="c-calendar-87"]/div/div[1]/div[1]').click()
time.sleep(1)
self.driver.find_element(
By.CSS_SELECTOR, current_selection_year_start).click()
# 点击日期选择器的月份
self.driver.find_element(
By.XPATH, '//*[@id="c-calendar-87"]/div/div[1]/div[2]').click()
time.sleep(1)
self.driver.find_element(
By.CSS_SELECTOR, current_selection_month_start).click()
# 点击日期选择器的日期
self.driver.find_element(
By.CSS_SELECTOR, current_selection_day_start).click()
# 点击确定
self.driver.find_element(
By.XPATH, '//*[@id="c-calendar-81"]/div[3]/button').click()
# 点击查询
self.driver.find_element(By.XPATH, "//div[@id='J_search']").click()
MessageToSlack.post_message_to_slack('press the search div!')
time.sleep(random.randint(4, 6))
# 调取performance log分析函数
performance_log_customer_query = self.driver.get_log("performance")
self.log_analysis_customer_query(
performance_log_customer_query, customer_name, customer_id)
else:
raise Exception(
"cannot find this search form in customer list page. Please check is login problem or other")
# 客户列表日志分析函数
def log_analysis_customer_query(self, performance_log_customer_query, customer_name, customer_id):
for row in performance_log_customer_query:
log_json_customer_query = json.loads(row['message'])
log_customer_query = log_json_customer_query['message']
# MessageToSlack.post_message_to_slack(
# "点击查询客户的performance log在for循环中处理的结果")
# MessageToSlack.post_message_to_slack(log_customer_query)
method_customer_query = str(log_customer_query['method'])
if method_customer_query != 'Network.responseReceived':
continue
url_customer_query = str(
log_customer_query['params']['response']['url'])
if url_customer_query != 'https://merchant.finance.cainiao.com/funds/signApproveDetail/signApproveDetailData.do':
continue
requestId_customer_query = str(
log_customer_query['params']['requestId'])
try:
customer_query_page_data = \
self.driver.execute_cdp_cmd('Network.getResponseBody',
{'requestId': requestId_customer_query})[
'body']
cqd = json.loads(customer_query_page_data)
# MessageToSlack.post_message_to_slack('点击查询客户的cqd结果数据')
# MessageToSlack.post_message_to_slack(cqd)
total_customer_query = cqd['data']['total']
if total_customer_query > 0:
# 调取跳转参数设置页面的函数
resultList = cqd['data']['resultList']
for item in resultList:
if str(item['companyName']) != customer_name:
continue
approveNo = item['approveNo']
self.parameter_setting_data.append({
'approveNo': approveNo,
'customer_id': customer_id,
'customer_name': customer_name
})
else:
MessageToSlack.post_message_to_slack(
'No data for this company %s was found' % customer_name)
except Exception as customer_query_e:
MessageToSlack.post_message_to_slack(
'Problem after press the search button! ' + str(customer_query_e))
MessageToSlack.post_message_to_slack('数据已存入parameter_setting_data中')
# 调取跳转参数设置页面的函数
def goto_parameter_setting(self):
parameter_setting_data = list_dict_duplicate_removal(
self.parameter_setting_data)
# MessageToSlack.post_message_to_slack('去重复后的parameter_setting_data')
# MessageToSlack.post_message_to_slack(parameter_setting_data)
for ii in parameter_setting_data:
approveNo = ii['approveNo']
customer_id = ii['customer_id']
customer_name = ii['customer_name']
parameter_setting_url = 'https://merchant.finance.cainiao.com/funds/signApproveDetail/loanParameterSettings.htm?approveNo=' + approveNo
try:
self.driver.get(parameter_setting_url)
except Exception as get_parameter_setting:
MessageToSlack.post_message_to_slack(
str(get_parameter_setting))
MessageToSlack.post_message_to_slack(
'get parameter setting page again')
self.driver.get(parameter_setting_url)
# print('跳转到参数设置的页面标题为:' + self.driver.title)
time.sleep(random.randint(4, 6))
# 调取performance log分析函数
performance_log_parameter_setting = self.driver.get_log(
"performance")
self.log_analysis_parameter_setting(
performance_log_parameter_setting, customer_name, customer_id)
# 参数设置日志分析函数
def log_analysis_parameter_setting(self, performance_log_parameter_setting, customer_name, customer_id):
for row in performance_log_parameter_setting:
log_json_parameter_setting = json.loads(row['message'])
log_parameter_setting = log_json_parameter_setting['message']
if str(log_parameter_setting['method']) != 'Network.responseReceived':
continue
url_parameter_setting = log_parameter_setting['params']['response']['url']
if str(url_parameter_setting) != 'https://merchant.finance.cainiao.com/funds/signApproveDetail/pledgeRateData.do':
continue
requestId_parameter_setting = log_parameter_setting['params']['requestId']
try:
parameter_setting_page_data = self.driver.execute_cdp_cmd('Network.getResponseBody', {
'requestId': requestId_parameter_setting})['body']
psd = json.loads(parameter_setting_page_data)
# MessageToSlack.post_message_to_slack('psd')
# MessageToSlack.post_message_to_slack(psd)
total_parameter_setting = psd['data']['resultList']
if len(total_parameter_setting) > 0:
resultList = psd['data']['resultList']
for item in resultList:
item['customer_id'] = customer_id
item['customer_name'] = customer_name
self.discount_rate_data.append(item)
else:
MessageToSlack.post_message_to_slack(
'No data for this company %s was found' % customer_name)
except Exception as parameter_setting_e:
MessageToSlack.post_message_to_slack(
'Problem after press the search button! ' + str(parameter_setting_e))
# 获取cai_niao_watermark_dailylogs表中stock_central_amt>0并且日期範圍由2年欠的今天到今天的customer_name数据
def get_db_customer_data(self):
record_exist = 0
db_host = self.pro_db_host
db_user = self.pro_db_user
db_pwd = self.pro_db_pwd
db_name = self.pro_db_name
two_yrs_ago = datetime.datetime.now() - relativedelta(years=2)
start_date = two_yrs_ago.strftime('%Y-%m-%d')
end_date = datetime.datetime.now().strftime('%Y-%m-%d')
try:
connection = pymysql.connect(host=db_host, user=db_user, password=db_pwd, database=db_name,
cursorclass=pymysql.cursors.DictCursor)
MessageToSlack.post_message_to_slack(
"The database is connected to query data")
with connection:
with connection.cursor() as cursor:
check_sql = "SELECT EXISTS ( SELECT `customer_name` FROM `cai_niao_watermark_dailylogs` WHERE `stock_central_amt` > 0 AND `created_at` BETWEEN %s AND %s)"
cursor.execute(check_sql, (start_date, end_date))
result = cursor.fetchone()
if (list(result.values()))[0] == 1:
record_exist = 1
if record_exist == 1:
select_sql = "SELECT customer_id,customer_name FROM `cai_niao_watermark_dailylogs` WHERE `stock_central_amt` > 0 AND `created_at` BETWEEN %s AND %s"
cursor.execute(select_sql, (start_date, end_date))
dbs_response = cursor.fetchall()
self.need_customer_data = list_dict_duplicate_removal(
dbs_response)
connection.commit()
except Exception as ds:
MessageToSlack.post_message_to_slack(
"get_db_customer_data抛出异常:%s" % str(ds))
connection.close()
# 多个数据库执行数据存储
def save_to_db(self):
# save to dbs
self.db_save_discount_rate(
self.pro_db_host, self.pro_db_user, self.pro_db_pwd, self.pro_db_name)
self.db_save_discount_rate(
self.u02_db_host, self.u02_db_user, self.u02_db_pwd, self.u02_db_name)
self.db_save_discount_rate(
self.u01_db_host, self.u01_db_user, self.u01_db_pwd, self.u01_db_name)
# 将获取到的信息存储到数据库中
def db_save_discount_rate(self, db_host, db_user, db_pwd, db_name):
discount_rate_data = self.discount_rate_data
# MessageToSlack.post_message_to_slack("discount_rate_data:")
# MessageToSlack.post_message_to_slack(discount_rate_data)
if len(discount_rate_data) > 0:
try:
connection = pymysql.connect(
host=db_host, user=db_user, password=db_pwd, database=db_name,
cursorclass=pymysql.cursors.DictCursor)
MessageToSlack.post_message_to_slack(
"connect with db successfully")
with connection:
for data in discount_rate_data:
download_date = datetime.datetime.now().strftime('%Y-%m-%d')
created_at = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
updated_at = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
customer_id = data['customer_id']
customer_name = data['customer_name']
all_assets_value = data['allAssetsValue']
assets_receivable_value = data['assetsReceivableValue']
central_good_value = data['centralGoodValue']
central_pledge_rate = int(data['centralPledgeRate']) # int
currency = data['currency']
discount_assets_receivable_value = data['discountAssetsReceivableValue']
goods_owner_name = data['goodsOwnerName']
goods_value = data['goodsValue']
head_trip_pledge_rate = int(data['headTripPledgeRate']) # int
head_trip_value = data['headTripValue']
pledge_goods_value = data['pledgeGoodsValue']
# int
pledge_rate = int(data['pledgeRate'])
receivable_pledge_rate = int(data['receivablePledgeRate']) # int
store_name = data['storeName']
store_t_b_id = data['storeTBId']
record_exist = 0
with connection.cursor() as cursor:
check_sql = "SELECT EXISTS ( SELECT `download_date` FROM `cai_niao_company_discountrate_dailylogs` WHERE `download_date` = %s and `customer_id` = %s and `store_t_b_id` = %s)"
cursor.execute(
check_sql, (download_date, customer_id, store_t_b_id))
result = cursor.fetchone()
if (list(result.values()))[0] == 1:
record_exist = 1
if record_exist == 0:
MessageToSlack.post_message_to_slack(
"Not found today record, insert that record")
# 执行插入数据
# 新增语句
insert_sql = f"Insert INTO `cai_niao_company_discountrate_dailylogs` (`download_date`,`created_at`,`customer_id`,`customer_name`,`all_assets_value`,`assets_receivable_value`,`central_good_value`,`central_pledge_rate`,`currency`,`discount_assets_receivable_value`,`goods_owner_name`,`goods_value`,`head_trip_pledge_rate`,`head_trip_value`,`pledge_goods_value`,`pledge_rate`,`receivable_pledge_rate`,`store_name`,`store_t_b_id`) VALUES ('{download_date}', '{created_at}', '{customer_id}', '{customer_name}', '{all_assets_value}', '{assets_receivable_value}', '{central_good_value}', {central_pledge_rate}, '{currency}', '{discount_assets_receivable_value}', '{goods_owner_name}', '{goods_value}', {head_trip_pledge_rate}, '{head_trip_value}', '{pledge_goods_value}', {pledge_rate}, {receivable_pledge_rate}, '{store_name}', '{store_t_b_id}')"
MessageToSlack.post_message_to_slack("insert_sql: %s" % insert_sql)
with connection.cursor() as cursor:
cursor.execute(insert_sql)
elif record_exist == 1:
MessageToSlack.post_message_to_slack(
"Today record is existed, update that record")
# 执行更新数据
# 更新语句
update_sql = f"UPDATE `cai_niao_company_discountrate_dailylogs` SET `updated_at` = '{updated_at}',`all_assets_value` = '{all_assets_value}',`assets_receivable_value` = '{assets_receivable_value}',`central_good_value` = '{central_good_value}',`central_pledge_rate` = {central_pledge_rate},`currency` = '{currency}',`discount_assets_receivable_value` = '{discount_assets_receivable_value}',`goods_owner_name` = '{goods_owner_name}',`goods_value` = '{goods_value}',`head_trip_pledge_rate` = {head_trip_pledge_rate},`head_trip_value` = '{head_trip_value}',`pledge_goods_value` = '{pledge_goods_value}',`pledge_rate` = {pledge_rate},`receivable_pledge_rate` = {receivable_pledge_rate},`store_name` = '{store_name}',`store_t_b_id` = '{store_t_b_id}' WHERE `download_date` = '{download_date}' and `customer_id` = '{customer_id}' and `store_t_b_id` = '{store_t_b_id}'"
MessageToSlack.post_message_to_slack("update_sql: %s" % update_sql)
with connection.cursor() as cursor:
cursor.execute(update_sql)
connection.commit()
MessageToSlack.post_message_to_slack(
"Inserted into %s" % db_name)
except Exception as ds:
MessageToSlack.post_message_to_slack(
"db_save_discount_rate抛出异常:%s" % str(ds))
connection.close()
else:
MessageToSlack.post_message_to_slack(
'No data need to store as no data grabbed')
MessageToSlack.post_message_to_slack("Bye")
# 关闭所有的浏览器窗口
def teardown_method(self):
# self.driver.quit()
MessageToSlack.post_message_to_slack(
"浏览器要关闭时打开的页面的标题: %s" % self.driver.title)
MessageToSlack.post_message_to_slack("Browser Close")
# 列表里的字典元素去重复
def list_dict_duplicate_removal(data_list):
def run_function(x, y): return x if y in x else x + [y]
return reduce(run_function, [[], ] + data_list)
if __name__ == '__main__':
scrape_cainiao = Cainiao_Scrape(
'https://merchant.finance.cainiao.com/funds/signApproveDetail/SignApproveDetailManage.htm',
config ('PRO_DB_HOST'),
config ('PRO_DB_USERNAME'),
config ('PRO_DB_PASSWORD'),
config ('PRO_DB_DATABASE'),
config ('U02_DB_HOST'),
config ('U02_DB_USERNAME'),
config ('U02_DB_PASSWORD'),
config ('U02_DB_DATABASE'),
config ('U01_DB_HOST'),
config ('U01_DB_USERNAME'),
config ('U01_DB_PASSWORD'),
config ('U01_DB_DATABASE'),
config ('CAINIAO_AC'),
config ('CAINIAO_PWD')
)
# 获取cai_niao_watermark_dailylogs表中stock_central_amt>0并且日期範圍由2年前的今天到今天的customer_name数据
scrape_cainiao.get_db_customer_data()
# 浏览器配置函数
scrape_cainiao.setup_method('')
# 链接菜鸟后台网址,并scrape相关数据
scrape_cainiao.login_cainiao ()
# 关闭所有的浏览器窗口
scrape_cainiao.teardown_method ()
# 数据存储到数据库的函数
scrape_cainiao.save_to_db ()