-
-
Notifications
You must be signed in to change notification settings - Fork 1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Bash installer #256
Bash installer #256
Conversation
@itchyny Did a full review of this, some testing and made some tweaks/fixes where I saw them. As a starting point: this is an incredible first contribution, I'm really impressed 👏. I think it's now at a stage where I'm happy to have this merged. I just want to have a few other maintainers give their 👀 on it and ensure I only merge this at a time where I can be around to make any quick fixes should problems pop up. Let me know what you think of any of my changes. Again: great work! @Homebrew/maintainers would appreciate as many of you as possible taking a look at this and offering any thoughts. Thanks! |
|
||
# Use an extra newline and bold to avoid this being missed. | ||
ohai "Homebrew has enabled anonymous aggregate formulae and cask analytics." | ||
echo "$(cat <<EOS |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why echo
and cat
at once? cat
alone should suffice.
# This script installs to /usr/local only. To install elsewhere (which is | ||
# unsupported) you can untar https://github.com/Homebrew/brew/tarball/master | ||
# anywhere you like. | ||
HOMEBREW_PREFIX="/usr/local" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Bash has a lot of pitfalls and places where things can go wrong if we’re distracted.
I’d feel safer if every variable would be readonly
when possible (i.e. if it’s not, you know it will change) and used single quotes unless double quotes are necessary.
tty_reset="$(tty_escape 0)" | ||
|
||
shell_join() { | ||
local arg |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Similarly, local
variables should be local -r
(local and readonly).
MACOS_OLDEST_SUPPORTED="10.13" | ||
|
||
# no analytics during installation | ||
export HOMEBREW_NO_ANALYTICS_THIS_RUN=1 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
To make a variable readonly and exported at the same time, declare -rx
works.
|
||
####################################################################### script | ||
if [[ "$OSTYPE" == "linux-gnu" ]]; then | ||
abort "$(cat <<'EOABORT' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Again, it’s weird to me that a function is called and then cat
is called inside. In this case, there’s also the case that EOABORT
is quoted, which is inconsistent with the rest of the code.
} | ||
|
||
should_install_command_line_tools() { | ||
if version_gt "$macos_version" "10.13"; then |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All variables should be ${var}
instead of $var
. That’s one of those simple things that can save us from a world of trouble by doing everywhere, and we definitely do not want this script to fail due to mistakes.
In addition, it makes the script consistent throughout, since several cases already use the former notation.
ohai "You are using macOS ${macos_version}." | ||
ohai "${who} do not provide support for this ${what}." | ||
|
||
echo "$(cat <<EOS |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Again, I don’t get the use of cat
, as echo
alone would suffice. And we can make it look nicer by keeping the indentation and removing it on output, like so:
echo "
Some message
With ${variables}
" | sed -E 's/^ {2}//'
Replacing the 2
with however many spaces we have at the start of the line.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I personally prefer simpler and less magical (no undenting).
cat <<EOS
Hello, world!
EOS
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I disagree that the sed
call is either complex or magical, especially when you consider the script as a whole, but I won’t bikeshed it. Not using echo
and cat
at the same time should be considered, though.
There’s also
cat <<-EOS
Hello
World
EOS
The <<-
removes the indentation (not as good as Ruby’s <<~
), but it only works with tabs.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Undenting is also probably not worth the complexity, agreed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Or we could just echo
every line separately, which also aligns nicely with ohai
, as seen below.
Initial Linux support on top of this PR branch: https://github.com/dawidd6/install/tree/install-sh-linux. |
if [[ "$OSTYPE" == "linux-gnu" ]]; then | ||
abort "$(cat <<'EOABORT' | ||
To install Homebrew on Linux, paste at a terminal prompt: | ||
sh -c "$(curl -fsSL https://raw.githubusercontent.com/Linuxbrew/install/master/install.sh)" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We should be explicit (/bin/bash -c
). /bin/sh
is often a link to something else and can change (e.g. in Ubuntu it used to point to bash
and later dash
), which might mean unexpected breakage when we least expect it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But it's a sh
script actually, not bash
.
https://github.com/Linuxbrew/install/blob/master/install.sh
Look at the shebang.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@dawidd6 in this PR it's #!/bin/bash
. On most systems /bin/sh
runs bash or some other interpreter in compatibility mode, IIRC.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
When you run sh -c "…"
the shebang line is ignored. The script will be run using sh
, not with whatever the shebang line specifies. We should either remove Bash-isms from the script and test with dash
, or change the installation instructions to bash -c "…"
.
@vitorgalvao and others: I appreciate the style suggestions but as this PR is otherwise ready to go (and I'm limited in the windows in which I can merge it and it's limiting other things going in until it's done) I'm going to merge as-is and accept PRs to tweak style. Ideally all style checks will be enforced by The |
Thanks so much for your first, incredible contribution! Without people like you submitting PRs we couldn't run this project. You rock, @itchyny! |
Great, thank you all for throughout reviews! I'm honored and I love Homebrew! |
Hi, I looked into the installer and translated into bash one line by one. Needs some more works (
not sure how to compare version string.. maybe I'll implement this with arraysparameter substitution works). I love Homebrew, thank you all.Why?
Future versions of macOS won’t include scripting language runtimes by default, and might require you to install additional packages. If your software depends on scripting languages, it’s recommended that you bundle the runtime within the app. (49764202)
https://developer.apple.com/documentation/macos_release_notes/macos_catalina_10_15_release_notesbut shell script is hard to write
I introduced shellcheck integration. This tool catches various common mistakes in shell script and there's no reason to follow it.
a few notes
for x in ${arr[@]}
splits an element containing a space,for x in "${a[@]}"
aborts withunbound variable
whenset -u
,"${a[@]-}"
emits an empty string when the array is empty,"${a[@]+"${a[@]}"}"
(see https://stackoverflow.com/questions/7577052) works actually but the syntax is ugly. Checking the length is much simpler and readable.stat
is not portable.