1<?php 2 3namespace dokuwiki\test\Parsing\ParserMode; 4 5use dokuwiki\Parsing\Handler; 6use dokuwiki\Parsing\Parser; 7 8/** 9 * Base class for parser mode tests 10 * 11 * Sets up a fresh Parser and Handler for each test. Provides assertion helpers 12 * for comparing handler call sequences. 13 */ 14abstract class ParserTestBase extends \DokuWikiTest 15{ 16 /** @var Parser parser instance for the current test */ 17 protected Parser $P; 18 /** @var Handler handler instance that records calls made by the parser */ 19 protected Handler $H; 20 21 /** @inheritdoc */ 22 public function setUp(): void 23 { 24 parent::setUp(); 25 $this->H = new Handler(); 26 $this->P = new Parser($this->H); 27 } 28 29 /** @inheritdoc */ 30 public function tearDown(): void 31 { 32 unset($this->P, $this->H); 33 parent::tearDown(); 34 } 35 36 /** 37 * Assert that handler calls match the expected calls, ignoring byte index positions 38 * 39 * The byte index (element [2] in each call) is stripped before comparison because 40 * it depends on internal parser state and is not relevant for most tests. 41 * 42 * @param array $expected the expected call sequence 43 * @param array $actual the actual handler calls (typically $this->H->calls) 44 * @param string $message optional failure message 45 */ 46 protected function assertCalls(array $expected, array $actual, string $message = ''): void 47 { 48 $this->assertEquals($expected, array_map($this->stripByteIndex(...), $actual), $message); 49 } 50 51 /** 52 * Remove the byte index from a single handler call 53 * 54 * Recursively processes nested calls (e.g. footnotes). 55 * 56 * @param array $call a single handler call [method, args, byteindex] 57 * @return array the call with the byte index removed 58 */ 59 private function stripByteIndex(array $call): array 60 { 61 unset($call[2]); 62 if ($call[0] === 'nest') { 63 $call[1][0] = array_map($this->stripByteIndex(...), $call[1][0]); 64 } 65 return $call; 66 } 67} 68