Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 34 additions & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,40 @@
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-stdlib</artifactId>
</dependency>

<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-api</artifactId>
<version>0.11.5</version>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-impl</artifactId>
<scope>runtime</scope>
<version>0.11.5</version>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-jackson</artifactId>
<scope>runtime</scope>
<version>0.11.5</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>jakarta.inject</groupId>
<artifactId>jakarta.inject-api</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
Expand Down
28 changes: 27 additions & 1 deletion src/main/kotlin/com/coded/spring/ordering/Application.kt
Original file line number Diff line number Diff line change
@@ -1,10 +1,36 @@
package com.coded.spring.ordering

import org.springframework.boot.CommandLineRunner
import org.springframework.boot.autoconfigure.SpringBootApplication
import org.springframework.boot.runApplication
import org.springframework.context.annotation.Bean
import org.springframework.context.annotation.ComponentScan
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder
import org.springframework.security.crypto.password.PasswordEncoder

@SpringBootApplication
class Application
@ComponentScan("com.example.authentication")

class Application{


@Bean
fun initUsers(userRepository: UsersRepository, passwordEncoder: PasswordEncoder) = CommandLineRunner {
val user = UserEntity(
name = "HelloUser",
username = "testuser",
password = passwordEncoder.encode("password123"),
age = 18,
role = Roles.USER
)
if (userRepository.findByUsername(user.username) == null) {
println("Creating user ${user.username}")
userRepository.save(user)
} else {
println("User ${user.username} already exists")
}
}
}

