Homework 4 Reflection

Authentication

1. What did you struggle with when adding authorization to your back end?

We practiced authorization in Activity 4a, so I had a rough idea of how to implement authorization to my back-end. But, unlike Activity 4a, I used database tables to handle the tokens in the back-end. At first, it was unclear how to set up the users and tokens tables. Originally, the table had a token column and a username column. This is because I had my authorization routes (/register, /login, /logout) handling two cookies: one containing the authorization token and another containing the account username (for front-end purposes). But, I learned that it is more typical to have a user_id column rather than a username column (since user ids usually don't change). It took a bit of time to refactor my code for this change.

I also had a hard time remembering where the password should be plaintext and where the password should be hashed. In my tests, I was originally inserting the plaintext password into my database (when it should be the hashed password). I also made this mistake in my "npm run data" shell script.Additionally, for the function argon2.verify(hashed, plaintext), the first argument is the hashed password and the second argument is the plaintext password. At first, I had the two arguments switched.

2. What did you struggle with when adding authorization to your front end?

At first, I wasn't sure how to type the authorization routes axios calls in the front-end. I tried finding out if I could specify that the endpoint returns cookies. However, the type you give to axios calls refers to the response body type only. Cookies are sent with Set-Cookie headers and not in the response body, so this is not posible. Afterwards, I had the return type as "{}". However, the server terminal started warning that this matched any non-nullish object. As it turns out, a return type of "void" is the most appropriate option for my authorization routes since I am not returning any response body.

Originally, I thought about adding the logout functionality as just a link in the navigation bar. However, I could not figure out a way to do that. So, I decided to make an account page that had a logout button. This method would also help prevent accidental logouts, so I think this is an appropriate way to handle logging out.

Deployment

1. What did you struggle with when deploying your app to the internet?

For a while, I was visiting https://www.books.miyatoodles.space/ and nothing was returned to my browser. After some experimentation, I discovered that https://books.miyatoodles.space/ worked.I didn't add a CNAME DNS record to say that https://www.books.miyatoodles.space/ (with the www) is the same as https://books.miyatoodles.space/ (without the www). Now, both links are working as expected (after I added the CNAME DNS record).

Security Audit

1. If your app was vulnerable to XSS attacks, explain what you did to mitigate them. If it wasn't, explain why.

I attempted to submit JavaScript (<script>alert("Hello")</script>) into several input fields in my website, including into the username of a new account and the name of a new author. I did not find any issues with the JavaScript being executed when I navigated to a webpage that displayed the username or viewed the authors table. Some security settings, such as the Content-Security-Policy header, may have helped prevent the XSS attacks I tried to do.

2. If your app was vulnerable to CSRF attacks, explain what you did to mitigate them. If it wasn't, explain why.

I went to my production website, logged in, copied the token from my cookies, and then attempted to do the following curl on my local machine:

curl -X POST -H "Content-Type:application/json" -H "Cookie: token=(TOKEN)" -d "{\"author_id\": 7, \"title\": \"The Dark Tower: The Gunslinger\", \"pub_year\": \"1982\", \"genre\": \"adventure\"}" http://books.miyatoodles.space/book

I found that the attempt was unsuccessful.

3. If you added rate limiting with a firewall, include what commands you ran/packages you used. If you added rate limiting to your application code, indicate this.

I did not add rate limiting with a firewall. Instead, I added it to my application code using the express-rate-limit package. I limited it to 50 API requests within a 15 minute window, which I believe is enough for this application. I tested it by repeatingly updating the same book. After 50 API requests, I received HTTP 429 Too Many Requests errors (as expected).

4. Explain what HTTP headers you set, what they do, and why they're useful.

I used the Helmet package to automatically add HTTP headers. I used its default settings that are detailed below. Not all are needed for my application, but I decided to use Helmet's defaults for ease of implementation.

1) Content-Security-Policy: default-src 'self';base-uri 'self';font-src 'self' https: data:;form-action 'self';frame-ancestors 'self';img-src 'self' data:;object-src 'none';script-src 'self';script-src-attr 'none';style-src 'self' https: 'unsafe-inline';upgrade-insecure-requests

- It limits what sources the website will execute as JavaScript code. This helps defend against cross-site scripting attacks (XSS), which is when an attack submits JavaScript code into an input in a website and it then gets executed when it is viewed by other users.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/CSP

2) Cross-Origin-Embedder-Policy: This header is not set by default.

- Requires that CORP or CORS headers to be set for the website to load cross-site resources. This controls whether or not websites load resources from other sources.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Cross-Origin-Embedder-Policy

3) Cross-Origin-Opener-Policy: same-origin

- Ensures that one website that opens another website using Window.open() does not share the same browsing context group (BCG). This limits the information shared between the two websites and prevents XS-Leaks.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Cross-Origin-Opener-Policy

4) Cross-Origin-Resource-Policy: same-origin

- Blocks no-cors cross-origin or cross-site requests to a resource within a website. This helps prevent other websites from accessing a website's resource.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Cross-Origin-Resource-Policy

5) Origin-Agent-Cluster: ?1

- Web pages of the same origin are separate processes of web pages of different origins. This helps prevent one resource-intensive web page from degrading web pages from other origins.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Origin-Agent-Cluster

6) Referrer-Policy: no-referrer

- Controls what information is set in the Referer request header. no-referrer means no referer header is sent, so the destination website does not know any information about the source website.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Referrer-Policy

7) Strict-Transport-Security: max-age=31536000; includeSubDomains

- The host should only be accessed using HTTPS. Future HTTP requests should be automatically upgraded to HTTPS. This helps ensure encryption is enabled.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Strict-Transport-Security

8) X-Content-Type-Options: nosniff

- Browsers should not alter the Content-Type headers sent by the server. This preevents MIME type sniffing, which can be a security concern since some MIME types are executibles.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/X-Content-Type-Options

9) X-DNS-Prefetch-Control: off

- Disables DNS prefetching where browsers look up DNS resolution on links the user may choose to click on (and URLs for items such as images, CSS, JavaScript, etc.). It improves user privacy since there is no prefetching calls, but it does decrease performance.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/X-DNS-Prefetch-Control

10) X-Download-Options: noopen

- For Internet Explorer 8. Users are unable to open a file download within a website. Users must save the file locally and then open it. This prevents users from executing the file download within a website's seurity context and doing a script injection.

- https://learn.microsoft.com/en-us/archive/blogs/ie/ie8-security-part-v-comprehensive-protection

11) X-Frame-Options: SAMEORIGIN

- Allows a website to only be embedded into an iframe if the surrounding web page is of the same origin. This helps prevent clickjacking, which is when a user unknowingly interacts with a webpage that they did not intend to interact with (potentially causing confidential information to be stolen).

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/X-Frame-Options

12) X-Permitted-Cross-Domain-Policies: none

- Controls cross-origin access with Adobe Flash Player and Microsoft Silverlight. This prevents cross-origin access from these applications.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/X-Permitted-Cross-Domain-Policies

13) X-Powered-By: The X-Powered-By header, if present, is removed.

- This header is set by default in Express and other frameworks. This is mainly removed to save bandwidth.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/X-Powered-By

14) X-XSS-Protection: 0

- Previously, browsers stopped pages from loading when they detected reflected cross-site scription (XSS attacks). However, this header is not needed anymore thanks to the Content-Security-Policy header. Thus, this header is disabled.

- https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/X-XSS-Protection

5. If you did anything else to secure your app, explain what you did and why.

I did not add anything else to secure my application, but I'm always willing to learn more about security features.

Home