diff --git a/init-certs.sh b/init-certs.sh index 03a7201..9ef9342 100644 --- a/init-certs.sh +++ b/init-certs.sh @@ -5,7 +5,11 @@ SCRIPT_DIR="$(CDPATH= cd -- "$(dirname -- "$0")" && pwd)" # Domains that need certificates. This list must cover every # /etc/letsencrypt/live// certificate referenced by nginx configs. -DOMAINS="ai.sggai.site dms.sggai.site lsbd2.loveteemo.com" +DOMAINS=" +ai.sggai.site +dms.sggai.site +lsbd2.loveteemo.com +" # Let's Encrypt registration email. CERT_EMAIL="243823965@qq.com" diff --git a/push-git.sh b/push-git.sh new file mode 100644 index 0000000..16ad5cf --- /dev/null +++ b/push-git.sh @@ -0,0 +1,142 @@ +#!/usr/bin/env sh +# +# 这个脚本用于一键提交并推送当前 Git 仓库。 +# +# 使用命令案例: +# sh push-git.sh "提交说明" +# chmod +x push-git.sh && ./push-git.sh "提交说明" +# ./push-git.sh -m "提交说明" --pull-rebase +# ./push-git.sh -m "提交说明" --dry-run +# +# 这个脚本做的事情: +# 1. 自动进入脚本所在 Git 仓库根目录,并检查当前分支和远程仓库。 +# 2. 如果存在本地改动,执行 git add -A 和 git commit -m "提交说明"。 +# 3. 按当前分支推送到远程仓库;首次推送会自动设置 upstream。 + +set -eu + +SCRIPT_DIR="$(CDPATH= cd -- "$(dirname -- "$0")" && pwd)" +REMOTE="origin" +MESSAGE="" +PULL_REBASE=0 +NO_VERIFY=0 +DRY_RUN=0 + +usage() { + cat <<'EOF' +Usage: + ./push-git.sh "commit message" + ./push-git.sh -m "commit message" [--pull-rebase] [--dry-run] + +Options: + -m, --message MESSAGE Commit message. + -r, --remote REMOTE Git remote name. Default: origin. + --pull-rebase Run git pull --rebase before pushing. + --no-verify Skip git commit hooks. + --dry-run Print commands without running them. + -h, --help Show this help. +EOF +} + +die() { + echo "Error: $*" >&2 + exit 1 +} + +run() { + echo "git $*" + if [ "$DRY_RUN" -eq 1 ]; then + return 0 + fi + + git "$@" +} + +while [ "$#" -gt 0 ]; do + case "$1" in + -m|--message) + [ "$#" -ge 2 ] || die "$1 requires a value" + MESSAGE="$2" + shift 2 + ;; + -r|--remote) + [ "$#" -ge 2 ] || die "$1 requires a value" + REMOTE="$2" + shift 2 + ;; + --pull-rebase) + PULL_REBASE=1 + shift + ;; + --no-verify) + NO_VERIFY=1 + shift + ;; + --dry-run) + DRY_RUN=1 + shift + ;; + -h|--help) + usage + exit 0 + ;; + --) + shift + break + ;; + -*) + die "unknown option: $1" + ;; + *) + if [ -z "$MESSAGE" ]; then + MESSAGE="$1" + else + MESSAGE="$MESSAGE $1" + fi + shift + ;; + esac +done + +REPO_ROOT="$(git -C "$SCRIPT_DIR" rev-parse --show-toplevel)" +cd "$REPO_ROOT" + +BRANCH="$(git rev-parse --abbrev-ref HEAD)" +[ -n "$BRANCH" ] && [ "$BRANCH" != "HEAD" ] || die "detached HEAD detected; checkout a branch before pushing" + +git remote get-url "$REMOTE" >/dev/null || die "remote not found: $REMOTE" + +STATUS="$(git status --porcelain)" +if [ -n "$STATUS" ]; then + if [ -z "$MESSAGE" ]; then + if [ "$DRY_RUN" -eq 1 ]; then + MESSAGE="" + else + printf "Commit message: " + IFS= read -r MESSAGE + fi + fi + + [ -n "$MESSAGE" ] || die "commit message is required when there are local changes" + + run add -A + + if [ "$NO_VERIFY" -eq 1 ]; then + run commit -m "$MESSAGE" --no-verify + else + run commit -m "$MESSAGE" + fi +else + echo "No local file changes to commit." +fi + +if [ "$PULL_REBASE" -eq 1 ]; then + run fetch "$REMOTE" + run pull --rebase "$REMOTE" "$BRANCH" +fi + +if git rev-parse --abbrev-ref --symbolic-full-name '@{u}' >/dev/null 2>&1; then + run push "$REMOTE" "$BRANCH" +else + run push -u "$REMOTE" "$BRANCH" +fi