2012-04-14 11 views
6

Ich versuche, die Sicherheit meiner Anwendung zu verbessern. Immer wenn ich Daten vom Benutzer (egal ob über POST oder GET) erhalte, die eine ganze Zahl sein sollen, validiere ich das entsprechend. Aber oft sind die Daten VARCHAR und manchmal HTML.Schutz vor SQL-Injektion in ColdFusion

Wie schütze ich in diesem Fall meine Datenbank vor der SQL-Injektion?

Kann <cfqueryparam value="#form.textInput#" cfsqltype="cf_sql_varchar"> die Abfrage davor schützen, eine schädliche SQL-Anweisung innerhalb eines VARCHAR-Werts zu senden?

Antwort

5

Die kurze Antwort auf Ihre Frage ist "Ja".

Ich blockiere Hackversuche mit drei Methoden.

  1. Ich benutze cfqueryparam in allen meinen Datenbankabfragen. Ich werde cfparam am Anfang der Vorlage/cfm-Dateien für URL-Bereichsvariablen verwenden.

  2. Ich habe Portcullis oder Varianten davon verwendet. Sie können es von http://portcullis.riaforge.org/ bekommen. Portcullis wird sich auch gegen Cross-Site-Scripting-Angriffe verteidigen.

  3. Ich verwende Windows IIS 7.5 (Windows Server 2008 R2). Ich verwende die URL-Rewrite-Funktion, um den Großteil der URL-basierten Angriffe zu blockieren. Sie können ähnliche Dinge mit Apache und dem von ihm unterstützten Neuschreiben machen. Hier sind meine IIS URL Rewrite-Regeln:

    <?xml version="1.0" encoding="UTF-8"?> 
    <appcmd> 
        <CONFIG CONFIG.SECTION="system.webServer/rewrite/globalRules" path="MACHINE/WEBROOT/APPHOST" overrideMode="Inherit" locked="false"> 
         <system.webServer-rewrite-globalRules> 
          <rule name="SQL Injection - EXEC - SCRIPT_NAME" stopProcessing="true"> 
           <match url="^.*EXEC\s*[\(|%28].*$" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - EXEC - QS" stopProcessing="true"> 
           <match url=".*" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
            <add input="{QUERY_STRING}" pattern="^.*EXEC\s*[\(|%28].*$" /> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - CAST - SCRIPT_NAME" stopProcessing="true"> 
           <match url="^.*CAST\s*[\(|%28].*$" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - CAST - QS" stopProcessing="true"> 
           <match url=".*" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
            <add input="{QUERY_STRING}" pattern="^.*CAST\s*[\(|%28].*$" /> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - DECLARE - SCRIPT_NAME" stopProcessing="true"> 
           <match url="^.*DECLARE.*$" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - DECLARE - QS" stopProcessing="true"> 
           <match url=".*" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
            <add input="{QUERY_STRING}" pattern="^.*DECLARE.*$" /> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - NVARCHAR - SCRIPT_NAME" stopProcessing="true"> 
           <match url="^.*CHAR\s*[\(|%28].*$" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - NVARCHAR - QS" stopProcessing="true"> 
           <match url=".*" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
            <add input="{QUERY_STRING}" pattern="^.*CHAR\s*[\(|%28].*$" /> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - sp_password - SCRIPT_NAME" stopProcessing="true"> 
           <match url="^.*sp_password.*$" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - sp_password - QS" stopProcessing="true"> 
           <match url=".*" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
            <add input="{QUERY_STRING}" pattern="^.*sp_password.*$" /> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - xp - SCRIPT_NAME" stopProcessing="true"> 
           <match url="^.*%20xp_.*$" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
          <rule name="SQL Injection - xp - QS" stopProcessing="true"> 
           <match url=".*" /> 
           <conditions logicalGrouping="MatchAll" trackAllCaptures="false"> 
            <add input="{QUERY_STRING}" pattern="^.*%20xp_.*$" /> 
           </conditions> 
           <serverVariables> 
           </serverVariables> 
           <action type="CustomResponse" statusCode="403" statusReason="Forbidden" statusDescription="Forbidden" /> 
          </rule> 
         </system.webServer-rewrite-globalRules> 
        </CONFIG> 
    </appcmd> 
    

