如何获得超过 20 颗星的所有公共 GitHub 存储库的列表?

dan*_*nvk 5 github github-api

我想获得所有公共 GitHub 存储库的列表,其中包含超过一定数量的星(比如 15 或 20)。我可以使用 GitHub GraphQL API 获取超过 15 颗星的存储库列表:

query {
  search(query: "is:public stars:>15", type: REPOSITORY, first:10) {
    repositoryCount
    edges {
      node {
        ... on Repository {
          nameWithOwner
          stargazers {
            totalCount
          }
        }
      }
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

结果如下所示:

{
  "data": {
    "search": {
      "repositoryCount": 704279,
      "edges": [
        { "node": { "nameWithOwner": "freeCodeCamp/freeCodeCamp", "stargazers": { "totalCount": 308427 } } },
        { "node": { "nameWithOwner": "996icu/996.ICU", "stargazers": { "totalCount": 249062 } } },
        { "node": { "nameWithOwner": "vuejs/vue", "stargazers": { "totalCount": 156364 } } },
        { "node": { "nameWithOwner": "facebook/react", "stargazers": { "totalCount": 143121 } } },
        { "node": { "nameWithOwner": "tensorflow/tensorflow", "stargazers": { "totalCount": 140562 } } },
        { "node": { "nameWithOwner": "twbs/bootstrap", "stargazers": { "totalCount": 138369 } } },
        { "node": { "nameWithOwner": "EbookFoundation/free-programming-books", "stargazers": { "totalCount": 136421 } } },
        { "node": { "nameWithOwner": "sindresorhus/awesome", "stargazers": { "totalCount": 125160 } } },
        { "node": { "nameWithOwner": "getify/You-Dont-Know-JS", "stargazers": { "totalCount": 115851 } } },
        { "node": { "nameWithOwner": "ohmyzsh/ohmyzsh", "stargazers": { "totalCount": 102749 } } }
      ]
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

有 704,279 个存储库,但我最多可以请求 100 个存储库/查询并使用游标逐步浏览结果。因此,如果有足够的时间,这似乎会奏效。但不幸的是,GitHub GraphQL API将您限制为任何查询的前 1,000 个结果,所以这行不通。

我可以使用星号范围 ( stars:1000..1500)运行多个查询,但是一旦您使用较少的星力进行回购(有超过 1,000 个回购,恰好有 123 颗星),这就会崩溃。

我可以通过更多方式分解查询(例如,按创建回购的日期),但这开始变得疯狂。有没有更简单的方法来获得 15 个或更多星的公共 GitHub 存储库的完整列表?

dan*_*nvk 2

按创建日期和星级范围分割(问题中提到的“疯狂”解决方案)在实践中效果很好。

\n\n

您可以使用这样的 GraphQL 查询来获取在给定日期范围内创建的具有 15-20 颗星的存储库数量:

\n\n
query {\n  search(query: "is:public stars:15..20 created:2016-01-01..2016-01-09", type: REPOSITORY, first: 1) {\n    repositoryCount\n  }\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

回复:

\n\n
{ "data": { "search": { "repositoryCount": 534 } } }\n
Run Code Online (Sandbox Code Playgroud)\n\n

对于给定的星级范围(例如 15\xe2\x80\x9320),您从长日期范围(例如 2007\xe2\x80\x932020)开始并获取结果计数。如果超过 1,000,则将日期范围分成两部分并获取每个结果的计数。继续递归分割,直到每个星级范围/日期间隔低于 1,000 个结果。

\n\n

这是执行此操作的代码:

\n\n
query {\n  search(query: "is:public stars:15..20 created:2016-01-01..2016-01-09", type: REPOSITORY, first: 1) {\n    repositoryCount\n  }\n}\n
Run Code Online (Sandbox Code Playgroud)\n\n

最好从低星级范围向上抓取,因为在抓取过程中,回购更有可能获得星星而不是失去星星。

\n\n

对我来说,这最终需要 1,102 次不同的搜索。这是使用此方法收集的CSV 文件(约 50MB),其中包含 2020 年 2 月 3 日拥有 15 颗星以上的所有存储库。有关更多详细信息,请参阅此博客文章随附的源代码。

\n