{"id":15862,"date":"2019-06-06T09:57:32","date_gmt":"2019-06-06T09:57:32","guid":{"rendered":"https:\/\/www.bartbusschots.ie\/s\/?p=15862"},"modified":"2019-06-27T00:21:42","modified_gmt":"2019-06-27T00:21:42","slug":"getting-a-bash-like-prompt-in-zsh","status":"publish","type":"post","link":"https:\/\/www.bartbusschots.ie\/s\/2019\/06\/06\/getting-a-bash-like-prompt-in-zsh\/","title":{"rendered":"Getting a Bash-like Prompt in Zsh"},"content":{"rendered":"<div class=\"pps-series-post-details pps-series-post-details-variant-classic pps-series-post-details-18702\" data-series-id=\"581\"><div class=\"pps-series-meta-content\"><div class=\"pps-series-meta-text\">This entry is part 2 of 6 in the series <a href=\"https:\/\/www.bartbusschots.ie\/s\/series\/bash-to-zsh\/\">Bash to Zsh<\/a><\/div><\/div><\/div><p><a href=\"https:\/\/support.apple.com\/en-us\/HT208050\" rel=\"noopener noreferrer\" target=\"_blank\">Apple recently announced<\/a> that it&#8217;s moving the MacOS from the <a href=\"https:\/\/en.wikipedia.org\/wiki\/Bash_(Unix_shell)\" rel=\"noopener noreferrer\" target=\"_blank\">Bourne-again Shell<\/a> (Bash) to the <a href=\"https:\/\/en.wikipedia.org\/wiki\/Z_shell\" rel=\"noopener noreferrer\" target=\"_blank\">Z Shell<\/a> (Zsh), and advised developers to make the change now, so they&#8217;re ready when they remove Bash altogether in some later version of the OS. Since I&#8217;m a big believer in not swimming up-stream, I decided to take their advice and switched to the Z Shell immediately.<\/p>\n<p>The first thing I noticed was that the default prompt Apple provides for Zsh on their OS gives a lot less information than their default for Bash did. This is a sample of their old Bash prompt:<\/p>\n<pre class=\"crayon:false\">\r\nbart-imac2018:Documents bart$\r\n<\/pre>\n<p>That tells me the machine I&#8217;m on (<code>bart-imac2018<\/code>), the folder I&#8217;m in (<code>Documents<\/code>), and the username the shell is running as (<code>bart<\/code>), and whether or not I have super-user privileges (<code>$<\/code> means no, <code>#<\/code> means yes). These are all very useful things, particularly when you SSH around a lot and <code>su<\/code>\/<code>sudo<\/code> to different accounts. Also, IMO showing only the top-level folder rather than the full path gives a nice balance between the prompt getting too big, and not knowing where you are. I&#8217;ve never felt an urge to change the Mac&#8217;s default Bash prompt.<\/p>\n<p>I can&#8217;t say the same about the Mac&#8217;s default Z Shell prompt! This is what I get on the same machine with the Z shell:<\/p>\n<pre class=\"crayon:false\">\r\nbart-imac2018%\r\n<\/pre>\n<p>It only shows the machine name (<code>bart-imac2018<\/code>) and whether or not I have super-user privileges (<code>%<\/code> for no, <code>#<\/code> for yes)!<\/p>\n<p>Thankfully getting back to the old Bash-like prompt is easy \u00e2\u20ac\u201d the TL;DR version is that you simply need to add the following line to your <code>~\/.zshrc<\/code> file:<\/p>\n<pre class=\"crayon:false\">\r\nPROMPT='%m:%1~ %n%# '\r\n<\/pre>\n<p>If you&#8217;d like to understand how exactly that works, and what other choices you have, read on!<\/p>\n<p><!--more--><\/p>\n<h2>Changing the Prompt<\/h2>\n<p>Like with Bash, your Zsh prompt is controlled using the <code>PROMPT<\/code> environment variable. You set the prompt using a formatting string where the % symbol indicates the start of a formatting variable that will get replaced by the appropriate value in the displayed prompt.<\/p>\n<p>Let&#8217;s start with a really simple example that has no formatting variables \u00e2\u20ac\u201d to set your prompt to <code>boogers> <\/code> simply execute the following:<\/p>\n<pre class=\"crayon:false\">\r\nPROMPT='boogers> '\r\n<\/pre>\n<p>You can do this safely because the change only applies to the current shell, so just open a new Terminal window to restore sanity!<\/p>\n<p>There are lots of formatting variables you can include (you can see all of them in <a href=\"http:\/\/zsh.sourceforge.net\/Doc\/Release\/Prompt-Expansion.html#Prompt-Expansion\" rel=\"noopener noreferrer\" target=\"_blank\">the relevant section of the Zsh docs<\/a>), but the ones we&#8217;ll need are the ones for the computer name (AKA <em>machine name<\/em>), the current folder, and the current username:<\/p>\n<dl>\n<dt>Machine Name (<code>%m<\/code> or <code>%M<\/code>)<\/dt>\n<dd>You probably just know your computer by it&#8217;s plain hostname (<code>bart-imac2018<\/code> in my case), but it actually has a fully qualified domain name (<code>bart-imac2018.localdomain<\/code> in my case). We can show either in the Zsh prompt \u00e2\u20ac\u201d the plain hostname is <code>%m<\/code>, and the fully qualified domain name (FQDN) is <code>%M<\/code>. On servers the FQDN might be useful, but on personal computers it rarely is, so to save space, I&#8217;d definitely recommend using <code>%m<\/code>. Also, the default Bash prompt on the Mac uses just the hostname too.<\/dd>\n<dt>Current Folder (<code>%\/<\/code>, <code>%~<\/code>, or <code>%.<\/code>)<\/dt>\n<dd>If you want to see the full path to your shell&#8217;s present working directory you can use <code>%\/<\/code> (e.g. <code>\/Users\/bart\/Documents<\/code>). If you want the full path, but shortened a little when possible, you can use <code>%~<\/code>, this will replace the path to your home directory with a <code>~<\/code> when ever possible (e.g. <code>~\/Documents<\/code>). Finally, if you just want to see the top-level current folder, you can use <code>%.<\/code> (e.g. <code>Documents<\/code>).<\/dd>\n<dt>Username (<code>%n<\/code>)<\/dt>\n<dd>The username is simple available via %n (for name).<\/dd>\n<dt>Privilege Level (<code>%#<\/code>)<\/dt>\n<dd>Whether or not the shell currently has super-user (root) privileges, if you do <code>%#<\/code> is replaced with a <code>#<\/code>, and if you don&#8217;t, with a <code>%<\/code>.<\/dd>\n<\/dl>\n<p>So, putting all that together, we can get back to the old Bash-style prompt with:<\/p>\n<pre class=\"crayon:false\">\r\nPROMPT='%M:%1~ %n%# '\r\n<\/pre>\n<h2>Making the Change Permanent<\/h2>\n<p>Now that we know what we want to set our prompt to, how do we tell the Mac to set the prompt this way each time we open a new Terminal window? We need to add the command into one of Zsh&#8217;s startup scripts.<\/p>\n<p>Zsh has many startup scripts, some always get executed, some only get execute for login shells, and some only for interactive shells. Since I only care about the prompt when I&#8217;m interactively typing into a shell, I want to add my change to the file that gets executed only for interactive shells. For Zsh that&#8217;s <code>~\/.zshrc<\/code>.<\/p>\n<p>So, this is what my <code>~\/.zshrc<\/code> file now looks like:<\/p>\n<pre class=\"lang:zsh decode:true \" >\r\n# set the prompt to be bash-like\r\nPROMPT='%m:%1~ %n%# '\r\n<\/pre>\n","protected":false},"excerpt":{"rendered":"<div class=\"pps-series-post-details pps-series-post-details-variant-classic pps-series-post-details-18702 pps-series-meta-excerpt\" data-series-id=\"581\"><div class=\"pps-series-meta-content\"><div class=\"pps-series-meta-text\">This entry is part 2 of 6 in the series <a href=\"https:\/\/www.bartbusschots.ie\/s\/series\/bash-to-zsh\/\">Bash to Zsh<\/a><\/div><\/div><\/div><p>Apple recently announced that it&#8217;s moving the MacOS from the Bourne-again Shell (Bash) to the Z Shell (Zsh), and advised developers to make the change now, so they&#8217;re ready when they remove Bash altogether in some later version of the OS. Since I&#8217;m a big believer in not swimming up-stream, I decided to take their [&hellip;]<\/p>\n","protected":false},"author":3,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_memberships_contains_paid_content":false,"footnotes":"","jetpack_publicize_message":"","jetpack_publicize_feature_enabled":true,"jetpack_social_post_already_shared":true,"jetpack_social_options":{"image_generator_settings":{"template":"highway","default_image_id":0,"font":"","enabled":false},"version":2},"jetpack_post_was_ever_published":false},"categories":[12,446],"tags":[406,549,458,580],"series":[581],"class_list":["post-15862","post","type-post","status-publish","format-standard","hentry","category-computers-tech","category-sysadmin","tag-commandline","tag-macos","tag-tutorial","tag-zsh","series-bash-to-zsh"],"jetpack_publicize_connections":[],"jetpack_featured_media_url":"","jetpack_shortlink":"https:\/\/wp.me\/p7t9xK-47Q","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/posts\/15862","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/users\/3"}],"replies":[{"embeddable":true,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/comments?post=15862"}],"version-history":[{"count":2,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/posts\/15862\/revisions"}],"predecessor-version":[{"id":15922,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/posts\/15862\/revisions\/15922"}],"wp:attachment":[{"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/media?parent=15862"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/categories?post=15862"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/tags?post=15862"},{"taxonomy":"series","embeddable":true,"href":"https:\/\/www.bartbusschots.ie\/s\/wp-json\/wp\/v2\/series?post=15862"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}