Skip to content

Commit 036207a

Browse files
committed
feat: add first draft of CLI install script
1 parent 878c6cf commit 036207a

File tree

1 file changed

+333
-0
lines changed

1 file changed

+333
-0
lines changed

genkit-tools/cli/install.sh

Lines changed: 333 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,333 @@
1+
#!/usr/bin/env bash
2+
3+
## <script src="./readability.js"></script>
4+
## <link href="https://cdnjs.cloudflare.com/ajax/libs/prism/1.16.0/themes/prism-okaidia.min.css" rel="stylesheet" />
5+
## <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.16.0/components/prism-core.min.js" data-manual></script>
6+
## <script src="https://cdnjs.cloudflare.com/ajax/libs/prism/1.16.0/components/prism-bash.min.js"></script>
7+
## <style>body {color: #272822; background-color: #272822; font-size: 0.8em;} </style>
8+
9+
# Configuration variables
10+
DOMAIN="genkit.tools"
11+
TRACKING_ID="UA-XXXXXXXXX-X" # Not used when analytics is commented out
12+
13+
: ==========================================
14+
: Introduction
15+
: ==========================================
16+
17+
# This script allows you to install the latest version of the
18+
# "genkit" command by running:
19+
#
20+
: curl -sL $DOMAIN | bash
21+
#
22+
# If you do not want to use this script, you can manually
23+
# download the latest "genkit" binary.
24+
#
25+
: curl -Lo ./genkit_bin https://$DOMAIN/bin/linux/latest
26+
#
27+
# Alternatively, you can download a specific version.
28+
#
29+
: curl -Lo ./genkit_bin https://$DOMAIN/bin/linux/v1.12.0
30+
#
31+
# Note: On Mac, replace "linux" with "macos" in the URL.
32+
#
33+
# For full details about installation options for the Genkit CLI
34+
# please see our documentation.
35+
# https://firebase.google.com/docs/genkit/
36+
#
37+
# Please report bugs / issues with this script on Github.
38+
# https://github.com/firebase/genkit
39+
#
40+
41+
: ==========================================
42+
: Advanced Usage
43+
: ==========================================
44+
45+
# The behavior of this script can be modified at runtime by passing environmental
46+
# variables to the `bash` process.
47+
#
48+
# For example, passing an argument called arg1 set to true and one called arg2 set
49+
# to false would look like this.
50+
#
51+
: curl -sL $DOMAIN | arg1=true arg2=false bash
52+
#
53+
# These arguments are optional, but be aware that explicitly setting them will help
54+
# ensure consistent behavior if / when defaults are changed.
55+
#
56+
57+
: -----------------------------------------
58+
: Upgrading - default: false
59+
: -----------------------------------------
60+
61+
# By default, this script will not replace an existing "genkit" install.
62+
# If you'd like to upgrade an existing install, set the "upgrade" variable to true.
63+
#
64+
: curl -sL $DOMAIN | upgrade=true bash
65+
#
66+
# This operation could (potentially) break an existing install, so use it with caution.
67+
#
68+
69+
: -----------------------------------------
70+
: Uninstalling - default false
71+
: -----------------------------------------
72+
73+
# You can remove the binary by passing the "uninstall" flag.
74+
#
75+
: curl -sL $DOMAIN | uninstall=true bash
76+
#
77+
# This will remove the binary file and any cached data.
78+
#
79+
80+
: -----------------------------------------
81+
: Analytics - default true
82+
: -----------------------------------------
83+
84+
# This script reports anonymous success / failure analytics.
85+
# You can disable this reporting by setting the "analytics" variable to false.
86+
#
87+
: curl -sL $DOMAIN | analytics=false bash
88+
#
89+
# By default we report all data anonymously and do not collect any information
90+
# except platform type (Darwin, Win, etc) in the case of an unsupported platform
91+
# error.
92+
#
93+
94+
: ==========================================
95+
: Source Code
96+
: ==========================================
97+
98+
# This script contains a large amount of comments so you can understand
99+
# how it interacts with your system. If you're not interested in the
100+
# technical details, you can just run the command above.
101+
102+
# We begin by generating a unique ID for tracking the anonymous session.
103+
CID=$(head -80 /dev/urandom | LC_ALL=c tr -dc 'a-zA-Z0-9' | fold -w 32 | head -n 1)
104+
# Credit: https://gist.github.com/earthgecko/3089509
105+
106+
# We can use this CID in all calls to the Google Analytics endpoint via
107+
# this reusable function.
108+
send_analytics_event()
109+
{
110+
# Analytics tracking is currently disabled
111+
# Uncomment the block below to enable analytics
112+
113+
# if [ ! "$analytics" = "false" ]; then
114+
# curl -s https://www.google-analytics.com/collect \
115+
# -d "tid=$TRACKING_ID" \
116+
# -d "t=event" \
117+
# -d "ec=$DOMAIN" \
118+
# -d "ea=$1" \
119+
# -d "v=1" \
120+
# -d "cid=$CID" \
121+
# -o /dev/null
122+
# fi
123+
124+
# For now, just return success
125+
return 0
126+
}
127+
128+
# We send one event to count the number of times this script is ran. At the
129+
# end we also report success / failure, but it's possible that the script
130+
# will crash before we get to that point, so we manually count invocations here.
131+
send_analytics_event start
132+
133+
# We try to detect any existing binaries on $PATH or two common locations.
134+
GENKIT_BINARY=${GENKIT_BINARY:-$(which genkit)}
135+
LOCAL_BINARY="$HOME/.local/bin/genkit"
136+
# For info about why we place the binary at this location, see
137+
# https://unix.stackexchange.com/a/8658
138+
GLOBAL_BINARY="/usr/local/bin/genkit"
139+
if [[ -z "$GENKIT_BINARY" ]]; then
140+
if [ -e "$LOCAL_BINARY" ]; then
141+
GENKIT_BINARY="$LOCAL_BINARY"
142+
elif [ -e "$GLOBAL_BINARY" ]; then
143+
GENKIT_BINARY="$GLOBAL_BINARY"
144+
fi
145+
fi
146+
147+
# If the user asked for us to uninstall genkit, then do so.
148+
if [ "$uninstall" = "true" ]; then
149+
if [[ -z "$GENKIT_BINARY" ]]; then
150+
echo "Cannot detect any Genkit CLI installations."
151+
echo "Please manually remove any \"genkit\" binaries not in \$PATH."
152+
else
153+
# Assuming binary install, skip npm check
154+
echo "-- Removing binary file..."
155+
sudo rm -- "$GENKIT_BINARY"
156+
fi
157+
echo "-- Removing genkit cache..."
158+
rm -rf ~/.cache/genkit
159+
160+
echo "-- genkit has been uninstalled"
161+
echo "-- All Done!"
162+
163+
send_analytics_event uninstall
164+
exit 0
165+
fi
166+
167+
# We need to ensure that we don't mess up an existing "genkit"
168+
# install, so before doing anything we check to see if this system
169+
# has "genkit" installed and if so, we exit out.
170+
echo "-- Checking for existing genkit installation..."
171+
172+
if [[ ! -z "$GENKIT_BINARY" ]]; then
173+
INSTALLED_GENKIT_VERSION=$("$GENKIT_BINARY" --version)
174+
175+
# In the case of a corrupt genkit install, we wont be able to
176+
# retrieve a version number, so to keep the logs correct, we refer to
177+
# your existing install as either the CLI version or as a "corrupt install"
178+
if [[ ! -z "$INSTALLED_GENKIT_VERSION" ]]; then
179+
GENKIT_NICKNAME="genkit@$INSTALLED_GENKIT_VERSION"
180+
else
181+
GENKIT_NICKNAME="a corrupted genkit binary"
182+
fi
183+
184+
# Skip npm check - assume binary install
185+
# If the user didn't pass upgrade=true, then we print the command to do an upgrade and exit
186+
if [ ! "$upgrade" = "true" ]; then
187+
echo "Your machine has $GENKIT_NICKNAME installed."
188+
echo "If you would like to upgrade your install run: curl -sL $DOMAIN | upgrade=true bash"
189+
190+
send_analytics_event already_installed
191+
exit 0
192+
else
193+
# If the user did pass upgrade=true, then we allow the script to continue and overwrite the install.
194+
echo "-- Your machine has $GENKIT_NICKNAME, attempting upgrade..."
195+
196+
send_analytics_event upgrade
197+
fi
198+
fi
199+
200+
echo "-- Checking your machine type..."
201+
202+
# Now we need to detect the platform we're running on (Linux / Mac / Other)
203+
# so we can fetch the correct binary and place it in the correct location
204+
# on the machine.
205+
206+
# We use "tr" to translate the uppercase "uname" output into lowercase
207+
UNAME=$(uname -s | tr '[:upper:]' '[:lower:]')
208+
209+
# Detect architecture
210+
ARCH=$(uname -m)
211+
case "$ARCH" in
212+
x86_64) ARCH_SUFFIX="x64";;
213+
aarch64|arm64) ARCH_SUFFIX="arm64";;
214+
*) ARCH_SUFFIX="x64";; # Default to x64
215+
esac
216+
217+
# Then we map the output to the names used on the Github releases page
218+
case "$UNAME" in
219+
linux*) MACHINE="linux-${ARCH_SUFFIX}";;
220+
darwin*) MACHINE="darwin-${ARCH_SUFFIX}";;
221+
mingw*|msys*|cygwin*) MACHINE="win32-x64";;
222+
esac
223+
224+
# If we never define the $MACHINE variable (because our platform is neither Mac,
225+
# Linux, or Windows), then we can't finish our job, so just log out a helpful message
226+
# and close.
227+
if [[ -z "$MACHINE" ]]; then
228+
echo "Your operating system is not supported, if you think it should be please file a bug."
229+
echo "https://github.com/firebase/genkit/"
230+
echo "-- All done!"
231+
232+
send_analytics_event "missing_platform_${UNAME}_${ARCH}"
233+
exit 0
234+
fi
235+
236+
# We have enough information to generate the binary's download URL.
237+
DOWNLOAD_URL="https://$DOMAIN/bin/$MACHINE/latest"
238+
echo "-- Downloading binary from $DOWNLOAD_URL"
239+
240+
# We use "curl" to download the binary with a flag set to follow redirects
241+
# (Github download URLs redirect to CDNs) and a flag to show a progress bar.
242+
curl -o "/tmp/genkit_standalone.tmp" -L --progress-bar $DOWNLOAD_URL
243+
244+
GENKIT_BINARY=${GENKIT_BINARY:-$GLOBAL_BINARY}
245+
INSTALL_DIR=$(dirname -- "$GENKIT_BINARY")
246+
247+
# We need to ensure that the INSTALL_DIR exists.
248+
# On some platforms like the Windows Subsystem for Linux it may not.
249+
# We created it using a non-destructive mkdir command.
250+
mkdir -p -- "$INSTALL_DIR" 2> /dev/null
251+
252+
# If the directory does not exist or is not writable, we resort to sudo.
253+
sudo=""
254+
if [ ! -w "$INSTALL_DIR" ]; then
255+
sudo="sudo"
256+
fi
257+
258+
$sudo mkdir -p -- "$INSTALL_DIR"
259+
$sudo mv -f "/tmp/genkit_standalone.tmp" "$GENKIT_BINARY"
260+
261+
# Once the download is complete, we mark the binary file as readable
262+
# and executable (+rx).
263+
echo "-- Setting permissions on binary... $GENKIT_BINARY"
264+
$sudo chmod +rx "$GENKIT_BINARY"
265+
266+
# If all went well, the "genkit" binary should be located on our PATH so
267+
# we'll run it once, asking it to print out the version. This is helpful as
268+
# standalone genkit binaries do a small amount of setup on the initial run
269+
# so this not only allows us to make sure we got the right version, but it
270+
# also does the setup so the first time the developer runs the binary, it'll
271+
# be faster.
272+
VERSION=$("$GENKIT_BINARY" --version)
273+
274+
# If no version is detected then clearly the binary failed to install for
275+
# some reason, so we'll log out an error message and report the failure
276+
# to headquarters via an analytics event.
277+
if [[ -z "$VERSION" ]]; then
278+
echo "Something went wrong, genkit has not been installed."
279+
echo "Please file a bug with your system information on Github."
280+
echo "https://github.com/firebase/genkit/"
281+
echo "-- All done!"
282+
283+
send_analytics_event failure
284+
exit 1
285+
fi
286+
287+
# In order for the user to be able to actually run the "genkit" command
288+
# without specifying the absolute location, the INSTALL_DIR path must
289+
# be present inside of the PATH environment variable.
290+
291+
echo "-- Checking your PATH variable..."
292+
if [[ ! ":$PATH:" == *":$INSTALL_DIR:"* ]]; then
293+
echo ""
294+
echo "It looks like $INSTALL_DIR isn't on your PATH."
295+
echo "Please add the following line to either your ~/.profile or ~/.bash_profile, then restart your terminal."
296+
echo ""
297+
echo "PATH=\$PATH:$INSTALL_DIR"
298+
echo ""
299+
echo "For more information about modifying PATHs, see https://unix.stackexchange.com/a/26059"
300+
echo ""
301+
send_analytics_event missing_path
302+
fi
303+
304+
# We also try to upgrade the local binary if it exists.
305+
# This helps prevent having two mismatching versions of "genkit".
306+
if [[ "$GENKIT_BINARY" != "$LOCAL_BINARY" ]] && [ -e "$LOCAL_BINARY" ]; then
307+
echo "-- Upgrading the local binary installation $LOCAL_BINARY..."
308+
cp "$GENKIT_BINARY" "$LOCAL_BINARY" # best effort, okay if it fails.
309+
chmod +x "$LOCAL_BINARY"
310+
fi
311+
312+
# Since we've gotten this far we know everything succeeded. We'll just
313+
# let the developer know everything is ready and take our leave.
314+
echo "-- genkit@$VERSION is now installed"
315+
echo "-- All Done!"
316+
317+
send_analytics_event success
318+
exit 0
319+
320+
# ------------------------------------------
321+
# Notes
322+
# ------------------------------------------
323+
#
324+
# This script contains hidden JavaScript which is used to improve
325+
# readability in the browser (via syntax highlighting, etc), right-click
326+
# and "View source" of this page to see the entire bash script!
327+
#
328+
# You'll also notice that we use the ":" character in the Introduction
329+
# which allows our copy/paste commands to be syntax highlighted, but not
330+
# ran. In bash : is equal to `true` and true can take infinite arguments
331+
# while still returning true. This turns these commands into no-ops so
332+
# when ran as a script, they're totally ignored.
333+
#

0 commit comments

Comments
 (0)