The \href{https://build.libelektra.org/}{\tt Elektra buildserver} handles a variety of tasks that reaches from testing Pull Requests (P\+Rs) to deploying new versions of the Elektra homepage.

\subsection*{Legacy build jobs}

Build jobs that are not ported into Jenkinsfiles use {\ttfamily Github Pull Request Builder} to trigger builds on PR\textquotesingle{}s.

If you are not yet authorized, the following question will be asked (by user )\+: \begin{DoxyVerb}Can one of the admins verify if this patch should be build?
\end{DoxyVerb}


Then one of the admins (sorted by activity)\+:


\begin{DoxyItemize}
\item 
\item 
\item 
\item 
\item 
\item 
\end{DoxyItemize}

need to confirm by saying\+: \begin{DoxyVerb}.*add\W+to\W+whitelist.*
\end{DoxyVerb}


or if just the pull request should be checked\+: \begin{DoxyVerb}.*build\W+allow.*
\end{DoxyVerb}


Afterwards builds can be issued via commands as described in {\ttfamily T\+R\+I\+G\+G\+E\+RS} below.

\subsection*{Jenkinsfiles}

Jenkinsfiles describe what actions the build system should execute on what build slave. Currently Elektra uses two different files.

\subsubsection*{Jenkinsfile.\+daily}


\begin{DoxyItemize}
\item Jenkinsfile.\+daily is for daily maintanence tasks, like cleaning up build servers.
\item \href{https://build.libelektra.org/jenkins/job/libelektra-daily/}{\tt Buildjob\+: libelektra-\/daily}
\item \href{https://master.libelektra.org/scripts/jenkins/Jenkinsfile.daily}{\tt Jenkinsfile.\+daily}
\end{DoxyItemize}

\subsubsection*{Jenkinsfile}


\begin{DoxyItemize}
\item Triggered on code changes and is for testing changes to the codebase.
\item \href{https://build.libelektra.org/jenkins/job/libelektra/}{\tt Buildjob\+: libelektra}
\item \href{https://master.libelektra.org/scripts/jenkins/Jenkinsfile}{\tt Jenkinsfile}
\end{DoxyItemize}

\subsubsection*{D\+SL}

The language used is a groovy based D\+SL described in the \href{https://jenkins.io/doc/book/pipeline/jenkinsfile/}{\tt Jenkinsfile book}. Most groovy syntax is allowed to describe pipelines in a Jenkinsfile, but it is executed in a sandbox which might block certain calls.

Since plugins might extend the pool of available commands or variables a full list of currently available syntax can be seen in \href{https://build.libelektra.org/jenkins/job/libelektra/pipeline-syntax/}{\tt pipeline syntax} after a login to the build server.

\subsection*{Security}

Since a malicious PR could easily destroy the build server and slaves or expose credentials some restrictions are introduced. Only PR authors that have the right to push to libelektra can modify the Jenkinsfile and have those changes be respected for the respective branch.

This setting can be modified on the respective build job configuration site.

\subsection*{Triggers}

All Triggers are described in the configuration of the respective build jobs.

The \href{https://build.libelektra.org/jenkins/job/libelektra-daily/}{\tt daily build} is executed according to a cron schedule.

The \href{https://build.libelektra.org/jenkins/job/libelektra/}{\tt libelektra} build is triggered for all branches of the libelektra repository except for {\ttfamily debian}. Additionally all open branches in forks targeting libelektra\textquotesingle{}s repository via P\+Rs are going to be build. Pushes to any of those branches will trigger a new build automatically.

The following phrases can be used as comments to manually trigger a specific build\+:


\begin{DoxyItemize}
\item jenkins build \href{https://build.libelektra.org/jenkins/job/libelektra-daily/}{\tt daily} please
\item jenkins build \href{https://build.libelektra.org/job/elektra-git-buildpackage-jessie/}{\tt git-\/buildpackage-\/jessie} please
\item jenkins build \href{https://build.libelektra.org/jenkins/job/libelektra/}{\tt libelektra} please
\end{DoxyItemize}

Additionally {\ttfamily jenkins build all please} can be used to trigger all build jobs relevant for PR\textquotesingle{}s. Since this needs a lot of resources please use it only if


\begin{DoxyItemize}
\item all of the {\bfseries standard PR jobs} were already {\bfseries successful}, and
\item you are sure that you {\bfseries do not want change anything} in your PR anymore
\end{DoxyItemize}

\subsection*{Test Environments}

We use Docker containers to provide the various test environments.

They are described \href{https://master.libelektra.org/scripts/docker}{\tt in the repository} and the Jenkinsfile describes how to build them. If a rebuild of the images is needed is determined by the hash of the Dockerfile used to describe it. If it has not changed the build step will be skipped. In the case that an image needed a build it will afterwards be uploaded into a private Docker image registry (currently on a7) and thus is shared between all Docker capable build slaves.

\subsection*{Tests}

We will use the Docker images build as described earlier to run compilations and tests for Elektra. This allows us to run tests independent of which nodes are available (as the environment is portable).

The Jenkinsfile describes the steps used to run tests. Helper functions for easily adding new tests are available (build\+And\+Test, Build\+And\+Test\+Asan, ...).

The {\ttfamily with\+Docker\+Env} helper makes sure to print the following information at the start of a test branch\+:
\begin{DoxyItemize}
\item branch name
\item build machine
\item docker image id
\end{DoxyItemize}

Coverage reports are generated automatically when using the build\+And\+Test helper and the appropriate Cmake flags for coverage generation have been set. They are uploaded to \href{https://doc.libelektra.org/coverage/}{\tt https\+://doc.\+libelektra.\+org/coverage/}.

Artifacts from {\ttfamily ctest} are also preserved automatically when using build\+And\+Test. The function also takes care of providing a stagename based path so multiple tests can not overwrite files that share the same name.

Tests are executed in order dictated by the Jenkinsfile. In general new tests should be added to the \textquotesingle{}full build stage\textquotesingle{} that will only run after a standard full test run succeeded. This saves execution time on the build server for most common errors.

Since there is no strict way to enforce the way tests are added we encourage you to read the existing configuration and modify existing tests so they suite your needs.

\subsection*{Deployment}

For runs of the build job that are run in the master branch we also execute deployment steps after all tests pass. We use it to build debian packages and move it into the repository on the a7 node. Additionally we recompile the homepage and deploy it on the a7 node.

\subsection*{Issues with the build environment}

If you have issues that are related to the build system you can open a normal issue and tag it with {\ttfamily build} and {\ttfamily question}. If you feel like your inquiry does not warrent a issue on its own, please use \href{https://issues.libelektra.org/160}{\tt our buildserver issue}.

\subsection*{Jenkins}

This section describes how to replicate the current Jenkins configuration.

\subsubsection*{Jenkins libelektra configuration}

The {\ttfamily libelektra} build job is a multibranch pipeline job. It is easiest to add via the Blue\+Ocean interface.

Most of the default settings should be ok, however some settings need to be verified or added to build Elektra correctly\+:
\begin{DoxyItemize}
\item In Branch Sources under Behaviours {\ttfamily Filter by name} should be added to exclude the {\ttfamily debian} branch from being build. The reason for this is that the {\ttfamily debian} branch is not providing a Jenkinsfile.
\item {\ttfamily Advanced clone behaviors} should be added and the path to the git mirror needs to be specified\+: {\ttfamily /home/jenkins/git\+\_\+mirrors/libelektra}. This reference repository is created and maintained by our \href{https://build.libelektra.org/jenkins/job/libelektra-daily/}{\tt daily buildjob}.
\item Under Property strategy you can add {\ttfamily Trigger build on pull request comment}. {\ttfamily jenkins build (libelektra$\vert$all) please} is a good starting point.
\item For Build Configuration you want to specify {\ttfamily by Jenkinsfile} and add the script path\+: {\ttfamily scripts/jenkins/\+Jenkinsfile}.
\end{DoxyItemize}

\subsubsection*{Add a Jenkins node}

A node needs to have a J\+RE (Java Runtime Environment) installed. Further it should run an S\+SH (Secure S\+Hell) server. If you want to provide environments via Docker you need to install that as well.

A {\ttfamily jenkins} user with 47000\+:47000 ids should be created as this is what is expected in Docker images. Additionally a public key authentification should be set up so the jenkins master can establish an ssh connection with the node. If the node should be able to interact with Docker the jenkins user should be added to the {\ttfamily docker} group.

Nodes should be set to only build jobs matching their labels and to be online as much as possible. As for labels {\ttfamily gitmirror} should be if you want to cache repositories on this node. If Docker is available the {\ttfamily docker} label should be set. 