Last active
March 11, 2025 08:05
-
-
Save andelink/212607a0fa850a71329f4fadca2c8991 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env zsh | |
setopt errexit pipefail no_unset | |
############################################################################### | |
# A sloppy attempt at scripting https://github.com/maxgoedjen/secretive | |
############################################################################### | |
zmodload -Fa zsh/parameter p:commands | |
(( $+commands[bat] )) && local -a cat=(bat -pplhelp) || local -a cat=(cat) | |
(( $+commands[eza] )) && local -a ls=(eza -a1stime) || local -a ls=(ls -Galtr) | |
autoload colors; colors | |
local reverse=$'\e['${color[reverse]}m underline=$'\e['${color[underline]}m | |
function print-usage() { | |
${cat} <<EOH | |
${ZSH_ARGZERO:t} | |
Creates a new SSH key in the ${bold_color}Secure Enclave${reset_color} via Secretive. | |
USAGE: | |
${ZSH_ARGZERO:t} [OPTIONS] NAME | |
ARGS: | |
<NAME> | |
Command line arguments are joined with, and all non-alphanumeric characters | |
are replaced by, hyphens to form the key name. | |
Note that within Secretive, names are not unique. Uniqueness is enforced only | |
on the filesystem. It is an error to create a new key with a name that already | |
exists at ${underline}~/.ssh/\${name}.pub${reset_color}. | |
OPTIONS: | |
-h, --help | |
Display this help message. | |
-l, --list | |
List existing keys. | |
-k, --kickstart | |
(Re)start the Secretive SSH launch agent. | |
-c, --copy | |
Copy public key to clipboard, creating a new key if needed. | |
-s, --suffix | |
Append key type to name e.g. ${fg[blue]}github-personal${reset_color} → ${fg[blue]}github-personal-ecdsa${reset_color}. | |
EOH | |
} | |
function error() { | |
echo -e "${fg_bold[red]}ERROR${reset_color}" "$*" >&2 | |
exit 1 | |
} | |
# Require Secretive | |
osascript -e 'id of app "Secretive"' > /dev/null 2>&1 \ | |
|| error "Secretive not found, install with: brew install secretive" | |
# No arguments => stderr; -h/--help => stdout | |
(( ! $# )) && print-usage >&2 && exit 2 | |
(( ${(M)#@:#(-h|--help)} )) && print-usage && exit $? | |
(( ${(M)#@:#(-l|--list)} )) && ${ls} ~/.ssh/*.pub && exit $? | |
(( ${(M)#@:#(-k|--kickstart)} )) && launchctl kickstart -pk gui/501/com.maxgoedjen.Secretive.SecretAgent && exit $? | |
# Join args, replace non-alphanumerics w/hyphen, optionally append suffix | |
local name="${(*)${@:#(-?|--*)}//[^[:alnum:]]##/-}" | |
if (( ${(M)#@:#(-s|--suffix)} )) { | |
name="${(*)name/%-#(-ecdsa-#)#/-ecdsa}" | |
} | |
# Copy to clipboard if public key exists and --copy option supplied | |
if [[ -f ~/.ssh/${name}.pub && ${(M)@:#(-c|--copy)} ]] { | |
pbcopy < ~/.ssh/${name}.pub | |
echo -e "Copied ${bold_color}~/.ssh/${name}.pub${reset_color} to clipboard" | |
exit $? | |
} | |
# Abort if public key with this name already exists | |
if [[ -f ~/.ssh/${name}.pub ]] { | |
error "${reverse}~/.ssh/${name}.pub${reset_color} already exists" | |
} | |
# Cache existing keys, then create new key | |
local keysdir=~/Library/Containers/com.maxgoedjen.Secretive.SecretAgent/Data/PublicKeys | |
local -a oldkeys=(${keysdir}/*.pub(N^om)) newkeys=() | |
killall Secretive > /dev/null 2>&1 || true | |
osascript -s s - <<EOF | |
-- will restore focus later | |
tell application "System Events" to set frontmostProcess to first process where it is frontmost | |
-- surely very brittle code | |
tell application "Secretive" to activate | |
delay 1 | |
tell application "System Events" to tell process "Secretive" | |
click menu item "New Secret" of menu "File" of menu bar 1 | |
delay 0.5 | |
keystroke "${name}" | |
keystroke return | |
click menu item "Close" of menu "File" of menu bar 1 | |
end tell | |
delay 1 | |
-- return focus | |
tell application "System Events" to set frontmost of frontmostProcess to true | |
EOF | |
# Diff new vs old to identify newly created key, abort if results are unexpected | |
newkeys=(${keysdir}/*.pub(N^om)) | |
newkeys=(${newkeys:|oldkeys}) | |
if (( ${#newkeys} != 1 )) { | |
error "Expected 1 new key, but found ${#newkeys}" "\n ${^newkeys[@]}" # " | |
} | |
# Symlink new key to ~/.ssh | |
ln -vwis ${newkeys[1]} ~/.ssh/${name}.pub | |
# :tada: list all keys | |
echo -e "\n${underline}${bold_color}Keys${reset_color}" | |
${ls} ~/.ssh/*.pub | |
# Copy to clipboard if public key exists and --copy option supplied | |
if [[ -f ~/.ssh/${name}.pub && ${(M)@:#(-c|--copy)} ]] { | |
pbcopy < ~/.ssh/${name}.pub | |
echo -e "\nCopied ${bold_color}~/.ssh/${name}.pub${reset_color} to clipboard" | |
exit $? | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Shared here: maxgoedjen/secretive#499 (comment)
Usage:
create-secretive-key.mp4