1<?php 2 3/** 4 * Test cases for @{class:ArcanistDiffParser}. 5 */ 6final class ArcanistDiffParserTestCase extends PhutilTestCase { 7 8 public function testParser() { 9 $root = dirname(__FILE__).'/diff/'; 10 foreach (Filesystem::listDirectory($root, $hidden = false) as $file) { 11 $this->parseDiff($root.$file); 12 } 13 } 14 15 private function parseDiff($diff_file) { 16 $contents = Filesystem::readFile($diff_file); 17 $file = basename($diff_file); 18 19 $parser = new ArcanistDiffParser(); 20 $changes = $parser->parseDiff($contents); 21 22 switch ($file) { 23 case 'colorized.hggitdiff': 24 $this->assertEqual(1, count($changes)); 25 break; 26 case 'basic-missing-both-newlines-plus.udiff': 27 case 'basic-missing-both-newlines.udiff': 28 case 'basic-missing-new-newline-plus.udiff': 29 case 'basic-missing-new-newline.udiff': 30 case 'basic-missing-old-newline-plus.udiff': 31 case 'basic-missing-old-newline.udiff': 32 $expect_old = strpos($file, '-old-') || strpos($file, '-both-'); 33 $expect_new = strpos($file, '-new-') || strpos($file, '-both-'); 34 $expect_two = strpos($file, '-plus'); 35 36 $this->assertEqual(count($changes), $expect_two ? 2 : 1); 37 $change = reset($changes); 38 $this->assertTrue($change !== null); 39 40 $hunks = $change->getHunks(); 41 $this->assertEqual(1, count($hunks)); 42 43 $hunk = reset($hunks); 44 $this->assertEqual((bool)$expect_old, $hunk->getIsMissingOldNewline()); 45 $this->assertEqual((bool)$expect_new, $hunk->getIsMissingNewNewline()); 46 break; 47 case 'basic-binary.udiff': 48 $this->assertEqual(1, count($changes)); 49 $change = reset($changes); 50 $this->assertEqual( 51 ArcanistDiffChangeType::FILE_BINARY, 52 $change->getFileType()); 53 break; 54 case 'basic-multi-hunk.udiff': 55 $this->assertEqual(1, count($changes)); 56 $change = reset($changes); 57 $hunks = $change->getHunks(); 58 $this->assertEqual(4, count($hunks)); 59 $this->assertEqual('right', $change->getCurrentPath()); 60 $this->assertEqual('left', $change->getOldPath()); 61 break; 62 case 'basic-multi-hunk-content.svndiff': 63 $this->assertEqual(1, count($changes)); 64 $change = reset($changes); 65 $hunks = $change->getHunks(); 66 $this->assertEqual(2, count($hunks)); 67 68 $there_is_a_literal_trailing_space_here = ' '; 69 70 $corpus_0 = <<<EOCORPUS 71 asdfasdf 72+% quack 73 % 74-% 75 %% 76 %% 77 %%% 78 79EOCORPUS; 80 $corpus_1 = <<<EOCORPUS 81 %%%%% 82 %%%%% 83{$there_is_a_literal_trailing_space_here} 84-! 85+! quack 86 87EOCORPUS; 88 $this->assertEqual( 89 $corpus_0, 90 $hunks[0]->getCorpus()); 91 $this->assertEqual( 92 $corpus_1, 93 $hunks[1]->getCorpus()); 94 break; 95 case 'svn-ignore-whitespace-only.svndiff': 96 $this->assertEqual(2, count($changes)); 97 $hunks = reset($changes)->getHunks(); 98 $this->assertEqual(0, count($hunks)); 99 break; 100 case 'svn-property-add.svndiff': 101 $this->assertEqual(1, count($changes)); 102 $change = reset($changes); 103 $hunks = reset($changes)->getHunks(); 104 $this->assertEqual(1, count($hunks)); 105 $this->assertEqual( 106 array( 107 'duck' => 'quack', 108 ), 109 $change->getNewProperties()); 110 break; 111 case 'svn-property-modify.svndiff': 112 $this->assertEqual(2, count($changes)); 113 114 $change = array_shift($changes); 115 $this->assertEqual(0, count($change->getHunks())); 116 $this->assertEqual( 117 array( 118 'svn:ignore' => '*.phpz', 119 ), 120 $change->getOldProperties()); 121 $this->assertEqual( 122 array( 123 'svn:ignore' => '*.php', 124 ), 125 $change->getNewProperties()); 126 127 $change = array_shift($changes); 128 $this->assertEqual(0, count($change->getHunks())); 129 $this->assertEqual( 130 array( 131 'svn:special' => '*', 132 ), 133 $change->getOldProperties()); 134 $this->assertEqual( 135 array( 136 'svn:special' => 'moo', 137 ), 138 $change->getNewProperties()); 139 break; 140 case 'svn-property-delete.svndiff': 141 $this->assertEqual(1, count($changes)); 142 $change = reset($changes); 143 144 $this->assertEqual(0, count($change->getHunks())); 145 $this->assertEqual( 146 $change->getOldProperties(), 147 array( 148 'svn:special' => '*', 149 )); 150 $this->assertEqual( 151 array( 152 ), 153 $change->getNewProperties()); 154 break; 155 case 'svn-property-merged.svndiff': 156 $this->assertEqual(1, count($changes)); 157 $change = reset($changes); 158 159 $this->assertEqual(count($change->getHunks()), 0); 160 161 $this->assertEqual( 162 $change->getOldProperties(), 163 array()); 164 $this->assertEqual( 165 $change->getNewProperties(), 166 array()); 167 break; 168 case 'svn-property-merge.svndiff': 169 $this->assertEqual(1, count($changes)); 170 $change = reset($changes); 171 172 $this->assertEqual(count($change->getHunks()), 0); 173 $this->assertEqual( 174 $change->getOldProperties(), 175 array( 176 )); 177 $this->assertEqual( 178 $change->getNewProperties(), 179 array( 180 'svn:mergeinfo' => <<<EOTEXT 181Merged /tfb/branches/internmove/www/html/js/help/UIFaq.js:r83462-126155 182Merged /tfb/branches/ads-create-v3/www/html/js/help/UIFaq.js:r140558-142418 183EOTEXT 184 )); 185 break; 186 case 'svn-property-older-than-1.5.svndiff': 187 // In SVN 1.5, the format for property diffs changed to use the words 188 // "Added", "Deleted" and "Modified" instead of "Name". This is an old 189 // property change diff which uses "Name". 190 $this->assertEqual(1, count($changes)); 191 $change = reset($changes); 192 193 $this->assertEqual(count($change->getHunks()), 0); 194 $this->assertEqual( 195 $change->getOldProperties(), 196 array( 197 )); 198 $this->assertEqual( 199 $change->getNewProperties(), 200 array( 201 'svn:executable' => '*', 202 )); 203 break; 204 case 'svn-binary-add.svndiff': 205 $this->assertEqual(1, count($changes)); 206 $change = reset($changes); 207 $this->assertEqual( 208 ArcanistDiffChangeType::FILE_BINARY, 209 $change->getFileType()); 210 $this->assertEqual(0, count($change->getHunks())); 211 $this->assertEqual( 212 array( 213 'svn:mime-type' => 'application/octet-stream', 214 ), 215 $change->getNewProperties()); 216 break; 217 case 'svn-binary-diff.svndiff': 218 case 'svn-binary-diff-freebsd.svndiff': 219 $this->assertEqual(1, count($changes)); 220 $change = reset($changes); 221 $this->assertEqual( 222 ArcanistDiffChangeType::FILE_BINARY, 223 $change->getFileType()); 224 $this->assertEqual(count($change->getHunks()), 0); 225 break; 226 case 'git-delete-file.gitdiff': 227 $this->assertEqual(1, count($changes)); 228 $change = reset($changes); 229 $this->assertEqual( 230 ArcanistDiffChangeType::TYPE_DELETE, 231 $change->getType()); 232 $this->assertEqual( 233 'scripts/intern/test/testfile2', 234 $change->getCurrentPath()); 235 $this->assertEqual(1, count($change->getHunks())); 236 break; 237 case 'git-binary-change.gitdiff': 238 $this->assertEqual(1, count($changes)); 239 $change = reset($changes); 240 $this->assertEqual( 241 ArcanistDiffChangeType::FILE_BINARY, 242 $change->getFileType()); 243 $this->assertEqual(0, count($change->getHunks())); 244 break; 245 case 'git-filemode-change.gitdiff': 246 $this->assertEqual(1, count($changes)); 247 $change = reset($changes); 248 $this->assertEqual(1, count($change->getHunks())); 249 $this->assertEqual( 250 array( 251 'unix:filemode' => '100644', 252 ), 253 $change->getOldProperties()); 254 $this->assertEqual( 255 array( 256 'unix:filemode' => '100755', 257 ), 258 $change->getNewProperties()); 259 break; 260 case 'git-filemode-change-only.gitdiff': 261 $this->assertEqual(count($changes), 2); 262 $change = reset($changes); 263 $this->assertEqual(count($change->getHunks()), 0); 264 $this->assertEqual( 265 array( 266 'unix:filemode' => '100644', 267 ), 268 $change->getOldProperties()); 269 $this->assertEqual( 270 array( 271 'unix:filemode' => '100755', 272 ), 273 $change->getNewProperties()); 274 break; 275 case 'svn-empty-file.svndiff': 276 $this->assertEqual(2, count($changes)); 277 $change = array_shift($changes); 278 $this->assertEqual(0, count($change->getHunks())); 279 break; 280 case 'git-ignore-whitespace-only.gitdiff': 281 $this->assertEqual(count($changes), 2); 282 283 $change = array_shift($changes); 284 $this->assertEqual(count($change->getHunks()), 0); 285 $this->assertEqual( 286 $change->getOldPath(), 287 'scripts/intern/test/testfile2'); 288 $this->assertEqual( 289 $change->getCurrentPath(), 290 'scripts/intern/test/testfile2'); 291 292 $change = array_shift($changes); 293 $this->assertEqual(count($change->getHunks()), 1); 294 $this->assertEqual( 295 $change->getOldPath(), 296 'scripts/intern/test/testfile3'); 297 $this->assertEqual( 298 $change->getCurrentPath(), 299 'scripts/intern/test/testfile3'); 300 break; 301 case 'git-move.gitdiff': 302 case 'git-move-edit.gitdiff': 303 case 'git-move-plus.gitdiff': 304 305 $extra_changeset = (bool)strpos($file, '-plus'); 306 $has_hunk = (bool)strpos($file, '-edit'); 307 308 $this->assertEqual($extra_changeset ? 3 : 2, count($changes)); 309 310 $change = array_shift($changes); 311 $this->assertEqual($has_hunk ? 1 : 0, 312 count($change->getHunks())); 313 $this->assertEqual( 314 $change->getType(), 315 ArcanistDiffChangeType::TYPE_MOVE_HERE); 316 317 $target = $change; 318 319 $change = array_shift($changes); 320 $this->assertEqual(0, count($change->getHunks())); 321 $this->assertEqual( 322 ArcanistDiffChangeType::TYPE_MOVE_AWAY, 323 $change->getType()); 324 325 $this->assertEqual( 326 $change->getCurrentPath(), 327 $target->getOldPath()); 328 $this->assertTrue( 329 in_array($target->getCurrentPath(), $change->getAwayPaths())); 330 break; 331 case 'git-merge-header.gitdiff': 332 $this->assertEqual(1, count($changes)); 333 $change = reset($changes); 334 $this->assertEqual( 335 ArcanistDiffChangeType::TYPE_MESSAGE, 336 $change->getType()); 337 $this->assertEqual( 338 '501f6d519703458471dbea6284ec5f49d1408598', 339 $change->getCommitHash()); 340 break; 341 case 'git-new-file.gitdiff': 342 $this->assertEqual(1, count($changes)); 343 $change = reset($changes); 344 $this->assertEqual( 345 ArcanistDiffChangeType::TYPE_ADD, 346 $change->getType()); 347 break; 348 case 'git-copy.gitdiff': 349 $this->assertEqual(2, count($changes)); 350 351 $change = array_shift($changes); 352 $this->assertEqual(0, count($change->getHunks())); 353 $this->assertEqual( 354 ArcanistDiffChangeType::TYPE_COPY_HERE, 355 $change->getType()); 356 $this->assertEqual( 357 'flib/intern/widgets/ui/UIWidgetRSSBox.php', 358 $change->getCurrentPath()); 359 360 $change = array_shift($changes); 361 $this->assertEqual(0, count($change->getHunks())); 362 $this->assertEqual( 363 ArcanistDiffChangeType::TYPE_COPY_AWAY, 364 $change->getType()); 365 $this->assertEqual( 366 'lib/display/intern/ui/widget/UIWidgetRSSBox.php', 367 $change->getCurrentPath()); 368 369 break; 370 case 'git-copy-plus.gitdiff': 371 $this->assertEqual(2, count($changes)); 372 373 $change = array_shift($changes); 374 $this->assertEqual(3, count($change->getHunks())); 375 $this->assertEqual( 376 ArcanistDiffChangeType::TYPE_COPY_HERE, 377 $change->getType()); 378 $this->assertEqual( 379 'flib/intern/widgets/ui/UIWidgetGraphConnect.php', 380 $change->getCurrentPath()); 381 382 $change = array_shift($changes); 383 $this->assertEqual(0, count($change->getHunks())); 384 $this->assertEqual( 385 ArcanistDiffChangeType::TYPE_COPY_AWAY, 386 $change->getType()); 387 $this->assertEqual( 388 'lib/display/intern/ui/widget/UIWidgetLunchtime.php', 389 $change->getCurrentPath()); 390 break; 391 case 'svn-property-multiline.svndiff': 392 $this->assertEqual(1, count($changes)); 393 $change = array_shift($changes); 394 395 $this->assertEqual(0, count($change->getHunks())); 396 $this->assertEqual( 397 array( 398 'svn:ignore' => 'tags', 399 ), 400 $change->getOldProperties()); 401 $this->assertEqual( 402 array( 403 'svn:ignore' => "tags\nasdf\nlol\nwhat", 404 ), 405 $change->getNewProperties()); 406 break; 407 case 'git-empty-files.gitdiff': 408 $this->assertEqual(2, count($changes)); 409 while ($change = array_shift($changes)) { 410 $this->assertEqual(0, count($change->getHunks())); 411 } 412 break; 413 case 'git-mnemonicprefix.gitdiff': 414 // Check parsing of diffs created with `diff.mnemonicprefix` 415 // configuration option set to `true`. 416 $this->assertEqual(1, count($changes)); 417 $this->assertEqual(1, count(reset($changes)->getHunks())); 418 break; 419 case 'git-commit.gitdiff': 420 case 'git-commit-logdecorate.gitdiff': 421 $this->assertEqual(1, count($changes)); 422 $change = reset($changes); 423 $this->assertEqual( 424 ArcanistDiffChangeType::TYPE_MESSAGE, 425 $change->getType()); 426 $this->assertEqual( 427 '76e2f1339c298c748aa0b52030799ed202a6537b', 428 $change->getCommitHash()); 429 $this->assertEqual( 430 <<<EOTEXT 431 432Deprecating UIActionButton (Part 1) 433 434Summary: Replaces calls to UIActionButton with <ui:button>. I tested most 435 of these calls, but there were some that I didn't know how to 436 reach, so if you are one of the owners of this code, please test 437 your feature in my sandbox: www.ngao.devrs013.facebook.com 438 439 @brosenthal, I removed some logic that was setting a disabled state 440 on a UIActionButton, which is actually a no-op. 441 442Reviewed By: brosenthal 443 444Other Commenters: sparker, egiovanola 445 446Test Plan: www.ngao.devrs013.facebook.com 447 448 Explicitly tested: 449 * ads creation flow (add keyword) 450 * ads manager (conversion tracking) 451 * help center (create a discussion) 452 * new user wizard (next step button) 453 454Revert: OK 455 456DiffCamp Revision: 94064 457 458git-svn-id: svn+ssh://tubbs/svnroot/tfb/trunk/www@223593 2c7ba8d8 459EOTEXT 460 , $change->getMetadata('message')); 461 break; 462 case 'git-binary.gitdiff': 463 $this->assertEqual(1, count($changes)); 464 $change = reset($changes); 465 $this->assertEqual( 466 ArcanistDiffChangeType::TYPE_CHANGE, 467 $change->getType()); 468 $this->assertEqual( 469 ArcanistDiffChangeType::FILE_BINARY, 470 $change->getFileType()); 471 break; 472 case 'git-odd-filename.gitdiff': 473 $this->assertEqual(2, count($changes)); 474 $change = reset($changes); 475 $this->assertEqual( 476 'old/'."\342\210\206".'.jpg', 477 $change->getOldPath()); 478 $this->assertEqual( 479 'new/'."\342\210\206".'.jpg', 480 $change->getCurrentPath()); 481 break; 482 case 'hg-binary-change.hgdiff': 483 case 'hg-solo-binary-change.hgdiff': 484 $this->assertEqual(1, count($changes)); 485 $change = reset($changes); 486 $this->assertEqual( 487 ArcanistDiffChangeType::TYPE_ADD, 488 $change->getType()); 489 $this->assertEqual( 490 ArcanistDiffChangeType::FILE_BINARY, 491 $change->getFileType()); 492 break; 493 case 'hg-binary-delete.hgdiff': 494 $this->assertEqual(1, count($changes)); 495 $change = reset($changes); 496 $this->assertEqual( 497 ArcanistDiffChangeType::TYPE_DELETE, 498 $change->getType()); 499 $this->assertEqual( 500 ArcanistDiffChangeType::FILE_BINARY, 501 $change->getFileType()); 502 break; 503 case 'git-replace-symlink.gitdiff': 504 $this->assertEqual(1, count($changes)); 505 $change = array_shift($changes); 506 $this->assertEqual( 507 ArcanistDiffChangeType::TYPE_CHANGE, 508 $change->getType()); 509 break; 510 case 'svn-1.7-property-added.svndiff': 511 $this->assertEqual(1, count($changes)); 512 $change = head($changes); 513 $new_properties = $change->getNewProperties(); 514 $this->assertEqual(2, count($new_properties)); 515 $this->assertEqual('*', idx($new_properties, 'svn:executable')); 516 $this->assertEqual('text/html', idx($new_properties, 'svn:mime-type')); 517 break; 518 case 'hg-diff-range.hgdiff': 519 $this->assertEqual(1, count($changes)); 520 $change = array_shift($changes); 521 $this->assertEqual( 522 'Test.java', 523 $change->getOldPath()); 524 $this->assertEqual( 525 'Test.java', 526 $change->getCurrentPath()); 527 break; 528 case 'hg-patch.hgdiff': 529 $this->assertEqual(1, count($changes)); 530 break; 531 case 'hg-patch-git.hgdiff': 532 $this->assertEqual(1, count($changes)); 533 break; 534 case 'custom-prefixes.gitdiff': 535 $this->assertEqual(1, count($changes)); 536 $change = head($changes); 537 $this->assertEqual( 538 'file', 539 $change->getCurrentPath()); 540 break; 541 case 'custom-prefixes-edit.gitdiff': 542 $this->assertEqual(1, count($changes)); 543 $change = head($changes); 544 $this->assertEqual( 545 'file', 546 $change->getCurrentPath()); 547 break; 548 case 'more-newlines.svndiff': 549 $this->assertEqual(1, count($changes)); 550 break; 551 case 'suppress-blank-empty.gitdiff': 552 $this->assertEqual(1, count($changes)); 553 break; 554 case 'svn-property-windows.svndiff': 555 $this->assertEqual(1, count($changes)); 556 break; 557 case 'rcs-addline.rcsdiff': 558 $this->assertEqual(1, count($changes)); 559 $change = array_shift($changes); 560 $this->assertEqual( 561 ArcanistDiffChangeType::TYPE_CHANGE, 562 $change->getType()); 563 break; 564 case 'rcs-deleteline.rcsdiff': 565 $this->assertEqual(1, count($changes)); 566 $change = array_shift($changes); 567 $this->assertEqual( 568 ArcanistDiffChangeType::TYPE_CHANGE, 569 $change->getType()); 570 break; 571 case 'comment.svndiff': 572 $this->assertEqual(1, count($changes)); 573 $change = array_shift($changes); 574 $this->assertEqual( 575 ArcanistDiffChangeType::TYPE_CHANGE, 576 $change->getType()); 577 break; 578 case 'svnlook-basics.svndiff': 579 case 'svnlook-add.svndiff': 580 case 'svnlook-delete.svndiff': 581 case 'svnlook-copied.svndiff': 582 $this->assertEqual(1, count($changes)); 583 break; 584 case 'git-format-patch.gitdiff': 585 $this->assertEqual(2, count($changes)); 586 587 $change = array_shift($changes); 588 $this->assertEqual( 589 ArcanistDiffChangeType::TYPE_MESSAGE, 590 $change->getType()); 591 $this->assertEqual('WIP', $change->getMetadata('message')); 592 593 $change = array_shift($changes); 594 $this->assertEqual( 595 ArcanistDiffChangeType::TYPE_CHANGE, 596 $change->getType()); 597 break; 598 case 'svn-double-diff.svndiff': 599 $this->assertEqual(1, count($changes)); 600 601 $change = array_shift($changes); 602 $hunks = $change->getHunks(); 603 $this->assertEqual(1, count($hunks)); 604 break; 605 case 'git-remove-spaces.gitdiff': 606 $this->assertEqual(1, count($changes)); 607 608 $change = array_shift($changes); 609 $this->assertEqual('file with spaces.txt', $change->getOldPath()); 610 break; 611 default: 612 throw new Exception(pht('No test block for diff file %s.', $diff_file)); 613 break; 614 } 615 } 616 617 public function testGitCommonFilenameExtraction() { 618 static $tests = array( 619 'a/filename.c b/filename.c' => 'filename.c', 620 "a/filename.c b/filename.c\n" => 'filename.c', 621 "a/filename.c b/filename.c\r\n" => 'filename.c', 622 'filename.c filename.c' => 'filename.c', 623 '1/filename.c 2/filename.c' => 'filename.c', 624 '"a/\\"quotes\\"" "b/\\"quotes\\""' => '"quotes"', 625 '"a/\\"quotes and spaces\\"" "b/\\"quotes and spaces\\""' => 626 '"quotes and spaces"', 627 '"a/\\342\\230\\203" "b/\\342\\230\\203"' => 628 "\xE2\x98\x83", 629 'a/Core Data/filename.c b/Core Data/filename.c' => 630 'Core Data/filename.c', 631 'some file with spaces.c some file with spaces.c' => 632 'some file with spaces.c', 633 '"foo bar.c" foo bar.c' => 'foo bar.c', 634 '"a/foo bar.c" b/foo bar.c' => 'foo bar.c', 635 'src/file dst/file' => 'file', 636 637 // Renames are handled by the "rename from ..." lines later in 638 // the diff, for simplicity of parsing; this is also how git 639 // itself handles it. 640 'a/foo.c b/bar.c' => null, 641 'a/foo bar.c b/baz troz.c' => null, 642 '"a/foo bar.c" b/baz troz.c' => null, 643 'a/foo bar.c "b/baz troz.c"' => null, 644 '"a/foo bar.c" "b/baz troz.c"' => null, 645 'filename file with spaces.c filename file with spaces.c' => 646 'filename file with spaces.c', 647 ); 648 649 foreach ($tests as $input => $expect) { 650 $result = ArcanistDiffParser::extractGitCommonFilename($input); 651 $this->assertEqual( 652 $expect, 653 $result, 654 pht('Split: %s', $input)); 655 } 656 } 657 658 659 public function runSingleRename($diffline, $from, $to, $old, $new) { 660 $str = "diff --git $diffline\nsimilarity index 95%\n" 661 ."rename from $from\nrename to $to\n"; 662 $parser = new ArcanistDiffParser(); 663 $changes = $parser->parseDiff($str); 664 $this->assertTrue( 665 $changes !== null, 666 pht("Parsed:\n%s", $str)); 667 $this->assertEqual( 668 $old == $new ? 1 : 2, count($changes), 669 pht("Parsed one change:\n%s", $str)); 670 $change = reset($changes); 671 $this->assertEqual( 672 array($old, $new), 673 array($change->getOldPath(), $change->getCurrentPath()), 674 pht('Split: %s', $diffline)); 675 } 676 677 public function testGitRenames() { 678 $this->runSingleRename('a/old.c b/new.c', 679 'old.c', 'new.c', 680 'old.c', 'new.c'); 681 $this->runSingleRename('old.c new.c', 682 'old.c', 'new.c', 683 'old.c', 'new.c'); 684 $this->runSingleRename('1/old.c 2/new.c', 685 'old.c', 'new.c', 686 'old.c', 'new.c'); 687 $this->runSingleRename('from/file.c to/file.c', 688 'from/file.c', 'to/file.c', 689 'from/file.c', 'to/file.c'); 690 $this->runSingleRename('"a/\\"quotes1\\"" "b/\\"quotes2\\""', 691 '"\\"quotes1\\""', '"\\"quotes2\\""', 692 '"quotes1"', '"quotes2"'); 693 $this->runSingleRename('"a/\\"quotes spaces1\\"" "b/\\"quotes spaces2\\""', 694 '"\\"quotes spaces1\\""', '"\\"quotes spaces2\\""', 695 '"quotes spaces1"', '"quotes spaces2"'); 696 $this->runSingleRename('"a/\\342\\230\\2031" "b/\\342\\230\\2032"', 697 '"\\342\\230\\2031"', '"\\342\\230\\2032"', 698 "\xE2\x98\x831", "\xE2\x98\x832"); 699 $this->runSingleRename('a/Core Data/old.c b/Core Data/new.c', 700 'Core Data/old.c', 'Core Data/new.c', 701 'Core Data/old.c', 'Core Data/new.c'); 702 $this->runSingleRename('file with spaces.c file with spaces.c', 703 'file with spaces.c', 'file with spaces.c', 704 'file with spaces.c', 'file with spaces.c'); 705 $this->runSingleRename('a/non-quoted filename.c "b/quoted filename.c"', 706 'non-quoted filename.c', '"quoted filename.c"', 707 'non-quoted filename.c', 'quoted filename.c'); 708 $this->runSingleRename('non-quoted filename.c "quoted filename.c"', 709 'non-quoted filename.c', '"quoted filename.c"', 710 'non-quoted filename.c', 'quoted filename.c'); 711 $this->runSingleRename('"a/quoted filename.c" b/non quoted filename.c', 712 '"quoted filename.c"', 'non quoted filename.c', 713 'quoted filename.c', 'non quoted filename.c'); 714 $this->runSingleRename('"quoted filename.c" non-quoted filename.c', 715 '"quoted filename.c"', 'non-quoted filename.c', 716 'quoted filename.c', 'non-quoted filename.c'); 717 $this->runSingleRename('old file with spaces.c new file with spaces.c', 718 'old file with spaces.c', 'new file with spaces.c', 719 'old file with spaces.c', 'new file with spaces.c'); 720 $this->runSingleRename('old file old file', 721 'old file old', 'file', 722 'old file old', 'file'); 723 } 724} 725