blob: 61217cfa241b8ef9cada52be198db6d556c8c471 [file] [log] [blame]
#!/usr/bin/env bash
#
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you under the Apache License, Version 2.0 (the
# "License"); you may not use this file except in compliance
# with the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
set -eEuo pipefail
trap 'exit 1' ERR
declare DEBUG
if [ "${DEBUG}" = 'true' ] ; then
set -x
fi
declare GITHUB_TOKEN
declare -a GITHUB_AUTH
GITHUB_AUTH=('--header' "Authorization: token ${GITHUB_TOKEN}")
declare GITHUB_API_URL="https://api.github.com"
# the user_id of the buildbot that leaves the comments we want to hide.
declare BUILD_BOT_USER_ID="${BUILD_BOT_USER_ID:-49303554}"
declare REPO="${REPO:-apache/hbase}"
declare JOB_NAME="${JOB_NAME:-HBase-PreCommit-GitHub-PR}"
JOB_NAME="$(echo "${JOB_NAME}" | cut -d/ -f1)"
declare CURL="${CURL:-curl}"
function fetch_comments {
local pr="$1"
local comments_file
local -a curl_args
curl_args=(
--fail
"${GITHUB_AUTH[@]}"
--header 'Accept: application/vnd.github+json'
--header 'X-GitHub-Api-Version: 2022-11-28'
--request GET
--url "${GITHUB_API_URL}/repos/${REPO}/issues/${pr}/comments?per_page=500"
)
if [ "${DEBUG}" = true ] ; then
curl_args+=(--verbose)
else
curl_args+=(--silent)
fi
comments_file="$(mktemp "comments_${pr}" 2>/dev/null || mktemp -t "comments_${pr}.XXXXXXXXXX")" || \
{ >&2 echo 'cannot create temp file'; exit 1 ;}
"${CURL}" "${curl_args[@]}" > "${comments_file}"
if [ "${DEBUG}" = 'true' ] ; then
>&2 cat "${comments_file}"
fi
echo "${comments_file}"
}
function hide_old_comment {
local pr="$1"
local comment_id="$2"
local -a curl_args
local query
read -r -d '' query << EOF || :
mutation {
minimizeComment(input: { subjectId: \"$comment_id\", classifier: OUTDATED }) {
minimizedComment {
isMinimized,
minimizedReason
}
}
}
EOF
# remove newlines and whitespace rather than escaping them
query="${query//[$'\r\n\t ']/}"
curl_args=(
--fail
"${GITHUB_AUTH[@]}"
--header 'Accept: application/vnd.github+json'
--header 'Content-Type: application/json'
--header 'X-GitHub-Api-Version: 2022-11-28'
--request POST
--url "${GITHUB_API_URL}/graphql"
)
if [ "${DEBUG}" = true ] ; then
curl_args+=(--verbose)
else
curl_args+=(--silent)
fi
"${CURL}" "${curl_args[@]}" --data "{ \"query\": \"${query}\" }"
}
function identify_most_recent_build_number {
local pr="$1"
local comments_file="$2"
local jq_filter
read -r -d '' jq_filter << EOF || :
.[] \
| select(.user.id == ${BUILD_BOT_USER_ID}) \
| .body \
| capture("${JOB_NAME}/job/PR-${pr}/(?<buildnum>[0-9]+)/") \
| .buildnum
EOF
jq -r "${jq_filter}" "${comments_file}" \
| sort -nu \
| tail -n1
}
function identify_old_comment_ids {
local pr="$1"
local comments_file="$2"
local most_recent_build_number="$3"
local jq_filter
read -r -d '' jq_filter << EOF || :
.[] \
| select(.user.id == ${BUILD_BOT_USER_ID}) \
| { node_id, buildnum: (.body | capture("${JOB_NAME}/job/PR-${pr}/(?<buildnum>[0-9]+)/") | .buildnum | tonumber) } \
| select(.buildnum < (${most_recent_build_number} | tonumber)) \
| .node_id
EOF
jq -r "${jq_filter}" "${comments_file}"
}
function main {
local pr="$1"
local comments_file
local most_recent_build_number
comments_file="$(fetch_comments "$pr")"
most_recent_build_number="$(identify_most_recent_build_number "${pr}" "${comments_file}")"
for comment_id in $(identify_old_comment_ids "${pr}" "${comments_file}" "${most_recent_build_number}") ; do
hide_old_comment "${pr}" "${comment_id}"
sleep 1
done
}
main "$@"