Code Styling Project

It’s not a bug, it’s always a feature.
  • Deutsch
  • English
  • rss
  • Home
  • Blog
  • Impressum
  • Entwicklungen
  • Fehlerbehebungen
  • Anleitungen

PHP Funktion version_compare korrekt verwenden

codestyling | 29. März 2009 | 14:58

Immer wieder findet man Plugins oder Themes, in denen eine eigentümliche Verwendung von version_compare zu finden ist. Wenn man sich jedoch mal genauer die Beschreibung der entsprechenden Funktion in der verfügbaren PHP Dokumentation durchließt, kommt man zu dem Schluss, das ein Vergleich mit > 2.6.999 nur um für 2.7 testen zu wollen, unnötig ist.
Um dies zu demonstrieren, habe ich eine paar Zeilen PHP Code geschrieben, die dieses zeigen.

was steht in der PHP Dokumentation

Die originale Beschreibung der Funktion version_compare ist leider nicht deutsch verfügbar. Deshalb erkläre ich mal kurz, was das Wichtige daran ist. Die Funktionsdefinition sieht so aus:

PHP
1
mixed version_compare  ( string $version1  , string $version2  [, string $operator  ] )
timing: 0.046s

Es sind also 2 Versionen als Strings nötig, die miteinander verglichen werden. Der 3. Parameter $operator ist optional und gibt den Vergleichsoperator an. Dadurch das dieser Operator optional ist, ist auch das Ergebnis der Funktion nicht direkt definiert, sondern hängt davon ab, ob man einen Operator angegeben hat oder nicht.

ohne den Parameter $operator

Verwendet man die Funktion ohne diesen Operator, ist der Rückgabewert den Funktion ein Zahlenwert der folgende Werte annehmen kann:

  • Ergebnis: -1 … die 1. Versionsnummer ist kleiner als die 2. Versionsnummer
  • Ergebnis: 0 … die beiden Versionsnummern sind gleich
  • Ergebnis: 1 … die 1. Versionsnummer ist größer als die 2. Versionsnummer

mit Verwendung des Parameters $operator

Wenn man einen Vergleichsoperator aus folgender Liste verwendet: <, lt, <=, le, >, gt, >=, ge, ==, =, eq, !=, <>, ne dann ist das Ergebnis ein Wahrheitswert und kann nur TRUE oder FALSE sein, weil man ja auf einen bestimmten Vergleich testet.

was ist mit Entwicklungsversionen, die Buchstaben enthalten ?

Wer sich schon mal mit Entwicklerversionen beschäftigt hat, wird auf Versionen gestoßen sein, die in etwa so aussehen:

  • 2.8-bleeding-edge
  • 2.8RC1-123456

Sogar für die korrekten Vergleiche der Entwicklerversionen und Hauptversionen ist in der PHP Funktion gesorgt. Wenn eine Versionskennung also Sonderzeichen wie: ‘_’ oder ‘+’ oder ‘-’ enthält, werden diese intern erst einmal durch ‘.’ ersetzt. Ebenfalls werden Zahlen von Buchstaben mit ‘.’ getrennt, wenn vorhanden. Zu Beispiel wird: ‘4.3.2RC1′ intern zu ‘4.3.2.RC.1′ umgewandelt, bevor der Vergleich ausgeführt wird.
Die Text Anteile in der Versionsnummer werden nach folgenden Schema geordnet und intern im Vergleich benutzt: dev < alpha = a < beta = b < RC < pl. Damit lassen sich dann auch Entwicklungsversionen korrekt einordnen und vergleichen.

Code Beispiel zur Illustration

Ich habe mal ein paar bekannte Versionskennungen von WordPress in ein kleines Script verpackt und die Vergleichsergebnisse als HTML Tabelle ausgeben lassen. Es ist sehr gut zu sehen, wie die Vergleiche arbeiten.

PHP
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
<?php
$tests = array(
	array('2.7.1' => '2.7.1'),
	array('2.7.1' => '2.7.2'),
	array('2.7.1' => '2.8-bleeding-edge'),
	array('2.8' => '2.8-bleeding-edge'),
	array('2.8alpha' => '2.8-bleeding-edge'),
	array('2.8-bleeding-edge' => '2.8.1'),
	array('2.8-bleeding-edge' => '2.7'),
	array('2.7-bleeding-edge' => '2.8-bleeding-edge'),
	array('2.8' => '2.8alpha'),
	array('2.8' => '2.8RC1-123456'),
	array('2.7' => '2.8alpha'),
	array('2.7.1' => '2.8alpha'),
	array('2.7.2' => '2.8alpha'),
);
 
