mirror of
https://github.com/malarinv/pass-dotenv.git
synced 2026-03-08 02:12:34 +00:00
Add dotenv management extension and necessary files
- Introduced dotenv.bash for importing and exporting .env files to/from the password store. - Created Makefile for installation instructions. - Added LICENSE file for compliance with GNU General Public License v3.0. - Included README.md with detailed usage instructions and installation steps. - Established .env.file for environment variable configuration.
This commit is contained in:
175
extension/dotenv.bash
Executable file
175
extension/dotenv.bash
Executable file
@@ -0,0 +1,175 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
# pass extension for managing .env files
|
||||
|
||||
VERSION="0.1.0"
|
||||
PASS_DIR="$PASSWORD_STORE_DIR"
|
||||
|
||||
# Helper functions
|
||||
die() {
|
||||
echo "Error: $*" >&2
|
||||
exit 1
|
||||
}
|
||||
|
||||
yesno() {
|
||||
local answer
|
||||
read -r -p "$1 [y/N] " answer
|
||||
[[ "$answer" =~ [Yy] ]]
|
||||
}
|
||||
|
||||
# Import .env file into pass
|
||||
cmd_import() {
|
||||
local env_file="${1:-.env}"
|
||||
[[ -f "$env_file" ]] || die "Environment file not found: $env_file"
|
||||
|
||||
local project_name
|
||||
project_name=$(basename "$PWD")
|
||||
echo "Importing environment variables for project: $project_name"
|
||||
|
||||
while IFS= read -r line || [[ -n "$line" ]]; do
|
||||
# Trim leading whitespace from the whole line first
|
||||
line="${line#"${line%%[![:space:]]*}"}"
|
||||
|
||||
# Skip empty lines and comment-only lines
|
||||
if [[ -z "$line" ]] || [[ "$line" =~ ^# ]]; then
|
||||
continue
|
||||
fi
|
||||
|
||||
local comment=""
|
||||
local key_value_part="$line"
|
||||
|
||||
# Check for inline comment
|
||||
if [[ "$line" == *"#"* ]]; then
|
||||
key_value_part="${line%%#*}"
|
||||
comment="${line#*#}"
|
||||
fi
|
||||
|
||||
# Split on the first '='
|
||||
local key="${key_value_part%%=*}"
|
||||
local value="${key_value_part#*=}"
|
||||
|
||||
# Trim whitespace from key and value
|
||||
key="${key#"${key%%[![:space:]]*}"}"
|
||||
key="${key%"${key##*[![:space:]]}"}"
|
||||
value="${value#"${value%%[![:space:]]*}"}"
|
||||
value="${value%"${value##*[![:space:]]}"}"
|
||||
|
||||
# Check for *file* tag in comment
|
||||
if [[ "$comment" == *"*file*"* ]]; then
|
||||
# The value is a file path. Let's remove quotes around it if any.
|
||||
if [[ "$value" =~ ^'(.*)'$ ]]; then
|
||||
value="${BASH_REMATCH[1]}"
|
||||
elif [[ "$value" =~ ^"(.*)"$ ]]; then
|
||||
value="${BASH_REMATCH[1]}"
|
||||
fi
|
||||
|
||||
local file_path="$value"
|
||||
if [[ ! -f "$file_path" ]]; then
|
||||
local env_dir
|
||||
env_dir=$(dirname "$env_file")
|
||||
if [[ -f "$env_dir/$file_path" ]]; then
|
||||
file_path="$env_dir/$file_path"
|
||||
else
|
||||
echo "Warning: File not found for $key: $value. Skipping." >&2
|
||||
continue
|
||||
fi
|
||||
fi
|
||||
echo "Reading value for $key from file: $file_path"
|
||||
local abs_file_path
|
||||
abs_file_path=$(realpath "$file_path")
|
||||
local file_content
|
||||
file_content=$(<"$file_path")
|
||||
value="# dotenv-file-path: $abs_file_path
|
||||
$file_content"
|
||||
else
|
||||
# It's a regular value, remove quotes if they are there.
|
||||
if [[ "$value" =~ ^'(.*)'$ ]]; then
|
||||
value="${BASH_REMATCH[1]}"
|
||||
elif [[ "$value" =~ ^"(.*)"$ ]]; then
|
||||
value="${BASH_REMATCH[1]}"
|
||||
fi
|
||||
fi
|
||||
|
||||
local store_path="dotenv/$project_name/$key"
|
||||
echo "Importing $key to $store_path"
|
||||
printf "%s" "$value" | pass insert --multiline "$store_path" >/dev/null || die "Failed to insert $key"
|
||||
done < "$env_file"
|
||||
|
||||
echo "Import complete."
|
||||
}
|
||||
|
||||
|
||||
# Export .env file from pass
|
||||
cmd_export() {
|
||||
local project_name="${1:-$(basename "$PWD")}"
|
||||
local env_file=".env"
|
||||
|
||||
echo "Exporting environment variables for project: $project_name"
|
||||
|
||||
local project_path="dotenv/$project_name"
|
||||
pass ls "$project_path" >/dev/null 2>&1 || die "No environment variables found for project: $project_name"
|
||||
|
||||
if [[ -f "$env_file" ]] && ! yesno "Overwrite existing $env_file?"; then
|
||||
die "Export aborted."
|
||||
fi
|
||||
|
||||
# Clear the file
|
||||
> "$env_file"
|
||||
|
||||
pass ls "$project_path" | while read -r entry; do
|
||||
local key
|
||||
key=$(basename "$entry")
|
||||
local full_content
|
||||
full_content=$(pass show "$project_path/$key")
|
||||
|
||||
if [[ "$full_content" =~ ^#\ dotenv-file-path:\ (.*) ]]; then
|
||||
local original_path="${BASH_REMATCH[1]}"
|
||||
# Get content after the first line (the header)
|
||||
local file_content
|
||||
file_content=$(echo "$full_content" | tail -n +2)
|
||||
|
||||
local new_filename
|
||||
new_filename=$(basename "$original_path")
|
||||
local new_filepath="./$new_filename"
|
||||
|
||||
echo "Exporting $key to file: $new_filepath"
|
||||
# Use printf to avoid issues with content starting with -
|
||||
printf "%s" "$file_content" > "$new_filename"
|
||||
|
||||
echo "$key=$new_filepath # *file*" >> "$env_file"
|
||||
else
|
||||
echo "Exporting $key"
|
||||
echo "$key=$full_content" >> "$env_file"
|
||||
fi
|
||||
done
|
||||
|
||||
echo "Export complete. See $env_file"
|
||||
}
|
||||
|
||||
# Show help
|
||||
cmd_help() {
|
||||
cat <<-_EOF
|
||||
Usage: pass dotenv import|export [project_name]
|
||||
|
||||
Commands:
|
||||
import - Import a .env file into the password store.
|
||||
export - Export a .env file from the password store.
|
||||
_EOF
|
||||
}
|
||||
|
||||
|
||||
# Main command handler
|
||||
case "$1" in
|
||||
import)
|
||||
shift
|
||||
cmd_import "$@"
|
||||
;;
|
||||
export)
|
||||
shift
|
||||
cmd_export "$@"
|
||||
;;
|
||||
-h|--help|help)
|
||||
cmd_help
|
||||
;;
|
||||
*) die 'Usage: pass dotenv import|export [project_name]' ;;
|
||||
esac
|
||||
Reference in New Issue
Block a user