Back That Thang Up!

Back That Thang Up!
Juvenile craft beer? Who knew?

The software app Brewfather is an amazing tool. You can easily build recipes, create equipment profiles, water profiles, keep inventory and connect monitoring devices like iSpindel.

I stumbled upon a problem though. What happens if a recipe mistakenly changes or gets deleted? The only option I could find was to manually download a pdf, BeerXM or Brewfather recipe JSON.

So I decided to put some of my nerdy skills to use and create a script to back up all of our recipes. Anyone can use it, you just need to create an API key.

#!/bin/bash
# MIT License
#
# Copyright (c) 2022 RLG
#
# Permission is hereby granted, free of charge, to any person obtaining a # copy of this software and associated documentation files (the
# "Software"), to deal in the Software without restriction, including
# without limitation the rights to use, copy, modify, merge, publish, 
# distribute, sublicense, and/or sell copies of the Software, and to 
# permit persons to whom the Software is furnished to do so, subject to 
# the following conditions:
#
# The above copyright notice and this permission notice shall be included 
# in all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 
# OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 
# 
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
# IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 
# CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 
# TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 
# SOFTWARE OR THE USE OR OTHER DEALINGS IN THESOFTWARE.

########################################################
#
# CANNOT USE SH!!!!! NEWLINES NOT FORMED CORRECTLY!!!
#
########################################################

# Environment variable should be set
# Add to ~/.bashrc (or ~/.bash_profile, ~/.shrc, ~/.cshrc, etc.)
#   export USERID={super_secret_key}
#   export APIKEY={super_secret_key}
# source ~/.bashrc

########################################################
# 
# https://docs.brewfather.app/api
#
########################################################

#USERID=xyz123
#APIKEY=1234567890123456789012345678901234567890abcd

BASE64=$(echo -n "$USERID":"$APIKEY" | base64 | tr -d '\r\n');

########################################################

########################################################

# Retrieve batch of json records
get_batch () {
    RETVAL=$(curl -X 'GET' \
    "https://api.brewfather.app/v2/recipes$1" \
    -H "Authorization: Basic $BASE64" \
    -H 'accept: application/json' \
    -H 'Content-Type: application/json');
    echo "$RETVAL";
}

tar_up () {
    # Set name file archive
    arc_name="Brewfather-$1.tar.gz";  

    cd "$2" || exit;
    tar -czf "$2/$arc_name" "arc/"*;  

    # Find and remove archives older than 180 days
    find "$2/"*.gz -type f -mtime +180 -exec rm {} \;
}

DATENAME=$( date +"%Y-%b-%d" );
DIRPATH="/path/to/Brewfather/directory"
COUNTER=0;
ITERATOR=0;
LASTID="START";
LENGTH="0";
LIMIT=50;

BATCH="$( get_batch '?limit='$LIMIT'&complete=True' )";

# Make temporary directory
mkdir $DIRPATH/arc;

# Stop when empty array return
while [[ "${BATCH}" != '[]' ]];
do
    # Get length of batch array
    LENGTH="$( echo "$BATCH" | jq 'length' )";

    # While LastID is not null and iteration is less than length of array
    while [[ -z "${LASTID}" || $ITERATOR -lt $LENGTH ]];
    do
        # Set last ID
        LASTID="$( echo "$BATCH" | jq -r '.['$ITERATOR']._id' )";

        # Get name
        recipename="$( echo "$BATCH" | jq -r '.['$ITERATOR'].name' )";

        # Write contents to file with name
        echo "$BATCH" | jq -r '.['$ITERATOR']' >> "${DIRPATH}/arc/$recipename.json";

        # Increment
        ITERATOR=$(( ITERATOR + 1 ));
        COUNTER=$(( COUNTER + 1 ));
    done

    # Get next batch
    ITERATOR=0;
    BATCH="$( get_batch '?limit='"$LIMIT"'&complete=True&start_after='"$LASTID" )";

done

tar_up "$DATENAME" "$DIRPATH";

# Remove temporary directory
rm -rf $DIRPATH/arc;

echo $COUNTER "Recipes copied";

Enjoy!