|
1 |
| -# git-undo ⏪✨ |
2 |
| - |
3 |
| -*A universal "Ctrl + Z" for Git commands.* 🔄 |
4 |
| - |
5 |
| -`git-undo` tracks every mutating Git command you run and can roll it back with a single `git undo` 🚀 |
6 |
| -No reflog spelunking, no cherry‑picks—just instant reversal. ⚡ |
7 |
| - |
8 |
| -## Table of Contents |
9 |
| -1. [Introduction](#introduction) |
10 |
| -2. [Features](#features) |
11 |
| -3. [Installation](#installation) |
12 |
| - - [cURL one‑liner](#curl-one-liner-preferred) |
13 |
| - - [Manual clone](#manual-clone) |
14 |
| - - [Shell‑hook integration](#shell-hook-integration) |
15 |
| - - [Using go install](#using-go-install) |
16 |
| -4. [Quick Start](#quick-start) |
17 |
| -5. [Usage](#usage) |
18 |
| -6. [Supported Git Commands](#supported-git-commands) |
19 |
| -7. [Examples](#examples) |
20 |
| -8. [Development & Testing](#development--testing) |
21 |
| -9. [Contributing & Feedback](#contributing--feedback) |
22 |
| -10. [License](#license) |
| 1 | +# git-undo |
23 | 2 |
|
24 |
| ---- |
25 |
| - |
26 |
| -## Introduction |
27 |
| -`git-undo` makes destructive Git operations painless to reverse. |
28 |
| -It records each mutating command (commit, add, merge, stash, …) per‑repository in a tiny log file inside `.git/git-undo/`, |
29 |
| -then generates the matching *anti‑command* when you call **`git undo`**. |
30 |
| - |
31 |
| -## Features |
32 |
| -- **One‑shot undo** for commits, adds, branches, stashes, merges, and more. |
33 |
| -- **Sequential undo / redo** - walk backward *or* forward through history. |
34 |
| -- **Smart guidance** - detects checkout/switch operations and suggests `git back` instead. |
35 |
| -- Verbose & dry‑run modes for full transparency. |
36 |
| -- Per‑repository command log you can inspect or clear at any time. |
| 3 | +# **Ctrl+Z for Git commands** |
37 | 4 |
|
38 |
| -## Installation |
39 |
| - |
40 |
| -### Prerequisites |
41 |
| -* Git |
42 |
| -* Go ≥ 1.21 (auto‑upgrades to 1.24 via Go toolchain) |
43 |
| -* Zsh or Bash Shells (more shells coming soon) |
44 |
| - |
45 |
| -### cURL one‑liner *(preferred)* |
| 5 | +## 1. `git undo`: one simple command to undo (almost) any Git operation: |
46 | 6 |
|
47 | 7 | ```bash
|
48 |
| -curl -fsSL https://raw.githubusercontent.com/amberpixels/git-undo/main/install.sh | bash |
49 |
| -``` |
50 |
| - |
51 |
| -### Manual clone |
52 |
| -```bash |
53 |
| -git clone https://github.com/amberpixels/git-undo.git |
54 |
| -cd git-undo |
55 |
| -./install.sh |
| 8 | +git add . |
| 9 | +git commit -m "oops, wrong files" |
| 10 | +git undo # Back to before commit, files still staged |
| 11 | +git undo # Back to before add, clean working directory |
56 | 12 | ```
|
57 | 13 |
|
58 |
| -### Shell‑hook integration |
59 |
| -- For zsh: |
60 |
| - - The installer drops [`scripts/git-undo-hook.zsh`](scripts/git-undo-hook.zsh) into `~/.config/git-undo/` |
61 |
| -and appends a `source` line to your `.zshrc`. |
62 |
| -- For bash: |
63 |
| - - The installer drops [`scripts/git-undo-hook.bash`](scripts/git-undo-hook.bash) into `~/.config/git-undo/` |
64 |
| -and appends a `source` line to your `.bashrc` / `.bash_profile` (depending on your OS). |
65 |
| - |
66 |
| -### Using go install |
| 14 | +## 2. `git back`: undo navigation commands e.g. `git checkout`, `git switch`: |
67 | 15 |
|
68 | 16 | ```bash
|
69 |
| -go install github.com/amberpixels/git-undo/cmd/git-undo@latest |
| 17 | +# Assume we're on main |
| 18 | +git switch feature-branch |
| 19 | +git back # back to main |
| 20 | +git back # back to feature-branch |
70 | 21 | ```
|
71 | 22 |
|
72 |
| -## Quick Start |
73 |
| -```bash |
74 |
| -git add . |
75 |
| -git commit -m "oops" # commit, then regret it |
76 |
| -git undo # resets to HEAD~1, keeps changes staged (like Ctrl+Z) |
77 |
| -git undo # undoes `git add .` as well |
78 |
| -``` |
| 23 | +## 3. `git undo undo` Undoed accidently? Undo it as well. (like Ctrl+Shift+Z) |
79 | 24 |
|
80 |
| -Need the commit back? |
81 | 25 | ```bash
|
82 |
| -git undo undo # redo last undo (like Ctrl+Shift+Z) |
| 26 | +git add . |
| 27 | +git commit -m "oops, wrong files" |
| 28 | +git undo # Back to before commit, files still staged |
| 29 | +git undo undo # Back to commited again |
83 | 30 | ```
|
84 | 31 |
|
85 |
| -## Usage |
86 |
| -| Command | Effect | |
87 |
| -|----------------------|---------------------------------------------------| |
88 |
| -| `git undo` | Roll back the last mutating Git command | |
89 |
| -| `git undo undo` | Re-roll back the last undoed command | |
90 |
| -| `git undo --verbose` | Show the generated inverse command before running | |
91 |
| -| `git undo --dry-run` | Print what *would* be executed, do nothing | |
92 |
| -| `git undo --log` | Dump your logged command history | |
93 |
| - |
94 |
| -### Version Information |
95 |
| - |
96 |
| -Check the version of git-undo: |
| 32 | +## 4. `git undo --dry-run`: see what would be undone: |
97 | 33 |
|
98 | 34 | ```bash
|
99 |
| -git undo version # Standard version command |
100 |
| -git undo self version # The same (just a consistent way for other `git undo self` commands) |
| 35 | +# Make some changes |
| 36 | +git add file.txt |
| 37 | +git undo --dry-run # shows hint to run "git restore --staged ." |
| 38 | +git commit -m "test commit" |
| 39 | +git undo --dry-run # shows hint to run "git reset --soft HEAD~1" |
101 | 40 | ```
|
102 | 41 |
|
103 |
| -The version detection works in the following priority: |
104 |
| -1. Git tag version (if in a git repository with tags) |
105 |
| -2. Build-time version (set during compilation) |
106 |
| -3. "unknown" (fallback) |
| 42 | +## 5. Debug options: `git undo --verbose`, `git undo --log` |
107 | 43 |
|
108 |
| -### Self-Management Commands |
| 44 | +Now you can use Git confidently, knowing any command is easily undoable. |
109 | 45 |
|
110 |
| -Update git-undo to the latest version: |
| 46 | +## Installation Options |
111 | 47 |
|
| 48 | +### One-liner (Recommended) |
112 | 49 | ```bash
|
113 |
| -git undo self update |
| 50 | +curl -fsSL https://raw.githubusercontent.com/amberpixels/git-undo/main/install.sh | bash |
114 | 51 | ```
|
115 |
| - |
116 |
| -Uninstall git-undo: |
117 |
| - |
| 52 | +### Manual Installation (useful for development, debugging, troubleshooting) |
118 | 53 | ```bash
|
119 |
| -git undo self uninstall |
| 54 | +git clone https://github.com/amberpixels/git-undo.git |
| 55 | +cd git-undo |
| 56 | +./install.sh |
120 | 57 | ```
|
121 | 58 |
|
122 |
| -## Supported Git Commands |
123 |
| -* `commit` |
124 |
| -* `add` |
125 |
| -* `branch` |
126 |
| -* `stash push` |
127 |
| -* `merge` |
128 |
| -* `checkout -b` |
129 |
| -* More on the way—PRs welcome! |
| 59 | +**Requirements:** Git, Go ≥ 1.21, Bash/Zsh |
| 60 | + |
| 61 | +## Supported commands to be undo-ed: |
| 62 | + |
| 63 | +| Git Command | How it's undone | Notes | |
| 64 | +|-------------|-----------------|-------| |
| 65 | +| **`git add`** | `git restore --staged <files>` or `git reset <files>` | Unstages files. Uses `git reset` if no HEAD exists | |
| 66 | +| **`git commit`** | `git reset --soft HEAD~1` | Keeps changes staged. Handles merge commits and tagged commits | |
| 67 | +| **`git branch <name>`** | `git branch -D <name>` | Deletes the created branch | |
| 68 | +| **`git checkout -b <name>`** | `git branch -D <name>` | Deletes branch created by checkout -b | |
| 69 | +| **`git switch -c <name>`** | `git branch -D <name>` | Deletes branch created by switch -c | |
| 70 | +| **`git switch <branch>`** | `git switch -` | Returns to previous branch | |
| 71 | +| **`git merge <branch>`** | `git reset --merge ORIG_HEAD` | Handles both fast-forward and merge commits | |
| 72 | +| **`git cherry-pick <commit>`** | `git reset --hard HEAD~1` | Removes cherry-picked commit | |
| 73 | +| **`git revert <commit>`** | `git reset --hard HEAD~1` | Removes revert commit | |
| 74 | +| **`git reset`** | `git reset <previous-head>` | Restores to previous HEAD position using reflog | |
| 75 | +| **`git stash` / `git stash push`** | `git stash pop` | Pops and removes the stash | |
| 76 | +| **`git rm <files>`** | `git restore --source=HEAD --staged --worktree <files>` | Restores removed files | |
| 77 | +| **`git rm --cached <files>`** | `git add <files>` | Re-adds files to index | |
| 78 | +| **`git mv <old> <new>`** | `git mv <new> <old>` | Reverses the move operation | |
| 79 | +| **`git tag <name>`** | `git tag -d <name>` | Deletes the created tag | |
| 80 | +| **`git restore --staged <files>`** | `git add <files>` | Re-stages the files | |
| 81 | + |
| 82 | +### Not Yet Supported (Returns helpful error message): |
| 83 | + |
| 84 | +| Git Command | Reason | |
| 85 | +|-------------|--------| |
| 86 | +| **`git checkout <branch>`** | Only `checkout -b` is supported (regular checkout navigation not undoable) | |
| 87 | +| **`git clean`** | Cannot recover deleted untracked files (would need pre-operation backup) | |
| 88 | +| **`git restore --worktree`** | Previous working tree state unknown | |
| 89 | +| **`git restore --source=<ref>`** | Previous state from specific reference unknown | |
| 90 | +| **`git stash pop/apply`** | Would need to re-stash, which is complex | |
| 91 | +| **Branch/tag deletion** | Cannot restore deleted branches/tags (would need backup) | |
| 92 | + |
| 93 | +## How It Works |
| 94 | + |
| 95 | +After installation both `shell hooks` and `git hooks` are installed, that track any git command and send them to `git-undo` (a git plugin) binary. There git commands are categorized and stored in a tiny log file (`.git/git-undo/commands`). Later, when calling `git undo` it reads the log and decide if it's possible (and how) to undo previous command. |
130 | 96 |
|
131 | 97 | ## Examples
|
132 |
| -Undo a merge commit: |
133 |
| -```bash |
134 |
| -git merge feature/main |
135 |
| -git undo # resets --merge ORIG_HEAD |
136 |
| -``` |
137 | 98 |
|
138 |
| -Undo adding specific files: |
| 99 | +**Undo a merge:** |
139 | 100 | ```bash
|
140 |
| -git add file1.go file2.go |
141 |
| -git undo # unstages file1.go file2.go |
| 101 | +git merge feature-branch |
| 102 | +git undo # resets --merge ORIG_HEAD |
142 | 103 | ```
|
143 | 104 |
|
144 |
| -Smart guidance for branch operations: |
| 105 | +**Undo adding specific files:** |
145 | 106 | ```bash
|
146 |
| -git checkout feature-branch |
147 |
| -git undo # guides you to use git back instead |
148 |
| -# git-undo ℹ️: Last operation can't be undone. Use git back instead. |
| 107 | +git add file1.js file2.js |
| 108 | +git undo # unstages just those files |
149 | 109 | ```
|
150 | 110 |
|
151 |
| -## Development & Testing |
| 111 | +**Undo branch creation:** |
152 | 112 | ```bash
|
153 |
| -make tidy # fmt, vet, mod tidy |
154 |
| -make test # unit tests |
155 |
| -make lint # golangci‑lint |
156 |
| -make build # compile to ./build/git-undo |
157 |
| -make install # installs Go binary and adds zsh hook |
| 113 | +git checkout -b new-feature |
| 114 | +git undo # deletes branch, returns to previous |
158 | 115 | ```
|
159 | 116 |
|
160 |
| -## Development |
161 |
| - |
162 |
| -### Building with Version Information |
163 |
| - |
164 |
| -To build git-undo with a specific version: |
| 117 | +### Self-Management |
165 | 118 |
|
| 119 | +Get the version information: |
166 | 120 | ```bash
|
167 |
| -# Using git describe |
168 |
| -VERSION=$(git describe --tags --always 2>/dev/null || echo "dev") |
169 |
| -go build -ldflags "-X main.version=$VERSION" ./cmd/git-undo |
170 |
| - |
171 |
| -# Or manually specify version |
172 |
| -go build -ldflags "-X main.version=v1.2.3" ./cmd/git-undo |
| 121 | +go install github.com/amberpixels/git-undo/cmd/git-undo@latest |
173 | 122 | ```
|
174 | 123 |
|
175 |
| -### Testing |
176 |
| - |
177 |
| -Run the test suite: |
| 124 | +Update to latest version: |
| 125 | +```bash |
| 126 | +git undo self update |
| 127 | +``` |
178 | 128 |
|
| 129 | +Uninstall: |
179 | 130 | ```bash
|
180 |
| -go test ./... |
| 131 | +git undo self uninstall |
181 | 132 | ```
|
182 | 133 |
|
183 |
| -## Contributing & Feedback |
184 |
| -Spotted a bug or missing undo case? |
185 |
| -Opening an issue or PR makes the tool better for everyone. |
186 |
| -If `git-undo` saved your bacon, please **star the repo** and share suggestions! |
| 134 | +## Contributing |
| 135 | + |
| 136 | +Found a Git command that should be undoable? [Open an issue](https://github.com/amberpixels/git-undo/issues) or submit a PR! |
187 | 137 |
|
188 | 138 | ## License
|
189 |
| -[MIT](LICENSE) |
| 139 | + |
| 140 | +MIT - see [LICENSE](LICENSE) file. |
| 141 | + |
| 142 | +--- |
| 143 | + |
| 144 | +**Make Git worry-free.** [⭐ Star this repo](https://github.com/amberpixels/git-undo) if git-undo makes your development workflow better! |
0 commit comments