Anthony Sottile | 8f61529 | 2022-01-15 19:24:05 -0500 | [diff] [blame] | 1 | from __future__ import annotations |
| 2 | |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 3 | import pytest |
| 4 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 5 | from pre_commit_hooks.mixed_line_ending import main |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 6 | |
| 7 | |
| 8 | @pytest.mark.parametrize( |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 9 | ('input_s', 'output'), |
| 10 | ( |
| 11 | # mixed with majority of 'LF' |
| 12 | (b'foo\r\nbar\nbaz\n', b'foo\nbar\nbaz\n'), |
| 13 | # mixed with majority of 'CRLF' |
| 14 | (b'foo\r\nbar\nbaz\r\n', b'foo\r\nbar\r\nbaz\r\n'), |
| 15 | # mixed with majority of 'CR' |
| 16 | (b'foo\rbar\nbaz\r', b'foo\rbar\rbaz\r'), |
| 17 | # mixed with as much 'LF' as 'CRLF' |
| 18 | (b'foo\r\nbar\n', b'foo\nbar\n'), |
| 19 | # mixed with as much 'LF' as 'CR' |
| 20 | (b'foo\rbar\n', b'foo\nbar\n'), |
| 21 | # mixed with as much 'CRLF' as 'CR' |
| 22 | (b'foo\r\nbar\r', b'foo\r\nbar\r\n'), |
| 23 | # mixed with as much 'CRLF' as 'LF' as 'CR' |
| 24 | (b'foo\r\nbar\nbaz\r', b'foo\nbar\nbaz\n'), |
| 25 | ), |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 26 | ) |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 27 | def test_mixed_line_ending_fixes_auto(input_s, output, tmpdir): |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 28 | path = tmpdir.join('file.txt') |
Anthony Sottile | 47c4d9e | 2017-09-05 19:27:34 -0700 | [diff] [blame] | 29 | path.write_binary(input_s) |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 30 | ret = main((str(path),)) |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 31 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 32 | assert ret == 1 |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 33 | assert path.read_binary() == output |
| 34 | |
| 35 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 36 | def test_non_mixed_no_newline_end_of_file(tmpdir): |
| 37 | path = tmpdir.join('f.txt') |
| 38 | path.write_binary(b'foo\nbar\nbaz') |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 39 | assert not main((str(path),)) |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 40 | # the hook *could* fix the end of the file, but leaves it alone |
| 41 | # this is mostly to document the current behaviour |
| 42 | assert path.read_binary() == b'foo\nbar\nbaz' |
| 43 | |
| 44 | |
| 45 | def test_mixed_no_newline_end_of_file(tmpdir): |
| 46 | path = tmpdir.join('f.txt') |
| 47 | path.write_binary(b'foo\r\nbar\nbaz') |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 48 | assert main((str(path),)) |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 49 | # the hook rewrites the end of the file, this is slightly inconsistent |
| 50 | # with the non-mixed case but I think this is the better behaviour |
| 51 | # this is mostly to document the current behaviour |
| 52 | assert path.read_binary() == b'foo\nbar\nbaz\n' |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 53 | |
| 54 | |
| 55 | @pytest.mark.parametrize( |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 56 | ('fix_option', 'input_s'), |
| 57 | ( |
| 58 | # All --fix=auto with uniform line endings should be ok |
| 59 | ('--fix=auto', b'foo\r\nbar\r\nbaz\r\n'), |
| 60 | ('--fix=auto', b'foo\rbar\rbaz\r'), |
| 61 | ('--fix=auto', b'foo\nbar\nbaz\n'), |
| 62 | # --fix=crlf with crlf endings |
| 63 | ('--fix=crlf', b'foo\r\nbar\r\nbaz\r\n'), |
| 64 | # --fix=lf with lf endings |
| 65 | ('--fix=lf', b'foo\nbar\nbaz\n'), |
| 66 | ), |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 67 | ) |
Anthony Sottile | 1566cf9 | 2018-12-03 08:34:05 -0800 | [diff] [blame] | 68 | def test_line_endings_ok(fix_option, input_s, tmpdir, capsys): |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 69 | path = tmpdir.join('input.txt') |
Anthony Sottile | 47c4d9e | 2017-09-05 19:27:34 -0700 | [diff] [blame] | 70 | path.write_binary(input_s) |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 71 | ret = main((fix_option, str(path))) |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 72 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 73 | assert ret == 0 |
| 74 | assert path.read_binary() == input_s |
Anthony Sottile | 1566cf9 | 2018-12-03 08:34:05 -0800 | [diff] [blame] | 75 | out, _ = capsys.readouterr() |
| 76 | assert out == '' |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 77 | |
| 78 | |
Anthony Sottile | 1566cf9 | 2018-12-03 08:34:05 -0800 | [diff] [blame] | 79 | def test_no_fix_does_not_modify(tmpdir, capsys): |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 80 | path = tmpdir.join('input.txt') |
| 81 | contents = b'foo\r\nbar\rbaz\nwomp\n' |
| 82 | path.write_binary(contents) |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 83 | ret = main(('--fix=no', str(path))) |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 84 | |
| 85 | assert ret == 1 |
| 86 | assert path.read_binary() == contents |
Anthony Sottile | 1566cf9 | 2018-12-03 08:34:05 -0800 | [diff] [blame] | 87 | out, _ = capsys.readouterr() |
Anthony Sottile | f5c42a0 | 2020-02-05 11:10:42 -0800 | [diff] [blame] | 88 | assert out == f'{path}: mixed line endings\n' |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 89 | |
| 90 | |
Anthony Sottile | 1566cf9 | 2018-12-03 08:34:05 -0800 | [diff] [blame] | 91 | def test_fix_lf(tmpdir, capsys): |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 92 | path = tmpdir.join('input.txt') |
| 93 | path.write_binary(b'foo\r\nbar\rbaz\n') |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 94 | ret = main(('--fix=lf', str(path))) |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 95 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 96 | assert ret == 1 |
| 97 | assert path.read_binary() == b'foo\nbar\nbaz\n' |
Anthony Sottile | 1566cf9 | 2018-12-03 08:34:05 -0800 | [diff] [blame] | 98 | out, _ = capsys.readouterr() |
Anthony Sottile | f5c42a0 | 2020-02-05 11:10:42 -0800 | [diff] [blame] | 99 | assert out == f'{path}: fixed mixed line endings\n' |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 100 | |
| 101 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 102 | def test_fix_crlf(tmpdir): |
| 103 | path = tmpdir.join('input.txt') |
| 104 | path.write_binary(b'foo\r\nbar\rbaz\n') |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 105 | ret = main(('--fix=crlf', str(path))) |
Morgan Courbet | fc8a5b2 | 2017-06-13 21:38:14 +0200 | [diff] [blame] | 106 | |
Anthony Sottile | fbcd096 | 2017-09-05 20:20:43 -0700 | [diff] [blame] | 107 | assert ret == 1 |
| 108 | assert path.read_binary() == b'foo\r\nbar\r\nbaz\r\n' |
Anthony Sottile | 76047f6 | 2017-09-27 07:47:24 -0700 | [diff] [blame] | 109 | |
| 110 | |
| 111 | def test_fix_lf_all_crlf(tmpdir): |
| 112 | """Regression test for #239""" |
| 113 | path = tmpdir.join('input.txt') |
| 114 | path.write_binary(b'foo\r\nbar\r\n') |
Max Rozentsveyg | f35bfed | 2020-05-20 12:07:45 -0400 | [diff] [blame] | 115 | ret = main(('--fix=lf', str(path))) |
Anthony Sottile | 76047f6 | 2017-09-27 07:47:24 -0700 | [diff] [blame] | 116 | |
| 117 | assert ret == 1 |
| 118 | assert path.read_binary() == b'foo\nbar\n' |