Completed
Push — spip-2-stable ( d79e3d )
by cam
30:47 queued 16:59
created

visites.php ➔ calculer_visites()   F

Complexity

Conditions 28
Paths 1326

Size

Total Lines 155
Code Lines 101

Duplication

Lines 12
Ratio 7.74 %

Importance

Changes 0
Metric Value
cc 28
eloc 101
nc 1326
nop 1
dl 12
loc 155
rs 2
c 0
b 0
f 0

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
/***************************************************************************\
4
 *  SPIP, Systeme de publication pour l'internet                           *
5
 *                                                                         *
6
 *  Copyright (c) 2001-2016                                                *
7
 *  Arnaud Martin, Antoine Pitrou, Philippe Riviere, Emmanuel Saint-James  *
8
 *                                                                         *
9
 *  Ce programme est un logiciel libre distribue sous licence GNU/GPL.     *
10
 *  Pour plus de details voir le fichier COPYING.txt ou l'aide en ligne.   *
11
\***************************************************************************/
12
13
14
if (!defined('_ECRIRE_INC_VERSION')) return;
15
if (!defined('_CRON_LOT_FICHIERS_VISITE')) define('_CRON_LOT_FICHIERS_VISITE', 100);
16
17
### Pour se debarrasser du md5, comment faire ? Un index sur 'referer' ?
18
### ou alors la meme notion, mais sans passer par des fonctions HEX ?
19
20
//
21
// prendre en compte un fichier de visite
22
//
23
// http://doc.spip.org/@compte_fichier_visite
24
function compte_fichier_visite($fichier, &$visites, &$visites_a, &$referers, &$referers_a) {
25
26
	// Noter la visite du site (article 0)
27
	$visites ++;
28
29
	$content = array();
30
	if (lire_fichier($fichier, $content))
31
		$content = @unserialize($content);
32
	if (!is_array($content)) return;
33
34
	foreach ($content as $source => $num) {
35
		list($log_type, $log_id_num, $log_referer)
36
			= preg_split(",\t,", $source, 3);
37
		
38
		// Noter le referer
39
		if ($log_referer)
40
			$referers[$log_referer]++;
41
42
		// S'il s'agit d'un article, noter ses visites
43
		if ($log_type == 'article'
44
		AND $id_article = intval($log_id_num)) {
45
			$visites_a[$id_article] ++;
46
			if ($log_referer)
47
				$referers_a[$id_article][$log_referer]++;
48
		}
49
	}
50
}
51
52
53
// http://doc.spip.org/@calculer_visites
54
function calculer_visites($t) {
55
	include_spip('base/abstract_sql');
56
57
	// Initialisations
58
	$visites = array(); # visites du site
59
	$visites_a = array(); # tableau des visites des articles
60
	$referers = array(); # referers du site
61
	$referers_a = array(); # tableau des referers des articles
62
63
	// charger un certain nombre de fichiers de visites,
64
	// et faire les calculs correspondants
65
66
	// Traiter jusqu'a 100 sessions datant d'au moins 30 minutes
67
	$sessions = preg_files(sous_repertoire(_DIR_TMP, 'visites'));
68
69
	$compteur = _CRON_LOT_FICHIERS_VISITE;
70
	$date_init = time()-30*60;
71
	foreach ($sessions as $item) {
72
		if (($d=@filemtime($item)) < $date_init) {
73
			if (!$d) $d = $date_init; // si le fs ne donne pas de date, on prend celle du traitement, mais tout cela risque d'etre bien douteux
74
			$d = date("Y-m-d",$d);
75
			spip_log("traite la session $item");
76
			compte_fichier_visite($item,
77
				$visites[$d], $visites_a[$d], $referers[$d], $referers_a[$d]);
78
			spip_unlink($item);
79
			if (--$compteur <= 0)
80
				break;
81
		}
82
		#else spip_log("$item pas vieux");
83
	}
84
	if (!count($visites))
85
		return;
86
87
	include_spip('genie/popularites');
88
	list($a,$b) = genie_popularite_constantes(24*3600);
0 ignored issues
show
Unused Code introduced by
The assignment to $a is unused. Consider omitting it like so list($first,,$third).

This checks looks for assignemnts to variables using the list(...) function, where not all assigned variables are subsequently used.

Consider the following code example.

<?php

function returnThreeValues() {
    return array('a', 'b', 'c');
}

list($a, $b, $c) = returnThreeValues();

print $a . " - " . $c;

Only the variables $a and $c are used. There was no need to assign $b.

Instead, the list call could have been.

list($a,, $c) = returnThreeValues();
Loading history...
89
90
	// Maintenant on dispose de plusieurs tableaux qu'il faut ventiler dans
91
	// les tables spip_visites, spip_visites_articles, spip_referers
92
	// et spip_referers_articles ; attention a affecter tout ca a la bonne
93
	// date (celle de la visite, pas celle du traitement)
94
	foreach(array_keys($visites) as $date)
95
		if ($visites[$date]) {
96
97
			// 1. les visites du site (facile)
98
			if (!sql_countsel('spip_visites', "date='$date'"))
99
				sql_insertq('spip_visites',
100
					array('date' => $date, 'visites' => $visites[$date]));
101
			else 
102
				sql_update('spip_visites', array('visites' => "visites+".intval($visites[$date])), "date='$date'");
103
		
104
			// 2. les visites des articles 
105
			if ($visites_a[$date]) {
106
				$ar = array();	# tableau num -> liste des articles ayant num visites
107
				foreach($visites_a[$date] as $id_article => $n) {
108
					if (!sql_countsel('spip_visites_articles',
109
						 "id_article=$id_article AND date='$date'")){
110
						sql_insertq('spip_visites_articles',
111
								array('id_article' => $id_article,
112
								      'visites' => 0,
113
								      'date' => $date));
114
					}
115
					$ar[$n][] = $id_article;
116
				}
117
				foreach ($ar as $n => $liste) {
118
					$tous = sql_in('id_article', $liste);
119
					sql_update('spip_visites_articles',
120
						array('visites' => "visites+$n"),
121
						   "date='$date' AND $tous");
122
		
123
					$ref = $noref = array();
124
					foreach($liste as $id) {
125
						if (isset($referers_a[$date][$id]))
126
							$ref[]= $id ;
127
						else $noref[]=$id;
128
					}
129
					// il faudrait ponderer la popularite ajoutee ($n) par son anciennete eventuelle
130
					// sur le modele de ce que fait genie/popularites
131 View Code Duplication
					if (count($noref))
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
132
						sql_update('spip_articles',
133
							array('visites' => "visites+$n",
134
							 'popularite' => "popularite+".round($n*$b,2),
135
							 'maj' => 'maj'),
136
							sql_in('id_article',$noref));
137
							   
138 View Code Duplication
					if (count($ref))
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
139
						sql_update('spip_articles',
140
							   array('visites' => "visites+".($n+1),
141
							 'popularite' => "popularite+".round($n*$b,2),
142
							 'maj' => 'maj'),
143
							sql_in('id_article',$ref));
144
							   
145
					## Ajouter un JOIN sur le statut de l'article ?
146
				}
147
			}
148
			// 3. Les referers du site
149
			// insertion pour les nouveaux, au tableau des increments sinon
150
			if ($referers[$date]) {
151
				$ar = array();
152
				$trouver_table = charger_fonction('trouver_table', 'base');
153
				$desc = $trouver_table('referers');
154
				$n = preg_match('/(\d+)/',$desc['field']['referer'], $r);
155
				$n = $n ? $r[1] : 255;
156
				foreach ($referers[$date] as $referer => $num) {
157
					$referer_md5 = sql_hex(substr(md5($referer), 0, 15));
158
					$referer = substr($referer,0,$n);
159
					if (!sql_countsel('spip_referers', "referer_md5=$referer_md5"))
160
						sql_insertq('spip_referers',
161
							array('visites' => $num,
162
							      'visites_jour' => $num,
163
							      'visites_veille' => $num,
164
							      'date' => $date,
165
							      'referer' => $referer,
166
							      'referer_md5' => $referer_md5));
167
					else $ar[$num][] = $referer_md5;
168
				}
169
		
170
			// appliquer les increments sur les anciens
171
			// attention on appelle sql_in en mode texte et pas array
172
			// pour ne pas passer sql_quote() sur les '0x1234' de referer_md5, cf #849
173
				foreach ($ar as $num => $liste) {
174
					sql_update('spip_referers', array('visites' => "visites+$num", 'visites_jour' => "visites_jour+$num"), sql_in('referer_md5',join(', ', $liste)));
175
				}
176
			}
177
			
178
			// 4. Les referers d'articles
179
			if ($referers_a[$date]) {
180
				$ar = array();
181
				$insert = array();
0 ignored issues
show
Unused Code introduced by
$insert is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
182
				// s'assurer d'un slot pour chacun
183
				foreach ($referers_a[$date] as $id_article => $referers)
184
					foreach ($referers as $referer => $num) {
185
						$referer_md5 = sql_hex(substr(md5($referer), 0, 15));
186
						$prim = "(id_article=$id_article AND referer_md5=$referer_md5)";
187
						if (!sql_countsel('spip_referers_articles', $prim))
188
							sql_insertq('spip_referers_articles',
189
							     array('visites' => $num,
190
								   'id_article' => $id_article,
191
								   'referer' => $referer,
192
								   'referer_md5' => $referer_md5));
193
						else $ar[$num][] = $prim;
194
					}
195
				// ajouter les visites
196
				foreach ($ar as $num => $liste) {
197
					sql_update('spip_referers_articles', array('visites' => "visites+$num"), join(" OR ", $liste));
198
					## Ajouter un JOIN sur le statut de l'article ?
199
				}
200
			}
201
		}
202
203
	// S'il reste des fichiers a manger, le signaler pour reexecution rapide
204
	if ($compteur==0) {
205
		spip_log("il reste des visites a traiter...");
206
		return -$t;
207
	}
208
}
209
210
//
211
// Calcule les stats en plusieurs etapes
212
//
213
// http://doc.spip.org/@genie_visites_dist
214
function genie_visites_dist($t) {
215
	$encore = calculer_visites($t);
216
217
	// Si ce n'est pas fini on redonne la meme date au fichier .lock
218
	// pour etre prioritaire lors du cron suivant
219
	if ($encore)
220
		return (0 - $t);
221
222
	return 1;
223
}
224
?>
0 ignored issues
show
Best Practice introduced by
It is not recommended to use PHP's closing tag ?> in files other than templates.

Using a closing tag in PHP files that only contain PHP code is not recommended as you might accidentally add whitespace after the closing tag which would then be output by PHP. This can cause severe problems, for example headers cannot be sent anymore.

A simple precaution is to leave off the closing tag as it is not required, and it also has no negative effects whatsoever.

Loading history...
225