fun main(args: Array<String>) {
runApplication<Application>(*args)
Expand Down
13 changes: 13 additions & 0 deletions src/main/kotlin/com/coded/spring/ordering/HelloWorld.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package com.coded.spring.ordering

import org.springframework.web.bind.annotation.GetMapping
import org.springframework.web.bind.annotation.RestController

@RestController
class HelloWorld {

@GetMapping("/Hello")
fun sayingHello(): String{
return "Hello World ,, najla"
}
}
46 changes: 46 additions & 0 deletions src/main/kotlin/com/coded/spring/ordering/OnlineOrdering.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
package com.coded.spring.ordering

import org.springframework.web.bind.annotation.GetMapping
import org.springframework.web.bind.annotation.PostMapping
import org.springframework.web.bind.annotation.RequestBody
import org.springframework.web.bind.annotation.RestController

@RestController
class OnlineOrdering (val ordersRepositry: OrdersRepositry){



// var customerOrd://customerOrder("ali","pizza hut", listOf("pizza", "chicken wings" , "pepsi") )

var customerOrdList = mutableListOf<customerOrder>()
@PostMapping("/order")
fun order(@RequestBody newOrder: customerOrder): String{
customerOrdList.add(newOrder)
return "your order submitted"
}

@GetMapping("/order")
fun allOrder (): List<customerOrder>{
return customerOrdList
}

@PostMapping("/orderDB")
fun orderDB (@RequestBody newOrder: customerOrderDB){
var theOrder= OrdersEntity()
theOrder.userId = newOrder.userId
theOrder.resturant = newOrder.resturant
theOrder.items = newOrder.items
ordersRepositry.save(theOrder)

}

@GetMapping("/orderDB")
fun orderDB ():List<OrdersEntity>{
var allOrderDB = OrdersEntity()
return ordersRepositry.findAll()
}
}


data class customerOrder(var user: String,var resturant: String , var items: List<String>)
data class customerOrderDB(var userId: Int,var resturant: String , var items: String)
21 changes: 21 additions & 0 deletions src/main/kotlin/com/coded/spring/ordering/OrdersEntity.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package com.coded.spring.ordering

import jakarta.persistence.*
import org.springframework.data.jpa.repository.JpaRepository
import org.springframework.stereotype.Repository

@Repository
interface OrdersRepositry : JpaRepository<OrdersEntity,Int>
@Entity
@Table(name = "orders")
data class OrdersEntity (
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
val id: Int,
var userId: Int,
var resturant: String,
var items: String
){
constructor(): this (0,0,"","")

}
29 changes: 29 additions & 0 deletions src/main/kotlin/com/coded/spring/ordering/UserEntity.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
package com.coded.spring.ordering

import jakarta.persistence.*
import org.springframework.data.jpa.repository.JpaRepository
import org.springframework.stereotype.Repository

@Repository
interface UsersRepository: JpaRepository<UserEntity,Int>{
fun findByUsername(username: String): UserEntity?
}

@Entity
@Table(name = "users")
data class UserEntity(
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
val id: Int? = null ,
var name: String,
var age: Int,
var username: String,
var password: String,
@Enumerated(EnumType.STRING)
val role: Roles = Roles.USER) {
constructor() : this(0, "name", 0, "username", "password", Roles.USER)
}

enum class Roles{
USER,ADMIN
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package com.example.authentication

import com.coded.spring.ordering.UsersRepository
import org.springframework.security.core.userdetails.*
import org.springframework.stereotype.Service

@Service
class CustomUserDetailsService(
private val usersRepository: UsersRepository
) : UserDetailsService {
override fun loadUserByUsername(username: String): UserDetails {
val user = usersRepository.findByUsername(username)
?: throw UsernameNotFoundException("User not found")

return User.builder()
.username(user.username)
.password(user.password)
.roles(user.role.toString())
.build()
}
}
58 changes: 58 additions & 0 deletions src/main/kotlin/com/example/authentication/SecurityConfig.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
package com.example.authentication

import com.example.authentication.jwt.JwtAuthenticationFilter
import org.springframework.context.annotation.Bean
import org.springframework.context.annotation.Configuration
import org.springframework.security.authentication.AuthenticationManager
import org.springframework.security.authentication.AuthenticationProvider
import org.springframework.security.authentication.dao.DaoAuthenticationProvider
import org.springframework.security.config.annotation.authentication.configuration.AuthenticationConfiguration
import org.springframework.security.config.annotation.web.builders.HttpSecurity
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity
import org.springframework.security.config.http.SessionCreationPolicy
import org.springframework.security.core.userdetails.UserDetailsService
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder
import org.springframework.security.crypto.password.PasswordEncoder
import org.springframework.security.web.SecurityFilterChain
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter



@Configuration
@EnableWebSecurity
class SecurityConfig(
private val jwtAuthFilter: JwtAuthenticationFilter,
private val userDetailsService: UserDetailsService
) {

@Bean
fun securityFilterChain(http: HttpSecurity): SecurityFilterChain {
http.csrf { it.disable() }
.authorizeHttpRequests {
it.requestMatchers("/auth/**").permitAll()
.anyRequest().authenticated()
}
.sessionManagement {
it.sessionCreationPolicy(SessionCreationPolicy.STATELESS)
}
.authenticationProvider(authenticationProvider())
.addFilterBefore(jwtAuthFilter, UsernamePasswordAuthenticationFilter::class.java)

return http.build()
}

@Bean
fun passwordEncoder(): PasswordEncoder = BCryptPasswordEncoder()

@Bean
fun authenticationManager(config: AuthenticationConfiguration): AuthenticationManager =
config.authenticationManager

@Bean
fun authenticationProvider(): AuthenticationProvider {
val provider = DaoAuthenticationProvider()
provider.setUserDetailsService(userDetailsService)
provider.setPasswordEncoder(passwordEncoder())
return provider
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package com.example.authentication.jwt

import org.springframework.security.authentication.*
import org.springframework.security.core.userdetails.UserDetailsService
import org.springframework.security.core.userdetails.UsernameNotFoundException
import org.springframework.web.bind.annotation.*


@RestController
@RequestMapping("/auth")
class AuthenticationController(
private val authenticationManager: AuthenticationManager,
private val userDetailsService: UserDetailsService,
private val jwtService: JwtService
) {

@PostMapping("/login")
fun login(@RequestBody authRequest: AuthenticationRequest): AuthenticationResponse {
val authToken = UsernamePasswordAuthenticationToken(authRequest.username, authRequest.password)
val authentication = authenticationManager.authenticate(authToken)

if (authentication.isAuthenticated) {
val userDetails = userDetailsService.loadUserByUsername(authRequest.username)
val token = jwtService.generateToken(userDetails.username)
return AuthenticationResponse (token)
} else {
throw UsernameNotFoundException("Invalid user request!")
}
}
}

data class AuthenticationRequest(
val username: String,
val password: String
)

data class AuthenticationResponse(
val token: String
)
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package com.example.authentication.jwt

import jakarta.servlet.FilterChain
import jakarta.servlet.http.*
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken
import org.springframework.security.core.context.SecurityContextHolder
import org.springframework.security.core.userdetails.UserDetailsService
import org.springframework.security.web.authentication.WebAuthenticationDetailsSource
import org.springframework.stereotype.Component
import org.springframework.web.filter.OncePerRequestFilter

@Component
class JwtAuthenticationFilter(
private val jwtService: JwtService,
private val userDetailsService: UserDetailsService
) : OncePerRequestFilter() {

override fun doFilterInternal(
request: HttpServletRequest,
response: HttpServletResponse,
filterChain: FilterChain
) {
val authHeader = request.getHeader("Authorization")
if (authHeader == null || !authHeader.startsWith("Bearer ")) {
filterChain.doFilter(request, response)
return
}

val token = authHeader.substring(7)
val username = jwtService.extractUsername(token)

if (SecurityContextHolder.getContext().authentication == null) {
if (jwtService.isTokenValid(token, username)) {
val userDetails = userDetailsService.loadUserByUsername(username)
val authToken = UsernamePasswordAuthenticationToken(
userDetails, null, userDetails.authorities
)
authToken.details = WebAuthenticationDetailsSource().buildDetails(request)
SecurityContextHolder.getContext().authentication = authToken
}
}

filterChain.doFilter(request, response)
}
}
Loading