2
#!/bin/sh
LOG='log --pretty=format:"%h - %an, %ar : %s"'

git $LOG

I expect this to output an actual git log in the specified format. However, all I get is a fatal argument error.

I have also tried the options below, and they also do not work:

LOG="log --pretty=format:\"%h - %an, %ar : %s\""
LOG='log --pretty=format:\"%h - %an, %ar : %s\"'

However, strangely the script below DOES work, and I don't understand why:

LOG='--pretty=format:"%h - %an, %ar : %s"'
git log "$LOG"

It has been argued that shell is considering the variable to be only one argument, however the following works fine:

LOG1LINE='log --pretty=oneline'
git $LOG1LINE
1

2 Answers 2

4

Here is one way to overcome this problem. Using bash arrays:

#!/bin/bash
#It's important to use bash instead of sh for this to work

LOG=(log --pretty=format:"%h - %an, %ar : %s")
git "${LOG[@]}"
Sign up to request clarification or add additional context in comments.

7 Comments

I get "Syntax error: "(" unexpected" when I try to declare my array. I get it even if I use declare -a LOG=(b).
Are you sure you're using bash?
I'm using the default terminal that comes with Ubuntu. How can I check for sure?
Run this: echo $SHELL
echo $SHELL results in: /bin/bash
|
2

This is a product of how the shell handles arguments.

The first thing the shell does is substitute variables. Quotes that were used in the variable definition are not preserved here. Then it chunks them into arguments, based on either quotes or, if these are not present, word boundaries. Quotes that were quoted when they were first used are escaped at that time, and consequently cannot define word boundaries.

Consequently, the arguments passed to git in your first example are:

  • log
  • --pretty=format:"%h
  • -
  • %an,
  • %ar
  • :
  • %s"

In the later example, the arguments passed to git are:

  • log
  • --pretty=format:"%h - %an, %ar : %s"

2 Comments

Is there any way to preserve the quotes?
@onlywei: Not really. The shell parses (& removes) quotes before replacing variable values, so by the time any quotes in the variable appear, it's too late for them to do any good. Solution: use an array instead (see anubhava's answer).

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.