Skip to content

Commit

Permalink
add elvish support, only load interactive.* if login and interactive,…
Browse files Browse the repository at this point in the history
… as intended

/close #179
  • Loading branch information
balupton committed Oct 7, 2023
1 parent ca5ac94 commit 53dd037
Show file tree
Hide file tree
Showing 21 changed files with 269 additions and 28 deletions.
6 changes: 6 additions & 0 deletions .github/workflows/dorothy-workflow.yml
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ jobs:
setup-util-fish
setup-util-nu
setup-util-xonsh
setup-util-elvish
dorothy install
# nu -c 'echo $nu.loginshell-path'
- name: 'Dorothy Login Shell: bash'
Expand Down Expand Up @@ -64,6 +65,11 @@ jobs:
run: |
command-exists dorothy
echo-style --success='ok'
- name: 'Dorothy Login Shell: elvish'
shell: elvish {0}
run: |
command-exists dorothy
echo-style --success='ok'
- name: 'Trunk Format'
if: github.event_name == 'push'
shell: bash -leo pipefail {0}
Expand Down
10 changes: 6 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@

Dorothy is a dotfile ecosystem featuring:

- seamless support for [Bash](<https://en.wikipedia.org/wiki/Bash_(Unix_shell)>), [Fish](<https://en.wikipedia.org/wiki/Fish_(Unix_shell)>), [Zsh](https://en.wikipedia.org/wiki/Z_shell), [Nu](https://www.nushell.sh), [Xonsh](https://xon.sh)
- seamless support for [Bash](<https://en.wikipedia.org/wiki/Bash_(Unix_shell)>), [Fish](<https://en.wikipedia.org/wiki/Fish_(Unix_shell)>), [Zsh](https://en.wikipedia.org/wiki/Z_shell), [Nu](https://www.nushell.sh), [Xonsh](https://xon.sh), [Elvish](https://elv.sh)
- seamless support for multiple operating systems and architectures
- seamless support for your favorite terminal and GUI editors
- automatic configuration of your environment variables for what you have installed on your system
Expand Down Expand Up @@ -189,24 +189,26 @@ For each shell that you configured during the Dorothy installation (can be recon
- [Fish](<https://en.wikipedia.org/wiki/Fish_(Unix_shell)>) loads our [`init.fish`](https://github.com/bevry/dorothy/blob/master/init.fish) script
- [Nu](https://www.nushell.sh) loads our [`init.nu`](https://github.com/bevry/dorothy/blob/master/init.nu) script
- [Xonsh](https://xon.sh) loads our [`init.xsh`](https://github.com/bevry/dorothy/blob/master/init.xsh) script
- [Elvish](https://elv.sh) loads our [`init.elv`](https://github.com/bevry/dorothy/blob/master/init.elv) script
- POSIX shells ([Bash](<https://en.wikipedia.org/wiki/Bash_(Unix_shell)>), [Zsh](https://en.wikipedia.org/wiki/Z_shell), etc) load our [`init.sh`](https://github.com/bevry/dorothy/blob/master/init.sh) script

1. The initialization script will:

1. Ensure the `DOROTHY` environment variable is set to the location of the Dorothy installation.

1. If a login shell, it loads our login script `sources/login.(sh|fish|nu|xsh)`, which will:
1. If a login shell, it loads our login script `sources/login.(sh|fish|nu|xsh|elv)`, which will:

1. Apply any configuration changes necessary for that login shell
1. Load our environment script `sources/environment.(sh|fish|nu|xsh)`, which will:
1. Load our environment script `sources/environment.(sh|fish|nu|xsh|elv)`, which will:

1. Invoke `commands/setup-environment-commands` which determines and applies all necessary environment configuration changes to the shell. It loads your `user/config(.local)/environment.bash` configuration script for your own custom environment configuration that will be applied to all your login shells.

1. If a login and interactive shell, it loads our interactive script `sources/interactive.(sh|fish|nu|xsh)`, which will:
1. If a login and interactive shell, it loads our interactive script `sources/interactive.(sh|fish|nu|xsh|elv)`, which will:

1. Load your own `user/config(.local)/interactive.(sh|fish|nu|xsh)` configuration script for your own interactive login shell configuration.
- Nu will only load `interactive.nu` and it must exist.
- Xonsh will only load `interactive.xsh` if it exists.
- Elvish will only load `interactive.elv` if it exists.
- Fish shell will load `interactive.fish` if it exists, otherwise it will load `interactive.sh`.
- POSIX shells will load their `interactive.(bash|zsh|...etc)` file if it exists, otherwise they will load `interactive.sh` if exists.
1. Load any common alias and function utilities.
Expand Down
59 changes: 52 additions & 7 deletions commands/dorothy
Original file line number Diff line number Diff line change
Expand Up @@ -1085,14 +1085,21 @@ function dorothy() (

function ensure_shell_configured {
# process arguments
local item option_clean='no' option_uninstall='no'
local item option_clean='no' use_bash='' use_zsh='' use_fish='' use_nu='' use_xonsh='' use_elvish=''
while test "$#" -ne 0; do
item="$1"
shift
case "$item" in
'--clean' | '--clean=yes') option_clean='yes' ;;
'--no-clean' | '--clean=no') option_clean='no' ;;
'--uninstall') option_uninstall='yes' ;;
'--uninstall')
use_bash='no'
use_zsh='no'
use_fish='no'
use_nu='no'
use_xonsh='no'
use_elvish='no'
;;
'--'*) help "An unrecognised flag was provided: $item" ;;
*) help "An unrecognised argument was provided: $item" ;;
esac
Expand All @@ -1102,7 +1109,10 @@ function dorothy() (

# bash
# bash always exists, so always default to positive
if test "$option_uninstall" = 'yes' || confirm --positive --ppid=$$ -- "Would you like $(echo-style --bold=Bash) to use Dorothy?"; then
if test -z "$use_bash" && confirm --positive --ppid=$$ -- "Would you like $(echo-style --bold=Bash) to use Dorothy?"; then
use_bash='yes'
fi
if test "$use_bash" = 'yes'; then
setup-util-bash --quiet

# cleanup
Expand All @@ -1126,7 +1136,10 @@ function dorothy() (

# zsh
# https://zsh.sourceforge.io/Intro/intro_3.html
if test "$option_uninstall" = 'yes' || confirm --positive="$(echo-exit-affirmative -- command-exists zsh)" --ppid=$$ -- "Would you like $(echo-style --bold=Zsh) to use Dorothy?"; then
if test -z "$use_zsh" && confirm --positive="$(echo-exit-affirmative -- command-exists zsh)" --ppid=$$ -- "Would you like $(echo-style --bold=Zsh) to use Dorothy?"; then
use_zsh='yes'
fi
if test "$use_zsh" = 'yes'; then
setup-util-zsh --quiet
mkdir -p "$ZDOTDIR"

Expand Down Expand Up @@ -1155,7 +1168,10 @@ function dorothy() (
fi

# fish
if test "$option_uninstall" = 'yes' || confirm --positive="$(echo-exit-affirmative -- command-exists fish)" --ppid=$$ -- "Would you like $(echo-style --bold=Fish) to use Dorothy?"; then
if test -z "$use_fish" && confirm --positive="$(echo-exit-affirmative -- command-exists fish)" --ppid=$$ -- "Would you like $(echo-style --bold=Fish) to use Dorothy?"; then
use_fish='yes'
fi
if test "$use_fish" = 'yes'; then
setup-util-fish --quiet
mkdir -p "$HOME/.config/fish"

Expand All @@ -1174,7 +1190,10 @@ function dorothy() (
fi

# nu
if test "$option_uninstall" = 'yes' || confirm --positive="$(echo-exit-affirmative -- command-exists nu)" --ppid=$$ -- "Would you like $(echo-style --bold=Nu) to use Dorothy?"; then
if test -z "$use_nu" && confirm --positive="$(echo-exit-affirmative -- command-exists nu)" --ppid=$$ -- "Would you like $(echo-style --bold=Nu) to use Dorothy?"; then
use_nu='yes'
fi
if test "$use_nu" = 'yes'; then
setup-util-nu --quiet

# trunk-ignore(shellcheck/SC2016)
Expand All @@ -1187,7 +1206,10 @@ function dorothy() (
fi

# xonsh
if test "$option_uninstall" = 'yes' || confirm --positive="$(echo-exit-affirmative -- command-exists xonsh)" --ppid=$$ -- "Would you like $(echo-style --bold=Xonsh) to use Dorothy?"; then
if test -z "$use_xonsh" && confirm --positive="$(echo-exit-affirmative -- command-exists xonsh)" --ppid=$$ -- "Would you like $(echo-style --bold=Xonsh) to use Dorothy?" 'Xonsh support is currently beta-quality.'; then
use_xonsh='yes'
fi
if test "$use_xonsh" = 'yes'; then
# https://xon.sh/xonshrc.html
setup-util-xonsh --quiet
mkdir -p "$HOME/.config/xonsh/rc.d"
Expand All @@ -1201,6 +1223,26 @@ function dorothy() (
--find='.+? # Dorothy' --replace=''
fi

# elvish
if test -z "$use_elvish" && confirm --positive="$(echo-exit-affirmative -- command-exists elvish)" --ppid=$$ -- "Would you like $(echo-style --bold=Elvish) to use Dorothy?" 'Elvish support is currently beta-quality.'; then
use_elvish='yes'
fi
if test "$use_elvish" = 'yes'; then
# https://elv.sh/ref/command.html#rc-file
# https://elv.sh/ref/runtime.html
# https://github.com/elves/elvish/issues/1726
setup-util-elvish --quiet
mkdir -p "$HOME/.config/elvish"

# configure
config-helper --file="$HOME/.config/elvish/rc.elv" -- \
--find='.+? # Dorothy' --replace="eval (cat '$DOROTHY/init.elv' | slurp) # Dorothy"
else
mkdir -p "$HOME/.config/elvish"
config-helper --file="$HOME/.config/elvish/rc.elv" -- \
--find='.+? # Dorothy' --replace=''
fi

echo-segment --g2='Dorothy Shell Configuration'
}

Expand Down Expand Up @@ -1463,6 +1505,9 @@ function dorothy() (
if test -f "$DOROTHY/user/config/interactive.xsh"; then
config-edit --file="$DOROTHY/user/config/interactive.xsh" --needle="\$DOROTHY_THEME" --line="\$DOROTHY_THEME = $(echo-quote -- "$theme")" --add
fi
if test -f "$DOROTHY/user/config/interactive.elv"; then
config-edit --file="$DOROTHY/user/config/interactive.elv" --needle="\$DOROTHY_THEME" --line="set-env DOROTHY_THEME $(echo-quote -- "$theme")" --add
fi

# log
echo-style --success='Configuration change applied, ' --notice='restart your terminal for the change to take effect.'
Expand Down
33 changes: 33 additions & 0 deletions commands/setup-util-elvish
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
#!/usr/bin/env bash

# https://elv.sh/get/

function setup_util_elvish() (
source "$DOROTHY/sources/bash.bash"

# improve performance
if is-needle --quiet "$@" && ! is-needle --upgrade "$@" && ! is-needle --uninstall "$@" && command-exists elvish; then
return 0
fi

# setup
local arch options=(
--cli='elvish'
"$@"
AUR='elvish'
DEB='elvish'
BREW='elvish'
PORT='elvish'
SCOOP='elvish'
PKG='elvish'
PKGIN='elvish'
PKGADD='elvish'
NIX='elvish'
)
setup-util "${options[@]}"
)

# fire if invoked standalone
if test "$0" = "${BASH_SOURCE[0]}"; then
setup_util_elvish "$@"
fi
17 changes: 17 additions & 0 deletions init.elv
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
#!/usr/bin/env elvish
use runtime

# this should be consistent with:
# $DOROTHY/init.*
# $DOROTHY/commands/dorothy
if (has-env 'DOROTHY') {
set-env 'DOROTHY' $E:HOME'/.local/share/dorothy'
}

# https://elv.sh/ref/command.html#rc-file
# https://elv.sh/ref/runtime.html
# https://github.com/elves/elvish/issues/1726
if (not-eq $runtime:effective-rc-path $nil) {
eval (cat $E:DOROTHY'/sources/login.elv' | slurp)
eval (cat $E:DOROTHY'/sources/interactive.elv' | slurp)
}
5 changes: 3 additions & 2 deletions init.fish
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,9 @@ if ! set -q DOROTHY
set -xg DOROTHY (dirname (status -f))
end

# login
if status --is-login
source "$DOROTHY/sources/login.fish"
source "$DOROTHY/sources/interactive.fish"
if status --is-interactive
source "$DOROTHY/sources/interactive.fish"
end
end
4 changes: 3 additions & 1 deletion init.nu
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,7 @@ $env.PATH = ($env.PATH | split row (char esep) | prepend $'($env.HOME)/.local/sh

if $nu.is-login {
source ./sources/login.nu
source ./sources/interactive.nu
if $nu.is-interactive {
source ./sources/interactive.nu
}
}
2 changes: 1 addition & 1 deletion init.sh
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ if test "${DOROTHY_LOAD-}" = 'yes'; then
# init dorothy's environment for the login shell
. "$DOROTHY/sources/login.sh"

# if the login shell is interactive, then init dorothy for the interactive login shell
# if the login shell is also interactive, then init dorothy for the interactive login shell
# [test -t 0] and [test -s] are true despite [env -i bash -lc ...]
case $- in *i*) . "$DOROTHY/sources/interactive.sh" ;; esac
fi
5 changes: 2 additions & 3 deletions init.xsh
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,5 @@ if ${...}.get('DOROTHY') == None:

if $XONSH_LOGIN == True:
execx(compilex(open($DOROTHY + '/sources/login.xsh').read()))

if $XONSH_INTERACTIVE == True:
execx(compilex(open($DOROTHY + '/sources/interactive.xsh').read()))
if $XONSH_INTERACTIVE == True:
execx(compilex(open($DOROTHY + '/sources/interactive.xsh').read()))
33 changes: 33 additions & 0 deletions sources/config.elv
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
#!/usr/bin/env elvish

# @todo: couldn't get this going

# for scripts and sources to load a configuration file
# load_dorothy_config ...<filename>
fn load_dorothy_config {|@filenames|
var dorothy_config_loaded = $false

# for each filename, load a single config file
for filename filenames {
if ?(test -f $E:DOROTHY'/user/config.local/'$filename) {
# load user/config.local/*
eval (cat $E:DOROTHY'/user/config.local/'$filename | slurp)
set dorothy_config_loaded = $true
} elif ?(test -f $E:DOROTHY'/user/config/'$filename) {
# otherwise load user/config/*
eval (cat $E:DOROTHY'/user/config/'$filename | slurp)
set dorothy_config_loaded = $true
} elif ?(test -f $E:DOROTHY'/config/'$filename) {
# otherwise load default configuration
eval (cat $E:DOROTHY'/config/'$filename | slurp)
set dorothy_config_loaded = $true
}
# otherwise try next filename
}

# if nothing was loaded, then fail
if (eq dorothy_config_loaded $false) {
echo-style --error="Missing the configuration file: $argv" >/dev/stderr
return 2 # No such file or directory
}
}
12 changes: 7 additions & 5 deletions sources/config.xsh
Original file line number Diff line number Diff line change
@@ -1,29 +1,31 @@
#!/usr/bin/env xonsh

# @todo: couldn't get this going

from os import path

# for scripts and sources to load a configuration file
# load_dorothy_config ...<filename>
def load_dorothy_config(*args):
dorothy_config_loaded = 'no'
dorothy_config_loaded = False

# for each filename, load a single config file
for filename in args:
if path.exists($DOROTHY + '/user/config.local/' + filename):
# load user/config.local/*
execx(compilex(open($DOROTHY + '/user/config.local/' + filename).read()))
dorothy_config_loaded = 'yes'
dorothy_config_loaded = True
elif path.exists($DOROTHY + '/user/config/' + filename):
# otherwise load user/config/*
execx(compilex(open($DOROTHY + '/user/config/' + filename).read()))
dorothy_config_loaded = 'yes'
dorothy_config_loaded = True
elif path.exists($DOROTHY + '/config/' + filename):
# otherwise load default configuration
execx(compilex(open($DOROTHY + '/config/' + filename).read()))
dorothy_config_loaded = 'yes'
dorothy_config_loaded = True
# otherwise try next filename

# if nothing was loaded, then fail
if dorothy_config_loaded == 'no':
if dorothy_config_loaded == False:
echo-style --error=@('Missing the configuration file: ' + args.join(' ')) >/dev/stderr
return 2 # No such file or directory
9 changes: 9 additions & 0 deletions sources/env.bash
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,9 @@ function on_env_finish {
echo "setenv $name"
elif test "$shell" = 'xonsh'; then
echo 'del $'"$name"
elif test "$shell" = 'elvish'; then
# https://elv.sh/ref/builtin.html#unset-env
echo "unset-env $name"
else
echo "export $name='';"
fi
Expand All @@ -116,6 +119,9 @@ function on_env_finish {
echo "setenv $name $value"
elif test "$shell" = 'xonsh'; then
echo '$'"$name = '$value'.split(':')"
elif test "$shell" = 'elvish'; then
# https://elv.sh/ref/builtin.html#set-env
echo "set-env $name $value"
else
echo "export $name='$value';"
fi
Expand All @@ -127,6 +133,9 @@ function on_env_finish {
echo "setenv $name $value"
elif test "$shell" = 'xonsh'; then
echo '$'"$name = '$value'"
elif test "$shell" = 'elvish'; then
# https://elv.sh/ref/builtin.html#set-env
echo "set-env $name = $value"
else
echo "export $name='$value';"
fi
Expand Down
4 changes: 4 additions & 0 deletions sources/environment.elv
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
#!/usr/bin/env elvish

# set the environment variables
eval ($E:DOROTHY'/commands/setup-environment-commands' elvish | slurp)
18 changes: 18 additions & 0 deletions sources/interactive.elv
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
#!/usr/bin/env elvish

# use test -f, instead of os builtin, as test -f actually handles /user symlink

# Load the configuration for interactive shells
if ?(test -f $E:DOROTHY'/user/config.local/interactive.elv') {
eval (cat $E:DOROTHY'/user/config.local/interactive.elv' | slurp)
} elif ?(test -f $E:DOROTHY'/user/config/interactive.elv') {
eval (cat $E:DOROTHY'/user/config/interactive.elv' | slurp)
} elif ?(test -f $E:DOROTHY'/config/interactive.elv') {
eval (cat $E:DOROTHY'/config/interactive.elv' | slurp)
}

# Continue with the shell extras
# use ./history.elv
eval (cat $E:DOROTHY'/sources/theme.elv' | slurp)
# use ./ssh.elv
# use ./autocomplete.elv
Loading

0 comments on commit 53dd037

Please sign in to comment.