Skip to main content

使用 Copilot 生成优化的评审过程

使用 Copilot 自动化评审以优化和改进评审过程。

谁可以使用此功能?

适用于所有付费 Copilot 计划

介绍

在减少对次要实现细节(如命名和样式约定)花费的时间时,代码评审更高效,而是将精力集中在满足用户需求的更高级别设计、解决问题和功能上。

在本文中,我们将展示如何通过自动评审 Copilot 优化你的审阅过程,这样你可以减少在细微更改上花费的时间,更多地专注于对问题解决的细致探讨和对实现过程的深入理解,从而不仅仅是充分,而是巧妙地满足用户需求。

1. 提升来自 Copilot 的审查质量

Copilot 代码评审 可以为存储库中的所有拉取请求提供自动评审,并通过捕获代码中不需要的更改提高审阅效率。 与自定义说明配对时,会更有效, Copilot 代码评审 因为它可以提供根据团队工作方式、使用的工具或项目细节而定制的响应。

编写自定义说明的最佳做法包括:

  • 不同的标题
  • 要点
  • 简短的直接说明

我们来看一个示例。 如果要使用 Python 生成订单处理系统,自定义说明可能包括特定于Python的格式、性能和安全编码做法,以及与项目直接相关的指南。 以下示例显示了自定义指令的几行可能是什么样子。

## Repository context
- This repository implements an order processing system (order intake, payment, fulfillment) where correctness, security, and auditability are critical. 

## Style and conventions
- Follow the PEP 8 and PEP 257 style guide for Python.
- Use clear, domain-relevant names (orders, payments, inventory, customers, shipments).
- Prefer small, focused functions and methods with clearly defined responsibilities.

## Secure coding 
- Verify proper input validation and sanitization.
- Review authentication and authorization logic.

## Error handling guidelines
- Handle timeouts and network errors gracefully.
- Ensure failures are logged with enough detail for debugging.

## Order processing context
- Ensure order creation, payment handling, and updates are idempotent to avoid duplicate orders or duplicate charges.
- Validate and normalize all order, payment, and customer data before persisting or acting on it.
- Do not log or persist sensitive data (passwords, raw payment details, full identifiers) without hashing, encryption, or redaction.
- Call out obvious performance issues in core order workflows (e.g., N+1 queries, per-order synchronous network calls) and suggest simpler, more efficient alternatives.

## Review style
- Be concise, specific and actionable.
- Explain the "why" behind recommendations using bullet points.

在下一部分,我们将演示自定义指令如何正向影响 Copilot 在 PR 中给出的审查评论。

2. 自动审核以改进样式规范和性能

当自动 Copilot 代码评审 启用时,Copilot 会在拉取请求从草稿状态移出后自动进行审查。

假设你提交一个拉取请求,其中包含以下函数来更新订单处理系统中的库存。

def notify_inventory(product_id, quantity):
    requests.post("http://inventory-service/update", json={"product_id": product_id, "quantity": quantity})

虽然这可以正常运行,但它缺乏清晰性和稳健性。 类型的意图是隐式的,没有文档字符串,它不包括错误处理或日志记录,这使得它不清楚通知是否实际工作。

Copilot 将查看代码,并可能提出以下注释和代码建议。

注意

以下响应是示例。 副驾驶聊天 的回答是不确定的,因此你可能会得到与这里所显示的不同的回答。

Missing error handling for network calls

The notify_inventory function makes a synchronous network call without any error handling for timeouts, connection failures, or non-200 responses.

Why this matters:

- Network failures will cause unhandled exceptions and crash the order processing flow
- Orders could be marked as CONFIRMED but inventory never gets updated
- This violates the requirement to "handle timeouts and network errors gracefully"
- Failures won't be logged with enough detail for debugging

Recommendation: Add proper error handling with timeout and logging:
def notify_inventory(product_id: str, quantity: int) -> bool:
    """Notify the inventory service of order placement.

    Args:
        product_id: The product identifier.
        quantity: The quantity ordered.

    Returns:
        True if the notification succeeded; False otherwise.
    """
    try:
        response = requests.post(
            "http://inventory-service/update",
            json={"product_id": product_id, "quantity": quantity},
            timeout=5,
        )
        response.raise_for_status()
        logger.info(
            "Inventory notified for product %s, quantity %d (status %d)",
            product_id,
            quantity,
            response.status_code,
        )
        return True
    except requests.exceptions.Timeout:
        logger.error(
            "Timeout notifying inventory for product %s, quantity %d",
            product_id,
            quantity,
            exc_info=True,
        )
    except requests.exceptions.RequestException:
        logger.error(
            "Failed to notify inventory for product %s, quantity %d",
            product_id,
            quantity,
            exc_info=True,
        )
    return False

Copilot 的响应遵循你在自定义指令中提供的指导原则。 在此示例中,它遵循适用于Python的 PEP 8 和 257 样式指南,并建议改进以更好地处理超时和错误日志记录,同时简明地解释建议背后的推理。

注意

在接受和提交之前,请始终仔细查看 Copilot 的建议。

在编码时,自动审查评论可以帮助你更好地理解;在审阅时,它们能帮助你专注于对他人的反馈并缩小其范围。

3. 标记安全漏洞并修复它们

