Created
April 11, 2022 09:49
-
-
Save reckface/c9b8da097d23f413ecfbe900036c03d8 to your computer and use it in GitHub Desktop.
Self-hosted Azure DevOps agents
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -e | |
if [ -z "$AZP_URL" ]; then | |
echo 1>&2 "error: missing AZP_URL environment variable" | |
exit 1 | |
fi | |
print_header() { | |
lightcyan='\033[1;36m' | |
nocolor='\033[0m' | |
echo -e "${lightcyan}$1${nocolor}" | |
} | |
DEV_CERT="${DEV_CERT_FILE:-devops_server.crt}" | |
if [ ! -e "$DEV_CERT" ]; then | |
print_header "Installing Corporate certificates." | |
cp $DEV_CERT /etc/pki/ca-trust/source/anchors/ | |
update-ca-trust extract | |
keytool -importcert -file /etc/pki/ca-trust/source/anchors/coporate_root.crt -alias coporate_Root -trustcacerts -storepass changeit -noprompt | |
keytool -importcert -file /etc/pki/ca-trust/source/anchors/$DEV_CERT -alias DevOps -trustcacerts -storepass changeit -noprompt | |
fi | |
if [ -z "$AZP_TOKEN_FILE" ]; then | |
if [ -z "$AZP_TOKEN" ]; then | |
echo 1>&2 "error: missing AZP_TOKEN environment variable" | |
exit 1 | |
fi | |
AZP_TOKEN_FILE=/azp/.token | |
echo -n $AZP_TOKEN > "$AZP_TOKEN_FILE" | |
fi | |
unset AZP_TOKEN | |
if [ -n "$AZP_WORK" ]; then | |
mkdir -p "$AZP_WORK" | |
fi | |
export AGENT_ALLOW_RUNASROOT="1" | |
cleanup() { | |
if [ -e config.sh ]; then | |
print_header "Cleanup. Removing Azure Pipelines agent..." | |
# If the agent has some running jobs, the configuration removal process will fail. | |
# So, give it some time to finish the job. | |
print_header "Cleanup. updating $AZP_URL..." | |
# the 'dirname' command strips the collection name from the url | |
base_url=$(dirname "$AZP_URL") | |
# then I replace the baseUrl with the full url | |
if [ "$base_url" != "$AZP_URL" ]; then | |
sed -i "s,$base_url,$AZP_URL,g" .agent | |
sed -i "s,$base_url,$AZP_URL,g" .credentials | |
fi | |
cat .agent | |
while true; do | |
./config.sh remove --unattended --auth PAT --token $(cat "$AZP_TOKEN_FILE") && break | |
echo "Retrying in 30 seconds..." | |
sleep 30 | |
done | |
fi | |
} | |
# Let the agent ignore the token env variables | |
export VSO_AGENT_IGNORE=AZP_TOKEN,AZP_TOKEN_FILE | |
print_header "1. Determining matching Azure Pipelines agent..." | |
AZP_AGENT_PACKAGES=$(curl -LsS \ | |
-u user:$(cat "$AZP_TOKEN_FILE") \ | |
-H 'Accept:application/json;' \ | |
"$AZP_URL/_apis/distributedtask/packages/agent?platform=$TARGETARCH&top=1") | |
AZP_AGENT_PACKAGE_LATEST_URL=$(echo "$AZP_AGENT_PACKAGES" | jq -r '.value[0].downloadUrl') | |
if [ -z "$AZP_AGENT_PACKAGE_LATEST_URL" -o "$AZP_AGENT_PACKAGE_LATEST_URL" == "null" ]; then | |
echo 1>&2 "error: could not determine a matching Azure Pipelines agent" | |
echo 1>&2 "check that account '$AZP_URL' is correct and the token is valid for that account" | |
exit 1 | |
fi | |
print_header "2. Downloading and extracting Azure Pipelines agent..." | |
curl -LsS $AZP_AGENT_PACKAGE_LATEST_URL | tar -xz & wait $! | |
CREATED_ON=$(date +%F) | |
# persist variables | |
touch .env | |
echo "CREATED_ON=$CREATED_ON" >> .env | |
export JAVA_HOME=$(readlink -f /usr/bin/java | sed "s:/bin/java::") | |
echo "JAVA_HOME=$JAVA_HOME" >> .env | |
export PATH="$PATH:$JAVA_HOME/bin" | |
PREFIX="docker-agent" | |
SUFFIX=$(openssl rand -hex 2); | |
if [[ -z "${ECS_CONTAINER_METADATA_URI}" ]]; then | |
echo "Not running in ECS" | |
else | |
echo "HOST_TYPE=ECS" >> .env | |
SUFFIX=$(echo "$ECS_CONTAINER_METADATA_URI" | awk -F/ '{print $NF}' | cut -d "-" -f 1) | |
PREFIX="ecs-task" | |
fi | |
if [[ -z "${KUBERNETES_SERVICE_HOST}" ]]; then | |
echo "Not running in EKS" | |
else | |
echo "HOST_TYPE=EKS" >> .env | |
SUFFIX=$(echo "$HOSTNAME" | awk -F- '{print $NF}') | |
PREFIX="eks-pod" | |
fi | |
source ./env.sh | |
print_header "3. Configuring Azure Pipelines agent..." | |
./config.sh --unattended \ | |
--agent "${AZP_AGENT_NAME:-$PREFIX-$SUFFIX}" \ | |
--url "$AZP_URL" \ | |
--auth PAT \ | |
--token $(cat "$AZP_TOKEN_FILE") \ | |
--pool "${AZP_POOL:-core_docker}" \ | |
--work "${AZP_WORK:-_work}" \ | |
--replace \ | |
--sslskipcertvalidation \ | |
--acceptTeeEula & wait $! | |
print_header "4. Running Azure Pipelines agent..." | |
trap 'cleanup; exit 0' EXIT | |
trap 'cleanup; exit 130' INT | |
trap 'cleanup; exit 143' TERM | |
chmod +x ./run.sh | |
# To be aware of TERM and INT signals call run.sh | |
# Running it with the --once flag at the end will shut down the agent after the build is executed | |
./run.sh "$@" & wait $! |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
FROM amazonlinux:latest | |
# To make it easier for build and release pipelines to run apt-get, | |
# configure apt to not require confirmation (assume the -y argument by default) | |
# ENV DEBIAN_FRONTEND=noninteractive | |
RUN yum update -y && yum install -y git cmake gcc make \ | |
openssl-devel libssh2-devel openssh-server \ | |
ca-certificates curl wget jq tar libicu67 zip unzip \ | |
openssl tree \ | |
git-daemon | |
RUN yum install -y java-11-amazon-corretto-headless | |
RUN update-ca-trust enable | |
RUN yum install -y https://github.com/PowerShell/PowerShell/releases/download/v7.2.2/powershell-lts-7.2.2-1.rh.x86_64.rpm | |
ENV DOTNET_SYSTEM_GLOBALIZATION_INVARIANT=1 | |
RUN rpm -Uvh https://packages.microsoft.com/config/centos/7/packages-microsoft-prod.rpm | |
RUN yum install -y dotnet-sdk-3.1 dotnet-sdk-6.0 | |
RUN JAVA_HOME=$(readlink -f /usr/bin/java | sed "s:/bin/java::") \ | |
echo $JAVA_HOME \ | |
java -version | |
COPY p80root.crt /etc/pki/ca-trust/source/anchors/ | |
RUN update-ca-trust extract; | |
ENV PATH="$PATH:/tmp/.dotnet/tools" | |
ENV DOTNET_CLI_HOME=/tmp | |
RUN echo $PATH | |
RUN dotnet tool install -g dotnetsay | |
RUN dotnet tool list -g | |
# Can be 'linux-x64', 'linux-arm64', 'linux-arm', 'rhel.6-x64'. | |
ENV TARGETARCH=rhel.6-x64 | |
RUN rpmkeys --import "http://keyserver.ubuntu.com/pks/lookup?op=get&search=0x3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF" && \ | |
curl https://download.mono-project.com/repo/centos7-stable.repo | tee /etc/yum.repos.d/mono-centos7-stable.repo && \ | |
yum update -y && yum install -y mono-devel | |
WORKDIR /azp | |
COPY p80root.crt . | |
COPY devops-server.crt . | |
COPY ./start.sh . | |
RUN chmod +x start.sh | |
ENTRYPOINT ["./start.sh"] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
set -e | |
if [ -z "$AZP_URL" ]; then | |
echo 1>&2 "error: missing AZP_URL environment variable" | |
exit 1 | |
fi | |
if [ -z "$AZP_HOST" ]; then | |
echo 1>&2 "error: missing AZP_HOST environment variable" | |
exit 1 | |
fi | |
print_header() { | |
lightcyan='\033[1;36m' | |
nocolor='\033[0m' | |
echo -e "${lightcyan}$1${nocolor}" | |
} | |
DEV_CERT=devops_host.crt | |
if [ ! -e "$DEV_CERT" ]; then | |
print_header "Installing Corporate certificates." | |
echo -n | openssl s_client -connect $AZP_HOST:443 -servername $AZP_HOST \ | |
| openssl x509 > $DEV_CERT | |
cp $DEV_CERT /usr/local/share/ca-certificates/ | |
update-ca-certificates | |
keytool -importcert -file /usr/local/share/ca-certificates/coporate_root.crt -alias CorporateRoot -cacerts -storepass changeit -noprompt | |
keytool -importcert -file /usr/local/share/ca-certificates/$DEV_CERT -alias DevOps -cacerts -storepass changeit -noprompt | |
cert-sync /etc/ssl/certs/ca-certificates.crt | |
fi | |
if [ -z "$AZP_TOKEN_FILE" ]; then | |
if [ -z "$AZP_TOKEN" ]; then | |
echo 1>&2 "error: missing AZP_TOKEN environment variable" | |
exit 1 | |
fi | |
AZP_TOKEN_FILE=/azp/.token | |
echo -n $AZP_TOKEN > "$AZP_TOKEN_FILE" | |
fi | |
unset AZP_TOKEN | |
if [ -n "$AZP_WORK" ]; then | |
mkdir -p "$AZP_WORK" | |
fi | |
export AGENT_ALLOW_RUNASROOT="1" | |
cleanup() { | |
if [ -e config.sh ]; then | |
print_header "Cleanup. Removing Azure Pipelines agent..." | |
# If the agent has some running jobs, the configuration removal process will fail. | |
# So, give it some time to finish the job. | |
print_header "Cleanup. updating $AZP_URL..." | |
# the 'dirname' command strips the collection name from the url | |
base_url=$(dirname "$AZP_URL") | |
# then I replace the baseUrl with the full url | |
if [ "$base_url" != "$AZP_URL" ]; then | |
sed -i "s,$base_url,$AZP_URL,g" .agent | |
sed -i "s,$base_url,$AZP_URL,g" .credentials | |
fi | |
cat .agent | |
while true; do | |
./config.sh remove --unattended --auth PAT --token $(cat "$AZP_TOKEN_FILE") && break | |
echo "Retrying in 30 seconds..." | |
sleep 30 | |
done | |
fi | |
} | |
# Let the agent ignore the token env variables | |
export VSO_AGENT_IGNORE=AZP_TOKEN,AZP_TOKEN_FILE | |
print_header "1. Determining matching Azure Pipelines agent..." | |
AZP_AGENT_PACKAGES=$(curl -LsS \ | |
-u user:$(cat "$AZP_TOKEN_FILE") \ | |
-H 'Accept:application/json;' \ | |
"$AZP_URL/_apis/distributedtask/packages/agent?platform=$TARGETARCH&top=1") | |
AZP_AGENT_PACKAGE_LATEST_URL=$(echo "$AZP_AGENT_PACKAGES" | jq -r '.value[0].downloadUrl') | |
if [ -z "$AZP_AGENT_PACKAGE_LATEST_URL" -o "$AZP_AGENT_PACKAGE_LATEST_URL" == "null" ]; then | |
echo 1>&2 "error: could not determine a matching Azure Pipelines agent" | |
echo 1>&2 "check that account '$AZP_URL' is correct and the token is valid for that account" | |
exit 1 | |
fi | |
print_header "2. Downloading and extracting Azure Pipelines agent..." | |
curl -LsS $AZP_AGENT_PACKAGE_LATEST_URL | tar -xz & wait $! | |
export PATH="$PATH:/tmp/.dotnet/tools" | |
source ./env.sh | |
print_header "3. Configuring Azure Pipelines agent..." | |
./config.sh --unattended \ | |
--agent "${AZP_AGENT_NAME:-agent_$(hostname)}" \ | |
--url "$AZP_URL" \ | |
--auth PAT \ | |
--token $(cat "$AZP_TOKEN_FILE") \ | |
--pool "${AZP_POOL:-core_docker}" \ | |
--work "${AZP_WORK:-_work}" \ | |
--replace \ | |
--sslskipcertvalidation \ | |
--acceptTeeEula & wait $! | |
print_header "4. Running Azure Pipelines agent..." | |
trap 'cleanup; exit 0' EXIT | |
trap 'cleanup; exit 130' INT | |
trap 'cleanup; exit 143' TERM | |
chmod +x ./run.sh | |
# To be aware of TERM and INT signals call run.sh | |
# Running it with the --once flag at the end will shut down the agent after the build is executed | |
./run.sh "$@" & wait $! |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
FROM ubuntu:21.10 | |
# To make it easier for build and release pipelines to run apt-get, | |
# configure apt to not require confirmation (assume the -y argument by default) | |
ENV DEBIAN_FRONTEND=noninteractive | |
RUN echo "APT::Get::Assume-Yes \"true\";" > /etc/apt/apt.conf.d/90assumeyes | |
RUN apt-get update && apt-get install -y --no-install-recommends \ | |
ca-certificates \ | |
curl \ | |
jq \ | |
git \ | |
iputils-ping \ | |
libcurl4 \ | |
libicu67 \ | |
libunwind8 \ | |
netcat \ | |
libssl1.0 \ | |
wget \ | |
apt-transport-https \ | |
dirmngr \ | |
software-properties-common \ | |
default-jre \ | |
tree \ | |
openssl \ | |
ca-certificates-java \ | |
&& rm -rf /var/lib/apt/lists/* | |
RUN apt-get update && apt-get install -y \ | |
zip | |
RUN export java=$(update-java-alternatives -l | head -n 1 | awk -F ' ' '{print $NF}') | |
# Install dotnet | |
RUN wget -q https://packages.microsoft.com/config/ubuntu/20.04/packages-microsoft-prod.deb; \ | |
dpkg -i packages-microsoft-prod.deb; \ | |
apt-get update; \ | |
apt-get install -y \ | |
dotnet-sdk-3.1 \ | |
dotnet-sdk-6.0 \ | |
powershell; \ | |
dotnet tool install -g dotnetsay; \ | |
apt install nuget; \ | |
apt-get update; \ | |
export PATH="$PATH:/tmp/.dotnet/tools" | |
COPY coporate_root.crt /usr/local/share/ca-certificates/ | |
COPY coporate_na.crt /usr/local/share/ca-certificates/ | |
RUN update-ca-certificates; | |
# Can be 'linux-x64', 'linux-arm64', 'linux-arm', 'rhel.6-x64'. | |
ENV TARGETARCH=linux-x64 | |
RUN apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3FA7E0328081BFF6A14DA29AA6A19B38D3D831EF; \ | |
echo "deb https://download.mono-project.com/repo/ubuntu stable-trusty main" | tee /etc/apt/sources.list.d/mono-official-stable.list; \ | |
apt-get update; \ | |
apt-get install -y --no-install-recommends mono-complete; \ | |
rm -rf /var/lib/apt/lists/* | |
WORKDIR /azp | |
COPY coporate_root.crt . | |
COPY coporate_na.crt . | |
COPY ./start.sh . | |
RUN chmod +x start.sh | |
ENTRYPOINT ["./ubuntu-start.sh"] |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment