Regular Expressions, ein Anfang

Mischa Sameli, Geschäftsführer & Leiter Entwicklung

Regular Expression, kurz RegEx, sind eine ausgezeichnete Möglichkeit für Suchen und Ersetzen mit Unbekannten. In der Programmierwelt sind Regular Expressionen sehr verbreitet, da sie sich eben sehr zum suchen und ersetzen eignen. So unabdingbar reguläre Ausdrücke für die Programmierung sind, so komplex und vielfältig ist der Aufbau derselbigen – deshalb eine kleine Einführung ins Thema.

So funktioniert zum Beispiel der Word-Import-Filter im Editor in unserem CMS nur mit Regular Expressionen. Denn mit Suchmustern lassen sich Microsofts unzählige Varianten von abartigen Schriftformatierungen überhaupt irgendwie erfassen. Da kann man nicht nach einer bestimmten Zeichenfolge suchen.
Leider unterscheiden sich die Regeln von Programmiersprache zu Programmiersprache, nur die Idee ist immer ähnlich. Und da ich mir Regular Expressions, respektive die Methodik eh nie merken kann, beginne ich hier eine neue Sparte.

Beispiel 1: leere Links

Web-Editoren generieren gerne einmal leere Links, HTML-Formatierungen, die keinen Sinn ergeben. Hauptsächlich sind diese leeren Links dank den Thumbnails entstanden. Zum Beispiel, wenn man ein Bild als Thumbnail einfügt und dann das Bild löscht, kann es vorkommen, dass ein Editor nur das Bild entfernt, nicht aber den Link, der um das Bild herum gestanden hat. So bleibt also Link-Leiche stehen. Naja ist ja nicht so schlimm, ein leerer Link ist ja unsichtbar (ausser er hat das css-attribut display:block !). Und im Linkchecker erscheinen vielleicht einmal Links, welche es gar nirgends mehr gibt, respektive nicht ersichtlich sind. Trotzdem ist sowas natürlich störend, und auch nicht valid im Sinne des W3C.
Was tun? Filtern, richtig, aber wie. Wonach würdet Ihr jetzt spontan suchen? Schwierig was? Hier eine Lösung, es gibt sicher auch bessere:

1Suche nach <a href="http://www.tol.ch"></a>
2
3RegEx:
4<a([^>]*)>
</a>

Übersetzt heisst das: Der Text muss mit "<a beginnen, bis zum nächsten > kann dann alles mögliche auftauchen (title, class, style, tabindex – man weiss es einfach nicht), und dann muss der Tag gleich geschlossen sein. Alles zusammen ergibt dann folgenden CF-Code:

1REReplaceNoCase( clean, "<a([^>]*)></a>", "", "ALL" )

Nett oder? Ja, aber leider gibts da noch ein Problem: Anker. Anker werden hiermit natürlich auch entfernt – den Rest der Geschicht könnt ihr euch denken. Also würde die komplette RegEx dann so heissen:

1REReplaceNoCase( clean, "<a ([^name=])([^>]*)></a>", "", "ALL" )

Beispiel 2: ganze Tags Filtern

Wir möchten also ganze Tags herausfilten, aus unbestimmten Zwecken. Ich gehe mal weiter im Beispiel, dass ich letzte Woche gebraucht habe. Im Editor brauche ich für den Shop eine Möglichkeit, die Formulare bearbeiten zu können. Dazu habe ich als Grundlage nur eine Tabelle – aber leider keine Formular-Tags. Um ein Formular per JavaScript aber bearbeiten zu können, brauche ich ein Formular. Also muss ich beim Öffnen der Tabelle nur zum Bearbeiten ein Pseudo-Formular rundherum platzieren. Diese form-Tags sollen beim Speichern aber wieder entfernt werden. Also im Gegensatz zum Beispiel 1 sieht die Ausgangslage hier so aus:

1Filtern nach:
21. <form ....
32. </form>

Der ganze Code zwischen beiden Tags muss natürlich stehen bleiben. Also konzentrieren wir und nur auf die beiden Tags. Und auch hier ist die Lösung simpel:

1<(/)?form([^>]*)>

Wir beginnen mit einem "<", dann kann bereits "/" folgen, wenn nämlich der Endtag gefunden wird. Dieses Muster bilden wir mit "(/)?" ab. danach kommt in jedem Fall "form" und anschliessen kann wieder wie bei Beispiel 1 alles Mögliche folgen bis zu zum ">". Dies wird wieder abgebildet mit "([^>]*)>". Zusammengesetzt gibt es folgenden Code:

1REReplaceNoCase( clean, "<(/)?form([^>]*)>", "", "ALL" )

Das waren nun einmal einfache Beispiel, und da gibt es noch viele, viele mehr. Und dann wäre da noch ein Link: http://www.regxlib.com/