Security - fidransky/kiv-pia-labs GitHub Wiki
TOTD:
- authentication vs. authorization
- explore common security vulnerabilities
- secure a web app using Spring Security
Security in general is a broad problem but an integral part of every web application. When creating a web application, all of its parts must be secured. It's not enough to secure e.g. the front-end/HTML part and leave the server open to public.
Rather than trying to solve each known security vulnerability separately, it's better to first define a problem and then find ways to prevent it.
Authentication is the act of validating that users are whom they claim to be. This is the first step in any security process.
Complete an authentication process with:
- passwords
- one-time password (OTP)
- authentication apps
- biometrics
In some instances, systems require the successful verification of more than one factor before granting access. This multi-factor authentication (MFA) requirement is often deployed to increase security beyond what passwords alone can provide.
Authorization in system security is the process of giving the user permission to access a specific resource or function. This term is often used interchangeably with access control or client privilege.
Currently, our chat rooms web app is not secured in any way (almost). We'll see why it's a problem, then fix it.
Cross-Site Scripting (XSS) attacks are a type of injection, in which malicious scripts are injected into otherwise benign and trusted websites. XSS attacks occur when an attacker uses a web application to send malicious code, generally in the form of a browser side script, to a different end user. Flaws that allow these attacks to succeed are quite widespread and occur anywhere a web application uses input from a user within the output it generates without validating or encoding it.
There are two types of XSS attacks:
- Reflected or Nonpersistent XSS
- Stored or Persistent XSS
Reflected XSS
In Reflected or Nonpersistent XSS, untrusted user data is submitted to a web application, which is immediately returned in the response, adding untrustworthy content to the page. The web browser assumes the code came from the web server and executes it. This might allow a hacker to send you a link that, when followed, causes your browser to retrieve your private data from a site you use and then make your browser forward it to the hacker's server.
http://localhost:8080/hello?from=<script>alert('Reflected XSS');</script>
Stored XSS
In Stored or Persistent XSS, the attacker's input is stored by the webserver. Subsequently, any future visitors may execute that malicious code.
<script>window.addEventListener('DOMContentLoaded', () => { document.querySelector('#descriptionField').value = 'Stored XSS'; document.forms[1].submit(); });</script>
Cross-Site Request Forgery (CSRF) is an attack that forces an end user to execute unwanted actions on a web application in which they’re currently authenticated. With a little help of social engineering (such as sending a link via email or chat), an attacker may trick the users of a web application into executing actions of the attacker’s choosing. If the victim is a normal user, a successful CSRF attack can force the user to perform state changing requests like transferring funds, changing their email address, and so forth. If the victim is an administrative account, CSRF can compromise the entire web application.
https://jsbin.com/kugawaqeji/edit?html,js,output
Add org.springframework.boot:spring-boot-starter-security
dependency to pia-labs-core module.
Spring Security authentication consists of implementing two interfaces in custom application classes:
- in
User
domain class, implementorg.springframework.security.core.userdetails.UserDetails
interface - in
UserService
service class, implementorg.springframework.security.core.userdetails.UserDetailsService
interface (Spring MVC)
Additionally, you'd need to implement UserRepository
so that UserService
can actually retrieve the stored user data from its findByUsername
method.
Finally, implement getCurrentUser
method in UserService
to retrieve the currently authenticated user from security context (Spring MVC):
public User getCurrentUser() {
var authentication = SecurityContextHolder.getContext().getAuthentication();
if (authentication.getPrincipal() instanceof UserDetails user) {
return (User) loadUserByUsername(user.getUsername());
}
throw new IllegalStateException("Authentication principal is not a supported user object.");
}
Create a new @Configuration
class called SecurityConfigation
in pia-labs_ui module.
Add @EnableWebSecurity(debug = true)
annotation to the SecurityConfigation
class.
Define a SecurityFilterChain
bean using HttpSecurity
as its dependency (Spring MVC):
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
return http
.formLogin(AbstractAuthenticationFilterConfigurer::permitAll)
.logout(LogoutConfigurer::permitAll)
.authorizeHttpRequests(configurer -> configurer
.requestMatchers("/hello").permitAll()
.anyRequest().authenticated()
)
.build();
}
With the authentication now implemented in core and web layer, we'll continue by printing the current user's username in the server-side rendered UI.
Additionally, we'll add a logout link leading to the Spring Security-generated logout page.
Add org.thymeleaf.extras:thymeleaf-extras-springsecurity6
dependencies to pia-labs-ui module.
In layout.html
:
- Add security XML namespace to the HTML tag:
xmlns:sec="http://www.thymeleaf.org/extras/spring-security"
- Print current user's username in navbar:
<th:block sec:authentication="name" />
- Add logout button to navbar:
<a th:href="@{/logout}">Log out</a>
- https://www.okta.com/identity-101/authentication-vs-authorization/
- https://www.baeldung.com/spring-prevent-xss
- https://owasp.org/www-community/attacks/csrf
- https://spring.io/blog/2022/02/21/spring-security-without-the-websecurityconfigureradapter
- https://docs.spring.io/spring-security/reference/reactive/getting-started.html
- https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/X-XSS-Protection#browser_compatibility