PageRenderTime 74ms CodeModel.GetById 41ms RepoModel.GetById 7ms app.codeStats 0ms

/core/ViewDataTable/Factory.php

https://github.com/CodeYellowBV/piwik
PHP | 212 lines | 71 code | 22 blank | 119 comment | 14 complexity | bf522f63533aec5099a6caa53a9ec2d1 MD5 | raw file
Possible License(s): LGPL-3.0, JSON, MIT, GPL-3.0, LGPL-2.1, GPL-2.0, AGPL-1.0, BSD-2-Clause, BSD-3-Clause
  1. <?php
  2. /**
  3. * Piwik - free/libre analytics platform
  4. *
  5. * @link http://piwik.org
  6. * @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
  7. *
  8. */
  9. namespace Piwik\ViewDataTable;
  10. use Piwik\Common;
  11. use Piwik\Piwik;
  12. use Piwik\Plugins\CoreVisualizations\Visualizations\HtmlTable;
  13. /**
  14. * Provides a means of creating {@link Piwik\Plugin\ViewDataTable} instances by ID.
  15. *
  16. * ### Examples
  17. *
  18. * **Creating a ViewDataTable for a report**
  19. *
  20. * // method in MyPlugin\Controller
  21. * public function myReport()
  22. * {
  23. * $view = Factory::build('table', 'MyPlugin.myReport');
  24. * $view->config->show_limit_control = true;
  25. * $view->config->translations['myFancyMetric'] = "My Fancy Metric";
  26. * return $view->render();
  27. * }
  28. *
  29. * **Displaying a report in another way**
  30. *
  31. * // method in MyPlugin\Controller
  32. * // use the same data that's used in myReport() above, but transform it in some way before
  33. * // displaying.
  34. * public function myReportShownDifferently()
  35. * {
  36. * $view = Factory::build('table', 'MyPlugin.myReport', 'MyPlugin.myReportShownDifferently');
  37. * $view->config->filters[] = array('MyMagicFilter', array('an arg', 'another arg'));
  38. * return $view->render();
  39. * }
  40. *
  41. * **Force a report to be shown as a bar graph**
  42. *
  43. * // method in MyPlugin\Controller
  44. * // force the myReport report to show as a bar graph if there is no viewDataTable query param,
  45. * // even though it is configured to show as a table.
  46. * public function myReportShownAsABarGraph()
  47. * {
  48. * $view = Factory::build('graphVerticalBar', 'MyPlugin.myReport', 'MyPlugin.myReportShownAsABarGraph',
  49. * $forceDefault = true);
  50. * return $view->render();
  51. * }
  52. *
  53. *
  54. * @api
  55. */
  56. class Factory
  57. {
  58. /**
  59. * Cache for getDefaultTypeViewDataTable result.
  60. *
  61. * @var array
  62. */
  63. private static $defaultViewTypes = null;
  64. /**
  65. * Creates a {@link Piwik\Plugin\ViewDataTable} instance by ID. If the **viewDataTable** query parameter is set,
  66. * this parameter's value is used as the ID.
  67. *
  68. * See {@link Piwik\Plugin\ViewDataTable} to read about the visualizations that are packaged with Piwik.
  69. *
  70. * @param string|null $defaultType A ViewDataTable ID representing the default ViewDataTable type to use. If
  71. * the **viewDataTable** query parameter is not found, this value is used as
  72. * the ID of the ViewDataTable to create.
  73. *
  74. * If a visualization type is configured for the report being displayed, it
  75. * is used instead of the default type. (See {@hook ViewDataTable.getDefaultType}).
  76. * If nothing is configured for the report and `null` is supplied for this
  77. * argument, **table** is used.
  78. * @param bool|false|string $apiAction The API method for the report that will be displayed, eg,
  79. * `'UserSettings.getBrowser'`.
  80. * @param bool|false|string $controllerAction The controller name and action dedicated to displaying the report. This
  81. * action is used when reloading reports or changing the report visualization.
  82. * Defaulted to `$apiAction` if `false` is supplied.
  83. * @param bool $forceDefault If true, then the visualization type that was configured for the report will be
  84. * ignored and `$defaultType` will be used as the default.
  85. * @throws \Exception
  86. * @return \Piwik\Plugin\ViewDataTable
  87. */
  88. public static function build($defaultType = null, $apiAction = false, $controllerAction = false, $forceDefault = false)
  89. {
  90. if (false === $controllerAction) {
  91. $controllerAction = $apiAction;
  92. }
  93. $defaultViewType = self::getDefaultViewTypeForReport($apiAction);
  94. if (!$forceDefault && !empty($defaultViewType)) {
  95. $defaultType = $defaultViewType;
  96. }
  97. $isWidget = Common::getRequestVar('widget', '0', 'string');
  98. if (!empty($isWidget)) {
  99. $params = array();
  100. } else {
  101. $login = Piwik::getCurrentUserLogin();
  102. $params = Manager::getViewDataTableParameters($login, $controllerAction);
  103. }
  104. $savedViewDataTable = false;
  105. if (!empty($params['viewDataTable'])) {
  106. $savedViewDataTable = $params['viewDataTable'];
  107. }
  108. $type = Common::getRequestVar('viewDataTable', $savedViewDataTable, 'string');
  109. // Common::getRequestVar removes backslashes from the defaultValue in case magic quotes are enabled.
  110. // therefore do not pass this as a default value to getRequestVar()
  111. if ('' === $type) {
  112. $type = $defaultType ? : HtmlTable::ID;
  113. }
  114. $visualizations = Manager::getAvailableViewDataTables();
  115. if (array_key_exists($type, $visualizations)) {
  116. return self::createViewDataTableInstance($visualizations[$type], $controllerAction, $apiAction, $params);
  117. }
  118. if (class_exists($type)) {
  119. return self::createViewDataTableInstance($type, $controllerAction, $apiAction, $params);
  120. }
  121. if (array_key_exists($defaultType, $visualizations)) {
  122. return self::createViewDataTableInstance($visualizations[$defaultType], $controllerAction, $apiAction, $params);
  123. }
  124. if (array_key_exists(HtmlTable::ID, $visualizations)) {
  125. return self::createViewDataTableInstance($visualizations[HtmlTable::ID], $controllerAction, $apiAction, $params);
  126. }
  127. throw new \Exception('No visualization found to render ViewDataTable');
  128. }
  129. /**
  130. * Returns the default viewDataTable ID to use when determining which visualization to use.
  131. */
  132. private static function getDefaultViewTypeForReport($apiAction)
  133. {
  134. $defaultViewTypes = self::getDefaultTypeViewDataTable();
  135. return isset($defaultViewTypes[$apiAction]) ? $defaultViewTypes[$apiAction] : false;
  136. }
  137. /**
  138. * Returns a list of default viewDataTables ID to use when determining which visualization to use for multiple
  139. * reports.
  140. */
  141. private static function getDefaultTypeViewDataTable()
  142. {
  143. if (null === self::$defaultViewTypes) {
  144. self::$defaultViewTypes = array();
  145. /**
  146. * Triggered when gathering the default view types for all available reports.
  147. *
  148. * If you define your own report, you may want to subscribe to this event to
  149. * make sure the correct default Visualization is used (for example, a pie graph,
  150. * bar graph, or something else).
  151. *
  152. * If there is no default type associated with a report, the **table** visualization
  153. * used.
  154. *
  155. * **Example**
  156. *
  157. * public function getDefaultTypeViewDataTable(&$defaultViewTypes)
  158. * {
  159. * $defaultViewTypes['Referrers.getSocials'] = HtmlTable::ID;
  160. * $defaultViewTypes['Referrers.getUrlsForSocial'] = Pie::ID;
  161. * }
  162. *
  163. * @param array &$defaultViewTypes The array mapping report IDs with visualization IDs.
  164. */
  165. Piwik::postEvent('ViewDataTable.getDefaultType', array(&self::$defaultViewTypes));
  166. }
  167. return self::$defaultViewTypes;
  168. }
  169. /**
  170. * @param string $klass
  171. * @param string $controllerAction
  172. * @param string $apiAction
  173. * @param array $params
  174. *
  175. * @internal param string $viewDataTableId
  176. * @return \Piwik\Plugin\ViewDataTable
  177. */
  178. private static function createViewDataTableInstance($klass, $controllerAction, $apiAction, $params)
  179. {
  180. if (empty($params)) {
  181. $params = array();
  182. }
  183. if (!is_subclass_of($klass, 'Piwik\Plugin\Visualization')) {
  184. // for now we ignore those params in case it is not a visualization. We do not want to apply
  185. // any of those saved parameters to sparklines etc. Need to find a better solution here
  186. $params = array();
  187. }
  188. return new $klass($controllerAction, $apiAction, $params);
  189. }
  190. }