接下来,假设你的任务是改进密码存储在订单处理系统中的方式。 可使用认为足以对用户密码进行哈希处理以便保护用户密码的代码提交拉取请求。

def get_password_hash(password: str, salt: str) -> str:
    """Hash a password with the given salt using SHA-256.

    Returns the hexadecimal representation of the hashed password.
    """
    return hashlib.sha256((password + salt).encode()).hexdigest()

class User:
    """Represents a user in the order processing system."""

    def __init__(self, username: str, password: str, salt: str):
        """Initialize a User with username, password, and salt.

        The password is hashed and stored for authentication.
        """
        self.username = username
        self.salt = salt
        self.password_hash = get_password_hash(password, self.salt)

    def verify_password(self, password: str) -> bool:
        """Verify a plain-text password against the stored hash."""
        return get_password_hash(password, self.salt) == self.password_hash

但是,在此示例中,使用 SHA-256 是不可接受的,因为它的计算成本不足以保护用户密码。

虽然 Copilot 代码评审 可以提出安全最佳实践建议,但针对 Copilot自动修复 的 code scanning 方案更进一步。 通过利用code scanning的能力结合CodeQL分析来分析GitHub存储库中的代码并查找安全漏洞和编码错误,Copilot自动修复然后可以对扫描结果提出修复建议,从而更有效地预防和减少漏洞。

例如, Copilot自动修复 可以对代码进行以下注释。

Using SHA-256 for password hashing is insecure for authentication systems. SHA-256 is designed to be fast, making it vulnerable to brute-force attacks. 

To fix the problem, use a password-specific hashing algorithm like bcrypt, scrypt, or argon2 (e.g., `argon2-cffi` from the PyPI package) which are designed to be slow and include built-in salting mechanisms.

Copilot自动修复 还将针对漏洞进行潜在修复的代码建议供你查看。 在这种情况下,它可能会提出代码建议(如下所示)导入包并更新与哈希密码相关的代码。

from argon2 import PasswordHasher
def get_initial_hash(password: str):
    ph = PasswordHasher()
    return ph.hash(password)

def check_password(password: str, known_hash):
    ph = PasswordHasher()
    return ph.verify(known_hash, password)

注意

  • 在接受 Copilot 提议的任何更改之前,请始终核实并确认。
  • 在此示例中, Copilot 代码评审 还可以突出显示生成唯一盐的必要性。

如你所看到的,自动识别漏洞以及修复漏洞的建议有助于确保安全成为优先事项。 Copilot自动修复 使你能够专注于了解安全编码以及最适合代码库和项目的修补程序。

4. 添加可靠性、可维护性和覆盖范围检查

到目前为止,Copilot 代码评审 已就样式和设计方面针对每个拉取请求提供反馈,而用于 Copilot自动修复 的 code scanning 已标记并修复了安全漏洞。 为了关注代码的长期健康,GitHub Code Quality 增加了可靠性、可维护性和代码覆盖率检查。 它将针对明确定义的反模式进行确定性的、基于规则的 CodeQL 分析,与由 Copilot 提供支持、用于识别现有规则未覆盖问题的分析结合起来,因此这两种方法在每次变更中都能相辅相成。

启用 Code Quality 后,它会将可靠性和可维护性问题以拉取请求中的内联评论形式发布,每条评论都附带一个由 Copilot 提供支持的一键自动修复,可直接应用。 它还报告覆盖率指标,这些指标显示与默认分支相比,更改是维护还是减少测试套件报告的代码覆盖率。 如果要强制实施这些标准,规则集可能需要解析基于规则的发现,并在合并之前满足覆盖阈值。

有关详细信息,请参阅“GitHub 代码质量”。

使用 Copilot 优化了评论

自动审阅注释可帮助你优化评论并更有效地保护代码,而不管你的体验级别如何。

  • 自定义说明帮助优化Copilot 代码评审的响应,使其更符合我们的项目和用户需求。我们还了解到如何定制Copilot在反馈中提供的解释程度。
  • Copilot 代码评审 帮助我们快速改进错误日志记录,并了解为什么很重要。
  •           针对 Copilot自动修复 的 code scanning 方案帮助我们避免使用不充分的密码哈希方式,并保护用户数据。
    
  • GitHub Code Quality 会标记可靠性和可维护性问题,并在拉取请求中报告代码覆盖率;借助规则集,我们可以要求这些问题在合并前得到解决,并达到代码覆盖率阈值。

后续步骤

若要使用 Copilot 的评审功能提高评论的效率和有效性,请按照以下步骤开始操作。

  1. 自定义说明的创建应结合项目和代码库的具体要求。 自行编写,或从我们的示例库中获取灵感。 请参阅“自定义说明”。
  2. 若要为存储库启用自动 Copilot 代码评审 ,请参阅 通过GitHub Copilot配置自动代码评审
  3. 若要为存储库配置 Copilot自动修复 ,需要启用 code scanning。 一旦code scanning启用CodeQL分析,Copilot自动修复就默认启用。 有关最简单的设置,请参阅 配置代码扫描的默认设置
  4. 若要向拉取请求添加可靠性、可维护性和覆盖范围检查,请为存储库启用 GitHub Code Quality 。 请参阅“启用 GitHub Code Quality”。

延伸阅读

若要更深入地查看 AI 生成的代码,请参阅 查看 AI 生成的代码