在 GitHub 拉取请求中查找字符串
Find a string in a GitHub Pull Request
我想构建一个机器人,让您知道某个字符串(例如 DONT_MERGE_ME
是否出现在 GitHub 合并请求中,这样我就可以阻止失败的提交 检查并添加对开发者有用的评论。
假设您提交了如下代码,您不想意外地与您的 PR 合并(例如,您正在四处乱逛)。
const bar = 'some-hack-value'; // DONT_MERGE_ME
给定 PR id,我想弄清楚 PR 中是否仍然包含字符串 DONT_MERGE_ME
。然而,
- GitHub Code Search API 有很多限制,例如最大文件大小为 384KiB,并且只搜索 默认分支
- GitHub Commit Search API 仅搜索 默认分支
- GitHub Pull Requests Search API 仅搜索 title/body/comment
考虑到上述限制,对于给定的 PR id 和提交,看起来解决这个问题的唯一方法是在 PR 中找到该提交之前的所有提交,下载差异,并对它们求和向上。
有没有更简单的方法来使用 GitHub API?
我推荐的方法是订阅 pull_request
事件。如果 payload.action
是 opened
或 synchronize
,拉取请求的 load the diff 并在所有已更改的行中查找字符串。
您可以通过将 .diff
添加到任何拉取请求 URL 来预览拉取请求的差异响应,例如https://patch-diff.githubusercontent.com/raw/gr2m/sandbox/pull/194.diff
找到以 +
开头的行并在其中查找您的字符串
如果你使用 JavaScript octokit
包,你可以像这样加载一个 pull request
const { data: diff } = octokit.rest.pulls.get({ owner, repo, pull_number, mediaType: { format: "diff }})
同时查看 TODO GitHub App,它的源也是开源的
我发现(感谢@Gregor 的提示),如果您通过某些 headers,则有一个 GitHub API 用于将拉取请求作为 diff 获取。
我们是否可以获得回购 PR 的增量:
const pullId = 14956; // NOTE: 73 files changed!
const repoFullname = 'eslint/eslint';
const url = `https://api.github.com/repos/${repoFullname}/pulls/${pullId}.diff`;
const diffStr = (await axios.get(url,requestConfig)).data;
然后,我们可以使用parse-diff
库来解析这些,并过滤掉add
变化,匹配我们想要的内容变化。
// Search for this word
const KEYWORD = 'Requirements';
// Analyze all files
const files = parse(diffStr);
const filesWithMatchingAdds = files.map(
file => ({
file: file.to,
adds: file.chunks.map(
chunk => chunk.changes
// Only look for added lines
.filter(chunk => chunk.type === 'add')
// That match our keyword
.filter(chunk => chunk.content.includes(KEYWORD))
).flat()}) // collapse into one array
// Only files with at least one match
).filter(file => file.adds.length);
输出看起来像
[
{
"file": "tests/tools/internal-rules/multiline-comment-style.js",
"adds": [
{
"type": "add",
"add": true,
"ln": 4,
"content": "+// Requirements"
}
]
}
]
完整要点here。
我想构建一个机器人,让您知道某个字符串(例如 DONT_MERGE_ME
是否出现在 GitHub 合并请求中,这样我就可以阻止失败的提交 检查并添加对开发者有用的评论。
假设您提交了如下代码,您不想意外地与您的 PR 合并(例如,您正在四处乱逛)。
const bar = 'some-hack-value'; // DONT_MERGE_ME
给定 PR id,我想弄清楚 PR 中是否仍然包含字符串 DONT_MERGE_ME
。然而,
- GitHub Code Search API 有很多限制,例如最大文件大小为 384KiB,并且只搜索 默认分支
- GitHub Commit Search API 仅搜索 默认分支
- GitHub Pull Requests Search API 仅搜索 title/body/comment
考虑到上述限制,对于给定的 PR id 和提交,看起来解决这个问题的唯一方法是在 PR 中找到该提交之前的所有提交,下载差异,并对它们求和向上。
有没有更简单的方法来使用 GitHub API?
我推荐的方法是订阅 pull_request
事件。如果 payload.action
是 opened
或 synchronize
,拉取请求的 load the diff 并在所有已更改的行中查找字符串。
您可以通过将 .diff
添加到任何拉取请求 URL 来预览拉取请求的差异响应,例如https://patch-diff.githubusercontent.com/raw/gr2m/sandbox/pull/194.diff
找到以 +
开头的行并在其中查找您的字符串
如果你使用 JavaScript octokit
包,你可以像这样加载一个 pull request
const { data: diff } = octokit.rest.pulls.get({ owner, repo, pull_number, mediaType: { format: "diff }})
同时查看 TODO GitHub App,它的源也是开源的
我发现(感谢@Gregor 的提示),如果您通过某些 headers,则有一个 GitHub API 用于将拉取请求作为 diff 获取。
我们是否可以获得回购 PR 的增量:
const pullId = 14956; // NOTE: 73 files changed!
const repoFullname = 'eslint/eslint';
const url = `https://api.github.com/repos/${repoFullname}/pulls/${pullId}.diff`;
const diffStr = (await axios.get(url,requestConfig)).data;
然后,我们可以使用parse-diff
库来解析这些,并过滤掉add
变化,匹配我们想要的内容变化。
// Search for this word
const KEYWORD = 'Requirements';
// Analyze all files
const files = parse(diffStr);
const filesWithMatchingAdds = files.map(
file => ({
file: file.to,
adds: file.chunks.map(
chunk => chunk.changes
// Only look for added lines
.filter(chunk => chunk.type === 'add')
// That match our keyword
.filter(chunk => chunk.content.includes(KEYWORD))
).flat()}) // collapse into one array
// Only files with at least one match
).filter(file => file.adds.length);
输出看起来像
[
{
"file": "tests/tools/internal-rules/multiline-comment-style.js",
"adds": [
{
"type": "add",
"add": true,
"ln": 4,
"content": "+// Requirements"
}
]
}
]
完整要点here。