Diese Regeln werden das C: \ Windows \ System32 \ inetsrv \ config \ applicationHost.config Datei für IIS. Allerdings empfehle ich **** NICHT, dass Sie diese Datei direkt bearbeiten. Ein Fehler und IIS wird nicht geladen. Kopiere stattdessen & die obigen Regeln und speichere sie als "iis-global-rewrite.xml". Dann führen Sie die folgende Batchdatei, die Regeln zu dem IIS-Server hinzuzufügen:

C:\Windows\System32\inetsrv\appcmd.exe set config -in < iis-global-rewrite.xml 

Die IIS Rewrite-Regeln mit IIS arbeiten sollten 7.0 (Windows Server 2008), aber ich habe es nicht getestet.

Diese Regeln können auch auf eine einzelne Site mithilfe der Datei web.config angewendet werden, wenn Sie keinen Zugriff auf den Server haben.

Warum verwende ich drei verschiedene Methoden zum Schutz? Denn keiner von ihnen deckt alle Grundlagen ab. Die IIS-Umschreibungsregeln schützen nur vor URL-basierten Angriffen. Hacker können auch Formular-Submission-Angriffe verwenden, die dasselbe tun. Ich bevorzuge die IIS-Regeln als eine erste Schutzlinie, weil es mit allen Seiten auf dem Server einschließlich PHP, ASP, usw. funktioniert. Portcullis ist eine gute zweite Verteidigungslinie für ColdFusion, weil es formbasierte Angriffe und einige Cross-Site-Scripting fängt Anschläge. Die letzte Verteidigungslinie ist der cfqueryparam/cfparam-Code, der vor URL/formbasierten SQL-Injection-Angriffen schützt.

Wenn alle drei Methoden verwendet werden, sollte der Server/die Site sehr sicher sein. Ich würde immer noch empfehlen, Serverprotokolle von Zeit zu Zeit zu überprüfen, da sich Angriffe entwickeln und verbessern.

+1

Wow, das ist einfach perfekt. Ich führe CF auf IIS, also werde ich definitiv in die Sicherung meiner Web-App mit etwas fortgeschritteneren Umschreibungsregeln schauen. Vielen Dank! – Eleeist

+0

IIS URL Rewrite und Apache mod_rewrite sind sehr nützliche Tools für Verteidigung und SEO. http://blogs.iis.net/ruslany/archive/2009/04/08/10-url-rewriting-tips-and-tricks.aspx hat einige nützliche Beispiele für IIS URL Rewrite. –

6

Die kurze Antwort ist ja.

cfqueryparam wird einige SQL-Injection-Angriffe von auftreten stoppen.

Es gibt andere Angriffsvariablen, die verwendet werden können, seien Sie also vorsichtig, aber gut geschriebene Coldfusion kann sehr sicher sein.

Seien Sie vorsichtig bei Cross-Site-Scripting-Angriffen, wenn Sie Eingabehtml speichern und später anzeigen, achten Sie besonders auf JavaScript-Tags.

+0

Danke! Das war sehr hilfreich. – Eleeist

+3

Die einzige Zeit, in der cfqueryparam einen SQL-Injection-Angriff * nicht * stoppt, hat nichts mit der Art des Angriffs zu tun, sondern mit der Art des Codes in der Datenbank. Wenn Sie beispielsweise eine Datenbankprozedur aufrufen, die ein Varchar-Argument verwendet und diese dynamisch als SQL ausgeführt hat, hilft Ihnen keine Menge an parametrisierten Abfragen. CfQueryParam verhindert * immer * SQL-Injection-Angriffe bei Verwendung von Plain SQL (keine Datenbankprozeduraufrufe usw.). –

+1

Vergessen Sie nicht, 'maxlength' auch in Textfeldern mit variabler Länge zu verwenden, wo es geeignet ist. Wenn Sie wissen, dass ein Textfeld nur Zeichenfolgen mit einer Länge von bis zu 16 Zeichen enthält, müssen Sie keine längeren Zeichenfolgen zulassen, da sie als Fehler gekennzeichnet werden sollten. –