# author:qinguanglei
# ddate:2023/11/20 10:15
import traceback
import allure
from selenium.webdriver.chrome import webdriver
from selenium.webdriver import ActionChains
from common import constant
from common.logger import log
from common.read_yaml import get_filed_from_yaml
from common.verifycode import VerifyCode
from test_buy.page_buy import PageBuy

module = 'buy'


class StepsBuy(object):
    def __init__(self, driver):
        self.page_buy = PageBuy(driver)
        self.driver = driver

    @allure.step("打开浏览器")
    def open_browser(self):
        try:
            log.info('当前url： %s', get_filed_from_yaml(module, "data", "url"))
            self.page_buy.open_page(get_filed_from_yaml(module, "data", "url"))
        except Exception as e:
            log.error(f'打开浏览器问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("登录")
    def login(self):
        try:
            # 获取账号输入元素
            account_element = self.page_buy.get_account()
            # 获取密码输入元素
            password_element = self.page_buy.get_password()
            # 获取账号与密码
            account = get_filed_from_yaml(module, "data", "account")
            password = get_filed_from_yaml(module, "data", "password")
            # 填充账号密码
            self.page_buy.input_text(account_element, account)
            self.page_buy.input_text(password_element, password)
            # 登录特殊处理一下，验证码最多尝试5次，有一次成功，则成功。若5次都失败，案例直接失败
            max_retry = 5
            i = 5
            while i > 0:
                # 先获取验证码图片元素
                verify_code_element = self.page_buy.get_verify_image()
                # 获取验证码输入元素
                verify_input_element = self.page_buy.get_verify_code()
                # 获取验证码中的文字信息
                verify_code_text = VerifyCode(verify_code_element, self.driver).indentify_verify_image()
                # 填充验证码
                self.page_buy.input_text(verify_input_element, verify_code_text)
                log.info(f'填充的验证码内容为{verify_code_text}。')
                # 获取登录按钮
                login_button_element = self.page_buy.get_login_button()
                # 点击登录
                self.page_buy.single_click(login_button_element)
                # 判断登录是否成功，登录成功会切换到另外一个页面，通过页面title来判断是否切换成功
                if self.page_buy.get_window_title() != constant.LOGIN_SUCCESS:
                    # 表示不登录成功，此时将1减去1
                    i -= 1
                    log.warn('执行登录失败一次，次数多了将直接导致案例失败。')
                else:
                    # 表示登录成功，跳出循环
                    log.info('登录成功，开始执行案例。')
                    break
            if i <= 0:
                log.error(
                    f'验证码已经连续{max_retry}次识别失败，本案例执行时登录失败，请检查环境是否出现问题，特别是分辨率是否调整。')
                assert False
            log.info(f'登录成功。')
        except Exception as e:
            log.error(f'登录过程问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("进入普通采购单界面")
    def enter_buy_op_page(self):
        try:
            # 定位采购管理元素
            buy_management_button = self.page_buy.get_buy_management()
            # 鼠标移动到采购管理按钮
            self.page_buy.move_to_element(buy_management_button)
            # 定位到隐藏的采购按钮
            buy_button = self.page_buy.get_buy()
            # 鼠标移动到采购按钮
            self.page_buy.move_to_element(buy_button)
            # 定位到采购申请op
            buy_op_button = self.page_buy.get_buy_op()
            # 鼠标移动到采购申请op
            self.page_buy.move_to_element(buy_op_button)
            # 点击采购申请op
            buy_op_button.click()
            log.info(f'成功进去普通采购单页面。')
        except Exception as e:
            log.error(f'进入普通采购单界面问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("打开新建普通采购单界面")
    def enter_new_op_frame(self):
        try:
            # 先进入到采购iframe
            iframe_buy = self.page_buy.get_iframe_buy()
            # 转到这个iframe下
            self.page_buy.switch_to_iframe(iframe_buy)
            # 获取新建按钮
            new_create_button = self.page_buy.get_new()
            # 点击新建
            self.page_buy.single_click(new_create_button)

            # 后续操作在一对话框形式的iframe里，切换到这个子iframe
            sub_iframe_dialog = self.page_buy.get_sub_iframe_dialog()
            self.page_buy.switch_to_iframe(sub_iframe_dialog)
            log.info(f'成功打开新建普通采购单界面。')
        except Exception as e:
            log.error(f'进入新建普通采购单界面问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("输入供应商")
    def input_supplier_bk(self):
        try:
            # 先从yaml中获取供应商内容
            supplier_content = get_filed_from_yaml(module, "data", "supplier")
            # 触发请求供应商按钮
            supplier_request = self.page_buy.get_supplier_request()
            self.page_buy.single_click(supplier_request)
            # 输入供应商信息
            supplier_input = self.page_buy.get_supplier_input()
            self.page_buy.input_text(supplier_input, supplier_content)
            # 开始查询,点击搜索按钮查询
            supplier_search = self.page_buy.get_supplier_search()
            self.page_buy.single_click(supplier_search)
            # 获取供应商dialog
            supplier_dialog = self.page_buy.get_supplier_dialog()
            # 获取查询结果，先获取结果表
            supplier_table = self.page_buy.get_table_from_dialog(supplier_dialog)
            # 获取供应商表中的所有行
            supplier_table_rows = self.page_buy.get_all_rows_from_tale(supplier_table)
            # 遍历供应商
            for i, current_row in enumerate(supplier_table_rows):
                self.page_buy.single_click(current_row)
                # 获取当前供应商的列信息
                columns = self.page_buy.get_all_columns_from_row(current_row)
                # 遍历列内容,这里只是先打印出日志，便于查看问题
                for j, curr_column in enumerate(columns):
                    log.info(
                        '查询出供应商表，的第 %s 行，第 %s 列的内容为 %s' % (i, j, self.page_buy.get_text(curr_column)))
                # 挑选出一列，因为前端是模糊查询，有可能是供应商编码，有可能是供应商名称，匹配第一条即可
                if (supplier_content in self.page_buy.get_text(columns[1])) or (
                        supplier_content in self.page_buy.get_text(columns[2])):
                    '''选中当前行'''
                    # self.page_buy.single_click(current_row)
                    # self.page_buy.single_click(columns[1])
                    current_row.click()
                    '''点击确认'''
                    supplier_table_ensure = self.page_buy.get_ensure_from_dialog(supplier_dialog)
                    self.page_buy.single_click(supplier_table_ensure)
                    '''选中后退出，不再查询'''
                    break
            log.info(f'供应商{supplier_content}输入成功。')
        except Exception as e:
            log.error(f'输入供应商问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("输入供应商")
    def input_supplier(self):
        try:
            # 先从yaml中获取供应商内容
            supplier_content = get_filed_from_yaml(module, "data", "supplier")
            # 获取供应商输入内容元素
            supplier_input = self.page_buy.get_supplier_content()
            # 输入供应商
            self.page_buy.input_text(supplier_input, supplier_content)
            log.info(f'供应商{supplier_content}输入成功。')
        except Exception as e:
            log.error(f'输入供应商问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("输入仓库")
    def input_warehouse_bk(self):
        try:
            # 先从yaml中获取仓库内容
            ware_content = get_filed_from_yaml(module, "data", "warehouse")
            # 点击仓库请求按钮
            ware_request = self.page_buy.get_ware_request()
            self.page_buy.single_click(ware_request)
            # 输入仓库数据
            # ware_input = self.page_buy.get_ware_input()
            # self.page_buy.input_text(ware_input, ware_content)
            # 搜索仓库信息
            ware_search = self.page_buy.get_ware_search()
            self.page_buy.single_click(ware_search)
            # 仓库dialog
            ware_dialog = self.page_buy.get_ware_dialog()
            # 确定仓库信息的表
            ware_table = self.page_buy.get_table_from_dialog(ware_dialog)
            # 获取该表下的行数据集
            ware_table_rows = self.page_buy.get_all_rows_from_tale(ware_table)
            log.info("仓库表的行数：%s" % len(ware_table_rows))
            # 遍历仓库表行
            for i, current_row in enumerate(ware_table_rows):
                # 获取当前行的列
                columns = self.page_buy.get_all_columns_from_row(current_row)

                log.info(f'仓库表第{i}行一共有{len(columns)}列。')
                # 遍历列内容,这里只是先打印出日志，便于查看问题
                for j, curr_column in enumerate(columns):
                    log.info(
                        '查询出仓库表，的第 %s 行，第 %s 列的内容为 %s' % (i, j, self.page_buy.get_text(curr_column)))
                # 挑选出一列，因为前端是模糊查询，有可能是仓库编码，有可能是仓库名称，匹配第一条即可
                if (ware_content in self.page_buy.get_text(columns[1])) or (
                        ware_content in self.page_buy.get_text(columns[2])):
                    '''选中当前行'''
                    # self.driver.execute_script("arguments[0].click();", current_row)
                    # self.page_buy.single_click(current_row)
                    self.page_buy.select_one_row(current_row)
                    '''点击确认'''
                    ware_table_ensure = self.page_buy.get_ensure_from_dialog(ware_dialog)
                    self.page_buy.single_click(ware_table_ensure)
                    '''选中后退出，不再查询'''
                    break
            log.info(f'仓库{ware_content}输入成功。')
        except Exception as e:
            log.error(f'输入仓库问题：{e.__doc__}{traceback.format_exc()}')
            assert False

        @allure.step("输入仓库")
        def input_warehouse_bk(self):
            try:
                # 先从yaml中获取仓库内容
                ware_content = get_filed_from_yaml(module, "data", "warehouse")
                # 点击仓库请求按钮
                ware_request = self.page_buy.get_ware_request()
                self.page_buy.single_click(ware_request)
                # 输入仓库数据
                # ware_input = self.page_buy.get_ware_input()
                # self.page_buy.input_text(ware_input, ware_content)
                # 搜索仓库信息
                ware_search = self.page_buy.get_ware_search()
                self.page_buy.single_click(ware_search)
                # 仓库dialog
                ware_dialog = self.page_buy.get_ware_dialog()
                # 确定仓库信息的表
                ware_table = self.page_buy.get_table_from_dialog(ware_dialog)
                # 获取该表下的行数据集
                ware_table_rows = self.page_buy.get_all_rows_from_tale(ware_table)
                log.info("仓库表的行数：%s" % len(ware_table_rows))
                # 遍历仓库表行
                for i, current_row in enumerate(ware_table_rows):
                    # 获取当前行的列
                    columns = self.page_buy.get_all_columns_from_row(current_row)

                    log.info(f'仓库表第{i}行一共有{len(columns)}列。')
                    # 遍历列内容,这里只是先打印出日志，便于查看问题
                    for j, curr_column in enumerate(columns):
                        log.info(
                            '查询出仓库表，的第 %s 行，第 %s 列的内容为 %s' % (i, j, self.page_buy.get_text(curr_column)))
                    # 挑选出一列，因为前端是模糊查询，有可能是仓库编码，有可能是仓库名称，匹配第一条即可
                    if (ware_content in self.page_buy.get_text(columns[1])) or (
                            ware_content in self.page_buy.get_text(columns[2])):
                        '''选中当前行'''
                        # self.driver.execute_script("arguments[0].click();", current_row)
                        # self.page_buy.single_click(current_row)
                        self.page_buy.select_one_row(current_row)
                        '''点击确认'''
                        ware_table_ensure = self.page_buy.get_ensure_from_dialog(ware_dialog)
                        self.page_buy.single_click(ware_table_ensure)
                        '''选中后退出，不再查询'''
                        break
                log.info(f'仓库{ware_content}输入成功。')
            except Exception as e:
                log.error(f'输入仓库问题：{e.__doc__}{traceback.format_exc()}')
                assert False

    @allure.step("输入仓库")
    def input_warehouse(self):
        try:
            # 先从yaml中获取仓库内容
            ware_content = get_filed_from_yaml(module, "data", "warehouse")
            # 点击仓库输入内容元素
            warehouse_content_input = self.page_buy.get_warehouse_content()
            # 输入仓库信息
            self.page_buy.input_text(warehouse_content_input, ware_content)
            log.info(f'仓库{ware_content}输入成功。')
        except Exception as e:
            log.error(f'输入仓库问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("输入协议")
    def input_protocol(self):
        try:
            # 先从yaml中获取协议内容
            protocol_content = get_filed_from_yaml(module, "data", "protocol")
            # 获取协议输入内容元素
            protocol_content_input = self.page_buy.get_protocol_context()
            # 输入仓库信息
            self.page_buy.input_text(protocol_content_input, protocol_content)
            log.info(f'协议{protocol_content}输入成功。')
        except Exception as e:
            log.error(f'输入协议问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("输入业务员")
    def input_businessman(self):
        try:
            # 先从yaml中获取协议内容
            businessman_content = get_filed_from_yaml(module, "data", "businessman")
            # 获取业务员输入内容元素
            businessman_content_input = self.page_buy.get_businessman_content()
            # 输入仓库信息
            self.page_buy.input_text(businessman_content_input, businessman_content)
            log.info(f'业务员{businessman_content}输入成功。')
        except Exception as e:
            log.error(f'输入业务员问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("添加商品")
    def add_merchandise(self):
        try:
            # 先从yaml中获取协议内容
            merchandise_content = get_filed_from_yaml(module, "data", "merchandise")
            # 点击商品录入按钮
            merchandise = self.page_buy.get_merchandise()
            self.page_buy.single_click(merchandise)
            # 获取商品dialog
            merchandise_dialog = self.page_buy.get_merchandise_dialog()
            # 输入商品信息
            # merchandise_input = self.page.get_input_from_dialog(merchandise_dialog)
            merchandise_input = self.page_buy.get_merchandise_input()
            self.page_buy.input_text(merchandise_input, merchandise_content)
            # 点击搜索
            # merchandise_search = self.page.get_search_from_dialog(merchandise_dialog)
            merchandise_search = self.page_buy.get_merchandise_search()
            self.page_buy.single_click(merchandise_search)
            # 获取搜索出来的表信息
            merchandise_table = self.page_buy.get_table_from_dialog(merchandise_dialog)
            # 获取表的全部行
            merchandise_table_rows = self.page_buy.get_all_rows_from_tale(merchandise_table)
            # 遍历行
            for i, current_row in enumerate(merchandise_table_rows):
                # 获取当前供应商的列信息
                columns = self.page_buy.get_all_columns_from_row(current_row)
                # 遍历列内容,这里只是先打印出日志，便于查看问题
                for j, curr_column in enumerate(columns):
                    log.info(
                        '查询出商品表，的第 %s 行，第 %s 列的内容为 %s' % (i, j, self.page_buy.get_text(curr_column)))
                # 挑选出一列，模糊查询，匹配商品编码,商品名称,规格型号,厂家物料编码
                if ((merchandise_content in self.page_buy.get_text(columns[1])) or
                        (merchandise_content in self.page_buy.get_text(columns[3])) or
                        (merchandise_content in self.page_buy.get_text(columns[4])) or
                        (merchandise_content in self.page_buy.get_text(columns[6]))):
                    '''选中当前行'''
                    '''先获取复选框'''
                    box = self.page_buy.get_merchandise_all_select()
                    self.page_buy.single_click(box)
                    '''点击确认'''
                    ensure = self.page_buy.get_ensure_from_dialog(merchandise_dialog)
                    self.page_buy.single_click(ensure)
                    '''选中后退出，不再查询'''
                    break
            log.info(f'商品{merchandise_content}输入成功。')
        except Exception as e:
            log.error(f'添加商品问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("明细处理")
    def detail_proc(self):
        try:
            # 获取商品明细表
            detail_table = self.page_buy.get_detail_table()
            # 获取明细表中所有行
            detail_rows = self.page_buy.get_all_rows_from_tale(detail_table)
            # 遍历商品行，填入商品数量
            for i, current_row in enumerate(detail_rows):
                # 获取当前行所有的列
                columns = self.page_buy.get_all_columns_from_row(current_row)
                # 遍历列内容,这里只是先打印出日志，便于查看问题
                for j, curr_column in enumerate(columns):
                    # 第1列columns[1]为数量
                    if j == 1:
                        # 先点击该元素
                        self.page_buy.single_click(columns[j])
                        # 再获取输入元素信息
                        quantity_element = self.page_buy.get_input_from_column(columns[j])
                        # 输入数量
                        quantity_element.clear()
                        self.page_buy.input_text(quantity_element, 1000)
                    # 第10列columns[10]为含税单价
                    if j == 10:
                        # 先点击该元素
                        self.page_buy.single_click(columns[j])
                        # 再获取输入元素信息
                        price_element = self.page_buy.get_input_from_column(columns[j])
                        # 输入价格
                        price_element.clear()
                        self.page_buy.input_text(price_element, 100)

                    log.info('详情清单，的第 %s 行，第 %s 列的内容为 %s' % (i, j, self.page_buy.get_text(curr_column)))
            log.info(f'商品明细处理成功。')
        except Exception as e:
            log.error(f'商品明细处理问题：{e.__doc__}{traceback.format_exc()}')
            assert False

    @allure.step("订单保存处理")
    def save_proc(self):
        # 保存
        save_button = self.page_buy.get_save()
        self.page_buy.single_click(save_button)
        # 获取采购单号
        order_no = self.page_buy.get_order_no()
        log.info("订单号：%s" % self.page_buy.get_text(order_no))

    @allure.step("订单提交处理")
    def submit_proc(self):
        # 保存
        submit_button = self.page_buy.get_submit_element()
        self.page_buy.single_click(submit_button)


