diff --git a/composer-require-checker.json b/composer-require-checker.json
index 3e87a142..7878977e 100644
--- a/composer-require-checker.json
+++ b/composer-require-checker.json
@@ -8,7 +8,6 @@
"Symfony\\Bridge\\Twig\\TokenParser\\TransTokenParser",
"Symfony\\UX\\TwigComponent\\Twig\\ComponentTokenParser",
"Symfony\\UX\\TwigComponent\\Twig\\PropsTokenParser",
- "Twig\\Extra\\Cache\\TokenParser\\CacheTokenParser",
- "\\SimpleXMLElement"
+ "Twig\\Extra\\Cache\\TokenParser\\CacheTokenParser"
]
}
diff --git a/src/Report/Reporter/CheckstyleReporter.php b/src/Report/Reporter/CheckstyleReporter.php
index 880b8dd8..f37f1219 100644
--- a/src/Report/Reporter/CheckstyleReporter.php
+++ b/src/Report/Reporter/CheckstyleReporter.php
@@ -8,35 +8,52 @@
use TwigCsFixer\Report\Report;
use TwigCsFixer\Report\SniffViolation;
-/**
- * Human-readable output with context.
- */
final class CheckstyleReporter implements ReporterInterface
{
public const NAME = 'checkstyle';
public function display(OutputInterface $output, Report $report, ?string $level = null): void
{
- $checkstyle = new \SimpleXMLElement('');
+ $text = ''."\n";
+
+ $text .= ''."\n";
foreach ($report->getFiles() as $file) {
$fileMessages = $report->getMessages($file, $level);
- if (\count($fileMessages) > 0) {
- /** @var \SimpleXMLElement $fileNode */
- $fileNode = $checkstyle->addChild('file');
- $fileNode->addAttribute('name', $file);
-
- foreach ($fileMessages as $message) {
- /** @var \SimpleXMLElement $violation */
- $violation = $fileNode->addChild('violation');
- $violation->addAttribute('column', (string) $message->getLinePosition());
- $violation->addAttribute('severity', strtolower(SniffViolation::getLevelAsString($message->getLevel())));
- $violation->addAttribute('message', $message->getMessage());
- $violation->addAttribute('source', $message->getSniffName() ?? '');
+ if (0 === \count($fileMessages)) {
+ continue;
+ }
+
+ $text .= ' '."\n";
+ foreach ($fileMessages as $message) {
+ $line = (string) $message->getLine();
+ $linePosition = (string) $message->getLinePosition();
+ $sniffName = $message->getSniffName();
+
+ $text .= ' getLevel())).'"';
+ $text .= ' message="'.$this->xmlEncode($message->getMessage()).'"';
+ if (null !== $sniffName) {
+ $text .= ' source="'.$sniffName.'"';
+ }
+ $text .= '/>'."\n";
}
+ $text .= ' '."\n";
}
- $output->writeln((string) $checkstyle->asXML());
+ $text .= ''."\n";
+
+ $output->writeln($text);
+ }
+
+ private function xmlEncode(string $data): string
+ {
+ return htmlspecialchars($data, \ENT_XML1 | \ENT_QUOTES);
}
}
diff --git a/tests/Command/TwigCsFixerCommandTest.php b/tests/Command/TwigCsFixerCommandTest.php
index 02c3981b..e8945577 100644
--- a/tests/Command/TwigCsFixerCommandTest.php
+++ b/tests/Command/TwigCsFixerCommandTest.php
@@ -116,7 +116,7 @@ public function testExecuteWithReportOption(): void
$commandTester = new CommandTester($command);
$commandTester->execute([
- 'paths' => [$this->getTmpPath(__DIR__.'/Fixtures/file.twig')],
+ 'paths' => [$this->getTmpPath(__DIR__.'/Fixtures')],
'--no-cache' => true, // To avoid cache output
'--report' => 'null',
]);
diff --git a/tests/Report/Formatter/CheckstyleReporterTest.php b/tests/Report/Formatter/CheckstyleReporterTest.php
new file mode 100644
index 00000000..1198030a
--- /dev/null
+++ b/tests/Report/Formatter/CheckstyleReporterTest.php
@@ -0,0 +1,82 @@
+addMessage($violation0);
+ $violation1 = new SniffViolation(SniffViolation::LEVEL_WARNING, 'Warning', $file, 2, 22, 'WarningSniff');
+ $report->addMessage($violation1);
+ $violation2 = new SniffViolation(SniffViolation::LEVEL_ERROR, 'Error', $file, 3, 33, 'ErrorSniff');
+ $report->addMessage($violation2);
+ $violation3 = new SniffViolation(SniffViolation::LEVEL_FATAL, 'Fatal', $file);
+ $report->addMessage($violation3);
+
+ $output = new BufferedOutput(OutputInterface::VERBOSITY_NORMAL, true);
+ $textFormatter->display($output, $report, $level);
+
+ $text = $output->fetch();
+ static::assertStringContainsString($expected, $text);
+ }
+
+ /**
+ * @return iterable
+ */
+ public static function displayDataProvider(): iterable
+ {
+ yield [
+ sprintf(
+ <<
+
+
+
+
+
+
+
+
+ EOD,
+ __DIR__
+ ),
+ null,
+ ];
+
+ yield [
+ sprintf(
+ <<
+
+
+
+
+
+
+ EOD,
+ __DIR__
+ ),
+ Report::MESSAGE_TYPE_ERROR,
+ ];
+ }
+}
diff --git a/tests/Report/ReporterFactoryTest.php b/tests/Report/ReporterFactoryTest.php
index d01c0bef..289e5dba 100644
--- a/tests/Report/ReporterFactoryTest.php
+++ b/tests/Report/ReporterFactoryTest.php
@@ -5,6 +5,7 @@
namespace TwigCsFixer\Tests\Report;
use PHPUnit\Framework\TestCase;
+use TwigCsFixer\Report\Reporter\CheckstyleReporter;
use TwigCsFixer\Report\Reporter\NullReporter;
use TwigCsFixer\Report\Reporter\TextReporter;
use TwigCsFixer\Report\ReporterFactory;
@@ -18,6 +19,7 @@ public function testGetReporter(): void
static::assertInstanceOf(TextReporter::class, $reporterFactory->getReporter());
static::assertInstanceOf(TextReporter::class, $reporterFactory->getReporter(TextReporter::NAME));
static::assertInstanceOf(NullReporter::class, $reporterFactory->getReporter(NullReporter::NAME));
+ static::assertInstanceOf(CheckstyleReporter::class, $reporterFactory->getReporter(CheckstyleReporter::NAME));
}
public function testGetMessageForAnotherFile(): void