Load original file metadata when loading Xliff 1.2 files

This commit is contained in:
Pablo Borowicz 2018-11-08 18:05:28 -03:00 committed by Fabien Potencier
parent 006dacd18d
commit 4073319d0f
4 changed files with 138 additions and 29 deletions

View File

@ -1,6 +1,11 @@
CHANGELOG
=========
4.3.0
-----
* Improved Xliff 1.2 loader to load the original file's metadata
4.2.0
-----

View File

@ -82,38 +82,50 @@ class XliffFileLoader implements LoaderInterface
$xml = simplexml_import_dom($dom);
$encoding = strtoupper($dom->encoding);
$xml->registerXPathNamespace('xliff', 'urn:oasis:names:tc:xliff:document:1.2');
foreach ($xml->xpath('//xliff:trans-unit') as $translation) {
$attributes = $translation->attributes();
$namespace = 'urn:oasis:names:tc:xliff:document:1.2';
$xml->registerXPathNamespace('xliff', $namespace);
if (!(isset($attributes['resname']) || isset($translation->source))) {
continue;
}
foreach ($xml->xpath('//xliff:file') as $file) {
$fileAttributes = $file->attributes();
$source = isset($attributes['resname']) && $attributes['resname'] ? $attributes['resname'] : $translation->source;
// If the xlf file has another encoding specified, try to convert it because
// simple_xml will always return utf-8 encoded values
$target = $this->utf8ToCharset((string) (isset($translation->target) ? $translation->target : $translation->source), $encoding);
$file->registerXPathNamespace('xliff', $namespace);
$catalogue->set((string) $source, $target, $domain);
foreach ($file->xpath('.//xliff:trans-unit') as $translation) {
$attributes = $translation->attributes();
$metadata = array();
if ($notes = $this->parseNotesMetadata($translation->note, $encoding)) {
$metadata['notes'] = $notes;
}
if (isset($translation->target) && $translation->target->attributes()) {
$metadata['target-attributes'] = array();
foreach ($translation->target->attributes() as $key => $value) {
$metadata['target-attributes'][$key] = (string) $value;
if (!(isset($attributes['resname']) || isset($translation->source))) {
continue;
}
}
if (isset($attributes['id'])) {
$metadata['id'] = (string) $attributes['id'];
}
$source = isset($attributes['resname']) && $attributes['resname'] ? $attributes['resname'] : $translation->source;
// If the xlf file has another encoding specified, try to convert it because
// simple_xml will always return utf-8 encoded values
$target = $this->utf8ToCharset((string) ($translation->target ?? $translation->source), $encoding);
$catalogue->setMetadata((string) $source, $metadata, $domain);
$catalogue->set((string) $source, $target, $domain);
$metadata = array(
'file' => array(
'original' => (string) $fileAttributes['original'],
),
);
if ($notes = $this->parseNotesMetadata($translation->note, $encoding)) {
$metadata['notes'] = $notes;
}
if (isset($translation->target) && $translation->target->attributes()) {
$metadata['target-attributes'] = array();
foreach ($translation->target->attributes() as $key => $value) {
$metadata['target-attributes'][$key] = (string) $value;
}
}
if (isset($attributes['id'])) {
$metadata['id'] = (string) $attributes['id'];
}
$catalogue->setMetadata((string) $source, $metadata, $domain);
}
}
}

View File

@ -84,7 +84,16 @@ class XliffFileLoaderTest extends TestCase
$this->assertEquals(utf8_decode('föö'), $catalogue->get('bar', 'domain1'));
$this->assertEquals(utf8_decode('bär'), $catalogue->get('foo', 'domain1'));
$this->assertEquals(array('notes' => array(array('content' => utf8_decode('bäz'))), 'id' => '1'), $catalogue->getMetadata('foo', 'domain1'));
$this->assertEquals(
array(
'notes' => array(array('content' => utf8_decode('bäz'))),
'id' => '1',
'file' => array(
'original' => 'file.ext',
),
),
$catalogue->getMetadata('foo', 'domain1')
);
}
public function testTargetAttributesAreStoredCorrectly()
@ -164,11 +173,41 @@ class XliffFileLoaderTest extends TestCase
$loader = new XliffFileLoader();
$catalogue = $loader->load(__DIR__.'/../fixtures/withnote.xlf', 'en', 'domain1');
$this->assertEquals(array('notes' => array(array('priority' => 1, 'content' => 'foo')), 'id' => '1'), $catalogue->getMetadata('foo', 'domain1'));
$this->assertEquals(
array(
'notes' => array(array('priority' => 1, 'content' => 'foo')),
'id' => '1',
'file' => array(
'original' => 'file.ext',
),
),
$catalogue->getMetadata('foo', 'domain1')
);
// message without target
$this->assertEquals(array('notes' => array(array('content' => 'bar', 'from' => 'foo')), 'id' => '2'), $catalogue->getMetadata('extra', 'domain1'));
$this->assertEquals(
array(
'notes' => array(array('content' => 'bar', 'from' => 'foo')),
'id' => '2',
'file' => array(
'original' => 'file.ext',
),
),
$catalogue->getMetadata('extra', 'domain1')
);
// message with empty target
$this->assertEquals(array('notes' => array(array('content' => 'baz'), array('priority' => 2, 'from' => 'bar', 'content' => 'qux')), 'id' => '123'), $catalogue->getMetadata('key', 'domain1'));
$this->assertEquals(
array(
'notes' => array(
array('content' => 'baz'),
array('priority' => 2, 'from' => 'bar', 'content' => 'qux'),
),
'id' => '123',
'file' => array(
'original' => 'file.ext',
),
),
$catalogue->getMetadata('key', 'domain1')
);
}
public function testLoadVersion2()
@ -257,4 +296,30 @@ class XliffFileLoaderTest extends TestCase
$this->assertSame('processed', $metadata['notes'][0]['category']);
$this->assertSame('true', $metadata['notes'][0]['content']);
}
public function testLoadWithMultipleFileNodes()
{
$loader = new XliffFileLoader();
$catalogue = $loader->load(__DIR__.'/../fixtures/resources-multi-files.xlf', 'en', 'domain1');
$this->assertEquals(
array(
'id' => '1',
'file' => array(
'original' => 'file.ext',
),
),
$catalogue->getMetadata('foo', 'domain1')
);
$this->assertEquals(
array(
'notes' => array(array('content' => 'note')),
'id' => '4',
'file' => array(
'original' => 'otherfile.ext',
),
),
$catalogue->getMetadata('test', 'domain1')
);
}
}

View File

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="utf-8"?>
<xliff xmlns="urn:oasis:names:tc:xliff:document:1.2" version="1.2">
<file source-language="en" datatype="plaintext" original="file.ext">
<body>
<trans-unit id="1">
<source>foo</source>
<target>bar</target>
</trans-unit>
</body>
</file>
<file source-language="en" datatype="plaintext" original="otherfile.ext">
<body>
<trans-unit id="2">
<source>extra</source>
</trans-unit>
<trans-unit id="3">
<source>key</source>
<target></target>
</trans-unit>
<trans-unit id="4">
<source>test</source>
<target>with</target>
<note>note</note>
</trans-unit>
</body>
</file>
</xliff>