När det gäller de mest populära Javascript-biblioteken måste man erkänna att det under deras utvecklingshistoria (9, 6 och 5 år för Angular, React respektive Vue) har hänt mycket bra saker när det gäller säkerhet, särskilt i samband med sårbarheten för XSS-attacker. Den här artikeln kommer dock att diskutera de små fällorna och principerna som utvecklare fortfarande bör vara medvetna om.
XSS
Vi lever i en tid av ramverk, inte av språk. Detta innebär att programmerare bör kunna oroa sig mindre för många aspekter av utvecklingen, inklusive säkerhet. Majoriteten av de nuvarande backend-ramverken implementerar säkerhetsmoduler som testas av externa, specialiserade företag och stora organisationer. Det är därför, minskad säkerhetsmedvetenhet kan vara tydligt, till exempel mellan unga programmerare, som tar mer ansvar för produkterna, särskilt när det gäller frilansarbete.
En av de vanligaste attackerna på applikationens klientsida är XSS (Cross-Site Scripting). Det utförs genom att injicera körbara skript på klientsidan i webbapplikationer [1] och använder implementerade HTML-renderingsmetoder eller Javascript kod utvärderare som exekverar den. XSS är relativt lukrativt eftersom många olika data kan samlas in, inklusive sessionscookies eller användardata, och det kan installera ett spårningsprogram som en keylogger, vilket gör det farligt för både användare och företagare. Ibland utförs andra former av attacker för att tillåta XSS på sidan, t.ex. SQL-injektion.
Exempel
Inloggningsformuläret på sidan återger loginName-parametern som skickas med GET-begäran i inmatningen för inloggningsnamn. Värdet behandlas inte av vare sig server- eller klientsidan av applikationen. Genom att begära: http://localhost:8080/login?name=<script>alert(document.cookies)</script>
kod exekveras och data exponeras
Detta är ett exempel på en reflekterad XSS-attack, där skript injiceras via en särskilt förberedd URL-adress som skickas till offret och återspeglas av serversvaret. Andra kända populära former av attacker är följande:
- Lagrad XSS utförs med injicerad data som lagras på serversidan, vanligtvis genom formulär som finns tillgängliga i applikationen. Klientapplikationen renderar kod som är lagrad i t.ex. en databas.
- DOM XSS utför en XSS-attack utan att använda serversidan. I den fortsatta delen av artikeln kommer vi att fokusera på denna form av attack.
Aktuella sårbarheter i React- och Vue-biblioteken
För de aktuella versionerna React/Vue har två stora problem upptäckts som ännu inte är officiellt åtgärdade. Den första sårbarheten har samma karaktär för alla ramverk och är relaterad till metoder som tillåter rendering av rå HTML i mallar: v-html och farligtSättaInnerHTML, respektive för Vue och React. Varje dokumentation [2] informerar läsarna om att oklok användning kan utsätta användare för XSS-attacker. Om det inte finns några andra alternativ för att lösa problemet, se till att data är filtrerad och flydde. Även om de är farliga, bör du inte förvänta dig att dessa metoder är fixade. Använd dem på egen risk.
Under första kvartalet 2018 upptäcktes en stor bugg i React, vilket möjliggjorde direkt exekvering av kod genom att ställa in egenskapen för taggelement. Att skicka exempelkod inom attribut, såsom javascript:alert(1)
och att köra en renderad länk kommer att exekvera koden. Detta problem [4] är fortfarande öppet och ingen fix har förberetts och sammanfogats, så se till att din kod är säker. Exempel som föreslagits i den officiella diskussionen föreslår några sätt att övervinna detta problem.
Om det inte är möjligt att uppdatera till de senaste versionerna kan du se till att gamla problem inte orsakar problem för dig genom att se till att din kod inte är exponerad för:
- barn nod injektion - React, användning av React.skapaElement [5]
- Rendering på serversidan - React/Vue [6]
- CSS-injektion [8]
Det handlar fortfarande om Javascript. Det handlar fortfarande om front-end
Glöm inte att förutom själva ramverken eller biblioteken har Javascript som språk vissa farliga funktioner, som måste undvikas eller användas med försiktighet. De är i allmänhet relaterade till DOM-manipulation eller skriptexekvering. eval() representerar flaggskeppsfunktioner av den här typen och är extremt farlig eftersom den exekverar given strängifierad kod direkt [9]. Ta också en bättre titt på din kod när du hittar en av dessa funktioner:
- dokument.skriv
- dokument.skriveln
- (element).innerHTML
- (element).outerHTML
- (element).insertAdjacentHTML
Här kan det vara till hjälp att använda linters med korrekta regler för att hitta sådana sårbara punkter. Det finns också många öppna eller kommersiella kodanalysatorer som kan hjälpa dig att upptäcka säkerhetsluckor i utvecklad kod.
Oavsett vilket bibliotek/ramverk som väljs måste vi fortfarande komma ihåg grundläggande principer för frontend-utveckling. För det första ska du alltid se till att den externa kod du injicerar kommer från en pålitlig källa. Revision dina beroenden och välj dem med omsorg. Vissa kan innehålla allvarliga sårbarheter som exponerar din kod även om allt är bra med själva koden. Du kan läsa mer om säkerhet i beroenden här:
https://thecodest.co/blog/security-in-javascript-packages/
Så... ska du fortfarande vara orolig?
Ja - och jag uppmanar alla att aldrig lita på externa bibliotek eller på sig själv när det gäller säkerhet. Oavsett hur säker du förväntar dig att din programvara ska vara, försök alltid att testa den så mycket som möjligt med avseende på vanliga attackformer [10].
- https://reactjs.org/docs/dom-elements.html#dangerouslysetinnerhtml
- https://vuejs.org/v2/guide/syntax.html#Raw-HTML
- https://github.com/facebook/react/issues/12441
- http://danlec.com/blog/xss-via-a-spoofed-react-element
- https://medium.com/node-security/the-most-common-xss-vulnerability-in-react-js-applications-2bdffbcc1fa0
- https://github.com/dotboris/vuejs-serverside-template-xss
- https://frontarm.com/james-k-nelson/how-can-i-use-css-in-js-securely/
- https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/eval#Do_not_ever_use_eval!
Läs mer om detta:
5 misstag du bör undvika när du underhåller ett projekt i PHP
PHP utveckling. Symfony konsolkomponent - tips och tricks
Varför behöver vi Symfony Polyfill (... och varför vi inte borde göra det)