protected function assertColumnValues($rowsWithValues) { $index = 0; foreach ($this->table->getRows() as $row) { $rowToCheck = $rowsWithValues[$index]; foreach ($rowToCheck as $columnToCheck => $expectedValue) { $actualValue = $row->getColumn($columnToCheck); $this->assertEquals($expectedValue, $actualValue, "{$columnToCheck} in row {$index} does not match assumed {$actualValue} is {$expectedValue}"); } $index++; } $this->assertEquals(count($rowsWithValues), $this->table->getRowsCount()); }
/** * See {@link PatternRecursive}. * * @param DataTable $table * @return int The number of deleted rows. */ public function filter($table) { $rows = $table->getRows(); foreach ($rows as $key => $row) { // A row is deleted if // 1 - its label doesnt contain the pattern // AND 2 - the label is not found in the children $patternNotFoundInChildren = false; try { $idSubTable = $row->getIdSubDataTable(); $subTable = Manager::getInstance()->getTable($idSubTable); // we delete the row if we couldn't find the pattern in any row in the // children hierarchy if ($this->filter($subTable) == 0) { $patternNotFoundInChildren = true; } } catch (Exception $e) { // there is no subtable loaded for example $patternNotFoundInChildren = true; } if ($patternNotFoundInChildren && !Pattern::match($this->patternToSearchQuoted, $row->getColumn($this->columnToFilter), $invertedMatch = false)) { $table->deleteRow($key); } } return $table->getRowsCount(); }
/** * @param DataTable $table */ public function filter($table) { $numRows = 0; $lastGroupFromPreviousPage = null; foreach ($table->getRows() as $row) { $this->addRowIfNeeded($row, $numRows); $numRows++; $subtable = $row->getSubtable(); if ($subtable) { if (!$this->hasRows()) { $lastGroupFromPreviousPage = $row; } foreach ($subtable->getRows() as $subRow) { $this->addRowIfNeeded($subRow, $numRows); $numRows++; } $row->removeSubtable(); } if ($this->hasNumberOfRequestedRowsFound()) { break; } } $this->prependGroupIfFirstSiteBelongsToAGroupButGroupIsMissingInRows($lastGroupFromPreviousPage); $table->setRows($this->rows); }
/** * See {@link ColumnCallbackReplace}. * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $row) { $extraColumnParameters = array(); foreach ($this->extraColumnParameters as $columnName) { $extraColumnParameters[] = $row->getColumn($columnName); } foreach ($this->columnsToFilter as $column) { // when a value is not defined, we set it to zero by default (rather than displaying '-') $value = $this->getElementToReplace($row, $column); if ($value === false) { $value = 0; } $parameters = array_merge(array($value), $extraColumnParameters); if (!is_null($this->functionParameters)) { $parameters = array_merge($parameters, $this->functionParameters); } $newValue = call_user_func_array($this->functionToApply, $parameters); $this->setElementToReplace($row, $column, $newValue); $this->filterSubTable($row); } } if (in_array('label', $this->columnsToFilter)) { // we need to force rebuilding the index $table->setLabelsHaveChanged(); } }
/** * See {@link ColumnCallbackAddMetadata}. * * @param DataTable $table */ public function filter($table) { if ($this->applyToSummaryRow) { $rows = $table->getRows(); } else { $rows = $table->getRowsWithoutSummaryRow(); } foreach ($rows as $key => $row) { $parameters = array(); foreach ($this->columnsToRead as $columnsToRead) { $parameters[] = $row->getColumn($columnsToRead); } if (!is_null($this->functionParameters)) { $parameters = array_merge($parameters, $this->functionParameters); } if (!is_null($this->functionToApply)) { $newValue = call_user_func_array($this->functionToApply, $parameters); } else { $newValue = $parameters[0]; } if ($newValue !== false) { $row->addMetadata($this->metadataToAdd, $newValue); } } }
/** * See {@link GroupBy}. * * @param DataTable $table */ public function filter($table) { $groupByRows = array(); $nonGroupByRowIds = array(); foreach ($table->getRows() as $rowId => $row) { // skip the summary row if ($rowId == DataTable::ID_SUMMARY_ROW) { continue; } // reduce the group by column of this row $groupByColumnValue = $row->getColumn($this->groupByColumn); $parameters = array_merge(array($groupByColumnValue), $this->parameters); $groupByValue = call_user_func_array($this->reduceFunction, $parameters); if (!isset($groupByRows[$groupByValue])) { // if we haven't encountered this group by value before, we mark this row as a // row to keep, and change the group by column to the reduced value. $groupByRows[$groupByValue] = $row; $row->setColumn($this->groupByColumn, $groupByValue); } else { // if we have already encountered this group by value, we add this row to the // row that will be kept, and mark this one for deletion $groupByRows[$groupByValue]->sumRow($row, $copyMeta = true, $table->getMetadata(DataTable::COLUMN_AGGREGATION_OPS_METADATA_NAME)); $nonGroupByRowIds[] = $rowId; } } // delete the unneeded rows. $table->deleteRows($nonGroupByRowIds); }
/** * @param DataTable $table */ protected function filterTable($table) { foreach ($table->getRows() as $row) { $newColumns = $this->getRenamedColumns($row->getColumns()); $row->setColumns($newColumns); $this->filterSubTable($row); } }
/** * See {@link ColumnCallbackDeleteMetadata}. * * @param DataTable $table */ public function filter($table) { $this->enableRecursive(true); foreach ($table->getRows() as $row) { $row->deleteMetadata($this->metadataToRemove); $this->filterSubTable($row); } }
/** * Decodes all columns of the given data table * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $row) { $value = $row->getColumn($this->columnToDecode); if ($value !== false) { $value = self::decodeLabelSafe($value); $row->setColumn($this->columnToDecode, $value); $this->filterSubTable($row); } } }
private function deleteRowsWithNoVisit(DataTable $table) { foreach ($table->getRows() as $key => $row) { $nbVisits = Metric::getMetric($row, 'nb_visits'); $nbActions = Metric::getMetric($row, 'nb_actions'); if ($nbVisits == 0 && $nbActions == 0) { // case of keyword/website/campaign with a conversion for this day, but no visit, we don't show it $table->deleteRow($key); } } }
private function deleteRowsWithNoVisit(DataTable $table) { $metrics = new Metrics\Processed(); foreach ($table->getRows() as $key => $row) { $nbVisits = $metrics->getColumn($row, Metrics::INDEX_NB_VISITS); $nbActions = $metrics->getColumn($row, Metrics::INDEX_NB_ACTIONS); if ($nbVisits == 0 && $nbActions == 0) { // case of keyword/website/campaign with a conversion for this day, but no visit, we don't show it $table->deleteRow($key); } } }
/** * See {@link ColumnCallbackAddColumn}. * * @param DataTable $table The table to filter. */ public function filter($table) { foreach ($table->getRows() as $row) { $columnValues = array(); foreach ($this->columns as $column) { $columnValues[] = $row->getColumn($column); } $parameters = array_merge($columnValues, $this->functionParameters); $value = call_user_func_array($this->functionToApply, $parameters); $row->setColumn($this->columnToAdd, $value); $this->filterSubTable($row); } }
/** * Executes the filter an adjusts all columns to fit the defined range * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $row) { $value = $row->getColumn($this->columnToFilter); if ($value !== false) { if ($value < self::$minimumValue) { $row->setColumn($this->columnToFilter, self::$minimumValue); } elseif ($value > self::$maximumValue) { $row->setColumn($this->columnToFilter, self::$maximumValue); } } } }
/** * See {@link AddSegmentByLabelMapping}. * * @param DataTable $table */ public function filter($table) { if (empty($this->segment) || empty($this->mapping)) { return; } foreach ($table->getRows() as $row) { $label = $row->getColumn('label'); if (!empty($this->mapping[$label])) { $label = $this->mapping[$label]; $row->setMetadata('segment', $this->segment . '==' . urlencode($label)); } } }
/** * See {@link ReplaceColumnNames}. * * @param DataTable $table */ public function filter($table) { if (!isset($this->nameToAppend) || '' === $this->nameToAppend || false === $this->nameToAppend) { return; } foreach ($table->getRows() as $row) { $columns = $row->getColumns(); foreach ($columns as $column => $value) { $row->deleteColumn($column); $row->setColumn($column . $this->nameToAppend, $value); } $this->filterSubTable($row); } }
/** * Filters the given data table * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $key => $row) { $params = array(); foreach ($this->columnsToFilter as $column) { $params[] = $row->getColumn($column); } $params = array_merge($params, $this->functionParams); if (call_user_func_array($this->function, $params) === true) { $table->deleteRow($key); } $this->filterSubTable($row); } }
/** * Template method called from self::manipulate. * Flatten each data table. * * @param DataTable $dataTable * @return DataTable */ protected function manipulateDataTable($dataTable) { // apply filters now since subtables have their filters applied before generic filters. if we don't do this // now, we'll try to apply filters to rows that have already been manipulated. this results in errors like // 'column ... already exists'. if (Common::getRequestVar('disable_queued_filters', 0, 'int', $this->request) == 0) { $dataTable->applyQueuedFilters(); } $newDataTable = $dataTable->getEmptyClone($keepFilters = false); foreach ($dataTable->getRows() as $row) { $this->flattenRow($row, $newDataTable); } return $newDataTable; }
/** * See {@link Pattern}. * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $key => $row) { //instead search must handle // - negative search with -piwik // - exact match with "" // see (?!pattern) A subexpression that performs a negative lookahead search, which matches the search string at any point where a string not matching pattern begins. $value = $row->getColumn($this->columnToFilter); if ($value === false) { $value = $row->getMetadata($this->columnToFilter); } if (!self::match($this->patternToSearchQuoted, $value, $this->invertedMatch)) { $table->deleteRow($key); } } }
/** * See {@link MetadataCallbackAddMetadata}. * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $key => $row) { if (!$this->applyToSummaryRow && $key == DataTable::ID_SUMMARY_ROW) { continue; } $params = array(); foreach ($this->metadataToRead as $name) { $params[] = $row->getMetadata($name); } $newValue = call_user_func_array($this->functionToApply, $params); if ($newValue !== false) { $row->addMetadata($this->metadataToAdd, $newValue); } } }
/** * Adds the processed metrics. See {@link AddColumnsProcessedMetrics} for * more information. * * @param DataTable $table */ public function filter($table) { $rowsIdToDelete = array(); foreach ($table->getRows() as $key => $row) { $nbVisits = $this->getColumn($row, Metrics::INDEX_NB_VISITS); $nbActions = $this->getColumn($row, Metrics::INDEX_NB_ACTIONS); if ($nbVisits == 0 && $nbActions == 0 && $this->deleteRowsWithNoVisit) { // case of keyword/website/campaign with a conversion for this day, // but no visit, we don't show it $rowsIdToDelete[] = $key; continue; } $nbVisitsConverted = (int) $this->getColumn($row, Metrics::INDEX_NB_VISITS_CONVERTED); if ($nbVisitsConverted > 0) { $conversionRate = round(100 * $nbVisitsConverted / $nbVisits, $this->roundPrecision); try { $row->addColumn('conversion_rate', $conversionRate . "%"); } catch (\Exception $e) { // conversion_rate can be defined upstream apparently? FIXME } } if ($nbVisits == 0) { $actionsPerVisit = $averageTimeOnSite = $bounceRate = $this->invalidDivision; } else { // nb_actions / nb_visits => Actions/visit // sum_visit_length / nb_visits => Avg. Time on Site // bounce_count / nb_visits => Bounce Rate $actionsPerVisit = round($nbActions / $nbVisits, $this->roundPrecision); $visitLength = $this->getColumn($row, Metrics::INDEX_SUM_VISIT_LENGTH); $averageTimeOnSite = round($visitLength / $nbVisits, $rounding = 0); $bounceRate = round(100 * $this->getColumn($row, Metrics::INDEX_BOUNCE_COUNT) / $nbVisits, $this->roundPrecision); } try { $row->addColumn('nb_actions_per_visit', $actionsPerVisit); $row->addColumn('avg_time_on_site', $averageTimeOnSite); // It could be useful for API users to have raw sum length value. //$row->addMetadata('sum_visit_length', $visitLength); } catch (\Exception $e) { } try { $row->addColumn('bounce_rate', $bounceRate . "%"); } catch (\Exception $e) { } $this->filterSubTable($row); } $table->deleteRows($rowsIdToDelete); }
/** * @param DataTable $table */ public function filter($table) { $dimension = CustomDimensionsRequestProcessor::buildCustomDimensionTrackingApiName($this->idDimension); foreach ($table->getRows() as $row) { $label = $row->getColumn('label'); if ($label !== false) { if ($label === Archiver::LABEL_CUSTOM_VALUE_NOT_DEFINED) { $label = ''; } $row->setMetadata('segment', $dimension . '==' . urlencode($label)); } $subTable = $row->getSubtable(); if ($subTable) { $subTable->filter('Piwik\\Plugins\\CustomDimensions\\DataTable\\Filter\\AddSubtableSegmentMetadata', array($this->idDimension, $label)); } } }
/** * See {@link ColumnCallbackAddColumn}. * * @param DataTable $table The table to filter. */ public function filter($table) { $columns = $this->columns; $functionParams = $this->functionParameters; $functionToApply = $this->functionToApply; foreach ($table->getRows() as $row) { $row->setColumn($this->columnToAdd, function (DataTable\Row $row) use($columns, $functionParams, $functionToApply) { $columnValues = array(); foreach ($columns as $column) { $columnValues[] = $row->getColumn($column); } $parameters = array_merge($columnValues, $functionParams); return call_user_func_array($functionToApply, $parameters); }); $this->filterSubTable($row); } }
/** * See {@link ReplaceSummaryRowLabel}. * * @param DataTable $table */ public function filter($table) { $rows = $table->getRows(); foreach ($rows as $id => $row) { if ($row->getColumn('label') == DataTable::LABEL_SUMMARY_ROW || $id == DataTable::ID_SUMMARY_ROW) { $row->setColumn('label', $this->newLabel); break; } } // recurse foreach ($rows as $row) { if ($row->isSubtableLoaded()) { $subTable = Manager::getInstance()->getTable($row->getIdSubDataTable()); $this->filter($subTable); } } }
/** * See {@link MetadataCallbackAddMetadata}. * * @param DataTable $table */ public function filter($table) { if ($this->applyToSummaryRow) { $rows = $table->getRows(); } else { $rows = $table->getRowsWithoutSummaryRow(); } foreach ($rows as $key => $row) { $params = array(); foreach ($this->metadataToRead as $name) { $params[] = $row->getMetadata($name); } $newValue = call_user_func_array($this->functionToApply, $params); if ($newValue !== false) { $row->addMetadata($this->metadataToAdd, $newValue); } } }
/** * See {@link ColumnCallbackAddColumnQuotient}. * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $row) { $value = $this->getDividend($row); if ($value === false && $this->shouldSkipRows) { continue; } // Delete existing column if it exists $existingValue = $row->getColumn($this->columnNameToAdd); if ($existingValue !== false) { continue; } $divisor = $this->getDivisor($row); $formattedValue = $this->formatValue($value, $divisor); $row->addColumn($this->columnNameToAdd, $formattedValue); $this->filterSubTable($row); } }
/** * @param DataTable $table */ public function filter($table) { if (!$this->dimensionValue) { return; } $dimension = CustomDimensionsRequestProcessor::buildCustomDimensionTrackingApiName($this->idDimension); if ($this->dimensionValue === Archiver::LABEL_CUSTOM_VALUE_NOT_DEFINED) { $dimensionValue = ''; } else { $dimensionValue = urlencode($this->dimensionValue); } $conditionAnd = ';'; $partDimension = $dimension . '==' . $dimensionValue . $conditionAnd; foreach ($table->getRows() as $row) { $label = $row->getColumn('label'); if ($label !== false) { $row->setMetadata('segment', $partDimension . 'actionUrl=$' . urlencode($label)); $row->setMetadata('url', urlencode($label)); } } }
/** * See {@link ColumnCallbackAddMetadata}. * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $key => $row) { if (!$this->applyToSummaryRow && $key == DataTable::ID_SUMMARY_ROW) { continue; } $parameters = array(); foreach ($this->columnsToRead as $columnsToRead) { $parameters[] = $row->getColumn($columnsToRead); } if (!is_null($this->functionParameters)) { $parameters = array_merge($parameters, $this->functionParameters); } if (!is_null($this->functionToApply)) { $newValue = call_user_func_array($this->functionToApply, $parameters); } else { $newValue = $parameters[0]; } if ($newValue !== false) { $row->addMetadata($this->metadataToAdd, $newValue); } } }
/** * See {@link AddSegmentBySegmentValue}. * * @param DataTable $table * @return int The number of deleted rows. */ public function filter($table) { if (empty($this->report) || !$table->getRowsCount()) { return; } $dimension = $this->report->getDimension(); if (empty($dimension)) { return; } $segments = $dimension->getSegments(); if (empty($segments)) { return; } /** @var \Piwik\Plugin\Segment $segment */ $segment = reset($segments); $segmentName = $segment->getSegment(); foreach ($table->getRows() as $row) { $value = $row->getMetadata('segmentValue'); $filter = $row->getMetadata('segment'); if ($value !== false && $filter === false) { $row->setMetadata('segment', sprintf('%s==%s', $segmentName, urlencode($value))); } } }
/** * See {@link PatternRecursive}. * * @param DataTable $table * @return int The number of deleted rows. */ public function filter($table) { $rows = $table->getRows(); foreach ($rows as $key => $row) { // A row is deleted if // 1 - its label doesnt contain the pattern // AND 2 - the label is not found in the children $patternNotFoundInChildren = false; $subTable = $row->getSubtable(); if (!$subTable) { $patternNotFoundInChildren = true; } else { // we delete the row if we couldn't find the pattern in any row in the // children hierarchy if ($this->filter($subTable) == 0) { $patternNotFoundInChildren = true; } } if ($patternNotFoundInChildren && !Pattern::match($this->patternToSearchQuoted, $row->getColumn($this->columnToFilter), $invertedMatch = false)) { $table->deleteRow($key); } } return $table->getRowsCount(); }
/** * Executes the filter an adjusts all columns to fit the defined range * * @param DataTable $table */ public function filter($table) { foreach ($table->getRows() as $row) { $value = $row->getColumn($this->columnToFilter); if ($value === false) { $value = $row->getMetadata($this->columnToFilter); if ($value !== false) { if ($value < (double) self::$minimumValue) { $row->setMetadata($this->columnToFilter, self::$minimumValue); } elseif ($value > (double) self::$maximumValue) { $row->setMetadata($this->columnToFilter, self::$maximumValue); } } continue; } if ($value !== false) { if ($value < (double) self::$minimumValue) { $row->setColumn($this->columnToFilter, self::$minimumValue); } elseif ($value > (double) self::$maximumValue) { $row->setColumn($this->columnToFilter, self::$maximumValue); } } } }