From dc47e186586d8ffb4f85af66927c25e6bde87986 Mon Sep 17 00:00:00 2001
From: Florian Weber <florian@webflo.org>
Date: Wed, 13 Jun 2012 16:20:08 +0200
Subject: [PATCH] Issue #1632384.

---
 .../Drupal/locale/Tests/LocaleXmlParserTest.php    |   28 ++++++++
 core/modules/locale/locale.compare.inc             |    2 +-
 core/modules/locale/locale.fetch.inc               |   76 ++++++++++++++++++--
 core/modules/locale/tests/test.l10n_server.xml     |   60 ++++++++++++++++
 4 files changed, 161 insertions(+), 5 deletions(-)
 create mode 100644 core/modules/locale/lib/Drupal/locale/Tests/LocaleXmlParserTest.php
 create mode 100644 core/modules/locale/tests/test.l10n_server.xml

diff --git a/core/modules/locale/lib/Drupal/locale/Tests/LocaleXmlParserTest.php b/core/modules/locale/lib/Drupal/locale/Tests/LocaleXmlParserTest.php
new file mode 100644
index 0000000..e6f18b7
--- /dev/null
+++ b/core/modules/locale/lib/Drupal/locale/Tests/LocaleXmlParserTest.php
@@ -0,0 +1,28 @@
+<?php
+
+namespace Drupal\locale\Tests;
+
+use Drupal\simpletest\UnitTestBase;
+
+class LocaleXmlParserTest extends UnitTestBase {
+  public static function getInfo() {
+    return array(
+      'name' => 'Parse XML',
+      'description' => 'Test XML parser for available languages.',
+      'group' => 'Locale',
+    );
+  }
+
+  function testXmlParser() {
+    module_load_include('inc', 'locale', 'locale.fetch');
+
+    $path = DRUPAL_ROOT . '/' . drupal_get_path('module', 'locale') . '/tests/test.l10n_server.xml';
+    $file = file_get_contents($path);
+
+    $result = locale_translation_parse_xml($file);
+    $this->assertTrue(is_array($result), t('Parsed XML to an array.'));
+    $this->assertNotNull($result['languages'], t('The array contains languages.'));
+    $this->assertIdentical(10, count($result['languages']), t('The array contains the correct amount of languages.'));
+    $this->assertNotNull($result['languages']['af'], t('Language %language is defined.', array('%language' => $result['languages']['af']['name'])));
+  }
+}
diff --git a/core/modules/locale/locale.compare.inc b/core/modules/locale/locale.compare.inc
index 3a48a94..b055ec2 100644
--- a/core/modules/locale/locale.compare.inc
+++ b/core/modules/locale/locale.compare.inc
@@ -154,7 +154,7 @@ function locale_build_projects() {
 
 /**
  * Fetch an array of projects for translation update.
- * 
+ *
  * @return
  *   Array of project data including .info file data.
  */
diff --git a/core/modules/locale/locale.fetch.inc b/core/modules/locale/locale.fetch.inc
index 8f6d01c..7e00eb4 100644
--- a/core/modules/locale/locale.fetch.inc
+++ b/core/modules/locale/locale.fetch.inc
@@ -1,9 +1,77 @@
 <?php
 
 /**
- * @todo
- * Based on l10n_update_get_server().
+ * @file
+ * Fetch and parse the list of available languages from a translation server.
  */
-function locale_get_server($url) {
-  // @todo convert l10n_update.parser.inc to PHP5 code. See update.fetch.inc.
+
+/**
+ * Get server information.
+ */
+function locale_translation_get_server($server) {
+  // Fetch up to date information if available.
+  if (!empty($server['server_url']) && $fetch = locale_translation_fetch_server($server['server_url'])) {
+    $server = array_merge($server, $fetch);
+  }
+  // If we have an update url this is ok, otherwise we return none.
+  if (!empty($server['update_url'])) {
+    return $server;
+  }
+  else {
+    return FALSE;
+  }
+}
+
+/**
+ * Fetch remote server metadata from a server URL.
+ *
+ * @param $server_url
+ *
+ * @return
+ *   Array of parsed data about available languages, or FALSE if there was an
+ *   error parsing the string.
+ */
+function locale_translation_fetch_server($url) {
+  $xml = drupal_http_request($url);
+  if (isset($xml->data)) {
+    return locale_translation_parse_xml($xml->data);
+  }
+  else {
+    return FALSE;
+  }
+}
+
+/**
+ * Parse the raw xml in a list of languages with server metadata.
+ *
+ * @param $raw_xml
+ *   A raw XML string of available languages.
+ *
+ * @return
+ *   Array of parsed data about available languages, or NULL if there was an
+ *   error parsing the string.
+ */
+function locale_translation_parse_xml($raw_xml) {
+  try {
+    $xml = new SimpleXMLElement($raw_xml);
+  } catch (Exception $e) {
+    // SimpleXMLElement::__construct produces an E_WARNING error message for
+    // each error found in the XML data and throws an exception if errors
+    // were detected. Catch any exception and return failure (NULL).
+    return NULL;
+  }
+  $data = array();
+  foreach ($xml as $k => $v) {
+    $data[$k] = (string) $v;
+  }
+  $data['languages'] = array();
+  if (isset($xml->languages)) {
+    foreach ($xml->languages->children() as $language) {
+      $langcode = (string) $language->code;
+      foreach ($language as $k => $v) {
+        $data['languages'][$langcode][$k] = (string) $v;
+      }
+    }
+  }
+  return $data;
 }
diff --git a/core/modules/locale/tests/test.l10n_server.xml b/core/modules/locale/tests/test.l10n_server.xml
new file mode 100644
index 0000000..494f4f0
--- /dev/null
+++ b/core/modules/locale/tests/test.l10n_server.xml
@@ -0,0 +1,60 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<l10n_server>
+  <version>1.1</version>
+  <name>Translations</name>
+  <link>http://localize.drupal.org/</link>
+  <update_url>http://ftp.drupal.org/files/translations/%core/%project/%project-%release.%language.po</update_url>
+  <l10n_remote>http://localize.drupal.org/</l10n_remote>
+  <languages>
+    <language>
+      <name>Afrikaans</name>
+      <native>Afrikaans</native>
+      <code>af</code>
+    </language>
+    <language>
+      <name>Albanian</name>
+      <native>Shqip</native>
+      <code>sq</code>
+    </language>
+    <language>
+      <name>Amharic</name>
+      <native>አማርኛ</native>
+      <code>am</code>
+    </language>
+    <language>
+      <name>Arabic</name>
+      <native>العربية</native>
+      <code>ar</code>
+    </language>
+    <language>
+      <name>Armenian</name>
+      <native>Հայերեն</native>
+      <code>hy</code>
+    </language>
+    <language>
+      <name>Assamese</name>
+      <native>Assamese</native>
+      <code>as</code>
+    </language>
+    <language>
+      <name>Asturian</name>
+      <native>Asturianu</native>
+      <code>ast</code>
+    </language>
+    <language>
+      <name>Azerbaijani</name>
+      <native>azərbaycan</native>
+      <code>az</code>
+    </language>
+    <language>
+      <name>Vietnamese</name>
+      <native>Tiếng Việt</native>
+      <code>vi</code>
+    </language>
+    <language>
+      <name>Welsh</name>
+      <native>Cymraeg</native>
+      <code>cy</code>
+    </language>
+  </languages>
+</l10n_server>
-- 
1.7.10.3

