|
@@ -1,27 +1,64 @@
|
|
|
#!/bin/zsh
|
|
#!/bin/zsh
|
|
|
|
|
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
+# NAVIGATION UTILITIES
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
+
|
|
|
eval "$(zoxide init zsh)"
|
|
eval "$(zoxide init zsh)"
|
|
|
|
|
|
|
|
-zi() { z "$@" }
|
|
|
|
|
-za() { z "$@" }
|
|
|
|
|
-zrm() { zoxide remove "$@" }
|
|
|
|
|
|
|
+# Zoxide aliases with better names
|
|
|
|
|
+zcd() { z "$@" }
|
|
|
|
|
+zadd() { z "$@" }
|
|
|
|
|
+zremove() { zoxide remove "$@" }
|
|
|
|
|
+
|
|
|
|
|
+# Legacy aliases for backward compatibility
|
|
|
|
|
+alias zi=zcd
|
|
|
|
|
+alias za=zadd
|
|
|
|
|
+alias zrm=zremove
|
|
|
|
|
|
|
|
|
|
+# Open files with xdg-open (non-blocking)
|
|
|
function open {
|
|
function open {
|
|
|
- for i in $*; do
|
|
|
|
|
- setsid nohup xdg-open $i > /dev/null 2> /dev/null
|
|
|
|
|
|
|
+ if [[ $# -eq 0 ]]; then
|
|
|
|
|
+ echo "Usage: open <file1> [file2] ..."
|
|
|
|
|
+ echo "Opens files using the system default application"
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ for i in "$@"; do
|
|
|
|
|
+ if [[ ! -e "$i" ]]; then
|
|
|
|
|
+ echo "Warning: '$i' does not exist" >&2
|
|
|
|
|
+ continue
|
|
|
|
|
+ fi
|
|
|
|
|
+ setsid nohup xdg-open "$i" > /dev/null 2> /dev/null &
|
|
|
done
|
|
done
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Find and open files with fzf
|
|
|
function fopen() {
|
|
function fopen() {
|
|
|
|
|
+ if ! command -v fd >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: fd is not installed" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if ! command -v fzf >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: fzf is not installed" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
local selected
|
|
local selected
|
|
|
selected=$(fd "$@" | fzf --preview 'bat --color=always --style=numbers --line-range=:500 {}')
|
|
selected=$(fd "$@" | fzf --preview 'bat --color=always --style=numbers --line-range=:500 {}')
|
|
|
[[ -n "$selected" ]] && setsid nohup xdg-open "$selected" >/dev/null 2>&1 &
|
|
[[ -n "$selected" ]] && setsid nohup xdg-open "$selected" >/dev/null 2>&1 &
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# =============================================================================
|
|
|
# DEVELOPMENT TOOLS
|
|
# DEVELOPMENT TOOLS
|
|
|
-# Package manager detection with caching
|
|
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
+
|
|
|
|
|
+# Smart package manager detection and execution
|
|
|
function _package_manager {
|
|
function _package_manager {
|
|
|
local pkg_manager=""
|
|
local pkg_manager=""
|
|
|
|
|
+
|
|
|
|
|
+ # Detect package manager based on lock files
|
|
|
if [[ -f bun.lockb ]]; then
|
|
if [[ -f bun.lockb ]]; then
|
|
|
pkg_manager="bun"
|
|
pkg_manager="bun"
|
|
|
elif [[ -f pnpm-lock.yaml ]]; then
|
|
elif [[ -f pnpm-lock.yaml ]]; then
|
|
@@ -31,15 +68,17 @@ function _package_manager {
|
|
|
elif [[ -f package-lock.json ]]; then
|
|
elif [[ -f package-lock.json ]]; then
|
|
|
pkg_manager="npm"
|
|
pkg_manager="npm"
|
|
|
else
|
|
else
|
|
|
- pkg_manager="pnpm"
|
|
|
|
|
|
|
+ pkg_manager="pnpm" # Default fallback
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
|
|
|
+ # Auto-detect npm scripts if command exists in package.json
|
|
|
if [[ -f package.json ]] && [[ $1 != "run" ]] && [[ $1 != "install" ]] && [[ $1 != "add" ]] && [[ $1 != "remove" ]] && [[ $1 != "i" ]] && [[ $1 != "rm" ]]; then
|
|
if [[ -f package.json ]] && [[ $1 != "run" ]] && [[ $1 != "install" ]] && [[ $1 != "add" ]] && [[ $1 != "remove" ]] && [[ $1 != "i" ]] && [[ $1 != "rm" ]]; then
|
|
|
- if jq -e ".scripts[\"$1\"] != null" package.json >/dev/null 2>&1; then
|
|
|
|
|
|
|
+ if command -v jq >/dev/null 2>&1 && jq -e ".scripts[\"$1\"] != null" package.json >/dev/null 2>&1; then
|
|
|
set -- "run" "$@"
|
|
set -- "run" "$@"
|
|
|
fi
|
|
fi
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
|
|
|
+ # Execute with corepack if available, otherwise direct command
|
|
|
if command -v corepack >/dev/null 2>&1; then
|
|
if command -v corepack >/dev/null 2>&1; then
|
|
|
corepack ${pkg_manager} "$@"
|
|
corepack ${pkg_manager} "$@"
|
|
|
else
|
|
else
|
|
@@ -47,10 +86,18 @@ function _package_manager {
|
|
|
fi
|
|
fi
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-# Improved development commit with optional message
|
|
|
|
|
|
|
+# Quick development commit with auto-push
|
|
|
function dc() {
|
|
function dc() {
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: dc [commit_message]"
|
|
|
|
|
+ echo "Quickly commit all changes and push to remote"
|
|
|
|
|
+ echo "If no message provided, uses timestamp-based message"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
if ! git rev-parse --is-inside-work-tree &>/dev/null; then
|
|
if ! git rev-parse --is-inside-work-tree &>/dev/null; then
|
|
|
- echo "Error: Not in a git repository"
|
|
|
|
|
|
|
+ echo "Error: Not in a git repository" >&2
|
|
|
return 1
|
|
return 1
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
@@ -69,13 +116,35 @@ function dc() {
|
|
|
commit_msg="dev: automated commit - ${timestamp}"
|
|
commit_msg="dev: automated commit - ${timestamp}"
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
|
- # pass other args
|
|
|
|
|
- git commit -m "$commit_msg" --no-gpg-sign "$@"
|
|
|
|
|
- git push &>/dev/null || { echo "Push failed"; return 1; }
|
|
|
|
|
|
|
+ # Commit with message and push
|
|
|
|
|
+ if git commit -m "$commit_msg" --no-gpg-sign; then
|
|
|
|
|
+ if git push &>/dev/null; then
|
|
|
|
|
+ echo "Committed and pushed successfully"
|
|
|
|
|
+ else
|
|
|
|
|
+ echo "Warning: Commit successful but push failed" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+ else
|
|
|
|
|
+ echo "Commit failed" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-# Git branch cleanup helper
|
|
|
|
|
|
|
+# Clean up merged git branches
|
|
|
function git-clean() {
|
|
function git-clean() {
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: git-clean"
|
|
|
|
|
+ echo "Safely delete merged branches (both local and optionally remote)"
|
|
|
|
|
+ echo "Protects main, master, and develop branches"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if ! git rev-parse --is-inside-work-tree &>/dev/null; then
|
|
|
|
|
+ echo "Error: Not in a git repository" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
local current_branch=$(git rev-parse --abbrev-ref HEAD)
|
|
local current_branch=$(git rev-parse --abbrev-ref HEAD)
|
|
|
local branches_to_delete=$(git branch --merged | grep -v "^\*" | grep -v "master" | grep -v "main" | grep -v "develop")
|
|
local branches_to_delete=$(git branch --merged | grep -v "^\*" | grep -v "master" | grep -v "main" | grep -v "develop")
|
|
|
|
|
|
|
@@ -100,117 +169,136 @@ function git-clean() {
|
|
|
echo "$branches_to_delete" | xargs -I{} git push origin --delete {}
|
|
echo "$branches_to_delete" | xargs -I{} git push origin --delete {}
|
|
|
echo "Remote branches deleted"
|
|
echo "Remote branches deleted"
|
|
|
fi
|
|
fi
|
|
|
|
|
+ else
|
|
|
|
|
+ echo "Operation cancelled"
|
|
|
fi
|
|
fi
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function sm { /opt/sublime_merge/sublime_merge $1; }
|
|
|
|
|
|
|
+# Open Sublime Merge
|
|
|
|
|
+function sm {
|
|
|
|
|
+ if [[ ! -f /opt/sublime_merge/sublime_merge ]]; then
|
|
|
|
|
+ echo "Error: Sublime Merge not found at /opt/sublime_merge/sublime_merge" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+ /opt/sublime_merge/sublime_merge "$@"
|
|
|
|
|
+}
|
|
|
|
|
|
|
|
|
|
+# Quick access to Neovim config
|
|
|
function vimrc {
|
|
function vimrc {
|
|
|
- cd $XDG_CONFIG_HOME/nvim
|
|
|
|
|
|
|
+ if [[ -z "$XDG_CONFIG_HOME" ]]; then
|
|
|
|
|
+ echo "Error: XDG_CONFIG_HOME not set" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ local original_dir=$(pwd)
|
|
|
|
|
+ cd "$XDG_CONFIG_HOME/nvim" || {
|
|
|
|
|
+ echo "Error: Cannot access $XDG_CONFIG_HOME/nvim" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ }
|
|
|
nvim
|
|
nvim
|
|
|
- cd - >/dev/null
|
|
|
|
|
|
|
+ cd "$original_dir"
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Quick access to Zsh config
|
|
|
function zshrc {
|
|
function zshrc {
|
|
|
- cd $XDG_CONFIG_HOME/zsh
|
|
|
|
|
|
|
+ if [[ -z "$XDG_CONFIG_HOME" ]]; then
|
|
|
|
|
+ echo "Error: XDG_CONFIG_HOME not set" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ local original_dir=$(pwd)
|
|
|
|
|
+ cd "$XDG_CONFIG_HOME/zsh" || {
|
|
|
|
|
+ echo "Error: Cannot access $XDG_CONFIG_HOME/zsh" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ }
|
|
|
nvim
|
|
nvim
|
|
|
- cd - >/dev/null
|
|
|
|
|
|
|
+ cd "$original_dir"
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-# FILE SHARING AND NETWORKING
|
|
|
|
|
-function upload_file() {
|
|
|
|
|
- local usage="Usage: $0 [-o] <file>"
|
|
|
|
|
- local one_time=true
|
|
|
|
|
-
|
|
|
|
|
- # Parse options
|
|
|
|
|
- while getopts ":o" opt; do
|
|
|
|
|
- case ${opt} in
|
|
|
|
|
- o ) one_time=false ;;
|
|
|
|
|
- \? )
|
|
|
|
|
- echo "Invalid option: -$OPTARG" >&2
|
|
|
|
|
- echo $usage
|
|
|
|
|
- return 1 ;;
|
|
|
|
|
- esac
|
|
|
|
|
- done
|
|
|
|
|
- shift $((OPTIND -1))
|
|
|
|
|
-
|
|
|
|
|
- # Check file argument
|
|
|
|
|
|
|
+# Expose local port through SSH tunnel
|
|
|
|
|
+function expose() {
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: expose <port>"
|
|
|
|
|
+ echo "Create SSH tunnel to expose local port through remote server"
|
|
|
|
|
+ echo "Example: expose 3000 # Exposes localhost:3000"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
if [[ -z "$1" ]]; then
|
|
if [[ -z "$1" ]]; then
|
|
|
- echo $usage
|
|
|
|
|
|
|
+ echo "Error: Port number required" >&2
|
|
|
|
|
+ echo "Usage: expose <port>" >&2
|
|
|
return 1
|
|
return 1
|
|
|
fi
|
|
fi
|
|
|
- if [[ ! -f "$1" ]]; then
|
|
|
|
|
- echo "Error: File not found: $1"
|
|
|
|
|
|
|
+
|
|
|
|
|
+ # Validate port number
|
|
|
|
|
+ if ! [[ "$1" =~ ^[0-9]+$ ]] || [[ "$1" -lt 1 ]] || [[ "$1" -gt 65535 ]]; then
|
|
|
|
|
+ echo "Error: Invalid port number. Must be between 1-65535" >&2
|
|
|
return 1
|
|
return 1
|
|
|
fi
|
|
fi
|
|
|
-
|
|
|
|
|
- local url="https://drop.mz.uy"
|
|
|
|
|
- echo "Uploading $1 to $url... (one-time: ${one_time})"
|
|
|
|
|
-
|
|
|
|
|
- # Prepare upload options
|
|
|
|
|
- local form_data=("-F" "file=@$1")
|
|
|
|
|
- if $one_time; then
|
|
|
|
|
- form_data+=("-F" "one_time=")
|
|
|
|
|
- fi
|
|
|
|
|
-
|
|
|
|
|
- # Try up to 3 times with a short delay between attempts
|
|
|
|
|
- local max_attempts=3
|
|
|
|
|
- local attempt=1
|
|
|
|
|
- local success=false
|
|
|
|
|
-
|
|
|
|
|
- while (( attempt <= max_attempts )) && ! $success; do
|
|
|
|
|
- if (( attempt > 1 )); then
|
|
|
|
|
- echo "Retry attempt $attempt of $max_attempts..."
|
|
|
|
|
- sleep 1
|
|
|
|
|
- fi
|
|
|
|
|
-
|
|
|
|
|
- local full_response=$(curl -i "${form_data[@]}" "$url" 2>/dev/null)
|
|
|
|
|
- local curl_status=$?
|
|
|
|
|
-
|
|
|
|
|
- if [[ $curl_status -eq 0 ]]; then
|
|
|
|
|
- local url_response=$(echo "$full_response" | tail -n 1)
|
|
|
|
|
- local token=$(echo "$full_response" | grep -i "X-Token:" | awk '{print $2}' | tr -d '\r')
|
|
|
|
|
-
|
|
|
|
|
- if [[ -n "$url_response" ]]; then
|
|
|
|
|
- echo -n "$url_response" | wl-copy
|
|
|
|
|
- echo "✓ Uploaded: $url_response (copied to clipboard)"
|
|
|
|
|
-
|
|
|
|
|
- if [[ -n "$token" ]]; then
|
|
|
|
|
- echo "Management token: $token"
|
|
|
|
|
- fi
|
|
|
|
|
-
|
|
|
|
|
- success=true
|
|
|
|
|
- break
|
|
|
|
|
- fi
|
|
|
|
|
|
|
+
|
|
|
|
|
+ # Check if port is already in use
|
|
|
|
|
+ if lsof -i ":$1" >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Warning: Port $1 is already in use" >&2
|
|
|
|
|
+ echo "Current processes using port $1:"
|
|
|
|
|
+ lsof -i ":$1"
|
|
|
|
|
+ echo -n "Continue anyway? [y/N] "
|
|
|
|
|
+ read confirm
|
|
|
|
|
+ if [[ ! "$confirm" =~ ^[Yy]$ ]]; then
|
|
|
|
|
+ echo "Operation cancelled"
|
|
|
|
|
+ return 1
|
|
|
fi
|
|
fi
|
|
|
-
|
|
|
|
|
- (( attempt++ ))
|
|
|
|
|
- done
|
|
|
|
|
-
|
|
|
|
|
- if ! $success; then
|
|
|
|
|
- echo "× Failed to upload file after $max_attempts attempts"
|
|
|
|
|
- return 1
|
|
|
|
|
fi
|
|
fi
|
|
|
|
|
+
|
|
|
|
|
+ echo "Creating SSH tunnel for port $1..."
|
|
|
|
|
+ ssh marianozunino@srv.us -R 1:localhost:"$1"
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-function expose() {
|
|
|
|
|
- if [ -z "$1" ]; then
|
|
|
|
|
- echo "Usage: expose <port>"
|
|
|
|
|
|
|
+# Find process using a specific port
|
|
|
|
|
+function ppid {
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: ppid <port>"
|
|
|
|
|
+ echo "Find processes using the specified port"
|
|
|
|
|
+ echo "Alias: pport"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if [[ -z "$1" ]]; then
|
|
|
|
|
+ echo "Error: Port number required" >&2
|
|
|
|
|
+ echo "Usage: ppid <port>" >&2
|
|
|
return 1
|
|
return 1
|
|
|
fi
|
|
fi
|
|
|
- ssh marianozunino@srv.us -R 1:localhost:$1
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-function ppid {
|
|
|
|
|
- lsof -i :$1
|
|
|
|
|
|
|
+
|
|
|
|
|
+ # Validate port number
|
|
|
|
|
+ if ! [[ "$1" =~ ^[0-9]+$ ]] || [[ "$1" -lt 1 ]] || [[ "$1" -gt 65535 ]]; then
|
|
|
|
|
+ echo "Error: Invalid port number. Must be between 1-65535" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ lsof -i ":$1"
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Alias for ppid function
|
|
|
alias pport="ppid"
|
|
alias pport="ppid"
|
|
|
|
|
|
|
|
|
|
+# =============================================================================
|
|
|
# KUBERNETES AND DEVOPS
|
|
# KUBERNETES AND DEVOPS
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
+
|
|
|
|
|
+# Kubernetes port forwarding with kubefwd
|
|
|
function kf {
|
|
function kf {
|
|
|
- if [ -z "$1" ]; then
|
|
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
echo "Usage: kf <cluster> [service-name]"
|
|
echo "Usage: kf <cluster> [service-name]"
|
|
|
|
|
+ echo "Forward Kubernetes services using kubefwd"
|
|
|
|
|
+ echo "Example: kf prod my-service"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if [[ -z "$1" ]]; then
|
|
|
|
|
+ echo "Error: Cluster name required" >&2
|
|
|
|
|
+ echo "Usage: kf <cluster> [service-name]" >&2
|
|
|
return 1
|
|
return 1
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
@@ -218,14 +306,23 @@ function kf {
|
|
|
local cluster="oc-$1-eks-cluster"
|
|
local cluster="oc-$1-eks-cluster"
|
|
|
local svc_filter=""
|
|
local svc_filter=""
|
|
|
|
|
|
|
|
- if [ ! -z "$2" ]; then
|
|
|
|
|
|
|
+ if [[ -n "$2" ]]; then
|
|
|
svc_filter="-l app.kubernetes.io/instance=$2"
|
|
svc_filter="-l app.kubernetes.io/instance=$2"
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
|
- sudo -E kubefwd svc -n ${namespace} -x ${cluster} ${svc_filter}
|
|
|
|
|
|
|
+ if ! command -v kubefwd >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: kubefwd is not installed" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ echo "Starting kubefwd for cluster: $cluster"
|
|
|
|
|
+ sudo -E kubefwd svc -n "${namespace}" -x "${cluster}" ${svc_filter}
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# =============================================================================
|
|
|
# SYSTEM AND UTILITY FUNCTIONS
|
|
# SYSTEM AND UTILITY FUNCTIONS
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
+
|
|
|
# Lazy-load handler for heavy tools
|
|
# Lazy-load handler for heavy tools
|
|
|
function _lazy_load() {
|
|
function _lazy_load() {
|
|
|
local cmd="$1"
|
|
local cmd="$1"
|
|
@@ -241,102 +338,181 @@ function _lazy_load() {
|
|
|
# Example: lazy load kubectl completion
|
|
# Example: lazy load kubectl completion
|
|
|
_lazy_load kubectl "kubectl completion zsh"
|
|
_lazy_load kubectl "kubectl completion zsh"
|
|
|
|
|
|
|
|
|
|
+# Configure Wacom tablet for current session
|
|
|
function wacom {
|
|
function wacom {
|
|
|
- if [ "$XDG_SESSION_TYPE" = "wayland" ]; then
|
|
|
|
|
- systemctl --user enable opentabletdriver --now
|
|
|
|
|
- otd loadsettings ~/Sync/wacom/wacom.json
|
|
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: wacom"
|
|
|
|
|
+ echo "Configure Wacom tablet for current display session"
|
|
|
|
|
+ echo "Supports both Wayland and X11 sessions"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if [[ "$XDG_SESSION_TYPE" = "wayland" ]]; then
|
|
|
|
|
+ if ! command -v otd >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: opentabletdriver (otd) not found" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ systemctl --user enable opentabletdriver --now
|
|
|
|
|
+
|
|
|
|
|
+ local config_file="$HOME/Sync/System/Configs/wacom/wacom.json"
|
|
|
|
|
+ if [[ -f "$config_file" ]]; then
|
|
|
|
|
+ otd loadsettings "$config_file"
|
|
|
|
|
+ echo "Wacom configured for Wayland"
|
|
|
else
|
|
else
|
|
|
- xsetwacom --set "Wacom One by Wacom S Pen stylus" ResetArea
|
|
|
|
|
- xsetwacom --set "Wacom One by Wacom S Pen stylus" MapToOutput DisplayPort-0
|
|
|
|
|
- xsetwacom --set "Wacom One by Wacom S Pen stylus" Rotate half
|
|
|
|
|
-
|
|
|
|
|
- xsetwacom --set "Wacom One by Wacom S Pen eraser" ResetArea
|
|
|
|
|
- xsetwacom --set "Wacom One by Wacom S Pen eraser" MapToOutput DisplayPort-0
|
|
|
|
|
|
|
+ echo "Warning: Config file not found at $config_file" >&2
|
|
|
|
|
+ fi
|
|
|
|
|
+ else
|
|
|
|
|
+ if ! command -v xsetwacom >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: xsetwacom not found" >&2
|
|
|
|
|
+ return 1
|
|
|
fi
|
|
fi
|
|
|
|
|
+
|
|
|
|
|
+ xsetwacom --set "Wacom One by Wacom S Pen stylus" ResetArea
|
|
|
|
|
+ xsetwacom --set "Wacom One by Wacom S Pen stylus" MapToOutput DisplayPort-0
|
|
|
|
|
+ xsetwacom --set "Wacom One by Wacom S Pen stylus" Rotate half
|
|
|
|
|
+
|
|
|
|
|
+ xsetwacom --set "Wacom One by Wacom S Pen eraser" ResetArea
|
|
|
|
|
+ xsetwacom --set "Wacom One by Wacom S Pen eraser" MapToOutput DisplayPort-0
|
|
|
|
|
+
|
|
|
|
|
+ echo "Wacom configured for X11"
|
|
|
|
|
+ fi
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Enhanced cat with bat, context-aware display
|
|
|
function cat {
|
|
function cat {
|
|
|
- if [ -n "$SSH_TTY" ] || [ -n "$SSH_CLIENT" ] || [ -n "$SSH_CONNECTION" ]; then
|
|
|
|
|
- bat --plain --paging=never "$@"
|
|
|
|
|
- else
|
|
|
|
|
- bat "$@"
|
|
|
|
|
- fi
|
|
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: cat [file1] [file2] ..."
|
|
|
|
|
+ echo "Enhanced cat using bat with syntax highlighting"
|
|
|
|
|
+ echo "Automatically adjusts output for SSH sessions"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if ! command -v bat >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Warning: bat not found, falling back to system cat" >&2
|
|
|
|
|
+ command cat "$@"
|
|
|
|
|
+ return $?
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if [[ -n "$SSH_TTY" ]] || [[ -n "$SSH_CLIENT" ]] || [[ -n "$SSH_CONNECTION" ]]; then
|
|
|
|
|
+ bat --plain --paging=never "$@"
|
|
|
|
|
+ else
|
|
|
|
|
+ bat "$@"
|
|
|
|
|
+ fi
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Toggle display resolution and configuration
|
|
|
function toggle_resolution() {
|
|
function toggle_resolution() {
|
|
|
- local mirror_mode=false
|
|
|
|
|
-
|
|
|
|
|
- # Verificar flags
|
|
|
|
|
- while [[ $# -gt 0 ]]; do
|
|
|
|
|
- case $1 in
|
|
|
|
|
- -m|--mirror)
|
|
|
|
|
- mirror_mode=true
|
|
|
|
|
- shift
|
|
|
|
|
- ;;
|
|
|
|
|
- *)
|
|
|
|
|
- shift
|
|
|
|
|
- ;;
|
|
|
|
|
- esac
|
|
|
|
|
- done
|
|
|
|
|
-
|
|
|
|
|
- # Obtener estado actual del monitor interno
|
|
|
|
|
- current_state=$(swaymsg -t get_outputs | jq -r '.[] | select(.name == "eDP-1") | "\(.current_mode.width)x\(.current_mode.height):\(.scale)"')
|
|
|
|
|
-
|
|
|
|
|
- # Detectar monitores externos conectados
|
|
|
|
|
- external_monitor=""
|
|
|
|
|
- if swaymsg -t get_outputs | jq -r '.[].name' | grep -q "DP-2"; then
|
|
|
|
|
- external_monitor="DP-2"
|
|
|
|
|
- elif swaymsg -t get_outputs | jq -r '.[].name' | grep -q "HDMI-A-1"; then
|
|
|
|
|
- external_monitor="HDMI-A-1"
|
|
|
|
|
- fi
|
|
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: toggle_resolution [-m|--mirror]"
|
|
|
|
|
+ echo "Toggle between different display resolutions and modes"
|
|
|
|
|
+ echo "Options:"
|
|
|
|
|
+ echo " -m, --mirror Force mirror mode"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ local mirror_mode=false
|
|
|
|
|
+
|
|
|
|
|
+ # Parse flags
|
|
|
|
|
+ while [[ $# -gt 0 ]]; do
|
|
|
|
|
+ case $1 in
|
|
|
|
|
+ -m|--mirror)
|
|
|
|
|
+ mirror_mode=true
|
|
|
|
|
+ shift
|
|
|
|
|
+ ;;
|
|
|
|
|
+ *)
|
|
|
|
|
+ shift
|
|
|
|
|
+ ;;
|
|
|
|
|
+ esac
|
|
|
|
|
+ done
|
|
|
|
|
|
|
|
- if [[ "$mirror_mode" == true ]] || [[ -n "$external_monitor" ]]; then
|
|
|
|
|
- echo "Switching to mirror mode (1920x1080)..."
|
|
|
|
|
|
|
+ # Check if swaymsg is available
|
|
|
|
|
+ if ! command -v swaymsg >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: swaymsg not found. This function requires Sway window manager" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ # Check if jq is available
|
|
|
|
|
+ if ! command -v jq >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: jq not found. Required for JSON parsing" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
|
|
|
- # Configurar monitor interno a 1920x1080
|
|
|
|
|
- swaymsg output eDP-1 resolution 1920x1080@120Hz scale 1.0 pos 0 0
|
|
|
|
|
|
|
+ # Get current state of internal monitor
|
|
|
|
|
+ local current_state
|
|
|
|
|
+ current_state=$(swaymsg -t get_outputs | jq -r '.[] | select(.name == "eDP-1") | "\(.current_mode.width)x\(.current_mode.height):\(.scale)"')
|
|
|
|
|
|
|
|
- # Configurar monitor externo si está conectado
|
|
|
|
|
- if [[ -n "$external_monitor" ]]; then
|
|
|
|
|
- swaymsg output "$external_monitor" resolution 1920x1080@60Hz pos 0 0
|
|
|
|
|
- echo "Mirror mode enabled: eDP-1 + $external_monitor at 1920x1080"
|
|
|
|
|
- else
|
|
|
|
|
- echo "Monitor interno configurado a 1920x1080 (sin monitor externo detectado)"
|
|
|
|
|
- fi
|
|
|
|
|
|
|
+ # Detect connected external monitors
|
|
|
|
|
+ local external_monitor=""
|
|
|
|
|
+ if swaymsg -t get_outputs | jq -r '.[].name' | grep -q "DP-2"; then
|
|
|
|
|
+ external_monitor="DP-2"
|
|
|
|
|
+ elif swaymsg -t get_outputs | jq -r '.[].name' | grep -q "HDMI-A-1"; then
|
|
|
|
|
+ external_monitor="HDMI-A-1"
|
|
|
|
|
+ fi
|
|
|
|
|
|
|
|
- elif [[ "$current_state" == "2880x1920:2.0" ]]; then
|
|
|
|
|
- echo "Switching to 1920x1080 (16:9)..."
|
|
|
|
|
- swaymsg output eDP-1 resolution 1920x1080@120Hz scale 1.0
|
|
|
|
|
|
|
+ if [[ "$mirror_mode" == true ]] || [[ -n "$external_monitor" ]]; then
|
|
|
|
|
+ echo "Switching to mirror mode (1920x1080)..."
|
|
|
|
|
|
|
|
- # Deshabilitar mirroring si hay monitor externo
|
|
|
|
|
- if [[ -n "$external_monitor" ]]; then
|
|
|
|
|
- swaymsg output "$external_monitor" pos 1920 0
|
|
|
|
|
- echo "Extended mode: $external_monitor positioned to the right"
|
|
|
|
|
- fi
|
|
|
|
|
|
|
+ # Configure internal monitor to 1920x1080
|
|
|
|
|
+ swaymsg output eDP-1 resolution 1920x1080@120Hz scale 1.0 pos 0 0
|
|
|
|
|
|
|
|
|
|
+ # Configure external monitor if connected
|
|
|
|
|
+ if [[ -n "$external_monitor" ]]; then
|
|
|
|
|
+ swaymsg output "$external_monitor" resolution 1920x1080@60Hz pos 0 0
|
|
|
|
|
+ echo "Mirror mode enabled: eDP-1 + $external_monitor at 1920x1080"
|
|
|
else
|
|
else
|
|
|
- echo "Switching to 2880x1920 (3:2) native..."
|
|
|
|
|
- swaymsg output eDP-1 resolution 2880x1920@120Hz scale 2.0
|
|
|
|
|
-
|
|
|
|
|
- # Deshabilitar mirroring si hay monitor externo
|
|
|
|
|
- if [[ -n "$external_monitor" ]]; then
|
|
|
|
|
- swaymsg output "$external_monitor" pos 1440 0
|
|
|
|
|
- echo "Extended mode: $external_monitor positioned to the right"
|
|
|
|
|
- fi
|
|
|
|
|
|
|
+ echo "Internal monitor configured to 1920x1080 (no external monitor detected)"
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ elif [[ "$current_state" == "2880x1920:2.0" ]]; then
|
|
|
|
|
+ echo "Switching to 1920x1080 (16:9)..."
|
|
|
|
|
+ swaymsg output eDP-1 resolution 1920x1080@120Hz scale 1.0
|
|
|
|
|
+
|
|
|
|
|
+ # Disable mirroring if external monitor is present
|
|
|
|
|
+ if [[ -n "$external_monitor" ]]; then
|
|
|
|
|
+ swaymsg output "$external_monitor" pos 1920 0
|
|
|
|
|
+ echo "Extended mode: $external_monitor positioned to the right"
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ else
|
|
|
|
|
+ echo "Switching to 2880x1920 (3:2) native..."
|
|
|
|
|
+ swaymsg output eDP-1 resolution 2880x1920@120Hz scale 2.0
|
|
|
|
|
+
|
|
|
|
|
+ # Disable mirroring if external monitor is present
|
|
|
|
|
+ if [[ -n "$external_monitor" ]]; then
|
|
|
|
|
+ swaymsg output "$external_monitor" pos 1440 0
|
|
|
|
|
+ echo "Extended mode: $external_monitor positioned to the right"
|
|
|
fi
|
|
fi
|
|
|
|
|
+ fi
|
|
|
|
|
|
|
|
- # Mostrar estado final
|
|
|
|
|
- echo "Current configuration:"
|
|
|
|
|
- swaymsg -t get_outputs | jq -r '.[] | select(.active == true) | " \(.name): \(.current_mode.width)x\(.current_mode.height)@\(.current_mode.refresh/1000)Hz scale:\(.scale) pos:(\(.rect.x),\(.rect.y))"'
|
|
|
|
|
|
|
+ # Show final state
|
|
|
|
|
+ echo "Current configuration:"
|
|
|
|
|
+ swaymsg -t get_outputs | jq -r '.[] | select(.active == true) | " \(.name): \(.current_mode.width)x\(.current_mode.height)@\(.current_mode.refresh/1000)Hz scale:\(.scale) pos:(\(.rect.x),\(.rect.y))"'
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Launch Code::Blocks with high contrast theme
|
|
|
function cb {
|
|
function cb {
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: cb [codeblocks-args]"
|
|
|
|
|
+ echo "Launch Code::Blocks with high contrast theme"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if [[ ! -f /usr/bin/codeblocks ]]; then
|
|
|
|
|
+ echo "Error: Code::Blocks not found at /usr/bin/codeblocks" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
export GTK_THEME=HighContrast
|
|
export GTK_THEME=HighContrast
|
|
|
export GDK_THEME=HighContrast
|
|
export GDK_THEME=HighContrast
|
|
|
export QT_STYLE_OVERRIDE=HighContrast
|
|
export QT_STYLE_OVERRIDE=HighContrast
|
|
|
export XDG_CURRENT_DESKTOP=GNOME
|
|
export XDG_CURRENT_DESKTOP=GNOME
|
|
|
|
|
|
|
|
- # Reiniciar configuración GTK
|
|
|
|
|
|
|
+ # Reset GTK configuration
|
|
|
unset GTK2_RC_FILES
|
|
unset GTK2_RC_FILES
|
|
|
unset GTK_RC_FILES
|
|
unset GTK_RC_FILES
|
|
|
|
|
|
|
@@ -344,9 +520,26 @@ function cb {
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
+# Create a new git repository on remote server
|
|
|
function zrepo() {
|
|
function zrepo() {
|
|
|
- if [ -z "$1" ]; then
|
|
|
|
|
- echo "Usage: zrepo <repo>"
|
|
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: zrepo <repo-name>"
|
|
|
|
|
+ echo "Create a new bare git repository on remote server"
|
|
|
|
|
+ echo "Example: zrepo my-project"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if [[ -z "$1" ]]; then
|
|
|
|
|
+ echo "Error: Repository name required" >&2
|
|
|
|
|
+ echo "Usage: zrepo <repo-name>" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ # Validate repository name (basic check)
|
|
|
|
|
+ if [[ ! "$1" =~ ^[a-zA-Z0-9_-]+$ ]]; then
|
|
|
|
|
+ echo "Error: Repository name contains invalid characters" >&2
|
|
|
|
|
+ echo "Use only letters, numbers, hyphens, and underscores" >&2
|
|
|
return 1
|
|
return 1
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
@@ -354,40 +547,65 @@ function zrepo() {
|
|
|
local SERVER="git@zvps"
|
|
local SERVER="git@zvps"
|
|
|
local PATH_ON_SERVER="/var/git/$REPO.git"
|
|
local PATH_ON_SERVER="/var/git/$REPO.git"
|
|
|
|
|
|
|
|
- ssh $SERVER "
|
|
|
|
|
|
|
+ echo "Creating repository '$REPO' on $SERVER..."
|
|
|
|
|
+
|
|
|
|
|
+ ssh "$SERVER" "
|
|
|
if [ -d $PATH_ON_SERVER ]; then
|
|
if [ -d $PATH_ON_SERVER ]; then
|
|
|
- echo 'Error: repo already exists'
|
|
|
|
|
|
|
+ echo 'Error: Repository '$REPO' already exists'
|
|
|
exit 1
|
|
exit 1
|
|
|
fi
|
|
fi
|
|
|
mkdir -p $PATH_ON_SERVER &&
|
|
mkdir -p $PATH_ON_SERVER &&
|
|
|
git init --bare $PATH_ON_SERVER &&
|
|
git init --bare $PATH_ON_SERVER &&
|
|
|
chown -R git:git $PATH_ON_SERVER &&
|
|
chown -R git:git $PATH_ON_SERVER &&
|
|
|
chmod -R 755 $PATH_ON_SERVER
|
|
chmod -R 755 $PATH_ON_SERVER
|
|
|
- " || return 1
|
|
|
|
|
|
|
+ " || {
|
|
|
|
|
+ echo "Failed to create repository" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ }
|
|
|
|
|
|
|
|
- echo "Repo created on $SERVER:$PATH_ON_SERVER"
|
|
|
|
|
|
|
+ echo "Repository created on $SERVER:$PATH_ON_SERVER"
|
|
|
|
|
|
|
|
if git rev-parse --is-inside-work-tree >/dev/null 2>&1; then
|
|
if git rev-parse --is-inside-work-tree >/dev/null 2>&1; then
|
|
|
git remote add origin "$SERVER:$PATH_ON_SERVER"
|
|
git remote add origin "$SERVER:$PATH_ON_SERVER"
|
|
|
- echo "Remote 'origin' added to your local repo."
|
|
|
|
|
|
|
+ echo "Remote 'origin' added to your local repository"
|
|
|
else
|
|
else
|
|
|
- echo "Run 'git clone $SERVER:$PATH_ON_SERVER' to clone the repo."
|
|
|
|
|
|
|
+ echo "To clone this repository, run:"
|
|
|
|
|
+ echo " git clone $SERVER:$PATH_ON_SERVER"
|
|
|
fi
|
|
fi
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
+# Check if a command exists
|
|
|
function _has {
|
|
function _has {
|
|
|
- return $( whence $1 >/dev/null )
|
|
|
|
|
|
|
+ if [[ $# -eq 0 ]]; then
|
|
|
|
|
+ echo "Usage: _has <command>" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ whence "$1" >/dev/null 2>&1
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
-# History-based directory navigation
|
|
|
|
|
|
|
+# History-based directory navigation with fzf
|
|
|
function cdr {
|
|
function cdr {
|
|
|
|
|
+ # Show help if requested
|
|
|
|
|
+ if [[ "$1" == "-h" || "$1" == "--help" ]]; then
|
|
|
|
|
+ echo "Usage: cdr"
|
|
|
|
|
+ echo "Navigate to recently visited directories using fzf"
|
|
|
|
|
+ return 0
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
|
|
+ if ! command -v fzf >/dev/null 2>&1; then
|
|
|
|
|
+ echo "Error: fzf is not installed" >&2
|
|
|
|
|
+ return 1
|
|
|
|
|
+ fi
|
|
|
|
|
+
|
|
|
local dir
|
|
local dir
|
|
|
dir=$(dirs -pl | awk '!x[$0]++' | fzf --height 40% --reverse)
|
|
dir=$(dirs -pl | awk '!x[$0]++' | fzf --height 40% --reverse)
|
|
|
[[ -n "$dir" ]] && cd "$dir"
|
|
[[ -n "$dir" ]] && cd "$dir"
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+# Fix swaymsg when running inside tmux
|
|
|
if [[ -v TMUX ]]; then
|
|
if [[ -v TMUX ]]; then
|
|
|
function swaymsg {
|
|
function swaymsg {
|
|
|
export SWAYSOCK=$XDG_RUNTIME_DIR/sway-ipc.$UID.$(pgrep -x sway).sock
|
|
export SWAYSOCK=$XDG_RUNTIME_DIR/sway-ipc.$UID.$(pgrep -x sway).sock
|
|
@@ -395,24 +613,19 @@ if [[ -v TMUX ]]; then
|
|
|
}
|
|
}
|
|
|
fi
|
|
fi
|
|
|
|
|
|
|
|
-# COMPLETIONS
|
|
|
|
|
-for completion_file in ~/.local/share/zsh/*-autocomplete.zsh; do
|
|
|
|
|
- echo $completion_file
|
|
|
|
|
- if [ -f "$completion_file" ]; then
|
|
|
|
|
- source "$completion_file"
|
|
|
|
|
- fi
|
|
|
|
|
-done
|
|
|
|
|
|
|
|
|
|
-if command -v rop &> /dev/null; then eval "$(rop completion zsh)"; fi
|
|
|
|
|
-if command -v goq &> /dev/null; then eval "$(goq completion zsh)"; fi
|
|
|
|
|
-if command -v kubefwd &> /dev/null; then eval "$(kubefwd completion zsh)"; fi
|
|
|
|
|
-if command -v bombadil &> /dev/null; then eval "$(bombadil generate-completions zsh)"; fi
|
|
|
|
|
-if command -v eza &> /dev/null; then compdef eza=ls; fi
|
|
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
+# ALIASES
|
|
|
|
|
+# =============================================================================
|
|
|
|
|
|
|
|
|
|
+# Development aliases
|
|
|
alias dev='~/Dev/marianozunino/dev/dev'
|
|
alias dev='~/Dev/marianozunino/dev/dev'
|
|
|
alias p='_package_manager'
|
|
alias p='_package_manager'
|
|
|
alias fo='fopen'
|
|
alias fo='fopen'
|
|
|
-alias drop='upload_file'
|
|
|
|
|
-alias dump='upload_file'
|
|
|
|
|
-alias pport=ppid
|
|
|
|
|
-alias unChonk="echo '🧹 Starting the great node_modules purge...' && find . -name 'node_modules' -type d -prune -exec sh -c 'echo \"💥 Deleting {}\" && rm -rf \"{}\"' \;"
|
|
|
|
|
|
|
+alias pport='ppid'
|
|
|
|
|
+
|
|
|
|
|
+# Node.js cleanup alias
|
|
|
|
|
+alias unChonk="echo 'Starting the great node_modules purge...' && find . -name 'node_modules' -type d -prune -exec sh -c 'echo \"Deleting {}\" && rm -rf \"{}\"' \;"
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+
|