PerspectiveGraph

遵循以下最佳实践的项目将能够自愿的自我认证,并显示他们已经实现了核心基础设施计划(OpenSSF)徽章。

没有一套可以保证软件永远不会有缺陷或漏洞的做法;如果规范或假设是错误的,即使合适的方法也可能失败。也没有哪些做法可以保证一个项目能够维持健康和运作良好的开发者社区。但是,遵循最佳做法可以帮助改善项目的成果。例如,一些做法可以在发布之前进行多人评估,这可以帮助您找到其他难以找到的技术漏洞,并帮助建立信任,并希望不同公司的开发人员之间进行重复的交互。要获得徽章,必须满足所有“必须”和“禁止”的条款,满足所有“应该”条款或有合适的理由,所有“建议”条款必须满足或未满足(至少希望考虑)。欢迎通过 GitHub网站创建问题或提出请求进行反馈。另外还有一个一般讨论邮件列表

如果这是您的项目,请在您的项目页面上显示您的徽章状态!徽章状态如下所示: 项目13828的徽章级别为passing 这里是如何嵌入它:
您可以通过将其嵌入在您的Markdown文件中:
[![OpenSSF Best Practices](https://www.bestpractices.dev/projects/13828/badge)](https://www.bestpractices.dev/projects/13828)
或将其嵌入到HTML中来显示您的徽章状态:
<a href="https://www.bestpractices.dev/projects/13828"><img src="https://www.bestpractices.dev/projects/13828/badge"></a>


这些是通过级别条款。您还可以查看白银黄金级别条款。

Baseline Series: 基准等级1 基准等级2 基准等级3

        

 基本 13/13

  • 常规

    请注意,其他项目可能使用相同的名称。

    Finds the reachable paths from internet exposure, through excessive privilege, to a sensitive asset, by correlating the scanners you already run into one live graph of your environment. Flags them in the pull request that opens them and ships the fix as a PR. Open source, Apache-2.0.

    请使用 SPDX许可证表达格式;例子包括“Apache-2.0”,“BSD-2-Clause”,“BSD-3-Clause”,“GPL-2.0+”,“LGPL-3.0 +”,“MIT”和“(BSD-2-Clause OR Ruby)”。
    如果有多种语言,请将它们列为逗号分隔值(可选空格),并将它们从最多到最少使用。如果有长列表,请至少列出前三个最常见的列表。如果没有语言(例如,这是仅文档或仅测试项目),请使用单个字符“ - ”。请使用每种语言的常规大小写,例如“JavaScript”。
    通用平台枚举(CPE)是用于信息技术系统,软件和软件包的结构化命名方案。在报告漏洞时,它可用于多个系统和数据库。
  • 基本项目网站内容


    项目网站必须简明扼要地描述软件的作用(它解决了什么问题?)。 [description_good]
    必须采用潜在用户可以理解的语言(例如,它使用最少的术语/行话)。

    The README opens by stating the problem the software solves and how, before any feature list: security tools report what they found and almost never what they know nothing about, and a false negative is invisible — nobody opens a ticket for an attack path they were never shown. PerspectiveGraph correlates the output of the scanners a team already runs into a single graph of the environment and reports the few routes that lead from the internet to critical assets, turning the pull request that opens one red and offering the fix as a pull request of its own.

    https://github.com/luiacuaniello/perspectivegraph#readme



    项目网站必须提供有关如何获取和提供反馈(错误报告或增强功能)以及如何贡献的信息。 [interact]

    The README covers all three:

    Obtain: signed release binaries for linux/macOS/Windows, signed multi-arch container images on GHCR, and make demo to run the whole stack locally — https://github.com/luiacuaniello/perspectivegraph#see-the-whole-engine-in-90-seconds
    Feedback: GitHub Issues for bugs and enhancements; security reports go through a separate private channel — https://github.com/luiacuaniello/perspectivegraph/issues and https://github.com/luiacuaniello/perspectivegraph/blob/main/SECURITY.md
    Contribute: CONTRIBUTING.md, linked from the README, plus issues labelled "good first issue" — https://github.com/luiacuaniello/perspectivegraph/blob/main/CONTRIBUTING.md



    关于如何贡献的信息必须解释贡献流程(例如,是否使用拉请求?) (需要网址) [contribution]
    除非另有说明,否则我们假定 GitHub上的项目使用问题列表(Issues)和拉(Pull)请求。这些信息可以简短,例如,说明项目使用拉请求,问题跟踪器或邮寄到邮件列表中的哪一个。

    关于如何贡献的信息应包括对可接受的贡献的要求(例如,引用任何所需的编码标准)。 (需要网址) [contribution_requirements]

    CONTRIBUTING.md has a "Conventions" section stating the requirements explicitly: Go code must be gofmt, go vet and gosec clean, with an inline justification for any unavoidable gosec finding rather than a blanket exclude; new logic needs tests, and parsers need a fuzz test; new dependencies must be pure-Go. Frontend changes must pass tsc, build and vitest, use the inline SVG icon set rather than emoji, and take colours from the CSS design tokens. Dependency updates must go through make lockfile. Every user-facing change must update the docs, .env.example and the Postman collection. A preceding section lists the exact CI commands to run locally before opening a pull request.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/CONTRIBUTING.md#conventions


  • FLOSS许可证


    项目生产的软件必须作为FLOSS发布。 [floss_license]
    FLOSS是以符合开源定义免费软件定义。此类许可证的示例包括 CC0 MIT BSD 2条款 BSD 3条款修订版 Apache 2.0 Lesser GNU通用公共许可证(LGPL),以及 GNU通用公共许可证(GPL)。为了我们的目的,这意味着许可证必须是:该软件也可以用其他许可证(例如,“GPLv2或专有”是可以接受的)。

    The Apache-2.0 license is approved by the Open Source Initiative (OSI).



    建议由项目生成的软件的任何必需的许可证是由开放源码促进会(OSI)批准的许可证(英文)[floss_license_osi]
    OSI (开放源代码促进会)使用严格的审批流程来确定哪些许可证是开源软件(OSS)。

    The Apache-2.0 license is approved by the Open Source Initiative (OSI).



    项目必须将其许可证在其源代码存储库中的标准位置发布。 (需要网址) [license_location]
    一种约定是将许可证发布为名为LICENSE或COPYING的顶级文件,其后可以带有扩展名,例如“ .txt”或“ .md”。另一种约定是使用一个名为LICENSES的目录,其中包含许可证文件。这些文件通常被命名为其SPDX许可证标识符,后跟适当的文件扩展名,如REUSE Specification中所述。请注意,此标准只是源存储库上的要求。从源代码生成某些内容(例如可执行文件,程序包或容器)时,无需包括许可证文件。例如,在为综合R存档网络(CRAN)生成R软件包时,请遵循标准CRAN惯例:如果许可证是标准许可证,请使用标准简短许可证规范(以避免安装另一文本副本)并列出排除文件(例如.Rbuildignore)中的LICENSE文件。同样,在创建Debian软件包时,您可以在版权文件中放置一个指向/ usr / share / common-licenses中的许可证文本的链接,并从创建的软件包中排除许可证文件(例如,通过在调用dh_auto_install之后删除文件) )。我们鼓励在可行的情况下以生成的格式包含机器可读的许可证信息。

    Non-trivial license location file in repository: https://github.com/luiacuaniello/perspectivegraph/blob/main/LICENSE.


  • 文档


    项目必须为项目生成的软件提供基本文档。 [documentation_basics]
    该文档必须在某些媒体(例如文本或视频)中,包括:如何安装它,如何启动它,如何使用它(可能使用教程使用示例)以及如何安全地使用它(例如,做什么和不做什么),如果这是软件的一个适当的话题。安全文档不需要太长篇幅。项目可以使用非项目内容的超文本链接作为文档。如果项目不生产软件,请选择“不适用”(N/A)。

    Some documentation basics file contents found.



    项目必须提供描述项目生成的软件的外部接口(输入和输出)的参考文档。 [documentation_interface]
    外部接口的文档向最终用户或开发人员解释如何使用它。这将包括其应用程序接口(API),如果软件有。如果它是一个库,记录可以调用的主要类/类型和方法/函数。如果是Web应用程序,定义其URL接口(通常是其REST接口)。如果是命令行界面,请记录其支持的参数和选项。在许多情况下,最好是自动生成大部分文档,以便本文档随着软件的更改而保持同步,但这并不是必需的。项目可以使用非项目材料的超文本链接作为文档。文档可以自动生成(实际上这通常是最好的方法)。可以使用Swagger / OpenAPI生成REST接口的文档。代码界面文档可以使用 JSDoc (JavaScript), ESDoc (JavaScript),pydoc(Python)和Doxygen(很多)。仅在实现代码中添加注释不足以满足本条款;在没有阅读所有源代码的情况下,需要一个简单的方法来查看信息。如果项目不生产软件,请选择“不适用”(N/A)。

    The external interface is documented in four complementary places:

    GraphQL API: the full schema is frozen in the repository and guarded by a snapshot test that fails the build on any undeclared change — https://github.com/luiacuaniello/perspectivegraph/blob/main/docs/api/schema.graphql
    Compatibility contract: what is stable, what may change, and what a version bump means — https://github.com/luiacuaniello/perspectivegraph/blob/main/docs/API-STABILITY.md
    Ingest event contract and REST endpoints: documented in the manual, with every endpoint exercised by an importable Postman collection (55 requests) — https://github.com/luiacuaniello/perspectivegraph/blob/main/docs/MANUAL.md and https://github.com/luiacuaniello/perspectivegraph/blob/main/docs/perspectivegraph.postman_collection.json
    Configuration: every environment variable, with semantics and defaults — https://github.com/luiacuaniello/perspectivegraph/blob/main/.env.example


  • 其他


    项目网站(网站,存储库和下载URL)必须使用TLS支持HTTPS。 [sites_https]
    您可以从Let's Encrypt获取免费证书。项目可以使用(例如) GitHub页面实现此条款, GitLab页面,或 SourceForge项目页面。如果您使用具有自定义域的GitHub页面,则可以使用内容传送网络(CDN)作为代理来支持HTTPS,例如博客文章“使用CloudFlare安全加速GitHub页面”,以满足此条款。如果您支持HTTP,我们敦促您将HTTP流量重定向到HTTPS。

    Given only https: URLs.



    该项目必须有一个或多个讨论机制(包括建议的更改和问题),可搜索,允许通过URL访问消息和主题,使新人能够参与一些讨论,并且不需要客户端安装专有软件。 [discussion]
    可接受机制的示例包括归档邮件列表,GitHub问题和拉请求讨论,Bugzilla,Mantis和Trac。如果满足这些标准,异步讨论机制(如IRC)是可以接受的;确保有一个URL可访问归档机制。允许专有JavaScript,但不鼓励。

    GitHub supports discussions on issues and pull requests.



    项目应该提供英文文档,并能够接受英文的代码的错误报告和评论。 [english]
    英语是计算机技术的通用语言;支持英语增加了全球不同潜在开发者和检视者的数量。即使核心开发人员的主要语言不是英文,项目也可以达到这个标准。


    必须维护该项目。 [maintained]
    至少,项目应尝试响应重大问题和漏洞报告。可能正在维护一个积极追求徽章的项目。所有项目和人员的资源都有限,典型项目必须拒绝某些提议的更改,因此有限的资源和提议拒绝本身并不表示未维护的项目。

    当项目知道将不再维护该项目时,应将此标准设置为“未满足”,并使用适当的机制向其他人指示该项目将不会得到维护。例如,使用“ DEPRECATED”作为其自述文件的第一个标题,在其主页开头附近添加“ DEPRECATED”,在其代码存储库项目说明的开头添加“ DEPRECATED”,在其中添加无需维护的标志其自述文件和/或主页,在任何软件包存储库中将其标记为已弃用(例如npm deprecate ),和/或使用代码存储库的标记系统对其进行归档(例如GitHub的“ archive”设置,GitLab的“ archived”标记, Gerrit的“只读”状态,或SourceForge的“已放弃”项目状态)。可以在这里找到更多讨论。

    The project is actively maintained: 136 commits in the last 90 days and 15 releases, the most recent being v1.2.0. Releases are automated with release-please and every one carries a changelog entry. Issues and pull requests are handled by the maintainer.

    https://github.com/luiacuaniello/perspectivegraph/commits/main
    https://github.com/luiacuaniello/perspectivegraph/releases


 变更控制 9/9

  • 公开的版本控制的源代码存储库


    该项目必须有一个版本控制的源代码存储库。它必须是公开可读的并可通过URL访问。 [repo_public]
    该URL可以与项目URL相同。该项目可能在特定情况下使用私人(非公开)分支,而更改不会公开发布(例如,在向公众披露漏洞之前修复漏洞)。

    Repository on GitHub, which provides public git repositories with URLs.



    项目的源代码存储库必须跟踪所做的更改,谁进行了更改,何时进行了更改。 [repo_track]

    Repository on GitHub, which uses git. git can track the changes, who made them, and when they were made.



    为了实现协作检视,项目的源代码存储库必须包括临时版本,以便检视版本之间的变化;它不得仅包括最终版本。 [repo_interim]
    项目可以选择从其公共源代码库中删除特定的临时版本(例如,修复特定的未公开安全漏洞,可能永远不会公开发布的内容,或者包括不能合法发布而且不是最终版本的内容)。

    The repository contains the full development history, not release snapshots: 136 commits on main, of which only 14 are the automated release commits - so 122 are interim work available for review between releases. Changes land through pull requests that run the full CI suite (build, vet, tests, race detector, staticcheck, gosec, govulncheck, CodeQL, Trivy, fuzzing and an 80% coverage gate) before merge.

    https://github.com/luiacuaniello/perspectivegraph/commits/main
    https://github.com/luiacuaniello/perspectivegraph/pulls?q=is%3Apr+is%3Aclosed



    建议使用通用分布式版本控制软件(例如,git)作为项目的源代码存储库。 [repo_distributed]
    Git不是必须,项目在合适场景可以使用集中版本控制软件(如subversion)。

    Repository on GitHub, which uses git. git is distributed.


  • 唯一版本编号


    项目生成的用于每个用户使用的版本必须具有唯一版本标识符。 [version_unique]
    本条款可以通过各种方式来满足,包括提交ID(例如git提交ID或者Mercurial 更改列表id)或版本号(包括使用语义版本或基于日期的方案,如YYYYMMDD的版本号)。

    Every release has a unique version identifier. 16 git tags, all of the form vX.Y.Z, with no duplicates. Versions are produced by release-please from Conventional Commits, so a version is never reused or hand-assigned, and the same identifier appears on the git tag, the GitHub release, the release binaries, the container image tags on GHCR, and the version markers in the README.

    https://github.com/luiacuaniello/perspectivegraph/tags



    建议使用语义版本控制(SemVer)格式进行发布。 [version_semver]
    其他版本编号方案,如提交ID(例如git commit id或mercurial changeset id)或基于日期的方案,如YYYYMMDD,可以用作版本号,因为它们是唯一的。一些备选方案可能会导致问题,因为用户可能无法轻松确定是否是最新的。如果所有目标客户仅运行最新版本,则SemVer可能不太有助于识别软件版本(例如,它是通过持续交付不断更新的单个网站或互联网服务的代码)。


    建议项目识别其版本控制系统中的每个版本。例如,建议使用git的项目,使用git标签识别每个版本。 [version_tags]

    Every release is identified in version control by a git tag of the form vX.Y.Z, created automatically by release-please when the release pull request is merged. 16 tags to date, matching the 15 published GitHub releases one to one.

    https://github.com/luiacuaniello/perspectivegraph/tags


  • 发行说明


    该项目必须在每个版本中提供发布说明,这是该版本中主要变化的可读的摘要,以帮助用户确定是否应升级,升级影响将如何。发行说明不能是版本控制日志的原始输出(例如,“git log”命令结果不是发行说明)。其产出不适用于多个地点的项目(如单个网站或服务的软件),并采用持续交付,可以选择“N/A”。 (需要网址) [release_notes]
    发行说明可以以各种方式实施。许多项目将它们添加到名为“NEWS”,“CHANGELOG”或“ChangeLog”的文件中,可选的包含“.txt”,“.md”或“.html”等扩展名。历史上,术语“更改日志”是指每个更改的日志,但为了满足这些条款,需要的是可读取的摘要。发行说明可以由版本控制系统机制提供,例如 GitHub发布工作流程

    Non-trivial release notes file in repository: https://github.com/luiacuaniello/perspectivegraph/blob/main/CHANGELOG.md.



    发行说明必须列出每个新版本中修复的每个公开的漏洞。如果没有发行说明或者没有公开的漏洞,选择“不适用”。 [release_notes_vulns]
    如果用户通常不能在自己的计算机上实际更新软件,而必须依靠中间人来执行升级(对于内核和与内核交织的底层软件通常是这种情况),项目可以选择“不适用”(N/A)。

    N/A: no publicly known vulnerability with a CVE assignment has ever affected this project's own code. Every release carries generated release notes (release-please, from Conventional Commits) and a CHANGELOG entry, so the mechanism to record such a fix exists and will be used if one is ever assigned. Security reporting goes through a private channel documented in SECURITY.md, and no advisory has been published against the repository.

    https://github.com/luiacuaniello/perspectivegraph/releases
    https://github.com/luiacuaniello/perspectivegraph/security/advisories


 报告 8/8

  • 错误报告流程


    项目必须为用户提交错误报告(例如,使用问题跟踪器或邮件列表)提供相关流程。 (需要网址) [report_process]

    Non-trivial SECURITY[.md] file found file in repository: https://github.com/luiacuaniello/perspectivegraph/blob/main/SECURITY.md. [osps_do_02_01]



    项目必须使用问题跟踪器来跟踪每个问题。 [report_tracker]

    GitHub Issues is enabled and is the tracker for individual issues, with labels used to mark entry points for new contributors ("good first issue"). Pull requests are tracked in the same place and every one runs the full CI suite before merge.

    https://github.com/luiacuaniello/perspectivegraph/issues



    该项目必须响应过去2-12个月内(含)提交的大多数错误报告;响应不需要包括修复。 [report_responses]

    No bug report has been submitted by anyone other than the maintainer in the period. The five open issues were all opened by the maintainer as scoped tasks for new contributors, so there is no backlog of unacknowledged external reports. The project went public very recently; the tracker is open and monitored.



    该项目应该对过去2-12个月内(包括)的大部分(> 50%)的增强请求作出回应。 [enhancement_responses]
    答复可能是“不”或有关其价值的讨论。目的只是对某些请求有一些回应,这表明项目还活着。为了该条款的目的,项目不需要计数无效请求(例如,来自垃圾邮件发送者或自动系统)。如果项目不再进行增强,请选择“未满足”,并将介绍此情况的URL包含在内。如果一个项目有超出处理能力的增强需求数量,请选择“未满足”并解释。

    Same situation as bug reports: no enhancement request has been submitted by a third party in the period. Planned work is tracked publicly in ROADMAP.md, which states explicitly what is done, what is scaffolded and what has not been started, so the direction is reviewable before anyone asks.

    https://github.com/luiacuaniello/perspectivegraph/issues
    https://github.com/luiacuaniello/perspectivegraph/blob/main/ROADMAP.md



    该项目必须有一个公开的报告和回复的档案供后续搜索。 (需要网址) [report_archive]

    GitHub Issues is the public, searchable archive of reports and responses; it is open to anyone without an account for reading, and every issue keeps its full comment history. Pull request discussions are archived in the same place, and each release links the commits it contains.

    https://github.com/luiacuaniello/perspectivegraph/issues?q=is%3Aissue


  • 漏洞报告流程


    项目必须在项目网站上发布报告漏洞的流程。 (需要网址) [vulnerability_report_process]
    例如,https://PROJECTSITE/security 上的一个明确指定的邮箱地址,通常以 security@example.org 的形式。这可能与其错误报告流程相同。漏洞报告可能一直是公开的,但是许多项目都有一个私密漏洞报告机制。

    SECURITY.md publishes the process: how to report, what to include, what happens next, and what is in and out of scope. It states the preferred private channel and a fallback if private reporting is unavailable, and describes how the reporter is credited in the advisory and release notes unless they prefer anonymity. It is linked from the README and surfaced by GitHub in the repository's Security tab.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/SECURITY.md



    如果支持私有漏洞报告,项目必须包括如何以保密的方式发送信息。 (需要网址) [vulnerability_report_private]
    示例包括使用HTTPS(TLS)或使用OpenPGP加密的电子邮件在网络上提交的私密缺陷报告。如果漏洞报告总是公开的(从来没有私密漏洞报告),请选择“不适用”(N/A)。

    Private reporting is supported and is the preferred route. GitHub private vulnerability reporting is enabled on the repository (verified: the API reports "enabled": true), so a reporter uses Security → Report a vulnerability and the report stays private to the maintainers until a fix is published. SECURITY.md documents this as the first option, with a fallback for cases where it is unavailable: open a minimal public issue containing no details, asking only for a private contact.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/SECURITY.md



    该项目在过去6个月收到的任何漏洞报告的初始响应时间必须小于或等于14天。 [vulnerability_report_response]
    如果过去6个月没有报告漏洞,请选择“不适用”(N/A)。

    N/A: no vulnerability report has been received. The repository has no published or draft security advisories, and no third party has opened an issue. The reporting channel is documented and live (GitHub private vulnerability reporting is enabled on the repository), so reports have somewhere to arrive; none have.

    https://github.com/luiacuaniello/perspectivegraph/security/advisories


 质量 13/13

  • 可工作的构建系统


    如果项目生成的软件需要构建使用,项目必须提供可以从源代码自动重新构建软件的可工作的构建系统。 [build]
    构建系统确定重建软件(以及以什么顺序)需要执行哪些操作,然后执行这些步骤。例如,它可以调用编译器来编译源代码。如果从源代码创建可执行文件,则必须可以修改项目的源代码,然后通过这些修改生成更新的可执行文件。如果项目生成的软件取决于外部库,则构建系统不必构建那些外部库。如果在修改源代码之后不需要构建任何使用该软件的软件,请选择“不适用”(N/A)。

    建议使用通用工具来构建软件。 [build_common_tools]
    例如,Maven,Ant,cmake,自动工具,make,rake(Ruby)或devtools (R)。

    该项目应该仅使用FLOSS工具来构建。 [build_floss_tools]

    The entire toolchain is FLOSS: Go (BSD-3-Clause), Node/npm (MIT), Make, Docker/BuildKit (Apache-2.0), Helm (Apache-2.0), and for the release path cosign, syft and Trivy (all Apache-2.0). Nothing proprietary is required to build, test or release. CGO_ENABLED=0 keeps the build free of a system C toolchain as well.


  • 自动测试套件


    该项目必须使用至少一个作为FLOSS公开发布的自动测试套件(该测试套件可以作为单独的FLOSS项目维护)。 [test]
    该项目可以使用多个自动测试套件(例如,一个是快速运行的测试套件,而另一个更为彻底但需要特殊设备)。

    Two automated suites, both FLOSS: Go's standard testing package (BSD-3-Clause) for the backend, and Vitest (MIT) for the dashboard. How to run them is documented in CONTRIBUTING.md and wired into the Makefile (make test), and CI runs both on every push.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/CONTRIBUTING.md#dev-loop
    https://github.com/luiacuaniello/perspectivegraph/blob/main/Makefile



    测试套件应该以该语言的标准方式进行调用。 [test_invocation]
    例如“make check”,“mvn test”或“rake test”。

    go test ./... for the backend and npm test for the frontend — the standard invocation for each language, with no custom harness. make test runs the backend suite for convenience.



    建议测试套件覆盖大部分(或理想情况下所有)代码分支,输入字段和功能。 [test_most]

    Statement coverage on the engine (internal/ and pkg/) is 81.1%, enforced by a CI gate that fails below 80% and uses cross-package attribution so a package tested through another still gets credit. 533 tests across 56 packages. Beyond unit tests: 11 Go fuzz targets against the ingest parsers, a deterministic hostile-input battery (11 collectors × 23 payloads) that runs on every build, -race across all packages, an integration suite against a real Apache AGE database, and a CloudGoat benchmark that measures the path-finding engine's precision and recall against declared ground truth.

    Not covered: cmd/ sits at ~1% by design — it is process wiring, and the security-relevant parts of it (the production, auth and secret startup gates) are extracted into pure functions that are tested.



    建议项目实施持续集成,将新的或更改的代码经常集成到中央代码库中,并对结果进行自动化测试。 [test_continuous_integration]

    Every push and pull request runs build, go vet, tests, -race, staticcheck, gosec, govulncheck, the coverage gate, the frontend build/lint/test/audit, an Apache AGE integration job, container image scanning with Trivy, CodeQL, gitleaks and OpenSSF Scorecard. Fuzzing runs as its own workflow. Releases are automated end to end: release-please cuts the version, then binaries and multi-arch images are built, signed with cosign, and attested with an SBOM and SLSA provenance.

    https://github.com/luiacuaniello/perspectivegraph/actions


  • 新功能测试


    该项目必须有通用的策略(正式或非正式),当主要的新功能被添加到项目生成的软件中,该功能的测试应该同时添加到自动测试套件。 [test_policy]
    只要有相应的策略,即使是通过口头传播,也就是说开发人员应该为主要的新功能在自动化测试套件中添加测试,选择“Met”。

    CONTRIBUTING.md states it under "Conventions": "Tests (and a fuzz test for parsers) for new logic." The policy is enforced mechanically as well as socially — a coverage gate fails the build below 80% on internal/ and pkg/, so new logic without tests moves the number down and blocks the merge.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/CONTRIBUTING.md#conventions



    该项目必须有证据表明,在项目生成的软件的最近重大变化中,已经遵守了添加测试的条款: test_policy [tests_are_added]
    主要功能通常在发行说明中提及。不需要完美,只需证明,当新的主要功能添加到项目生成的软件时,测试通常会在实践中被添加到自动化测试套件中。

    Recent major changes each shipped with their tests, visible in the commit history. Examples: request correlation added internal/reqid with 8 tests including hostile-input cases; the file-based secret support added 8 tests plus 3 for the startup gate that refuses an unreadable secret; moving /metrics to its own listener added tests for both halves of the mux decision and for the configuration plumbing; the GraphQL cost guard added 6 tests, one of which reproduces a 1.2 KB document that previously took the guard over ten seconds to measure. The suite is 533 tests across 56 packages.

    https://github.com/luiacuaniello/perspectivegraph/commits/main



    建议您在更改提案的说明文档中添加测试策略要求(请参阅test_policy)。 [tests_documented_added]
    但是,只要在实践中添加了测试,即使是非正式规则也是可以接受的。

    The policy is in CONTRIBUTING.md, which is the instructions for change proposals, in the "Conventions" section alongside the exact CI commands to run locally before opening a pull request. The pull request template is in .github/PULL_REQUEST_TEMPLATE.md.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/CONTRIBUTING.md#conventions


  • 警告标志


    该项目必须启用一个或多个编译器警告标志,“安全”语言模式,或者使用单独的“linter”工具查找代码质量错误或常见的简单错误,如果至少有一个FLOSS工具可以在所选择的语言实现此条款。 [warnings]
    编译器警告标志的例子包括gcc/clang “-Wall”。 “安全”语言模式的示例包括JavaScript “use strict”和perl5的“使用警告”。一个单独的“linter”工具用于检查源代码以查找代码质量错误或常见的简单错误。这些通常在源代码或构建指令中启用。

    Go: go vet on every build, plus staticcheck (which on introduction found real defects vet does not see), gosec for security patterns and govulncheck for vulnerable dependencies. Frontend: ESLint and the TypeScript compiler (tsc -b). All run in CI on every push and pull request.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/.github/workflows/ci.yml



    该项目必须处理警告。 [warnings_fixed]
    告警是通过执行warnings条款确定的。该项目应该修复告警或在源代码中将其标记为误报。理想情况下,不会有告警,但项目可能会接受一些告警(通常每100行小于1个告警,或整体少于10个告警)。

    Zero tolerance on both sides. Go is gated by vet, staticcheck and gosec; the frontend runs eslint . --max-warnings=0, so a warning fails the build exactly as an error does. Two suppressions exist, both scoped to the line or file where the decision was made and both carrying the reason inline: a rule false positive on factory-produced icon components, and a deliberate state reset inside a debounced effect whose cleared values are not in the effect's dependencies.



    建议在实际情况下,项目以最严格方式对待项目生成的软件中的告警。 [warnings_strict]
    某些项目无法有效启用某些警告。需要证明的是,项目正在努力的启用警告标志,以便早期发现错误。

    Maximally strict on both sides: no warning of any kind is tolerated in CI


 安全 16/16

  • 安全开发知识


    该项目必须至少有一个主要开发人员知道如何设计安全软件。 [know_secure_design]
    这需要了解以下设计原则,包括 Saltzer和Schroeder 中的8项原则:
    • 机制经济(保持设计简单实用,例如采用彻底简化)
    • 故障安全默认(默认情况下,访问决策应拒绝),项目安装应默认安全)
    • 完全仲裁(必须检查每个可能被限制的访问权限,并且不可绕过)
    • 开放式设计(安全机制不应该依赖于攻击者对其设计的无知,而应该更容易地保护和更改信息,例如密钥和密码)
    • 特权分离(理想情况下,对重要对象的访问应该取决于多个条件,从而破坏一个保护系统将无法实现完全访问。如,多因子身份验证,要求密码和硬件令牌,比单因子认证安全性更高)
    • 最小权限(进程应该以最少的权限运行)
    • 最少的公共机制(设计应该最大限度地减少所有用户所依赖的,涉及到多个用户的共同机制,如,临时文件的目录)
    • 心理可接受性(人机接口必须设计为易于使用 —— 设计为“最不惊讶”)
    • 有限的攻击面(攻击面 —— 一组不同的入口,其​​中攻击者可以尝试输入或提取数据 —— 应该受到限制)
    • 输入验证与白名单(输入通常应该在被接受之前检查以确定是否有效;此验证应使用白名单(仅接受已知的有效值),而不是黑名单(尝试列出已知的非法值))。
    项目中的“主要开发人员”的定义是熟悉项目代码的任何人,很乐意对其进行更改,并被项目中大多数其他参与者确认。主要开发人员通常会在过去一年中通过代码,文档或回答问题提供一些贡献。开发人员通常被认为是主要开发人员,如果他们启动项目(并且还没有离开项目满三年),可以选择在私人漏洞报告渠道(如果有的话)上接收信息,可以代表项目接受提交,或执行项目软件的最终版本发布。如果只有一个开发者,那个人是主要开发人员。

    The maintainer's professional field is cybersecurity software engineering, and the design record is public rather than asserted. The project's threat model enumerates trust boundaries and assets, then walks each surface with STRIDE, recording both the control and the residual risk — including cases where the residual is uncomfortable, such as an in-memory brute-force lockout that a restart clears.

    The design applies least privilege (read-only cloud roles, viewer/admin RBAC, per-tenant isolation), fail-closed defaults (the binary refuses to start with SSO configured but issuer or audience missing, with credentials that parse to nothing, with an unreadable mounted secret, or with a declared production environment and an unreachable database), defence in depth (HMAC on ingest, rate limits with bounded state, query cost limits, a tamper-evident audit log, encryption at rest), and input validation at every trust boundary.



    该项目的主要开发人员中,至少有一个必须知道导致这类型软件漏洞的常见错误类型,以及至少有一种方法来对付或缓解这些漏洞。 [know_common_errors]
    示例(取决于软件的类型)包括SQL注入,操作系统注入,经典缓冲区溢出,跨站点脚本(XSS),缺少认证和缺少授权。请参阅 CWE/SANS 25种最常见漏洞 OWASP十大漏洞类型项目

    Common vulnerability classes are addressed explicitly, each with a countermeasure and a regression test:

    Injection: parameterised queries; a hostile-input battery of 11 collectors × 23 payloads on every build; 11 fuzz targets on the parsers.
    Broken authentication: constant-time token comparison; algorithm allowlist on JWT verification; mandatory issuer and audience, enforced by refusing to start — which closes the confused-deputy case where a token minted for another application sharing the same JWKS would otherwise be accepted.
    Denial of service: body-size caps, per-IP rate limiting with a bounded client table, and GraphQL depth and cost budgets. A fragment-expansion bomb that stalled the guard for over ten seconds was found and fixed by memoisation; the reproduction is a permanent test.
    Log injection: structured logging only, never message interpolation, verified empirically against a forged log line.
    Prompt injection: environment-derived strings are bounded and neutralised before reaching the model, with the hostile inputs kept as a permanent test.
    Supply chain: SHA-pinned Actions, digest-pinned base images, govulncheck, Trivy, CodeQL, gitleaks, cosign signatures, SBOM and SLSA provenance.


  • 使用基础的良好加密实践

    请注意,某些软件不需要使用加密机制。

    项目生成的软件默认情况下,只能使用由专家公开发布和审查的加密协议和算法(如果使用加密协议和算法)。 [crypto_published]
    这些加密条款并不总是适用,因为某些软件不需要直接使用加密功能。

    Only published, expert-reviewed primitives, all from the Go standard library: AES-GCM (NIST SP 800-38D), Ed25519 (RFC 8032), HMAC (RFC 2104), SHA-2 (FIPS 180-4), TLS 1.2/1.3 (RFC 5246 / RFC 8446), RSA-SSA with SHA-2 for JWT verification (RFC 7518), and PKCE S256 (RFC 7636). Nothing bespoke.



    如果项目生成的软件是应用程序或库,其主要目的不是实现加密,那么它应该只调用专门设计实现加密功能的软件,而不应该重新实现自己的。 [crypto_call]

    The project implements no cryptography. Every primitive is called from the Go standard library — crypto/aes, crypto/cipher, crypto/ed25519, crypto/hmac, crypto/sha256, crypto/rand, crypto/tls — and JWT verification uses the widely reviewed golang-jwt/jwt/v5, restricted to an explicit allowlist of signing methods so algorithm confusion is impossible. The one place the project writes protocol code by hand is the PKCE challenge, and that too calls crypto.subtle.digest("SHA-256") rather than implementing a hash.



    项目所产生的软件中,所有依赖于密码学的功能必须使用FLOSS实现。 [crypto_floss]

    All cryptography-dependent functionality runs on the Go standard library (BSD-3-Clause), golang-jwt/jwt/v5 (MIT), and the Web Crypto API in the browser. Verification tooling - cosign, syft, Trivy - is Apache-2.0. There is no proprietary or export-restricted component anywhere in the cryptographic path.



    项目生成的软件中的安全机制使用的默认密钥长度必须至少达到2030年(如2012年所述)的NIST最低要求。必须提供配置,以使较小的密钥长度被完全禁用。 [crypto_keylength]
    这些最小位长度是:对称密钥112,因式分解模数2048,离散对数密钥224,离散对数组2048,椭圆曲线224和散列224(密码散列不涉及该位长度),关于密码散列的更多信息可以在 crypto_password_storage 条款)。请参阅 http://www.keylength.com 以比较不同组织的密钥长度建议。在某些配置中,软件可能允许较小的密钥长度(理想情况下不会,因为这允许降级攻击,但是互操作性有时需要较短的密钥长度)。

    Defaults exceed the NIST minimums through 2030 and beyond: AES-256 for encryption at rest, Ed25519 (≈128-bit security) for signatures, SHA-256 for hashing and HMAC, TLS 1.2 as the floor with 1.3 preferred, and RSA JWT verification restricted to RS256/384/512.

    Smaller keylengths cannot be selected at all: the algorithms and sizes are fixed in code with no configuration knob to weaken them, which satisfies the requirement more strongly than making the weakening merely disableable. The one length an operator supplies is the at-rest encryption key, which must be exactly 32 bytes or the process refuses to start.



    项目产生的软件中的默认安全机制不得取决于已被破解的密码算法(例如,MD4,MD5,单DES,RC4,Dual_EC_DRBG)或使用不适合上下文的密码模式(例如,ECB模式几乎不适当,因为它揭示了密文中相同的块,如 ECB企鹅所示。CTR模式通常是不合适的,因为如果重复输入状态,则它不执行认证并导致重复)。 [crypto_working]
    在许多情况下,最好选择设计用于组合保密和认证的块密码算法模式,例如Galois / Counter Mode(GCM)和EAX。项目可以允许用户为必要的兼容性启用已被破解的加密机制,但是需要用户知道他们正在这么做。

    No default security mechanism depends on a broken algorithm. No MD4, MD5, single DES, RC4 or Dual_EC_DRBG appears anywhere, and no CBC-mode construction is used - the at-rest cipher is AES-GCM, an AEAD. The only legacy primitive present is SHA-1, used solely for git-style content-addressed identifiers, never for authentication, integrity or confidentiality, and annotated inline where it appears. No interoperability constraint forces a weak algorithm on this project.



    由项目产生的软件中的默认安全机制不应该依赖于具有已知严重弱点的加密算法或模式(例如,SHA-1密码散列算法或SSH中的CBC模式)。 [crypto_weaknesses]
    CERT:SSH CBC漏洞中讨论了SSH中CBC模式的问题。

    Defaults are modern: AES-256-GCM at rest, Ed25519 for export signatures, HMAC-SHA-256 for ingest authentication, SHA-256 for the audit hash chain, RS256/384/512 for JWT verification against the IdP's JWKS, PKCE with the S256 challenge method, and TLS with MinVersion: TLS 1.2. No MD5, DES, RC4 or CBC-mode construction anywhere.

    One deliberate use of SHA-1 exists and is declared: pkg/ontology/event.go derives content-addressed node identifiers git-style. It is not a security primitive — the digest identifies a node, never authenticates or protects anything — and it is annotated inline (#nosec G505) so the intent is reviewable at the call site rather than hidden in a global exclude.



    项目产生的软件中的安全机制应该​​对密钥协商协议实施完美的前向保密(PFS),如果长期密钥集合中的一个长期密钥在将来泄露,也不能破坏从一组长期密钥导出的会话密钥。 [crypto_pfs]

    The project implements no key agreement of its own: all transport uses Go's standard crypto/tls with MinVersion: TLS 1.2, whose default cipher suite selection is ECDHE-based, and TLS 1.3 - negotiated whenever the peer supports it - provides forward secrecy unconditionally. The same applies to outbound connections (Postgres, NATS, IdP JWKS, LLM providers) and to TLS terminated at an ingress.



    如果项目产生的软件存储用于外部用户认证的密码,则必须使用密钥拉伸(迭代)算法(例如,PBKDF2,Bcrypt或Scrypt)将密码存储为每用户盐值不同的迭代散列 。 [crypto_password_storage]
    此条款仅适用于软件强制使用密码验证用户身份的情况(如服务器端Web应用程序)。在软件存储用于认证到其他系统的密码(例如,该软件实现某个其他系统的客户端)的情况下,这是不适用的,因为该软件的至少某个部分必须经常访问未散列加密的密码。

    The software stores no user passwords. Authentication is either a bearer API token supplied by the operator, or OIDC, where the identity provider holds the credential and the project only verifies signed JWTs against its JWKS.

    For completeness, since a reviewer will find it: a static API token may optionally be configured as sha256$<hex> so only its digest is stored. Plain SHA-256 is correct there and iterated hashing would not be: these are high-entropy random secrets, not user-chosen passwords, so there is no low-entropy guessing space for a work factor to defend. That is the same approach GitHub and Stripe take for API keys.



    由项目生成的软件中的安全机制必须使用密码学安全的随机数生成器生成所有加密密钥和随机数,并且不得使用密码学不安全的生成器。 [crypto_random]
    密码安全的随机数生成器可以是硬件随机数生成器,或者它可以是使用诸如Hash_DRBG,HMAC_DRBG,CTR_DRBG,Yarrow或Fortuna之类的算法的加密安全的伪随机数生成器(CSPRNG)。对安全性随机数生成器的调用示例包括Java的java.security.SecureRandom和JavaScript的window.crypto.getRandomValues。调用不安全随机数生成器的示例包括Java的java.util.Random和JavaScript的Math.random。

    Every security-relevant value comes from crypto/rand: AES-GCM nonces (a fresh random nonce per seal), request identifiers, ticket and validation identifiers, and generated tokens.

    math/rand/v2 appears only where determinism is the requirement and security is not involved: the Monte Carlo risk simulation and the uncertainty sampling, which are seeded deliberately so a before/after comparison reflects the change rather than sampling noise, plus the synthetic load and scenario generators used in testing. Those call sites carry an inline #nosec G404 stating exactly that.


  • 安全交付防御中间人(MITM)的攻击


    该项目必须使用一种针对MITM攻击的传递机制。使用https或ssh + scp是可以接受的。 [delivery_mitm]
    一个更强大的机制是使用数字签名的软件包发布软件,因为这样可以减轻对分发系统的攻击,但只有在用户确信签名的公钥是否正确的情况下才可以确定。用户实际上会检查签名。

    Distribution channels use HTTPS exclusively. [osps_br_03_02]



    不得通过http协议获取加密散列(例如,sha1sum)并直接使用,而不检查密码学签名。 [delivery_unsigned]
    这些散列可以在传输过程中修改。

    Nothing is retrieved over http, and the hash is never trusted on its own. Releases publish SHA256SUMS together with SHA256SUMS.bundle, a cosign keyless signature over that file, so the documented verification order is signature first and checksum second — the README gives the exact command. Container images are signed with cosign and carry an SPDX SBOM and SLSA build provenance. Go dependencies are verified against go.sum and the public checksum database; GitHub Actions are pinned to commit SHAs; base images are pinned by digest; npm uses npm ci against a committed lockfile.

    https://github.com/luiacuaniello/perspectivegraph#check-your-own-account-in-30-seconds


  • 修正公开的漏洞


    被公开了超过60天的中等或更高严重程度的漏洞,必须被修复。 [vulnerabilities_fixed_60_days]
    该漏洞必须由项目本身修补和发布(修补程序可能在其他地方开发)。一旦漏洞具有公开发布的非付费信息的CVE(例如,在国家漏洞数据库)或项目已被通知,且信息已经发布给公众(可能是项目自己发布),则视为漏洞已经公众所知。如果其 CVSS 2.0 基本分数为4或更高,则漏洞是中等到高的严重性。 注意:这意味着全世界的所有攻击者可能会对用户造成长达60天的伤害。这个标准通常比Google在重新启动负责任的披露中所推荐的容易得多。因为Google建议,如果报告不是公开的,那么当项目得到通知,甚至报告尚未公开时,60天的时间段就会开始。

    There are no unpatched vulnerabilities of any severity. No vulnerability has ever been publicly known against this project's own code, and dependencies are gated: govulncheck runs on every build against the Go vulnerability database, Trivy scans the release images, CodeQL performs taint analysis, and Dependabot opens update pull requests which are merged promptly. A finding in any of these fails CI, so an unpatched dependency cannot sit for 60 days — it blocks the next merge.



    项目在得到报告后应该迅速修复所有致命漏洞。 [vulnerabilities_critical_fixed]

    No critical vulnerability has been reported to date. The evidence that the project fixes security defects rapidly comes from its own auditing: a denial of service in the GraphQL cost guard (a 1.2 KB document that stalled the guard for over ten seconds), two unbounded maps reachable pre-authentication, and a production configuration that could start with authentication silently disabled were each found and fixed within the same working session, with regression tests that fail without the fix.


  • 其他安全问题


    公共存储库不得泄漏旨在限制公众访问的有效私人凭证(例如,工作密码或私钥)。 [no_leaked_credentials]
    项目可以泄漏测试和不重要数据库的“样本”凭据,只要它们不旨在限制公共访问。

    gitleaks scans the full history on every build and fails it on a finding; the last scan covered 116 commits with no leaks. .gitignore excludes .env, /secrets/, *.pem, *.key and *.crt. Credentials are never committed: the repository ships .env.example and .env.production.example with empty values, and the software additionally accepts every credential through a <KEY>_FILE path so it need not be written into a file at all.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/.github/workflows/ci.yml


 分析 8/8

  • 静态代码分析


    如果至少有一个FLOSS工具以所选择的语言实现此条款,则至少需要将一个静态代码分析工具应用于软件发布之前任何提议的主要生成版本。 [static_analysis]
    静态代码分析工具检查软件代码(源代码,中间代码或可执行文件),而不用特定输入执行。本条款中,编译器警告和“安全”语言模式不被视为静态代码分析工具(它们通常避免深入分析,因为速度至关重要)。此类静态代码分析工具的示例包括 cppcheck clang静态分析器 FindBugs (包括FindSecurityBugs), PMD Brakeman Coverity质量分析器 HP Fortify静态代码分析器。更多的工具列表可以在诸如维基百科静态代码分析工具列表关于静态代码分析的OWASP信息 NIST源代码安全分析器列表 Wheeler的静态分析工具列表 SWAMP 是使用各种工具评估软件漏洞的免费平台。如果没有可用于所使用的实现语言的FLOSS静态分析工具,请选择“N/A”。

    Six static analysis tools run on every push and pull request, well beyond compiler warnings:

    staticcheck, which on introduction found real defects that go vet does not see
    gosec, security-focused SAST
    CodeQL, semantic taint analysis
    govulncheck, which reports reachable vulnerable code paths rather than merely vulnerable versions
    gitleaks, secret scanning across the full history
    ESLint and tsc for the dashboard
    There is also a repository-specific gate: a test holds every configuration key the backend reads to all three deployment surfaces, so a key that is settable in one place and silently ignored in another fails the build.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/.github/workflows/ci.yml



    建议至少有一个用于static_analysis标准的静态分析工具包括在分析语言或环境中查找常见漏洞的规则或方法。 [static_analysis_common_vulnerabilities]
    专门设计用于寻找常见漏洞的静态分析工具更有可能找到它们。也就是说,使用任何静态工具通常会帮助找到一些问题,所以我们“通过”级别的徽章建议,但不要求这个条款。

    Two of the tools are specifically vulnerability-oriented. gosec carries rules for the common Go classes: command and SQL injection, path traversal, weak cryptography, insecure randomness, unhandled errors. CodeQL performs dataflow taint tracking for the OWASP-style classes, following untrusted input to sensitive sinks across function boundaries. govulncheck goes further than a version comparison, reporting only vulnerabilities whose affected code the binary actually reaches.



    使用静态代码分析发现的所有中,高严重性可利用漏洞必须在确认后及时修复。 [static_analysis_fixed]
    如果其 CVSS 2.0 评分为4或更高,则此漏洞是中等到高的严重性。

    Findings are fixed or justified inline, never suppressed globally. CONTRIBUTING.md forbids blanket excludes, so every suppression is a // #nosec Gxxx -- why it's safe comment at the call site where a reviewer will see it.

    Two concrete cases. gosec raised G703 (path traversal via taint analysis) on the code that reads a mounted secret; it was reviewed, judged a false positive for that context (the path comes from an environment variable, and anyone who can set the process environment already owns it), and annotated with that reasoning rather than excluded. staticcheck raised ST1018 on a literal U+202E character in a test file, a Trojan Source pattern, which was replaced with an escape sequence.

    All six tools currently report zero findings.



    建议每次提交或至少每天执行静态源代码分析。 [static_analysis_often]

    On every commit, not merely daily. staticcheck, gosec, govulncheck, go vet, gitleaks, ESLint and tsc run on every push and every pull request, and a finding fails the build. CodeQL runs on push and pull request and on a weekly schedule, so newly published query packs are applied to unchanged code. Extended fuzzing runs weekly on its own schedule.

    https://github.com/luiacuaniello/perspectivegraph/actions


  • 动态代码分析


    建议在发布之前,至少将一个动态分析工具应用于软件任何发布的主要生产版本。 [dynamic_analysis]
    动态分析工具通过执行特定输入来检查软件。例如,项目可以使用模糊工具(例如, American Fuzzy Lop )或Web应用扫描程序(例如, ZAP w3af )。在某些情况下, OSS-Fuzz 项目可以对您的项目应用模糊测试。为满足此条款,动态分析工具需要以某种方式改变输入,以寻找各种问题,或者将其作为一个具有至少80%分支覆盖率的自动测试套件。 动态分析维基百科页面 OWASP的fuzzing页面 识别一些动态分析工具。分析工具可能专注于寻找安全漏洞,但这不是必需的。

    Three kinds of dynamic analysis run against the software as it executes.

    Fuzzing: 14 Go fuzz targets against the ingest parsers, which are the boundary where attacker-influenceable bytes become graph structure. Their seed corpora execute on every go test, and a dedicated workflow runs extended campaigns weekly (Sunday, with a configurable duration on manual dispatch).

    Race detection: go test -race across all 56 packages on every push. It instruments the running program to catch data races that no static tool sees.

    A hostile-input battery: 11 collectors by 23 payloads (nesting bombs, invalid UTF-8, lone surrogates, 5 MB strings, path traversal, template injection, NUL bytes, bidirectional overrides), driven through the real parsers deterministically on every build. A 10-second per-payload timeout means a parser that can be stalled fails the test.

    All of this runs before every release, since releases are cut from main only after CI is green.

    https://github.com/luiacuaniello/perspectivegraph/blob/main/.github/workflows/fuzz.yml



    建议如果项目生成的软件包含使用内存不安全语言编写的软件(例如C或C++),则至少有一个动态工具(例如,fuzzer或web应用扫描程序)与检测缓冲区覆盖等内存安全问题的机制例行应用。如果该项目生成的软件没有以内存不安全语言编写,请选择“不适用”(N / A)。 [dynamic_analysis_unsafe]
    检测内存安全问题的机制的示例包括AddressSanitizer(ASAN)(可在GCC和LLVM中使用),“Memory Sanitizer” valgrind 。其他可能使用的工具包括ThreadSanitizerUndefinedBehaviorSanitizer。广泛的断言也将起作用。

    The project produces no software in a memory-unsafe language. The backend is Go and the dashboard TypeScript, both memory-safe, and the backend is built with CGO_ENABLED=0 so no C is linked in. That also keeps the release binaries static and portable.

    Fuzzing is nonetheless used extensively (14 targets), because in Go the classes it catches are panics, unbounded allocation and non-termination rather than buffer overwrites.



    建议由项目生成的软件包括许多运行时断言,在动态分析期间检查。 [dynamic_analysis_enable_assertions]
    这个标准并不建议使生产过程中的断言;这完全取决于项目及其用户的决定。该标准的重点是部署之前的动态分析过程中改善故障检测。在生产使用中启用断言与在动态分析(例如测试)期间启用断言完全不同。在某些情况下,在生产中使用断言是极其不明智的(尤其是在高完整性组件中)。存在许多反对在生产环境中启用断言的论点,例如,库不应使调用程序崩溃,它们的存在可能会导致应用商店拒绝,和/或在生产环境中激活断言可能会暴露诸如私钥之类的私有数据。请注意,在许多Linux发行版中都未定义NDEBUG ,因此C / C ++缺省情况下,assert()将在这些环境中启用生产。对于那些环境中的生产,使用不同的断言机制或定义NDEBUG可能很重要。

    The race detector is the Go analogue of an assertion-heavy build, and it is enabled exactly where the criterion suggests: -race runs across all packages in CI, and is not enabled in production builds, which are CGO_ENABLED=0 static binaries.

    Tests additionally assert invariants that production code does not re-check. Two examples: the hand-rolled priority queue must agree with container/heap element by element on randomised input full of ties, and scoring output must stay byte-identical across an optimisation.



    通过动态代码分析发现的所有严重性为中,高的可利用漏洞必须在确认后及时修复。 [dynamic_analysis_fixed]
    如果 CVSS 2.0 基本分数为4,那么一个漏洞是中等到高的严重性。如果您没有运行动态代码分析,没有发现任何这样的漏洞,选择“不适用”(N/A)。

    No unfixed finding exists. The clearest example of the process working came from dynamic analysis of the GraphQL cost guard. A purpose-built probe timed the guard against a 1.2 KB document of non-cyclic fragments and showed it running for over ten seconds before a single field resolved, which is a denial of service in the very guard meant to prevent one. It was fixed in the same session by memoising fragment costs (49 µs for the same input), and the reproduction is now a permanent test that fails if the expansion stops being linear.

    Race-detector and fuzzing runs are currently clean.



该数据可在社区数据许可协议 – 许可性,版本 2.0 (CDLA-Permissive-2.0)下获取。这意味着数据接收方可以共享数据,无论是否经过修改,只要数据接收方在共享数据时提供本协议文本。请注明Luigi Iacuaniello和OpenSSF最佳实践徽章贡献者。

项目徽章条目拥有者: Luigi Iacuaniello.
最后更新于 2026-07-26 15:51:09 UTC, 最后更新于 2026-08-07 13:24:38 UTC。 最后在 2026-08-07 11:55:52 UTC 获得通过徽章。