Skip to content

Commit

Permalink
#147: Use Bash process controller for CI process
Browse files Browse the repository at this point in the history
  • Loading branch information
BR0kEN- committed Jul 6, 2018
1 parent 0fd312e commit 4ab7213
Show file tree
Hide file tree
Showing 12 changed files with 209 additions and 145 deletions.
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
Expand Up @@ -16,3 +16,6 @@
[submodule "matrix/roles/api/files/cikit-rest-api"]
path = matrix/roles/api/files/cikit-rest-api
url = https://github.com/BR0kEN-/cikit-rest-api.git
[submodule "scripts/roles/cikit-ci/files/bash-process-controller"]
path = scripts/roles/cikit-ci/files/bash-process-controller
url = https://github.com/BR0kEN-/bash-process-controller.git
4 changes: 4 additions & 0 deletions cmf/all/.cikit/ci/post-deploy.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,10 @@
connection: local
become: yes

vars_files:
- ../config.yml
- ../../scripts/vars/main.yml

tasks:
- name: Move reports to the website directory
shell: "cp -r {{ workspace }}/docroot/reports/ {{ dist }}/docroot"
21 changes: 13 additions & 8 deletions cmf/all/.cikit/ci/server-cleaner.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,16 +16,21 @@

vars_files:
- ../config.yml

vars:
mysql_query: "mysql -u{{ mysql.user }} -p{{ mysql.pass }} -se"
- ../../scripts/vars/main.yml

tasks:
- name: Remove all builds
shell: "{{ item }}"
- name: Compute disk usage
shell: df -H | head -2 | tail -1 | awk '{printf "%d", $5}'
register: disk_usage

