# HG changeset patch
# User Jan Vrany <jan.vrany@fit.cvut.cz>
# Date 1551961332 0
# Thu Mar 07 12:22:12 2019 +0000
# Node ID 9bb1db01b5e9a9d6c7c6e1ebb48b7c2fe6606c33
# Parent 8a885a75daa90cf3ec38e716fab10e80b9039844
Issue 256: fix parsing branch list when branch name(s) contains spaces
Since branch names may contain space, we must use custom template
to get a a robust machine readable output.
diff -r 8a885a75daa9 -r 9bb1db01b5e9 mercurial/HGCommand.st
a
|
b
|
|
1437 | 1437 | closed == true ifTrue:[ |
1438 | 1438 | stream nextPut:'--closed' |
1439 | 1439 | ]. |
| 1440 | stream |
| 1441 | nextPut:'--template'; |
| 1442 | nextPut:HGCommandParser templateBranches. |
1440 | 1443 | |
1441 | 1444 | "Created: / 27-11-2012 / 19:54:08 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 1445 | "Modified: / 07-03-2019 / 11:03:36 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
1442 | 1446 | ! |
1443 | 1447 | |
1444 | 1448 | parseError:stream |
diff -r 8a885a75daa9 -r 9bb1db01b5e9 mercurial/HGCommandParser.st
a
|
b
|
|
76 | 76 | |
77 | 77 | !HGCommandParser class methodsFor:'templates'! |
78 | 78 | |
| 79 | templateBranches |
| 80 | ^ '{branch}\0{rev}:{node}\0{ifeq(closed,''True'',''C'',ifeq(active,''False'',''I'',''A''))}\n' |
| 81 | |
| 82 | "Created: / 07-03-2019 / 11:02:46 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 83 | ! |
| 84 | |
79 | 85 | templateHeads |
80 | 86 | ^'{rev}:{node}\n' |
81 | 87 | |
… |
… |
|
250 | 256 | ! |
251 | 257 | |
252 | 258 | parseBranchesEntryAllowForInvalidBranchheadsMessage: allowForInvalidBrancheadsMessage |
253 | | | name branch | |
| 259 | | name branch state | |
254 | 260 | |
255 | | name := self parseName. |
256 | | stream skipSeparators. |
| 261 | name := self parseNameUpToNullOrNewLine. |
257 | 262 | allowForInvalidBrancheadsMessage ifTrue:[ |
258 | | stream peek isDigit ifFalse:[ |
| 263 | stream peek == Character null ifFalse:[ |
259 | 264 | | message | |
260 | 265 | |
261 | 266 | message := name , ' ', stream nextLine. |
262 | 267 | self notify: message. |
263 | | name := self parseName. |
264 | | stream skipSeparators. |
| 268 | name := self parseNameUpToNullOrNewLine. |
265 | 269 | ]. |
266 | | ]. |
| 270 | ]. |
267 | 271 | branch := HGBranch new. |
268 | 272 | branch setName: name. |
269 | | |
| 273 | |
| 274 | self expect: Character null. |
270 | 275 | self parseNodeId. |
271 | | stream peek == Character space ifTrue:[ |
272 | | stream next. |
273 | | stream peek == $( ifFalse:[self error:'''('' expected but ''' , stream peek , ''' found']. |
274 | | stream next. |
275 | | stream peek == $i ifTrue:[ |
276 | | self expect:'inactive)'. |
277 | | branch setActive: false. |
278 | | ] ifFalse:[ |
279 | | stream peek == $c ifTrue:[ |
280 | | self expect:'closed)'. |
281 | | branch setClosed: true. |
282 | | ] ifFalse:[ |
283 | | self error:'Unexpected branch attribute (only ''closed'' and ''inactive'' supported)''' |
284 | | ] |
285 | | ]. |
286 | | ]. |
| 276 | self expect: Character null. |
| 277 | state := stream next. |
| 278 | state == $A ifTrue:[ |
| 279 | branch setActive: true |
| 280 | ] ifFalse:[ state == $C ifTrue:[ |
| 281 | branch setClosed: true |
| 282 | ] ifFalse:[ state == $I ifTrue:[ |
| 283 | branch setActive: false |
| 284 | ] ifFalse:[ |
| 285 | self error: 'Invalid branch state: ' , state |
| 286 | ]]]. |
287 | 287 | self expectLineEnd. |
288 | 288 | ^branch |
289 | 289 | |
290 | 290 | "Created: / 08-10-2014 / 20:54:46 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 291 | "Modified: / 07-03-2019 / 12:17:14 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
291 | 292 | ! |
292 | 293 | |
293 | 294 | parseConfig |
… |
… |
|
509 | 510 | ]. |
510 | 511 | |
511 | 512 | "Created: / 27-11-2012 / 20:21:27 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 513 | "Modified: / 07-03-2019 / 11:17:52 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
512 | 514 | ! |
513 | 515 | |
514 | 516 | parseNameList |
… |
… |
|
527 | 529 | "Created: / 27-11-2012 / 20:30:02 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
528 | 530 | ! |
529 | 531 | |
| 532 | parseNameUpTo: terminator1 or: terminator2 |
| 533 | ^String streamContents:[:out| |
| 534 | | c | |
| 535 | [ c := stream peek. c == terminator1 or:[ c == terminator2] ] whileFalse:[ |
| 536 | out nextPut:stream next |
| 537 | ] |
| 538 | ]. |
| 539 | |
| 540 | "Created: / 07-03-2019 / 12:16:26 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 541 | ! |
| 542 | |
| 543 | parseNameUpToNullOrNewLine |
| 544 | ^ self parseNameUpTo: Character null or: Character cr. |
| 545 | |
| 546 | "Created: / 07-03-2019 / 12:16:53 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 547 | ! |
| 548 | |
| 549 | parseNameZ |
| 550 | ^String streamContents:[:out| |
| 551 | [ stream peek == Character null ] whileFalse:[ |
| 552 | out nextPut:stream next |
| 553 | ] |
| 554 | ]. |
| 555 | |
| 556 | "Created: / 07-03-2019 / 11:18:24 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 557 | ! |
| 558 | |
530 | 559 | parseNodeId |
531 | 560 | "Parses node id from stream and returns it. Support both, |
532 | 561 | short and full node ids" |
diff -r 8a885a75daa9 -r 9bb1db01b5e9 mercurial/HGCommandParserTests.st
a
|
b
|
|
110 | 110 | |
111 | 111 | | branches | |
112 | 112 | |
113 | | branches := (HGCommandParser on: 'default 5:f22945219f9be25a1fe436d81afece07b89330be |
114 | | branch1 4:5bd21fb5eea8a7cb4adf45bccfea76cda11df84a (inactive) |
115 | | branch2 3:32d32dee719fb422a69cfa6f7f8c1d8e299de2df (closed) |
116 | | ') parseCommandBranches. |
| 113 | branches := (HGCommandParser on: (('default|5:f22945219f9be25a1fe436d81afece07b89330be|A |
| 114 | branch1|4:5bd21fb5eea8a7cb4adf45bccfea76cda11df84a|I |
| 115 | branch2|3:32d32dee719fb422a69cfa6f7f8c1d8e299de2df|C |
| 116 | ' copyReplaceAll: $| with: Character null))) parseCommandBranches. |
117 | 117 | |
118 | 118 | self assert: branches size == 3. |
119 | 119 | |
… |
… |
|
130 | 130 | self assert: branches third isClosed. |
131 | 131 | |
132 | 132 | "Created: / 27-11-2012 / 19:00:30 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 133 | "Modified: / 07-03-2019 / 12:12:20 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
133 | 134 | ! |
134 | 135 | |
135 | 136 | test_cmd_branches_02 |
136 | 137 | |
137 | 138 | | branches | |
138 | 139 | |
139 | | branches := (HGCommandParser on: 'invalid branchheads cache (visible): tip differs |
140 | | default 5694:756610fa329d48cd8b225524016713485aefbb95 |
141 | | jv 5684:2c32b6c5d3543cd0381f9b346d62bfeabb95e6c6 |
142 | | ') parseCommandBranches. |
| 140 | branches := (HGCommandParser on: (('invalid branchheads cache (visible): tip differs |
| 141 | default|5694:756610fa329d48cd8b225524016713485aefbb95|A |
| 142 | jv|5684:2c32b6c5d3543cd0381f9b346d62bfeabb95e6c6|A |
| 143 | ')copyReplaceAll: $| with: Character null)) parseCommandBranches. |
143 | 144 | |
144 | 145 | self assert: branches size == 2. |
145 | 146 | |
… |
… |
|
152 | 153 | self assert: branches second isClosed not. |
153 | 154 | |
154 | 155 | "Created: / 08-10-2014 / 20:39:33 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 156 | "Modified: / 07-03-2019 / 12:08:26 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 157 | ! |
| 158 | |
| 159 | test_cmd_branches_issue256b |
| 160 | |
| 161 | | branches | |
| 162 | |
| 163 | branches := (HGCommandParser on: (('default|6:6b8bef68bf9c6b8bef686b8bef68bf9c6b8bef68|A |
| 164 | test branches issue256b |5:9db0e56bb86e6b8bef686b8bef68bf9c6b8bef68|I |
| 165 | ') copyReplaceAll: $| with: Character null)) parseCommandBranches. |
| 166 | |
| 167 | self assert: branches size == 2. |
| 168 | |
| 169 | self assert: branches first name = 'default'. |
| 170 | self assert: branches first isActive. |
| 171 | self assert: branches first isClosed not. |
| 172 | |
| 173 | self assert: branches second name = 'test branches issue256b '. |
| 174 | self assert: branches second isActive not. |
| 175 | self assert: branches second isClosed not. |
| 176 | |
| 177 | "Created: / 07-03-2019 / 10:21:57 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 178 | "Modified: / 07-03-2019 / 12:07:31 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
155 | 179 | ! |
156 | 180 | |
157 | 181 | test_cmd_err_branches_01 |
diff -r 8a885a75daa9 -r 9bb1db01b5e9 mercurial/HGTests.st
a
|
b
|
|
479 | 479 | self assert:(repo branches contains: [:b|b name = 'test branches issue256a']). |
480 | 480 | |
481 | 481 | "Created: / 07-01-2019 / 22:42:24 / Jan Vrany <jan.vrany@fit.cvut.cz>" |
| 482 | ! |
| 483 | |
| 484 | test_branches_issue256b |
| 485 | " |
| 486 | Change branch with spaces & commit. Check whether commited changeset |
| 487 | has the branch set. |
| 488 | " |
| 489 | |
| 490 | | repo wc | |
| 491 | |
| 492 | repo := self repositoryNamed:'test_repo_01'. |
| 493 | wc := repo workingCopy. |
| 494 | self assert: repo branches size == 1. |
| 495 | wc branch: 'test branches issue256b'. |
| 496 | |
| 497 | "Modify some file" |
| 498 | (wc / 'f1.txt') writingFileDo:[:s | s nextPutAll:'modified...' ]. |
| 499 | wc commit: testSelector , ' - commit 01'. |
| 500 | |
| 501 | self assert: wc changeset branches size == 1. |
| 502 | self assert: wc changeset branches anElement name = 'test branches issue256b'. |
| 503 | self assert: repo branches size == 2. |
| 504 | self assert:(repo branches contains: [:b|b name = 'default']). |
| 505 | self assert:(repo branches contains: [:b|b name = 'test branches issue256b']). |
| 506 | |
| 507 | wc branch: 'default'. |
| 508 | "Modify some file" |
| 509 | (wc / 'f1.txt') writingFileDo:[:s | s nextPutAll:'modified_default...' ]. |
| 510 | wc commit: testSelector , ' - commit default branch 01'. |
| 511 | |
| 512 | self assert: wc changeset branches size == 1. |
| 513 | self assert: wc changeset branches anElement name = 'default'. |
| 514 | |
| 515 | "Created: / 06-03-2019 / 10:32:50 / svestkap" |
482 | 516 | ! ! |
483 | 517 | |
484 | 518 | !HGTests methodsFor:'tests - changesets'! |