From 6472e1b3f2be73cf19d3377e90c69f4f35226a99 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sylwester=20Zieli=C5=84ski?= Date: Sun, 6 Aug 2023 12:12:35 +0200 Subject: [PATCH] Remove moustache --- .github/workflows/deploy-all.yml | 59 -- .github/workflows/generate-readme.yml | 27 - moustache/README.mo | 92 -- moustache/mo | 1106 ------------------------- moustache/split.sh | 39 - 5 files changed, 1323 deletions(-) delete mode 100644 .github/workflows/deploy-all.yml delete mode 100644 .github/workflows/generate-readme.yml delete mode 100644 moustache/README.mo delete mode 100755 moustache/mo delete mode 100755 moustache/split.sh diff --git a/.github/workflows/deploy-all.yml b/.github/workflows/deploy-all.yml deleted file mode 100644 index ac5f3e562..000000000 --- a/.github/workflows/deploy-all.yml +++ /dev/null @@ -1,59 +0,0 @@ -name: Deploy Internal & create Readme -on: - push: - tags: - - '*' -jobs: - generateReadme: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v3 - with: - ref: main - fetch-depth: 0 - - uses: actions/setup-java@v3 - with: - distribution: 'corretto' - java-version: '17' - - shell: bash - run: | - git config user.email mag@nordicsemi.no - git config user.name "Github Action" - VERSION=`git describe --tags --abbrev=0` - VERSION=`./moustache/split.sh $VERSION` - rm -f ./README.md - VERSION=$VERSION ./moustache/mo ./moustache/README.mo > ./README.md - git add . - git diff-index --quiet HEAD || git commit -m "Update readme to version=$VERSION" && git push - deployAabToGooglePlayAlpha: - needs: generateReadme - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v3 - with: - ref: main - fetch-depth: 0 - - uses: actions/setup-java@v3 - with: - distribution: 'corretto' - java-version: '17' - - shell: bash - env: - KEYSTORE_ALIAS: ${{ secrets.KEYSTORE_ALIAS }} - KEYSTORE_KEY_PSWD: ${{ secrets.KEYSTORE_KEY_PSWD }} - KEYSTORE_PSWD: ${{ secrets.KEYSTORE_PSWD }} - GPG_SIGNING_KEY: ${{ secrets.GPG_SIGNING_KEY }} - GPG_PASSWORD: ${{ secrets.GPG_PASSWORD }} - OSSR_USERNAME: ${{ secrets.OSSR_USERNAME }} - OSSR_PASSWORD: ${{ secrets.OSSR_PASSWORD }} - SONATYPE_STATING_PROFILE_ID: ${{ secrets.SONATYPE_STATING_PROFILE_ID }} - run: | - pwd - echo "${{ secrets.GOOGLE_SERVICES }}" | base64 --decode > app/google-services.json - echo "${{ secrets.KEYSTORE_FILE }}" > keystore.asc - gpg -d --passphrase "${{ secrets.KEYSTORE_FILE_PSWD }}" --batch keystore.asc > keystore - echo "${{ secrets.GPG_FILE }}" > sec.gpg.asc - gpg -d --passphrase "${{ secrets.GPG_FILE_PSWD }}" --batch sec.gpg.asc > sec.gpg - echo "${{ secrets.API_KEY_FILE }}" > fastlane-api.json.asc - gpg -d --passphrase "${{ secrets.API_KEY_FILE_PSWD }}" --batch fastlane-api.json.asc > fastlane-api.json - fastlane deployInternal diff --git a/.github/workflows/generate-readme.yml b/.github/workflows/generate-readme.yml deleted file mode 100644 index 92b7c41cd..000000000 --- a/.github/workflows/generate-readme.yml +++ /dev/null @@ -1,27 +0,0 @@ -name: Generate README.md -on: - workflow_dispatch: -jobs: - restorePassword: - runs-on: ubuntu-latest - steps: - - uses: actions/checkout@v2 - with: - fetch-depth: 0 - - uses: actions/setup-java@v3 - with: - distribution: 'corretto' - java-version: '17' - - shell: bash - env: - CONTACT_EMAIL: ${{ secrets.CONTACT_EMAIL }} - run: | - git config user.email $CONTACT_EMAIL - git config user.name "Github Action" - git describe --tags - VERSION=`git describe --tags --abbrev=0` - VERSION=`./moustache/split.sh $VERSION` - rm -f ./README.md - VERSION=$VERSION ./moustache/mo ./moustache/README.mo > ./README.md - git add . - git diff-index --quiet HEAD || git commit -m "Update readme to version=$VERSION" && git push diff --git a/moustache/README.mo b/moustache/README.mo deleted file mode 100644 index a951ac407..000000000 --- a/moustache/README.mo +++ /dev/null @@ -1,92 +0,0 @@ -# nRF Toolbox - -The nRF Toolbox is a container app that stores your Nordic Semiconductor apps for Bluetooth Low Energy -in one location. - -It contains applications demonstrating standard Bluetooth LE profiles: -* **Cycling Speed and Cadence**, -* **Running Speed and Cadence**, -* **Heart Rate Monitor**, -* **Blood Pressure Monitor**, -* **Health Thermometer Monitor**, -* **Glucose Monitor**, -* **Continuous Glucose Monitor**, -* **Proximity Monitor** - -Since version 1.10.0 the *nRF Toolbox* also supports the **Nordic UART Service** which may be used -for bidirectional text communication between devices. - -### How to import to Android Studio - -The production version of nRF Toolbox depends on -[Android BLE Library](https://github.com/NordicSemiconductor/Android-BLE-Library/) and demonstrates -use of the Android BLE Common Library (ble-common module), which provides parsers for common profiles -adopted by Bluetooth SIG. - -You may also include the BLE Library and BLE Common Library as modules. Clone the library project -to the same root folder. - -If you are having issue like [#40](https://github.com/NordicSemiconductor/Android-nRF-Toolbox/issues/40) -or [#41](https://github.com/NordicSemiconductor/Android-nRF-Toolbox/issues/41), the correct folders -structure should look like this: - -![Folders structure](resources/structure.png) - -If you prefer a different name for BLE library, update the -[*settings.gradle*](https://github.com/NordicSemiconductor/Android-nRF-Toolbox/blob/master/settings.gradle) -file. - -If you get ["Missing Feature Watch" error](https://github.com/NordicSemiconductor/Android-nRF-Toolbox/issues/41#issuecomment-355291101), -switch the configuration to 'app'. - -### BleManager and how to use it - -There are 4 different solutions how to use the manager shown in different profiles. -The very basic approach is used by the BPS nd GLS profiles. Each of those activities holds a -static reference to the manager. Keeping the manager as a view model object protects from disposing it -when device orientation changes and the activities are being destroyed and recreated. However, this -approach does not allow to keep the connections in background mode and therefore is not a solution -that should be used in any production-ready application. - -A better implementation may be found in CGMS, CSC, HRS, HTS, PRX, RSCS, UART. The `BleManager` instance is maintained -by the running service. The service is started in order to connect to a device and stopped when user -decides to disconnect from it. When an activity is destroyed it unbinds from the service, but the -service is still running, so the incoming data may continue to be handled. All device-related data -are kept by the service and may be obtained by a activity when it binds to it in order to be -shown to the user. - -### Nordic UART Service - -The UART profile allows for fast prototyping of devices. The service itself is very simple, having -just 2 characteristics, one for sending data and one for receiving. The data may be any byte array -but it is very often used with just text. Each UART configuration can be created as a separate profile. -Each of them, when pressed, will send the stored command to the device. -You may export your configuration to XML and share between other devices. Swipe the screen to -right to show the log with all events. - -### Device Firmware Update - -**DFU is now available as a separate application** -https://github.com/NordicSemiconductor/Android-DFU-Library - -### Dependencies - -nRF Toolbox depends on [Android BLE Library](https://github.com/NordicSemiconductor/Android-BLE-Library/) -which has to be cloned into the same root folder as this app. If you prefer a different name, -update the [*settings.gradle*](https://github.com/NordicSemiconductor/Android-BLE-Library/blob/master/settings.gradle) file. - -The nRF Toolbox also uses the nRF Logger API library which may be found here: -https://github.com/NordicSemiconductor/nRF-Logger-API. The library is included in dependencies -in *build.gradle* file. This library allows the app to create log entries in the -[nRF Logger](https://play.google.com/store/apps/details?id=no.nordicsemi.android.log) application. -Please, read the library documentation on GitHub for more information about the usage and permissions. - -The graph in HRM profile is created using the [MPAndroidChart v3.1.0](https://github.com/PhilJay/MPAndroidChart) -contributed based on the [Apache 2.0 license](http://www.apache.org/licenses/LICENSE-2.0). - -### Note -- Android 5.0 or newer is required. -- Compatible with nRF5 devices running samples from the Nordic SDK and other devices implementing - standard profiles. -- Development kits: https://www.nordicsemi.com/Software-and-tools/Development-Kits. -- The nRF5 SDK and SoftDevices are available online at http://developer.nordicsemi.com. diff --git a/moustache/mo b/moustache/mo deleted file mode 100755 index ba8e48d19..000000000 --- a/moustache/mo +++ /dev/null @@ -1,1106 +0,0 @@ -#!/usr/bin/env bash -# -#/ Mo is a mustache template rendering software written in bash. It inserts -#/ environment variables into templates. -#/ -#/ Simply put, mo will change {{VARIABLE}} into the value of that -#/ environment variable. You can use {{#VARIABLE}}content{{/VARIABLE}} to -#/ conditionally display content or iterate over the values of an array. -#/ -#/ Learn more about mustache templates at https://mustache.github.io/ -#/ -#/ Simple usage: -#/ -#/ mo [OPTIONS] filenames... -#/ -#/ Options: -#/ -#/ -u, --fail-not-set -#/ Fail upon expansion of an unset variable. -#/ -x, --fail-on-function -#/ Fail when a function returns a non-zero status code. -#/ -e, --false -#/ Treat the string "false" as empty for conditionals. -#/ -h, --help -#/ This message. -#/ -s=FILE, --source=FILE -#/ Load FILE into the environment before processing templates. -#/ Can be used multiple times. -# -# Mo is under a MIT style licence with an additional non-advertising clause. -# See LICENSE.md for the full text. -# -# This is open source! Please feel free to contribute. -# -# https://github.com/tests-always-included/mo - - -# Public: Template parser function. Writes templates to stdout. -# -# $0 - Name of the mo file, used for getting the help message. -# $@ - Filenames to parse. -# -# Options: -# -# --allow-function-arguments -# -# Permit functions in templates to be called with additional arguments. This -# puts template data directly in to the path of an eval statement. Use with -# caution. Not listed in the help because it only makes sense when mo is -# sourced. -# -# -u, --fail-not-set -# -# Fail upon expansion of an unset variable. Default behavior is to silently -# ignore and expand into empty string. -# -# -x, --fail-on-function -# -# Fail when a function used by a template returns an error status code. -# Alternately, ou may set the MO_FAIL_ON_FUNCTION environment variable to a -# non-empty value to enable this behavior. -# -# -e, --false -# -# Treat "false" as an empty value. You may set the MO_FALSE_IS_EMPTY -# environment variable instead to a non-empty value to enable this behavior. -# -# -h, --help -# -# Display a help message. -# -# -s=FILE, --source=FILE -# -# Source a file into the environment before processing template files. -# This can be used multiple times. -# -# -- -# -# Used to indicate the end of options. You may optionally use this when -# filenames may start with two hyphens. -# -# Mo uses the following environment variables: -# -# MO_ALLOW_FUNCTION_ARGUMENTS - When set to a non-empty value, this allows -# functions referenced in templates to receive additional -# options and arguments. This puts the content from the -# template directly into an eval statement. Use with extreme -# care. -# MO_FUNCTION_ARGS - Arguments passed to the function -# MO_FAIL_ON_FUNCTION - If a function returns a non-zero status code, abort -# with an error. -# MO_FAIL_ON_UNSET - When set to a non-empty value, expansion of an unset env -# variable will be aborted with an error. -# MO_FALSE_IS_EMPTY - When set to a non-empty value, the string "false" will be -# treated as an empty value for the purposes of conditionals. -# MO_ORIGINAL_COMMAND - Used to find the `mo` program in order to generate a -# help message. -# -# Returns nothing. -mo() ( - # This function executes in a subshell so IFS is reset. - # Namespace this variable so we don't conflict with desired values. - local moContent f2source files doubleHyphens - - IFS=$' \n\t' - files=() - doubleHyphens=false - - if [[ $# -gt 0 ]]; then - for arg in "$@"; do - if $doubleHyphens; then - #: After we encounter two hyphens together, all the rest - #: of the arguments are files. - files=("${files[@]}" "$arg") - else - case "$arg" in - -h|--h|--he|--hel|--help|-\?) - moUsage "$0" - exit 0 - ;; - - --allow-function-arguments) - # shellcheck disable=SC2030 - MO_ALLOW_FUNCTION_ARGUMENTS=true - ;; - - -u | --fail-not-set) - # shellcheck disable=SC2030 - MO_FAIL_ON_UNSET=true - ;; - - -x | --fail-on-function) - # shellcheck disable=SC2030 - MO_FAIL_ON_FUNCTION=true - ;; - - -e | --false) - # shellcheck disable=SC2030 - MO_FALSE_IS_EMPTY=true - ;; - - -s=* | --source=*) - if [[ "$arg" == --source=* ]]; then - f2source="${arg#--source=}" - else - f2source="${arg#-s=}" - fi - - if [[ -f "$f2source" ]]; then - # shellcheck disable=SC1090 - . "$f2source" - else - echo "No such file: $f2source" >&2 - exit 1 - fi - ;; - - --) - #: Set a flag indicating we've encountered double hyphens - doubleHyphens=true - ;; - - *) - #: Every arg that is not a flag or a option should be a file - files=(${files[@]+"${files[@]}"} "$arg") - ;; - esac - fi - done - fi - - moGetContent moContent "${files[@]}" || return 1 - moParse "$moContent" "" true -) - - -# Internal: Call a function. -# -# $1 - Variable for output -# $2 - Function to call -# $3 - Content to pass -# $4 - Additional arguments as a single string -# -# This can be dangerous, especially if you are using tags like -# {{someFunction ; rm -rf / }} -# -# Returns nothing. -moCallFunction() { - local moArgs moContent moFunctionArgs moFunctionResult - - moArgs=() - moTrimWhitespace moFunctionArgs "$4" - - # shellcheck disable=SC2031 - if [[ -n "${MO_ALLOW_FUNCTION_ARGUMENTS-}" ]]; then - # Intentionally bad behavior - # shellcheck disable=SC2206 - moArgs=($4) - fi - - moContent=$(echo -n "$3" | MO_FUNCTION_ARGS="$moFunctionArgs" eval "$2" "${moArgs[@]}") || { - moFunctionResult=$? - # shellcheck disable=SC2031 - if [[ -n "${MO_FAIL_ON_FUNCTION-}" && "$moFunctionResult" != 0 ]]; then - echo "Function '$2' with args (${moArgs[*]+"${moArgs[@]}"}) failed with status code $moFunctionResult" - exit "$moFunctionResult" - fi - } - - # shellcheck disable=SC2031 - local "$1" && moIndirect "$1" "$moContent" -} - - -# Internal: Scan content until the right end tag is found. Creates an array -# with the following members: -# -# [0] = Content before end tag -# [1] = End tag (complete tag) -# [2] = Content after end tag -# -# Everything using this function uses the "standalone tags" logic. -# -# $1 - Name of variable for the array -# $2 - Content -# $3 - Name of end tag -# $4 - If -z, do standalone tag processing before finishing -# -# Returns nothing. -moFindEndTag() { - local content remaining scanned standaloneBytes tag - - #: Find open tags - scanned="" - moSplit content "$2" '{{' '}}' - - while [[ "${#content[@]}" -gt 1 ]]; do - moTrimWhitespace tag "${content[1]}" - - #: Restore content[1] before we start using it - content[1]='{{'"${content[1]}"'}}' - - case $tag in - '#'* | '^'*) - #: Start another block - scanned="${scanned}${content[0]}${content[1]}" - moTrimWhitespace tag "${tag:1}" - moFindEndTag content "${content[2]}" "$tag" "loop" - scanned="${scanned}${content[0]}${content[1]}" - remaining=${content[2]} - ;; - - '/'*) - #: End a block - could be ours - moTrimWhitespace tag "${tag:1}" - scanned="$scanned${content[0]}" - - if [[ "$tag" == "$3" ]]; then - #: Found our end tag - if [[ -z "${4-}" ]] && moIsStandalone standaloneBytes "$scanned" "${content[2]}" true; then - #: This is also a standalone tag - clean up whitespace - #: and move those whitespace bytes to the "tag" element - # shellcheck disable=SC2206 - standaloneBytes=( $standaloneBytes ) - content[1]="${scanned:${standaloneBytes[0]}}${content[1]}${content[2]:0:${standaloneBytes[1]}}" - scanned="${scanned:0:${standaloneBytes[0]}}" - content[2]="${content[2]:${standaloneBytes[1]}}" - fi - - local "$1" && moIndirectArray "$1" "$scanned" "${content[1]}" "${content[2]}" - return 0 - fi - - scanned="$scanned${content[1]}" - remaining=${content[2]} - ;; - - *) - #: Ignore all other tags - scanned="${scanned}${content[0]}${content[1]}" - remaining=${content[2]} - ;; - esac - - moSplit content "$remaining" '{{' '}}' - done - - #: Did not find our closing tag - scanned="$scanned${content[0]}" - local "$1" && moIndirectArray "$1" "${scanned}" "" "" -} - - -# Internal: Find the first index of a substring. If not found, sets the -# index to -1. -# -# $1 - Destination variable for the index -# $2 - Haystack -# $3 - Needle -# -# Returns nothing. -moFindString() { - local pos string - - string=${2%%$3*} - [[ "$string" == "$2" ]] && pos=-1 || pos=${#string} - local "$1" && moIndirect "$1" "$pos" -} - - -# Internal: Generate a dotted name based on current context and target name. -# -# $1 - Target variable to store results -# $2 - Context name -# $3 - Desired variable name -# -# Returns nothing. -moFullTagName() { - if [[ -z "${2-}" ]] || [[ "$2" == *.* ]]; then - local "$1" && moIndirect "$1" "$3" - else - local "$1" && moIndirect "$1" "${2}.${3}" - fi -} - - -# Internal: Fetches the content to parse into a variable. Can be a list of -# partials for files or the content from stdin. -# -# $1 - Variable name to assign this content back as -# $2-@ - File names (optional) -# -# Returns nothing. -moGetContent() { - local moContent moFilename moTarget - - moTarget=$1 - shift - if [[ "${#@}" -gt 0 ]]; then - moContent="" - - for moFilename in "$@"; do - #: This is so relative paths work from inside template files - moContent="$moContent"'{{>'"$moFilename"'}}' - done - else - moLoadFile moContent || return 1 - fi - - local "$moTarget" && moIndirect "$moTarget" "$moContent" -} - - -# Internal: Indent a string, placing the indent at the beginning of every -# line that has any content. -# -# $1 - Name of destination variable to get an array of lines -# $2 - The indent string -# $3 - The string to reindent -# -# Returns nothing. -moIndentLines() { - local content fragment len posN posR result trimmed - - result="" - - #: Remove the period from the end of the string. - len=$((${#3} - 1)) - content=${3:0:$len} - - if [[ -z "${2-}" ]]; then - local "$1" && moIndirect "$1" "$content" - - return 0 - fi - - moFindString posN "$content" $'\n' - moFindString posR "$content" $'\r' - - while [[ "$posN" -gt -1 ]] || [[ "$posR" -gt -1 ]]; do - if [[ "$posN" -gt -1 ]]; then - fragment="${content:0:$posN + 1}" - content=${content:$posN + 1} - else - fragment="${content:0:$posR + 1}" - content=${content:$posR + 1} - fi - - moTrimChars trimmed "$fragment" false true " " $'\t' $'\n' $'\r' - - if [[ -n "$trimmed" ]]; then - fragment="$2$fragment" - fi - - result="$result$fragment" - - moFindString posN "$content" $'\n' - moFindString posR "$content" $'\r' - - # If the content ends in a newline, do not indent. - if [[ "$posN" -eq ${#content} ]]; then - # Special clause for \r\n - if [[ "$posR" -eq "$((posN - 1))" ]]; then - posR=-1 - fi - - posN=-1 - fi - - if [[ "$posR" -eq ${#content} ]]; then - posR=-1 - fi - done - - moTrimChars trimmed "$content" false true " " $'\t' - - if [[ -n "$trimmed" ]]; then - content="$2$content" - fi - - result="$result$content" - - local "$1" && moIndirect "$1" "$result" -} - - -# Internal: Send a variable up to the parent of the caller of this function. -# -# $1 - Variable name -# $2 - Value -# -# Examples -# -# callFunc () { -# local "$1" && moIndirect "$1" "the value" -# } -# callFunc dest -# echo "$dest" # writes "the value" -# -# Returns nothing. -moIndirect() { - unset -v "$1" - printf -v "$1" '%s' "$2" -} - - -# Internal: Send an array as a variable up to caller of a function -# -# $1 - Variable name -# $2-@ - Array elements -# -# Examples -# -# callFunc () { -# local myArray=(one two three) -# local "$1" && moIndirectArray "$1" "${myArray[@]}" -# } -# callFunc dest -# echo "${dest[@]}" # writes "one two three" -# -# Returns nothing. -moIndirectArray() { - unset -v "$1" - - # IFS must be set to a string containing space or unset in order for - # the array slicing to work regardless of the current IFS setting on - # bash 3. This is detailed further at - # https://github.com/fidian/gg-core/pull/7 - eval "$(printf "IFS= %s=(\"\${@:2}\") IFS=%q" "$1" "$IFS")" -} - - -# Internal: Determine if a given environment variable exists and if it is -# an array. -# -# $1 - Name of environment variable -# -# Be extremely careful. Even if strict mode is enabled, it is not honored -# in newer versions of Bash. Any errors that crop up here will not be -# caught automatically. -# -# Examples -# -# var=(abc) -# if moIsArray var; then -# echo "This is an array" -# echo "Make sure you don't accidentally use \$var" -# fi -# -# Returns 0 if the name is not empty, 1 otherwise. -moIsArray() { - # Namespace this variable so we don't conflict with what we're testing. - local moTestResult - - moTestResult=$(declare -p "$1" 2>/dev/null) || return 1 - [[ "${moTestResult:0:10}" == "declare -a" ]] && return 0 - [[ "${moTestResult:0:10}" == "declare -A" ]] && return 0 - - return 1 -} - - -# Internal: Determine if the given name is a defined function. -# -# $1 - Function name to check -# -# Be extremely careful. Even if strict mode is enabled, it is not honored -# in newer versions of Bash. Any errors that crop up here will not be -# caught automatically. -# -# Examples -# -# moo () { -# echo "This is a function" -# } -# if moIsFunction moo; then -# echo "moo is a defined function" -# fi -# -# Returns 0 if the name is a function, 1 otherwise. -moIsFunction() { - local functionList functionName - - functionList=$(declare -F) - # shellcheck disable=SC2206 - functionList=( ${functionList//declare -f /} ) - - for functionName in "${functionList[@]}"; do - if [[ "$functionName" == "$1" ]]; then - return 0 - fi - done - - return 1 -} - - -# Internal: Determine if the tag is a standalone tag based on whitespace -# before and after the tag. -# -# Passes back a string containing two numbers in the format "BEFORE AFTER" -# like "27 10". It indicates the number of bytes remaining in the "before" -# string (27) and the number of bytes to trim in the "after" string (10). -# Useful for string manipulation: -# -# $1 - Variable to set for passing data back -# $2 - Content before the tag -# $3 - Content after the tag -# $4 - true/false: is this the beginning of the content? -# -# Examples -# -# moIsStandalone RESULT "$before" "$after" false || return 0 -# RESULT_ARRAY=( $RESULT ) -# echo "${before:0:${RESULT_ARRAY[0]}}...${after:${RESULT_ARRAY[1]}}" -# -# Returns nothing. -moIsStandalone() { - local afterTrimmed beforeTrimmed char - - moTrimChars beforeTrimmed "$2" false true " " $'\t' - moTrimChars afterTrimmed "$3" true false " " $'\t' - char=$((${#beforeTrimmed} - 1)) - char=${beforeTrimmed:$char} - - # If the content before didn't end in a newline - if [[ "$char" != $'\n' ]] && [[ "$char" != $'\r' ]]; then - # and there was content or this didn't start the file - if [[ -n "$char" ]] || ! $4; then - # then this is not a standalone tag. - return 1 - fi - fi - - char=${afterTrimmed:0:1} - - # If the content after doesn't start with a newline and it is something - if [[ "$char" != $'\n' ]] && [[ "$char" != $'\r' ]] && [[ -n "$char" ]]; then - # then this is not a standalone tag. - return 2 - fi - - if [[ "$char" == $'\r' ]] && [[ "${afterTrimmed:1:1}" == $'\n' ]]; then - char="$char"$'\n' - fi - - local "$1" && moIndirect "$1" "$((${#beforeTrimmed})) $((${#3} + ${#char} - ${#afterTrimmed}))" -} - - -# Internal: Join / implode an array -# -# $1 - Variable name to receive the joined content -# $2 - Joiner -# $3-$* - Elements to join -# -# Returns nothing. -moJoin() { - local joiner part result target - - target=$1 - joiner=$2 - result=$3 - shift 3 - - for part in "$@"; do - result="$result$joiner$part" - done - - local "$target" && moIndirect "$target" "$result" -} - - -# Internal: Read a file into a variable. -# -# $1 - Variable name to receive the file's content -# $2 - Filename to load - if empty, defaults to /dev/stdin -# -# Returns nothing. -moLoadFile() { - local content len - - # The subshell removes any trailing newlines. We forcibly add - # a dot to the content to preserve all newlines. - # As a future optimization, it would be worth considering removing - # cat and replacing this with a read loop. - - content=$(cat -- "${2:-/dev/stdin}" && echo '.') || return 1 - len=$((${#content} - 1)) - content=${content:0:$len} # Remove last dot - - local "$1" && moIndirect "$1" "$content" -} - - -# Internal: Process a chunk of content some number of times. Writes output -# to stdout. -# -# $1 - Content to parse repeatedly -# $2 - Tag prefix (context name) -# $3-@ - Names to insert into the parsed content -# -# Returns nothing. -moLoop() { - local content context contextBase - - content=$1 - contextBase=$2 - shift 2 - - while [[ "${#@}" -gt 0 ]]; do - moFullTagName context "$contextBase" "$1" - moParse "$content" "$context" false - shift - done -} - - -# Internal: Parse a block of text, writing the result to stdout. -# -# $1 - Block of text to change -# $2 - Current name (the variable NAME for what {{.}} means) -# $3 - true when no content before this, false otherwise -# -# Returns nothing. -moParse() { - # Keep naming variables mo* here to not overwrite needed variables - # used in the string replacements - local moArgs moBlock moContent moCurrent moIsBeginning moNextIsBeginning moTag - - moCurrent=$2 - moIsBeginning=$3 - - # Find open tags - moSplit moContent "$1" '{{' '}}' - - while [[ "${#moContent[@]}" -gt 1 ]]; do - moTrimWhitespace moTag "${moContent[1]}" - moNextIsBeginning=false - - case $moTag in - '#'*) - # Loop, if/then, or pass content through function - # Sets context - moStandaloneAllowed moContent "${moContent[@]}" "$moIsBeginning" - moTrimWhitespace moTag "${moTag:1}" - - # Split arguments from the tag name. Arguments are passed to - # functions. - moArgs=$moTag - moTag=${moTag%% *} - moTag=${moTag%%$'\t'*} - moArgs=${moArgs:${#moTag}} - moFindEndTag moBlock "$moContent" "$moTag" - moFullTagName moTag "$moCurrent" "$moTag" - - if moTest "$moTag"; then - # Show / loop / pass through function - if moIsFunction "$moTag"; then - moCallFunction moContent "$moTag" "${moBlock[0]}" "$moArgs" - moParse "$moContent" "$moCurrent" false - moContent="${moBlock[2]}" - elif moIsArray "$moTag"; then - eval "moLoop \"\${moBlock[0]}\" \"$moTag\" \"\${!${moTag}[@]}\"" - else - moParse "${moBlock[0]}" "$moCurrent" true - fi - fi - - moContent="${moBlock[2]}" - ;; - - '>'*) - # Load partial - get name of file relative to cwd - moPartial moContent "${moContent[@]}" "$moIsBeginning" "$moCurrent" - moNextIsBeginning=${moContent[1]} - moContent=${moContent[0]} - ;; - - '/'*) - # Closing tag - If hit in this loop, we simply ignore - # Matching tags are found in moFindEndTag - moStandaloneAllowed moContent "${moContent[@]}" "$moIsBeginning" - ;; - - '^'*) - # Display section if named thing does not exist - moStandaloneAllowed moContent "${moContent[@]}" "$moIsBeginning" - moTrimWhitespace moTag "${moTag:1}" - moFindEndTag moBlock "$moContent" "$moTag" - moFullTagName moTag "$moCurrent" "$moTag" - - if ! moTest "$moTag"; then - moParse "${moBlock[0]}" "$moCurrent" false "$moCurrent" - fi - - moContent="${moBlock[2]}" - ;; - - '!'*) - # Comment - ignore the tag content entirely - # Trim spaces/tabs before the comment - moStandaloneAllowed moContent "${moContent[@]}" "$moIsBeginning" - ;; - - .) - # Current content (environment variable or function) - moStandaloneDenied moContent "${moContent[@]}" - moShow "$moCurrent" "$moCurrent" - ;; - - '=') - # Change delimiters - # Any two non-whitespace sequences separated by whitespace. - # This tag is ignored. - moStandaloneAllowed moContent "${moContent[@]}" "$moIsBeginning" - ;; - - '{'*) - # Unescaped - split on }}} not }} - moStandaloneDenied moContent "${moContent[@]}" - moContent="${moTag:1}"'}}'"$moContent" - moSplit moContent "$moContent" '}}}' - moTrimWhitespace moTag "${moContent[0]}" - moArgs=$moTag - moTag=${moTag%% *} - moTag=${moTag%%$'\t'*} - moArgs=${moArgs:${#moTag}} - moFullTagName moTag "$moCurrent" "$moTag" - moContent=${moContent[1]} - - # Now show the value - # Quote moArgs here, do not quote it later. - moShow "$moTag" "$moCurrent" "$moArgs" - ;; - - '&'*) - # Unescaped - moStandaloneDenied moContent "${moContent[@]}" - moTrimWhitespace moTag "${moTag:1}" - moFullTagName moTag "$moCurrent" "$moTag" - moShow "$moTag" "$moCurrent" - ;; - - *) - # Normal environment variable or function call - moStandaloneDenied moContent "${moContent[@]}" - moArgs=$moTag - moTag=${moTag%% *} - moTag=${moTag%%$'\t'*} - moArgs=${moArgs:${#moTag}} - moFullTagName moTag "$moCurrent" "$moTag" - - # Quote moArgs here, do not quote it later. - moShow "$moTag" "$moCurrent" "$moArgs" - ;; - esac - - moIsBeginning=$moNextIsBeginning - moSplit moContent "$moContent" '{{' '}}' - done - - echo -n "${moContent[0]}" -} - - -# Internal: Process a partial. -# -# Indentation should be applied to the entire partial. -# -# This sends back the "is beginning" flag because the newline after a -# standalone partial is consumed. That newline is very important in the middle -# of content. We send back this flag to reset the processing loop's -# `moIsBeginning` variable, so the software thinks we are back at the -# beginning of a file and standalone processing continues to work. -# -# Prefix all variables. -# -# $1 - Name of destination variable. Element [0] is the content, [1] is the -# true/false flag indicating if we are at the beginning of content. -# $2 - Content before the tag that was not yet written -# $3 - Tag content -# $4 - Content after the tag -# $5 - true/false: is this the beginning of the content? -# $6 - Current context name -# -# Returns nothing. -moPartial() { - # Namespace variables here to prevent conflicts. - local moContent moFilename moIndent moIsBeginning moPartial moStandalone moUnindented - - if moIsStandalone moStandalone "$2" "$4" "$5"; then - # shellcheck disable=SC2206 - moStandalone=( $moStandalone ) - echo -n "${2:0:${moStandalone[0]}}" - moIndent=${2:${moStandalone[0]}} - moContent=${4:${moStandalone[1]}} - moIsBeginning=true - else - moIndent="" - echo -n "$2" - moContent=$4 - moIsBeginning=$5 - fi - - moTrimWhitespace moFilename "${3:1}" - - # Execute in subshell to preserve current cwd and environment - ( - # It would be nice to remove `dirname` and use a function instead, - # but that's difficult when you're only given filenames. - cd "$(dirname -- "$moFilename")" || exit 1 - moUnindented="$( - moLoadFile moPartial "${moFilename##*/}" || exit 1 - moParse "${moPartial}" "$6" true - - # Fix bash handling of subshells and keep trailing whitespace. - # This is removed in moIndentLines. - echo -n "." - )" || exit 1 - moIndentLines moPartial "$moIndent" "$moUnindented" - echo -n "$moPartial" - ) || exit 1 - - # If this is a standalone tag, the trailing newline after the tag is - # removed and the contents of the partial are added, which typically - # contain a newline. We need to send a signal back to the processing - # loop that the moIsBeginning flag needs to be turned on again. - # - # [0] is the content, [1] is that flag. - local "$1" && moIndirectArray "$1" "$moContent" "$moIsBeginning" -} - - -# Internal: Show an environment variable or the output of a function to -# stdout. -# -# Limit/prefix any variables used. -# -# $1 - Name of environment variable or function -# $2 - Current context -# $3 - Arguments string if $1 is a function -# -# Returns nothing. -moShow() { - # Namespace these variables - local moJoined moNameParts moContent - - if moIsFunction "$1"; then - moCallFunction moContent "$1" "" "$3" - moParse "$moContent" "$2" false - return 0 - fi - - moSplit moNameParts "$1" "." - - if [[ -z "${moNameParts[1]-}" ]]; then - if moIsArray "$1"; then - eval moJoin moJoined "," "\${$1[@]}" - echo -n "$moJoined" - else - # shellcheck disable=SC2031 - if moTestVarSet "$1"; then - echo -n "${!1}" - elif [[ -n "${MO_FAIL_ON_UNSET-}" ]]; then - echo "Env variable not set: $1" >&2 - exit 1 - fi - fi - else - # Further subindexes are disallowed - eval "echo -n \"\${${moNameParts[0]}[${moNameParts[1]%%.*}]}\"" - fi -} - - -# Internal: Split a larger string into an array. -# -# $1 - Destination variable -# $2 - String to split -# $3 - Starting delimiter -# $4 - Ending delimiter (optional) -# -# Returns nothing. -moSplit() { - local pos result - - result=( "$2" ) - moFindString pos "${result[0]}" "$3" - - if [[ "$pos" -ne -1 ]]; then - # The first delimiter was found - result[1]=${result[0]:$pos + ${#3}} - result[0]=${result[0]:0:$pos} - - if [[ -n "${4-}" ]]; then - moFindString pos "${result[1]}" "$4" - - if [[ "$pos" -ne -1 ]]; then - # The second delimiter was found - result[2]="${result[1]:$pos + ${#4}}" - result[1]="${result[1]:0:$pos}" - fi - fi - fi - - local "$1" && moIndirectArray "$1" "${result[@]}" -} - - -# Internal: Handle the content for a standalone tag. This means removing -# whitespace (not newlines) before a tag and whitespace and a newline after -# a tag. That is, assuming, that the line is otherwise empty. -# -# $1 - Name of destination "content" variable. -# $2 - Content before the tag that was not yet written -# $3 - Tag content (not used) -# $4 - Content after the tag -# $5 - true/false: is this the beginning of the content? -# -# Returns nothing. -moStandaloneAllowed() { - local bytes - - if moIsStandalone bytes "$2" "$4" "$5"; then - # shellcheck disable=SC2206 - bytes=( $bytes ) - echo -n "${2:0:${bytes[0]}}" - local "$1" && moIndirect "$1" "${4:${bytes[1]}}" - else - echo -n "$2" - local "$1" && moIndirect "$1" "$4" - fi -} - - -# Internal: Handle the content for a tag that is never "standalone". No -# adjustments are made for newlines and whitespace. -# -# $1 - Name of destination "content" variable. -# $2 - Content before the tag that was not yet written -# $3 - Tag content (not used) -# $4 - Content after the tag -# -# Returns nothing. -moStandaloneDenied() { - echo -n "$2" - local "$1" && moIndirect "$1" "$4" -} - - -# Internal: Determines if the named thing is a function or if it is a -# non-empty environment variable. When MO_FALSE_IS_EMPTY is set to a -# non-empty value, then "false" is also treated is an empty value. -# -# Do not use variables without prefixes here if possible as this needs to -# check if any name exists in the environment -# -# $1 - Name of environment variable or function -# $2 - Current value (our context) -# MO_FALSE_IS_EMPTY - When set to a non-empty value, this will say the -# string value "false" is empty. -# -# Returns 0 if the name is not empty, 1 otherwise. When MO_FALSE_IS_EMPTY -# is set, this returns 1 if the name is "false". -moTest() { - # Test for functions - moIsFunction "$1" && return 0 - - if moIsArray "$1"; then - # Arrays must have at least 1 element - eval "[[ \"\${#${1}[@]}\" -gt 0 ]]" && return 0 - else - # If MO_FALSE_IS_EMPTY is set, then return 1 if the value of - # the variable is "false". - # shellcheck disable=SC2031 - [[ -n "${MO_FALSE_IS_EMPTY-}" ]] && [[ "${!1-}" == "false" ]] && return 1 - - # Environment variables must not be empty - [[ -n "${!1-}" ]] && return 0 - fi - - return 1 -} - -# Internal: Determine if a variable is assigned, even if it is assigned an empty -# value. -# -# $1 - Variable name to check. -# -# Returns true (0) if the variable is set, 1 if the variable is unset. -moTestVarSet() { - [[ "${!1-a}" == "${!1-b}" ]] -} - - -# Internal: Trim the leading whitespace only. -# -# $1 - Name of destination variable -# $2 - The string -# $3 - true/false - trim front? -# $4 - true/false - trim end? -# $5-@ - Characters to trim -# -# Returns nothing. -moTrimChars() { - local back current front last target varName - - target=$1 - current=$2 - front=$3 - back=$4 - last="" - shift 4 # Remove target, string, trim front flag, trim end flag - - while [[ "$current" != "$last" ]]; do - last=$current - - for varName in "$@"; do - $front && current="${current/#$varName}" - $back && current="${current/%$varName}" - done - done - - local "$target" && moIndirect "$target" "$current" -} - - -# Internal: Trim leading and trailing whitespace from a string. -# -# $1 - Name of variable to store trimmed string -# $2 - The string -# -# Returns nothing. -moTrimWhitespace() { - local result - - moTrimChars result "$2" true true $'\r' $'\n' $'\t' " " - local "$1" && moIndirect "$1" "$result" -} - - -# Internal: Displays the usage for mo. Pulls this from the file that -# contained the `mo` function. Can only work when the right filename -# comes is the one argument, and that only happens when `mo` is called -# with `$0` set to this file. -# -# $1 - Filename that has the help message -# -# Returns nothing. -moUsage() { - grep '^#/' "${MO_ORIGINAL_COMMAND}" | cut -c 4- - echo "" - echo "MO_VERSION=$MO_VERSION" -} - - -# Save the original command's path for usage later -MO_ORIGINAL_COMMAND="$(cd "${BASH_SOURCE[0]%/*}" || exit 1; pwd)/${BASH_SOURCE[0]##*/}" -MO_VERSION="2.2.0" - -# If sourced, load all functions. -# If executed, perform the actions as expected. -if [[ "$0" == "${BASH_SOURCE[0]}" ]] || [[ -z "${BASH_SOURCE[0]}" ]]; then - mo "$@" -fi diff --git a/moustache/split.sh b/moustache/split.sh deleted file mode 100755 index fe1f6ef2e..000000000 --- a/moustache/split.sh +++ /dev/null @@ -1,39 +0,0 @@ -#!/bin/bash -# -# Copyright (c) 2022, Nordic Semiconductor -# All rights reserved. -# -# Redistribution and use in source and binary forms, with or without modification, are -# permitted provided that the following conditions are met: -# -# 1. Redistributions of source code must retain the above copyright notice, this list of -# conditions and the following disclaimer. -# -# 2. Redistributions in binary form must reproduce the above copyright notice, this list -# of conditions and the following disclaimer in the documentation and/or other materials -# provided with the distribution. -# -# 3. Neither the name of the copyright holder nor the names of its contributors may be -# used to endorse or promote products derived from this software without specific prior -# written permission. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED -# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A -# PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -# HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, -# OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY -# OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -# NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, -# EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -# - - -str="$1" - -IFS='%' # space is set as delimiter -read -ra ADDR <<< "$str" # str is read into an array as tokens separated by IFS -echo "${ADDR[0]}" -