Wikiup:Technik/Skin/JS/Encoding

aus Wikipedia, der freien Enzyklopädie
< Wikiup:Technik‎ | Skin‎ | JS

Diese Seite gibt Möglichkeiten an, wie im JavaScript-Code für Wiki-Projekte das URL-Encoding umgesetzt werden kann, also das Verbergen von Sonderzeichen sowie Schriftzeichen außerhalb des ASCII-Zeichensatzes. Neben der Hauptanwendung bei der Bildung von URL gibt es auch andere Situationen, für die die Methoden genauso verwendet werden können und müssen. Das Verbergen der Zeichen wird auch als Maskieren oder Kodieren bezeichnet.

Situation und Sonderzeichen

Es gibt unterschiedliche Anforderungen an das Resultat des Vorgangs. Abhängig davon kommen unterschiedliche Funktionen in Frage; möglicherweise muss mit einem kleinen Eingriff nachgesteuert werden.

  • Sicherheit gegen böswillig untergeschobenen Schadcode.
    • Zu maskieren sind in URL vor allem: ' " und bei erhöhten Anforderungen auch ( ).
    • Bei generiertem HTML auch < >.
  • Funktionstüchtigkeit von URL, die freie Daten transportieren sollen.
    • Insbesondere sind Leerzeichen, # % und & hinderlich.
  • Lesbarkeit der produzierten URL.
    • Oft wird gewünscht, bei allen notwendigen Maskierungen von Zeichen die URL so lesbar wie möglich zu halten.

Zu beachten ist, dass auf der kodierenden Seite nicht jede Form der Dekodierung unterstützt werden muss.

  • Wo Webserver angesteuert werden, sind sie nicht verpflichtet, jede Form der „Prozentkodierung “ zu verstehen. Soweit Software für Server nach 2000 geschrieben wurde, wird ein breites Spektrum beherrscht. Teilweise wird aber für die Dekodierung des HTTP GET nur ein eingeschränktes Repertoire unterstützt. Hinzu kommt, dass vor 2000 geschriebene Server-Software möglicherweise nur knapp 200 8-Bit-ANSI-Zeichen erwartet, während heute umfassende UTF-8-Zeichen üblich sind.
  • Leerzeichen können auf drei verschiedene Arten kodiert sein:
    1. Als Pluszeichen + im traditionellen Query-Format,
    2. als %20 bei der Prozentkodierung,
    3. als _ in der Wiki-Software.
  • Zur Kodierung der ANSI-Zeichen von 160 bis 255 gibt es zwei verschiedene Techniken:
    1. Als direkte Kodierung mit Prozentzeichen und zwei Oktetts.
      • ü wird zu %FC (25210).
    2. Als UTF-8-Kodierung.
      • ü wird zu %C3%BC

Funktionen zur Kodierung

Funktion Herkunft kodierte Sonderzeichen Resultat Leerzeichen
escape(s) JavaScript 1.0 ! " # $ % & ' ( ) , : ; < = > ? [ \ ] ^ ` { | } ~ ANSI; ü%FC %20
encodeURI(s) JavaScript 1.5 " % < > [ \ ] ^ ` { | } UTF-8; ü%C3%BC
encodeURIComponent(s) " # $ % & + , / : ; < = > ? @ [ \ ^ ` { | }
mw.util.rawurlencode(s) mediawiki.util ! " # $ % & ' ( ) * + , / : ; < = > ? @ [ \ ] ^ ` { | } ~
mw.util.wikiUrlencode(s)

mw.util.getUrl(s)

" # % & ' + < = > ? [ \ ] ^ ` { | } _
s.replace(re,ex) JavaScript 1.2 beliebig; re=Regulärer Ausdruck, ex=Austausch
mw.html.escape(s) mediawiki.html < > ' & " HTML-Entity
{{urlencode:}}
{{urlencode:|QUERY}}
Wiki-Parser ! " # $ % & ' ( ) * + , / : ; < = > ? @ [ \ ^ ` { } ~ UTF-8; ü%C3%BC +
{{urlencode:|PATH}} ! " # $ % & ' ( ) * + , / : ; < = > ? @ [ \ ^ ` { } %20
{{urlencode:|WIKI}} " # % & ' + < = > ? [ \ ^ ` { } ~ _
{{anchorencode:}} ! " # $ % & ' ( ) * + , / ; < = > ? @ [ \ ^ ` { } ~ UTF-8; ü.C3.BC _

Dabei steht s jeweils für die Ausgangs-Zeichenkette; das Ergebnis der Funktion ist jeweils die transformierte Zeichenkette.

Individuell kann man sich jedes einzelne Zeichen wie folgt umkodieren; hier die Umwandlung aller Leerzeichen in Unterstreichungsstriche:

  • s.replace( / /g, '_' )

Funktionen zur Dekodierung

Funktion Herkunft Gegenstück Bemerkung
unescape(s) JavaScript 1.0 Nur escape(s) Kein UTF-8
decodeURI(s) JavaScript 1.5 encodeURI(s) Oft kein ANSI
decodeURIComponent(s) JavaScript 1.5 encodeURIComponent(s)
mw.Title.getFragment(s) mw.Title .3C<
s.replace(re,ex) JavaScript 1.2 beliebig; re=Regulärer Ausdruck, ex=Austausch

Im Regelfall sollten diese Funktionen kein Pluszeichen in ein Leerzeichen umwandeln, weil das Gegenstück dies bei der Kodierung auch nicht macht.

Die Funktionen mit decodeURI können meist sämtliche Prozentkodierungen in einfache Zeichen zurückwandeln, sofern es sich um UTF-8 handelt. ANSI-Kodierungen statt UTF-8 führen mitunter dazu, dass nicht nur nicht dekodiert wird, sondern die Funktion und dann das ganze Skript abstürzt.

Bei einer unbekannt vorgefundenen URL weiß man nicht, welches Kodierungsverfahren angewendet wurde. Dann sollte sicherheitshalber die folgende Konstruktion benutzt werden:

try {
   s  =  decodeURIComponent(u);
} catch (e) {
   s  =  unescape(u);
}

Falls der erste Versuch („try“) einen fatalen Fehler auslöst, wird nicht gleich die gesamte Skript-Ausführung beendet, sondern es wird bei catch weiter ausgeführt. Für unescape() gibt es dann keine unzulässigen Kombinationen, und es ist kein Absturz zu befürchten.

Die Dekodier-Funktionen können unterschiedlich intelligent ausfallen. In den meisten Fällen ist es von der Logik her unterscheidbar. Hat das erste Oktett-Zeichen einen Wert von 160 bis 191, muss es als ANSI kodiert sein. Liegt es zwischen 192 und 255, dann wäre es UTF-8, falls das folgende Zeichen auch Prozent-kodiert ist, und ANSI, wenn das nicht der Fall ist. Pfiffige Funktionen könnten also auch universell dekodieren.

Individuell kann man hier wieder jedes einzelne Oktett oder Zeichen selbst umkodieren; hier beispielsweise die Rücktransformation aller Leerzeichen nach verschiedenen Methoden (die sich auch in einem einzigen regulären Ausdruck zusammenfassen ließen):

s  =  u.replace( /%20/g, ' ' ).replace( /_/g, ' ' ).replace( /\+/g, ' ' );