Reputation: 65550
I have both renamed and moved a file in git. I took the bar.js
file, edited the contents extensively, and moved it across directories.
This is what git status
is showing me:
$ git status
On branch feature/bar-chart
Changes not staged for commit:
(use "git add/rm <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
deleted: js/journey-graph/bar.js
Untracked files:
(use "git add <file>..." to include in what will be committed)
js/bar-chart/bar.js
I'd like to make a single commit that encompasses both the rename and the editing, and preserves the history attached to the file.
Is this possible with git?
Please note: I don't want to rely on git spotting automatically that the files are similar, and guessing that they have been renamed rather than manually added and deleted. I want to tell git exactly what has happened. (This is because I actually have quite a few edited files, and I'm nervous about git getting them confused.)
Upvotes: 0
Views: 51
Reputation: 11831
You can go
git mv file newname # Rename
edit, edit, edit, ... # Mangle
git add newname # Make *sure* the last version gets saved
git commit # Away we go
No changes are really recorded until the commit. And git mv
does exactky the same as deleting the old file and creating a new one with the same contents, as far as git cares. How the contents moved from one place to the other is none of git's concern.
Upvotes: 1
Reputation: 489073
Git commit does not care about renames.
Commit simply writes a commit that records the complete state of a work-tree (plus the usual other commit data). "The state of a work tree" never has any renaming in it. It just has files. File a.js
exists, or does not. File b.js
exists, or does not.
Renaming comes in when (and only when) you ask git to compare two trees. You can, for instance, ask git to compare "tree in latest commit" with "tree in working directory". That's what git status
does.
You can also ask git to compare the trees of two different commits:
git diff HEAD~7 HEAD~2 # what changed between "7 commits ago" and "2 ago"
and git diff
takes options—-M
, -C
, and so on—that let you control how aggressive git gets in terms of rename and copy detection. The git status
command has no options for this; its rename-detector is permanently set to a moderate level.
The key point, though, is all this happens when you run the other commands: git commit
simply records a tree, and it's later (and earlier!), with other git commands, that git attempts to figure out whether things were renamed and/or copied.
Upvotes: 1