import.inc 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175
  1. <?php
  2. /**
  3. * @file
  4. * Browscap data import functions.
  5. */
  6. /**
  7. * Helper function to update the browscap data.
  8. *
  9. * @param bool $cron
  10. * Optional import environment. If false, display status messages to the user
  11. * in addition to logging information with the watchdog.
  12. */
  13. function _browscap_import($cron = TRUE) {
  14. // Check the local browscap data version number.
  15. $local_version = variable_get('browscap_version', 0);
  16. // Retrieve the current browscap data version number using HTTP.
  17. $current_version = drupal_http_request('http://www.browscap.org/version-number');
  18. // Log an error if the browscap version number could not be retrieved.
  19. if (isset($current_version->error)) {
  20. // Log a message with the watchdog.
  21. watchdog('browscap', "Couldn't check version: %error", array('%error' => $current_version->error), WATCHDOG_ERROR);
  22. // Display a message to user if the update process was triggered manually.
  23. if ($cron == FALSE) {
  24. drupal_set_message(t("Couldn't check version: %error", array('%error' => $current_version->error)), 'error');
  25. }
  26. return;
  27. }
  28. // Sanitize the returned version number.
  29. $current_version = check_plain(trim($current_version->data));
  30. // Compare the current and local version numbers to determine if the browscap
  31. // data requires updating.
  32. if ($current_version == $local_version) {
  33. // Log a message with the watchdog.
  34. watchdog('browscap', 'No new version of browscap to import');
  35. // Display a message to user if the update process was triggered manually.
  36. if ($cron == FALSE) {
  37. drupal_set_message(t('No new version of browscap to import'));
  38. }
  39. return;
  40. }
  41. // Set options for downloading data with or without compression.
  42. if (function_exists('gzdecode')) {
  43. $options = array(
  44. 'headers' => array('Accept-Encoding' => 'gzip'),
  45. );
  46. }
  47. else {
  48. // The download takes over ten times longer without gzip, and may exceed
  49. // the default timeout of 30 seconds, so we increase the timeout.
  50. $options = array('timeout' => 600);
  51. }
  52. // Retrieve the browscap data using HTTP.
  53. $browscap_data = drupal_http_request('http://www.browscap.org/stream?q=PHP_BrowsCapINI', $options);
  54. // Log an error if the browscap data could not be retrieved.
  55. if (isset($browscap_data->error) || empty($browscap_data)) {
  56. // Log a message with the watchdog.
  57. watchdog('browscap', "Couldn't retrieve updated browscap: %error", array('%error' => $browscap_data->error), WATCHDOG_ERROR);
  58. // Display a message to user if the update process was triggered manually.
  59. if ($cron == FALSE) {
  60. drupal_set_message(t("Couldn't retrieve updated browscap: %error", array('%error' => $browscap_data->error)), 'error');
  61. }
  62. return;
  63. }
  64. // Decompress the downloaded data if it is compressed.
  65. if (function_exists('gzdecode')) {
  66. $browscap_data->data = gzdecode($browscap_data->data);
  67. }
  68. // Parse the returned browscap data.
  69. // The parse_ini_string function is preferred but only available in PHP 5.3.0.
  70. if (version_compare(PHP_VERSION, '5.3.0', '>=')) {
  71. // Retrieve the browscap data.
  72. $browscap_data = $browscap_data->data;
  73. // Replace 'true' and 'false' with '1' and '0'
  74. $browscap_data = preg_replace(
  75. array(
  76. "/=\s*true\s*\n/",
  77. "/=\s*false\s*\n/",
  78. ),
  79. array(
  80. "=1\n",
  81. "=0\n",
  82. ),
  83. $browscap_data
  84. );
  85. // Parse the browscap data as a string.
  86. $browscap_data = parse_ini_string($browscap_data, TRUE, INI_SCANNER_RAW);
  87. }
  88. else {
  89. // Create a path and filename.
  90. $server = $_SERVER['SERVER_NAME'];
  91. $path = variable_get('file_temporary_path', '/tmp');
  92. $file = "$path/browscap_$server.ini";
  93. // Write the browscap data to a file.
  94. $browscap_file = fopen($file, "w");
  95. fwrite($browscap_file, $browscap_data->data);
  96. fclose($browscap_file);
  97. // Parse the browscap data as a file.
  98. $browscap_data = parse_ini_file($file, TRUE);
  99. }
  100. if ($browscap_data) {
  101. // Find the version information.
  102. // The version information is the first entry in the array.
  103. $version = array_shift($browscap_data);
  104. // Store the data available for each user agent.
  105. foreach ($browscap_data as $key => $values) {
  106. // Store the current value.
  107. $e = $values;
  108. // Create an array to hold the last parent.
  109. $last_parent = array();
  110. // Recurse through the available user agent information.
  111. while (isset($values['Parent']) && $values['Parent'] !== $last_parent) {
  112. $values = isset($browscap_data[$values['Parent']]) ? $browscap_data[$values['Parent']] : array();
  113. $e = array_merge($values, $e);
  114. $last_parent = $values;
  115. }
  116. // Replace '*?' with '%_'.
  117. $user_agent = strtr($key, '*?', '%_');
  118. // Change all array keys to lowercase.
  119. $e = array_change_key_case($e);
  120. // Delete all data about the current user agent from the database.
  121. db_delete('browscap')
  122. ->condition('useragent', $user_agent)
  123. ->execute();
  124. // Insert all data about the current user agent into the database.
  125. db_insert('browscap')
  126. ->fields(array(
  127. 'useragent' => $user_agent,
  128. 'data' => serialize($e),
  129. ))
  130. ->execute();
  131. }
  132. // Clear the browscap data cache.
  133. cache_clear_all('*', 'cache_browscap', TRUE);
  134. // Update the browscap version.
  135. variable_set('browscap_version', $current_version);
  136. // Log a message with the watchdog.
  137. watchdog('browscap', 'New version of browscap imported: %version', array('%version' => $current_version));
  138. // Display a message to user if the update process was triggered manually.
  139. if ($cron == FALSE) {
  140. drupal_set_message(t('New version of browscap imported: %version', array('%version' => $current_version)));
  141. }
  142. }
  143. }