ILIAS  trunk Revision v13.0_alpha-62-g3b72d83f2e5
LanguageInstallationManagerMigratedRemarksTest.php
Go to the documentation of this file.
1<?php
2
19declare(strict_types=1);
20
31use PHPUnit\Framework\Attributes\DataProvider;
32use PHPUnit\Framework\TestCase;
33
35{
42 private function callMigratedModuleRemarks(
43 array $shipped_migrated_modules,
44 array $customized_remarks = [],
45 array $shipped_line_comments = [],
46 array $overlay_only_modules = []
47 ): array {
48 $manager = $this->manager();
49 $method = new ReflectionMethod(LanguageInstallationManager::class, 'migratedModuleRemarks');
50
51 return $method->invoke(
52 $manager,
53 'de',
54 $shipped_migrated_modules,
55 $customized_remarks,
56 $shipped_line_comments,
57 $this->root . '/client-data',
58 $overlay_only_modules
59 );
60 }
61
62 private function seedOverlayWithRemark(string $identifier, string $value, string $remark): void
63 {
64 $catalog = new TranslationCatalog();
65 $entry = new \ILIAS\Language\ComponentTranslation\Catalog\TranslationEntry(self::MODULE, $identifier);
66 $entry->translate($value);
67 LocalChangeComments::setRemark($entry, $remark);
68 $catalog->add($entry);
69 MigratedPoFixture::writePair($this->overlayBase(), $catalog);
70 }
71
76 {
77 $this->shipPo(['greeting' => 'Hallo']);
78 $this->seedOverlayWithRemark('greeting', 'Hallo', 'Overlay-Bemerkung');
79 $this->collation_rows = [
80 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'DB-Bemerkung'],
81 ];
82
83 $remarks = $this->callMigratedModuleRemarks(
84 [self::MODULE => ['greeting' => 'Hallo']],
85 [self::MODULE => ['greeting' => 'Customizing-Bemerkung']]
86 );
87
88 $this->assertSame(['greeting' => 'Customizing-Bemerkung'], $remarks[self::MODULE]);
89 }
90
92 {
93 $this->shipPo(['greeting' => 'Hallo']);
94 $this->seedOverlayWithRemark('greeting', 'Hallo', 'Overlay-Bemerkung');
95 $this->collation_rows = [
96 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'DB-Bemerkung'],
97 ];
98
99 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Hallo']]);
100
101 $this->assertSame(['greeting' => 'Overlay-Bemerkung'], $remarks[self::MODULE]);
102 }
103
105 {
106 $this->shipPo(['greeting' => 'Hallo']);
107 $this->collation_rows = [
108 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'DB-Bemerkung'],
109 ];
110
111 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Hallo']]);
112
113 $this->assertSame(['greeting' => 'DB-Bemerkung'], $remarks[self::MODULE]);
114 }
115
118 {
119 $this->shipPo(['greeting' => 'Hallo', 'farewell' => 'Tschüss']);
120 $this->seedOverlayWithRemark('greeting', 'Hallo', 'Overlay-Bemerkung');
121 $this->collation_rows = [
122 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'DB-Bemerkung'],
123 ['module' => self::MODULE, 'identifier' => 'farewell', 'remarks' => 'DB-Bemerkung 2'],
124 ];
125
126 $remarks = $this->callMigratedModuleRemarks(
127 [self::MODULE => ['greeting' => 'Hallo', 'farewell' => 'Tschüss']],
128 [self::MODULE => ['customized' => 'Customizing-Bemerkung']],
129 [],
130 [self::MODULE]
131 );
132
133 $this->assertSame(['greeting' => 'Overlay-Bemerkung', 'customized' => 'Customizing-Bemerkung'], $remarks[self::MODULE]);
134 }
135
137 {
138 $this->shipPo(['greeting' => 'Hallo']);
139 $this->collation_rows = [];
140
141 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Hallo']]);
142
143 $this->assertSame([], $remarks[self::MODULE] ?? []);
144 }
145
150 {
151 $this->shipPo(['greeting' => 'Hallo']);
152 $this->collation_rows = [
153 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'Alter Zeilenkommentar'],
154 ];
155
156 $remarks = $this->callMigratedModuleRemarks(
157 [self::MODULE => ['greeting' => 'Hallo']],
158 [],
159 [self::MODULE => ['greeting' => 'Alter Zeilenkommentar']]
160 );
161
162 $this->assertArrayNotHasKey('greeting', $remarks[self::MODULE] ?? []);
163 }
164
169 {
170 $catalog = new TranslationCatalog();
171 $entry = new \ILIAS\Language\ComponentTranslation\Catalog\TranslationEntry(self::MODULE, 'greeting');
172 $entry->translate('Hallo');
173 $entry->addExtractedComment('PO-Notiz');
174 $catalog->add($entry);
175 MigratedPoFixture::writePo($this->root . '/components/pilot/lang/pilot_de.po', $catalog);
176 $this->collation_rows = [
177 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'PO-Notiz'],
178 ];
179
180 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Hallo']]);
181
182 $this->assertArrayNotHasKey('greeting', $remarks[self::MODULE] ?? []);
183 }
184
187 {
188 $catalog = new TranslationCatalog();
189 $entry = new \ILIAS\Language\ComponentTranslation\Catalog\TranslationEntry(self::MODULE, 'greeting');
190 $entry->translate('Hallo');
191 $entry->addTranslatorNote('Eigene Notiz');
192 $catalog->add($entry);
193 MigratedPoFixture::writePo($this->root . '/components/pilot/lang/pilot_de.po', $catalog);
194 $this->collation_rows = [
195 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'Eigene Notiz'],
196 ];
197 $overlay = MigratedPoFixture::catalog(self::MODULE, ['greeting' => 'Hallo']);
198 LocalChangeComments::setRemark($overlay->find(self::MODULE, 'greeting'), ' Eigene Notiz ');
199 MigratedPoFixture::writePair($this->overlayBase(), $overlay);
200
201 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Hallo']]);
202
203 $this->assertArrayNotHasKey('greeting', $remarks[self::MODULE] ?? []);
204 }
205
211 {
212 $catalog = new TranslationCatalog();
213 foreach (['greeting' => 'Merk', 'other' => 'Notiz'] as $identifier => $note) {
214 $entry = new \ILIAS\Language\ComponentTranslation\Catalog\TranslationEntry(self::MODULE, $identifier);
215 $entry->translate('Wert');
216 $entry->addExtractedComment($note);
217 $catalog->add($entry);
218 }
219 MigratedPoFixture::writePo($this->root . '/components/pilot/lang/pilot_de.po', $catalog);
220 $overlay = MigratedPoFixture::catalog(self::MODULE, ['greeting' => 'Wert', 'other' => 'Wert']);
221 LocalChangeComments::setRemark($overlay->find(self::MODULE, 'greeting'), ' Merk ');
222 LocalChangeComments::setRemark($overlay->find(self::MODULE, 'other'), 'Eigene Bemerkung');
223 MigratedPoFixture::writePair($this->overlayBase(), $overlay);
224
225 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Wert', 'other' => 'Wert']]);
226
227 $this->assertSame(['other' => 'Eigene Bemerkung'], $remarks[self::MODULE]);
228 }
229
235 {
236 $this->shipPo(['greeting' => 'Hallo']);
237 $directories = new LanguageFileDirectoryManager(new CustomizingLanguageFileDirectory(), $this->directory);
238 MigratedLanguageFileSync::sync($directories, $this->root, 'de', self::MODULE, ['greeting' => 'Servus'], $this->root . '/client-data', false, null, ['greeting' => 'Merk']);
239 $this->assertSame('Merk', MigratedLanguageFileSync::loadRemarks($directories, 'de', self::MODULE, $this->root . '/client-data', $this->root)['greeting'] ?? null, 'precondition');
240
241 mkdir($this->root . '/backup');
242 $result = \ILIAS\Language\ComponentTranslation\ShippedPoMerger::merge($directories, $this->root, 'de', $this->root . '/client-data', $this->root . '/backup');
243 $this->assertSame([], $result['skipped'], 'precondition');
244 MigratedPoFixture::build($directories, $this->root);
245 $this->manager()->insertLanguageForInstallation('de');
246
247 $this->assertFileDoesNotExist($this->overlayBase() . '.po');
248 $shipped = MigratedPoFixture::readPo($this->root . '/components/pilot/lang/pilot_de.po')->find(self::MODULE, 'greeting');
249 $this->assertSame('Servus', $shipped?->getTranslation());
250 $this->assertSame(['Merk'], $shipped->getTranslatorComments());
251 $this->assertSame('Servus', $this->lngModules()[self::MODULE]['greeting']);
252 $this->assertSame('Servus', (new \ILIAS\Language\ComponentTranslation\TranslationGettextRepository())->getText(self::MODULE, 'de', 'greeting', $this->root . '/client-data'));
253 }
254
260 {
261 $this->shipPo(['greeting' => 'Hallo']);
262 $this->collation_rows = [
263 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => '28 08 2012 new variable'],
264 ];
265
266 $remarks = $this->callMigratedModuleRemarks([self::MODULE => ['greeting' => 'Hallo']]);
267
268 $this->assertArrayNotHasKey('greeting', $remarks[self::MODULE] ?? []);
269 }
270
275 {
276 $this->shipPo(['greeting' => 'Hallo']);
277 $this->collation_rows = [
278 ['module' => self::MODULE, 'identifier' => 'greeting', 'remarks' => 'Echte Admin-Bemerkung'],
279 ];
280
281 $remarks = $this->callMigratedModuleRemarks(
282 [self::MODULE => ['greeting' => 'Hallo']],
283 [],
284 [self::MODULE => ['greeting' => 'Ganz anderer Zeilenkommentar']]
285 );
286
287 $this->assertSame('Echte Admin-Bemerkung', $remarks[self::MODULE]['greeting'] ?? null);
288 }
289}
An in-memory gettext catalog (header block plus messages) and the only place of the component that re...
Tracks per overlay entry whether the current value still matches the value of the shipped ....
Reads the shipped .po of a migrated module and maintains its per-installation overlay: the ....
static merge(LanguageFileDirectoryManager $language_file_directory_manager, string $ilias_absolute_path, string $lang_key, ?string $client_data_dir, string $backup_directory, ?\Closure $after_module=null)
The module array just written to lng_modules could not be read back - almost always a wrong collation...
Write access to the language installation: installing, flushing and registering languages in the data...
Fixtures of the LanguageInstallationManager tests for modules migrated to PO/MO ("pilot").
manager(?\Closure $client_data_dir_resolver=null, ?\Closure $language_cache_invalidator=null, bool $with_resolver=true, bool $with_logger=true, ?LoggerInterface $logger=null)
callMigratedModuleRemarks(array $shipped_migrated_modules, array $customized_remarks=[], array $shipped_line_comments=[], array $overlay_only_modules=[])
testAMergedValueAndRemarkLeaveTheOverlayWithTheUpdateAfterTheBuild()
Whole way of a local change with a remark: "merge" takes value and remark into the shipped ....
testMigratedModuleRemarksExcludesADatedNewVariableMarkerRemark()
A dated "... new variable" placeholder (the legacy "not translated yet" marker) is never an administr...
testMigratedModuleRemarksExcludesALngDataRemarkThatMatchesTheShippedPoNote()
Same exclusion for the shipped .po's own "#." note of the identifier.
seedOverlayWithRemark(string $identifier, string $value, string $remark)
testMigratedModuleRemarksExcludesALngDataRemarkThatMatchesTheShippedTranslatorNote()
A lng_data remark equal to the shipped translator note ("# ") is no remark.
testMigratedModuleRemarksDropsAnOverlayRemarkTheShippedPoHasAsNoteNow()
A remark taken over by "merge" is a note of the shipped entry now: an overlay remark equal to it (tri...
testMigratedModuleRemarksExcludesALngDataRemarkThatMatchesTheShippedLineComment()
A lng_data remark that is only the carried-over "###" comment of the pre-migration ....
testMigratedModuleRemarksKeepsALngDataRemarkThatDiffersFromEveryShippedComment()
A lng_data remark that differs from every shipped comment is a real edit and is taken over.
testMigratedModuleRemarksOfAnOverlayOnlyModuleIgnoreLngData()
A module whose overlay is the only source: its lng_data remarks are not read, the overlay and the cus...
testMigratedModuleRemarksMergesLngDataOverlayAndCustomizingWithCustomizingWinning()
Merge precedence: lng_data is the base, the overlay overrides it, the customizing file overrides both...
static writePair(string $base_path, TranslationCatalog $catalog)
Writes "<base>.po" and, like MigratedLanguageFileSync::sync(), its compiled revision named by current...
static catalog(string $module, array $entries)
static writePo(string $file, TranslationCatalog $catalog)
static readPo(string $file)
static build(LanguageFileDirectoryManager $manager, string $ilias_absolute_path)
Builds the shipped .po files of $manager below $ilias_absolute_path into the artifact directory of re...
A directory of language files with a path and a prefix for them.
Read-only access to the installed languages (database) and the available or valid language files (fil...
Interface Observer \BackgroundTasks Contains several chained tasks and infos about them.