- name: Remove builds
shell: |-
COMMAND="mysql -u{{ mysql.user }} -p{{ mysql.pass }} -se"
${COMMAND} "SHOW DATABASES" | grep "{{ build_slug }}" | xargs -I "@@" ${COMMAND} "DROP DATABASE @@"
rm -rf {{ webroot }}/*{{ build_slug }}*
args:
warn: no
executable: bash
with_items:
- '{{ mysql_query }} "SHOW DATABASES" | grep "{{ build_slug }}" | xargs -I "@@" {{ mysql_query }} "DROP DATABASE @@"'
- 'rm -rf {{ webroot }}/*{{ build_slug }}*'
# The drive space is occupied by more than 90%.
when: disk_usage.stdout > 90
2 changes: 1 addition & 1 deletion cmf/all/scripts/vars/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ env_vars:

databases:
default:
name: "{{ cmf }}_{{ project | replace('-', '_') }}_{{ build_id | default(env) }}"
name: "{{ [cmf, build_id | default(project + '_' + env)] | join('_') | replace('-', '_') }}"
# source:
# # Database name on remote host.
# db: ""
Expand Down
7 changes: 7 additions & 0 deletions scripts/roles/cikit-ci/defaults/main.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
---
cikit_ci:
process_controller:
repo: https://github.com/BR0kEN-/bash-process-controller.git
dest: /var/ci/process-controller
# Either branch name or tag is also allowed.
version: HEAD
1 change: 1 addition & 0 deletions scripts/roles/cikit-ci/files/bash-process-controller
138 changes: 138 additions & 0 deletions scripts/roles/cikit-ci/files/tasks.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,138 @@
#!/usr/bin/env bash

# Allows continuing the process regardless of an exit code at one of the stages.
set +e

# ------------------------------------------------------------------------------
# The required configuration of a process.
# ------------------------------------------------------------------------------

declare -rA VARIABLES=(
[BUILD_NUMBER]="either \"stable\" or any custom value, like \"54\" or \"my-pr\""
[BUILD_MODE]="either \"full\", \"pull\" or whatever you have defined in \"scripts/tasks/reinstall/modes/*.yml\""
[BUILD_ENV]="the name of an environment to build or \"default\""
[CIKIT_PROJECT_DIR]="the path to directory where repository clones to"
[CIKIT_PROJECT_HOSTNAME]="the hostname where the project can be accessed"
[RUN_SNIFFERS]="either \"yes\" or whatever"
[RUN_TESTS]="either \"yes\" or whatever"
)

for VARIABLE in "${!VARIABLES[@]}"; do
if [ -z ${!VARIABLE+x} ]; then
echo "The \"$VARIABLE\" variable is missing! It's value must be ${VARIABLES[$VARIABLE]}."
exit 101
fi

# Ensure the variable is available in the subshells.
# shellcheck disable=SC2163
# https://github.com/koalaman/shellcheck/wiki/SC2163
export "${VARIABLE}"
done

# ------------------------------------------------------------------------------
# Read CIKit configuration.
# ------------------------------------------------------------------------------

declare -A CIKIT_PROJECT_CONFIG=()

for VARIABLE in webroot project build_slug; do
VALUE="$(awk '/^'"$VARIABLE"':/ {print $2}' < "$CIKIT_PROJECT_DIR/.cikit/config.yml")"

if [ -z "$VALUE" ]; then
echo "The value of \"$VARIABLE\" variable cannot be empty!"
exit 102
fi

CIKIT_PROJECT_CONFIG["$VARIABLE"]="$VALUE"
done

# ------------------------------------------------------------------------------
# Compute build parameters.
# ------------------------------------------------------------------------------

if [ "$BUILD_NUMBER" == "stable" ]; then
export IS_COMMIT=false
BUILD_ID="${CIKIT_PROJECT_CONFIG['project']}-$BUILD_ENV"
else
export IS_COMMIT=true
BUILD_ID="${CIKIT_PROJECT_CONFIG['project']}-${CIKIT_PROJECT_CONFIG['build_slug']}-$BUILD_NUMBER"
fi

# https://docs.python.org/2/using/cmdline.html#cmdoption-u
export PYTHONUNBUFFERED=1
# Replace underscores by dashes in the ID of a build.
export BUILD_ID="${BUILD_ID//_/-}"
# Form an absolute path to directory where the project is accessible from web.
export DESTINATION="${CIKIT_PROJECT_CONFIG['webroot']}/$BUILD_ID"

# Print the environment.
env

# ------------------------------------------------------------------------------
# Define the runtime.
# ------------------------------------------------------------------------------

cikit_run() {
cikit "$1" \
"${@:2}" \
--env="$BUILD_ENV" \
--site-url="https://$BUILD_ID.$CIKIT_PROJECT_HOSTNAME" \
--build-id="$BUILD_ID" \
--workspace="$CIKIT_PROJECT_DIR"
}

cikit_hook() {
local HOOK_PLAYBOOK="$CIKIT_PROJECT_DIR/.cikit/ci/$1.yml"

if [ -f "$HOOK_PLAYBOOK" ]; then
cikit_run "$HOOK_PLAYBOOK" --dist="$DESTINATION" --rc="$PROCESS_EXIT_CODE"
fi
}

export -f cikit_run cikit_hook

# ------------------------------------------------------------------------------
# Define the process.
# ------------------------------------------------------------------------------

PROCESS_pre() {
cikit_hook pre-deploy
}

PROCESS_main() {
# Install a project.
if ${IS_COMMIT}; then
cikit_run reinstall --actions="$(php -r "echo json_encode(array_map('trim', array_filter(explode(PHP_EOL, '$(git log -n1 --pretty=%B | awk -vRS="]" -vFS="[" '{print $2}')'))));")"
else
cikit_run reinstall --reinstall-mode="$BUILD_MODE"
fi

# Copy codebase to directory accessible from the web.
sudo rsync -ra --delete --chown=www-data:www-data ./ "$DESTINATION/"

if [ "$RUN_SNIFFERS" == "yes" ]; then
cikit_run sniffers
fi

if [ "$RUN_TESTS" == "yes" ]; then
cikit_run tests --run --headless
fi
}

PROCESS_post() {
cikit_hook post-deploy
}

PROCESS_clean() {
cikit_hook server-cleaner
}

PROCESS_finish() {
echo "Restore permissions for \"$USER\"."
# The "$USER" must be either "jenkins" or "gitlab-runner".
sudo chown -R "$USER":"$USER" "$CIKIT_PROJECT_DIR"
# The "$HOME" will be for the "$USER".
sudo chown -R "$USER":"$USER" "$HOME"
}

export -f PROCESS_pre PROCESS_main PROCESS_post PROCESS_clean PROCESS_finish
43 changes: 32 additions & 11 deletions scripts/roles/cikit-ci/tasks/main.yml
Original file line number Diff line number Diff line change
@@ -1,17 +1,38 @@
---
- name: Determine CI service
set_fact:
cikit_ci: "{{ 'gitlab-ci' if gitlab_ci_token | default or gitlab_ci_url | default else 'jenkins' }}"

- include_role:
# Install Gitlab CI if either "--gitlab-ci-token" or "--gitlab-ci-url"
# is passed. Use Jenkins otherwise.
name: "cikit-{{ cikit_ci }}"
cikit_ci_gitlab: "{{ gitlab_ci_token | default or gitlab_ci_url | default }}"

- include_role:
name: "cikit-{{ 'gitlab-ci' if cikit_ci_gitlab else 'jenkins' }}"

- name: Determine the group and owner of CI service
set_fact:
cikit_ci_owner: "{{ 'root' if cikit_ci_gitlab else jenkins_data.user }}"
cikit_ci_group: "{{ 'root' if cikit_ci_gitlab else jenkins_data.group }}"

- name: Ensure the directory for CI scripts exist
file:
path: "{{ cikit_ci.process_controller.dest | dirname }}"
mode: 0755
state: directory
owner: "{{ cikit_ci_owner }}"
group: "{{ cikit_ci_group }}"
register: cikit_ci_scripts_path

- name: Install/update CI process controller
git:
repo: "{{ cikit_ci.process_controller.repo }}"
dest: "{{ cikit_ci.process_controller.dest }}"
force: yes
update: yes
version: "{{ cikit_ci.process_controller.version }}"

- name: Deploy CI builder
template:
src: ci-builder.sh.j2
dest: /var/ci-builder.sh
mode: a+x
owner: "{{ jenkins_data.user if cikit_ci == 'jenkins' else 'root' }}"
group: "{{ jenkins_data.group if cikit_ci == 'jenkins' else 'root' }}"
- name: Deploy CI process handler
copy:
src: tasks.sh
dest: "{{ cikit_ci_scripts_path.path }}"
owner: "{{ cikit_ci_owner }}"
group: "{{ cikit_ci_group }}"
119 changes: 0 additions & 119 deletions scripts/roles/cikit-ci/templates/ci-builder.sh.j2

This file was deleted.

Loading

0 comments on commit 4ab7213

Please sign in to comment.