Wie schreibe ich eine XML Schnittstelle
Ich möchte euch hier demonstrieren wie man eine XML Schnittstelle einfach und schnell
programmiert...
Wir haben auf der einen Seite einen Script, der eine XML Anfrage an den Server schickt
und auf der anderen Seite einen Script, der die Anfrage bearbeitet.
Angenommen wir wollen 3 Funktionalitäten über XML steuern können:
ADD, UPDATE und DELETE sprich Hinzufügen, Ändern und Löschen.
Als erstes zeige ich euch wie man ein XML erzeugt und an den Server sendet:
Code
<?
function createxml($array) {
$buf = '';
foreach($array as $key => $value)
{
if(is_array($value))
{
$buf .= "<".strtolower($key).">" . createxml($value) . "</".strtolower($key).">n";
}
else{
$buf .="<".strtolower($key)."><![CDATA[$value]]></".strtolower($key).">n";
}
return $buf;
}
$aPOST["content"]["id"] = "2";
$aPOST["content"]["author_id"] = "1";
$aPOST["content"]["header"] = "Wir schreiben eine XML Api";
$aPOST["content"]["content"] = "Ich möchte euch hier Demonstrieren wie man eine
XML Schnitstelle..";
$aPOST["content"]["date"] = date("Y-m-d H:i:s");
$url = 'http://www.codejungle.org/xml-api.php';
$POST["cmd"]="ADD";
$POST["apikey"]="kmlnjierg8795th2bughj3fg02jgkm0ggi";
$POST["data"]=createxml($aPOST);
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
//curl_setopt($ch, CURLOPT_USERPWD, $user . ':' . $pwd);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $POST);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$feedback = curl_exec($ch);
$ErrNum = curl_errno($ch);
$ErrMsg = curl_error($ch);
curl_close($ch);
echo $feedback;
?>
Wir erstellen hier mit Hilfe der createxml Funktion aus einem Array eine XML
Datei. Danach senden wir mit Hilfe von curl drei Parameter an die Datei xml-api.php,
cmd damit unser Script weiß, welche Funktion er aufrufen soll, in unserem Fall ADD,
den API Key um sicherzustellen, dass nicht jeder die Schnittstelle benutzen kann und
data die eigentliche XML Datei.
Nun müssen wir einen Script erstellen, der die Anfrage entgegennimmt und richtig
verarbeiten kann.
Code
<?
$allowed_api_keys=array("kmlnjierg8795th2bughj3fg02jgkm0ggi");
//check if api key is valid
if(in_array($_POST[apikey], $allowed_api_keys)){
switch($_POST[cmd]){
case ADD;
$xml = simplexml_load_string($_POST[data]);
foreach($xml as $name => $value){
echo "$name => $value";
}
break;
default:
echo "Please check your provided command";
break;
}
} else {
echo "Your API - Key is invalid";
}
?>
Diese Datei überprüft zuerst ob der gesendete API Key existiert,
wenn ja, überprüfen wir noch welche Funktion übergeben wurde (in unserem Fall ADD).
Hier laden wir die XML Datei mit Hilfe der simplexml_load_string Funktion ein und
geben sie anschließend aus.
Man kann nun eine Funktion schreiben, die die übergebenen XML Daten weiter verarbeitet.
Die meisten Probleme machen nach meiner Erfahrung Umlaute und Sonderzeichen,
sie führen oft zu parse errors. Dies kann man teilweise mit Hilfe des Tags
lösen, wobei der Tag selbst allerdings auch zu parse errors führen kann...
Auf Wunsch von einem guten Freund möchte ich auch noch auf XML-RPC und Soap hinweisen,
beide eignen sich ebenfalls zur Remote XML Verarbeitung.
Ich hoffe euch hat mein kleiner Exkurs gefallen und freue mich über eure Kommentare.
LG
Andreas
2008-10-19 14:54:39
Comments (0) | Permalink | PDF Download
Shoutbox mit PHP und Ajax
Hallo,
nachdem mir heute etwas langweilig war und ich alles machen wollte, nur nicht das was ich sollte, hier ein kleiner Script der eine Shoutbox erzeugt.
Das Besondere ist, er kommt ohne Datenbank aus und benutzt ajax damit neu hinzugefügte Inhalte gleich angezeigt werden. Man kann ihn also auch als simplen Chatscript benutzen. Noch nicht implementiert sind Smilies, sollte sich aber mit str_replace recht einfach umsetzen lassen.
Source Code Downloaden | Demo
Code
<?php
# Shoutbox 1.0
# by Andreas Beder
# codejungle.org
# Licence GNU GPL 2
//config
$filename="content.txt";
// be sure the file have write permissions
$url="http://www.codejungle.org/shoutbox/";
//function
function get_content(){
global $filename;
$lines = file ($filename);
$start = count($lines)-12;
if ($start < 1) $start = 1;
for ($i = $start; $i < count ($lines); $i++){
$somecontent.=stripslashes($lines[$i]);
}
return $somecontent;
}
function add_content(){
global $filename;
if($_POST[submit] and $_POST[nick] and $_POST[content]){
//check content
//add content
$_SESSION["nick"]=$_POST[nick];
$somecontent=strip_tags($_POST[nick]).": ".strip_tags($_POST[content])."<br/>n";
$handle = fopen($filename, 'a+');
fwrite($handle, $somecontent);
}
}
function output_form(){
echo '
<form action="" method="post">
Nick:';
if($_SESSION[nick]){echo $_SESSION[nick].'<input type="hidden" name="nick" value="'.$_SESSION[nick].'"><br>';} else { echo '<br>
<input name="nick" type="text" value="'.$_SESSION[nick].'"><br>'; }
echo'
Text:<br>
<textarea rows="5" cols="100" name="content"></textarea><br>
<input type="submit" name="submit" value="save">
</form>
';
}
if($_GET[content]=="true"){
echo get_content();
die();
}
?>
<html>
<head>
<title>shoutbox demo</title>
<script type="text/javascript" language="javascript">
var http_request = false;
function macheRequest(url) {
http_request = false;
if (window.XMLHttpRequest) { // Mozilla, Safari,...
http_request = new XMLHttpRequest();
if (http_request.overrideMimeType) {
http_request.overrideMimeType('text/xml');
// zu dieser Zeile siehe weiter unten
}
} else if (window.ActiveXObject) { // IE
try {
http_request = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
try {
http_request = new ActiveXObject("Microsoft.XMLHTTP");
} catch (e) {}
}
}
if (!http_request) {
alert('Ende :( Kann keine XMLHTTP-Instanz erzeugen');
return false;
}
http_request.onreadystatechange = alertInhalt;
http_request.open('GET', url, true);
http_request.send(null);
}
function alertInhalt() {
if (http_request.readyState == 4) {
if (http_request.status == 200) {
document.getElementById("shoutbox").innerHTML=http_request.responseText;
var objDiv = document.getElementById("shoutbox");
objDiv.scrollTop = objDiv.scrollHeight;
setTimeout('macheRequest("<?php echo $url; ?>?content=true")',2000);
} else {
alert('Bei dem Request ist ein Problem aufgetreten.');
}
}
}
</script>
</head>
<body onload="macheRequest('<?php echo $url; ?>?content=true');">
<? add_content(); ?>
<div style="border:1px solid #ccc; width:500px; height:300px; max-height:300px; overflow:auto;"
name="shoutbox" id="shoutbox">
</div>
<? output_form(); ?>
</body>
</html>
Beachte, dass die content.txt Schreibrechte für den Webserver haben sollte.
Unter *nix geht das folgendermaßen:
chmod 640 content.txt && chown nobody:nogroup content.txt
Ich hoffe euch hat mein Script gefallen, über Verbesserungsvorschläge freue ich mich natürlich auch.
LG
Andreas
2008-10-11 00:46:14
Comments (17) | Permalink | PDF Download
PHP und MySQL Tuning
1. PHP caching mit eaccelerator
2. MySQL und Indexes
3. MySQL socket over TCP
4. PHP Sessionhandler DB
5. Temp- Dateien von MySQL und PHP
6. Codeprofiling
7. MySQL- Proxy
8. Benchmarking
1. Caching mit eaccelerator
eaccelerator ist eine gute Wahl für Server, die eine hohe Last bewältigen müssen.
Die Vorteile liegen darin, dass PHP Skripte nicht bei jedem Aufruf neu gelesen und
interpretiert werden müssen, was bei mehreren Anfragen Zeit spart.
Ausserdem schont es die Festplatte, da der interpretierte Code im RAM gehalten wird.
Es gibt diverse Benchmarks die belegen sollten, dass eaccelerator eines der besten Cachingsysteme für PHP ist.
Ich selber verwende eaccelerator seit mehreren Jahren und bin sehr zufrieden.
2. MySQL und Indexes
Etwas worauf man immer wieder stößt, wenn man sich mit Performance und MySQL beschäftigt, ist die Aufforderung Indexe richtig zu setzen. Dem kann man eigentlich wenig hinzufügen.
Es hat sich gezeigt, dass gerade bei größeren DBs die Geschwindigkeit dramatisch gesteigert werden kann, wenn man seine Indexes richtig setzt.
Die MySQL Funktion "explain" hilft dabei queries zu optimieren.
3. MySql und Sockets
Wenn es möglich ist, sollte man Socket- Verbindungen der TCP- Verbindung vorziehen, da TCP- Verbindungen meist nur ein unnötiger Overhead sind. Manche Seiten berichten von einem Performancegewinn bis zu 20 %.
Die Verbindung lässt sich in PHP relativ einfach aufbauen,
entweder man verwendet beim mysql_connect localhost, dann versucht die Funktion
selbstständig eine Socket- Verbindung aufzubauen, oder man gibt den Pfad direkt an:
Code
<?php mysql_connect("/tmp/mysql.sock", "root", "pass"); ?>
4. PHP Sessionhandler
Ich verwende seit kurzem für mein CMS einen Datenbank- Sessionhandler, weniger aus Performance- Gründen, als mehr zur Lastverteilung.
Wie ein Datenbank- Sessionhandler ausschaut, könnt ihr euch hier ansehen:
http://www.codejungle.org/tag/Database_Session_handler_for_php/3.html
5. Temp- Dateien von MySQL und PHP
Temporäre Dateien von MySQL und PHP kann man auch im RAM speichern,
dazu legt man einfach ein Verzeichnis im tmp Ordner an:
mkdir /tmp/ram
und weist einen Teil des Arbeitsspeichers diesem Verzeichnis zu (in dem Fall 150mb):
/bin/mount -t tmpfs /dev/shm /tmp/ram/ -o size=150m
Danach muss man MySQL und PHP nur noch sagen wo sie die Temp Dateien speichern sollen.
MySQL mit dem Parameter --tempdir=/tmp/ram/ starten
und in der php.ini den session.save_path auf /tmp/ram/ setzen.
Nach meinen Tests hat dies zwar nicht viel Performance gebracht, aber naja, Kleinvieh macht auch Mist.
6. Code Profiling
Code Profiling ist eine nützliche Methode um seinen Code zu verbessern.
Man sieht, welche Funktionen wie viel Speicher, CPU und Zeit brauchen und kann
dann seinen Code optimieren. Ich selber habe xdebug zum optimieren verwendet,
es gibt aber auch noch eine Reihe anderer Profiler.
mod-top z.B. habe ich mir bisher zwar noch nicht näher angeschaut, es scheint aber auch relativ brauchbar zu sein.
7. MySQL- Proxy
MySQL- Proxy kann man als DB Lastenverteiler, aber auch als eine Failover Lösung benutzen.
Ich selber habe einige Lastenverteiler getestet und hier meine Ergebnisse veröffentlicht:
http://www.codejungle.org/tag/Lastenverteilung_mit_MySQL_und_SQLrelay/5.html
8. Benchmarking
Bevor man in den produktiven Betrieb geht sollte man seine Anwendung immer einem Benchmark unterziehen.
Eine einfache Methode ist AB, was für Apache Benchmark steht.
Mit AB ist es möglich mehrere Anfragen paralell an den Webserver zu senden und in den meisten Fällen kann man so auch die Grenzen des Servers ermitteln.
Beispiel für einen Befehl:
ab -c 100 -n 100 http://testserver.com/
Apache Benchmark ist bei der Default- Installation von Apache dabei.
Desweiteren möchte ich auf memcache aufmerksam machen, ich selber habe zwar keine praktischen Erfahrungen mit dem Object- Cachingsystem, doch ich denke, dass es für HighLoad Anwendungen durchaus interessant ist.
Ich hoffe euch hat der Beitrag gefallen.
MFG
Andreas
Quellen:
http://eaccelerator.net/
http://www.xdebug.org/
http://www.mod-top.org/
http://forge.mysql.com/wiki/MySQL_Proxy
http://www.mysqlperformanceblog.com/
http://www.h07.org/projects/apachetuning/#21
http://www.danga.com/memcached/
2008-09-01 19:21:13
Comments (0) | Permalink | PDF Download
PHP im Hintergrund starten
Hallo,
nach meinem Urlaub mal wieder ein kleiner Artikel zum Thema PHP.
Manchmal ist es nützlich einen in den Hintergrund zu legen, dies dient zum Beispiel dazu bei rechen- und zeitintensiven Prozessen den Benutzer nicht warten zu lassen.
Code
<?php shell_exec("nohup php /var/www/test.php > /dev/null 2> /dev/null & echo $"); ?>
Die PHP Funktion shell_exec führt eine shell Befehl aus.
nohup nabelt ein Programm vom Elternprozess ab
php -q /var/www/test.php führt den PHP Script aus, der im Hintergrund laufen soll.
> /dev/null leitet die Ausgabe ins Nirgendwo um.
Wenn also diese Zeile im Browser geöffnet wird, wird ein Subprozess von php gestartet, das bedeutet der Benutzer kann weitersurfen, während der Prozess auf dem Server weiter läuft.
Leicht ist das z.B. mit einer Endlosschleife zu testen.
Um sich aktive Prozesse am Server anzusehen genügt z.B. folgender shell Befehl:
ps aux | grep php
Ich hoffe der Beitrag hat euch gefallen und freue mich über euer Feedback.
MFG
Andreas
2008-08-30 18:54:05
Comments (0) | Permalink | PDF Download
