# bash scripting

* Leverage [ShellCheck.net](https://www.shellcheck.net/) and the [VS Code Addin](https://marketplace.visualstudio.com/items?itemName=timonwong.shellcheck)

## bash scripting

![bash logo](/files/ycd87RsNsNtk3mUZHhQ3)

### Proper escaping - Everything is a string

#### Accessing values

{% code title="everything-is-a-string.sh" %}

```bash
#!/bin/bash

a="some string"

# this works, but I don't like it:
echo $a

# This is how I do it. Curly braces for string values:
echo "${a}"
```

{% endcode %}

#### Executing a command

{% code title="run-a-command.sh" %}

```bash
#!/bin/bash
# Running a command with backticks, but I don't like that:
fileContent=`cat 1.txt`

# Running a command with $( xxx )
fileContent="$( cat 1.txt )"
fileContent="$( echo "Hi" > 1.txt ; cat "./1.txt" ; rm ./1.txt )"
```

{% endcode %}

### Defining variables

#### Creating and accessing an array in bash

{% code title="array.sh" %}

```bash
#!/bin/bash
declare releaseNames=( "api-poi" "api-trip" "api-user" "api-user-java" )

echo "The array contains ${#releaseNames[@]} elements:"

for releaseName in "${releaseNames[@]}"; do
echo "  -  ${releaseName}"
done
```

{% endcode %}

#### Creating and accessing a hashmap / dict bash

```bash
declare -A helmValues
helmValues["a"]="val a"
helmValues["b"]="val b"

echo "a: '${helmValues["a"]}'"
echo "b: '${helmValues["b"]}'"
```

### Determine the directory of the script

{% code title="show:dir.sh" %}

```bash
#!/bin/bash
d="$( dirname "$( readlink -f "$0" )" )"
echo "Running in directory ${d}"
```

{% endcode %}

results in

```
$ pwd
/mnt/c/github/chgeuer/tips

$ ./show_dir.sh
Running in directory /mnt/c/github/chgeuer/tips
```

### Span a command across multiple lines

Use a baskslash (`\`) at the end of the line (no additional whitespace), and preferably indent the next line:

{% code title="multi-line.sh" %}

```bash
#!/bin/bash
response="$( cat payload.xml | curl \
  --silent --include \
  --request POST \
  --url "${triggerURI}" \
  --header "Content-Type: application/xml" \
  --data @- )"

echo "${response}"
```

{% endcode %}

### Lambda-style functions in bash

{% code title="health-probe.sh" %}

```bash
#!/bin/bash

#
# Define some function
#
function httpStatus {
  local url="$1"

  echo "$( curl \
  --silent \
  --output /dev/null \
  --write-out '%{http_code}' \
   "${url}" )"
}

function httpStatus2 { echo "$( curl --silent --output /dev/null --write-out '%{http_code}' $1 )" ; }

echo "Azure:    $( httpStatus "https://portal.azure.com/" )"
echo "Homepage: $( httpStatus2 "https://www.microsoft.com/" )"
```

{% endcode %}

results in

```bash
$ ./health-probe.sh
Azure:    200
Homepage: 200

$
```

### Creating a text file

The `cat > x <<-EOF ... EOF` syntax allows to create a file in the local directory. Please not that the lines 6 and 7 below (the content) are prefixed with a tabstop (), which does not show up in the actual text file.

```bash
#!/bin/bash

SERVER_IP="127.0.0.1"

cat > somefile.ini <<-EOF
	server=${SERVER_IP}
	port=5093
EOF
```

### base64-encode a text

The command `base64 --wrap=0` converts input into a long base64-encoded string without line breaks.

```bash
#!/bin/bash

FILE_CONTENT="$( cat ./foo.bin )"
ONE_LONG_BASE64_STR=$(echo "${FILE_CONTENT}" | base64 --wrap=0)
```

### Bash history

Put the following lines in `~/.inputrc`:

```
## arrow up
"\e[A":history-search-backward
## arrow down
"\e[B":history-search-forward
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://cookbook.geuer-pollmann.de/command-line-utilities/bash.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