function test_version_compare($first, $second) {
	$result = '-n.a.-';
	if (version_compare($first, $second, '<')) $result = 'ist kleiner';
	if (version_compare($first, $second, '>')) $result = 'ist größer als';
	if (version_compare($first, $second, '==')) $result = 'ist gleich mit';	
	return $result;
}
?>
<table width="100%" style="text-align:center;">
<?php
foreach($tests as $test) {
	foreach($test as $first => $second) {
?>
	<tr>
		<td><?php echo $first; ?></td>
		<td><?php echo test_version_compare($first, $second); ?></td>
		<td><?php echo $second; ?></td>
	</tr>
<?php
	}
}
?>
 
timing: 0.067s

Das Ergebnis des Aufrufes dieser PHP Seite sieht dann so aus:

2.7.1 ist gleich mit 2.7.1
2.7.1 ist kleiner 2.7.2
2.7.1 ist kleiner 2.8-bleeding-edge
2.8 ist größer als 2.8-bleeding-edge
2.8alpha ist kleiner 2.8-bleeding-edge
2.8-bleeding-edge ist kleiner 2.8.1
2.8-bleeding-edge ist größer als 2.7
2.7-bleeding-edge ist kleiner 2.8-bleeding-edge
2.8 ist größer als 2.8alpha
2.8 ist größer als 2.8RC1-123456
2.7 ist kleiner 2.8alpha
2.7.1 ist kleiner 2.8alpha
2.7.2 ist kleiner 2.8alpha

wie also sollte man die Funktion benutzen

Sehr oft hat man die Anforderung, das ein bestimmter Code-Abschnitt nur bei bestimmten WordPress Versionen ausgeführt werden soll. Sagen wir mal, der Code soll erst ab Version 2.7 ausgeführt werden. In existierenden Plugins findet man nicht selten diesen Test:

PHP
1
if (version_compare($wp_version, '2.6.999', '>')) ...
timing: 0.048s

Man kann das zwar so machen, ist aber nicht im Sinne des Erfinders. Die einfachere und auch verständliche Version des Tests kann man so aufschreiben:

PHP
1
if (version_compare($wp_version, '2.7alpha', '>=')) ...
timing: 0.051s

Dieser Test schließt alle Entwicklungsversionen von 2.7 mit ein und man sieht auf den ersten Blick, das nur eine gleich oder größere Version hier ein TRUE liefern wird.

Ich denke, diese kleine Übersicht über die Funktionsweise von version_compare räumt mit den falschen Vorstellung zur Arbeitsweise dieser Tests ein wenig auf.

Kategorien
Deutsch, WordPress (DE)
RSS Kommentare
RSS Kommentare

« Mathematische Finesse der Abwrack-Prämie WordPress 2.8 ändert das Metabox Modell für Admin Seiten »

1 Antwort    Schreib einen Kommentar

Sergej Müller

Sergej Müller

29.03.2009 | 15:38

Ich glaube, viele Plugin-Entwickler kopieren solche Abfragezeilen einfach irgendwo im Web oder aus einem Plugin heraus ohne nachzudenken, ob es eleganter geht - funktionieren tut es ja. Man vertraut ja der Quelle…

Antworten »

Du kannst diese Tags verwenden : <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

Navigation

  • Allgemein
  • jQuery in WordPress
  • Politik
  • WordPress (DE)

Suche

Neuere Beiträge ...

  • Probleme mit WordPress 2.8 lösen
  • WordPress 2.8 und das jQuery Update
  • “Page Columnist” - Artikel & Seiten in Spaltenformat
  • Plugin Kompatibilitäts-Check von BraveNewCode
  • WordPress 2.8 ändert das Metabox Modell für Admin Seiten

Ältere Beiträge ...

  • Mathematische Finesse der Abwrack-Prämie
  • WordCamp Vortrag “Lokalisierung” als PDF Download
  • Permalinks mit Umlauten ohne o42-clean-umlauts
  • WordPress 2.8 ändert Sprachdatei-Zugriffe
  • Wie verwende ich WordPress Metaboxen in eigenen Plugins
rss RSS Kommentare valid xhtml 1.0 design by jide powered by Wordpress get firefox