Skip to content

Instantly share code, notes, and snippets.

@jesusalc
Forked from leipzig/mycd.sh
Last active November 13, 2023 18:37
Show Gist options
  • Save jesusalc/b14a57ec9024ff1a3889be6b2c968bb7 to your computer and use it in GitHub Desktop.
Save jesusalc/b14a57ec9024ff1a3889be6b2c968bb7 to your computer and use it in GitHub Desktop.
directory based history bash profile
#!/usr/bin/env bash
#!/bin/bash
#
# .mycd von jesusalc
#
# REF https://gist.github.com/jesusalc/b14a57ec9024ff1a3889be6b2c968bb7
#
# Make sure there is a tty assigned
# if test -t 0 ; then
if [ -t 0 ] && [ -t 1 ] ; then
{
# if mesg n ; then # set not empty -IF DEFINED AND HAS SOMETHING GO IN(o>
# {
# echo hola
# exec 3>&1 4>&2 >>"${_log_file}" 2>&1 # How to redirect output REF: https://stackoverflow.co>
# _mycd_no_wall_broadcast_no_banner=1
# _mycd_running=1
function type_function_exists() {
type "$1" > /dev/null 2>&1
} # type_function_exists
## DEBUG First Concept ( type_function_exists nvm_select_from_mycd ) && return
## DEBUG Concept if ( ! type_function_exists nvm_select_from_myc ) ; then { echo "add new" ; } ; else ; { echo "skip repeats"; } ; fi
if ( ! type_function_exists nvm_select_from_myc ) ; then
{
## echo "add new" ;
function nvm_select_from_mycd(){
# local DEBUG=1
(( DEBUG )) && echo "debug nvm_select_from_mycd"
if [ -f ".nvmrc" ] ; then # file exists
{
BASHSELECTINGNVMNODE=$(<.nvmrc)
(( DEBUG )) && echo "# Current node responding is same as nvmrc then do nothing "
if [[ "$(node --version)" == *"${BASHSELECTINGNVMNODE}"* ]] ; then
{
(( DEBUG )) && echo ".nvmrc found and ..node version is"
(( DEBUG )) && node --version
set -e
set +e
}
else
{
(( DEBUG )) && echo ".nvmrc not found"
(( DEBUG )) && echo "# Is node installed in nvm ?"
if [[ "$(nvm ls | grep ${BASHSELECTINGNVMNODE} | head -1)" == *"${BASHSELECTINGNVMNODE}"* ]] ; then
{
(( DEBUG )) && echo "nvm ls shows has node verison installed found"
(( DEBUG )) && echo "tell to select it node version"
nvm use ${BASHSELECTINGNVMNODE} >/dev/null 2>&1;
# Confirm
if [[ "$(node --version)" == *"${BASHSELECTINGNVMNODE}"* ]] ; then
{
set -e
set +e
}
else
{
echo "ERROR Mycd - Failed to select node - nvm use ${BASHSELECTINGNVMNODE}"
}
fi
}
else
{
# Not installed
(( DEBUG )) && echo "not found"
nvm install ${BASHSELECTINGNVMNODE} >/dev/null 2>&1;
wait
# Do switch case again
if [[ "$(nvm ls | grep ${BASHSELECTINGNVMNODE} | head -1)" == *"${BASHSELECTINGNVMNODE}"* ]] ; then
{
(( DEBUG )) && echo "found"
(( DEBUG )) && echo "select it"
nvm use ${BASHSELECTINGNVMNODE} >/dev/null 2>&1;
# Confirm
if [[ "$(node --version)" == *"${BASHSELECTINGNVMNODE}"* ]] ; then
{
set -e
set +e
}
else
{
echo "ERROR Mycd - Failed to select node - nvm use ${BASHSELECTINGNVMNODE}"
}
fi
}
else
{
(( DEBUG )) && echo "Not installed"
(( DEBUG )) && echo "not found"
echo "ERROR Mycd - Failed to install node ${BASHSELECTINGNVMNODE} - nvm install ${BASHSELECTINGNVMNODE}"
}
fi
}
fi
}
fi
}
fi
return 0
} # end nvm_select_from_mycd
function nodenv_select_from_mycd(){
# local DEBUG=1
(( DEBUG )) && echo "debug nodenv_select_from_mycd"
if [ -f ".node-version" ] ; then # file exists
{
BASHSELECTINGNODENVNODE=$(<.node-version)
(( DEBUG )) && echo "# Current node responding is same as ode-version then do nothing"
if [[ "$(node --version)" == *"${BASHSELECTINGNODENVNODE}"* ]] ; then
{
(( DEBUG )) && echo "mycd nodenv found node"
(( DEBUG )) && node --version
set -e
set +e
}
else
{
(( DEBUG )) && echo "mycd nodenv node not found"
(( DEBUG )) && echo "# Is node installed in nodenv ?"
if [[ "$(nodenv versions | grep ${BASHSELECTINGNODENVNODE} | head -1)" == *"${BASHSELECTINGNODENVNODE}"* ]] ; then
{
(( DEBUG )) && echo "nodenv version found"
(( DEBUG )) && echo "nodenv select it"
nodenv local ${BASHSELECTINGNODENVNODE} >/dev/null 2>&1;
(( DEBUG )) && echo "# Confirm selection"
local confirming="$(~/.nodenv/shims/node --version)"
(( DEBUG )) && echo "${confirming}"
(( DEBUG )) && echo "${BASHSELECTINGNODENVNODE}"
if [[ "${confirming}" == *"${BASHSELECTINGNODENVNODE}"* ]] ; then
{
set -e
set +e
}
else
{
echo "ERROR Mycd 1 - Failed to select node ${confirming} != - nodenv local ${BASHSELECTINGNODENVNODE}"
}
fi
}
else
{
(( DEBUG )) && echo "mycd nodenv node version # Not installed"
(( DEBUG )) && echo "mycd nodenv node version not found"
nodenv install ${BASHSELECTINGNODENVNODE} >/dev/null 2>&1;
wait
(( DEBUG )) && echo "mycd nodenv # Do switch case again"
if [[ "$(node versions | grep ${BASHSELECTINGNODENVNODE} | head -1)" == *"${BASHSELECTINGNODENVNODE}"* ]] ; then
{
(( DEBUG )) && echo "mycd nodenv found again"
(( DEBUG )) && echo "mycd nodenv select it again"
nodenv local ${BASHSELECTINGNODENVNODE} >/dev/null 2>&1;
(( DEBUG )) && echo "# Confirm selection again"
local confirming="$(~/.nodenv/shims/node --version)"
(( DEBUG )) && echo "${confirming}"
(( DEBUG )) && echo "${BASHSELECTINGNODENVNODE}"
if [[ "${confirming}" == *"${BASHSELECTINGNODENVNODE}"* ]] ; then
{
set -e
set +e
}
else
{
echo "ERROR Mycd 2 - Failed to select again node ${confirming} - nodenv local ${BASHSELECTINGNODENVNODE}"
}
fi
}
else
{
(( DEBUG )) && echo "Not installed"
(( DEBUG )) && echo "not found"
echo "ERROR Mycd - Failed to install node ${BASHSELECTINGNODENVNODE} - nodenv install ${BASHSELECTINGNODENVNODE}"
}
fi
}
fi
}
fi
}
fi
return 0
} # end nodenv_select_from_mycd
function rbenv_select_from_mycd(){
# local DEBUG=1
(( DEBUG )) && echo "debug rbenv_select_from_mycd"
if [ -f ".ruby-version" ] ; then # file exists
{
BASHSELECTINGRBENVRUBY=$(<.ruby-version)
(( DEBUG )) && echo "# Current ruby responding is same as ode-version then do nothing"
if [[ "$(ruby --version)" == *"${BASHSELECTINGRBENVRUBY}"* ]] ; then
{
(( DEBUG )) && echo "mycd rbenv found ruby"
(( DEBUG )) && ruby --version
set -e
set +e
}
else
{
(( DEBUG )) && echo "mycd rbenv ruby not found"
(( DEBUG )) && echo "# Is ruby installed in rbenv ?"
if [[ "$(rbenv versions | grep ${BASHSELECTINGRBENVRUBY} | head -1)" == *"${BASHSELECTINGRBENVRUBY}"* ]] ; then
{
(( DEBUG )) && echo "rbenv version found"
(( DEBUG )) && echo "rbenv select it"
rbenv local ${BASHSELECTINGRBENVRUBY}
(( DEBUG )) && echo "# Confirm selection"
local confirming="$(~/.rbenv/shims/ruby --version)"
(( DEBUG )) && echo "${confirming}"
(( DEBUG )) && echo "${BASHSELECTINGRBENVRUBY}"
if [[ "${confirming}" == *"${BASHSELECTINGRBENVRUBY}"* ]] ; then
{
set -e
set +e
}
else
{
echo "ERROR Mycd 1 - Failed to select ruby ${confirming} != - rbenv local ${BASHSELECTINGRBENVRUBY}"
}
fi
}
else
{
(( DEBUG )) && echo "mycd rbenv ruby version # Not installed"
(( DEBUG )) && echo "mycd rbenv ruby version not found"
rbenv install ${BASHSELECTINGRBENVRUBY} >/dev/null 2>&1;
wait
(( DEBUG )) && echo "mycd rbenv # Do switch case again"
if [[ "$(ruby versions | grep ${BASHSELECTINGRBENVRUBY} | head -1)" == *"${BASHSELECTINGRBENVRUBY}"* ]] ; then
{
(( DEBUG )) && echo "mycd rbenv found again"
(( DEBUG )) && echo "mycd rbenv select it again"
rbenv local ${BASHSELECTINGRBENVRUBY} >/dev/null 2>&1;
(( DEBUG )) && echo "# Confirm selection again"
local confirming="$(~/.rbenv/shims/ruby --version)"
(( DEBUG )) && echo "${confirming}"
(( DEBUG )) && echo "${BASHSELECTINGRBENVRUBY}"
if [[ "${confirming}" == *"${BASHSELECTINGRBENVRUBY}"* ]] ; then
{
set -e
set +e
}
else
{
echo "ERROR Mycd 2 - Failed to select again ruby ${confirming} - rbenv local ${BASHSELECTINGRBENVRUBY}"
}
fi
}
else
{
(( DEBUG )) && echo "Not installed"
(( DEBUG )) && echo "not found"
echo "ERROR Mycd - Failed to install ruby ${BASHSELECTINGRBENVRUBY} - rbenv install ${BASHSELECTINGRBENVRUBY}"
}
fi
}
fi
}
fi
}
fi
return 0
} # end rbenv_select_from_mycd
function execute_files_mycd(){
if [ -f ".execute.sh" ] ; then # file exists
{
chmod +x .execute.sh
sh .execute.sh
}
fi
if [ -f ".execute.bash" ] ; then # file exists
{
chmod +x .execute.bash
bash .execute.bash
}
fi
if [ -f ".execute.zsh" ] ; then # file exists
{
chmod +x .execute.bash
bash .execute.bash
}
fi
if [ -f ".execute" ] ; then # file exists
{
chmod +x ./.execute
./.execute
}
fi
if [ -f ".autoexecute" ] ; then # file exists
{
chmod +x ./.autoexecute
./.autoexecute
}
fi
return 0
} # end execute_files_mycd
function git_projectparticipation_mycd(){
if [ -d "$PWD/.git" ] ; then # dir exists
{
if command -v projectparticipation >/dev/null 2>&1; then #Command Exists
{
projectparticipation
}
fi
if command -v gsb >/dev/null 2>&1; then #Command Exists
{
echo -e "\\033[38;5;93m === Git Status \\033[38;5;93m === \\033[38;5;123m ";
gsb
}
fi
}
fi
} # end git_projectparticipation_mycd
function mycd()
{
# if this directory is writable then write to directory-based history file
# otherwise write history in the usual home-based history file
tmpDir=$PWD
echo "#"`date '+%s'` >> $HISTFILE
echo $USER' has exited '$PWD' for '$@ >> $HISTFILE
builtin cd "$@" # do actual cd
if [ -f "$PWD/.tutorial" ] ; then
{
if [ -w $PWD ]; then
{
export HISTFILE="$PWD/.tutorial";
touch $HISTFILE;
chmod 644 $HISTFILE;
}
else
{
export HISTFILE="$HOME/.bash_history";
}
fi
}
else
{
if [ -w $PWD ]; then
{
export HISTFILE="$PWD/.dir_bash_history";
touch $HISTFILE;
chmod 644 $HISTFILE;
}
else
{
export HISTFILE="$HOME/.bash_history";
}
fi
}
fi
echo "#"`date '+%s'` >> $HISTFILE
echo $USER' has entered '$PWD' from '$OLDPWD >> $HISTFILE
} # end mycd
alias cd="mycd"
function mycd_decide_nvm_or_nodenv(){
local flag=0
( type_function_exists nvm ) && flag=$(( flag + 1 ))
( type_function_exists nodenv ) && flag=$(( flag + 3 ))
if (( flag == 4 )) ; then
{
echo "ERROR Two Node version managers found active nvm and nodenv. Consider removing one. Using nodenv now. "
nodenv_select_from_mycd
}
elif (( flag == 1 )) ; then
{
nvm_select_from_mycd
}
elif (( flag == 3 )) ; then
{
nodenv_select_from_mycd
}
else
{
return 0
}
fi
} # end mycd_decide_nvm_or_nodenv
# initial shell opened
# if .tutorial file exists in this repo then assign it
if [ -f "$PWD/.tutorial" ] ; then
{
export HISTFILE="$PWD/.tutorial"
}
else
{
export HISTFILE="$PWD/.dir_bash_history"
}
fi
# timestamp all history entries
export HISTTIMEFORMAT="%h/%d - %H:%M:%S "
export HISTCONTROL=ignoredups:erasedups
export HISTSIZE=1000000
export HISTFILESIZE=1000000
if [[ $(echo $0) == *"zsh" ]] ; then # [[ $(which $SHELL) == *"zsh" ]] &&
{
setopt append_history ## append, no clearouts
setopt hist_verify ## edit a recalled history line before executing
setopt completeinword
setopt interactive
setopt share_history ## Share history between multiple simultaneous zsh sessions.
setopt inc_append_history
}
elif [[ $(echo $0) == *"bash" ]] ; then # [[ $(which $SHELL) == *"bash" ]] &&
{
shopt -s histappend ## append, no clearouts
shopt -s histverify ## edit a recalled history line before executing
shopt -s histreedit ## reedit a history substitution line if it failed
}
fi
[ ! -z ${PROMPT_COMMAND+x} ] || PROMPT_COMMAND=""
export PROMPT_COMMAND="history -a; history -c; history -r; $PROMPT_COMMAND"
mycd_decide_nvm_or_nodenv
rbenv_select_from_mycd
execute_files_mycd
## Save the history after each command finishes
## (and keep any existing PROMPT_COMMAND settings)
export PROMPT_COMMAND="history -a; history -c; history -r; $PROMPT_COMMAND"
# }
# else
# {
# echo "skip repeats";
}
fi
# }
# else
# {
# echo doble hola
# _mycd_no_wall_broadcast_no_banner=1
# _mycd_cron_running=0
# exec 3>&1 1>>"${_log_file}" 2>&1 # How to write output to both console and file REF: https:/>
# exec 3>&1 4>&2 >>"${_log_file}" 2>&1 # How to redirect output REF: https://stackoverflow.co>
# }
# fi
}
fi
@jesusalc
Copy link
Author

