Merge "Do not use with_items for package installs"
[releng/builder.git] / jjb / autorelease / notify-build-failure.sh
1 #!/bin/bash -l
2 # SPDX-License-Identifier: EPL-1.0
3 ##############################################################################
4 # Copyright (c) 2017 The Linux Foundation and others.
5 #
6 # All rights reserved. This program and the accompanying materials
7 # are made available under the terms of the Eclipse Public License v1.0
8 # which accompanies this distribution, and is available at
9 # http://www.eclipse.org/legal/epl-v10.html
10 ##############################################################################
11 # This script parses the console log to discover which project has caused a
12 # build failure and notify the project as appropriate.
13
14 echo "---> notify-build-failure.sh"
15
16 NEWLINE=$'\n'
17 RELEASE_EMAIL="release@lists.opendaylight.org"
18 ARCHIVES_DIR="$JENKINS_HOSTNAME/$JOB_NAME/$BUILD_NUMBER"
19 CONSOLE_LOG="/tmp/autorelease-build.log"
20 STREAM=${JOB_NAME#*-*e-}
21 ERROR_LOG="$WORKSPACE/archives/error.log.gz"
22
23 wget -nv -O "$CONSOLE_LOG" "${BUILD_URL}consoleText"
24
25 # TODO: This section is still required since some of the projects use
26 # description. Remove this section when the reactor info is more consistant.
27 # extract failing project from reactor information
28 REACTOR_INFO=$(awk '/Reactor Summary:/ { flag=1 }
29           flag {
30              if ( sub(/^\[(INFO)\]/,"") && sub(/FAILURE \[.*/,"") ) {
31                  gsub(/[[:space:]]*::[[:space:]]*/,"::")
32                  gsub(/^[[:space:]]+|[[:space:]]+$|[.]/,"")
33                  print
34              }
35           }
36           /Final Memory:/ { flag=0 }' $CONSOLE_LOG)
37
38 # check for project format
39 if [[ ${REACTOR_INFO} =~ .*::*.*::*. ]]; then
40     # extract project and artifactId from full format
41     # Ex: REACTOR_INFO="ODL::sfc::odl-sfc-pot-netconf-renderer 072 " is broken down into
42     # NAME="ODL", PROJECT_="sfc" and NAME="odl-sfc-pot-netconf-renderer"
43     ODL=$(echo "${REACTOR_INFO}" | awk -F'::' '{ gsub(/^[ \t]+|[ \t]+[0-9]+[ \t]+$|[ \t]+$/, "", $1); print $1}')
44     PROJECT_=$(echo "${REACTOR_INFO}" | awk -F'::' '{ gsub(/^[ \t]+|[ \t]+[0-9]+[ \t]+$|[ \t]+$/, "", $2); print $2}')
45     NAME=$(echo "${REACTOR_INFO}" | awk -F'::' '{ gsub(/^[ \t]+|[ \t]+[0-9]+[ \t]+$|[ \t]+$/, "", $3); print $3}')
46 else
47     # set project from partial format
48     ODL=""
49     PROJECT_=""
50     NAME=$(echo "${REACTOR_INFO}" | awk '{ gsub(/^[ \t]+|[ \t]+$/, ""); print }')
51 fi
52
53 # determine ARTIFACT_ID for project mailing list
54 ARTIFACT_ID=$(awk -F: '/\[ERROR\].*mvn <goals> -rf :/ { print $2}' $CONSOLE_LOG)
55
56 # determine project mailing list using xpaths
57 # if project.groupId:
58 #     project.groupId is set and is not inherited
59 # else if project.parent.groupId:
60 #     project.groupId is not set but IS inherited from project.parent.groupId
61 # else
62 #     exclude project mailing list
63 if [ ! -z "$ARTIFACT_ID" ]; then
64     grouplist=()
65     while IFS="" read -r p; do
66         GROUP=$(xmlstarlet sel\
67               -N "x=http://maven.apache.org/POM/4.0.0"\
68               -t -m "/x:project[x:artifactId='$ARTIFACT_ID']"\
69               --if "/x:project/x:groupId"\
70               -v "/x:project/x:groupId"\
71               --elif "/x:project/x:parent/x:groupId"\
72               -v "/x:project/x:parent/x:groupId"\
73               --else -o ""\
74               "$p" 2>/dev/null)
75         if [ ! -z "${GROUP}" ]; then
76             # shellcheck disable=SC2207
77             grouplist+=($(echo "${GROUP}" | awk -F'.' '{ print $3 }'))
78         fi
79     done < <(find . -name "pom.xml")
80
81     if [ "${#grouplist[@]}" -eq 1 ]; then
82         PROJECT="${grouplist[0]}"
83     elif [ "${#grouplist[@]}" -gt 1 ]; then
84         GROUPLIST="NOTE: The artifactId: $ARTIFACT_ID matches multiple groups: ${grouplist[*]}"
85     else
86         echo "Unable to determine project.groupId using xpaths"
87     fi
88 else
89     echo "Unable to determine failed ARTIFACT_ID. Build likely successful or bug in this script."
90     exit 0
91 fi
92
93 # Construct email subject & body
94 PROJECT_STRING=${PROJECT:+" from $PROJECT"}
95 SUBJECT="[release] Autorelease $STREAM failed to build $ARTIFACT_ID$PROJECT_STRING"
96 # shellcheck disable=SC2034
97 ATTACHMENT_INCLUDE="Attached is a snippet of the error message related to the
98 failure that we were able to automatically parse as well as console logs."
99 # shellcheck disable=SC2034
100 ATTACHMENT_EXCLUDE="Unable to attach error message snippet related to the failure
101 since this exceeds the mail server attachment size limit. Please
102 refer ${ERROR_LOG##*/} in archives directory."
103 ATTACHMENT=ATTACHMENT_INCLUDE  # default behaviour
104 BODY="Attention ${PROJECT:-"OpenDaylight"}-devs,
105
106 Autorelease $STREAM failed to build $ARTIFACT_ID$PROJECT_STRING in build
107 $BUILD_NUMBER. \${!ATTACHMENT} ${PROJECT:+${NEWLINE}${GROUPLIST}}
108
109 Console Logs:
110 https://logs.opendaylight.org/$SILO/$ARCHIVES_DIR
111
112 Jenkins Build:
113 $BUILD_URL
114
115 Please review and provide an ETA on when a fix will be available.
116
117 Thanks,
118 ODL releng/autorelease team
119 "
120
121 # check if remote staging is complete successfully
122 BUILD_STATUS=$(awk '/\[INFO\] Remote staging finished/{flag=1;next}/Total time:/{flag=0}flag' $CONSOLE_LOG \
123                    | grep '\] BUILD' | awk '{print $3}')
124
125 if ([ ! -z "${NAME}" ] || [ ! -z "${ARTIFACT_ID}" ]) && [[ "${BUILD_STATUS}" != "SUCCESS" ]]; then
126     # project search pattern should handle both scenarios
127     # 1. Full format:    ODL :: $PROJECT :: $ARTIFACT_ID
128     # 2. Partial format: Building $ARTIFACT_ID
129     sed -e "/\[INFO\] Building \(${NAME} \|${ARTIFACT_ID} \|${ODL} :: ${PROJECT_} :: ${NAME} \)/,/Reactor Summary:/!d;//d" \
130           $CONSOLE_LOG | gzip > "$ERROR_LOG"
131
132     if [ -n "${PROJECT}" ]; then
133         RELEASE_EMAIL="${RELEASE_EMAIL}, ${PROJECT}-dev@lists.opendaylight.org"
134     fi
135
136     file_size=$(du -k "$ERROR_LOG" | cut -f1)
137
138     # Only send emails in production (releng), not testing (sandbox)
139     if [ "${SILO}" == "releng" ]; then
140         if [[ "$file_size" -gt 100 ]]; then
141             # shellcheck disable=SC2034
142             ATTACHMENT=ATTACHMENT_EXCLUDE
143             eval echo \""${BODY}"\" | mail \
144                 -r "Jenkins <jenkins-dontreply@opendaylight.org>" \
145                 -s "${SUBJECT}" "${RELEASE_EMAIL}"
146         else
147             eval echo \""${BODY}"\" | mail -a "$ERROR_LOG" \
148                 -r "Jenkins <jenkins-dontreply@opendaylight.org>" \
149                 -s "${SUBJECT}" "${RELEASE_EMAIL}"
150         fi
151     elif [ "${SILO}" == "sandbox" ]; then
152         echo "Running in sandbox, not actually sending notification emails"
153         echo "Subject: ${SUBJECT}"
154         eval echo \""Body: ${BODY}"\"
155     else
156         echo "Not sure how to notify in \"${SILO}\" Jenkins silo"
157     fi
158 fi
159
160 rm $CONSOLE_LOG