主导jenkins上线记录(leader认可版)

Ryder 2025-12-1 15 12/1

1.体验服务器

地址:http://39.102.121.104:8080/

账号:ryder 密码GeChao@2025

2.构建-执行-报告

失败第101次后...

2.1流水线执行

主导jenkins上线记录(leader认可版)

2.2 运行日志主导jenkins上线记录(leader认可版)

2.3 运行结束生成报告

主导jenkins上线记录(leader认可版)

2.4 错误截图助力快速定位,排查bug主导jenkins上线记录(leader认可版) 主导jenkins上线记录(leader认可版)

3.注意:sos救命!!!

运行内存不够用,要炸啦,快换一个大一点的服务器吧!(老板大气) 主导jenkins上线记录(leader认可版)

服务器jenkins以及docker基本命令:

docker ps | grep jenkins
docker exec -it e046a6e5c9a1 bash
su - jenkins
ssh-keygen -t ed25519 -C "jenkins@gitee-ssh"
公钥
cat ~/.ssh/id_ed25519.pub
私钥
cat ~/.ssh/id_ed25519
ssh -T git@gitee.com

# 重新构建镜像
docker-compose down
docker-compose up -d

# 查看jenkins的工作空间,删除废弃缓存
/var/jenkins_home/workspace

4.新增需求

4.1 数据库实时保存测试结果,结束后可视化用例报告发送钉钉群或公司邮箱

解决方案:

通过pytest钩子,每个测试用例执行完成后自动调用,连接轻量数据库,保存在数据库中,后面统计数据发送机器人通知

@pytest.hookimpl(tryfirst=True, hookwrapper=True)
def pytest_runtest_makereport(item, call):
    """
    pytest钩子:每个测试用例执行完成后自动调用
    """
    outcome = yield
    rep = outcome.get_result()
    page = item.funcargs.get("logged_in_page")  # 修改:使用Playwright的page对象
    current_date = datetime.now().strftime('%Y-%m-%d')

    if rep.when == 'call':  # 只在测试调用阶段处理
        # 1. 获取用例元数据
        keywords = item.keywords
        allure_label = keywords.get('allure_label')
        feature = getattr(allure_label, 'args', [''])[0]  # 功能模块
        title = keywords.get('__allure_display_name__', item.nodeid)  # 用例标题

        # 从测试用例的参数中获取"场景"字段
        case_data = item.funcargs.get('case', {})  # 获取参数化的case数据
        scenario = case_data.get('场景', item.nodeid)  # 优先使用"场景"字段,否则使用node_id
        logger.info(f"📋 测试场景: {scenario}")

        # 2. 初始化数据库连接
        with DbConnectionFactory() as db_factory:
            project_file_path = ProjectFilePath()
            # 通过getattr安全访问属性
            test_db_path = getattr(project_file_path, 'test_result_db_path', None)
            if test_db_path:
                sqlite_conn = db_factory.create_connection('sqlite', db_path=test_db_path).connect()
            else:
                # 如果无法获取数据库路径,使用默认路径
                from tools.path_manage import ROOT_PATH
                test_db_path = str(ROOT_PATH / 'auto_test_result_db.sqlite')
                sqlite_conn = db_factory.create_connection('sqlite', db_path=test_db_path).connect()

            # 3. 根据测试结果准备不同数据
            if rep.passed:
                # ✅ 测试通过
                execution_result = 'pass'
                extra_fields = ''
                extra_values = ''
                fail_params = []

            elif rep.failed:
                # ❌ 测试失败 - 自动截图
                execution_result = 'fail'

                # 修改:从 Allure 报告中获取已有的截图,或者跳过截图
                # Playwright 的失败截图已由 pytest-playwright 插件自动处理
                extra_fields = ''
                extra_values = ''
                fail_params = []
                logger.warning("⚠️ 测试失败,截图已由 Allure 自动处理")

            elif rep.skipped:
                # ⏭️ 测试跳过
                execution_result = 'skip'
                extra_fields = ''
                extra_values = ''
                fail_params = []
            else:
                return

            # 4. 检查是否已存在记录(同一天同一场景)
            test_db_id = sqlite_conn.select(
                table='test_result_tb',
                fields=["id"],
                where={"scenario": scenario, "create_date": current_date}  # 使用"场景"字段
            )

            if test_db_id and isinstance(test_db_id, list) and len(test_db_id) > 0:
                # 更新已有记录
                sqlite_conn.update(
                    table='test_result_tb',
                    updates={"execution_result": execution_result},
                    where={"id": test_db_id[0][0], "create_date": current_date}
                )
                logger.info(f"✅ 更新测试结果: {scenario} -> {execution_result}")
            else:
                # 插入新记录(动态SQL支持失败时的额外字段)
                base_sql = '''INSERT INTO test_result_tb
                              (execution_result, title, feature, scenario, create_date{extra_fields})
                              VALUES (?, ?, ?, ?, ?{extra_values})'''

                insert_params = [execution_result, title, feature, scenario, current_date] + fail_params  # 使用"场景"字段

                sqlite_conn.execute(
                    base_sql.format(extra_fields=extra_fields, extra_values=extra_values),
                    insert_params
                )
                logger.info(f"✅ 插入测试结果: {scenario} -> {execution_result}")

钉钉插件机器人通知:

主导jenkins上线记录(leader认可版)

4.2 运行方案:让我来维护这个框架,找到一个方法让其他代码能力弱的同事去用某种工具来截图流程和代码交给我,合作完成提升系统覆盖率

暂定!

4.3 轮询和定时构建1小时跑一次(以往有过网站服务宕机情况,绝对避免),发送报告,以最小风险保障线上安全以及最快速度发现问题并解决。

解决方案:

* * * * * = 每分钟、每小时、每天、每月、每周的所有时间点都触发 → 最终效果是「每分钟执行一次」。

主导jenkins上线记录(leader认可版)

每小时定时构建一次+每次提交代码构建一次(15分钟)。

定期清理服务器存储日志(7天前)、结果报告(保留最近 10 个 Allure 结果目录)

主导jenkins上线记录(leader认可版)主导jenkins上线记录(leader认可版)

成功清理!

主导jenkins上线记录(leader认可版)

5.后续安排

5.1 加入接口自动化集成

5.2 除去冗余代码,保持精简和健壮性

5.3 性能集成有空再做

5.4 学习前后端框架

5.5 平台写好后:用例管理+大模型赋能+对接提bug软件如coding与其他类似。

- THE END -

Ryder

12月10日18:14

最后修改:2025年12月10日
1

非特殊说明,本博所有文章均为博主原创。

共有 0 条评论