jesusalc commented Aug 2, 2016

History Directory Based Bash Histories For Linux, Mac, Bash, Shell, and Zsh ( tutorial, dir_bash_history, autoexecute, and execute); self-executing files inside a folder.

Rationale

Using a directory-based bash history allows for a record of shell actions on a directory basis, so a group of developers has some record of what was done while in a directory, when, and by whom. This can be helpful when trying to reconstruct history with limited documentation.

This was derived from http://dieter.plaetinck.be/per_directory_bash_history

Installation

cd ~/
git clone https://gist.github.com/jesusalc/b14a57ec9024ff1a3889be6b2c968bb7 .mycd
chmod +x .mycd/mycd.sh

Add to MAC Bash:

echo '. $HOME/.mycd/mycd.sh' >> ~/.bash_profile

Add to Linux Bash:

echo '. $HOME/.mycd/mycd.sh' >> ~/.bashrc

Add to Zsh:

echo '. $HOME/.mycd/mycd.sh' >> ~/.zshrc

Add .dir_bash_history to .gitignore in your work folder

echo '.dir_bash_history' >> ~/.gitignore
  • OR - Add .dir_bash_history to the GLOBAL env .gitignore, ignore:
mkdir -p  ~/.config/git
touch ~/.config/git/ignore
echo '.dir_bash_history' >> ~/.config/git/ignore

Remember to open a new tab or reopen the terminal for this to work.

Usage

This works while using the terminal, like Gnome-Terminal. Since it is attaching its functionality to the "cd" command,
YOU MUST USE "cd" in order for this technique TO WORK.

This script provides three functions:

  1. Stores local history inside a local file in each directory: .dir_bash_history

  2. Record local history inside a local file as tutorial instead: .tutorial
    ( for this to work, you have to create the file .tutorial )
    ( by doing this, it will stop writting .dir_bash_history and only to .tutorial file )

  3. Executes a local file inside a folder when it exists called: .execute, .execute.sh, .execute.bash, or .autoexecute
    ( for this to work, you have to create the file and place your desired executions here )

:)

@jesusalc
Copy link
Author

updated to use echo $0 instead of which shell to check for the current executing shell

@jesusalc
Copy link
Author

added looking into .nvmrc file and changing the node version to match.

@jesusalc
Copy link
Author

jesusalc commented Mar 7, 2021

added using nvm or nodenv to select version of node when doing cd into project with a .node-version or a .nvmrc file.

@jesusalc
Copy link
Author

jesusalc commented Mar 7, 2021

added selecting ruby version with rbenv when cd into folder

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment