Why LocalStorage is Vulnerable to XSS (and cookies are too)

Sdílet
Vložit
  • čas přidán 26. 08. 2024

Komentáře • 235

  • @ivands16
    @ivands16 Před 4 lety +92

    A users login session can be stolen in so many ways. The best think you can do is accept the fact that your vulnerable to XSS attacks. And think about ways to mitigate the damage that can be done when your users session has been hijacked. One example banks use is to ask for some kind of 2FA step each time you make a money transaction. The attacker might have the login session but probably not the 2FA code.

  • @paymankhayree8552
    @paymankhayree8552 Před 3 lety +70

    Jeah XSS attacks are always possible and the solution is to do enough input validation both on the client-side and on the server

    • @martapfahl940
      @martapfahl940 Před rokem

      all examples I saw worked through innerHTML… how is your code vulnerable without it?

  • @McGono
    @McGono Před 4 lety +124

    Completely agree with this, if you've got an XSS vuln then you've already lost the battle regardless of where you're storing things.

    • @aidemalo
      @aidemalo Před 4 lety +1

      This is partially wrong, *without* http-only cookie, and open XSS, you need simple one-stringer which will fit even in url to get the cookie = full access to the session/account. Else you limited to simple actions and the script required becomes more complicated.

    • @ProtectedClassTest
      @ProtectedClassTest Před 4 lety +7

      False. If you own a house do you just fortify your door? Saying well if they open the door were already doomed so no need for other emergency security measures anyway. Just fortify the fucking door. Do you do that?

    • @barricuda
      @barricuda Před 3 lety +13

      @@ProtectedClassTest If you have an XSS vulnerability, you don't own your house, I own your house. Go ahead and secure my new lamp, it's a dumb lamp anyways.

    • @ProtectedClassTest
      @ProtectedClassTest Před 3 lety +8

      @@barricuda maybe you own the house but if i got a vault my money is still safe. Keep the house, its dumb anyway

    • @EidosGaming
      @EidosGaming Před 3 lety +6

      @@ProtectedClassTest
      Why would an attacker want your token? To impersonate you and perform actions. How do they perform actions? Through API calls. But if they've XSSed you they can fetch freely from your computer, whether you use httponly cookies or local storage.
      In the house analogy it's more like if they mind controlled you. It doesn't matter what kind of protection you've got, if YOU can go through the doors and the vault, then they'll just use you to do as they wish.
      The only thing you're protected against is if they want to perform some action at a specific time, they depend on you being online and XSSed at that time.

  • @alexnezhynsky9707
    @alexnezhynsky9707 Před 4 lety +32

    Some sites have dedicated pages with zero JS where you make a payment or enter sensitive info like a CC number (often on a subdomain). Can't use JWT, but cookies will still work. Just my 2¢

  • @MarcoBiedermann
    @MarcoBiedermann Před 4 lety +9

    I agree. I does not matter if you store any information locally, no matter if it is sensitive or not. Also it does not matter if you store it in a cookie or in localStorage. You can manipulate both.
    When it comes to expiration, this can also be replicated using both methods but it has to be invalidated / checked on the server.
    So I guess it really does not matter where you store user data as long as you escape any vulnerable input.
    This can also be implemented using multiple layers:
    E.g. validate input on frontend if possible or validate request params / body by type (number, string, boolean) and format (isEmail, isUUID, isLowercase)
    Next would be to validate before inserting into your database on a model / entity level. Most ORMs provide this feature out of the box.
    Last option would be to validate against any database schema (Database Datatypes).
    Of course you should catch as many validation checks upfront but just in case, you have multiple layers of security

    • @nafiulawal1443
      @nafiulawal1443 Před 2 lety

      What happens if the attacker edits your html to include a js input, say with a click anchor tag and then makes a request. I think the main problem here is to increase security on the front-end because the back-end will have no idea. Maybe 2FA is the best option here.

    • @loucadufault6549
      @loucadufault6549 Před rokem

      @@nafiulawal1443 frontend validation is always useless from a security standpoint. If anything it's a (easily-defeated) deterrent.

  • @user-dq7kl5nu6x
    @user-dq7kl5nu6x Před 3 lety +7

    Correct me if I'm wrong, as I mostly had an experience as a backend dev, but I believe that xss attack and problem with local storage is quite different then what you describe. Practically if we have any vulnerability that allows for execution of malicious JavaScript on our side we practically screwed and yes, we can't do anything about it if attacker knows our auth flow. But problem with local storage as I understand it lies in that it's actually accessible to all JavaScript code without any domain protection, so if user goes to a site that attacker set up for him, then code on that site can read anything from local storage.
    Also even if you have authentication credentials split to protect user from both xss and csrf attacks and your own app is fine there are theoretical ways for an attacker to deal with it if he targets specific user/app, so like any security measures it's just a way of minimizing risks.

  • @hannessteffenhagen61
    @hannessteffenhagen61 Před 3 lety +6

    The reason why a HttpOnly cookie would be better is because the attacker doesn't get the actual JWT. For a single application you're right in that it won't make such a big difference, but the same JWT may be valid across different services so even if one service is vulnerable you'd want to avoid this extending to all other services sharing the same authentication method too.

  • @bulantut
    @bulantut Před 4 lety +6

    Content-Security-Policy response http header can be a added security for this, as this http header limits the outside requests of your img, link, scripts, etc.. to only allowed domains. That way even if an attacker can do something on the site but he wont get anything since he is not able to do a request on some domain that is not defined on your CSP.

    • @bawad
      @bawad  Před 4 lety +7

      sure but the whole point of stealing someones token/cookie is to do something as them on the site

  • @felleg4737
    @felleg4737 Před 3 lety +5

    while being a beginner web developer and exploring the ways of safe authentication and authorization, this topic makes me frustrated.
    but the fart sound under your video makes me a bit calmer, and gives me a mystical hope.

  • @lmfao7224
    @lmfao7224 Před 4 lety +3

    One thing to note if you store the JWT token in local storage and an attacker gets in, they can use the token to make AJAX requested outside of your infected website whereas if it was stored in a Http only cookie AJAX requests would have to be made on your infected website
    Implication of this? If you have a react front end and a backend and say a mobile app the front end gets hacked by XSS and it’s stored in Http only, shutting down the website temporarily will temporarily solve the issue as no more Ajax requests can be made with the cookie
    If you stored it in local storage the attacker can send this to a remote server and use it to make Http requests with or without your website meaning you would have to either shut down your backend or change your signing key while your website is down, this would affect all your other microswrvjcws and would make all your mobile / api uses log out

    • @FilipCordas
      @FilipCordas Před 3 lety

      One thing to note on cookies they are open to CSRF cheatsheetseries.owasp.org/cheatsheets/Cross-Site_Request_Forgery_Prevention_Cheat_Sheet.html.

    • @rewire6468
      @rewire6468 Před 5 měsíci

      Yes, you're correct. Unless your use a simple CSRF token on user-end. Say a random 16 character length cryptographically generated code which is keyed to each user (one different code per user). You store this nowhere else but in a simple JS var. This is always cleared if you leave the site. Thus, another domain or server cannot make requests on your behalf, even if they have your auth tokens, since they do not have this code. You simply refuse any request that does not contain the user's CSRF token, on your back-end.

  • @JoshCarpenterVO
    @JoshCarpenterVO Před 3 lety +1

    I know this is old, but seeing this in 2021 . . .
    Two things off the top of my head to consider -
    *if a request should ONLY be done based on a user's intent, it should require a second factor authentication, this makes this type of vulnerability significantly weaker
    *if a token could somehow be exfil'd to an external location rather than just have requests sent on your behalf while the app/tab/etc is open, they can make unrestricted requests regardless of app status, also offline introspection of the quality of the token (encryption methods, etc) is easier

  • @harishankar5901
    @harishankar5901 Před 3 lety +6

    wait maybe im not understanding this, but are xss attacks only possible if you implement something that allows users to run any html? I can't really picture myself doing that in any scenario...

    • @LorenzoLeonardini
      @LorenzoLeonardini Před 3 lety +5

      In general you get user content. A username, for example. Generally you sanitize your inputs, both in the front end and in the back end, but maybe a specific version of a library/framework you're using is vulnerable to something. As far as I'm concerned nowadays XSS is researched on sanitization libraries. The thing is, if you do everything properly, people shouldn't be able to perform XSS, but you can never know for sure. The only websites which are safe from XSS vulnerabilities are websites with no user content, i.e. static websites

  • @agussluzenti9596
    @agussluzenti9596 Před 3 lety +4

    Wow, it's a great video! I found it really useful and learned a couple of things. However, I think in production there are other things about authentication that are just so very difficult to do without a provider. I mean, web security is a whole another world, as developers we can make our best efforts to secure it. My point is, it's not as easy as say, I'm going to use jwt and store it there, for example, if you use JWT as authentication, how do you persist session securely? How invalidate a stolen jwt? All those things can be overwhelming to do it manually, Auth0 for example and other providers have a lot of security mitigations to help with that.

  • @andrewlee6142
    @andrewlee6142 Před 4 lety +2

    You can bake in IP address into the JWT payload. If the request comes from a IP that is not identical from the JWT payload IP, you can automatically deny it. This would dissallow the usage of the JWT from a different IP. rarbg enforces something similar, but for the purposes of preventing web crawlers, and non-human access.

    • @ferco0
      @ferco0 Před 3 lety +1

      not good for long-live jwt, like ip's are not a fix value, when changed brokes the token.

    • @Nikola9517
      @Nikola9517 Před 3 lety +3

      I’ve done that and it works. I’ve put ip in secure http only cookie, encrypted it with custom encryption and only after i decrypt it i becomes valid jwt, in my auth middleware i’m checking from which domain it is coming from (only my) and checking ip. It does log you out almost always if you are using vpn but it’s safer

    • @Nikola9517
      @Nikola9517 Před 3 lety +1

      also since it’s double encryption it is very cpu heavy so keep that in mind, encryption key is unique to user and it is stored in server memory and automatically refreshed, also good idea to use 2fa if you are allowing/not checking users ip

  • @ridingtigers
    @ridingtigers Před 2 lety +1

    I believe that SameSite cookies address this problem. In this case the cookie is only sent when making a request to the hosting server

  • @Meleeman011
    @Meleeman011 Před 3 lety +1

    i've seen csrf tokens being used, and those are assigned to the user at random by the server after each request while a user could steal that token, you can also make sure input is escaped, and use request validation, for example nobody can inject any scripts into you db for either xxs or sql injections. you can also sanitize the input so that commands are rendered as harmless strings. these work relatively well i think, although defeating a csrf token system might not be so difficult if you know what the token is before teh user makes a request

  • @DavidBadilloMusic
    @DavidBadilloMusic Před 10 měsíci

    I completely agree.
    Having a stash of money under the mattress is not safer than leaving that stash of money on the kitchen table if you haven't prevented the robber from getting into your house, to begin with.

  • @sbrugby1
    @sbrugby1 Před 4 lety +7

    ty sir, nother great explanation. cool demo

  • @Brad10
    @Brad10 Před rokem

    Awesome explanation and demonstration. Thank you!

  • @syedalimehdi-english
    @syedalimehdi-english Před 3 lety +2

    What if we encrypt JWT token before sending it to user?
    An encrypted token would be useless for attacker if we have some decryption method at the front end.

    • @Mr_BetaMax
      @Mr_BetaMax Před 3 lety +3

      The JavaScript is exposed in the browser, so the hacker could , arguably, just copy the js from the sources tab and use your own decryption 🤔

  • @ValtteriKaresto
    @ValtteriKaresto Před 4 lety +6

    Really good example why one shouldn’t use dangerouslySetInnerHTML. One good practice is to use CSP headers which will prevent attacker ”calling home” with malicious code (eg. sending your JWT to attacker). This also protects you from similar attacks if third party libraries would contain malicious code. But even with CSPs attacker can still make calls on your whitelisted endpoints.

  • @CPlayMasH_Tutoriales
    @CPlayMasH_Tutoriales Před 4 lety

    Http only cookies mitigate the majority of xss attacks because of the cross origin requests prevention that browsers have enabled by default

  • @jaredjewitt2917
    @jaredjewitt2917 Před 3 lety +2

    So I understand how using third party libraries which are bundled in your JS can make your app vulnerable to XSS. Such as a library looping through localstorage and sending it to their own API / database. But what I don't understand is how this specific example could make your app vulnerable. If a hacker were to replicate what you did, wouldn't they just see their own localstorage being printed? The same goes for phishing scams. Localstorage is domain specific, so if I clicked on a link to some-hacker.com how would they get access to my localstorage for my-site.com?

  • @ryanholton961
    @ryanholton961 Před 4 lety

    JWT is a popular choice for authentication and is implemented in many websites using web storage. Honestly, the site should be handling XSS (and most do), be aware of it, but unless it happens, localStorage and web storage in general is fine.

  • @amirhoseinfarhadi2268
    @amirhoseinfarhadi2268 Před 3 lety +2

    Can't belive stackoverflow didnt have dark mode back then

  • @faiztheawesomeguy
    @faiztheawesomeguy Před 3 lety

    Usually what i will do will encrypt the data when storing on cookies or localstorage. If hacker manage to get access to storage or cookies, then they need to decrypt those value in order to use the JWT.

    • @erik50468
      @erik50468 Před 3 lety

      But you will need to storage the decrypt key somewhere in the code, because I think that hash won't work for that case.
      Unless you encrypt in the server before send to client, but it's not will be like a classic server session?

  • @Dev_Everything
    @Dev_Everything Před 2 lety +1

    So how do you prevent javascript from being injected? That seems like the biggest problem.

  • @jcmusik7495
    @jcmusik7495 Před 4 lety +6

    Couldn’t you use some regex validation on the input fields that wouldn’t allow users to enter html or javascript?

    • @bawad
      @bawad  Před 4 lety +3

      cheatsheetseries.owasp.org/cheatsheets/Cross_Site_Scripting_Prevention_Cheat_Sheet.html

    • @dealloc
      @dealloc Před 4 lety +3

      Don't parse HTML with regex. Why? You will never get 100% spec compliance without a massive regex-which means there are different ways to circumvent the validation-and even then, you'll likely end up making a mistake that allows an attacker to use regex as another attack vector like RDoS (Regex Denial of Service).
      If you want to validate content-and you absolutely _need_ users to be able to write HTML, CSS or JS directly in your application-use a html sanitizer that parses HTML with a proper parser.
      But the best thing you can do is just not allow any HTML, CSS or JS (yes CSS is also an attack vector).

    • @nickwoodward819
      @nickwoodward819 Před 4 lety +2

      Obviously you want to sanitize fields, but XSS vulnerability doesn't have to come from your site, could be present in a 3rd party package or cdn, so you still need to worry about it

    • @exactzero
      @exactzero Před 4 lety

      Yes, that's sanitizing inputs which is a whole different topic. This video is after the fact of being hacked due to not implementing them.

    • @christianaustria741
      @christianaustria741 Před 4 lety +1

      i think in addition to that, you can just encode the output when displaying it inside the templates. I'm not very familiar with react but i feel like every SPA js library has built-in functionality for that.

  • @TheALEXiSounds
    @TheALEXiSounds Před 4 lety

    Whats your opinion on the double cookie method?
    1. Separate the header & payload from the signature.
    2. Store the header & payload into a secure cookie, as a string. Optional: including a random string, which can act as the redis key for scaling user session.
    3. Store the signature as a httponly, secure cookie, as a string. Optional: with the random string from step 2, store the signature into redis, where the key is the random string and value is the signature.
    That way the client will never have 100% access to the token, but then again as I'm typing this, if you are vulnerable to XSS then it doesnt matter lol.

    • @bawad
      @bawad  Před 4 lety +1

      😂 exactly

  • @SimonSezRide
    @SimonSezRide Před 2 lety

    How about we store the token in the application level variables. Will an XSS attacker be able to access that using some malicious JavaScript ? Is there a way to go that route where we don't use local or session storage or cookies. App makes a request for token every first call it makes to the server. I understand we will not be able to use features like stay logged in etc. but wont it be much secured ? I may be wrong please shed some light if possible. I know it is a very old video to comment now :)

  • @JuanVasquezq
    @JuanVasquezq Před 3 lety

    these are the vids we need

  • @abdicodes
    @abdicodes Před 4 lety +4

    What happened to the solution where you store the token in memory?

    • @bawad
      @bawad  Před 4 lety +6

      still vulnerable

    • @abdicodes
      @abdicodes Před 4 lety +6

      @@bawad no one is safe

    • @janjanusz8271
      @janjanusz8271 Před 4 lety

      Not really. You can keep the token out of the global scope, so the attacker cant access the scope. It happens automatically with webpach. Each modules are anonymous functions indeed and cant be accessed from global scope. (function(){all login scope with no console.log that haker can hook up to})()

    • @ivands16
      @ivands16 Před 4 lety +3

      @@janjanusz8271 Keeping it out of the global scope would work. But getting the token in the first place is probably an operation that can be done in any scope. So you have the same problem again. Plus you don't want your customers to be logged out each time they refresh the page or click on a link.

  • @chzmo
    @chzmo Před rokem

    What if you store a token in an encrypted format? Which can be decrypted by environmental variables 🤔? What do you think?

  • @LawZist
    @LawZist Před 4 lety

    Realy good and simple example of xss attack

  • @Nerketur
    @Nerketur Před 3 lety +1

    What you say is true, but I will retort that localStorage is a lot easier to read and access than cookies are, or any type of session.
    localStorage, if I'm not mistaken, is readable from anyone's session. Fred can read Daphne's token as long as they use the same computer, with or without XSS, XSS just makes it easier. Session storage is a lot harder to read without being the user, especially if the session is stored server-side.

  • @blueice3124
    @blueice3124 Před 3 lety

    That's why you setup input sanitization before officially deploying

  • @tafelito
    @tafelito Před 4 lety

    how you are vulnerable using in memory token with a refresh token in http only cookie like you did on your prev vid? The only downside I found, is that using TokenRefreshLink will only check if the token is valid when you do a request to the server, but if you get the data from the cache, it won't be checked. So maybe adding a timer with the token expiration date would cover that as well

  • @gcxs
    @gcxs Před rokem

    its ok to always open the third gate

  • @himanshushekhar3694
    @himanshushekhar3694 Před 3 lety +1

    thanks for the video really helpful

  • @suryapratimpaul
    @suryapratimpaul Před 3 lety +2

    Cookie with fixed domain and secure cannot get xss. Plus JS can be disabled for some cookie, I mean JS can't access such cookies.

  • @seth_sesu
    @seth_sesu Před rokem

    What about indexedDB? I assume this is less vulnerable to attacks?

  • @swapneshsinha
    @swapneshsinha Před 4 lety

    I believe its the expiration time on cookies that makes them little better than localStorage. Rest you are totally right that once front end compromised it doesn't matter u store data in cookie / localStorage either.

    • @elie2222
      @elie2222 Před 4 lety +1

      swapnesh sinha jwt stored in local storage has an expiration too. Jwt has it itself

    • @swapneshsinha
      @swapneshsinha Před 4 lety

      @@elie2222 Yes you are right but I didn't mentioned my comment about JWT specifically

    • @TheGryphon14
      @TheGryphon14 Před 3 lety

      @@elie2222 cookie expiration is a default browser feature but jwt is not. You have to implement your own server-side logic to "invalidate" the jwt.

    • @elie2222
      @elie2222 Před 3 lety +1

      @@TheGryphon14 You always have to have server side logic 🤷‍♂️

    • @TheGryphon14
      @TheGryphon14 Před 3 lety

      ​@@elie2222 we can use Expires or Max-Age with Set-Cookie header. That's what I mean by default browser feature. But how do we tell browsers to "expire" a local storage item?

  • @arthurbruel5545
    @arthurbruel5545 Před 4 lety

    "It's not really that difficult to write code that is vulnerable", he says, while staring at a div with the "dangerouslySetInnerHTML" prop being used.

  • @htmixl
    @htmixl Před 3 lety +1

    what about httpOnly cookie? Im learning about authentication and recently found a nice article explaining the best way is to have jwt in a regular variable, and a refresh token in a httponly cookie

    • @Mr_BetaMax
      @Mr_BetaMax Před 3 lety

      HttpOnly cookies are sent with the fetch request. So sending it to localhost:4000 ( which would presumably be the hackers own server) they could read the token on the server from cookies

    • @deltakapp676
      @deltakapp676 Před 3 lety +1

      @@Mr_BetaMax But if you use samesite="strict" then the cookie can't be sent to the hacker's server, right?

  • @swyxTV
    @swyxTV Před 4 lety +1

    i agree that if you're xss'ed you're pwned. like swapnesh said in the comments, cookies can have an expiration time, however even more than that, there is a serverside session as well that you can terminate if you believe you've been compromised (and so even unexpired, valid cookies will fail to do anything). whereas JWTs are typically accepted on without any further check (this is what lets serverless functions be scalable and stateless, altho some people do implement session checks) and therefore its riskier to keep long lived JWTs around in localstorage OR cookies. i had more great discussions in this thread mobile.twitter.com/swyx/status/1133780714988736512

    • @bawad
      @bawad  Před 4 lety

      yeah I think it's a good idea with any kind of long lived token to have some functionality to be able to revoke it

  • @BHFJohnny
    @BHFJohnny Před 2 lety

    Ok, Ben, now what? You just told be that it doesn’t matter if I store my token in local storage, because if I'm vulnerable to XSS, they could also, you know, get access to that or just do the fetches on my account without my permission, right?

  • @dailymeow3283
    @dailymeow3283 Před 3 lety

    How to prevent that please, is there any video for that,
    Maybe i could prevent that in nginx headers ?

  • @hatrick3117
    @hatrick3117 Před 4 lety +1

    Hey Ben, wanted to ask you to do something like your "chosing framework" video but about authentication (the one where you presenting a login behind choosing Gatsby CRA or Next). Do you think there is some thought process that we can have to go with cookie/local/memory, or it's all just semantics?

    • @bawad
      @bawad  Před 4 lety +2

      really just depends on your situation
      inmemory is probably the most secure because it's not persisted, cookies are great overall but if you use an httpOnly one you can't access it, localStorage let's you access the token but is tricky for SSR

  • @victorbjorklund
    @victorbjorklund Před 4 lety

    Good explanation. I had never thought about the risk with query-strings on the URL.

  • @ibrahimmohammed3484
    @ibrahimmohammed3484 Před 4 lety

    i still can't wrap my head about how a hacker target executing js on a victim's machine targeting my specific app or even if the attacker spoiled the victim machine and got his localstorage content, how would he relate to which app or website this token belongs !!

    • @bawad
      @bawad  Před 4 lety +7

      he could check window.location to see the url of the website

  • @czypherth
    @czypherth Před 3 lety +1

    is it possible to prevent this by actually making regex middleware or something and check whether the query strings are most likely javascript code and reject it if it is

    • @brandtleymcminn
      @brandtleymcminn Před 3 lety +1

      It's not feasible to do this. You'd be playing whackamole trying to tamp out any attempts to circumvent your checks and probably catch a lot of valid data in the crossfire. If you did manage to get around this, an attacker would just obfuscate the syntax making it more difficult to detect.
      The more proactive approach is to ensure you have layers of validation and leverage modern sanitization strategies afforded by your language or framework of choice.
      Secondarily, make sure you aren't storing sensitive information in the token itself. Publicly available info like a username or userId value is one thing, but you shouldn't store emails, phone numbers, personally identifiable info not pertinent to the operation of your application in an authtoken.
      Form here any request made to your API should be run through a pre-auth check to validate the token and validate any roles/permissions related to the userid that your endpoint handles accordingly. Like if a user doesn't have admin privileges, they shouldn't be allowed to query other user data.

    • @ozzyfromspace
      @ozzyfromspace Před 3 lety

      @Zyper there’s an entire class of attacks called “regex attacks” that focus on the fact that regex is actually a really compact algorithm, and if you know what you’re doing, you can make a regex filter damage the server. Yesterday, I saw a guy (on CZcams) tailor a string for a regex that messed it up real good… put it into a logical loop for like 30 seconds, which caused his little demo server to stress. The thing is, security vulnerabilities only work because we don’t see them as such.

  • @shilangyu
    @shilangyu Před 4 lety

    Here's a counter example: Let's assume a hypothetical situation. An app sanitizes ALL user input without exception. Is it still unsafe to store jwt in localstorage? It seems like the XSS example doesn't really apply to modern webpages, as you have shown you need to go out of your way to even make your site vulnerable in React. Waiting for your feedback, thanks :)

    • @Vaielab
      @Vaielab Před 4 lety +2

      To sanitize everything is simply impossible. Even google have some xss vulnerability (google "google xss vulnerability"). Some are browser based, other are brand new and not yet published. Unless you only accept alphanumeric chars, you most likely have some vulnerability somewhere.

    • @shilangyu
      @shilangyu Před 4 lety +1

      @@Vaielab what you're saying is new ways of performing an XSS, and yes it is browser based (ie. img tag or plain script tag). However they all rely on one thing: to work they need to embed themselves on your site as html. If one always treats user input as plain text none of these will work.

    • @filipitskov3742
      @filipitskov3742 Před 4 lety

      i think react always does sanitize the rendered jsx, unless you do, dangerouslySetInnerHtml

    • @swyxTV
      @swyxTV Před 4 lety +1

      @@shilangyu correct, but you might be missing just how many people add third party scripts to their site that may be compromised, and can therefore listen in on all user input. react doesnt save you from that

    • @shilangyu
      @shilangyu Před 4 lety

      @@swyxTV i agree, its very hard to have every library and piece of code in control. However i feel like excluding localStorage token method is: yes, better safe than sorry but at the same time not always necessary.

  • @nsambataufeeq1748
    @nsambataufeeq1748 Před 3 lety +1

    Just don't keep tokens around for too long, validate your inputs, both front and backend

  • @eyesight2073
    @eyesight2073 Před 4 lety

    I really did not get the point.
    How the attacker gets access to clients browser in the first place?
    Lets say I'm client to your application, logged with username & password on my browser. Now JWT is stored in my browser's local storage.
    Now how can an attacker has access to my browser to execute js?
    Those vulnerable input boxes are available to me only & not for attacker right?

    • @conradooliveira1214
      @conradooliveira1214 Před 4 lety +1

      Yes, but the attacker can send to the client a link that when the client enters that link, the injected js reads the user token from local storage and sends the token back to the attacker. Then the attacker can send requests to the server as if he was the logged in user.

  • @sneak9407
    @sneak9407 Před 2 lety

    I Still prefer cookie storage. You still can't read the cookies, you can only make request with them.
    JWT on local storage can be read and then taken to another PC and properly impersonate a user.
    Secondly if the frontend is XXS free, they will have no way to make request on behave of a user using cookies. While if storing JWT in local storage, if an XSS runs on your machine, they can still take those tokens and simulate authentication on their machine.

    • @daviddoyle7580
      @daviddoyle7580 Před 2 měsíci

      If the xss is running though they still have access to the cookie to make requests to endpoints even if they can't read the access tokens it doesn't matter, they still have the cookies to make the request. The cookie has an expiration though you might say but so does the jwt so it seems that local versus cookie is the same safety wise I think

  • @Liz3_
    @Liz3_ Před 4 lety

    but like if you render unsafe without a clear reason and respective measures you should go back to the drawing board. ive maybe experienced it 1-2 times that this feature had to be used

  • @pulga961
    @pulga961 Před 4 lety

    Another hacker example can be:
    browser.downloads.download(urlToVirus)
    will work in case browser has acess to device storage which most people grant.

  • @carlosjosejimenezbermudez9255

    The best approach I have come to learn is to not store it anywhere but in memory. This would cause your app to be unable to refresh without losing session, but there is a browser event that runs before refresh. You can essentially put your JWT in sessionStorage or localStorage during this event and remove it as soon as your app reloads. That way you only keep you token in insecure storage when it is absolutely necessary. And you give very little time for an attacker to use your token if at all.

    • @ivands16
      @ivands16 Před 4 lety +4

      haha funny fix. But not really usable. Your get weird bugs like when you open a second tab. The second tab will be logged out.

  • @petersrule
    @petersrule Před 4 lety +2

    How would you get someone else to run those codes in their browser? I see you just using those codes in your own browser.

    • @Pikoro09
      @Pikoro09 Před 4 lety +4

      When you have a site that allows users to submit anything. If this comment box had the dangerouslysetinnerhtml prop you could do that and run a script in the next persons browser that runs it.

    • @PJo336
      @PJo336 Před 4 lety

      I have the same question, don't really get it.

  • @CodeWithVlad
    @CodeWithVlad Před 3 lety

    This would not happen if you sanitize the HTML before dangerously setting it in that div.

  • @mrvectorhc7348
    @mrvectorhc7348 Před 4 lety

    There are ways to block inline javascript completely in html. This can solve the problem if your app is written in a separate app.js file.

    • @nickwoodward819
      @nickwoodward819 Před 4 lety +1

      The vulnerability doesn't have to be in your code though, just code you use

    • @mrvectorhc7348
      @mrvectorhc7348 Před 4 lety

      @@nickwoodward819 if hacker manages to insert malicious code into your website that does something in js it probably will be inline js (otherwise you can block 3rd party js origins) in which case it simply won't work

    • @nickwoodward819
      @nickwoodward819 Před 4 lety

      @@mrvectorhc7348 Can the code not be in a dependency that you need?

  • @justcurious1349
    @justcurious1349 Před 4 lety

    Hi Ben, what if we use httpOnly, secure and samesite=strict with cookies. Can we not prevent cookies with these attributes from xss

    • @FilipCordas
      @FilipCordas Před 3 lety

      Not with xss, since it's your site making the request and anything you can the attacker can do. Local storage can in fact be somewhat safer from CSRF.

  • @JLarky
    @JLarky Před 4 lety +7

    Reading comments makes me extremely sad

  • @impulse8170
    @impulse8170 Před 4 lety

    You could use XSRF/CSRF pattern as a parity token. For example store your auth token in cookies (http only and secure - only https) and a second jwt token in your local/session storage, that way an attacker can possibly only get one token at a time, so either XSS or XSRF... but your API expects both tokens. JWT can be set to be vaild for a certain time period, the XSRF token does not need to be as strikt as the auth token.

  • @IsaiahGamers
    @IsaiahGamers Před 4 lety

    Can subdomains access the same localstorage from the main domain?

    • @bawad
      @bawad  Před 4 lety +1

      I don't think so

  • @onions5113
    @onions5113 Před 3 lety

    About indexeddb how can attacker inject some payload on it?

    • @hypergraphic
      @hypergraphic Před 3 lety

      That's what I've been thinking about. The only problem with that is the files are probably unencrypted on the user's computer in a well-known location. So if that user has any malware on their computer, in theory, it's vulnerable, but at least you might cut down your attacks from the web.
      Based on what everyone has said, I think for apps where security is a priority, just have to do 2FA, not necessarily at signup, but definitely around critical operations.

  • @maxlimgj
    @maxlimgj Před 3 lety

    can u also share your source codes?

  • @reapi_com
    @reapi_com Před 4 lety

    Different domain cannot get cookie from original domain? Browser won’t send it.

    • @bawad
      @bawad  Před 4 lety

      if you make it http only, no javascript can access it

    • @gveresUW
      @gveresUW Před 4 lety +1

      @@bawad do you really need the javascript to access it? If it gets set as an http-only token and is sent to your server with each request, why does JS need access? BTW, i have your 3 hour video in my to watch list. So if you answered this question there, you can just point me back to that video.

  • @Luxcium
    @Luxcium Před 4 lety

    What is the difference with going from the textarea again compared to the console ? It’s only dangerous when it’s from the url ?

    • @DeadlyDragon_
      @DeadlyDragon_ Před 4 lety

      Its dangerous either way from my understanding, its the same XSS vulnerability.

    • @pipertripp
      @pipertripp Před 4 lety

      all that matters is that the user has injected some bad code into your site so that the code executes as part of your site's operation. A really common attack is adding attack code to a board post. If the system does escape that content and neutralize it, then whenever someone reads the post, they will get affected. So however the user gets bad code into your site, you need to escape it or strip it out so that it can't execute. This is an old problem that's been round for ages.

    • @exactzero
      @exactzero Před 4 lety

      No difference

  • @diamondminer81
    @diamondminer81 Před 3 lety

    Remember XSS is always possible with an extension.

  • @Aquazifyy
    @Aquazifyy Před 4 lety +1

    Hello Ben, is your previous video still a safe solution?

  • @artem_skok
    @artem_skok Před 3 lety

    The http only cookies are only sent to the origin that have created them. So the request to another domain will not have cookies in it and it occurres to be safer then localstorage . Please correct me if I am wrong.

  • @manengelo8427
    @manengelo8427 Před 2 lety

    But some one might as well just do to developer tools.. and get it... if in pc

  • @xushenxin
    @xushenxin Před 3 lety

    how about this: save the token in memory. save to local storage when page is unloading. When page is open again, read token from local storage to memory, then delete local storage. So when single page app is running, there is nothing in localstorge.

    • @neloka4313
      @neloka4313 Před 3 lety +1

      Yeah sure, that way I cannot have two tabs of your website opened at the same time while still being logged in.

  • @TheDestroDevShow
    @TheDestroDevShow Před 4 lety +1

    The New "SameSite" cookie will help to fix the issue for the cookie scenario you mentioned.

  • @DiegoArcega1
    @DiegoArcega1 Před 4 lety

    How would you be vulnerable using cookie httpOnly and domain?

    • @FilipCordas
      @FilipCordas Před 3 lety +2

      If you use fetch or any other way of sending http requests it will send that request with all the cookies. That is why you have to use Anti-CSRF Tokens.

    • @FilipCordas
      @FilipCordas Před 3 lety +1

      Just to add something on csrf the browsers now do support SameSite staff but if this is done with xss that site is the same so it will still send even with strict level.

    • @DiegoArcega1
      @DiegoArcega1 Před 3 lety

      @@FilipCordas makes a lot of sense Filip, thank you very much for replying

    • @TheGryphon14
      @TheGryphon14 Před 3 lety

      @@FilipCordas so the point is, make sure our site doesn't have any xss vulnerabilities right?

    • @FilipCordas
      @FilipCordas Před 3 lety

      @@TheGryphon14 Well sure you should not have any xss on your web app but sometimes things get overlooked so it's always best to to try and allow minimal amount damage even if you have a security flaw.

  • @nyume815
    @nyume815 Před 3 lety +1

    I'm always hungry so I get cookies

  • @elmehdiaa2882
    @elmehdiaa2882 Před 4 lety

    does the use of Auth0 solve the problem?

  • @KiwiCoke
    @KiwiCoke Před 2 lety

    Encrypting values in localstorage is a great option

  • @UTonesOfficial
    @UTonesOfficial Před 4 lety

    Hey Ben, thanks for all your vids. I have this idea, I don't know if this will work, just a newbie here trying to learn things and all. What if before we store the token locally, we encrypt it first, so that the available "token" locally is not the actual token itself. You know, just thinking. Sorry, newbie here.

    • @bawad
      @bawad  Před 4 lety +1

      Same problem, I'll just send the encrypted token to the server

    • @midsummerstation3345
      @midsummerstation3345 Před 4 lety +3

      The jwt token itself is encrypted by default

  • @AshwinKJosephperez
    @AshwinKJosephperez Před 3 lety

    Can we not restrict the domain to which the cookies are sent?

    • @TheGryphon14
      @TheGryphon14 Před 3 lety

      we can. developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Set-Cookie/SameSite

  • @JLarky
    @JLarky Před 4 lety +3

    Big oof.
    1. csrf tokens in headers
    2. http only, secure cookies
    3. content policy
    p.s. bonus point, Google PASETO

  • @dpaulflavius
    @dpaulflavius Před 3 lety

    I hope till today, you won't save jwt in localStorage :))

  • @Yahyazini
    @Yahyazini Před 4 lety

    Cookies are definitely better for storing jwt tokens with the added level of security using HttpOnly which prevents JS from seeing the cookie and Same-Site which only allows same domain to see the cookie. But again if you're writing code that's vulnerable there's no helping that.

  • @MrTarantino47
    @MrTarantino47 Před 4 lety +1

    Hey Ben, thanks for the video!
    Can we store our JWT token in .env file?

    • @bawad
      @bawad  Před 4 lety +1

      The token itself?!

    • @MrTarantino47
      @MrTarantino47 Před 4 lety

      Ben Awad , yes

    • @bawad
      @bawad  Před 4 lety +3

      why would you want to do that?

    • @hannad
      @hannad Před 4 lety

      No no no noooooooo

    • @weltmeister
      @weltmeister Před 4 lety +4

      I'm curious to how did you get that idea?

  • @timothyebiuwhe5209
    @timothyebiuwhe5209 Před 4 lety

    Have you tried setting the httpOnly flag on your cookies?

    • @Chaosweaver667
      @Chaosweaver667 Před 4 lety

      From what I recall, it's up to the browsers to abide by httpOnly, not an actual rule. I'm pretty sure most cookie extensions allow you to modify httpOnly cookies. I could be completely wrong.

    • @31redorange08
      @31redorange08 Před 4 lety

      To achieve what?

  • @VishnuASankaran
    @VishnuASankaran Před 3 lety

    You should do HTTP only cookies!

  • @DiogoOliveira-kz7wu
    @DiogoOliveira-kz7wu Před 4 lety

    what is the solution?

    • @bawad
      @bawad  Před 4 lety +4

      protect against xss the best you can cheatsheetseries.owasp.org/cheatsheets/Cross_Site_Scripting_Prevention_Cheat_Sheet.html

    • @carlosjosejimenezbermudez9255
      @carlosjosejimenezbermudez9255 Před 4 lety

      @@bawad Also, look into Identity Server 4 and OpenId Connect. Okta as an Auth provider is a potential solution.

  • @tambolaking5383
    @tambolaking5383 Před 4 lety

    One can run javascript even by editing inspect > element

  • @nomadshiba
    @nomadshiba Před 3 lety

    why not just use CSP: connect-src?
    try to send a fetch request on twitter, somewhere other than twitter

  • @TowfiqIslam1
    @TowfiqIslam1 Před 4 lety +1

    What about storing the JWT in Redux Store?

    • @RafaKoodziejczyk
      @RafaKoodziejczyk Před 4 lety

      Isn't redux store just using localStorage as it's backend? (Yes, you probably can change backend storage, but still it's still the same, as user JavaScript have access to the same data in that domain however it's executed or wrapped, until it's an in-memory storage as it's only one that can't be accessed by injected third party code.)

    • @z-aru
      @z-aru Před 4 lety

      Once you close the tab, the token will be gone.
      Unless you have some session mechanism like refreshToken, you still need to store the refreshToken

    • @hatrick3117
      @hatrick3117 Před 4 lety +1

      That is what he refered as "storing in memory", so it's all the same :)

  • @jairodavemejia4057
    @jairodavemejia4057 Před rokem

    use BFF instead, don't trust the client ever

  • @vitor14
    @vitor14 Před 4 lety +1

    I think a good way to fight against xss maybe is save some sort of device information hash, detect if the device changed to ask re enter the password.

    • @filipitskov3742
      @filipitskov3742 Před 4 lety +1

      Sry, what?🧐 Can you please explain what you meant here because i cant get a thing

    • @TheAngoRun
      @TheAngoRun Před 4 lety +4

      The device itself doesn't change. Attacker performs the attack on behalf of the user.

    • @vitor14
      @vitor14 Před 4 lety

      @@filipitskov3742 If I understood correctly the idea of the xss attack is to obtain the credentials to impersonate the user and to be able to access their personal data. So if we keep some kind of extra information, such as device information, or places where the user is usually connected, it would be easy to identify if someone is trying to enter with that stolen token.

    • @dealloc
      @dealloc Před 4 lety +2

      @@vitor14 Now you have other problems, especially in EU (GDPR). But that aside, this wouldn't solve your problem; any client-side information can be changed/faked-this is easy for an attacker to research before doing the attack, so you haven't really solved a problem.
      The best thing you can do is treat the client as always potentially malicious. Don't trust the client. Always sanitize data before passing the data through any of your services (validation, parsing, etc.). XSS may be the least of your problems.

  • @volkanakincom
    @volkanakincom Před 2 lety

    The title of the video is misleading. This video is about xss. But you get attention from people to watch the vide bu giving a wrong title.

  • @nickwoodward819
    @nickwoodward819 Před 4 lety

    I'm new to all this, but the OWASP cheat sheet seems to say you can defend against this using a 'fingerprint' or user context: github.com/OWASP/CheatSheetSeries/blob/master/cheatsheets/JSON_Web_Token_Cheat_Sheet_for_Java.md#token-sidejacking
    Explained a bit better here in the update this year: stackoverflow.com/questions/54258233/do-i-have-to-store-tokens-in-cookies-or-localstorage-or-session
    Would love to see a JS implementation of the first link

    • @bawad
      @bawad  Před 4 lety

      that'll protect you if they steal the token and try making requests on their on server
      but they can just make requests from your browser

    • @nickwoodward819
      @nickwoodward819 Před 4 lety

      @@bawad Well that sucks. So you're saying that just simply storing a JWT token is no less safe than any other available option? I guess I should just make sure that any important action requires actual login credentials?
      Thanks for the videos btw, great help!

    • @bawad
      @bawad  Před 4 lety +1

      1. From what I could figure out, if your vulnerable to XSS you're screwed no matter how you store your token
      2. That's a good idea

    • @nickwoodward819
      @nickwoodward819 Před 4 lety

      @@bawad Yeah, from what I've read the past couple of days you're right.
      RE an admin account - Does creating a local server that they log into, which then communicates with the webserver, cutting out the browser, sound like a good approach?

    • @bawad
      @bawad  Před 4 lety

      If your building a website, I don't think having it communicate with a local server adds much value

  • @eddie_writes96
    @eddie_writes96 Před 4 lety

    Clean your inputs y'all. Don't let your users write any javascript.

    • @eddie_writes96
      @eddie_writes96 Před 4 lety

      But even if we clean our inputs, team black hat would still be able to munipulate the DOM.

  • @Vaielab
    @Vaielab Před 4 lety

    So here is my 2 cents (and I might be completly wrong here, and I havent seen your other video about this yet)
    When you store your information in localstorage, you can get your session stolen. So someone else can be connected as you and do some sort of multi-step hack (do a request, have to wait for someone to accept your request do something else). And they can do it at anytime of the day when ever they want to.
    If you store your information in a http only cookie, the only time you can get hacked, is when you are currently on a hacked paged. As soon as you close the page, the hack is over. There is no way for the hacker to make other requests.
    With this idea, if you hacked thousands of account that were stored in localstorage, you could later launch a attack against the website where everybody do the same action at the same time, but if you used http only cookie, even if you haved hacker thousands of account, there might be only 20 currently online that will launch the attack.
    But then again, not a security expert, and I might be wrong.

    • @RafaKoodziejczyk
      @RafaKoodziejczyk Před 4 lety

      You are correct, but still it's all about a target, if your page is using cookie and to do an action you need just to execute a GET request then you can just post an image with the URL and once person open page with that image that action is done, and this works with cookies even if your site doesn't have any XSS vuln.
      For example to delete account your site just need to execute GET /user/delete/123
      Then simple image on external site would remove that user, while storing cookie in storage then this attack would fail as you need to send with token that attacker doesn't have on every request.
      So for critical requests you should avoid using get, use POST instead and validate http referer.
      But overall if your site have xss then your users are screwed, and it's better to use cookies but with httponly and secure flags, as it deny JS access to cookies and prevents sending cookies plain text without encryption. Or even use both ;)

  • @subvind
    @subvind Před 4 lety

    look up the definitions. one is time based (session/activity) the other is space based (local/area).

  • @MikeEnRegalia
    @MikeEnRegalia Před 4 lety +1

    Lol - of course it’s not hard to write a vulnerable react app if you use dangerouslySetInnerHtml. Duh.

  • @MrSkinkarde
    @MrSkinkarde Před 4 lety

    get to the point.. ahhmm ahhhm jesus christ these people on youtube. 15minutes of boredom.