ILIAS  trunk Revision v13.0_alpha-62-g3b72d83f2e5
ilObjLanguageExtGUITest.php
Go to the documentation of this file.
1<?php
2
19declare(strict_types=1);
20
21use PHPUnit\Framework\Attributes\DataProvider;
22use PHPUnit\Framework\TestCase;
23
24class ilObjLanguageExtGUITest extends TestCase
25{
27
29
32 {
33 $gui = $this->newGuiWithoutConstructor(ilObjLanguageExtGUI::class);
34
35 $this->assertSame(
36 ['save', 'upload', 'maintainExecute', 'saveSettings', 'saveNewEntry'],
37 $gui->getUnsafeGetCommands()
38 );
39 }
40
42 public function testGetSafePostCommandsIsEmpty(): void
43 {
44 $gui = $this->newGuiWithoutConstructor(ilObjLanguageExtGUI::class);
45
46 $this->assertSame([], $gui->getSafePostCommands());
47 }
48
50 public static function importedMessageProvider(): array
51 {
52 return [
53 'HTML-significant characters are escaped' => [
54 '<script>x</script>.lang',
55 static function (self $test, string $message): void {
56 $test->assertStringNotContainsString('<script>', $message);
57 $test->assertStringContainsString('&lt;script&gt;', $message);
58 $test->assertStringContainsString('&lt;/script&gt;', $message);
59 },
60 ],
61 'an ordinary file name is left unchanged' => [
62 'ilias_de.lang',
63 static function (self $test, string $message): void {
64 $test->assertStringContainsString('ilias_de.lang', $message);
65 },
66 ],
67 ];
68 }
69
71 #[DataProvider('importedMessageProvider')]
73 string $file_name,
74 \Closure $assertOnMessage
75 ): void {
76 $lng = $this->createStub(ilLanguage::class);
77 $lng->method('txt')->willReturnCallback(
78 static fn(string $key): string => $key === 'language_file_imported' ? 'Imported %s.' : $key
79 );
80
81 $gui = $this->newGuiWithoutConstructor(ilObjLanguageExtGUI::class);
82 $this->inject($gui, 'lng', $lng);
83 $this->inject($gui, 'refinery', new \ILIAS\Refinery\Factory(
84 $this->createStub(\ILIAS\Data\Factory::class),
85 $this->createStub(\ILIAS\Language\Language::class)
86 ));
87
88 $method = new ReflectionMethod(ilObjLanguageExtGUI::class, 'importedMessage');
89 $message = $method->invoke($gui, $file_name);
90
91 $this->assertStringStartsWith('Imported ', $message);
92 $assertOnMessage($this, $message);
93 }
94
96 private function callRemarkOf(array $comments, string $name): string
97 {
98 $gui = $this->newGuiWithoutConstructor(ilObjLanguageExtGUI::class);
99 $this->inject($gui, 'lng', $this->createStub(ilLanguage::class));
100
101 return (new ReflectionMethod(ilObjLanguageExtGUI::class, 'remarkOf'))->invoke($gui, $comments, $name);
102 }
103
105 {
106 $this->assertSame(
107 'Bitte prüfen',
108 $this->callRemarkOf(['pilot#:#greeting' => 'Bitte prüfen'], 'pilot#:#greeting')
109 );
110 }
111
114 {
115 $this->assertSame(
116 'Bitte prüfen',
117 $this->callRemarkOf(['pilot#:#item' => 'Bitte prüfen'], 'pilot#:#item [1]')
118 );
119 }
120
123 {
124 $this->assertSame(
125 'Form-spezifisch',
126 $this->callRemarkOf(
127 ['pilot#:#item' => 'Identifier-Bemerkung', 'pilot#:#item [1]' => 'Form-spezifisch'],
128 'pilot#:#item [1]'
129 )
130 );
131 }
132
134 {
135 $this->assertSame('', $this->callRemarkOf([], 'pilot#:#unknown'));
136 $this->assertSame('', $this->callRemarkOf(['pilot#:#other' => 'X'], 'pilot#:#greeting'));
137 }
138
141 {
142 $this->assertSame('', $this->callRemarkOf(['pilot#:#item' => 'Bemerkung'], 'pilot#:#greeting'));
143 }
144
146 public static function missingTopicProvider(): array
147 {
148 return [
149 'HTML' => ['<b>x</b>', '%3Cb%3Ex%3C%2Fb%3E', '&lt;b&gt;x&lt;/b&gt;'],
150 'quote, ampersand, space and hash' => ['a"b&c d#e', 'a%22b%26c%20d%23e', 'a&quot;b&amp;c d#e'],
151 'a numeric topic arrives as int' => [123, '123', '123'],
152 ];
153 }
154
156 #[DataProvider('missingTopicProvider')]
157 public function testBuildMissingEntriesEscapesTheTopicForTextParameterAndLink(string|int $topic, string $eid, string $text): void
158 {
159 $parameters = [];
160 $ctrl = $this->createStub(ilCtrl::class);
161 $ctrl->method('setParameter')->willReturnCallback(
162 static function (object $gui, string $name, mixed $value) use (&$parameters): void {
163 $parameters[] = [$name, $value];
164 }
165 );
166 $ctrl->method('getLinkTarget')->willReturn('ilias.php?a=1&b="2"');
167 $GLOBALS['DIC'] = new \ILIAS\DI\Container();
168 $GLOBALS['DIC']['ilCtrl'] = $ctrl;
169 $gui = $this->newGuiWithoutConstructor(ilObjLanguageExtGUI::class);
170 $this->inject($gui, 'lng', $this->createLanguageMockReturningTopicAsIs());
171 $this->inject($gui, 'refinery', new \ILIAS\Refinery\Factory(
172 $this->createStub(\ILIAS\Data\Factory::class),
173 $this->createStub(\ILIAS\Language\Language::class)
174 ));
175
176 $html = (new ReflectionMethod(ilObjLanguageExtGUI::class, 'buildMissingEntries'))->invoke($gui, [$topic]);
177
178 $this->assertSame([['eid', $eid], ['eid', '']], $parameters);
179 $this->assertStringContainsString('<li>' . $text . ' <a href="ilias.php&#x3F;a&#x3D;1&amp;b&#x3D;&quot;2&quot;">', $html);
180 }
181}
trait RestoresProcessState
Whatever a test does to the process (locale, LANGUAGE/LC_*, LOCPATH, the static state of the runtime ...
language handling
testRemarkOfFallsBackToTheIdentifiersCommentForAPluralFormKeyWithoutItsOwn()
A plural form ("identifier [form]") without a comment of its own falls back to the comment of its ide...
testGetUnsafeGetCommandsListsEveryDataChangingCommand()
A data-changing command missing here would be triggerable via GET without the CSRF token.
callRemarkOf(array $comments, string $name)
testGetSafePostCommandsIsEmpty()
No POST command is exempt from the CSRF token.
testRemarkOfIsEmptyForAnOrdinaryIdentifierWithoutAComment()
An ordinary identifier without a comment must not fall back to anything.
testImportedMessageEscapesHtmlSignificantCharactersAndKeepsTheLngText(string $file_name, \Closure $assertOnMessage)
Calls the real private importedMessage() via reflection: an uploaded file name must come out HTML-esc...
testRemarkOfPrefersThePluralFormsOwnCommentOverTheIdentifiersWhenBothArePresent()
A plural form's own comment wins over the identifier's.
testBuildMissingEntriesEscapesTheTopicForTextParameterAndLink(string|int $topic, string $eid, string $text)
The list text is HTML-escaped, the "eid" parameter URL-encoded and the link target safe inside the hr...
trait ilObjLanguageExtGUITestFixture
createLanguageMockReturningTopicAsIs(array $installed_languages=[])
newGuiWithoutConstructor(string $class)
@template T of object
inject(object $gui, string $property_name, mixed $value)
For a mock the property is looked up on its declaring class: a plain ReflectionProperty on the mock c...
Interface Observer \BackgroundTasks Contains several chained tasks and infos about them.
global $lng
Definition: privfeed.php:26
$comments
$GLOBALS["DIC"]
Definition: wac.php:66
$text
Definition: xapiexit.php:21