Generate Sensu Go Packages from internal Ruby Gems

Sensu-Go requires vastly different packaging for plugins than classic Sensu, and the docs are a bit sparse. Additionally, it seems the Sensu-Go team wants you to use Travis CI,  as most of their process appears to depend on this tool. While I have no issue with Travis CI, I wanted a simple bash script to build my plugins. I'm sharing my script here, keep in mind that this script does assume the assets will be uploaded to an S3 bucket. Please feel free to modify the scripts to meet your needs.

Please keep in mind theses scripts are far from perfect...

Requirements:

  1. docker
  2. aws cli setup and configured with a profile
  3. a unix like machine, eg linux, macOS, sorry no windows..

Place the following files in the root of your ruby gem source dir.

file: build-sensu-go.sh

#!/bin/bash

## SET THESES VARS TO MATCH YOUR ENVIROMENT
base_url="http://YOURBUCKETNAME.s3-website-us-west-2.amazonaws.com"
aws_profile="MY_AWS_PROFILE"
s3_bucket="YOUREBUCKETNAME"
## END SETTINGS 


gem_name=`basename $(ls *.gemspec) .gemspec`
version=`cat ${gem_name}.gemspec |grep version | grep -v -E 'required_ruby_version|required_rubygems_version|rubygems_version'| cut -f 2 -d '=' |sed 's/ //g' |tr -d "'"`
package_output_dir="sensu-go-package"

function cleanup {
    echo "Cleaning up output directory: ${package_output_dir}"
    if [[ ! -d "${package_output_dir}" ]]; then
        echo "creating output directory: ${package_output_dir}"
        mkdir -v ${package_output_dir}
    fi

    if [ "$(ls -A ${package_output_dir})" ]; then
        rm -rvf ${package_output_dir}/*
    fi
}

function uploadS3 {
    aws --profile=${aws_profile} s3 cp ./${package_output_dir}/${gem_name}-${version}.tar.gz s3://${s3_bucket}/${gem_name}/
    aws --profile=${aws_profile} s3 cp ./${package_output_dir}/asset-${gem_name}-${version}.yml s3://${s3_bucket}/${gem_name}/
    echo "asset url: ${base_url}/${gem_name}/asset-${gem_name}-${version}.yml"
}

# extractFileFromImage image source dst
function extractFileFromImage {
    CID=$(docker create $1)
    docker cp ${CID}:$2 $3
    docker rm ${CID}
}

function generateAssetYaml {
echo "generating asset.yml"
sha_sum=`cat ./${package_output_dir}/${gem_name}-${version}._sha512-checksums.txt|grep ${gem_name} |cut -f 1 -d ' '`
cat > ./${package_output_dir}/asset-${gem_name}-${version}.yml <<EOL
---
type: Asset
api_version: core/v2
metadata:
  name: ${gem_name}
  namespace: default
spec:
  url: ${base_url}/${gem_name}/${gem_name}-${version}.tar.gz
  sha512: ${sha_sum}
EOL
}

cleanup

echo "building sensu go package"
docker build --build-arg GEM_VERSION=${version} --build-arg GEM_NAME=${gem_name} -f Dockerfile.debian9 -t ${gem_name}-${version} . || exit 1
extractFileFromImage  ${gem_name}-${version} /assets/${gem_name}-${version}.tar.gz   ${package_output_dir}/
extractFileFromImage  ${gem_name}-${version}  /assets/${gem_name}-${version}._sha512-checksums.txt ${package_output_dir}/
generateAssetYaml
uploadS3

file: Dockerfile.debian9

FROM sensu/sensu-ruby-runtime-2.4.4-debian9:latest
ARG GEM_NAME
ARG GEM_VERSION
COPY . /assets/build/${GEM_NAME}-${GEM_VERSION}

WORKDIR /assets/build/

RUN gem install --no-ri --no-doc bundler \
    &&  printf "source 'https://rubygems.org'\ngem \"%s\", path:  \"%s\" \n" ${GEM_NAME} /assets/build/${GEM_NAME}-${GEM_VERSION} | tee Gemfile \
    && bundle install --path=lib/ --binstubs=bin/ --standalone  

RUN tar -czf /assets/${GEM_NAME}-${GEM_VERSION}.tar.gz -C /assets/build/ . \
    && (cd /assets/ && sha512sum /assets/${GEM_NAME}-${GEM_VERSION}.tar.gz > ${GEM_NAME}-${GEM_VERSION}._sha512-checksums.txt)

Do you have any question to us?

Contact us and we'll get back to you as soon as possible.