Regex für propitären Code > HTML

S

Saski

Aktives Mitglied
Thread Starter
Dabei seit
06.02.2005
Beiträge
658
Reaktionspunkte
0
Huhu! :)

Bin grad am überlegen. Was ist effektiver? Ich will eigene [bla]-Tags durch <bla>-Tags (HTML) ersetzen. Nach [bla]*[/bla] suchen, oder einmal nach [bla] und dann nach [/bla]?

Saski bunny
 
So mache ich es.

PHP:
	function reg_express(&$html) {
		$html = htmlspecialchars($html);
		$html = ereg_replace("\r","",$html);
		$html = ereg_replace("\n\n","</p><p>",$html);
		$html = ereg_replace("\n","<br />",$html);
		$html = ereg_replace("\[TAB]","<ul>",$html);
		$html = ereg_replace("\[TABSTOP]","</ul>",$html);
		$html = ereg_replace("\[L]","<li>",$html);
		$html = ereg_replace("\[EL]","</li>",$html);
		return $reg_express;
		}
 
Saski schrieb:
Huhu! :)

Bin grad am überlegen. Was ist effektiver? Ich will eigene [bla]-Tags durch <bla>-Tags (HTML) ersetzen. Nach [bla]*[/bla] suchen, oder einmal nach [bla] und dann nach [/bla]?
Mit regexes in PHP habe ich ehrlich gesagt nicht so viel Erfahrung.
Unter Perl würde mit [bla]*[/bla] das Problem entstehen, dass der * gierig (greedy) ist.
Das heisst [bla]*[/bla] würde beim folgenden Beispiel komplett matchen:
Code:
[Color=blue][bla][/COLOR]eins[/bla] was anderes [bla]zwei[/bla]noch was
neue Zeile [bla]drei[/bla]
und so weiter
[bla]vier[COLOR=blue][/bla][/COLOR]
Ist vielleicht nicht das, was Du gerne hättest.
Wie das unter PHP aussieht, kann ich nicht sicher sagen, aber ich fürchte ähnlich.

HTH
 
Saski, findet das auf dem Server oder lokal statt?

Vorausgesetzt, deine Syntax folgt dem Prinzip "Spitze Klammer auf" ["Slash"] ["dein_tag"] "Spitze Klammer zu", wäre es am effizientesten, nur den Teil nach dem (optionalen) Slash zu ersetzen, also statt:
PHP:
$html = ereg_replace("<blub>","<li>",$html);
$html = ereg_replace("</blub>","</li>",$html);
einfach nur
PHP:
$html = ereg_replace("blub>","li>",$html);
ersetzt alle einleitenden und schließenden Tags in einem Rutsch.

(Beispiel von dir wäre nett!)

cheers

PS: bei möglichen Überschneidungen wie <blub> und <blablub> müsste <blablub> natürlich zuerst geparst werden ...
 
Zuletzt bearbeitet:
Du solltest RegEx verwenden, weil diese dann Fehler im Properitärcode abfangen können. Wenn du z. B. auf
Code:
[b][i]hello, world[/ b]
ein normales str_replace() losläßt, wird daraus:
Code:
<b><i>hello, world</b>
Und das ist kein gültiges HTML. Ein regulärer Ausdruck würde dann nur
Code:
<b>[i]hello, world</b>
also gültiges HTML erzeugen.

Hinweis: Im ersten Beispiel oben mußte ich einen Leerschritt beim schliessenden Tag setzen, weil die Forumssoftware das leider als BBCode interpretiert hat – selbst in einem Code-Block.
 
Zuletzt bearbeitet:
Danke für eure Antworten! Werd das definitiv mit ein paar Regexen machen, geht doch viel einfacher, als da jetzt noch Irgendwas von PEAR einzubinden *g*

@Brandhoff: Es muss aus Kompatibilitätsgründen mit eckigen Klammern sein. Wie wär's damit?
PHP:
$html = eregi_replace("\[(.*?)b\]","<\\1b>",$html);
(Hab's jetzt nicht getestet)

@Ulfrinn: Ja, das ist natürlich ein Vorteil. Aber dauert das Parsen dann nicht doppelt so lange? :(

@Maceis: Das Fragezeichen im Schnipsel oben sorgt (soviel ich weiss) dafür, dass es nicht greedy ist :)
 
Bzgl. der Geschwindigkeit mußt du dir wahrscheinlich nicht allzuviele Gedanken machen. Du kannst ja einfach mal testen, wie lange PHP für so eine Seite braucht – Du wirst sehen, daß das relativ schnell ist. Vorausgesetzt, du willst nicht bei jedem Aufruf die Bibel parsen. ;)
 
Saski schrieb:
...
@maceis: Das Fragezeichen im Schnipsel oben sorgt (soviel ich weiss) dafür, dass es nicht greedy ist :)
Ja, in Perl ist das zumindest so.
Da musst Du allerdings dafür sorgen, dass alle vorkommen ersetzt werden und nicht nur das erste.
 
Wenn damit Code umgewandelt werden soll, der aus unsicherer Quelle kommt (Benutzereingaben), dann würde ich flugs auf Pear setzen, bevor du dir eine XSS Schwachstelle einbaust. Der Code in Pear unterliegt Qualitätsrichtlinen.

[script src="http://www.boese.de/attacke.js"></script> <foob]
 
... da muß ich doch gerade noch mal fragen, wie viele Tags ersetzt werden und wie die jeweils aussehen. Ob die Klammern in der Ausgangsdatei nun rund oder eckig sind, spielt dabei eine untergeordnete Rolle, auch wie die Ausgangs- und Ziel-Tags genau heißen, ist eigentlich egal.

Weil ich ein Freund von simplen Lösungen bin, würde ich bei mehreren Tags ein simples Array mit den zu verwurstenden Tags füllen und das in einer Schleife abarbeiten lassen, womit auch das von Nogger angeführte Problem im Grunde umgangen wäre, weil wir so nur explizite Positiv-Fälle parsen.

PHP:
$arrTagShredder = array (h1,h2,p,b,i,ul,ol,li);

for ( $i = 0; $i < sizeof ( $arrTagShredder ); $i++ ) {
	$html = eregi_replace ( "\[(/?)" . $arrTagShredder[$i] . "\]", "<\\1" . $arrTagShredder[$i] . ">", $html );
}

// Klammer auf, optionaler Slash (und *nur* dieser), Tag, Klammer zu
// Bei Abweichungen wie b -> strong wäre ein zweidimensionales Array der Weg, ekloa.

(wobei ich den Text ja einmal nach der Eingabe prüfen, gegenenfalls gleich parsen und dann ablegen würde ... die Parserei mittels RegExp ist nicht eben performant.)
 
Es soll sich um ein Forum handeln, weshalb die Beiträge auch nachträglich bearbeitbar bleiben sollen. Aber könnte die Beiträge natürlich auch wieder "rückwärts" parsen ;)
Ich mach mal eine Liste von den Tags:
[b ]bla[/b] -> <b>bla</b>
[i ]bla[/i] -> <i>bla</i>
[u ]bla[/u] -> <u>bla</u>
[center ]bla[/center] -> <center>bla</center>
[color=[i]dunkelschwarz[/i]][/ color] -> <span color="dunkelschwarz"></span>
[sn] -> <img src="img/sn.gif">
:) , ;-) , :,-( , usw. -> <img src="img/sn.gif">
 
Zurück
Oben Unten