peritus / bumpversion

Version-bump your software with a single command
https://pypi.python.org/pypi/bumpversion
MIT License
1.5k stars 147 forks source link

Invalid "part" argument results in corrupted repo under certain configs #118

Open coredumperror opened 8 years ago

coredumperror commented 8 years ago

As mentioned in #89, I managed to replicate this issue in a very simply repo. In a fresh git init'd folder, add and commit these two files:

.bumpversion.cfg:

[bumpversion]
current_version = 1.0.0
commit = True
tag = True
tag_name = {new_version}

[bumpversion:file:test.txt]
search = tmtpds.git@{current_version}
replace = tmtpds.git@{new_version}

test.txt:

This is a test, this is only a test.

tmtpds.git@1.0.0

If you then execute something like bumpversion blah --dry-run --verbose, using any invalid "part" argument besides major, minor, or patch, you'll see this output:

$ bumpversion giggle --dry-run --verbose
Reading config file .bumpversion.cfg:
[bumpversion]
current_version = 1.0.0
commit = True
tag = True
tag_name = {new_version}

[bumpversion:file:test.txt]
search = tmtpds.git@{current_version}
replace = tmtpds.git@{new_version}

Parsing version '1.0.0' using regexp '(?P<major>\d+)\.(?P<minor>\d+)\.(?P<patch>\d+)'
Parsed the following values: major=1, minor=0, patch=0
Attempting to increment part 'giggle'
Values are now: major=1, minor=0, patch=0
Dry run active, won't touch any files.
Parsing version '1.0.0' using regexp '(?P<major>\d+)\.(?P<minor>\d+)\.(?P<patch>\d+)'
Parsed the following values: major=1, minor=0, patch=0
New version will be '1.0.0'
Asserting files test.txt contain the version string:
Found 'tmtpds.git@1.0.0' in test.txt at line 2: tmtpds.git@1.0.0
Would change file test.txt:
--- a/test.txt
+++ b/test.txt
@@ -1,3 +1,3 @@
 This is a test, this is only a test.

-tmtpds.git@1.0.0
+tmtpds.git@tmtpds.git@1.0.0
Would write to config file .bumpversion.cfg:
[bumpversion]
current_version = 1.0.0
commit = True
tag = True
tag_name = {new_version}

[bumpversion:file:test.txt]
search = tmtpds.git@{current_version}
replace = tmtpds.git@{new_version}

Would prepare Git commit
Would add changes in file 'test.txt' to Git
Would add changes in file '.bumpversion.cfg' to Git
Would commit to Git with message 'Bump version: 1.0.0 → 1.0.0'
Would tag '1.0.0' in Git

Not only is it performing a commit without incrementing the version number, but it's also corrupting test.txt by repeating "tmtpds.git@" within the file. And if you're doing this on an existing repo with commits and tags and don't do --dry-run, you'll get an error from git: fatal: tag '1.0.0' already exists.

The cause of this appears to be that bumpversion doesn't sanitize its "part" argument, accepting any old string it's given, rather than throwing an error when it gets something it doesn't understand.

I'm not at all sure where that corruption is coming from, though. That's an entirely different problem than simple argument sanitization.

peritus commented 8 years ago

Ok, I just tried this and can reproduce this with the current version. Definitely a defect.

And I think you might be right with the last two paragraphs as to why this is.