Skip to content
Snippets Groups Projects
Commit 4f0c8141 authored by Seb Barnard's avatar Seb Barnard :speech_balloon:
Browse files

Merge branch 'develop' into 'issueTwelve'

Develop

See merge request !41
parents cabd504f 9b1bc9c1
No related branches found
No related tags found
7 merge requests!56tags will be saved to userFavTags table (needs user ID of current logged in user),!50Merging for latest changes,!46Develop,!44Branch update,!43Develop,!42Issue twelve,!41Develop
......@@ -23,6 +23,8 @@ repositories {
}
dependencies {
implementation 'io.jsonwebtoken:jjwt:0.9.1'
implementation 'org.springframework.session:spring-session-jdbc:2.4.3'
implementation 'org.springframework.boot:spring-boot-starter-validation'
implementation 'org.springframework.boot:spring-boot-starter-data-jdbc'
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
......
package com.example.clientproject.service.Utils;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.JwtBuilder;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import javax.crypto.spec.SecretKeySpec;
import javax.servlet.http.HttpSession;
import javax.xml.bind.DatatypeConverter;
import java.security.Key;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Optional;
@Component
public class JWTUtils {
private static String SECRET_KEY;
@Value("${jwt.secret_key}")
private void setSECRET_KEY(String aSECRET_KEY){
SECRET_KEY = aSECRET_KEY;
}
public static void getKey(){
System.out.println(SECRET_KEY);
}
// https://github.com/oktadev/okta-java-jwt-example/blob/master/src/main/java/com/okta/createverifytokens/JWTDemo.java
public static String createJWT(String id, String issuer, String subject, long ttlMillis) {
//The JWT signature algorithm we will be using to sign the token
SignatureAlgorithm signatureAlgorithm = SignatureAlgorithm.HS256;
long nowMillis = System.currentTimeMillis();
Date now = new Date(nowMillis);
//We will sign our JWT with our ApiKey secret
byte[] apiKeySecretBytes = DatatypeConverter.parseBase64Binary(SECRET_KEY);
Key signingKey = new SecretKeySpec(apiKeySecretBytes, signatureAlgorithm.getJcaName());
//Let's set the JWT Claims
JwtBuilder builder = Jwts.builder().setId(id)
.setIssuedAt(now)
.setSubject(subject)
.setIssuer(issuer)
.signWith(signatureAlgorithm, signingKey);
//if it has been specified, let's add the expiration
if (ttlMillis >= 0) {
long expMillis = nowMillis + ttlMillis;
Date exp = new Date(expMillis);
builder.setExpiration(exp);
}
//Builds the JWT and serializes it to a compact, URL-safe string
return builder.compact();
}
public static Claims decodeJWT(String jwt) {
//This line will throw an exception if it is not a signed JWS (as expected)
Claims claims = Jwts.parser()
.setSigningKey(DatatypeConverter.parseBase64Binary(SECRET_KEY))
.parseClaimsJws(jwt).getBody();
return claims;
}
public static String makeUserJWT(Integer userId, HttpSession session) {
String jwtId = "loginCred";
String jwtIssuer = "ShopHub";
int jwtTimeToLive = 800000;
String jwt = JWTUtils.createJWT(
jwtId, // claim = jti
jwtIssuer, // claim = iss
userId.toString(), // claim = sub
jwtTimeToLive // used to calculate expiration (claim = exp)
);
session.setAttribute("loginCredJWT", jwt);
return jwt.toString();
}
public static Optional<Integer> getLoggedInUserId(HttpSession session){
String loginJWT = (String) session.getAttribute("loginCredJWT");
if (loginJWT == null) {
System.out.println("Jwt is null");
return Optional.empty();
}
try{
Claims claims = JWTUtils.decodeJWT(loginJWT);
return Optional.of(Integer.parseInt(claims.getSubject()));
}catch (io.jsonwebtoken.MalformedJwtException e){
System.out.println("malformed jwt");
return Optional.empty();
}catch (io.jsonwebtoken.SignatureException e){
System.out.println("JWT was edited outside this scope");
return Optional.empty();
}catch (Exception e){
System.out.println(e);
return Optional.empty();
}
}
public static void logOutUser(HttpSession session){
session.removeAttribute("loginCredJWT");
}
}
package com.example.clientproject.web.controllers;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
@Controller
public class Redirect {
@GetMapping("/redirect")
public String redirect(@RequestParam(name="url") String url){
try{
return "redirect:/"+url;
}catch(Exception e){
return "redirect:/";
}
}
}
package com.example.clientproject.web.controllers;
import com.example.clientproject.data.users.Users;
import com.example.clientproject.service.Utils.JWTUtils;
import io.jsonwebtoken.Claims;
import org.dom4j.rule.Mode;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import javax.servlet.http.HttpSession;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
@Controller
public class SessionTestController {
@GetMapping("/sessionJWTTest")
public String jwtTest(Model model, HttpSession session){
Optional<Integer> user = JWTUtils.getLoggedInUserId(session);
if(user.isPresent()){
System.out.println(user.get());
}else{
System.out.println("No User");
}
System.out.println("Making jwt");
String jwt = JWTUtils.makeUserJWT(6, session);
System.out.println(jwt);
user = JWTUtils.getLoggedInUserId(session);
if(user.isPresent()){
System.out.println(user.get());
}else{
System.out.println("No User");
}
model.addAttribute("sessionData",user.get());
return "session-test";
}
}
package com.example.clientproject.web.controllers;
import com.example.clientproject.exceptions.ForbiddenErrorException;
import com.example.clientproject.service.Utils.JWTUtils;
import com.example.clientproject.service.dtos.UsersDTO;
import com.example.clientproject.service.searches.UsersSearch;
import com.example.clientproject.services.BusinessRegisterDTO;
......@@ -17,6 +18,7 @@ import org.springframework.web.bind.annotation.Mapping;
import org.springframework.web.bind.annotation.PostMapping;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import javax.validation.Valid;
import java.util.ArrayList;
import java.util.Arrays;
......@@ -42,7 +44,7 @@ public class SignInController {
return "registerbusiness.html";
}
saveBusiness.save(new BusinessRegisterDTO(brf));
return "redirect:/businessRegister";
return "redirect:/redirect?url=businessRegister";
}
@GetMapping("/businessRedirect")
......@@ -114,4 +116,16 @@ public class SignInController {
return "redirect:/dashboard";
}
/**
*
* @param model
* @param session the http session of the browser accessing the site
* @return returns a redirect to the login page after clearing the session jwt
*/
@GetMapping("/log_out")
public String jwtLogout(Model model, HttpSession session){
JWTUtils.logOutUser(session);
return "redirect:/login";
}
}
......@@ -8,4 +8,10 @@ spring.datasource.password=comsc
spring.datasource.driver-class-name=org.mariadb.jdbc.Driver
spring.mvc.ignore-default-model-on-redirect=true
\ No newline at end of file
spring.mvc.ignore-default-model-on-redirect=true
spring.session.store-type=jdbc
spring.session.jdbc.initialize-schema=always
spring.session.timeout.seconds=900
jwt.secret_key=xfVBfHdprpZqn73pbPotfLyBXNR8IWZ7MxhD59sFuBB7QjnLnWppFiZp6Yhu
\ No newline at end of file
......@@ -39,7 +39,7 @@
Business
</a>
<hr class="navbar-divider">
<a class="navbar-item">
<a class="navbar-item" href="/log_out">
<span class="icon mr-2"><i class="fas fa-sign-out-alt"></i></span>
Log Out
</a>
......
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Session Test</title>
</head>
<body>
<p th:text="${sessionData}"></p>
</body>
</html>
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment