pass: Switch pass-pick tool to external repository
Added pass-pick external repository. Factored out the program from this repository into its own development repository from which it is pulled as a submodule for these dotfiles.
This commit is contained in:
parent
a322799f39
commit
941760fd13
4 changed files with 9 additions and 392 deletions
3
.gitmodules
vendored
3
.gitmodules
vendored
|
@ -1,3 +1,6 @@
|
||||||
[submodule "polybar/.local/share/pomo-app"]
|
[submodule "polybar/.local/share/pomo-app"]
|
||||||
path = polybar/.local/share/pomo-app
|
path = polybar/.local/share/pomo-app
|
||||||
url = https://github.com/jsspencer/pomo.git
|
url = https://github.com/jsspencer/pomo.git
|
||||||
|
[submodule "pass/.local/share/pass-pick"]
|
||||||
|
path = pass/.local/share/pass-pick
|
||||||
|
url = https://git.martyoeh.me/Marty/pass-pick.git
|
||||||
|
|
|
@ -7,14 +7,14 @@ The current dotfiles are geared toward wayland for which the setup looks similar
|
||||||
|
|
||||||
* [x] vim configuration for simple programming tasks (especially go/typescript/python/bash) and prose
|
* [x] vim configuration for simple programming tasks (especially go/typescript/python/bash) and prose
|
||||||
* [x] academic workflow tools, to allow quick citation, pdf compilation, and preview
|
* [x] academic workflow tools, to allow quick citation, pdf compilation, and preview
|
||||||
* [x] simple, efficient polybar with package update notification, and spotify (mpris) integration
|
* [x] simple, efficient waybar with package update notification, and spotify (mpris) integration
|
||||||
* [x] tmux session management through `tm` and `tl` tools
|
* [x] tmux session management through `tm` and `tl` tools
|
||||||
* [x] tmux fuzzy-searching of terminal sessions to switch to with hot-key (`<C-A><C-s>`) in addition to normal session switching
|
* [x] tmux fuzzy-searching of terminal sessions to switch to with hot-key (`<C-A><C-s>`) in addition to normal session switching
|
||||||
* [x] system-wide color management (terminals, vim, qutebrowser, polybar, xresources) through `styler` command using [base16](http://chriskempson.com/projects/base16/) themes
|
* [x] system-wide color management (terminals, vim, qutebrowser, polybar, xresources) through `styler` command using [base16](http://chriskempson.com/projects/base16/) themes
|
||||||
* [x] quick theme switching by activating `styler` and fuzzy-searching themes with hot-key (`<Super>+F8`)
|
* [x] quick theme switching by activating `styler` and fuzzy-searching themes with hot-key (default `<Super>=<Shift>+S`)
|
||||||
* [x] many vim color-schemes with quick light/dark switching (`F8`) and individual theme switch (`<Space>+F8`)
|
* [x] many vim color-schemes with quick light/dark switching (`F8`) and individual theme switch (`<Space>+F8`)
|
||||||
* [x] quick directory jumping using z, with fzf integration
|
* [x] quick directory jumping using `z`, with `fzf` integration
|
||||||
* [x] fzf integrations for bibtex citation, vim buffer management, most recently used switching, shell command history, and more
|
* [x] `fzf`-like integrations for bibtex citation, vim buffer management, most recently used switching, shell command history, and more
|
||||||
|
|
||||||
[![Styler recoloring demo](https://gitlab.com/marty-oehme/dotfiles/-/wikis/uploads/bde87deda694590a2e08e21552e11309/styler.webp)](https://gitlab.com/marty-oehme/dotfiles/-/wikis/uploads/90894e53eff378db4d7f9f49e7a69fab/styler.mp4)
|
[![Styler recoloring demo](https://gitlab.com/marty-oehme/dotfiles/-/wikis/uploads/bde87deda694590a2e08e21552e11309/styler.webp)](https://gitlab.com/marty-oehme/dotfiles/-/wikis/uploads/90894e53eff378db4d7f9f49e7a69fab/styler.mp4)
|
||||||
|
|
||||||
|
|
|
@ -1,388 +0,0 @@
|
||||||
#!/usr/bin/env bash
|
|
||||||
#
|
|
||||||
# Pass picker
|
|
||||||
#
|
|
||||||
# Use a dmenu-like list selector to display and autofill your pass passwords.
|
|
||||||
# Can work with rofi, bemenu and dmenu, or a custom picker given as an option.
|
|
||||||
# Invoke it with `pass-pick`. You can set options through environment variables
|
|
||||||
# or through a configuration file.
|
|
||||||
#
|
|
||||||
# Keys:
|
|
||||||
# By default shows the available keys on rofi, but not on bemenu/dmenu.
|
|
||||||
# ROFI mapped keys (main password list):
|
|
||||||
# return autofill username/password combination
|
|
||||||
# alt+return enter entry submenu
|
|
||||||
# alt+u autofill username
|
|
||||||
# alt+p autofill password
|
|
||||||
# alt+ctrl+u send username to clipboard
|
|
||||||
# alt+ctrl+p send password to clipboard
|
|
||||||
# ROFI mapped keys (individual entry):
|
|
||||||
# return autofill selected field
|
|
||||||
# alt+return send selected field to clipboard
|
|
||||||
# alt+s reveal hidden password field
|
|
||||||
# alt+backspace back to main password menu
|
|
||||||
# Those options also work on bemenu, but have different (and fixed) mappings.
|
|
||||||
# BEMENU mapped keys (main password list):
|
|
||||||
# return autofill username/password combination
|
|
||||||
# alt+2 send username to clipboard
|
|
||||||
# alt+3 send password to clipboard
|
|
||||||
# alt+4 autofill username
|
|
||||||
# alt+5 autofill password
|
|
||||||
# alt+6 enter entry submenu
|
|
||||||
# BEMENU mapped keys (individual entry):
|
|
||||||
# return autofill selected field
|
|
||||||
# alt+2 send selected field to clipboard
|
|
||||||
# alt+3 back to main password menu
|
|
||||||
# alt+4 reveal hidden password field
|
|
||||||
|
|
||||||
# Selector wrapper
|
|
||||||
# Prefers rofi if found, otherwise bemenu or dmenu if found, complains if no selector available.
|
|
||||||
# Passes along any options given to main script.
|
|
||||||
rofi_opts=("$@")
|
|
||||||
_picker() {
|
|
||||||
if [ -n "$PICKER" ]; then
|
|
||||||
"${PICKER[@]}"
|
|
||||||
elif command -v rofi 1>/dev/null 2>/dev/null; then
|
|
||||||
rofi -dmenu -no-auto-select -i "${rofi_opts[@]}" "$@" -p "entry"
|
|
||||||
elif command -v bemenu 1>/dev/null 2>/dev/null; then
|
|
||||||
bemenu -l 20 -i -p "entry >"
|
|
||||||
elif command -v dmenu 1>/dev/null 2>/dev/null; then
|
|
||||||
dmenu -i -p "entry >"
|
|
||||||
else
|
|
||||||
printf "%s: 📦 %s must be installed for %s function.\n" "critical" "rofi/dmenu" "this" >&2
|
|
||||||
notify-send "📦 rofi/dmenu" --urgency="critical" "must be installed for this function."
|
|
||||||
exit 1
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
# parse, see https://unix.stackexchange.com/a/331965/8541
|
|
||||||
_parse_config() {
|
|
||||||
(grep -e "^$2=" -m 1 "$1" 2>/dev/null || printf "var=__UNDEFINED__\n") | head -n1 | cut -d '=' -f 2-
|
|
||||||
}
|
|
||||||
|
|
||||||
# read config file
|
|
||||||
get_config() {
|
|
||||||
local locations=(
|
|
||||||
"$PP_CONFIGURATION_FILE"
|
|
||||||
"${xdg_config_home:-$HOME/.config}/pass-picker/pass-picker.conf"
|
|
||||||
"$HOME/.pass-picker.conf"
|
|
||||||
"/etc/pass-picker.conf"
|
|
||||||
)
|
|
||||||
|
|
||||||
# return the first config file with a valid path
|
|
||||||
for config in "${locations[@]}"; do
|
|
||||||
if [[ -n "$config" && -f "$config" ]]; then
|
|
||||||
# see if the config has been given a value
|
|
||||||
local val
|
|
||||||
val="$(_parse_config "$config" "$1")"
|
|
||||||
break
|
|
||||||
fi
|
|
||||||
done
|
|
||||||
|
|
||||||
# if there was a config file but no value
|
|
||||||
# or there was no config file at all
|
|
||||||
if [ "$val" = "__UNDEFINED__" ] || [ -z "$val" ]; then
|
|
||||||
val="$2"
|
|
||||||
fi
|
|
||||||
printf -- "%s" "$val"
|
|
||||||
}
|
|
||||||
|
|
||||||
set_defaults() {
|
|
||||||
# The location of the pass-picker config file
|
|
||||||
# PP_CONFIGURATION_FILE="~/.config/pass-picker/pass-picker.conf"
|
|
||||||
# set options, leaving already set environment variables intact
|
|
||||||
# try to read any settings from config files
|
|
||||||
PICKER="${PP_PICKER:-$(get_config PICKER)}"
|
|
||||||
|
|
||||||
KEY_AUTOFILL="${PP_KEY_AUTOFILL:-$(get_config KEY_AUTOFILL Return)}"
|
|
||||||
KEY_ENTRY_OPEN="${PP_KEY_ENTRY_OPEN:-$(get_config KEY_ENTRY_OPEN Alt+Return)}"
|
|
||||||
KEY_FILL_USER="${PP_KEY_FILL_USER:-$(get_config KEY_FILL_USER Alt+u)}"
|
|
||||||
KEY_CLIP_USER="${PP_KEY_CLIP_USER:-$(get_config KEY_CLIP_USER Ctrl+Alt+u)}"
|
|
||||||
KEY_FILL_PASS="${PP_KEY_FILL_PASS:-$(get_config KEY_FILL_PASS Alt+p)}"
|
|
||||||
KEY_CLIP_PASS="${PP_KEY_CLIP_PASS:-$(get_config KEY_CLIP_PASS Ctrl+Alt+p)}"
|
|
||||||
KEY_ENTRYMENU_FILL="${PP_KEY_ENTRYMENU_FILL:-$(get_config KEY_ENTRYMENU_FILL Return)}"
|
|
||||||
KEY_ENTRYMENU_CLIP="${PP_KEY_ENTRYMENU_CLIP:-$(get_config KEY_ENTRYMENU_CLIP Alt+Return)}"
|
|
||||||
KEY_ENTRYMENU_SHOWFIELD="${KEY_ENTRYMENU_SHOWFIELD:-$(get_config KEY_ENTRYMENU_SHOWFIELD Alt+s)}"
|
|
||||||
KEY_ENTRYMENU_QUIT="${PP_KEY_ENTRYMENU_QUIT:-$(get_config KEY_ENTRYMENU_QUIT Alt+BackSpace)}"
|
|
||||||
|
|
||||||
AUTOFILL_BACKEND="${PP_AUTOFILL_BACKEND:-$(get_config AUTOFILL_BACKEND wtype)}"
|
|
||||||
AUTOFILL_CHAIN="${PP_AUTOENTRY_CHAIN:-$(get_config AUTOFILL_CHAIN 'username :tab password')}"
|
|
||||||
AUTOFILL_DELAY="${PP_AUTOENTRY_DELAY:-$(get_config AUTOFILL_DELAY 30)}"
|
|
||||||
PASS_USERNAME_FIELD="${PP_PASS_USERNAME_FIELD:-$(get_config PASS_USERNAME_FIELD 'username user login')}"
|
|
||||||
|
|
||||||
PASS_COFFIN_OPEN_TIME="${PP_PASS_COFFIN_OPEN_TIME:-$(get_config PASS_COFFIN_OPEN_TIME 0)}"
|
|
||||||
PASS_COFFIN_LOCATION="${PP_PASS_COFFIN_LOCATION:-$(get_config PASS_COFFIN_LOCATION)}"
|
|
||||||
}
|
|
||||||
|
|
||||||
# exit on escape pressed
|
|
||||||
exit_check() {
|
|
||||||
[ "$1" -eq 1 ] && exit
|
|
||||||
}
|
|
||||||
|
|
||||||
# simply return a list of all passwords in pass store
|
|
||||||
# TODO only show website names (+ folder names), and account names for multiple accounts on one site
|
|
||||||
list_passwords() {
|
|
||||||
shopt -s nullglob globstar
|
|
||||||
prefix=${PASSWORD_STORE_DIR:-~/.password-store}
|
|
||||||
password_files=("$prefix"/**/*.gpg)
|
|
||||||
password_files=("${password_files[@]#"$prefix"/}")
|
|
||||||
password_files=("${password_files[@]%.gpg}")
|
|
||||||
|
|
||||||
printf '%s\n' "${password_files[@]}"
|
|
||||||
}
|
|
||||||
|
|
||||||
# return password for argument passed
|
|
||||||
show_password() {
|
|
||||||
pass show "$1" | head -n1
|
|
||||||
}
|
|
||||||
|
|
||||||
# send password to clipboard
|
|
||||||
clip_password() {
|
|
||||||
pass show -c "$1"
|
|
||||||
}
|
|
||||||
|
|
||||||
# attempt to return the field specified
|
|
||||||
# attempts all (space separated) fields until the
|
|
||||||
# first one successfully returned
|
|
||||||
_p_get_field() {
|
|
||||||
local gp_entry="$1"
|
|
||||||
local gp_field="$2"
|
|
||||||
local clip="$3"
|
|
||||||
|
|
||||||
# return on first successfully returned key
|
|
||||||
for key in $gp_field; do
|
|
||||||
local value
|
|
||||||
value=$(_p_get_key_value "$gp_entry" "$key")
|
|
||||||
|
|
||||||
# found entry
|
|
||||||
if [ -n "$value" ]; then
|
|
||||||
|
|
||||||
if [ -n "$clip" ]; then
|
|
||||||
# copies to clipboard, removes any trailing newlines,
|
|
||||||
# and only keeps it in for 1 paste (1 loop to read in script, 1 to output)
|
|
||||||
if command -v wl-copy; then
|
|
||||||
echo "$value" | wl-copy -o && break
|
|
||||||
elif command -v xclip; then
|
|
||||||
echo "$value" | xclip -i -selection 'clipboard' -loops 2 -rmlastnl && break
|
|
||||||
elif command -v xsel; then
|
|
||||||
echo "$value" | xsel -b && break
|
|
||||||
else
|
|
||||||
notify-send "No clipboard utility" "Install wl-copy, xclip or xsel."
|
|
||||||
fi
|
|
||||||
else
|
|
||||||
echo "$value" && break
|
|
||||||
fi
|
|
||||||
|
|
||||||
fi
|
|
||||||
done
|
|
||||||
}
|
|
||||||
|
|
||||||
# returns the corresponding value for the key passed in
|
|
||||||
# arguments:
|
|
||||||
# $1: pass (file) entry to search through
|
|
||||||
# $2: string name of the containting key
|
|
||||||
_p_get_key_value() {
|
|
||||||
local value
|
|
||||||
value=$(list_fields "$1" | grep "$2")
|
|
||||||
|
|
||||||
# get everything after first colon, remove whitespace
|
|
||||||
echo "$value" | cut -d':' -f2- | tr -d '[:blank:]'
|
|
||||||
}
|
|
||||||
|
|
||||||
# return username for argument passed
|
|
||||||
show_username() {
|
|
||||||
_p_get_field "$1" "${PASS_USERNAME_FIELD}"
|
|
||||||
}
|
|
||||||
|
|
||||||
clip_username() {
|
|
||||||
_p_get_field "$1" "${PASS_USERNAME_FIELD}" "-c"
|
|
||||||
}
|
|
||||||
|
|
||||||
show_field() {
|
|
||||||
_p_get_field "$1" "$2"
|
|
||||||
}
|
|
||||||
|
|
||||||
clip_field() {
|
|
||||||
_p_get_field "$1" "$2" "-c"
|
|
||||||
}
|
|
||||||
|
|
||||||
list_fields() {
|
|
||||||
pass show "$1" | tail -n+2
|
|
||||||
}
|
|
||||||
|
|
||||||
# invoke the dotool to type inputs
|
|
||||||
_type() {
|
|
||||||
local tool="${AUTOFILL_BACKEND}"
|
|
||||||
local toolmode="$1"
|
|
||||||
local key="$2"
|
|
||||||
|
|
||||||
if [ "$tool" = "wtype" ]; then
|
|
||||||
if [ "$toolmode" = "type" ]; then
|
|
||||||
"$tool" -s "${AUTOFILL_DELAY}" -- "$key"
|
|
||||||
elif [ "$toolmode" = "key" ]; then
|
|
||||||
"$tool" -s "${AUTOFILL_DELAY}" -k "$key"
|
|
||||||
fi
|
|
||||||
elif [ "$tool" = "xdotool" ]; then
|
|
||||||
"$tool" "$toolmode" --delay "${AUTOFILL_DELAY}" "$key"
|
|
||||||
elif [ "$tool" = "ydotool" ]; then
|
|
||||||
"$tool" "$toolmode" --key-delay "${AUTOFILL_DELAY}" "$key"
|
|
||||||
else
|
|
||||||
"$tool" "$toolmode" "$key"
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
# automatically fill out fields
|
|
||||||
# transform special chain entries into valid dotool commands
|
|
||||||
autofill() {
|
|
||||||
local selected="${1}"
|
|
||||||
local autoentry_chain="${2}"
|
|
||||||
|
|
||||||
for part in $autoentry_chain; do
|
|
||||||
case "$part" in
|
|
||||||
":tab") _type key Tab ;;
|
|
||||||
":return") _type key Return ;;
|
|
||||||
":space") _type key space ;;
|
|
||||||
"username") _type type "$(show_username "$selected")" ;;
|
|
||||||
"password") _type type "$(show_password "$selected")" ;;
|
|
||||||
":direct") _type type "$selected" ;;
|
|
||||||
*) printf '%s' "$selected" ;;
|
|
||||||
esac
|
|
||||||
done
|
|
||||||
}
|
|
||||||
|
|
||||||
# opens a menu for the specified pass entry, containing its individual fields
|
|
||||||
entrymenu() {
|
|
||||||
local entry="$1"
|
|
||||||
local deobfuscate="$2"
|
|
||||||
local k_entrymenu_fill="${KEY_ENTRYMENU_FILL}"
|
|
||||||
local k_entrymenu_clip="${KEY_ENTRYMENU_CLIP}"
|
|
||||||
local k_entrymenu_showfield="${KEY_ENTRYMENU_SHOWFIELD}"
|
|
||||||
local k_entrymenu_quit="${KEY_ENTRYMENU_QUIT}"
|
|
||||||
|
|
||||||
local pass
|
|
||||||
if [ "$deobfuscate" = "true" ]; then
|
|
||||||
pass="$(show_password "$entry")"
|
|
||||||
else
|
|
||||||
pass="(hidden)"
|
|
||||||
fi
|
|
||||||
|
|
||||||
local field
|
|
||||||
field=$(
|
|
||||||
printf "password: %s\n%s" "$pass" "$(list_fields "$entry")" |
|
|
||||||
_picker \
|
|
||||||
-kb-accept-entry "" \
|
|
||||||
-kb-custom-1 "$k_entrymenu_fill" \
|
|
||||||
-kb-custom-2 "$k_entrymenu_clip" \
|
|
||||||
-kb-custom-3 "$k_entrymenu_quit" \
|
|
||||||
-kb-custom-4 "$k_entrymenu_showfield" \
|
|
||||||
-mesg " ᐊ $k_entrymenu_quit ᐊ | $k_entrymenu_fill: fill selection | $k_entrymenu_clip: clip selection | $k_entrymenu_showfield: reveal password"
|
|
||||||
)
|
|
||||||
exit_value=$?
|
|
||||||
exit_check "$exit_value"
|
|
||||||
|
|
||||||
# get field name
|
|
||||||
field=${field%%:*}
|
|
||||||
case "$exit_value" in
|
|
||||||
"0" | "10")
|
|
||||||
if [ "$field" = "password" ]; then
|
|
||||||
autofill "$entry" "password"
|
|
||||||
else
|
|
||||||
autofill "$(show_field "$entry" "$field")" ":direct"
|
|
||||||
fi
|
|
||||||
exit 0
|
|
||||||
;;
|
|
||||||
"11")
|
|
||||||
if [ "$field" = "password" ]; then
|
|
||||||
clip_password "$entry"
|
|
||||||
else
|
|
||||||
clip_field "$entry" "$field"
|
|
||||||
fi
|
|
||||||
exit 0
|
|
||||||
;;
|
|
||||||
"12")
|
|
||||||
main
|
|
||||||
;;
|
|
||||||
"13")
|
|
||||||
local toggle
|
|
||||||
if [ "$deobfuscate" = "true" ]; then
|
|
||||||
toggle=false
|
|
||||||
else
|
|
||||||
toggle=true
|
|
||||||
fi
|
|
||||||
entrymenu "$entry" "$toggle"
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
}
|
|
||||||
|
|
||||||
open_coffin() {
|
|
||||||
## there's a closed coffin in our directory
|
|
||||||
if [ -f "${PASS_COFFIN_LOCATION:-${PASSWORD_STORE_DIR:-~/.password-store}/.coffin/coffin.tar.gpg}" ]; then
|
|
||||||
if [ "$PASS_COFFIN_OPEN_TIME" -eq 0 ]; then
|
|
||||||
coffin_should_close_instantly=true
|
|
||||||
pass open -t 1h # we still set a maximum time limit just to hedge against failures
|
|
||||||
else
|
|
||||||
pass open -t "${PASS_COFFIN_OPEN_TIME:-3h}"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
|
|
||||||
# make sure we remember to close the coffin if the program terminates
|
|
||||||
close_coffin() {
|
|
||||||
if [ "$coffin_should_close_instantly" = true ]; then
|
|
||||||
pass close
|
|
||||||
fi
|
|
||||||
}
|
|
||||||
trap close_coffin SIGINT SIGTERM ERR EXIT
|
|
||||||
|
|
||||||
main() {
|
|
||||||
local autoentry_chain="${AUTOFILL_CHAIN}"
|
|
||||||
local k_autofill="${KEY_AUTOFILL}"
|
|
||||||
local k_fill_user="${KEY_FILL_USER}"
|
|
||||||
local k_clip_user="${KEY_CLIP_USER}"
|
|
||||||
local k_fill_pass="${KEY_FILL_PASS}"
|
|
||||||
local k_clip_pass="${KEY_CLIP_PASS}"
|
|
||||||
local k_submenu="${KEY_ENTRY_OPEN}"
|
|
||||||
|
|
||||||
open_coffin
|
|
||||||
|
|
||||||
entry="$(
|
|
||||||
list_passwords |
|
|
||||||
_picker -kb-accept-entry "" \
|
|
||||||
-kb-custom-1 "$k_autofill" \
|
|
||||||
-kb-custom-2 "$k_clip_user" \
|
|
||||||
-kb-custom-3 "$k_clip_pass" \
|
|
||||||
-kb-custom-4 "$k_fill_user" \
|
|
||||||
-kb-custom-5 "$k_fill_pass" \
|
|
||||||
-kb-custom-6 "$k_submenu" \
|
|
||||||
-mesg "| $k_autofill: fill credentials | $k_submenu: open entry | $k_fill_user: fill username | $k_fill_pass: fill password | $k_clip_user: clip username | $k_clip_pass: clip password |"
|
|
||||||
)"
|
|
||||||
exit_value=$?
|
|
||||||
|
|
||||||
echo "$entry"
|
|
||||||
exit_check "$exit_value"
|
|
||||||
case "$exit_value" in
|
|
||||||
"0" | "10")
|
|
||||||
autofill "$entry" "$autoentry_chain"
|
|
||||||
;;
|
|
||||||
"11")
|
|
||||||
clip_username "$entry"
|
|
||||||
;;
|
|
||||||
"12")
|
|
||||||
clip_password "$entry"
|
|
||||||
;;
|
|
||||||
"13")
|
|
||||||
autofill "$entry" "username"
|
|
||||||
;;
|
|
||||||
"14")
|
|
||||||
autofill "$entry" "password"
|
|
||||||
;;
|
|
||||||
"15")
|
|
||||||
entrymenu "$entry"
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
|
|
||||||
exit 0
|
|
||||||
}
|
|
||||||
|
|
||||||
set_defaults
|
|
||||||
main
|
|
1
pass/.local/bin/pass-pick
Symbolic link
1
pass/.local/bin/pass-pick
Symbolic link
|
@ -0,0 +1 @@
|
||||||
|
../share/pass-pick/pass-pick
|
1
pass/.local/share/pass-pick
Submodule
1
pass/.local/share/pass-pick
Submodule
|
@ -0,0 +1 @@
|
||||||
|
Subproject commit 846c6793538514a2ea8bbbddad5ff82fddf21a33
|
Loading…
Reference in a new issue