Kann eine URL-Rewrite-Bedingung zwei Servervariablen vergleichen?

Kann eine URL-Rewrite-Bedingung zwei Servervariablen vergleichen?

Ich versuche, zwei Servervariablen als Teil einer URL-Umschreibbedingung zu vergleichen. Aber zuerst etwas Kontext ...

Wenn Sie in IIS ein Verzeichnis anfordern http://www.example.com/foo, foosendet IIS eine 302-Weiterleitung „Objekt verschoben“ http://www.example.com/foo/als „Courtesy Redirect“ (Quelle).

Wenn Sie IIS+ARR als Reverseproxy mit SSL-Offloading verwenden, empfängt der Back-End-IIS-Knoten die Anforderung über http und nicht über https.

Kombinieren Sie diese beiden Verhaltensweisen, und die Höflichkeitsumleitungen von IIS lassen SSL fallen. Die Höflichkeitsumleitung verwendet dasselbe Schema wie die Anfrage, die IIS erhalten hat (Quelle), in diesem Fall http statt https.

Ich möchte eine ausgehende Umschreibregel erstellen, die die eingehende URL mit dem ausgehenden Standortheader vergleicht und sie in diesem Fall von http in https umschreibt:

  • Die Antwort ist eine Umleitung: {RESPONSE_STATUS}ist 302
  • Die eingehende Anfrage erfolgte über SSL: {HTTPS}ist „ein“
  • Die eingehende URL endet nicht mit einem Schrägstrich.
  • Der ausgehende Location-Header endet mit einem Schrägstrich.

All das oben Genannte wird in der Vorbedingung behandelt. Der schwierige Teil ist der letzte Teil:

  • Der Pfad des ausgehenden Location-Headers ist derselbe wie der eingehende URL, allerdings mit einem angehängten Schrägstrich.

Unten ist der Code, den ich bisher habe. Die Vorbedingung und das Umschreiben des Headers funktionieren beide einwandfrei. Die Bedingung verursacht jedoch einen 500-Fehler (URL-Umschreibmodulfehler), vermutlich weil ich {REQUEST_URI}das Muster verwende. Ich habe versucht, die Bedingung in zwei Teile aufzuteilen und Erfassungsgruppen zu verwenden, aber das hat auch nicht funktioniert. Irgendwelche Ideen?

<rule name="Fix: Courtesy Redirect + SSL Offloading = SSL dropped" preCondition="Courtesy Redirect Drops SSL" enabled="true">
    <match serverVariable="RESPONSE_LOCATION" pattern="^http://(.+/)$" />
    <conditions>
        <add input="{RESPONSE_LOCATION}" pattern="{REQUEST_URI}/" />
    </conditions>
    <action type="Rewrite" value="https://{R:1}" />
</rule>
<preConditions>
    <preCondition name="Courtesy Redirect Drops SSL">
        <add input="{RESPONSE_STATUS}" pattern="^302$" />
        <add input="{HTTPS}" pattern="^on$" />
        <add input="{REQUEST_URI}" pattern=".*[^/]$" />
        <add input="{RESPONSE_LOCATION}" pattern="^http://.+/$" />
    </preCondition>
</preConditions>

Antwort1

Sie können einbenutzerdefinierter Rewrite-Anbieter.Ein Provider ist C#-Code, der einen String in einen anderen String umwandelt. Sie können ihn dann auf ähnliche Weise verwenden wie rewrite map:

Sie können ein Trennzeichen auswählen, das in einer URL überhaupt nicht gültig ist. (Verwenden Sie möglicherweise ein Leerzeichen oder etwas Ähnliches. Ich werde es verwenden, |damit es in diesem Beitrag sichtbar ist, aber Sie sollten eine andere Zeichenfolge auswählen.)

Sie schreiben eine Regel, um den Wert der Servervariable festzulegen IsItMatching. Der Wert der Servervariable wird mithilfe Ihres benutzerdefinierten URL-Rewrite-Providers festgelegt:

{provider_name:{server_variable_1}|{server_variable_2}}

Der C#-Code, der den Provider implementiert, führt dann Folgendes aus (Pseudocode, keine Fehlerprüfung):

string Rewrite(string input)
{
    string[] inputVariables = input.split(separator);
    if (inputVariables[0] == inputVariables[1] + "/")
        return "yes";
    else
        return "no";
}

Anschließend schreiben Sie eine weitere Regel, um zu prüfen, ob der Wert der IsItMatchingServervariable „Ja“ oder „Nein“ ist.

verwandte Informationen