add tests for rebasing merged history
[git] / t / t9810-git-p4-rcs.sh
1 #!/bin/sh
2
3 test_description='git p4 rcs keywords'
4
5 . ./lib-git-p4.sh
6
7 test_expect_success 'start p4d' '
8         start_p4d
9 '
10
11 #
12 # Make one file with keyword lines at the top, and
13 # enough plain text to be able to test modifications
14 # far away from the keywords.
15 #
16 test_expect_success 'init depot' '
17         (
18                 cd "$cli" &&
19                 cat <<-\EOF >filek &&
20                 $Id$
21                 /* $Revision$ */
22                 # $Change$
23                 line4
24                 line5
25                 line6
26                 line7
27                 line8
28                 EOF
29                 sed "s/Revision/Revision: do not scrub me/" <filek >fileko &&
30                 sed "s/Id/Id: do not scrub me/" <fileko >file_text &&
31                 p4 add -t text+k filek &&
32                 p4 submit -d "filek" &&
33                 p4 add -t text+ko fileko &&
34                 p4 submit -d "fileko" &&
35                 p4 add -t text file_text &&
36                 p4 submit -d "file_text"
37         )
38 '
39
40 #
41 # Generate these in a function to make it easy to use single quote marks.
42 #
43 write_scrub_scripts () {
44         cat >"$TRASH_DIRECTORY/scrub_k.py" <<-\EOF &&
45         import re, sys
46         sys.stdout.write(re.sub(r'(?i)\$(Id|Header|Author|Date|DateTime|Change|File|Revision):[^$]*\$', r'$\1$', sys.stdin.read()))
47         EOF
48         cat >"$TRASH_DIRECTORY/scrub_ko.py" <<-\EOF
49         import re, sys
50         sys.stdout.write(re.sub(r'(?i)\$(Id|Header):[^$]*\$', r'$\1$', sys.stdin.read()))
51         EOF
52 }
53
54 test_expect_success 'scrub scripts' '
55         write_scrub_scripts
56 '
57
58 #
59 # Compare $cli/file to its scrubbed version, should be different.
60 # Compare scrubbed $cli/file to $git/file, should be same.
61 #
62 scrub_k_check () {
63         file="$1" &&
64         scrub="$TRASH_DIRECTORY/$file" &&
65         "$PYTHON_PATH" "$TRASH_DIRECTORY/scrub_k.py" <"$git/$file" >"$scrub" &&
66         ! test_cmp "$cli/$file" "$scrub" &&
67         test_cmp "$git/$file" "$scrub" &&
68         rm "$scrub"
69 }
70 scrub_ko_check () {
71         file="$1" &&
72         scrub="$TRASH_DIRECTORY/$file" &&
73         "$PYTHON_PATH" "$TRASH_DIRECTORY/scrub_ko.py" <"$git/$file" >"$scrub" &&
74         ! test_cmp "$cli/$file" "$scrub" &&
75         test_cmp "$git/$file" "$scrub" &&
76         rm "$scrub"
77 }
78
79 #
80 # Modify far away from keywords.  If no RCS lines show up
81 # in the diff, there is no conflict.
82 #
83 test_expect_success 'edit far away from RCS lines' '
84         test_when_finished cleanup_git &&
85         git p4 clone --dest="$git" //depot &&
86         (
87                 cd "$git" &&
88                 git config git-p4.skipSubmitEdit true &&
89                 sed "s/^line7/line7 edit/" <filek >filek.tmp &&
90                 mv -f filek.tmp filek &&
91                 git commit -m "filek line7 edit" filek &&
92                 git p4 submit &&
93                 scrub_k_check filek
94         )
95 '
96
97 #
98 # Modify near the keywords.  This will require RCS scrubbing.
99 #
100 test_expect_success 'edit near RCS lines' '
101         test_when_finished cleanup_git &&
102         git p4 clone --dest="$git" //depot &&
103         (
104                 cd "$git" &&
105                 git config git-p4.skipSubmitEdit true &&
106                 git config git-p4.attemptRCSCleanup true &&
107                 sed "s/^line4/line4 edit/" <filek >filek.tmp &&
108                 mv -f filek.tmp filek &&
109                 git commit -m "filek line4 edit" filek &&
110                 git p4 submit &&
111                 scrub_k_check filek
112         )
113 '
114
115 #
116 # Modify the keywords themselves.  This also will require RCS scrubbing.
117 #
118 test_expect_success 'edit keyword lines' '
119         test_when_finished cleanup_git &&
120         git p4 clone --dest="$git" //depot &&
121         (
122                 cd "$git" &&
123                 git config git-p4.skipSubmitEdit true &&
124                 git config git-p4.attemptRCSCleanup true &&
125                 sed "/Revision/d" <filek >filek.tmp &&
126                 mv -f filek.tmp filek &&
127                 git commit -m "filek remove Revision line" filek &&
128                 git p4 submit &&
129                 scrub_k_check filek
130         )
131 '
132
133 #
134 # Scrubbing text+ko files should not alter all keywords, just Id, Header.
135 #
136 test_expect_success 'scrub ko files differently' '
137         test_when_finished cleanup_git &&
138         git p4 clone --dest="$git" //depot &&
139         (
140                 cd "$git" &&
141                 git config git-p4.skipSubmitEdit true &&
142                 git config git-p4.attemptRCSCleanup true &&
143                 sed "s/^line4/line4 edit/" <fileko >fileko.tmp &&
144                 mv -f fileko.tmp fileko &&
145                 git commit -m "fileko line4 edit" fileko &&
146                 git p4 submit &&
147                 scrub_ko_check fileko &&
148                 ! scrub_k_check fileko
149         )
150 '
151
152 # hack; git p4 submit should do it on its own
153 test_expect_success 'cleanup after failure' '
154         (
155                 cd "$cli" &&
156                 p4 revert ...
157         )
158 '
159
160 # perl $File:: bug check
161 test_expect_success 'ktext expansion should not expand multi-line $File::' '
162         (
163                 cd "$cli" &&
164                 cat >lv.pm <<-\EOF
165                 my $wanted = sub { my $f = $File::Find::name;
166                                     if ( -f && $f =~ /foo/ ) {
167                 EOF
168                 p4 add -t ktext lv.pm &&
169                 p4 submit -d "lv.pm"
170         ) &&
171         test_when_finished cleanup_git &&
172         git p4 clone --dest="$git" //depot &&
173         (
174                 cd "$git" &&
175                 test_cmp "$cli/lv.pm" lv.pm
176         )
177 '
178
179 #
180 # Do not scrub anything but +k or +ko files.  Sneak a change into
181 # the cli file so that submit will get a conflict.  Make sure that
182 # scrubbing doesn't make a mess of things.
183 #
184 # This might happen only if the git repo is behind the p4 repo at
185 # submit time, and there is a conflict.
186 #
187 test_expect_success 'do not scrub plain text' '
188         test_when_finished cleanup_git &&
189         git p4 clone --dest="$git" //depot &&
190         (
191                 cd "$git" &&
192                 git config git-p4.skipSubmitEdit true &&
193                 git config git-p4.attemptRCSCleanup true &&
194                 sed "s/^line4/line4 edit/" <file_text >file_text.tmp &&
195                 mv -f file_text.tmp file_text &&
196                 git commit -m "file_text line4 edit" file_text &&
197                 (
198                         cd "$cli" &&
199                         p4 open file_text &&
200                         sed "s/^line5/line5 p4 edit/" <file_text >file_text.tmp &&
201                         mv -f file_text.tmp file_text &&
202                         p4 submit -d "file5 p4 edit"
203                 ) &&
204                 echo s | test_expect_code 1 git p4 submit &&
205                 (
206                         # make sure the file is not left open
207                         cd "$cli" &&
208                         ! p4 fstat -T action file_text
209                 )
210         )
211 '
212
213 # hack; git p4 submit should do it on its own
214 test_expect_success 'cleanup after failure 2' '
215         (
216                 cd "$cli" &&
217                 p4 revert ...
218         )
219 '
220
221 create_kw_file () {
222         cat <<\EOF >"$1"
223 /* A file
224         Id: $Id$
225         Revision: $Revision$
226         File: $File$
227  */
228 int main(int argc, const char **argv) {
229         return 0;
230 }
231 EOF
232 }
233
234 test_expect_success 'add kwfile' '
235         (
236                 cd "$cli" &&
237                 echo file1 >file1 &&
238                 p4 add file1 &&
239                 p4 submit -d "file 1" &&
240                 create_kw_file kwfile1.c &&
241                 p4 add kwfile1.c &&
242                 p4 submit -d "Add rcw kw file" kwfile1.c
243         )
244 '
245
246 p4_append_to_file () {
247         f="$1" &&
248         p4 edit -t ktext "$f" &&
249         echo "/* $(date) */" >>"$f" &&
250         p4 submit -d "appending a line in p4"
251 }
252
253 # Create some files with RCS keywords. If they get modified
254 # elsewhere then the version number gets bumped which then
255 # results in a merge conflict if we touch the RCS kw lines,
256 # even though the change itself would otherwise apply cleanly.
257 test_expect_success 'cope with rcs keyword expansion damage' '
258         test_when_finished cleanup_git &&
259         git p4 clone --dest="$git" //depot &&
260         (
261                 cd "$git" &&
262                 git config git-p4.skipSubmitEdit true &&
263                 git config git-p4.attemptRCSCleanup true &&
264                 (cd "$cli" && p4_append_to_file kwfile1.c) &&
265                 old_lines=$(wc -l <kwfile1.c) &&
266                 "$PERL_PATH" -n -i -e "print unless m/Revision:/" kwfile1.c &&
267                 new_lines=$(wc -l <kwfile1.c) &&
268                 test $new_lines = $(($old_lines - 1)) &&
269
270                 git add kwfile1.c &&
271                 git commit -m "Zap an RCS kw line" &&
272                 git p4 submit &&
273                 git p4 rebase &&
274                 git diff p4/master &&
275                 git p4 commit &&
276                 echo "try modifying in both" &&
277                 cd "$cli" &&
278                 p4 edit kwfile1.c &&
279                 echo "line from p4" >>kwfile1.c &&
280                 p4 submit -d "add a line in p4" kwfile1.c &&
281                 cd "$git" &&
282                 echo "line from git at the top" | cat - kwfile1.c >kwfile1.c.new &&
283                 mv kwfile1.c.new kwfile1.c &&
284                 git commit -m "Add line in git at the top" kwfile1.c &&
285                 git p4 rebase &&
286                 git p4 submit
287         )
288 '
289
290 test_expect_success 'cope with rcs keyword file deletion' '
291         test_when_finished cleanup_git &&
292         (
293                 cd "$cli" &&
294                 echo "\$Revision\$" >kwdelfile.c &&
295                 p4 add -t ktext kwdelfile.c &&
296                 p4 submit -d "Add file to be deleted" &&
297                 cat kwdelfile.c &&
298                 grep 1 kwdelfile.c
299         ) &&
300         git p4 clone --dest="$git" //depot &&
301         (
302                 cd "$git" &&
303                 grep Revision kwdelfile.c &&
304                 git rm -f kwdelfile.c &&
305                 git commit -m "Delete a file containing RCS keywords" &&
306                 git config git-p4.skipSubmitEdit true &&
307                 git config git-p4.attemptRCSCleanup true &&
308                 git p4 submit
309         ) &&
310         (
311                 cd "$cli" &&
312                 p4 sync &&
313                 ! test -f kwdelfile.c
314         )
315 '
316
317 # If you add keywords in git of the form $Header$ then everything should
318 # work fine without any special handling.
319 test_expect_success 'Add keywords in git which match the default p4 values' '
320         test_when_finished cleanup_git &&
321         git p4 clone --dest="$git" //depot &&
322         (
323                 cd "$git" &&
324                 echo "NewKW: \$Revision\$" >>kwfile1.c &&
325                 git add kwfile1.c &&
326                 git commit -m "Adding RCS keywords in git" &&
327                 git config git-p4.skipSubmitEdit true &&
328                 git config git-p4.attemptRCSCleanup true &&
329                 git p4 submit
330         ) &&
331         (
332                 cd "$cli" &&
333                 p4 sync &&
334                 test -f kwfile1.c &&
335                 grep "NewKW.*Revision.*[0-9]" kwfile1.c
336
337         )
338 '
339
340 # If you add keywords in git of the form $Header:#1$ then things will fail
341 # unless git-p4 takes steps to scrub the *git* commit.
342 #
343 test_expect_failure 'Add keywords in git which do not match the default p4 values' '
344         test_when_finished cleanup_git &&
345         git p4 clone --dest="$git" //depot &&
346         (
347                 cd "$git" &&
348                 echo "NewKW2: \$Revision:1\$" >>kwfile1.c &&
349                 git add kwfile1.c &&
350                 git commit -m "Adding RCS keywords in git" &&
351                 git config git-p4.skipSubmitEdit true &&
352                 git config git-p4.attemptRCSCleanup true &&
353                 git p4 submit
354         ) &&
355         (
356                 cd "$cli" &&
357                 p4 sync &&
358                 grep "NewKW2.*Revision.*[0-9]" kwfile1.c
359
360         )
361 '
362
363 test_expect_success 'kill p4d' '
364         kill_p4d
365 '
366
367 test_done