I dagens handledning lär vi oss hur du smärtfritt skyddar din CodeIgniter (pre 2.0) -applikation mot angreppssökningar angående Cross-Site Request Forgery. Biblioteket vi ska skapa idag kommer att automatisera alla skyddsmekanismer, vilket gör din webbplats starkare och säkrare.
Ansökningar om förfalskning på flera sidor är baserade på oskyddade formulär på dina webbplatser.
En angripare kan skapa en falsk form på sin webbplats - till exempel en sökformulär. Den här blanketten kan ha gömda inmatningar som innehåller skadliga data. Nu skickas formuläret inte till attackerens webbplats för att utföra sökningen. I verkligheten pekar formuläret på din webbplats! Eftersom din webbplats kommer att lita på att formuläret är äkta, går det igenom och utför de begärda (och kanske skadliga) åtgärderna.
Tänk dig att en användare är inloggad på din webbplats och omdirigeras till attackerens webbplats av någon anledning (phishing, XSS, du heter det). Attackerens formulär kan peka på ditt kontoets borttagningsformulär på din webbplats. Om användaren utför en "sök" på attackerens webbplats kommer hans konto att raderas utan att han vet!
Det finns många sätt att förhindra dessa typer av attacker.
POSTA
begära, jämföra det inlämnade token till den som finns i butiken och, om de skiljer sig, neka förfrågan. Din webbplats måste ändå skyddas mot XSS, för, om det inte är så, blir den här metoden värdelös.Vi måste göra tre saker för varje förfrågan:
POSTA
begära, validera det inlämnade token. För att göra detta automatiskt använder vi CodeIgniter krokar. Krokar tillåter oss att utföra alla åtgärder på olika delar av förfrågan. Vi behöver tre:
Låt oss börja. Vi går steg för steg för att förklara allt så noggrant som möjligt. Vi skapar den metod som genererar token först, så vi kan testa allt rätt efteråt. Skapa en fil i din system / application / krokar
mapp som heter "csrf.php
"och klistra in följande kod:
CI = & get_instance ();
Förhoppningsvis, vad vi har lagt till ovan borde se ganska grundläggande ut för dig. Vi skapar en klass, kallad CSRF_Protection
, en instansvariabel för att hålla CodeIgniter-förekomsten, två statiska variabler för att hålla namnet på den parameter som lagrar token och en för att lagra token själv för enkel åtkomst i hela klassen. Inom klasskonstruktören (__konstruera
), hämtar vi bara CodeIgniter-förekomsten och lagrar den i vår motsvarande instansvariabel.
Notera: "Parameterns namn" är namnet på fältet som innehåller token. Så på blanketterna är det namnet på den dolda inmatningen.
Efter klasskonstruktören klistra in följande kod:
/ ** * Genererar en CSRF-token och lagrar den på session. Endast en token per session genereras. * Detta måste vara kopplat till en krock efter styrenheten och före kroken * som kallar injektionsmetoden (). * * @return void * @author Ian Murray * / allmän funktion generate_token () // Ladda upp session bibliotek om inte laddat $ this-> CI-> load-> library ('session'); om ($ this-> CI-> session-> userdata (self :: $ token_name) === FALSE) // Skapa en token och lagra den på sessionen, eftersom gamla verkar ha gått ut. själv: $ token = md5 (uniqid (). mikrotime () .rand ()); $ this-> CI-> session-> set_userdata (själv :: $ token_name, self :: $ token); else // Ställ in den på lokal variabel för enkel åtkomst själv :: $ token = $ this-> CI-> session-> userdata (self :: $ token_name);
Steg för steg:
FALSK
, då är symbolen ännu inte närvarande. Vi måste se till att token lämnades in, och gäller om begäran är en POSTA
begäran. Fortsätt och klistra in följande kod i din csrf.php
fil:
/ ** * Validerar en inloggad token när POST-förfrågan görs. * * @return void * @author Ian Murray * / allmän funktion validate_tokens () // Är det här en postförfrågan? om ($ _SERVER ['REQUEST_METHOD'] == 'POST') // Är tokenfältet inställt och giltigt? $ posted_token = $ this-> CI-> input-> post (själv :: $ token_name); om $ posted_token === FALSE || $ posted_token! = $ this-> CI-> session-> userdata (self :: $ token_name)) // Ogiltig förfrågan, skicka fel 400. show_error ('Förfrågan var ogiltig. Token matchade inte. ', 400);
POSTA
begäran, vilket innebär att en blankett faktiskt lämnades in. Vi kontrollerar detta genom att ta en titt på REQUEST_METHOD
inom $ _SERVER
super global. $ This-> Cl> input> post (self :: $ TOKEN_NAME)
är FALSK
, då token var aldrig postad. Det här är den roliga delen! Vi måste injicera tokens i alla former. För att göra livet enklare för oss ska vi placera två metataggar inom vår (Räls-liknande). På så sätt kan vi inkludera token i AJAX-förfrågningar också.
Lägg till följande kod i din csrf.php
fil:
/ ** * Detta injicerar dolda taggar på alla POST-formulär med csrf-token. * Injektioner också meta headers i av utdata (om existerar) för enkel åtkomst * från JS-ramar. * * @return void * @author Ian Murray * / allmän funktion inject_tokens () $ output = $ this-> CI-> output-> get_output (); // Injicera i form $ output = preg_replace ('/ (<(form|FORM)[^>] * (metod | METHOD) = "(post | POST)" [^>] *) / ',' $ 0', $ output); // Injicera in i $ output = preg_replace ('/ (<\/head>) / ',''. "\ n". ''. "\ n". '$ 0', $ output); $ This-> Cl> output -> _ display ($ output);
display_override
krok, vi måste hämta den genererade produktionen från CodeIgniter. Vi gör detta genom att använda ($ This-> Cl> output-> get_output)
metod. POSTA
. rubrik
(om närvarande). Det här är enkelt, eftersom stängningshuvudet ska vara en gång per fil. display_override
krok, standardmetoden för att visa din vy kommer inte att ringas. Denna metod inkluderar alla sorters saker, som vi inte borde - bara för att injicera någon kod. Ringa det själva löser detta. Sist men inte minst måste vi skapa krokarna själva, så våra metoder kallas. Klistra in följande kod i din system / application / config / hooks.php
fil:
// // CSRF Skyddskrokar, rör inte dessa om du inte vet vad du gör. // // BESTÄLLNINGEN AV DESS HOPPAR ÄR MYCKET VIKTIGT !! // // DETTA ÄR GÅ FIRST I HOOK LISTEN post_controller_constructor. $ krok ['post_controller_constructor'] [] = array (// Mind "[]", det här är inte den enda post_controller_constructor hook' class' => 'CSRF_Protection', 'function' => 'validate_tokens', 'filnamn' = > 'csrf.php', 'filepath' => 'krokar'); // Genererar token (SKALL HOPPAS EFTER VALIDATIONEN HAR GJUTS, MEN INNAN KONTROLLEREN / UTFÖRS, ANVÄNDAR ANDRA ANVÄNDAR INTE TILLGÅNG TILL GILTIGT TOKEN FÖR TULLFORMER). $ hook ['post_controller_constructor'] [] = array (// Håll "[]", det här är inte den enda post_controller_constructor hook' class' => 'CSRF_Protection', 'function' => 'generate_token', 'filename' = ' > 'csrf.php', 'filepath' => 'krokar'); // Detta sprutar tokens i alla former $ hook ['display_override'] = array ('class' => 'CSRF_Protection', 'function' => 'inject_tokens', 'filnamn' => 'csrf.php', 'filepath' => "krokar");
post_controller_constructor
krok, så vi måste lägga till dessa fästen ("[]
"). Se dokumentationen på CodeIgniter krokar för mer info. post_controller_constructor
, genererar token om det inte har genererats än. form
och den rubrik
. Med minimal ansträngning har vi byggt ett ganska bra bibliotek för oss själva.
Du kan använda det här biblioteket i något projekt, och det kommer automatiskt att skydda din webbplats mot CSRF.
Om du vill bidra till det här lilla projektet, vänligen lämna en kommentar nedan, eller gaffel projektet på GitHub. Alternativt är, enligt CodeIgniter v2.0, skydd mot CSRF-attacker nu inbyggt i ramverket!