#!/bin/sh # SPDX-License-Identifier: MIT set -eu export TZ=UTC LC_ALL=C export GIT_CONFIG_NOSYSTEM=1 GIT_CONFIG_GLOBAL=/dev/null export GIT_AUTHOR_NAME='Example Author' export GIT_AUTHOR_EMAIL='author@example.invalid' export GIT_COMMITTER_NAME='Example Author' export GIT_COMMITTER_EMAIL='author@example.invalid' export GIT_AUTHOR_DATE='2026-10-25T12:00:00Z' export GIT_COMMITTER_DATE='2026-10-25T12:00:00Z' test "$(git --version)" = 'git version 2.56.0' mkdir stash-example cd stash-example new_case() { mkdir "$1" cd "$1" git -c init.templateDir= init -q -b main printf 'base\n' > note.txt printf 'original\n' > other.txt git add note.txt other.txt git commit -qm 'Base' } new_case apply printf 'saved change\n' > note.txt git stash push -qm 'Saved change' git stash apply -q test "$(cat note.txt)" = 'saved change' test "$(git stash list | wc -l | tr -d ' ')" = 1 printf 'apply: change restored; one stash remains\n' cd .. new_case pop printf 'saved change\n' > note.txt git stash push -qm 'Saved change' git stash pop -q test "$(cat note.txt)" = 'saved change' test -z "$(git stash list)" printf 'pop: change restored; no stash remains\n' cd .. new_case conflict printf 'saved change\n' > note.txt git stash push -qm 'Saved change' printf 'committed change\n' > note.txt git commit -qam 'Different change' printf 'unrelated edit\n' > other.txt if git stash pop -q > pop-output.txt 2>&1; then printf 'Expected a conflict\n' >&2 exit 1 else result=$? fi test "$result" = 1 test "$(git stash list | wc -l | tr -d ' ')" = 1 test -n "$(git ls-files -u -- note.txt)" printf 'conflict: exit 1; stash remains\n' printf 'combined decision\n' > note.txt git add --resolved -- note.txt test -z "$(git ls-files -u -- note.txt)" test -n "$(git diff --cached -- note.txt)" test -z "$(git diff --cached -- other.txt)" test "$(cat other.txt)" = 'unrelated edit' printf 'resolved: selected conflict staged; unrelated edit unstaged\n' test "$(git show :note.txt)" = 'combined decision' git diff --cached -- note.txt git diff -- other.txt git stash list # The sole retained entry was checked in this isolated example. git stash drop -q 'stash@{0}' test -z "$(git stash list)" printf 'checked resolution: retained stash deliberately dropped\n' cd .. new_case indexed printf 'staged\n' > note.txt git add note.txt printf 'staged\nworking\n' > note.txt git stash push -qm 'Two states' git stash apply --index -q test "$(git show :note.txt)" = 'staged' test "$(cat note.txt)" = "$(printf 'staged\nworking')" printf 'index: staged and later working edits restored separately\n'