You are viewing a plain text version of this content. The canonical link for it is here.
Posted to common-commits@hadoop.apache.org by aw...@apache.org on 2015/07/07 00:51:48 UTC
[1/3] hadoop git commit: HADOOP-12127. some personalities are still
using releaseaudit instead of asflicense (aw)
Repository: hadoop
Updated Branches:
refs/heads/HADOOP-12111 0a607a24c -> dcde7e4a2
HADOOP-12127. some personalities are still using releaseaudit instead of asflicense (aw)
Project: http://git-wip-us.apache.org/repos/asf/hadoop/repo
Commit: http://git-wip-us.apache.org/repos/asf/hadoop/commit/76ce1ce7
Tree: http://git-wip-us.apache.org/repos/asf/hadoop/tree/76ce1ce7
Diff: http://git-wip-us.apache.org/repos/asf/hadoop/diff/76ce1ce7
Branch: refs/heads/HADOOP-12111
Commit: 76ce1ce73b2df077a64db8f848443094460ae534
Parents: 0a607a2
Author: Allen Wittenauer <aw...@apache.org>
Authored: Mon Jul 6 15:47:32 2015 -0700
Committer: Allen Wittenauer <aw...@apache.org>
Committed: Mon Jul 6 15:47:32 2015 -0700
----------------------------------------------------------------------
dev-support/personality/flink.sh | 2 +-
dev-support/personality/hadoop.sh | 2 +-
dev-support/personality/hbase.sh | 2 +-
dev-support/personality/tajo.sh | 2 +-
dev-support/personality/tez.sh | 2 +-
dev-support/test-patch.d/apache-rat.sh | 84 -----------------------------
dev-support/test-patch.d/asflicense.sh | 84 +++++++++++++++++++++++++++++
7 files changed, 89 insertions(+), 89 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/personality/flink.sh
----------------------------------------------------------------------
diff --git a/dev-support/personality/flink.sh b/dev-support/personality/flink.sh
index a32e2d6..de2a0f1 100755
--- a/dev-support/personality/flink.sh
+++ b/dev-support/personality/flink.sh
@@ -113,7 +113,7 @@ function personality_modules
fi
return
;;
- releaseaudit)
+ asflicense)
# this is very fast and provides the full path if we do it from
# the root of the source
personality_enqueue_module .
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/personality/hadoop.sh
----------------------------------------------------------------------
diff --git a/dev-support/personality/hadoop.sh b/dev-support/personality/hadoop.sh
index 059d051..7722afb 100755
--- a/dev-support/personality/hadoop.sh
+++ b/dev-support/personality/hadoop.sh
@@ -183,7 +183,7 @@ function personality_modules
return
fi
;;
- releaseaudit)
+ asflicense)
# this is very fast and provides the full path if we do it from
# the root of the source
personality_enqueue_module .
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/personality/hbase.sh
----------------------------------------------------------------------
diff --git a/dev-support/personality/hbase.sh b/dev-support/personality/hbase.sh
index 46ad390..d8ca901 100755
--- a/dev-support/personality/hbase.sh
+++ b/dev-support/personality/hbase.sh
@@ -50,7 +50,7 @@ function personality_modules
fi
return
;;
- releaseaudit)
+ asflicense)
# this is very fast and provides the full path if we do it from
# the root of the source
personality_enqueue_module . -DHBasePatchProcess
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/personality/tajo.sh
----------------------------------------------------------------------
diff --git a/dev-support/personality/tajo.sh b/dev-support/personality/tajo.sh
index 719bada..56e5442 100755
--- a/dev-support/personality/tajo.sh
+++ b/dev-support/personality/tajo.sh
@@ -40,7 +40,7 @@ function personality_modules
fi
return
;;
- releaseaudit)
+ asflicense)
# this is very fast and provides the full path if we do it from
# the root of the source
personality_enqueue_module .
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/personality/tez.sh
----------------------------------------------------------------------
diff --git a/dev-support/personality/tez.sh b/dev-support/personality/tez.sh
index 77ad624..1d6a227 100755
--- a/dev-support/personality/tez.sh
+++ b/dev-support/personality/tez.sh
@@ -40,7 +40,7 @@ function personality_modules
fi
return
;;
- releaseaudit)
+ asflicense)
# this is very fast and provides the full path if we do it from
# the root of the source
personality_enqueue_module .
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/test-patch.d/apache-rat.sh
----------------------------------------------------------------------
diff --git a/dev-support/test-patch.d/apache-rat.sh b/dev-support/test-patch.d/apache-rat.sh
deleted file mode 100755
index 27349bf..0000000
--- a/dev-support/test-patch.d/apache-rat.sh
+++ /dev/null
@@ -1,84 +0,0 @@
-#!/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.
-
-if [[ ${BUILDTOOL} == maven
- || ${BUILDTOOL} == ant ]]; then
- add_plugin asflicense
- add_test asflicense
-fi
-
-## @description Verify all files have an Apache License
-## @audience private
-## @stability evolving
-## @replaceable no
-## @return 0 on success
-## @return 1 on failure
-function asflicense_postapply
-{
- local numpatch
-
- big_console_header "Determining number of patched ASF License errors"
-
- start_clock
-
- personality_modules patch asflicense
- case ${BUILDTOOL} in
- maven)
- modules_workers patch asflicense apache-rat:check
- ;;
- ant)
- modules_workers patch asflicense releaseaudit
- ;;
- *)
- return 0
- ;;
- esac
-
- # RAT fails the build if there are license problems.
- # so let's take advantage of that a bit.
- if [[ $? == 0 ]]; then
- add_vote_table 1 asflicense "Patch does not generate ASF License warnings."
- return 0
- fi
-
- #shellcheck disable=SC2038
- find "${BASEDIR}" -name rat.txt -o -name releaseaudit_report.txt \
- | xargs cat > "${PATCH_DIR}/patch-asflicense.txt"
-
- if [[ -s "${PATCH_DIR}/patch-asflicense.txt" ]] ; then
- numpatch=$("${GREP}" -c '\!?????' "${PATCH_DIR}/patch-asflicense.txt")
- echo ""
- echo ""
- echo "There appear to be ${numpatch} ASF License warnings after applying the patch."
- if [[ -n ${numpatch}
- && ${numpatch} -gt 0 ]] ; then
- add_vote_table -1 asflicense "Patch generated ${numpatch} ASF License warnings."
-
- echo "Lines that start with ????? in the ASF License "\
- "report indicate files that do not have an Apache license header:" \
- > "${PATCH_DIR}/patch-asflicense-problems.txt"
-
- ${GREP} '\!?????' "${PATCH_DIR}/patch-asflicense.txt" \
- >> "${PATCH_DIR}/patch-asflicense-problems.txt"
-
- add_footer_table asflicense "@@BASE@@/patch-asflicense-problems.txt"
- fi
- else
- # if we're here, then maven actually failed
- modules_messages patch asflicense true
- fi
- return 1
-}
http://git-wip-us.apache.org/repos/asf/hadoop/blob/76ce1ce7/dev-support/test-patch.d/asflicense.sh
----------------------------------------------------------------------
diff --git a/dev-support/test-patch.d/asflicense.sh b/dev-support/test-patch.d/asflicense.sh
new file mode 100755
index 0000000..27349bf
--- /dev/null
+++ b/dev-support/test-patch.d/asflicense.sh
@@ -0,0 +1,84 @@
+#!/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.
+
+if [[ ${BUILDTOOL} == maven
+ || ${BUILDTOOL} == ant ]]; then
+ add_plugin asflicense
+ add_test asflicense
+fi
+
+## @description Verify all files have an Apache License
+## @audience private
+## @stability evolving
+## @replaceable no
+## @return 0 on success
+## @return 1 on failure
+function asflicense_postapply
+{
+ local numpatch
+
+ big_console_header "Determining number of patched ASF License errors"
+
+ start_clock
+
+ personality_modules patch asflicense
+ case ${BUILDTOOL} in
+ maven)
+ modules_workers patch asflicense apache-rat:check
+ ;;
+ ant)
+ modules_workers patch asflicense releaseaudit
+ ;;
+ *)
+ return 0
+ ;;
+ esac
+
+ # RAT fails the build if there are license problems.
+ # so let's take advantage of that a bit.
+ if [[ $? == 0 ]]; then
+ add_vote_table 1 asflicense "Patch does not generate ASF License warnings."
+ return 0
+ fi
+
+ #shellcheck disable=SC2038
+ find "${BASEDIR}" -name rat.txt -o -name releaseaudit_report.txt \
+ | xargs cat > "${PATCH_DIR}/patch-asflicense.txt"
+
+ if [[ -s "${PATCH_DIR}/patch-asflicense.txt" ]] ; then
+ numpatch=$("${GREP}" -c '\!?????' "${PATCH_DIR}/patch-asflicense.txt")
+ echo ""
+ echo ""
+ echo "There appear to be ${numpatch} ASF License warnings after applying the patch."
+ if [[ -n ${numpatch}
+ && ${numpatch} -gt 0 ]] ; then
+ add_vote_table -1 asflicense "Patch generated ${numpatch} ASF License warnings."
+
+ echo "Lines that start with ????? in the ASF License "\
+ "report indicate files that do not have an Apache license header:" \
+ > "${PATCH_DIR}/patch-asflicense-problems.txt"
+
+ ${GREP} '\!?????' "${PATCH_DIR}/patch-asflicense.txt" \
+ >> "${PATCH_DIR}/patch-asflicense-problems.txt"
+
+ add_footer_table asflicense "@@BASE@@/patch-asflicense-problems.txt"
+ fi
+ else
+ # if we're here, then maven actually failed
+ modules_messages patch asflicense true
+ fi
+ return 1
+}
[3/3] hadoop git commit: HADOOP-12156. modernize smart-apply-patch
(aw)
Posted by aw...@apache.org.
HADOOP-12156. modernize smart-apply-patch (aw)
Project: http://git-wip-us.apache.org/repos/asf/hadoop/repo
Commit: http://git-wip-us.apache.org/repos/asf/hadoop/commit/dcde7e4a
Tree: http://git-wip-us.apache.org/repos/asf/hadoop/tree/dcde7e4a
Diff: http://git-wip-us.apache.org/repos/asf/hadoop/diff/dcde7e4a
Branch: refs/heads/HADOOP-12111
Commit: dcde7e4a23ca0a5dcd4b01104d2d39365b557bac
Parents: 3fee9f8
Author: Allen Wittenauer <aw...@apache.org>
Authored: Mon Jul 6 15:50:46 2015 -0700
Committer: Allen Wittenauer <aw...@apache.org>
Committed: Mon Jul 6 15:50:46 2015 -0700
----------------------------------------------------------------------
dev-support/smart-apply-patch.sh | 628 ++++++++++++++++++++++++++--------
dev-support/test-patch.sh | 2 +-
2 files changed, 492 insertions(+), 138 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/hadoop/blob/dcde7e4a/dev-support/smart-apply-patch.sh
----------------------------------------------------------------------
diff --git a/dev-support/smart-apply-patch.sh b/dev-support/smart-apply-patch.sh
index ddfd940..bfd2aeb 100755
--- a/dev-support/smart-apply-patch.sh
+++ b/dev-support/smart-apply-patch.sh
@@ -11,179 +11,533 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-#
-# Determine if the git diff patch file has prefixes.
-# These files are generated via "git diff" *without* the --no-prefix option.
-#
-# We can apply these patches more easily because we know that the a/ and b/
-# prefixes in the "diff" lines stands for the project root directory.
-# So we don't have to hunt for the project root.
-# And of course, we know that the patch file was generated using git, so we
-# know git apply can handle it properly.
-#
-# Arguments: git diff file name.
-# Return: 0 if it is a git diff with prefix; 1 otherwise.
-#
-has_prefix() {
- awk '/^diff --git / { if ($3 !~ "^a/" || $4 !~ "^b/") { exit 1 } }
- /^\+{3}|-{3} / { if ($2 !~ "^[ab]/" && $2 !~ "^/dev/null") { exit 1 } }' "$1"
- return $?
-}
+# Make sure that bash version meets the pre-requisite
-PATCH_FILE=$1
-DRY_RUN=$2
-if [ -z "$PATCH_FILE" ]; then
- echo usage: $0 patch-file
+if [[ -z "${BASH_VERSINFO}" ]] \
+ || [[ "${BASH_VERSINFO[0]}" -lt 3 ]] \
+ || [[ "${BASH_VERSINFO[0]}" -eq 3 && "${BASH_VERSINFO[1]}" -lt 2 ]]; then
+ echo "bash v3.2+ is required. Sorry."
exit 1
fi
-TMPDIR=${TMPDIR:-/tmp}
-PATCH=${PATCH:-patch} # allow overriding patch binary
+RESULT=0
+
+## @description Print a message to stderr
+## @audience public
+## @stability stable
+## @replaceable no
+## @param string
+function yetus_error
+{
+ echo "$*" 1>&2
+}
-# Cleanup handler for temporary files
-TOCLEAN=""
-cleanup() {
- if [[ -n ${TOCLEAN} ]]; then
- rm $TOCLEAN
+## @description Print a message to stderr if --debug is turned on
+## @audience public
+## @stability stable
+## @replaceable no
+## @param string
+function yetus_debug
+{
+ if [[ -n "${YETUS_SHELL_SCRIPT_DEBUG}" ]]; then
+ echo "[$(date) DEBUG]: $*" 1>&2
fi
- exit $1
}
-trap "cleanup 1" HUP INT QUIT TERM
-# Allow passing "-" for stdin patches
-if [ "$PATCH_FILE" == "-" ]; then
- PATCH_FILE="$TMPDIR/smart-apply.in.$RANDOM"
- cat /dev/fd/0 > $PATCH_FILE
- TOCLEAN="$TOCLEAN $PATCH_FILE"
-fi
+## @description Clean the filesystem as appropriate and then exit
+## @audience private
+## @stability evolving
+## @replaceable no
+## @param runresult
+function cleanup_and_exit
+{
+ local result=$1
-ISSUE_RE='^(HADOOP|YARN|MAPREDUCE|HDFS)-[0-9]+$'
-if [[ ${PATCH_FILE} =~ ^http || ${PATCH_FILE} =~ ${ISSUE_RE} ]]; then
- # Allow downloading of patches
- PFILE="$TMPDIR/smart-apply.in.$RANDOM"
- TOCLEAN="$TOCLEAN $PFILE"
- if [[ ${PATCH_FILE} =~ ^http ]]; then
- patchURL="${PATCH_FILE}"
- else # Get URL of patch from JIRA
- wget -q -O "${PFILE}" "http://issues.apache.org/jira/browse/${PATCH_FILE}"
- if [[ $? != 0 ]]; then
- echo "Unable to determine what ${PATCH_FILE} may reference." 1>&2
- cleanup 1
- elif [[ $(grep -c 'Patch Available' "${PFILE}") == 0 ]]; then
- echo "${PATCH_FILE} is not \"Patch Available\". Exiting." 1>&2
- cleanup 1
- fi
- relativePatchURL=$(grep -o '"/jira/secure/attachment/[0-9]*/[^"]*' "${PFILE}" | grep -v -e 'htm[l]*$' | sort | tail -1 | grep -o '/jira/secure/attachment/[0-9]*/[^"]*')
- patchURL="http://issues.apache.org${relativePatchURL}"
+ if [[ ${PATCH_DIR} =~ ^/tmp/apply-patch
+ && -d ${PATCH_DIR} ]]; then
+ rm -rf "${PATCH_DIR}"
+ fi
+
+ # shellcheck disable=SC2086
+ exit ${result}
+}
+
+## @description Setup the default global variables
+## @audience public
+## @stability stable
+## @replaceable no
+function setup_defaults
+{
+ PATCHURL=""
+ OSTYPE=$(uname -s)
+
+ # Solaris needs POSIX, not SVID
+ case ${OSTYPE} in
+ SunOS)
+ AWK=${AWK:-/usr/xpg4/bin/awk}
+ SED=${SED:-/usr/xpg4/bin/sed}
+ WGET=${WGET:-wget}
+ GIT=${GIT:-git}
+ GREP=${GREP:-/usr/xpg4/bin/grep}
+ PATCH=${PATCH:-/usr/gnu/bin/patch}
+ DIFF=${DIFF:-/usr/gnu/bin/diff}
+ FILE=${FILE:-file}
+ ;;
+ *)
+ AWK=${AWK:-awk}
+ SED=${SED:-sed}
+ WGET=${WGET:-wget}
+ GIT=${GIT:-git}
+ GREP=${GREP:-grep}
+ PATCH=${PATCH:-patch}
+ DIFF=${DIFF:-diff}
+ FILE=${FILE:-file}
+ ;;
+ esac
+
+ DRYRUNMODE=false
+ PATCH_DIR=/tmp
+ while [[ -e ${PATCH_DIR} ]]; do
+ PATCH_DIR=/tmp/apply-patch-${RANDOM}.${RANDOM}
+ done
+ PATCHMODES=("git" "patch")
+ PATCHMODE=""
+ PATCHPREFIX=0
+}
+
+## @description Print the usage information
+## @audience public
+## @stability stable
+## @replaceable no
+function yetus_usage
+{
+ echo "Usage: apply-patch.sh [options] patch-file | issue-number | http"
+ echo
+ echo "--debug If set, then output some extra stuff to stderr"
+ echo "--dry-run Check for patch viability without applying"
+ echo "--patch-dir=<dir> The directory for working and output files (default '/tmp/apply-patch-(random))"
+ echo
+ echo "Shell binary overrides:"
+ echo "--file-cmd=<cmd> The 'file' command to use (default 'file')"
+ echo "--grep-cmd=<cmd> The 'grep' command to use (default 'grep')"
+ echo "--git-cmd=<cmd> The 'git' command to use (default 'git')"
+ echo "--patch-cmd=<cmd> The GNU-compatible 'patch' command to use (default 'patch')"
+ echo "--wget-cmd=<cmd> The 'wget' command to use (default 'wget')"
+}
+
+## @description Interpret the command line parameters
+## @audience private
+## @stability stable
+## @replaceable no
+## @params $@
+## @return May exit on failure
+function parse_args
+{
+ local i
+
+ for i in "$@"; do
+ case ${i} in
+ --debug)
+ YETUS_SHELL_SCRIPT_DEBUG=true
+ ;;
+ --dry-run)
+ DRYRUNMODE=true
+ ;;
+ --file-cmd=*)
+ FILE=${i#*=}
+ ;;
+ --git-cmd=*)
+ GIT=${i#*=}
+ ;;
+ --grep-cmd=*)
+ GREP=${i#*=}
+ ;;
+ --help|-help|-h|help|--h|--\?|-\?|\?)
+ yetus_usage
+ exit 0
+ ;;
+ --patch-cmd=*)
+ PATCH=${i#*=}
+ ;;
+ --patch-dir=*)
+ PATCH_DIR=${i#*=}
+ ;;
+ --wget-cmd=*)
+ WGET=${i#*=}
+ ;;
+ --*)
+ ## PATCH_OR_ISSUE can't be a --. So this is probably
+ ## a plugin thing.
+ continue
+ ;;
+ *)
+ PATCH_OR_ISSUE=${i#*=}
+ ;;
+ esac
+ done
+
+ if [[ ! -d ${PATCH_DIR} ]]; then
+ mkdir -p "${PATCH_DIR}"
+ if [[ $? != 0 ]] ; then
+ yetus_error "ERROR: Unable to create ${PATCH_DIR}"
+ cleanup_and_exit 1
+ fi
fi
- if [[ -n $DRY_RUN ]]; then
- echo "Downloading ${patchURL}"
+}
+
+## @description Given a possible patch file, guess if it's a patch file without using smart-apply-patch
+## @audience private
+## @stability evolving
+## @param path to patch file to test
+## @return 0 we think it's a patch file
+## @return 1 we think it's not a patch file
+function guess_patch_file
+{
+ local patch=$1
+ local fileOutput
+
+ yetus_debug "Trying to guess is ${patch} is a patch file."
+ fileOutput=$("${FILE}" "${patch}")
+ if [[ $fileOutput =~ \ diff\ ]]; then
+ yetus_debug "file magic says it's a diff."
+ return 0
fi
- wget -q -O "${PFILE}" "${patchURL}"
- if [[ $? != 0 ]]; then
- echo "${PATCH_FILE} could not be downloaded." 1>&2
- cleanup 1
+ fileOutput=$(head -n 1 "${patch}" | "${GREP}" -E "^(From [a-z0-9]* Mon Sep 17 00:00:00 2001)|(diff .*)|(Index: .*)$")
+ if [[ $? == 0 ]]; then
+ yetus_debug "first line looks like a patch file."
+ return 0
fi
- PATCH_FILE="${PFILE}"
-fi
+ return 1
+}
+
+## @description Given ${PATCH_ISSUE}, determine what type of patch file is in use, and do the
+## @description necessary work to place it into ${PATCH_DIR}/patch.
+## @audience private
+## @stability evolving
+## @replaceable no
+## @return 0 on success
+## @return 1 on failure, may exit
+function locate_patch
+{
+ local notSureIfPatch=false
+ yetus_debug "locate patch"
-# Case for git-diff patches
-if grep -q "^diff --git" "${PATCH_FILE}"; then
- GIT_FLAGS="--binary -v"
- if has_prefix "$PATCH_FILE"; then
- GIT_FLAGS="$GIT_FLAGS -p1"
+ # Allow passing "-" for stdin patches
+ if [[ ${PATCH_OR_ISSUE} == - ]]; then
+ PATCH_FILE="${PATCH_DIR}/patch"
+ cat /dev/fd/0 > "${PATCH_FILE}"
+ elif [[ -f ${PATCH_OR_ISSUE} ]]; then
+ PATCH_FILE="${PATCH_OR_ISSUE}"
else
- GIT_FLAGS="$GIT_FLAGS -p0"
+ if [[ ${PATCH_OR_ISSUE} =~ ^http ]]; then
+ echo "Patch is being downloaded at $(date) from"
+ PATCHURL="${PATCH_OR_ISSUE}"
+ else
+ ${WGET} -q -O "${PATCH_DIR}/jira" "http://issues.apache.org/jira/browse/${PATCH_OR_ISSUE}"
+
+ case $? in
+ 0)
+ ;;
+ 2)
+ yetus_error "ERROR: .wgetrc/.netrc parsing error."
+ cleanup_and_exit 1
+ ;;
+ 3)
+ yetus_error "ERROR: File IO error."
+ cleanup_and_exit 1
+ ;;
+ 4)
+ yetus_error "ERROR: URL ${PATCH_OR_ISSUE} is unreachable."
+ cleanup_and_exit 1
+ ;;
+ *)
+ yetus_error "ERROR: Unable to fetch ${PATCH_OR_ISSUE}."
+ cleanup_and_exit 1
+ ;;
+ esac
+
+ if [[ -z "${PATCH_FILE}" ]]; then
+ if [[ $(${GREP} -c 'Patch Available' "${PATCH_DIR}/jira") == 0 ]] ; then
+ if [[ ${JENKINS} == true ]]; then
+ yetus_error "ERROR: ${PATCH_OR_ISSUE} is not \"Patch Available\"."
+ cleanup_and_exit 1
+ else
+ yetus_error "WARNING: ${PATCH_OR_ISSUE} is not \"Patch Available\"."
+ fi
+ fi
+
+ relativePatchURL=$(${GREP} -o '"/jira/secure/attachment/[0-9]*/[^"]*' "${PATCH_DIR}/jira" | ${GREP} -v -e 'htm[l]*$' | sort | tail -1 | ${GREP} -o '/jira/secure/attachment/[0-9]*/[^"]*')
+ PATCHURL="http://issues.apache.org${relativePatchURL}"
+ if [[ ! ${PATCHURL} =~ \.patch$ ]]; then
+ notSureIfPatch=true
+ fi
+ echo "${ISSUE} patch is being downloaded at $(date) from"
+ fi
+ fi
+ if [[ -z "${PATCH_FILE}" ]]; then
+ ${WGET} -q -O "${PATCH_DIR}/patch" "${PATCHURL}"
+ if [[ $? != 0 ]];then
+ yetus_error "ERROR: ${PATCH_OR_ISSUE} could not be downloaded."
+ cleanup_and_exit 1
+ fi
+ PATCH_FILE="${PATCH_DIR}/patch"
+ fi
fi
- if [[ -z $DRY_RUN ]]; then
- GIT_FLAGS="$GIT_FLAGS --stat --apply"
- echo Going to apply git patch with: git apply "${GIT_FLAGS}"
- else
- GIT_FLAGS="$GIT_FLAGS --check"
+
+ if [[ ! -f "${PATCH_DIR}/patch" ]]; then
+ cp "${PATCH_FILE}" "${PATCH_DIR}/patch"
+ if [[ $? == 0 ]] ; then
+ echo "Patch file ${PATCH_FILE} copied to ${PATCH_DIR}"
+ else
+ yetus_error "ERROR: Could not copy ${PATCH_FILE} to ${PATCH_DIR}"
+ cleanup_and_exit 1
+ fi
fi
- # shellcheck disable=SC2086
- git apply ${GIT_FLAGS} "${PATCH_FILE}"
- if [[ $? == 0 ]]; then
- cleanup 0
+
+ if [[ ! -f "${PATCH_DIR}/patch" ]]; then
+ cp "${PATCH_FILE}" "${PATCH_DIR}/patch"
+ if [[ $? == 0 ]] ; then
+ echo "Patch file ${PATCH_FILE} copied to ${PATCH_DIR}"
+ else
+ yetus_error "ERROR: Could not copy ${PATCH_FILE} to ${PATCH_DIR}"
+ cleanup_and_exit 1
+ fi
fi
- echo "git apply failed. Going to apply the patch with: ${PATCH}"
-fi
-# Come up with a list of changed files into $TMP
-TMP="$TMPDIR/smart-apply.paths.$RANDOM"
-TOCLEAN="$TOCLEAN $TMP"
+ if [[ ${notSureIfPatch} == "true" ]]; then
+ guess_patch_file "${PATCH_FILE}"
+ if [[ $? != 0 ]]; then
+ yetus_error "ERROR: ${PATCHURL} is not a patch file."
+ cleanup_and_exit 1
+ else
+ yetus_debug "The patch ${PATCHURL} was not named properly, but it looks like a patch file. proceeding, but issue/branch matching might go awry."
+ fi
+ fi
+}
+
+## @description if patch-level zero, then verify we aren't
+## @description just adding files
+## @audience public
+## @stability stable
+## @param filename
+## @param command
+## @param [..]
+## @replaceable no
+## @returns $?
+function verify_zero
+{
+ local logfile=$1
+ shift
+ local dir
+
+ # don't return /dev/null
+ # shellcheck disable=SC2016
+ changed_files1=$(${AWK} 'function p(s){if(s!~"^/dev/null"){print s}}
+ /^diff --git / { p($3); p($4) }
+ /^(\+\+\+|---) / { p($2) }' "${PATCH_DIR}/patch" | sort -u)
+
+ # maybe we interpreted the patch wrong? check the log file
+ # shellcheck disable=SC2016
+ changed_files2=$(${GREP} -E '^[cC]heck' "${logfile}" \
+ | ${AWK} '{print $3}' \
+ | ${SED} -e 's,\.\.\.$,,g')
-if $PATCH -p0 -E --dry-run < $PATCH_FILE 2>&1 > $TMP; then
- PLEVEL=0
- #if the patch applied at P0 there is the possability that all we are doing
- # is adding new files and they would apply anywhere. So try to guess the
- # correct place to put those files.
+ for filename in ${changed_files1} ${changed_files2}; do
- TMP2="$TMPDIR/smart-apply.paths.2.$RANDOM"
- TOCLEAN="$TOCLEAN $TMP2"
+ # leading prefix = bad
+ if [[ ${filename} =~ ^(a|b)/ ]]; then
+ return 1
+ fi
+
+ # touching an existing file is proof enough
+ # that pl=0 is good
+ if [[ -f ${filename} ]]; then
+ return 0
+ fi
- egrep '^patching file |^checking file ' $TMP | awk '{print $3}' | grep -v /dev/null | sort -u > $TMP2
+ dir=$(dirname ${filename} 2>/dev/null)
+ if [[ -n ${dir} && -d ${dir} ]]; then
+ return 0
+ fi
+ done
- if [ ! -s $TMP2 ]; then
- echo "Error: Patch dryrun couldn't detect changes the patch would make. Exiting."
- cleanup 1
+ # ¯\_(ツ)_/¯ - no way for us to know, all new files with no prefix!
+ yetus_error "WARNING: Patch only adds files; using patch level ${PATCHPREFIX}"
+ return 0
+}
+
+## @description run the command, sending stdout and stderr to the given filename
+## @audience public
+## @stability stable
+## @param filename
+## @param command
+## @param [..]
+## @replaceable no
+## @returns $?
+function run_and_redirect
+{
+ local logfile=$1
+ shift
+
+ # to the log
+ echo "${*}" > "${logfile}"
+ # the actual command
+ "${@}" >> "${logfile}" 2>&1
+}
+
+## @description git patch dryrun
+## @replaceable no
+## @audience private
+## @stability evolving
+function git_dryrun
+{
+ local prefixsize=${1:-0}
+
+ while [[ ${prefixsize} -lt 4
+ && -z ${PATCHMODE} ]]; do
+ run_and_redirect "${PATCH_DIR}/apply-patch-git-dryrun.log" \
+ "${GIT}" apply --binary -v --check "-p${prefixsize}" "${PATCH_FILE}"
+ if [[ $? == 0 ]]; then
+ PATCHPREFIX=${prefixsize}
+ PATCHMODE=git
+ echo "Verifying the patch:"
+ cat "${PATCH_DIR}/apply-patch-git-dryrun.log"
+ break
+ fi
+ ((prefixsize=prefixsize+1))
+ done
+
+ if [[ ${prefixsize} -eq 0 ]]; then
+ verify_zero "${PATCH_DIR}/apply-patch-git-dryrun.log"
+ if [[ $? != 0 ]]; then
+ PATCHMODE=""
+ PATCHPREFIX=""
+ git_dryrun 1
+ fi
fi
+}
- #first off check that all of the files do not exist
- FOUND_ANY=0
- for CHECK_FILE in $(cat $TMP2)
- do
- if [[ -f $CHECK_FILE ]]; then
- FOUND_ANY=1
+## @description patch patch dryrun
+## @replaceable no
+## @audience private
+## @stability evolving
+function patch_dryrun
+{
+ local prefixsize=${1:-0}
+
+ while [[ ${prefixsize} -lt 4
+ && -z ${PATCHMODE} ]]; do
+ run_and_redirect "${PATCH_DIR}/apply-patch-patch-dryrun.log" \
+ "${PATCH}" "-p${prefixsize}" -E --dry-run < "${PATCH_FILE}"
+ if [[ $? == 0 ]]; then
+ PATCHPREFIX=${prefixsize}
+ PATCHMODE=patch
+ if [[ ${DRYRUNMODE} == true ]]; then
+ echo "Verifying the patch:"
+ cat "${PATCH_DIR}/apply-patch-patch-dryrun.log"
+ fi
+ break
fi
+ ((prefixsize=prefixsize+1))
done
- if [[ "$FOUND_ANY" = "0" ]]; then
- #all of the files are new files so we have to guess where the correct place to put it is.
+ if [[ ${prefixsize} -eq 0 ]]; then
+ verify_zero "${PATCH_DIR}/apply-patch-patch-dryrun.log"
+ if [[ $? != 0 ]]; then
+ PATCHMODE=""
+ PATCHPREFIX=""
+ patch_dryrun 1
+ fi
+ fi
+}
+
+## @description driver for dryrun methods
+## @replaceable no
+## @audience private
+## @stability evolving
+function dryrun
+{
+ local method
- # if all of the lines start with a/ or b/, then this is a git patch that
- # was generated without --no-prefix
- if ! grep -qv '^a/\|^b/' $TMP2 ; then
- echo Looks like this is a git patch. Stripping a/ and b/ prefixes
- echo and incrementing PLEVEL
- PLEVEL=$[$PLEVEL + 1]
- sed -i -e 's,^[ab]/,,' $TMP2
+ for method in "${PATCHMODES[@]}"; do
+ if declare -f ${method}_dryrun >/dev/null; then
+ "${method}_dryrun"
fi
+ if [[ -n ${PATCHMODE} ]]; then
+ break
+ fi
+ done
- PREFIX_DIRS_AND_FILES=$(cut -d '/' -f 1 $TMP2 | sort -u)
-
- # if we are at the project root then nothing more to do
- if [[ -d hadoop-common-project ]]; then
- echo Looks like this is being run at project root
+ if [[ -n ${PATCHMODE} ]]; then
+ RESULT=0
+ return 0
+ fi
+ RESULT=1
+ return 1
+}
- # if all of the lines start with hadoop-common/, hadoop-hdfs/, hadoop-yarn/ or hadoop-mapreduce/, this is
- # relative to the hadoop root instead of the subproject root, so we need
- # to chop off another layer
- elif [[ "$PREFIX_DIRS_AND_FILES" =~ ^(hadoop-common-project|hadoop-hdfs-project|hadoop-yarn-project|hadoop-mapreduce-project)$ ]]; then
+## @description git patch apply
+## @replaceable no
+## @audience private
+## @stability evolving
+function git_apply
+{
+ echo "Applying the patch:"
+ run_and_redirect "${PATCH_DIR}/apply-patch-git-apply.log" \
+ "${GIT}" apply --binary -v --stat --apply "-p${PATCHPREFIX}" "${PATCH_FILE}"
+ cat "${PATCH_DIR}/apply-patch-git-apply.log"
+}
- echo Looks like this is relative to project root. Increasing PLEVEL
- PLEVEL=$[$PLEVEL + 1]
- elif ! echo "$PREFIX_DIRS_AND_FILES" | grep -vxq 'hadoop-common-project\|hadoop-hdfs-project\|hadoop-yarn-project\|hadoop-mapreduce-project' ; then
- echo Looks like this is a cross-subproject patch. Try applying from the project root
- cleanup 1
+## @description patch patch apply
+## @replaceable no
+## @audience private
+## @stability evolving
+function patch_apply
+{
+ echo "Applying the patch:"
+ run_and_redirect "${PATCH_DIR}/apply-patch-patch-apply.log" \
+ "${PATCH}" "-p${PATCHPREFIX}" -E < "${PATCH_FILE}"
+ cat "${PATCH_DIR}/apply-patch-patch-apply.log"
+}
+
+
+## @description driver for patch apply methods
+## @replaceable no
+## @audience private
+## @stability evolving
+function apply
+{
+ if declare -f ${PATCHMODE}_apply >/dev/null; then
+ "${PATCHMODE}_apply"
+ if [[ $? -gt 0 ]]; then
+ RESULT=1
+ else
+ RESULT=0
fi
+ else
+ yetus_error "ERROR: Patching method ${PATCHMODE} does not have a way to apply patches!"
+ RESULT=1
fi
-elif $PATCH -p1 -E --dry-run < $PATCH_FILE 2>&1 > /dev/null; then
- PLEVEL=1
-elif $PATCH -p2 -E --dry-run < $PATCH_FILE 2>&1 > /dev/null; then
- PLEVEL=2
-else
- echo "The patch does not appear to apply with p0 to p2";
- cleanup 1;
-fi
+}
+
+trap "cleanup_and_exit 1" HUP INT QUIT TERM
-# If this is a dry run then exit instead of applying the patch
-if [[ -n $DRY_RUN ]]; then
- cleanup 0;
+setup_defaults
+
+parse_args "$@"
+
+locate_patch
+
+dryrun
+
+if [[ ${RESULT} -gt 0 ]]; then
+ yetus_error "ERROR: Aborting! The patch cannot be verified."
+ cleanup_and_exit ${RESULT}
fi
-echo Going to apply patch with: $PATCH -p$PLEVEL
-$PATCH -p$PLEVEL -E < $PATCH_FILE
+if [[ ${DRYRUNMODE} == false ]]; then
+ apply
+fi
-cleanup $?
+cleanup_and_exit ${RESULT}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/hadoop/blob/dcde7e4a/dev-support/test-patch.sh
----------------------------------------------------------------------
diff --git a/dev-support/test-patch.sh b/dev-support/test-patch.sh
index f93cb4a..793c42f 100755
--- a/dev-support/test-patch.sh
+++ b/dev-support/test-patch.sh
@@ -1601,7 +1601,7 @@ function verify_patch_file
# Before building, check to make sure that the patch is valid
export PATCH
- "${BINDIR}/smart-apply-patch.sh" "${PATCH_DIR}/patch" dryrun
+ "${BINDIR}/smart-apply-patch.sh" --dry-run "${PATCH_DIR}/patch"
if [[ $? != 0 ]] ; then
echo "PATCH APPLICATION FAILED"
add_vote_table -1 patch "The patch command could not apply the patch during dryrun."
[2/3] hadoop git commit: HADOOP-12135. cleanup releasedocmaker
Posted by aw...@apache.org.
HADOOP-12135. cleanup releasedocmaker
Project: http://git-wip-us.apache.org/repos/asf/hadoop/repo
Commit: http://git-wip-us.apache.org/repos/asf/hadoop/commit/3fee9f8d
Tree: http://git-wip-us.apache.org/repos/asf/hadoop/tree/3fee9f8d
Diff: http://git-wip-us.apache.org/repos/asf/hadoop/diff/3fee9f8d
Branch: refs/heads/HADOOP-12111
Commit: 3fee9f8d18dd60d83da674b3cfbefe666915fad8
Parents: 76ce1ce
Author: Allen Wittenauer <aw...@apache.org>
Authored: Mon Jul 6 15:49:03 2015 -0700
Committer: Allen Wittenauer <aw...@apache.org>
Committed: Mon Jul 6 15:49:03 2015 -0700
----------------------------------------------------------------------
dev-support/releasedocmaker.py | 384 +++++++++++++++++++-----------------
1 file changed, 207 insertions(+), 177 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/hadoop/blob/3fee9f8d/dev-support/releasedocmaker.py
----------------------------------------------------------------------
diff --git a/dev-support/releasedocmaker.py b/dev-support/releasedocmaker.py
index 8e68b3c..6e01260 100755
--- a/dev-support/releasedocmaker.py
+++ b/dev-support/releasedocmaker.py
@@ -19,6 +19,7 @@
from glob import glob
from optparse import OptionParser
from time import gmtime, strftime
+import pprint
import os
import re
import sys
@@ -99,23 +100,44 @@ def mstr(obj):
return ""
return unicode(obj)
-def buildindex(master):
+def buildindex(title,license):
versions=reversed(sorted(glob("[0-9]*.[0-9]*.[0-9]*")))
with open("index.md","w") as indexfile:
+ if license is True:
+ indexfile.write(asflicense)
for v in versions:
- indexfile.write("* Apache Hadoop v%s\n" % (v))
+ indexfile.write("* %s v%s\n" % (title,v))
for k in ("Changes","Release Notes"):
- indexfile.write(" * %s\n" %(k))
- indexfile.write(" * [Combined %s](%s/%s.%s.html)\n" \
+ indexfile.write(" * %s (%s/%s.%s.html)\n" \
% (k,v,k.upper().replace(" ",""),v))
- if not master:
- indexfile.write(" * [Hadoop Common %s](%s/%s.HADOOP.%s.html)\n" \
- % (k,v,k.upper().replace(" ",""),v))
- for p in ("HDFS","MapReduce","YARN"):
- indexfile.write(" * [%s %s](%s/%s.%s.%s.html)\n" \
- % (p,k,v,k.upper().replace(" ",""),p.upper(),v))
indexfile.close()
+class GetVersions:
+ """ yo """
+ def __init__(self,versions, projects):
+ versions = versions
+ projects = projects
+ self.newversions = []
+ pp = pprint.PrettyPrinter(indent=4)
+ at=0
+ end=1
+ count=100
+ versions.sort()
+ print "Looking for %s through %s"%(versions[0],versions[-1])
+ for p in projects:
+ resp = urllib.urlopen("https://issues.apache.org/jira/rest/api/2/project/%s/versions"%p)
+ data = json.loads(resp.read())
+ for d in data:
+ if d['name'][0].isdigit and versions[0] <= d['name'] and d['name'] <= versions[-1]:
+ print "Adding %s to the list" % d['name']
+ self.newversions.append(d['name'])
+ newlist=list(set(self.newversions))
+ self.newversions=newlist
+
+ def getlist(self):
+ pp = pprint.PrettyPrinter(indent=4)
+ return(self.newversions)
+
class Version:
"""Represents a version number"""
def __init__(self, data):
@@ -261,8 +283,10 @@ class Jira:
class JiraIter:
"""An Iterator of JIRAs"""
- def __init__(self, versions):
- self.versions = versions
+ def __init__(self, version, projects):
+ self.version = version
+ self.projects = projects
+ v=str(version).replace("-SNAPSHOT","")
resp = urllib.urlopen("https://issues.apache.org/jira/rest/api/2/field")
data = json.loads(resp.read())
@@ -276,7 +300,7 @@ class JiraIter:
end=1
count=100
while (at < end):
- params = urllib.urlencode({'jql': "project in (HADOOP,HDFS,MAPREDUCE,YARN) and fixVersion in ('"+"' , '".join([str(v).replace("-SNAPSHOT","") for v in versions])+"') and resolution = Fixed", 'startAt':at, 'maxResults':count})
+ params = urllib.urlencode({'jql': "project in ('"+"' , '".join(projects)+"') and fixVersion in ('"+v+"') and resolution = Fixed", 'startAt':at, 'maxResults':count})
resp = urllib.urlopen("https://issues.apache.org/jira/rest/api/2/search?%s"%params)
data = json.loads(resp.read())
if (data.has_key('errorMessages')):
@@ -286,10 +310,8 @@ class JiraIter:
self.jiras.extend(data['issues'])
needaversion=False
- for j in versions:
- v=str(j).replace("-SNAPSHOT","")
- if v not in releaseVersion:
- needaversion=True
+ if v not in releaseVersion:
+ needaversion=True
if needaversion is True:
for i in range(len(data['issues'])):
@@ -351,21 +373,29 @@ class Outputs:
self.writeKeyRaw(jira.getProject(), line)
def main():
- parser = OptionParser(usage="usage: %prog --version VERSION [--version VERSION2 ...]",
+ parser = OptionParser(usage="usage: %prog --project PROJECT [--project PROJECT] --version VERSION [--version VERSION2 ...]",
epilog=
"Markdown-formatted CHANGES and RELEASENOTES files will be stored in a directory"
" named after the highest version provided.")
- parser.add_option("-v", "--version", dest="versions",
- action="append", type="string",
- help="versions in JIRA to include in releasenotes", metavar="VERSION")
- parser.add_option("-m","--master", dest="master", action="store_true",
- help="only create the master, merged project files")
parser.add_option("-i","--index", dest="index", action="store_true",
- help="build an index file")
- parser.add_option("-u","--usetoday", dest="usetoday", action="store_true",
- help="use current date for unreleased versions")
+ default=False, help="build an index file")
+ parser.add_option("-l","--license", dest="license", action="store_false",
+ default=True, help="Add an ASF license")
parser.add_option("-n","--lint", dest="lint", action="store_true",
help="use lint flag to exit on failures")
+ parser.add_option("-p", "--project", dest="projects",
+ action="append", type="string",
+ help="projects in JIRA to include in releasenotes", metavar="PROJECT")
+ parser.add_option("-r", "--range", dest="range", action="store_true",
+ default=False, help="Given versions are a range")
+ parser.add_option("-t", "--projecttitle", dest="title",
+ type="string",
+ help="Title to use for the project (default is Apache PROJECT)")
+ parser.add_option("-u","--usetoday", dest="usetoday", action="store_true",
+ default=False, help="use current date for unreleased versions")
+ parser.add_option("-v", "--version", dest="versions",
+ action="append", type="string",
+ help="versions in JIRA to include in releasenotes", metavar="VERSION")
(options, args) = parser.parse_args()
if (options.versions is None):
@@ -377,169 +407,169 @@ def main():
if (len(options.versions) <= 0):
parser.error("At least one version needs to be supplied")
- versions = [ Version(v) for v in options.versions ];
+ projects = options.projects
+
+ if (options.range is True):
+ versions = [ Version(v) for v in GetVersions(options.versions, projects).getlist() ]
+ else:
+ versions = [ Version(v) for v in options.versions ]
versions.sort();
- maxVersion = str(versions[-1])
+ if (options.title is None):
+ title=projects[0]
+ else:
+ title=options.title
- jlist = JiraIter(versions)
- version = maxVersion
+ for v in versions:
+ vstr=str(v)
+ jlist = JiraIter(vstr,projects)
- if version in releaseVersion:
- reldate=releaseVersion[version]
- elif options.usetoday:
- reldate=strftime("%Y-%m-%d", gmtime())
- else:
- reldate="Unreleased"
+ if vstr in releaseVersion:
+ reldate=releaseVersion[vstr]
+ elif options.usetoday:
+ reldate=strftime("%Y-%m-%d", gmtime())
+ else:
+ reldate="Unreleased"
- if not os.path.exists(version):
- os.mkdir(version)
+ if not os.path.exists(vstr):
+ os.mkdir(vstr)
- if options.master:
reloutputs = Outputs("%(ver)s/RELEASENOTES.%(ver)s.md",
"%(ver)s/RELEASENOTES.%(key)s.%(ver)s.md",
- [], {"ver":maxVersion, "date":reldate})
+ [], {"ver":v, "date":reldate, "title":title})
choutputs = Outputs("%(ver)s/CHANGES.%(ver)s.md",
"%(ver)s/CHANGES.%(key)s.%(ver)s.md",
- [], {"ver":maxVersion, "date":reldate})
- else:
- reloutputs = Outputs("%(ver)s/RELEASENOTES.%(ver)s.md",
- "%(ver)s/RELEASENOTES.%(key)s.%(ver)s.md",
- ["HADOOP","HDFS","MAPREDUCE","YARN"], {"ver":maxVersion, "date":reldate})
- choutputs = Outputs("%(ver)s/CHANGES.%(ver)s.md",
- "%(ver)s/CHANGES.%(key)s.%(ver)s.md",
- ["HADOOP","HDFS","MAPREDUCE","YARN"], {"ver":maxVersion, "date":reldate})
-
- reloutputs.writeAll(asflicense)
- choutputs.writeAll(asflicense)
-
- relhead = '# Hadoop %(key)s %(ver)s Release Notes\n\n' \
- 'These release notes cover new developer and user-facing incompatibilities, features, and major improvements.\n\n'
-
- chhead = '# Hadoop Changelog\n\n' \
- '## Release %(ver)s - %(date)s\n'\
- '\n'
-
- reloutputs.writeAll(relhead)
- choutputs.writeAll(chhead)
-
- errorCount=0
- warningCount=0
- lintMessage=""
- incompatlist=[]
- buglist=[]
- improvementlist=[]
- newfeaturelist=[]
- subtasklist=[]
- tasklist=[]
- testlist=[]
- otherlist=[]
-
- for jira in sorted(jlist):
- if jira.getIncompatibleChange():
- incompatlist.append(jira)
- if (len(jira.getReleaseNote())==0):
- warningCount+=1
-
- if jira.checkVersionString():
- warningCount+=1
-
- if jira.checkMissingComponent() or jira.checkMissingAssignee():
- errorCount+=1
- elif jira.getType() == "Bug":
- buglist.append(jira)
- elif jira.getType() == "Improvement":
- improvementlist.append(jira)
- elif jira.getType() == "New Feature":
- newfeaturelist.append(jira)
- elif jira.getType() == "Sub-task":
- subtasklist.append(jira)
- elif jira.getType() == "Task":
- tasklist.append(jira)
- elif jira.getType() == "Test":
- testlist.append(jira)
- else:
- otherlist.append(jira)
-
- line = '* [%s](https://issues.apache.org/jira/browse/%s) | *%s* | **%s**\n' \
- % (notableclean(jira.getId()), notableclean(jira.getId()), notableclean(jira.getPriority()),
- notableclean(jira.getSummary()))
-
- if (jira.getIncompatibleChange()) and (len(jira.getReleaseNote())==0):
- reloutputs.writeKeyRaw(jira.getProject(),"\n---\n\n")
- reloutputs.writeKeyRaw(jira.getProject(), line)
- line ='\n**WARNING: No release note provided for this incompatible change.**\n\n'
- lintMessage += "\nWARNING: incompatible change %s lacks release notes." % (notableclean(jira.getId()))
- reloutputs.writeKeyRaw(jira.getProject(), line)
-
- if jira.checkVersionString():
- lintMessage += "\nWARNING: Version string problem for %s " % jira.getId()
-
- if (jira.checkMissingComponent() or jira.checkMissingAssignee()):
- errorMessage=[]
- jira.checkMissingComponent() and errorMessage.append("component")
- jira.checkMissingAssignee() and errorMessage.append("assignee")
- lintMessage += "\nERROR: missing %s for %s " % (" and ".join(errorMessage) , jira.getId())
-
- if (len(jira.getReleaseNote())>0):
- reloutputs.writeKeyRaw(jira.getProject(),"\n---\n\n")
- reloutputs.writeKeyRaw(jira.getProject(), line)
- line ='\n%s\n\n' % (tableclean(jira.getReleaseNote()))
- reloutputs.writeKeyRaw(jira.getProject(), line)
-
- if (options.lint is True):
- print lintMessage
- print "======================================="
- print "Error:%d, Warning:%d \n" % (errorCount, warningCount)
-
- if (errorCount>0):
- cleanOutputDir(version)
- sys.exit(1)
-
- reloutputs.writeAll("\n\n")
- reloutputs.close()
-
- choutputs.writeAll("### INCOMPATIBLE CHANGES:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(incompatlist)
-
- choutputs.writeAll("\n\n### NEW FEATURES:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(newfeaturelist)
-
- choutputs.writeAll("\n\n### IMPROVEMENTS:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(improvementlist)
-
- choutputs.writeAll("\n\n### BUG FIXES:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(buglist)
-
- choutputs.writeAll("\n\n### TESTS:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(testlist)
-
- choutputs.writeAll("\n\n### SUB-TASKS:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(subtasklist)
-
- choutputs.writeAll("\n\n### OTHER:\n\n")
- choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
- choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
- choutputs.writeList(otherlist)
- choutputs.writeList(tasklist)
-
- choutputs.writeAll("\n\n")
- choutputs.close()
+ [], {"ver":v, "date":reldate, "title":title})
+
+ if (options.license is True):
+ reloutputs.writeAll(asflicense)
+ choutputs.writeAll(asflicense)
+
+ relhead = '# %(title)s %(key)s %(ver)s Release Notes\n\n' \
+ 'These release notes cover new developer and user-facing incompatibilities, features, and major improvements.\n\n'
+ chhead = '# %(title)s Changelog\n\n' \
+ '## Release %(ver)s - %(date)s\n'\
+ '\n'
+
+ reloutputs.writeAll(relhead)
+ choutputs.writeAll(chhead)
+ errorCount=0
+ warningCount=0
+ lintMessage=""
+ incompatlist=[]
+ buglist=[]
+ improvementlist=[]
+ newfeaturelist=[]
+ subtasklist=[]
+ tasklist=[]
+ testlist=[]
+ otherlist=[]
+
+ for jira in sorted(jlist):
+ if jira.getIncompatibleChange():
+ incompatlist.append(jira)
+ if (len(jira.getReleaseNote())==0):
+ warningCount+=1
+
+ if jira.checkVersionString():
+ warningCount+=1
+
+ if jira.checkMissingComponent() or jira.checkMissingAssignee():
+ errorCount+=1
+ elif jira.getType() == "Bug":
+ buglist.append(jira)
+ elif jira.getType() == "Improvement":
+ improvementlist.append(jira)
+ elif jira.getType() == "New Feature":
+ newfeaturelist.append(jira)
+ elif jira.getType() == "Sub-task":
+ subtasklist.append(jira)
+ elif jira.getType() == "Task":
+ tasklist.append(jira)
+ elif jira.getType() == "Test":
+ testlist.append(jira)
+ else:
+ otherlist.append(jira)
+
+ line = '* [%s](https://issues.apache.org/jira/browse/%s) | *%s* | **%s**\n' \
+ % (notableclean(jira.getId()), notableclean(jira.getId()), notableclean(jira.getPriority()),
+ notableclean(jira.getSummary()))
+
+ if (jira.getIncompatibleChange()) and (len(jira.getReleaseNote())==0):
+ reloutputs.writeKeyRaw(jira.getProject(),"\n---\n\n")
+ reloutputs.writeKeyRaw(jira.getProject(), line)
+ line ='\n**WARNING: No release note provided for this incompatible change.**\n\n'
+ lintMessage += "\nWARNING: incompatible change %s lacks release notes." % (notableclean(jira.getId()))
+ reloutputs.writeKeyRaw(jira.getProject(), line)
+
+ if jira.checkVersionString():
+ lintMessage += "\nWARNING: Version string problem for %s " % jira.getId()
+
+ if (jira.checkMissingComponent() or jira.checkMissingAssignee()):
+ errorMessage=[]
+ jira.checkMissingComponent() and errorMessage.append("component")
+ jira.checkMissingAssignee() and errorMessage.append("assignee")
+ lintMessage += "\nERROR: missing %s for %s " % (" and ".join(errorMessage) , jira.getId())
+
+ if (len(jira.getReleaseNote())>0):
+ reloutputs.writeKeyRaw(jira.getProject(),"\n---\n\n")
+ reloutputs.writeKeyRaw(jira.getProject(), line)
+ line ='\n%s\n\n' % (tableclean(jira.getReleaseNote()))
+ reloutputs.writeKeyRaw(jira.getProject(), line)
+
+ if (options.lint is True):
+ print lintMessage
+ print "======================================="
+ print "Error:%d, Warning:%d \n" % (errorCount, warningCount)
+
+ if (errorCount>0):
+ cleanOutputDir(version)
+ sys.exit(1)
+
+ reloutputs.writeAll("\n\n")
+ reloutputs.close()
+
+ choutputs.writeAll("### INCOMPATIBLE CHANGES:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(incompatlist)
+
+ choutputs.writeAll("\n\n### NEW FEATURES:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(newfeaturelist)
+
+ choutputs.writeAll("\n\n### IMPROVEMENTS:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(improvementlist)
+
+ choutputs.writeAll("\n\n### BUG FIXES:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(buglist)
+
+ choutputs.writeAll("\n\n### TESTS:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(testlist)
+
+ choutputs.writeAll("\n\n### SUB-TASKS:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(subtasklist)
+
+ choutputs.writeAll("\n\n### OTHER:\n\n")
+ choutputs.writeAll("| JIRA | Summary | Priority | Component | Reporter | Contributor |\n")
+ choutputs.writeAll("|:---- |:---- | :--- |:---- |:---- |:---- |\n")
+ choutputs.writeList(otherlist)
+ choutputs.writeList(tasklist)
+
+ choutputs.writeAll("\n\n")
+ choutputs.close()
if options.index:
- buildindex(options.master)
+ buildindex(title,options.license)
if __name__ == "__main__":
main()