Completed
Push — master ( 437185...b9fa04 )
by Michael
05:34
created

StatsModel   A

Complexity

Total Complexity 8

Size/Duplication

Total Lines 116
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 3

Test Coverage

Coverage 95.12%

Importance

Changes 9
Bugs 0 Features 0
Metric Value
wmc 8
c 9
b 0
f 0
lcom 1
cbo 3
dl 0
loc 116
ccs 39
cts 41
cp 0.9512
rs 10

2 Methods

Rating   Name   Duplication   Size   Complexity  
B getItems() 0 61 6
B save() 0 24 2
1
<?php
2
3
namespace Stats\Models;
4
5
use Joomla\Database\Query\LimitableInterface;
6
use Joomla\Model\AbstractDatabaseModel;
7
8
/**
9
 * Statistics database model
10
 *
11
 * @since  1.0
12
 */
13
class StatsModel extends AbstractDatabaseModel
14
{
15
	/**
16
	 * The query batch size
17
	 *
18
	 * @var    integer
19
	 * @since  1.0
20
	 */
21
	private $batchSize = 25000;
22
23
	/**
24
	 * Loads the statistics data from the database.
25
	 *
26
	 * @param   string  $column  A single column to filter on
27
	 *
28
	 * @return  \Generator  A Generator containing the response data
29
	 *
30
	 * @since   1.0
31
	 * @throws  \InvalidArgumentException
32
	 */
33 3
	public function getItems(string $column = '') : \Generator
34
	{
35 3
		$db = $this->getDb();
36
37
		// To keep from running out of memory, we need to know how many records are in the database to be able to loop correctly
38 3
		$totalRecords = $db->setQuery(
39 3
			$db->getQuery(true)
40 3
				->select('COUNT(unique_id)')
41 3
				->from('#__jstats')
42 3
		)->loadResult();
43
44
		// Validate the requested column is actually in the table
45 3
		if ($column !== '')
46
		{
47 2
			$columnList = $db->getTableColumns('#__jstats');
48
49
			// The column should exist in the table and be part of the API
50 2
			if (!in_array($column, array_keys($columnList)) && !in_array($column, ['unique_id', 'modified']))
51
			{
52 1
				throw new \InvalidArgumentException('An invalid data source was requested.', 404);
53
			}
54
55 1
			$query = $db->getQuery(true)
56 1
				->select($column);
57
		}
58
		else
59
		{
60 1
			$query = $db->getQuery(true)
61 1
				->select(['php_version', 'db_type', 'db_version', 'cms_version', 'server_os']);
62
		}
63
64 2
		$query->from('#__jstats')
65 2
			->group('unique_id');
66
67 2
		$limitable = $query instanceof LimitableInterface;
68
69
		// We can't have this as a single array, we run out of memory... This is gonna get interesting...
70 2
		for ($offset = 0; $offset < $totalRecords; $offset + $this->batchSize)
71
		{
72 2
			if ($limitable)
73
			{
74
				$query->setLimit($this->batchSize, $offset);
75
76
				$db->setQuery($query);
77
			}
78
			else
79
			{
80 2
				$db->setQuery($query, $offset, $this->batchSize);
81
			}
82
83 2
			yield $db->loadAssocList();
84
85 2
			$offset += $this->batchSize;
86
		}
87
88
		// Disconnect the DB to free some memory
89 2
		$db->disconnect();
90
91
		// And unset some variables
92 2
		unset($db, $query, $offset, $totalRecords);
93 2
	}
94
95
	/**
96
	 * Saves the given data.
97
	 *
98
	 * @param   \stdClass  $data  Data object to save.
99
	 *
100
	 * @return  void
101
	 *
102
	 * @since   1.0
103
	 */
104 2
	public function save(\stdClass $data)
105
	{
106 2
		$db = $this->getDb();
107
108
		// Set the modified date of the record
109 2
		$data->modified = (new \DateTime('now', new \DateTimeZone('UTC')))->format($db->getDateFormat());
110
111
		// Check if a row exists for this unique ID and update the existing record if so
112 2
		$recordExists = $db->setQuery(
113 2
			$db->getQuery(true)
114 2
				->select('unique_id')
115 2
				->from('#__jstats')
116 2
				->where('unique_id = ' . $db->quote($data->unique_id))
117 2
		)->loadResult();
118
119 2
		if ($recordExists)
120
		{
121 1
			$db->updateObject('#__jstats', $data, ['unique_id']);
122
		}
123
		else
124
		{
125 1
			$db->insertObject('#__jstats', $data, ['unique_id']);
0 ignored issues
show
Documentation introduced by
array('unique_id') is of type array<integer,string,{"0":"string"}>, but the function expects a string|null.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
126
		}
127 2
	}
128
}
129