1<?php
2/**
3 * Matomo - free/libre analytics platform
4 *
5 * @link https://matomo.org
6 * @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
7 *
8 */
9
10namespace Piwik\ViewDataTable;
11
12use Piwik\API\Request as ApiRequest;
13use Piwik\Common;
14
15class Request
16{
17    /**
18     * @var null|\Piwik\ViewDataTable\RequestConfig
19     */
20    public $requestConfig;
21
22    public function __construct($requestConfig)
23    {
24        $this->requestConfig = $requestConfig;
25    }
26
27    /**
28     * Function called by the ViewDataTable objects in order to fetch data from the API.
29     * The function init() must have been called before, so that the object knows which API module and action to call.
30     * It builds the API request string and uses Request to call the API.
31     * The requested DataTable object is stored in $this->dataTable.
32     */
33    public function loadDataTableFromAPI($extraParams = [])
34    {
35        // we build the request (URL) to call the API
36        $requestArray = $this->getRequestArray();
37        $requestArray = array_merge($extraParams, $requestArray);
38
39        // we make the request to the API
40        $request = new ApiRequest($requestArray);
41
42        // and get the DataTable structure
43        $dataTable = $request->process();
44
45        return $dataTable;
46    }
47
48    /**
49     * @return array  URL to call the API, eg. "method=Referrers.getKeywords&period=day&date=yesterday"...
50     */
51    public function getRequestArray()
52    {
53        // we prepare the array to give to the API Request
54        // we setup the method and format variable
55        // - we request the method to call to get this specific DataTable
56        // - the format = original specifies that we want to get the original DataTable structure itself, not rendered
57        $requestArray = array(
58            'method' => $this->requestConfig->apiMethodToRequestDataTable,
59            'format' => 'original'
60        );
61
62        $toSetEventually = array_merge(array(
63            'filter_limit',
64            'keep_totals_row',
65            'keep_summary_row',
66            'filter_sort_column',
67            'filter_sort_order',
68            'filter_excludelowpop',
69            'filter_excludelowpop_value',
70            'filter_column',
71            'filter_pattern',
72            'flat',
73            'totals',
74            'expanded',
75            'pivotBy',
76            'pivotByColumn',
77            'pivotByColumnLimit',
78        ), $this->requestConfig->getExtraParametersToSet());
79
80        foreach ($toSetEventually as $varToSet) {
81            $value = $this->getDefaultOrCurrent($varToSet);
82            if (false !== $value) {
83                $requestArray[$varToSet] = $value;
84            }
85        }
86
87        $segment = ApiRequest::getRawSegmentFromRequest();
88        if (!empty($segment)) {
89            $requestArray['segment'] = $segment;
90        }
91
92        if (ApiRequest::shouldLoadExpanded()) {
93            $requestArray['expanded'] = 1;
94        }
95
96        $requestArray = array_merge($requestArray, $this->requestConfig->request_parameters_to_modify);
97
98        if (!empty($requestArray['filter_limit'])
99            && $requestArray['filter_limit'] === 0
100        ) {
101            unset($requestArray['filter_limit']);
102        }
103
104        if ($this->requestConfig->disable_generic_filters) {
105            $requestArray['disable_generic_filters'] = '1';
106        }
107
108        if ($this->requestConfig->disable_queued_filters) {
109            $requestArray['disable_queued_filters'] = 1;
110        }
111
112        if (!empty($requestArray['compareSegments'])) {
113            $requestArray['compareSegments'] = Common::unsanitizeInputValues($requestArray['compareSegments']);
114        }
115
116        return $requestArray;
117    }
118
119    /**
120     * Returns, for a given parameter, the value of this parameter in the REQUEST array.
121     * If not set, returns the default value for this parameter @see getDefault()
122     *
123     * @param string $nameVar
124     * @return string|mixed Value of this parameter
125     */
126    protected function getDefaultOrCurrent($nameVar)
127    {
128        if (isset($_GET[$nameVar])) {
129            return Common::sanitizeInputValue($_GET[$nameVar]);
130        }
131
132        return $this->getDefault($nameVar);
133    }
134
135    /**
136     * Returns the default value for a given parameter.
137     * For example, these default values can be set using the disable* methods.
138     *
139     * @param string $nameVar
140     * @return mixed
141     */
142    protected function getDefault($nameVar)
143    {
144        if (isset($this->requestConfig->$nameVar)) {
145            return $this->requestConfig->$nameVar;
146        }
147
148        return false;
149    }
150}
151